linux社区爱心援助Linux认证系列教程业界动态站务新闻公司招聘建议留言网址大全LPI专题CISCO专题
设为首页
加入收藏
管理团队
JSP  
JAVA  
PERL  
 您的位置:首页 > article > Linux开发区 > 软件开发 >
栏目导栏
资料搜索
热门文章
·Linux 下 C 语言编程
·Linux下的通用线程池创建
·C++字符串转换篇
·linux C 进程操作篇
·linux上的C/C++编译器gcc/egcs
·linux C 文件权限控制篇
·GCC使用手册
·linux C 接口处理篇
·在Redhat Linux上安装 GCC 编译
·GCC使用指南
·C语言运算符
·Linux下C开发环境的构成和安装
·fopen()函数的参数说明
·GCC使用手册与常用命令
·Scheme 语言介绍
最新文章
·在Ubuntu Linux 8.04上构建GCC
·Linux操作系统下Socket编程地址
·将VC程序移植到Linux系统的几点
·Linux下malloc/free与new/dele
·Linux下用GTK和socket实现简单
·Linux操作系统下让Tomcat启动在
·Linux操作系统中如何编译C程序
·几种常被人们忽略的Linux系统下
·Eclipse编程工具 在Ubuntu下的
·Linux操作系统下的网络地址转换
·老手经验谈:Linux驱动程序开发
·Linux操作系统多线程同步Mutex
·Linux操作系统下C程序语言简易
·Linux系统平台下关于GCC编译及
·解决Linux系统下管道被接受方关
Google
 
用 Perl 进行 GNOME 编程
[ 作者:  加入时间:2007-10-11 16:44:51  来自:Linux联盟收集整理 ]

GNOME 是一个 UNIX 下的桌面系统,它提供了在 Unix 下编写图形程序的环境,支持鼠标拖放,程序间通信,CORBA 组件(也就是在 Windows 里面的 OLE),CORBA 组件是一组标准的,美观的编程接口,以及所有其它现代的图形应用程序应该包含的特征。所有这些都能在 Perl 的完成,也就是 Perl 程序员能够用GNOME 库来编写整洁漂亮的应用程序,但是这儿也有一点小小的问题。。。

% perldoc GNOMEmWzLinux联盟
No documentation found for "GNOME".

没有GNOME编程的帮助文档!。我最近需要写一个基于 GNOME 库的图形界面应用程序,就遇到了这个问题。我不得不自己解决所有的问题。所以我写了这个教程,来帮助亲爱的读者朋友,使你们不用也事事亲为。首先,放松一下,我们将创建一个极为简单,但是却很完整,很标准的 GNOME 应用程序。 mWzLinux联盟
GNOME系统构成简介:

整个 GNOME 系统非常的复杂,由很多的库和组件组成。幸运的是,教学及日常大部分的程序,你都只需要知道其中的两个部分: GTK+ 和 GNOME.

可能你已经听说过了 TK,另一个 Perl 程序员经常用到的图形工具库.Tk 所扮演的角色主要是与 X 窗口服务器通信,告诉它怎样画一个按钮,菜单,控制栏,对话框等,根据用户的点击情况执行相应的 Perl 子程序.Tk库一方面用到了 Perl 的便捷,另一方面又不得不与虽然强大但是却很原始难懂的X窗口系统打交道.

GTK+ 也完成相似的任务,但是却更简单。GTK+ 提供所有的窗口,按钮,文本标记,文本输入框,一切我们的程序用的到的图形控件。而且,严格的说还提供主窗口事件等待循环,以便监视用户的动作。

GNOME 库则在 GTK+ 的基础上进行了更高一个层次的抽象,为我们提供更高层的图形对象,比如主应用程序窗口,弹出窗口,按钮板,对话框,颜色字体选择器,甚至还提供与GNOME环境中其它部分的粘合交互通信,比如拼写检查,计算器及其它应用程序资源。

