c++开发模板notepad++插件开发入门
notepad++的插件开发可以去它的官网下载模板,提供了c/c++,delphi,等语言的插件模板,这里提供一下c++的开发模板。
这个工程是能直接编译跑过的,它实现了两个命令, hellonotepad++ 和hello (with dialog)
前者是实现了新建一个文档并输入了一段话,后者仅仅是弹出个messagebox,并不是我们想的是一个dock窗体.
这里先解释一下各个文件是干嘛用的.
menucmdid.h的意义跟他的名字一样,里面是定义了notepad++里面各个菜单项的id值,应该是点击了它对应的菜单触发了相应的回调的时候用得到,我这次的开发并没有用到这个文件里面的值.
notepad_plus_msgs.h里面则定义了一些枚举值,比如我们获取到的当前编辑状态是什么语言,其对应的枚举值在langtype里面就可以对应上,其中最主要的还是定义了notepad++本身的一些操作会促发的消息的枚举值,比如打开了文档,保存了文档,这些都是通过一个函数传过来给你的,你就需要根据类型去区分这次的操作是什么,从而做出响应
plugindefinition.h里面比较简单,就定义了几个函数跟插件的一些信息,比如plugininit是插件加载的时候调用的, commandmenuinit是初始化菜单用的,每个函数的顶部也有相关的英文说明.我们的每一个命令,都是要对应一个函数的,那些函数也可以定义在这个头文件里面, plugindefinition.cpp是它里面的每个函数的实现.
plugininterface.h就是整个插件跟notepad++交互的入口了,它定义了一些导出函数,比如:
void setinfo(nppdata),是将notepad++的句柄传递过来,我们根据句柄,就可以给它发送一些信号,这是我们能做二次开发的前提.
const tchar * getname()是返回这个插件的名字.
funcitem * getfuncsarray(int *)是获取我们所有的命令信息,我们自定义的命令都是没有参数跟返回值的.我们的命令是要以数组的方式存起来, int* 是用来获取我们的命令个数的,返回值是数组的首地址.
void benotified(scnotification *).这个函数就厉害了,这就是notepad++每次发生变化的时候用来通知我们的回调函数,无论是文件操作发生了变化或者是文本里面的内容发生了变化,比如你打开了文档,或者在文档里面新增或者删除了个字符,都会反应到这个函数里面. scnotification这个结构体的内容非常多,里面每一项变量都列举了哪些消息会用到它.
lresult messageproc(uint message, wparam wparam, lparam lparam) 这个好像是接收notepad++的窗体信号的,比如移动了它,最大化了,最小化了等,这个函数我没有用到.
然后就是resource.h了.就是在里面定义一些资源id而已
scintilla.h这个也很重要.在介绍这个之前,得先说明一下,notepad++的语法分析,语法高亮,智能提示,文本编辑等这些很重要的东西是基于scintilla做的,还有其他基于scintilla做的编辑器,比如notepad2, scite等,这个库在windows平台上就是一个窗体控件(这个东西也封装到qt上了,有机会一定要试一试),通过windows消息进行交互,你可以给他发一些消息,然后告诉他你应该做哪些事情,应该显示成什么样子,当他发生了改变,它也会给你发消息(通过benotified),告诉你他哪里变了.所以scintilla.h这里文件很重要,是交互的基础,是双方做的一个约定.里面基本都是一些宏定义跟结构体,关于这些宏定义跟结构体,在这里https://www.scintilla.org/scintilladoc.html可以找到英文的解释,做notepad++的插件开发 ,很多的工作都是在找我们需要用到的功能,是通过哪个消息去控制的.
最后就是nppplugindemo.cpp了,这个东西里面主要放了dllmain,dll加载的入口函数,跟plugininterface.h里面的一些导出函数的实现.然后我们如果是支持unicode字符集的话,还会有一个isunicode()的导出函数.
以上就是官方给的例子里面用到的文件说明了,官方还提供一些文件,但是这里没用到,比如dockingfeature文件夹里面的东西,那个是跟窗体有关的,后面会讲到.
以上的工程编译以后是个dll,放在notepad++的plugins文件夹,再打开软件,就会在插件菜单选项卡下看到这个插件了.
下面我们来看一下这个命令是怎么构成的.
struct funcitem { tchar_itemname[nbchar]; pfuncplugincmd _pfunc; int _cmdid; bool _init2check; shortcutkey *_pshkey; };
funcitem结构体就保存了命令的所有信息,其中_itemname是命令名字,不能超过64个字节, _pfunc是函数指针,要求无返回值无参数, _cmdid这个是注册以后的id值,这个我们不用管,是notepad++加载我们的命令以后去设置的,我们后面比如要做个有图标的选项卡,比如这些
就可以去取这个菜单id来使用了. _init2check这个是用来判断菜单前面是不是有个勾勾,标识菜单状态用的. shortcutkey就是默认快捷键了,它的结构体一看就明白,无须多说.
设置好命令的这些参数,我们就可以在命令对应的函数里面写我们的响应代码了,我们是通过句柄来发送消息的,下面我们来看一下hello这个命令.
void hello() { // open a new document ::sendmessage(nppdata._npphandle, nppm_menucommand, 0, idm_file_new); // get the current scintilla int which = -1; ::sendmessage(nppdata._npphandle, nppm_getcurrentscintilla, 0, (lparam)&which); if (which == -1) return; hwnd curscintilla = (which == 0)?nppdata._scintillamainhandle:nppdata._scintillasecondhandle; // say hello now : // scintilla control has no unicode mode, so we use (char *) here ::sendmessage(curscintilla, sci_settext, 0, (lparam)"hello, notepad++!"); }
::sendmessage(nppdata._npphandle, nppm_menucommand, 0,idm_file_new);
这里发送了一个消息,句柄就是nppdata._npphandle,nppdata这个是一个全局静态的变量,它里面存放了notepad++的句柄跟scintilla的句柄,但是scintilla有两个,应该是考虑了文档对比等功能的时候要用两个编辑框吧,一般我们用_scintillamainhandle就可以了.
然后这个消息的第二个参数是nppm_menucommand,代表是菜单消息的,然后最后是idm_file_new,就是相当于点击了文件新建的菜单选项了,换成其他的比如idm_file_close啊就是关闭文档了.
然后第二步是获取scintilla句柄,代码是
int which = -1;
::sendmessage(nppdata._npphandle, nppm_getcurrentscintilla, 0,(lparam)&which);
if (which == -1)
return;
hwnd curscintilla = (which== 0)?nppdata._scintillamainhandle:nppdata._scintillasecondhandle;
还是先通过notepad++的句柄和getcurrentscintilla,获取scintilla的状态,是0就是main那个句柄,否则就是second那个句柄,如果返回-1,那么就是没有激活的编辑框
第三步就是往里面写内容了
::sendmessage(curscintilla, sci_settext, 0, (lparam)"hello,notepad++!");
通过scintilla的句柄和settext这个信号变量,然后在最后的参数里面写上要设置的文本的内容.就完成了文本的设置.
从这里来看,做notepad++的开发也并不难,只要去摸清楚那些操作对应的信号枚举值跟参数,就可以了,具体就可以去scintilla官网查文档了.
入门开发就是这么简单.
上一篇: jQuery方法简洁实现隔行换色及toggleClass的使用
下一篇: 使用两个栈模拟一个队列
推荐阅读
-
python插件开发(python数据库编程入门)
-
python插件开发(python数据库编程入门)
-
c++开发模板notepad++插件开发入门
-
Xposed插件开发入门详解
-
android studio 插件开发 入门篇
-
node前端开发模板引擎Jade的入门
-
「B/S端开发」DevExtreme初级入门教程 - 用模板生成一个应用 DevExtremeVUEvue.jsB/S端开发
-
C++图形用户界面开发框架Qt 6.x入门级教程 - QML 应用程序 C++Qt图形界面
-
C++图形用户界面开发框架Qt 6.x入门级指南 - Qt Quick控件 C++图形C++qt界面
-
「B/S端开发」DevExtreme初级入门教程 - 用模板生成一个应用 DevExtremeVUEvue.jsB/S端开发