fltk教程03:关于例子Text Editor的理解。

本文主要介绍FLTK库中Text Editor的例子,通过主函数和关键代码讲解如何创建一个文本编辑器,包括使用Fl_Text_Buffer、Fl_Window及加载文件等功能。
部署运行你感兴趣的模型镜像
 例子Text Editor创建了一个简单的文本编辑器,代码参考fltk安装包里的例子.下面是对此例子的一些理解。

1.主程序同 fltk教程01中描述的基本一样:创建主窗口-->显示主窗口-->进入主循环。下面是main函数:
  1. // 主函数入口
  2. int main(int argc, char *argv[])
  3. {
  4.     textbuf = new Fl_Text_Buffer;
  5.     Fl_Window *window = new_view();
  6.     window->show(1, argv);
  7.     if(argc>1)
  8.         load_file(argv[1], -1);
  9.     return Fl::run();
  10. };
2.关于Fl_Text_Buffer类
#include <FL/Fl_Text_Buffer.H>
Fl_Text_Buffer类由Fl_Text_Editor类和Fl_Text_Display类使用,用于管理复杂的文本数据。它提供大量的方法用于完成文本的读取,保存,编辑等等操作。具体内容可参考: http://www.fltk.org/documentation.php/doc-1.3/Fl_Text_Buffer.html
注意以下三个成员函数与缓冲区回调函数有关:
  1. void add_modify_callback(Fl_Text_Modify_Cb bufModifiedCB, void *cbArg);
  2. void remove_modify_callback(Fl_Text_Modify_Cb bufModifiedCB, void *cbArg);
  3. void call_modify_callbacks();
回调函数定义为
  1. typedef void (*Fl_Text_Modified_Cb)(int pos, int nInserted, int nDeleted, int nRestyled, const char *deletedText, void *cbArg);
在这个例子中,回调函数用于在文本内容被修改时,标记修改标志(int changed)为1,——该标志在文本保存时设置为0。——然后调整窗口标题为"XXXX(modified)",代码如下
  1. void changed_cb(intint nInserted, int nDeleted, intconst char *, void *v)
  2. {
  3.     if((nInserted || nDeleted) && !loading)
  4.         changed = 1;
  5.     EditorWindow* w = (EditorWindow *)v;// 主窗口
  6.     set_title(w);//根据文本内容是否被修改,调整主窗口标题
  7.     if(loading)
  8.     {
  9.         w->editor->show_insert_position();
  10.     }
  11. }

方法01:add_modify_callback用于添加(注册)一个回调函数,该函数在用户调用call_modify_callback()时,或缓冲区内容有改动时被调用。在本例中,回调函数在创建主窗口时添加到文本缓冲区中。
  1. // new_view()
  2.     textbuf->add_modify_callback(changed_cb, w);
  3.     textbuf->call_modify_callbacks();
  4. // ...
方法02:call_modify_callabcks要求缓冲区调用所有已注册的回调函数(由add_modify_callback添加)。注意:call_modify_callbacks是用户手动的发出通知,告诉缓冲区需要调用对应的回调函数。缓冲区根据当前内容及状态产生回调函数的参数,并调用callbacks。这一过程有些类似于windows下的SendMessage(消息发送)与MessageHandler(消息处理)。 似乎可以允许有多个callbacks(不对:一个窗口仅有一个callback)。
例子中 ,多处调用了call_modify_callbacks,主要有:创建主窗口(new_view)、打开已保存的文件(load_file)、保存文件(save_file)、新建(new_cb)四处。

方法03:remove_modify_callback用于删除指定的已注册的回调函数。本例在关闭窗口(close_cb)时,调用此函数以进行清理.注意应在删除主窗口前调用此方法。

3. 关于窗口
(1)窗口定义
Editor例子中,基于类Fl_Double_Window定义了自己的主窗口类EditorWindow
  1. class EditorWindow : public Fl_Double_Window
  2. {
  3. public:
  4.     EditorWindow(int w, int h, const char *t);
  5.     ~EditorWindow();

  6.     Fl_Window           *replace_dlg;
  7.     Fl_Input            *replace_find;
  8.     Fl_Input            *replace_with;
  9.     Fl_Button           *replace_all;
  10.     Fl_Return_Button    *replace_next;
  11.     Fl_Button           *replace_cancel;

  12.     Fl_Text_Editor      *editor;
  13.     char                search[256];
  14. };