* 这里值得指出,有一个VB风格的集成图形编程环境,叫 Glade,支持像 VB 一样拖放控件。它能自动产生 Perl 代码,用 Glade 你会发现开发图形界面十分简单,但是我们还是建议你应该把这个教程看下去,这样你才能看懂那些产生的 perl 代码。 mWzLinux联盟
Hello,WorldmWzLinux联盟
这里我们展示经典的 “Hello,World” 程序的两个版本,一个用 GTK+ 实现,一个用 GNOME 实现mWzLinux联盟
GTK+ 版: 

   1 #!/usr/bin/perl -wmWzLinux联盟
   2mWzLinux联盟
   3 use strict;mWzLinux联盟
   4 use Gnome;mWzLinux联盟
   5 mWzLinux联盟
   6 my $NAME = 'Hello World';mWzLinux联盟
   7mWzLinux联盟
   8 init Gnome $NAME;mWzLinux联盟
   9mWzLinux联盟
  10 my $w = new Gtk::Window -toplevel;mWzLinux联盟
  11mWzLinux联盟
  12 my $label = new Gtk::Label "Hello, world";mWzLinux联盟
  13 $w->add($label);mWzLinux联盟
  14mWzLinux联盟
  15 show_all $w;mWzLinux联盟
  16 mWzLinux联盟
  17 main Gtk;mWzLinux联盟
在第四行,装载 Gnome 模块,这样就将一并装载其下的 GTK+ 模块。第八行注册并初始化这个程序,分配我们在该程序中需要的资源,init 语句后面根这个程序的标题,它将显示在标题栏。 mWzLinux联盟
在第十行,创建主窗口,也就是最顶层的窗口,它不是任何其它组件的子窗口。然后,我们创建内容为 “Hello,world” 的消息文本标签,任何我们想要在窗口中显示的文本都必须是派生于 Gtk::Label 对象的实例,在第十二行我们就是这样做的,并把派生的实例命名为 $label。但是仅仅是第十二行的一条语句没有任何作用,它仅仅创建了文本,却不能显示在任何地方显示出来。未了在窗口中显示它,我们必须用窗口的 add 方法把这个标签实例添加到待显示列。mWzLinux联盟
然后,我们决定在程序启动的时候应该显示上面。如果我们想要显示窗口中包含的所有的东西,在这里也就是那个消息文本标签,我们就需要调用窗口的 show_all 方法。注意,调用了 show_all 后窗口仍不会被显示,show_all 方法只是申明了程序运行的时候待显示的内容。mWzLinux联盟
最后,main Gtk 这条语句将把程序的控制权交给 GTK+ 的主事件等待循环,GTK+ 的主事件等待循环首先在屏幕上绘出窗口,在窗口里显示出文本,然后就等待用户的点击等动作了。mWzLinux联盟
*一旦运行到 main Gtk 语句,程序的状态就不确定了,以后发生的一切都要依赖于用户的动作。不象程序员通常编程时为整个程序设计好所有的运行流程,现在我们必须要适应这个被动的角色,要更具用户的动作来做出相应的响应,而要实现这一点,正如我们在后面看到的一样,多少得靠子函数。再次申明,当程序运行到 main Gtk 的时候,我们的工作就算完成了,而 GTK+ 监视用户动作则刚开始。

下面这个是程序的Gnome版:

     1  #!/usr/bin/perl -wmWzLinux联盟
     2  mWzLinux联盟
     3  use strict;mWzLinux联盟
     4  use Gnome;mWzLinux联盟
     5  mWzLinux联盟
     6  my $NAME = 'Hello World';mWzLinux联盟
     7  mWzLinux联盟
     8  init Gnome $NAME;mWzLinux联盟
     9  mWzLinux联盟
    10  my $app = new Gnome::App $NAME, $NAME;mWzLinux联盟
    11  mWzLinux联盟
    12  my $label = new Gtk::Label "Hello, world";mWzLinux联盟
    13  $app->set_contents($label);mWzLinux联盟
    14  mWzLinux联盟
    15  show_all $app;mWzLinux联盟
    16  mWzLinux联盟
    17  main Gtk;mWzLinux联盟
和上面的Gtk+版一样长,而且大部分语句都是一样的,下面这处有改动:

10 my $app = new Gnome::App $NAME, $NAME;mWzLinux联盟
不象在Gtk+中我们申明创建一个窗口,在这里我们从更高一层声明创建一整个程序。把程序的名称传递给 new,而且传递了两个。第一个是作为窗口的标题,第二个则是在 GNOME 的环境中对该程序进行注册。 把文本标签添加到窗口的语句也有变化: mWzLinux联盟
13 $app->set_contents($label);mWzLinux联盟
为什么在这里用 set_content 方法而不用 add 方法呢?这是由 GTK+ 把图形元素(也就是控件)显示在窗口中的方法决定的,GTK+ 如何显示图形元素由包含该图形元素的上一层元素,或称容器决定。通常,一个窗口只能放一个控件。但幸运的是很多控件都能自身包含其它的控件。而我们上面的那条语句则是申明,在窗口中只能放置文本标签类控件。 到现在你可能已经注意到了一点,当你用 GTK+ 编写好程序并运行它,然后点击程序中的退出按钮你却并不能退出,而不得用 Ctrl+C 或类似的强制方法退出。GNOME 中不存在这样的问题。当 GNOME 程序从窗口管理器中收到退出的通知时,它会给自己发送一个信号,当然不是 UNIX 内核中发送的那种信号,而是纯粹的 GNOME 特色的信号。我们需要捕捉这个信号,并且给这个信号编写一个相应的信号处理程序来退出程序。下面的语句就是完成这个功能:

mWzLinux联盟
    my $app = new Gnome::App $NAME, $NAME;mWzLinux联盟
    signal_connect $app 'delete_event',mWzLinux联盟
                         sub { Gtk->main_quit; return 0 };

我们指定了一个程序来处理 “delete event“ 信号,“delete event”信号意味这退出当前子程序,返回上一级程序。我们用一个匿名子程序来捕捉并处理它—-GTK+ 中的 main_quit 方法,这个方法将终止程序的主事件等待循环。 mWzLinux联盟
现在我们的程序就会完全的退出了。但是现在这个程序还不能做什么。

添加菜单条 mWzLinux联盟
像前面提到的,GNOME 优于 GTK+ 的地方在于,它提供更多我们在应用程序中需要用到的标准控件。现在来为我们的程序添加一个标准的菜单。在 signal_connect 语句后添加下面的内容

mWzLinux联盟
 $app->create_menus(mWzLinux联盟
        {type => 'subtree',mWzLinux联盟
         label => '_File',mWzLinux联盟
         subtree => [mWzLinux联盟
                {type => 'item',mWzLinux联盟
                 label => 'E_xit',mWzLinux联盟
                 pixmap_type => 'stock',mWzLinux联盟
                 pixmap_info => 'Menu_Quit'mWzLinux联盟
                }mWzLinux联盟
                    ]mWzLinux联盟
        },mWzLinux联盟
        {type => 'subtree',mWzLinux联盟
         label => '_Help',mWzLinux联盟
         subtree => [mWzLinux联盟
                {type => 'item', mWzLinux联盟
                 label => '_About...',mWzLinux联盟
                 pixmap_type => 'stock',mWzLinux联盟
                 pixmap_info => 'Menu_About'mWzLinux联盟
                }mWzLinux联盟
                    ]mWzLinux联盟
        }mWzLinux联盟
      );

mWzLinux联盟
我们为 create_menus 传递了一系列匿名的散列,每个散列都代表菜单中的一项。每个散列中的 subtree 关键字指明当前项下面还有子项。在散列的 label 关键字的值中,我们可以在需要定义为快捷键的字母前面加一个下划线。如上,Alt+ F就将打开菜单的 File 项。subtree 关键字的值其实可以是一个包含很多匿名散列的匿名数组,但是上面的程序段中,两个 subtree 关键字的值我们都只指定了一个匿名散列。 mWzLinux联盟
表征子项的散列中的 type 关键字都被赋于“item”,表示该子项为一个普通项,不像它的上一级包含子菜单。菜单的每个选项都可以有自己的图标。这里通过 “pixmap_type=>stock” 语句我们调用了 GNOME 自带的图标库,我们还用了 Menu_Quit 和 Menu_About 方法来实现标准的退出的弹出窗口功能。

现在,重新运行你的程序,你就将会看到菜单条了。还想来点特别炫的东西吗?我说过 GNOME 可以为你做到一切。用下面的语句启动程序: mWzLinux联盟
 LANG=fr_FR perl hello.pl

一切仍然正常,仍有菜单条,但是文字却变成了法语!实现这个转变的代码在哪里呢?GNOME 为你做了一切。LANG 后根pt_PT就将变成葡萄牙语,跟 de_DE 就将变成德语,跟 el_GR (如果你有那个字库的话)就将变成希腊语。神奇吧! 这里还有一个小问题:那个菜单好像出来能看不能用。由于我们已经知道了如何退出一个 GTK+ 程序,那么让我们首先让菜单的Exit项起作用。把这个菜单项的散列内容照下面修改:

