笔者构想了一种类似http/html的分布式GUI程序设计框架,适用于WIndows、桌面Linux、Mac OS以及C++,Java,Python等多种支持GUI编程的程序设计系统。但是对于手机小屏幕,可能不合适。

本系统包括窗口描述规则;gui.exe -- 一个命令行程序,用于解释执行该规则,你可以把gui.exe当成python.exe这种解释器,区别是gui.exe只解释执行图形程序;guid.exe --- 这是一个GUI服务器,用于编写实际的C++函数,相应客户端请求的页面或者函数调用,并将页面、函数调用结果传给客户端。

一、页面描述、请求服务器页面、函数调用

; 变量定义

@var

a=12 b="helo world" c=12.5

; 图形界面描述

@gui

1 WINDOW name="first" click="firstclick" title="测试" top=100 left=100 width=100 height=100 image="D:\test 1.bmp"

2 PANEL

3 TEXT name="t1" caption="My..."

2 WINDOW

3 TEXT caption=b

3 PANEL

4 TEXT captiion="Hello world"

; 初始化函数

@init

; 调用本地或者远程GUI服务器中的函数,返回值存进变量。

a=gui://localhost/cpp_fun1(12,"hello") $first.title=a $first.show

;为@gui添加一行节点 这里将在第一个参数指向的控件后,添加一个控件节点。该函数不做控件"层次"检查。

; 你可以再第一层控件后添加第三层控件。也就是说,即使你push_back成功了,不表示你的窗口描述就是正确的。

;系统在创建并绘制控件时,会做检查,如果检查到你的树形结构中,第一层控件节点有个第三层子节点,报错。

$first.push_back("t1",4,"TEXT","caption", "在函数里添加控件")

; 控件的键盘、鼠标处理函数

@firstclick

$first.title="Changed Titile"

鼠标、键盘处理函数,指定控件的以下属性即可:

click:单击

dblclick:双击

mousedown:鼠标按下

mouseup:鼠标抬起

mouseover:鼠标悬浮

mouseout:鼠标离开

mousemove:鼠标移动

mouseenter:鼠标进入

mouseleave:鼠标离开

keydown:按键按下

keyup:按键抬起

keypress:按键按下抬起

cpp_fun1是GUI服务器程序中的函数。其返回值将会被GUI客户端使用。

上述@gui部分,其实是对html的改进,目的是简化编程,让程序设计者和计算机都少做点事情。笔者实现上述@gui部分,用c++大概500行代码,如果使用html/xml,笔者在网上找了一些开源的xml解析库,通常十几个到几十个文件,统计上万行代码,甚至更多。也就说代码规模小了10倍甚至几十倍。而对应软件的解析效率,估计也能打到10倍甚至更多的增长。

为什么笔者随便一个设计,就会比html、xml好这么多呢?因为笔者为其限定了语法:

以数字开头,表示控件的层次。html/xml没有这个,系统检测但是,真正的GUI设计者,应该对自己的控件的层次了如指掌。

标签/控件无需重复两次, html是这种写法。

3.以行为单位。你不能把@gui中的一行拆开来写。

4.赋值语句不能有空格,也就是说"a=3",不能写成“a = 3”。同样,函数调用、参数之间也不能有空格。

5.区分大小写。

限定语法,计算机和程序设计者都能做更少的工作。

我们可以在上述GUI里写好几个窗口:

1 WINDOW name="first" click="firstclick" title="测试" top=100 left=100 width=100 height=100 image="D:\test 1.bmp"

2 DIV

3 A href="http://gnu.org/test.gui"

4 TEXT name="t1" caption="My..."

1 WINDOW name="s"

2 TEXT name="t1" caption="My..."

然后在@init中显示特定的窗口:

$first.show

如果你想,连续显示多个窗口:

$first.show

$s.show

多数情况下,用户可能会在@firstclick等键盘、鼠标处理函数中创建并显示窗口。

二、百分比指定控件大小和位置