基类Fl_Double_Window(头文件:#include <FL/Fl_Double_Window.H>)由Fl_Window派生,它提供了一种"双缓冲"窗口。如果可以的话,"双缓冲"通过Xdbe(X double buffering extension)实现;否则,它将窗口数据绘制到一个离屏像素图(off-screen pixmap)上,然后再将其复制到在屏窗口(on-screen window)中。
(ps.关于X window的原理,参考李先静的博客: X Window研究笔记)

(2)子窗口定义与创建
窗口中定义了一个查找替换对话框(replace_dlg),以及对话框中的一些控件,包括:
(2-1)文本输入控件:(#include <FL/Fl_Input.H>)
Fl_Input *replace_find;
Fl_Input *replace_with;
(2-2)按钮控件(#include <FL/Fl_Button.H> <FL/Fl_Return_Button.H>)
Fl_Button *replace_all;
Fl_Return_Button *replace_next;
Fl_Button *replace *replace_cancel;

创建该对话框的代码在EditorWindow::EditorWindow()构造器中,代码如下:
  1.     replace_dlg = new Fl_Window(300, 105, "Replace:");      // 开始组
  2.     replace_find = new Fl_Input(80, 10, 210, 25, "Find:");
  3.     replace_find->align(FL_ALIGN_LEFT);
  4.     replace_with = new Fl_Input(80, 40, 210, 25, "Replace:");
  5.     replace_with->align(FL_ALIGN_LEFT);
  6.     replace_all = new Fl_Button(10, 70, 90, 25, "Replace All");
  7.     replace_all->callback((Fl_Callback *)replall_cb, this);
  8.     replace_next = new Fl_Return_Button(105, 70, 120, 25, "Replace Next");
  9.     replace_next->callback((Fl_Callback *)replace2_cb, this);
  10.     replace_cancel = new Fl_Button(230, 70, 60, 25, "Cancel");
  11.     replace_cancel->callback((Fl_Callback *)replcan_cb, this);
  12.     replace_dlg->end();    //组结束
  13.     replace_dlg->set_non_modal();
第一行。创建对话框框架窗口,自动开始group,即后面创建的widget都是其组合中的成员,直到end()方法被调用(手动开始组合由begin()方法开始)。
第2~15行。创建各控件。
Fl_Widget::align()函数定义控件标签的位置,FL_ALIGN_LEFT指定标签位于控件左侧(外部)。
Fl_Widget::callback()函数定义按钮的回调函数。
Fl_Window::set_non_modal()函数指定窗口类型为non_modal(三种类型:modal,non_modal,normal)。

(2)删除子窗口
子窗口的删除在析构器EditorWindow::~EditorWindow()中
  1. delete replace_dlg;
注意,此处仅删除了replace_dlg(组合),而 组合中的控件没有被显式地删除,可能是组合内部隐式地删除了。

(3)子窗口的显示与隐藏
子窗口的显示由函数show()和hide()来实现显示与隐藏。根据需要,调用show和hide来显示或隐藏子窗口。

(4)文本编辑器Fl_Text_Editor(#include <FL/Fl_Text_Editor.H>)
为了能够对缓冲区文本进行处理,窗口中定义了编辑器的指针,
Fl_Text_Editor *editor;
但编辑器并不在EditorWindow中创建,而是在外部创建后,将其指针赋值给editor。
  1. EditorWindow* w = new EditorWindow(660, 400, title);
  2. w->begin();
  3. //...
  4. w->editor = new Fl_Text_Editor(0, 30, 660, 370);
  5. w->editor->buffer(textbuf);//Fl_Text_Buffer *textbuf;
Fl_Text_Editor为一个全功能的文本编辑窗口,支持多行文本编辑与语法高亮等特性。它用于操作指定的Fl_Text_Buffer对象。同样,由于编辑器是主窗口组合中的子窗口,所以不需要显示的删除。

(5)回调函数
关于回调函数略。

4. 菜单
。。。。

您可能感兴趣的与本文相关的镜像

ComfyUI

ComfyUI

AI应用
ComfyUI

ComfyUI是一款易于上手的工作流设计工具,具有以下特点:基于工作流节点设计,可视化工作流搭建,快速切换工作流,对显存占用小,速度快,支持多种插件,如ADetailer、Controlnet和AnimateDIFF等

评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值