谷歌浏览器的源码分析 34

Posted skiwnchh

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了谷歌浏览器的源码分析 34相关的知识,希望对你有一定的参考价值。

通过上一次的分析,我们看到所有网页数据经过html分析器之后,都会变成一个一个RenderObject对象,那么这些RenderObject对象又是怎么样显示到界面上面的呢?现在就带着这个疑问来分析下面的代码,这样肯定会找到解决方法的。怎么样找到入口呢?其实可以先从界面显示的类开始,可以看到显示界面的窗口类名称叫做Chrome_RenderWidgetHostHWND,有了这个类名称,就可以到代码里查看它在那里了。

#001  class RenderWidgetHost;

 

#002  class WebMouseEvent;

 

#003  class WebCursor;

 

#004 

 

#005  typedef CWinTraits<WS_CHILD | WS_CLIPCHILDREN | WS_CLIPSIBLINGS, 0>

 

#006      RenderWidgetHostHWNDTraits;

 

#007 

 

#008  static const wchar_t* const kRenderWidgetHostHWNDClass =

 

#009      L"Chrome_RenderWidgetHostHWND";

 

 

 

可看到这个窗口类名称是定义在这里,再跟着kRenderWidgetHostHWNDClass来查找,就会找到显示窗口,如下:

 

#001  class RenderWidgetHostHWND :

 

#002    public CWindowImpl<RenderWidgetHostHWND,

 

#003                       CWindow,

 

#004                       RenderWidgetHostHWNDTraits>,

 

#005    public RenderWidgetHostView {

 

#006   public:

 

#007    RenderWidgetHostHWND(RenderWidgetHost* render_widget_host);

 

#008    virtual ~RenderWidgetHostHWND();

 

#009 

 

#010    void set_close_on_deactivate(bool close_on_deactivate) {

 

#011      close_on_deactivate_ = close_on_deactivate;

 

#012    }

 

#013 

 

#014    void set_parent_hwnd(HWND parent) { parent_hwnd_ = parent; }

 

#015 

 

#016    DECLARE_WND_CLASS_EX(kRenderWidgetHostHWNDClass, CS_DBLCLKS, 0);

 

 

 

通过上面的分析,就可以找到显示网页的窗口类RenderWidgetHostHWND,在这个类里,主要显示的位置是在void RenderWidgetHostHWND::OnPaint(HDC dc)函数里面,它的代码如下:

 

#001  void RenderWidgetHostHWND::OnPaint(HDC dc) {

 

#002    DCHECK(render_widget_host_->process()->channel());

 

#003 

 

#004    CPaintDC paint_dc(m_hWnd);

 

#005    HBRUSH white_brush = reinterpret_cast<HBRUSH>(GetStockObject(WHITE_BRUSH));

 

#006 

 

#007    RenderWidgetHost::BackingStore* backing_store =

 

#008        render_widget_host_->GetBackingStore();

 

#009 

 

#010    if (backing_store) {

 

#011      gfx::Rect damaged_rect(paint_dc.m_ps.rcPaint);

 

#012 

 

#013      gfx::Rect bitmap_rect(

 

#014          0, 0, backing_store->size().width(), backing_store->size().height());

 

#015 

 

#016      gfx::Rect paint_rect = bitmap_rect.Intersect(damaged_rect);

 

#017      if (!paint_rect.IsEmpty()) {

 

#018        BitBlt(paint_dc.m_hDC,

 

#019               paint_rect.x(),

 

#020               paint_rect.y(),

 

#021               paint_rect.width(),

 

#022               paint_rect.height(),

 

#023               backing_store->dc(),

 

#024               paint_rect.x(),

 

#025               paint_rect.y(),

 

#026               SRCCOPY);

 

#027      }

 

......

 

#058  }

 

 

 

其实这个函数是通过如下发送消息给另一个进程进行渲染成BMP的图片,

 

Send(new ViewMsg_Repaint(routing_id_, view_size));

 

 

 

那么谁来接收ViewMsg_Repaint消息呢?继续细心地查找,就到在如下类函数里处理:

 

void RenderWidget::OnMsgRepaint(const gfx::Size& size_to_paint)

 

在这个函数,并不是最终的结果,它又会调用其它线程来处理渲染,以便达到异步的结果。它的调用过程如下:

 

1)  RenderWidget::DoDeferredPaint()  线程里开始渲染网页显示

 

2)  RenderWidget::PaintRect() 窗口里开始进行显示

 

3)  WebViewImpl::Paint() web视类开始显示。

 

4)  WebFrameImpl::Paint() web框架类开始显示。

 

5)  WebCore::ScrollView::paint() 滚动窗口显示。

 

6)  WebCore::Frame::paint() WebCore里的框架显示。

 

7)  WebCore::RenderLayer::paint() 分层显示。

 

8)  WebCore::RenderLayer::paintLayer()

 

9)  WebCore::RenderBlock::paint()  在每一层里显示每一块区域。

 

10)    WebCore::RenderBlock::paintObject() 显示这一区域的对象。

 

11)    WebCore::RenderBlock::paintContents() 显示需要显示的内容。

 

12)    WebCore::RenderFlow::paintLines() 这里需要显示文字。

 

13)    WebCore::RootInlineBox::paint() 开始显示一行文字。

 

14)    WebCore::InlineFlowBox::paint() 进行一行文字排列。

 

15)    WebCore::InlineTextBox::paint() 

 

16)    WebCore::GraphicsContext::drawText()  进行一个一个文字显示。

 

17)    WebCore::Font::drawText()  这里调用字体类来把文字的编码变成位图。

 

18)    WebCore::Font::drawSimpleText()  这里把位图显示到界面内存里。

 

 

 

通过上面的分析,可以看到显示一串文字的过程是如此复杂的过程。其它图片显示的过程也是一样,都把它们变成位图,然后再分层显示出来。那么javascript是怎么样显示的呢?这个会比上面的过程更加复杂,后面再仔细地分析它。下一次,主要仔细地看看这些过程里的一些类功能。

 

再分享一下我老师大神的人工智能教程吧。零基础!通俗易懂!风趣幽默!还带黄段子!希望你也加入到我们人工智能的队伍中来!https://blog.csdn.net/jiangjunshow

以上是关于谷歌浏览器的源码分析 34的主要内容,如果未能解决你的问题,请参考以下文章

谷歌浏览器的源码分析 4

谷歌浏览器的源码分析 21

谷歌浏览器的源码分析 7

谷歌浏览器的源码分析 9

谷歌浏览器的源码分析 29

谷歌浏览器的源码分析 13