多数GUI库的作者没有认识到 -- 特别是那些跨平台的库 -- GUI库的各种控件应该按百分比指定长度、宽度、和在父级控件中的位置 --而不是用像素。你创建window或者button时,应该通过百分比指定大小和位置。GUI库应该有自动将百分比转化为像素的功能,所有宣称跨平台的GUI库都应该加上这个功能,而且是所有控件都能通过百分比定位。这是html教给我们的常识。很可惜,在网页设计者这里很普通的常识,在GUI库那里却变成了奢侈品。

我们鼓励使用百分比来指定窗口大小和位置。如下代码,创建一个窗口,该窗口离屏幕左上角分别占屏幕长和宽的10% 20%,而该窗口的大小也是屏幕长和宽的80%、90%。

1 WINDOW name="first" click="firstclick" title="测试" top=10% left=20% width=80% height=90% image="D:\test 1.bmp"

三、C++实现。

gui.ex中,我们用一个简单的函数读取并解析上述文本:

read_gui("test.gui");

该函数的目的则是读取test文本,然后得到一颗树形结构 -- 这个过程和浏览器解析html是类似的。然后,遍历该结构,先父后子、先兄后弟,创建并显示窗口。笔者,使用Windows API快速做了个原型。如果希望,能跨平台,可那使用GTK更好 --- 注意,不要用QT。

除了该函数,我们还要实现test.gui中使用的宿主语言函数,也就是上文中的cpp_fun1.我们的解析程序解析test.gui要调用cpp_fun1,会把该函数的调用结果赋值给变量a -- 注意,变量a是test.gui的一个变量、并非c++程序中的变量。在实现中,我们可以使用map来存放变量名和值。

有了以上三点,一个单击的GUI设计方法就完成了。剩下的工作,则是实现各种控件。

四、基本控件的实现。

最简单、基础,必备的可能是WINDOW和TEXT,这很容易。WINDOW用于创建一个标准的Windows窗口,TEXT用于写文本。

比较重要的是容器控件,在OO库里,通常是叫PANEL,用于放置各种控件,在html则是

的好处在于可以嵌套放置,你可以在一个div里放一个div,多次嵌套。PANEL也应该如此。

一些OO GUI库的PANEL控件,用一种丑陋、莫名其妙的”布局对象“来控制其中的控件的布局,不提了。良好的设计大概是这样的:

1 WINDOW name="s"

2 PANEL layout="vertical"/"horizon“/”none" w=3 h=4

3 TEXT name="t1" caption="My..."

layout可以取值vertical或者horizon,其意义是,本PANEL的子控件,按照垂直、或者水平方式布局。如果你指定布局方式为None,则子控件按照top width摆放控件。

w和h的意义是,把PANEL平均分成3*4的矩形格子,控件依次放入其中。可以按行放置子控件,也可以按列放置子控件。

最后也是“叶子”控件 --- 他们必须放置于容器空间之中 Window或者PANEL。你不能在叶子控件里添加控件。通常,一个按钮、单行文本框、单选、多选、图像控件.... 是一个叶子控件。

不同OO库添加叶子控件的方法不一样,有的顶层窗口上不能直接放置叶子控件,必须添加一个PANEL,而另一些可以直接放置。我想,各自都有理由,笔者不想做约束,实现者考虑自己的需求,灵活掌握。

DELPHI VCL有自己的菜单控件TMENU,而在我们的GUI系统中,无需MENU控件,我们简单使用PANEL和TEXT就能拼出一个菜单:

1 WINDOW name="s"

2 PANEL layout="horizon“ w=1 h=2

3 PANEL name="menu" layout="horizon“ w=5 h=1

4 TEXT name="file" caption="文件" click="subshow"

4 TEXT name="edit" caption="编辑"

4 TEXT name="view" caption="查看"

4 TEXT name="tools" caption="工具"

4 TEXT name="help" caption="帮助"

3 PANEL name="submenu" layout=“vertical” w=1 h=3 show=no

4 TEXT name="new" caption="新建"

4 TEXT name="save" caption="保存"

4 TEXT name="open" caption=“打开"

3 PANEL name="content" layout="horizon“ w=1 h=1

@subshow

submenu.show

以上,名为menu的PANEL就是一个菜单,我们的菜单可以以各种文本的颜色显示,因为你已经实现了TEXT的彩色显示。

submenu是文件菜单的子菜单,show=no意为默认不现实,当你调用@submennu.show时,系统才绘制该子菜单。我们在名为file的text单击函数中,调用了该函数。