mWzLinux联盟
                {type => 'item',mWzLinux联盟
                 label => 'E_xit',mWzLinux联盟
                 pixmap_type => 'stock',mWzLinux联盟
                 pixmap_info => 'Menu_Quit',mWzLinux联盟
                 callback => sub {Gtk->main_quit; return 0 }mWzLinux联盟
                }

mWzLinux联盟
正如我们前面说到的一样,当我们选中这个选项之后,GNOME 会自动执行我们为那个选项编写的子程序。

添加一个弹出窗口 mWzLinux联盟
现在再改写其它菜单项的程序,为它们添加弹出窗口的功能。同样,GNOME 将会为我们完成这一切。我们为 About… 指定一个子程序的引用,

mWzLinux联盟
{type => 'item',mWzLinux联盟
                 label => '_About...',mWzLinux联盟
                 pixmap_type => 'stock',mWzLinux联盟
                 pixmap_info => 'Menu_About',mWzLinux联盟
                 callback => chunk73189886chunk#38;about_boxmWzLinux联盟
                }

这个子程序会创建并在窗口上显示这个弹出窗口:

mWzLinux联盟
sub about_box {mWzLinux联盟
               my $about = new Gnome::About $NAME, "v1.0",mWzLinux联盟
                  "(C) Simon Cozens, 2000", ["Simon Cozens"],mWzLinux联盟
                "This program is released undermWzLinux联盟
 the same terms as Perl itself";mWzLinux联盟
             show $about;mWzLinux联盟
         }

mWzLinux联盟
用 Gnome:About 类可以创建弹出窗口的实例:在这里我们给弹出窗口传递了我们程序的名称,版本,版权信息,作者的姓名和其它评论。然后用显示主窗口用到的 show 方法来同样显示这个弹出窗口。当点击 “OK” 按钮的时候,这个弹出窗口就关闭。

添加更多的东西

GNOME 系统还提供另外两个很有特色的交互项:工具栏和状态栏。我们首先添加工具栏,在添加菜单的语句后添加下面的语句:

mWzLinux联盟
$app->create_toolbar(mWzLinux联盟
    {mWzLinux联盟
        type => 'item',mWzLinux联盟
        label => 'Exit',mWzLinux联盟
        pixmap_type => 'stock',mWzLinux联盟
        pixmap_info => 'Quit',mWzLinux联盟
        hint => "Click here to quit",mWzLinux联盟
        callback => sub { Gtk->main_quit },mWzLinux联盟
    }, {mWzLinux联盟
        type => 'item',mWzLinux联盟
        label => 'About...',mWzLinux联盟
        pixmap_type => 'stock',mWzLinux联盟
        pixmap_info => 'About',mWzLinux联盟
        hint => "More information about this app",mWzLinux联盟
        callback => chunk73189426chunk#38;about_boxmWzLinux联盟
    }mWzLinux联盟
   );

我们同样给 creat_toolbar 函数传递了一系列的匿名散列,而且散列的很多关键值都是你熟悉的。hint 关键值的内容定义当鼠标旋停在按钮上的时候显示的内容。而每个选项绑定的处理函数和选项的图标都和前面一样。 接着添加状态栏:

mWzLinux联盟
    my $bar = new Gnome::AppBar 0,1,"user" ;mWzLinux联盟
    $bar->set_status("   Welcome   ");

    $app->set_statusbar( $bar );

首先,创建一个 AppBar 实例,它是一个程序的状态栏。然后用 set_status 定义状态栏的初始信息。状态栏到现在就已经存在了,但是还不会在屏幕上被显示出来。因为还没有指定它是属于整个 GNOME 环境中那个应用程序。所以我们用 set_statusbar 方法给它指定归属。现在它就会在主窗口中显示出来了。

完整程序清单

下面是读完这个教程,一步步按照我们说的做所应该生成的程序清单:

