SumatraPDF代码结构不完全解读

因为SumatraPDF在基本使用方面非常的好用,但一些别的功能不是很完善,因此就想通过修改一下它的源码来实现我想要的功能(比如说分窗口啊,注释啊之类的),大概读了三天吧…稍微有了一点感觉,就觉得这个工程量确实有点大…打了退堂鼓,但这几天的解读不能白白浪费,网上也没有很好的解读,于是就稍微写一些,留给以后想扩展其源码的人吧233.

编译

编译需要VS2017,我不知道更早的版本是否可行,但2019应该是不行的,因为它应该是已经移除了对xp的支持
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
然后需要安装WIN SDK8.1+10,需要安装141和xp支持,如果都安装了,没有意外应该还会编译失败,会报两个错误,我没有截图,就是编码错误,据说把错误级别调低就可以,但我没去查怎么调低,去把错误的编码重新换了一下,然后就编译成功了。

这个框架我不清楚是直接使用的WindowsAPI还是用的MFC,在我的查阅过程中很多声明都是混着用的感觉。

入口函数.\src\SumatraStartup.cpp:535

int APIENTRY WinMain(...){
	...
	CreateAndShowWindowInfo()//742
	...
}

一直到调用CreateAndShowWindowInfo方法前,都是初始化方法,在CreateAndShowWindowInfo方法(位于.\src\SumatraPDF.cpp)里,通过调用WindowsAPIShowWindow()方法来显示主窗体(变量为win->hwndFrame)。

在调用完CreateAndShowWindowInfo方法后,会存储或读取一些历史信息,并将当前目录改到c:\windows\system32下(为了不占用目录)

随后进入信息接收循环体(retCode = RunMessageLoop();//783),不断的接收窗口事件并分发事件,直到关闭窗体,之后释放内存。

文档界面信息类:\src\WindowInfo.h

class WindowInfo

里面保存了页面的缩放、offset、目录/书签是否显示等各种信息,每一个文档都会有一个这样的信息,最终所有的WindowInfo类会被保存到SumatraPDF.cpp:109std::vector<WindowInfo*> gWindows;中。

事件分发
事件分发与WindowsAPI有关,分发方法定义在\src\SumatraStartup.cpp:450,通过不断的调用GetMessage方法用MSG结构体(定义在\Microsoft SDKs\Windows\v7.1A\Include\WinUser.h中,结构如下)来接收可能存在的信息。

typedef struct tagMSG {
    HWND        hwnd;//接收消息的窗口句柄
    UINT        message;//消息标识符。这是一个数值,用以标识消息。
    WPARAM      wParam;//一个32位的「message parameter(消息参数)」,其含义和数值根据消息的不同而不同
    LPARAM      lParam;//一个32位的消息参数,其值与消息有关。
    DWORD       time;//消息放入消息队列中的时间。
    POINT       pt;//消息放入消息队列时的鼠标坐标。
#ifdef _MAC
    DWORD       lPrivate;
#endif
} MSG, *PMSG, NEAR *NPMSG, FAR *LPMSG;

接收到信息后,会进行相应的转换,并分发到各自的窗口中去处理事件,处理事件的方法是事先定义好后,在创建窗口的时候指派的,具体可以查看CreateWindowExW()方法的参数,该方法指定所创建窗口的标识符、父窗口和事件处理方法(以及其他属性,如风格,查看 创建一个简单窗口 )。

这里的窗口是广义的窗口,即按钮啊这些都算是一个窗口。

文件读取:\src\SumatraPDF.cpp:1427

WindowInfo* LoadDocument(LoadArgs& args)

参数args中包含文件路径,所展示窗口(当前焦点所在的,可能会在之后被新创建的窗口信息替换)等信息,用于读取并显示文档。如果没有其他问题,那么就会创建一个Controller类来装载全部的文档信息,在Controller内,实际上装载了一个BaseEngine类,它是真正的读取各个文档并抽取信息的类。Controller又在BaseEngine之上加上了窗体信息(如zoom倍率)。

在创建完成文档信息后,就会创建一个Tab用于切换窗口,最后,使用static void LoadDocIntoCurrentTab()//945来真正的在UI界面中显示。

创建窗口信息\src\SumatraPDF.cpp:1230
该方法单纯的创建一个窗体信息,但是并没有显示出来,等待其他方法来将该窗体显示出来

static WindowInfo* CreateWindowInfo()
发布了132 篇原创文章 · 获赞 77 · 访问量 12万+
展开阅读全文

没有更多推荐了,返回首页

©️2019 CSDN 皮肤主题: 精致技术 设计师: CSDN官方博客

分享到微信朋友圈

×

扫一扫,手机浏览