对于数据库记录的显示,我们实用上面的PANEL和TEXT控件即可:

1 WINDOW name="s"

2 PANEL name="db" layout="vertical"/"horizon“/”none" w=3 h=4

3 TEXT name="t1" caption="My..."

3 TEXT name="t2" caption="My..."

3 TEXT name="t3" caption="My..."

3 TEXT name="t4" caption="My..."

以上的PANEL中,存放3行4列文本,每行文本显示数据库的一条记录。

如果你有超过3条记录,你只需改变PANEL的w和h值,然后添加节点:

;变量后的"|"表示该变量是一个数组变量。

a|=“0000”,1,2,3

@gui

1 WINDOW name="s"

2 PANEL name="db" layout="vertical"/"horizon“/”none" w=3 h=4

; a|0引用数组的某一元素,等价于多数程序中的a[0],使用单符号操作符,解析更加容易。

3 TEXT name="t1" caption=a|0

3 TEXT name="t2" caption="My..."

3 TEXT name="t3" caption="My..."

@init

;调用C++/Python等实现语言函数,获得数据库记录,存在数组变量中.

a|=cpp_fun() $db.w=10 $db.w=10 $t1.caption=a|0 $t2.caption=a|1 $t3.caption=a|0

也许,我们该为这种GUI描述语言,添加for语句。

控件。这里的难点在于,vedio控件里的数据不是字符串,而是二进制数据。

我们的GUI描述文件怎么获得C++程序的二进制数据呢?

五、分布式GUI

我们可以基于以上框架,实现一个类似html中的控件/标签。

1 WINDOW name="first" click="firstclick" title="测试" top=100 left=100 width=100 height=100 image="D:\test 1.bmp"

2 DIV

3 A href="GUI://gnu.org/test.gui" caption="GNU官网"

4 TEXT name="t1" caption="My..."

当用户点击:

3 A href="GUI://gnu.org/test.gui" caption="GNU官网"

其实要创建并显示远程机器上的GUI程序,其文本描述和其中将要调用的C++函数都在远程机器上。

这就过程就好比你在网页中点击一个链接,会跳到一个新的页面。同样,你可以照搬html的设计打开一个新的窗口,旧窗口不用关闭。

在gnu.org上会运行一个GUI服务器、并存在一个test.gui文件。GUI服务器类似于http服务器,用于接受客户端请求,返回test.gui文本以及该文本中书写的各种宿主语言的函数调用结果。

假设GUI://gnu.org/test.gui的内容如下:

@gui

1 WINDOW name="test"

@init

$test.show

$.title=My_CPP_fun()

运行在gnu.org上的GUI服务器应该实现了My_CPP_fun函数,并且能够将其调用结果返回给客户端。

一个简单的GUI协议如下:

GET GUI://gnu.org/test.gui

这个类似http的GET请求,用于返回文本文件内容。

以下用于调用远程函数:

GET GUI://gnu.org/ My_CPP_fun 12 "test.abc" 223.4

以上调用远程服务器的My_CPP_fun函数,参数为12 "test.abc" 223.4

这样,一来,我们的GUI框架,就有了网络分布式能力。我们编写的GUI不但可以本地执行,而且可以把URL地址告诉别人,别人就能简单使用A标签使用你的GUI程序。 这个似乎很像Windows的远程协助,你可以让朋友控制你的电脑。