mWzLinux联盟
    #!/usr/bin/perl -w

    use strict;mWzLinux联盟
    use Gnome;

    my $NAME = 'Hello World';

    init Gnome $NAME;

    my $app = new Gnome::App $NAME, $NAME;

    signal_connect $app 'delete_event', sub { Gtk->main_quit; return 0 };

    $app->create_menus(mWzLinux联盟
               {type => 'subtree',mWzLinux联盟
                label => '_File',mWzLinux联盟
                subtree => [mWzLinux联盟
                    {type => 'item',mWzLinux联盟
                     label => 'E_xit',mWzLinux联盟
                     pixmap_type => 'stock',mWzLinux联盟
                     pixmap_info => 'Menu_Quit',mWzLinux联盟
                     callback => sub { Gtk->main_quit; return 0 }mWzLinux联盟
                    }mWzLinux联盟
                       ]mWzLinux联盟
               },mWzLinux联盟
               {type => 'subtree',mWzLinux联盟
                label => '_Help',mWzLinux联盟
                subtree => [mWzLinux联盟
                    {type => 'item', mWzLinux联盟
                     label => '_About...',mWzLinux联盟
                     pixmap_type => 'stock',mWzLinux联盟
                     pixmap_info => 'Menu_About',mWzLinux联盟
                     callback => chunk73189196chunk#38;about_boxmWzLinux联盟
                    }mWzLinux联盟
                       ]mWzLinux联盟
               }mWzLinux联盟
              );

    $app->create_toolbar(mWzLinux联盟
                 {mWzLinux联盟
                  type => 'item', mWzLinux联盟
                  label => 'Exit', mWzLinux联盟
                  pixmap_type => 'stock', mWzLinux联盟
                  pixmap_info => 'Quit', mWzLinux联盟
                  hint => "Click here to quit",mWzLinux联盟
                  callback => sub { Gtk->main_quit }, mWzLinux联盟
                 }, {mWzLinux联盟
                 type => 'item',mWzLinux联盟
                 label => 'About...', mWzLinux联盟
                 pixmap_type => 'stock',mWzLinux联盟
                 pixmap_info => 'About',mWzLinux联盟
                 hint => "More information about this app",mWzLinux联盟
                 callback => chunk73189196chunk#38;about_boxmWzLinux联盟
                }mWzLinux联盟
                );

    my $label = new Gtk::Label "Hello, world";mWzLinux联盟
    $app->set_contents($label);

    my $bar = new Gnome::AppBar 0,1,"user" ;mWzLinux联盟
    $bar->set_status("   Welcome   ");mWzLinux联盟
    $app->set_statusbar( $bar );

    show_all $app;

    main Gtk;

    sub about_box {mWzLinux联盟
      my $about = new Gnome::About $NAME, "v1.0", mWzLinux联盟
      "(C) Simon Cozens, 2000", ["Simon Cozens"], mWzLinux联盟
      "This program is released under the same terms as Perl itself";mWzLinux联盟
      show $about;mWzLinux联盟
    }

=head1 Summary

这样,我们用 GNOME/Perl 创建了我们的第一个应用程序。它拥有标准的 GNOME 界面,有标准的菜单栏,工具栏,状态栏,弹出窗口。它无论是看起来,还是真正运行起来都像一个真正的 GNOME 应用程序。总共只有大约 70 行 Perl 代码。

下一次,我们会创建一个更有用的应用程序,一个食谱管理器。在里面我们将会用到一些稍微复杂一些的控件,比如容器,文本输入域,滚动条和列表框。mWzLinux联盟

Linux联盟收集整理 ,转贴请标明原始链接,如有任何疑问欢迎来本站Linux论坛讨论
评论】【加入收藏夹】【 】【打印】【关闭
※ 相关链接
 ·PERL CGI 常见问题  (2007-10-11 17:34:39)
 ·Perl CGI编程安全点滴  (2007-10-11 17:31:59)
 ·入门教程:Perl XML:接口篇  (2007-10-11 17:23:09)
 ·用Perl DBI连接MySQL数据库  (2007-10-11 17:19:55)
 ·Perl 字符匹配实例解说  (2007-10-11 17:07:59)
 ·用 perl 实现文件上传的代码  (2007-10-11 17:03:01)
 ·Brian 的 Perl 问题之万能指南  (2007-10-11 17:01:25)
 ·优化你的 Perl 代码  (2007-10-11 16:59:18)
 ·本地调试PERL CGI程序环境  (2007-10-11 16:50:19)
 ·perl入门教程:Perl 程序的属性详解  (2007-10-11 16:24:19)