html服务器框架,一种类似http/html的分布式GUI程序设计框架相关推荐

  1. java swing漂亮界面框架_开源软件分享-漂亮的JavaFx GUI界面框架

    虽然说Java目前主要的应用领域是服务端,GUI桌面端软件也有极少量的应用场景(桌面软件还是C#方便),所以今天给大家分享一款漂亮的JavaFx GUI界面框架BootstrapFX. Java Fx ...

  2. java 分布式服务器通信,Pigeon是大众点评的一个分布式服务通信框架RPC

    Pigeon Documentation Release Notes Comitters 苗向彬,saber.miao Copyright and license Copyright 2015 Dia ...

  3. 第五章-分布式并行编程框架MapReduce

    第五章-分布式并行编程框架MapReduce 文章目录 第五章-分布式并行编程框架MapReduce MapReduce概述 分布式并行编程 MapReduce模型和函数 MapReduce体系结构 ...

  4. 图解高性能服务器开发两种模式,第四章 NETTY高性能架构设计

    目录 一.NIO存在问题以及Netty的优点 二.线程模型基本介绍 三.工作原理图(传统同步阻塞式IO) 四.Reactor模式 五.单Reactor单线程 六.单Reactor多线程 七.主从REA ...

  5. JAVA基础加强(张孝祥)_类加载器、分析代理类的作用与原理及AOP概念、分析JVM动态生成的类、实现类似Spring的可配置的AOP框架...

    1.类加载器 ·简要介绍什么是类加载器,和类加载器的作用 ·Java虚拟机中可以安装多个类加载器,系统默认三个主要类加载器,每个类负责加载特定位置的类:BootStrap,ExtClassLoader ...

  6. 边缘计算框架_【北大成果】一种集成多组网协议多边缘计算框架的边缘计算处理平台...

    项目简介 随着物联网设备的指数型增长,传统云计算的集中式处理方法已不能满足数据处理和数据安全等需求,边缘计算应运而生.边缘计算可以提升物联网的智能化,促使物联网在各个垂直行业落地生根.但是,一般的应用 ...

  7. 服务器存储系统的模式,服务器的三种存储方式

    服务器的三种存储方式 内容精选 换一换 CSBS在支持崩溃一致性备份的基础上,同时支持应用一致性备份.文件/磁盘数据在同一时间点,通过应用一致性备份内存数据,能够保证应用系统一致性,如包含MySQL或 ...

  8. 云服务器有几种类型,一般要如何选购

    目前云计算市场一片繁荣,云服务器越来越受到企业的青睐,那么云服务器一般分为哪几种类型,要如何才能选购上符合要求的服务器呢?群英来说说. 首先,云服务器一般分为公共云.私有云.混合云和裸机物理服务器这几 ...

  9. arma3自定义服务器,《绝地求生》自定义服务器要收费?类似《武装突袭3》

    原标题:<绝地求生>自定义服务器要收费?类似<武装突袭3> 虽然<绝地求生>正值下坡路,但开发商一直没有放弃,最近频繁更新,推出诸多新内容,前不久更是上线了&quo ...

最新文章

  1. 多个不同的app应用间应该如何进行消息推送呢?
  2. VMware View是如何帮助企业省钱的
  3. CTFshow php特性 web114
  4. 去中心化交易所前路明朗,基于EOS的去中心化交易所力拔头筹
  5. NeurIPS 2021 | PCAN:高效时序建模,提升多目标追踪与分割性能
  6. servlet 认证,授权
  7. OAuth2.0认证
  8. Redis实战(一):Redis一键安装脚本,Redis 介绍及 NIO 原理介绍
  9. Android 4.4 KitKat, the browser and the Chrome WebView
  10. 【POJ - 2762】Going from u to v or from v to u?(Tarjan缩点,树形dp 或 拓扑排序,欧拉图相关)
  11. Windows7修改hosts提示:您没有权限在此位置中保存文件
  12. 【动态规划】区间dp: P3205 合唱队
  13. 实验三 密码破解技术 201521410010
  14. 关于应用的外部接口设计心得
  15. jdbc数据库连接池连接
  16. 廖雪峰python学习笔记之Web开发
  17. 如何利用excel中的数据源制作数据地图
  18. python 正则表达式 前瞻_Python的正则表达式
  19. gpsgate 配置过程
  20. AU入门音频编辑基本认识

热门文章

  1. 前端学习(3091):vue+element今日头条管理-展示编辑文章
  2. 前端学习(2784):首页轮播图的渲染
  3. “约见”面试官系列之常见面试题之第九十三篇之vue获取数据在哪个周期函数(建议收藏)
  4. 前端学习(2362):上拉加载
  5. 前端学习(2233):react的子传父数据传递
  6. “约见”面试官系列之常见面试题第十八篇之深拷贝和浅拷贝得区别(建议收藏)
  7. 前端学习(1563):ng-if
  8. 63 javabean的作用域范围
  9. windows:(1)xmind常用快捷键
  10. java学习(120):set的iterator