当前位置:Linux教程 - Kde - KDE项目开发人员FAQ

KDE项目开发人员FAQ

KDE项目小组最近推出了最新的开发人员FAQ,由KDE项目开发人员David Faure编写,包含了KDE开发的方方面面,内容十分详尽。相信您看过这个FAQ后,将对KDE的开发过程有一个非常清晰地认识,没准以后就成为了一个KDE开发高手了呢。本FAQ分为基本问题、技术问题和调试问题三部分。

原文:http://developer.kde.org/documentation/other/developer-faq.html。
原问题由Philippe Fremy列出,David Faure回答。请把其他问题、回应或者评论发送给pfremy@chez.com。

KDE项目开发人员基本问题解答

Q:我想开发新的应用程序,你对此有什么建议?

大家都知道,我们还需要编写更多的KDE应用程序,不过,已有的kde应用程序更需要得到你的帮助。如果你想了解一下目前需要大家帮忙的地方,请不妨看看本页面上的相关内容。
在开发新的应用程序之前,请最好先查看一下apps.kde.com站点的内容,从中了解现有应用程序的开发情况。你还可以查询kde-devel@kde.org邮件列表,了解一下是不是已经有人在着手开发你正计划的同一项目了。
Q:我是一名程序开发人员,我能为KDE做点什么?

请从工作列表中查看一下目前的开发任务-其中必有一项属于你。当前,KOffice和KDevelop软件尽管受到很多赞誉,但是相关的开发人员太少了,你可以不妨瞧瞧这两个项目。其实,并不是说一定要成为KDE核心开发人员才能对KDE有所贡献。KDE是高度模块化的程序项目,在不必了解整个系统的情况下,你可以通过自己的工作来改进项目中的某一部分。
你还可以查询kde-devel,看看谁需要你的帮助。

你还可以通过使用最新版本的KDE从中发现自己可以援手的地方。比如,主题生成器(theme generator)、konsole计划编辑器、游戏的改进等等。这么大的项目,里面肯定有遗漏什么特性的地方,就等你大显身手了!

你对某个特定领域很熟悉吗?你对它很感兴趣吗?瞧瞧其中有没有你能上手的应用程序,要不你干脆自己写一个。KDE特别需要更多的、面向非专业人士的应用程序。

Q:我不是开发人员,我又能做点什么呢?

好多任务并不需要任何开发技能。比如,编写程序评估报告(参见kde-promo邮件列表)、帮助编写文档(参见i18n.kde.org/doc)、搞翻译(参见i18n.kde.org)、找bug(参见bugs.kde.org)等等。
Q:要参与KDE的开发需要达到怎样的开发水准?我应该学习什么?阅读什么?

你应该熟悉C++。还应该读过Qt指南,浏览过Qt的文档,对Qt比较熟悉。你还应该阅读一下KDE指南,了解该软件的结构和文档 。你还可以阅读KDE方面的书籍,反正没什么坏处。当然,要成为kde开发人员也不必非要熟悉KDE的整体结构。kde技术用起来很简单,所以,你还是把注意力放到自己真要做的工作上为好,以后再了解一点其他方面的情况就可以了。

developer.kde.org和doc.trolltech.co(还有$QTDIR/doc/html)包括了大量相关材料,应该充分利用这些材料。
你可以通过阅读这些学习材料,查找示例目录,看看其他人编写的程序代码。阅读和编写程序代码是学习编程的最佳方式。

Q:什么是cvs?我怎么从cvs得到kde?

参见匿名cvs页面。
Q:我能把自己编写的应用程序加到KDE里吗?

有三个要求:1.你的应用程序必须在最新版本KDE下编译(CVS)。2.你的应用程序必须稳定。3.你的应用程序必须可维护。你的程序也许没有太多的bug,受到的赞许也很多,但人们希望你能修补自己的程序bug,实现合理的程序要求。还可以参见下一个问题。

Q:在KDE内部或者外部开发,哪种情况更好一些?

核心开发人员Waldo Bastian在一封有版权的邮件中是这样解释的:

作为KDE开发人员的一分子就意味着你必须同其他人合作。这种合作可以为开发人员带来很多权利,同时也赋予了开发人员更多的责任。

这些权利有:你的代码将出现在所有发布版上,人们可以修补代码中的bug,你可以获得免费的译文和文档,大量的程序漏洞报告等等。

另一方面就是其责任了:你必须和项目中的其他开发人员保持联系,其他人可能修改你的代码,你必须尊重发布冻结(release freezes),你可以获得很多bug报告,人们希望你修补这些bug来维护自己的代码。

你不能只选择权利而忽略你的责任,权利和责任是相互依存的。

总而言之,软件的作者应该把自己的应用程序放到CVS里面去。我们通常不把软件放到KDE CVS里,除非作者希望这么做。反过来,如果作者乐于在CVS以外开发自己的程序那也是他作为作者的权利。除非某个应用程序的实际开发团队出现了分裂,否则非要把项目开发分开来做是毫无道理的。

但是……,如果把你的代码置于开放源代码许可协议管辖之下并将其放在了KDE CVS之内,那么你就给世界以(正如KDE所为)不可取消的权利来使用你的代码。KDE会使用这一权利来保护KDE的利益,即便违背了作者自己的愿望也是如此。

Q:我如何获得使用cvs的权利?

请询问Stephan Kulow(coolo@kde.org)或者David Faure(faure@kde.org),解释一下你为什么需要使用cvs。如果你对某个不属于你的应用程序做出了贡献,那么你最好首先把你的代码作为程序补丁提交给作者,让作者使用这些代码。如果作者并不负责维护自己的应用程序,你就可能成为新的维护人员……。尽管cvs权限并无限制,我们还是希望你不要在其他开发人员同意的情况下就弄乱人家的代码。

你还必须尊重软件发布版本规划的特性冻结(feature freeze,在developer.kde.org上发布)。

Q:我的应用程序不稳定,但是我想它加入KDE。

我们一般首先把这些程序放在kdenonbeta里面(== kde-alpha)。请在该软件版本中开发,到准备好以后,再把你的程序放到适当的kde软件包里。

Q:我不想失去自己的cvs历史记录。

当把你的应用程序放到kde之内的时候请提供你的cvs知识库的tgz包。

Q:特性冻结(feature freeze)适用于kdenonbeta吗?

不,kdenonbeta不是发布的软件包。但是,如果你希望自己的应用程序加入软件包,那么请在发布测试版之前提出申请。

Q:我可以在同一台计算机上同时安装稳定的和不稳定的两套KDE吗?

可以,请查看kde1和kde2页面。这种情况同样适用于kde 2的两个不同版本。
Q:我如何通过CVS模块检查目录?

检查顶级目录用''cvs co -l modulename''命令,用''cvs co modulename/admin''命令则检查模块中的admin/dir目录,然后可以用''cvs co modulename/subdir''命令检查你希望检查的目录。比方说,为了从kdenonbeta中找到唯一的reaktivate目录,你可以采用以下命令:cvs co -l kdenonbeta cvs co kdenonbeta/admin cvs co kdenonbeta/reaktivate。

然后照一般编译方式进行编译即可。以上的回答也适用于以下问题:“我怎么能得到单一语言的kde-i18n?”。

Q:我怎么能得到象tarballan程序那样的单一kde程序?

kdesdk/scripts/cvs2pack可以从kde源代码树和软件包中抽取出特定的应用程序。




KDE项目开发人员技术问题解答
Q:我该如何着手编写一个新的应用程序?

最简单的办法是使用kdesdk/kapptemplate或者kdevelop产生Makefile.am文件。或者,你可以从其他应用程序那里拷贝一份Makefile.am并把它安装在已有KDE源代码的新顶级目录下。第三,你还可以用以前开发软件的老办法,但你这样一来就没有用到autoconf/automake框架的强大开发功能了。

Q:什么是dcop、kpart、kio、kdesktop、kdeinit……

请查看developer.kde.org,特别是结构文挡。另外还可以查看kde书籍。

Q:我真的需要使用dcop和kpart吗?

当然,你不必一定要使用它们,不过用了会好得多。KPart可以实现强大的代码重用。Dcop具有脚本能力,功能强大。这些技术用起来既简单,部署的范围又广,如果你会用却不使用那可真丢人的。

Q:Makefile是如何产生的?

请参看autoconf和automake手册了解其内容。KDE软件构建系统(build system)通过一种名叫am_edit(你可以在admin目录下找到)的程序对此进行了改进和提升。基本上,automake把Makefile.am转变为Makefile.in文件,然后am_edit运行并用KDE特有标签的真实含义取代Makefile.in文件中所有的KDE特有标签,configure会根据Makefile.in文件创建一个Makefile文件。
am_edit所处理的KDE特有标签的说明:

Moc文件
如果你所有的.cpp/.cc文件中都包括其.moc文件(这是快速编译下的建议方式),或者,如果你正在编译单一的二进制文件/库,那么只要使用METASOURCES=AUTO即可。万一在同一目录下有多个二进制文件/库,那么你可能需要如下所示来使用该命令:
libsomething_la_METASOURCES = myfile.moc myotherfile.moc mybinary_METASOURCES = someotherfile.moc

QT Designer文件
myprogram_SOURCES 后面增加.ui文件即可

QT Designer文件
myprogram_SOURCES 后面增加.ui文件即可

DCOP stub和skel
myprogram_SOURCES里增加将生成的.skel和.stub文件即可

图标
KDE_ICON = AUTO 把图标安装到全局KDE目录,而appicondir = $(kde_datadir)/myapp/icons appicon_ICON = AUTO 则把图标安装到“myapp”指定目录(建议在只有某一个程序需要该图标的情况下这么作,这样可以避免弄乱全局目录,同时还避免了发生和代码名称的冲突)。
为了运行 AUTO (以及为了让图标正常装载),你需要采用以下的命名规范:<depth><size>-<type>-<name>.png。
其中:depth取值hi或者lo,也就是指hicolor或者locolor(实际图标风格的名称),size是16、22或者32。type的取值是,应用程序图标是''app''、mimetype图标是''mime''、菜单、工具条按钮是 ''action''、某些文件系统(目录等)图标是 ''filesys''、光驱/软驱/硬盘等图标是''device''。
你可以在图标选择对话框内找到同样的图标类型。
注意这一规范只对源代码有效。安装的时候,图标会被拷贝到正确的目录,并被简单命名为<name>.png。

文档
KDE_LANG = en (文档采用的语言)
KDE_DOCS = AUTO (如果目录就是应用程序的名字)
KDE_DOCS = myapp 使用特定的应用程序名称

翻译
为了让你的应用程序可译,你必须用i18n()把代码中出现在用户面前的英语字符串扩起来 。你还要在你的顶级Makefile.am中定义一个消息目标。脚本会调用所有的消息目标来创建kde-i18n模块中的pot文件。然后,翻译器就可以创建包含这些翻译消息的.po文件。
现在让我们回到消息目标(messages target)。它应当对包含i18n的源代码调用XGETTEXT——这不等于_SOURCES参数下的调用,因为_SOURCES包含了.ui和.skel文件,这两种文件不能同xgettext一起工作。这就是为什么你通常使用*.cpp、*.h,而不是以上文件的原因(如果可能,请保证包含了子目录)。所以,简单情况下,消息目标看起来如下所示:
messages:
$(XGETTEXT) *.cpp *.h -o $(podir)/mypotfile.pot
mypotfile是你的主KInstance的名字(对应用程序来说,这就是传递给KAboutData的第一个参数,对组件来说,比如part和插件,这就是你创建的KInstance的名字)。
如果你有.ui(Qt designer)或者.rc(XML-UI)文件,使用 messages: rc.cpp脚本即会用当前目录内的ui和rc文件创建rc.cpp。如果你在子目录下有.ui或者.rc文件,那么,在XGETTEXT调用之前,你需要向消息目标中增加$(EXTRACTRC) */*.rc >> rc.cpp这一指令。
还有一个特殊情况是“tip”文件,这是一种XML文件,其中包含了显示给用户的提示。在这种情况下应该使用以下命令:
messages:
perl ./preparetips > tips.cc
$(XGETTEXT) *.cpp *.h tips.cc -o $(podir)/mypotfile.pot
rm -f tips.cc
比如,你可以在kdebase/ktip下找到以上这种脚本(显然,临时tips.cc文件到底用什么名字并不重要)。
最后的问题是编译和安装.po文件。在kde-i18n以内,Makefile.ams文件包含了KDE_LANG=language 和POFILES=AUTO两个指令,意思是目录下所有的.po文件都安装了该语言。
如果你提交了独立的应用程序,而且你想让该程序安装自己的po文件,那么你通常会有一个po/子目录,该目录内的Makefile.am的文件会认定 POFILES=AUTO。在这种情况下,.po文件在拷贝的时候会根据自己的名字,比如$(PACKAGE).mo而得以建立(比如,de.po安装到de/LC_MESSAGES/$(PACKAGE).mo下面,而fr.po 则安装到fr/LC_MESSAGES/$(PACKAGE).mo下面)。

Qt-only程序
默认情况下,am_edit需要kdecore产生“meta-unload”中间文件。为了在建立Qt-only程序时禁用它,请使用KDE_OPTIONS = qtonly。

Q:make参数有哪些?

all:默认参数(当键入“make”时)。
clean:删除所有生成的文件。
distclean:还删除Makefile.cvs产生的文件,在KDE内不太有用(参看“dist”概念下的dist和cvs-clean以了解更好的清除文件方式)。
dist:通常用CVS源代码生成tarball,但在KDE内没有受到良好的支持。最好使用kdesdk/scripts/cvs2pack完成同样的功能。
cvs-clean:(只用于CVS用户)删除不在CVS中的任何文件(警告,如果你还没有提交变更就不要使用它!)。
force-reedit:重新运行Makefile.am中的automake和am_edit。
install:很好,安装所有的东西。
install-exec:只安装二进制文件和库。
install-data:只安装数据文件。
check:编译测试程序(比如,由check_PROGRAMS定义的文件)。在“make check”期间实际运行某些测试是正确而且有益的,请参看kdelibs/arts/tests/Makefile.am。

Q:我检查了cvs,没有configure和Makefile?

使用make -f Makefile.cvs,该命令会运行所有产生Makefile的步骤。

Q:不同的编译选项有哪些?

--enable-debug:增加调试符号,禁用程序优化、打开kdDebug()记录(log)。
--disable-debug:上一参数的反面:启用程序优化并关闭kdDebug()记录。
--enable-final:把所有的.cpp文件连接为一个大型的.all_cpp.cpp文件,然后编译该文件(而不是编译其中的各个.cpp文件)。这会让整个编译过程变得更快,通常会产生更好的优化代码,但也需要更多的内存。不过,当不同源代码文件所包含的.h文件相互冲突时经常会出现编译错误,或者,当使用的不同源文件内具有同一名字的静态函数时也会出现编译错误。这样做在节省软件打包时间上占了便宜,但是对开发者而言并不是这样,因为某个文件中的一个改动就意味着编译全部软件包。
--disable-fast-perl:默认情况下,KDE使用perl而不是sh和sed把Makefile.in转变为Makefile。这是Michael Matz对autoconf的补充。你可以使用该选项禁用它,但编译速度就变慢了。

Q:你建议我应该采用什么编译选项?

如果你是一名开发人员,你应该明确地在--enable-debug参数下编译Qt和KDE。这样,你以后甚至可以在Qt和KDE函数内部调试自己的程序。<br>如果你仅仅是个用户,你也可以使用 --enable-debug。不过,KDE在你的硬盘上会占据更大的空间但不会减慢桌面电脑的运行速度。优点是:当应用程序崩溃的时候你可以得到堆栈的运行记录。如果你执行程序总是崩溃,那么你不妨去bugs.kde.org站点查看你的bug是否已经存在,否则你就可以提交这一个bug,这样对改进kde大有裨益。

对Qt来说,该编译选项在qt-copy/README.qt-copy中解释。

Q:增加编译速度的窍门何在?

请参看以上的 --enable-final 参数。“make final”把当前目录下的文件当作一个文件来用,即便没有采用 --enable-final也是这样。“make no-final”则执行当前目录下的正常编译(即便采用了--enable-final)。 请包含你的moc文件!顺便提一句:kdesdk/scripts/includemocs会自动地完成该功能。请购买更多的内存,更快的计算机和另一个处理器。在一部装备两个PIII 866 MHzCPU、带1G内存的计算机上,编译kde的速度飞快!还有,就是不要使用gcc-2.96。:)

Q:我应该采用什么缩排格式?

如果你在编写已有的应用程序,请尊重作者的缩排格式。否则,你想怎么用就怎么用。

Q:QSpinNumber的bug是怎么回事?

QSpinNumber中有个bug,这个bug还没有的得到纠正。你可以采用KSpinNumber,它几乎具有和QSpinNumber同样的特性。

Q:我编译的时候系统显示“virtual tables error”?

这通常是因为moc文件没有和源文件同步,或者完全没有链接。请检查你是否在运行正确的moc。“which moc”命令可以找出结果。请重新生成你的moc文件(make force-reedit;make clean;make)。
Q:使用dcop的时候,我在myClassHeader.h 文件中增加了k_dcop,但看起来好象什么特别的事情也没有发生?

把myClassHeader.kidl加到Makefile.am中,然后再次运行make。

Q:某些Makefile.am中有一个.stub文件,这是干嘛使的?

Stub没有很好的文档化。stub可以让你把dcop注册应用程序当作其方法就是自己dcop slot的对象。通常,应用程序都有一个appnameIface.h文件,其中包含了所有的dcop slot。你可以在Makefile.am中增加一个appnameIface.stub并使用目标appnameIface。请参看使用konqueror stub的kdebase/khelpcenter示例。

Q:我在myClassHeader.h文件中增加了Q_OBJECT,但是没有产生moc文件?

你需要am_edit重新解析你的Makefile.am来产生正确的Makefile。如果它是你在该目录下所使用的第一个Q_OBJECT,那么你需要在kdesdk/scripts下重新运行Makefile.cvs 或者create_makefile。否则你只要运行“make force-reedit”即可。

Q:为了让程序跑的更快点,我把自己全部类都放到了一个cpp文件里,我该如何得到生成的moc和kidl文件呢?

如果某些类使用了Q_OBJECT宏,那你最好别那样作。KDE框架(am_edit)对这种做法的支持不是很好。METASOURCES=file.cpp可能还更有用些。

Q:我开发了一个kpart(或者插件)。但我不没有root权限,所以我不能安装它。我该如何让kde知道它呢?

使用其它前缀(比如$HOME/kdeprefix)配置和安装你的应用程序并且让KDE知道这一前缀: 或者,你可以设置KDEDIRS为$HOME/kdeprefix:$KDEDIR达到以上目的。为了让KDE知道新的前缀,你还可以编辑/etc/kderc并增加:

[Directories]
prefixes=/the/new/prefix

但这样做还不能解决该问题,你还要在设置了新的KDEDIRS之后运行“kbuildsycoca”。

Q:当我向KTradher请求我的kpart库的时候,它没有被列出来。

当你安装新的服务(比如应用程序或者part)的时候必须重新建立mimetype数据库。理论上说,这个过程应该是自发的(kded会察看这些目录),如果要自己动手,请运行“kbuildsycoca”。

Q:启动另一程序的最佳方式是什么?

kde2迁移指南中有个好法子。请察看kdelibs/KDE2PORTING.html。




KDE项目开发人员调试问题解答
Q:我怎么才能避免Dr Konqi?

你必须设置环境变量KDE_DEBUG(设置为1或者你实际喜欢的任何东西)。

Q:什么是核心文件?我怎么才能得到核心文件?

所为核心文件就是应用程序崩溃的时候的内存影像。使用核心文件,你现在就可以知道设置了哪个变量,应用程序是在哪个地方崩溃的。某些发布版程序禁止生成核心文件。为了重新启用这一功能,请使用“ulimit -c unlimited”命令。

只要你在程序崩溃后获得核心文件,你就可以用gdb appname core命令察看核心文件的内容。这样就会对给定应用程序核心文件打开gdb,一旦gdb提示符出现,最有用的命令就是“bt”,该命令产生崩溃信息的记录(backtrace)。

要了解如何使用gdb的更多信息请参看该页。
Q:打印stederr上的debug输出有更好的方法吗?

有的,你可以用kdDebug():kdDebug() &lt;&lt; &quot;KMyApp just started&quot; &lt;&lt;endl;

该命令语法很像cout,“&lt;&lt;”之间可以使用多种内部类型。这样就会打印出调试信息,这些调试信息在程序发布的时候会自动关闭(通过--disable-debug)。如果你希望程序发布期间还要获得这些消息,那么,因为这些消息都是警告或者错误,你不妨使用kdWarning()或者kdError()达到这一目的。

组件和库最好使用调试区域代码,比如kdDebug(1234)。使用“kdebugdialog”程序(它是kdebase的一部分)可以关闭或者打开该区域号码的调试输出信息,“kdebugdialog --fullmode”还允许控制记录输出的位置。

说白了:不要使用qDebug(),该函数在程序发布的时候不会被禁用。还要避免使用assert()或者kdFatal(),他们会在出现问题的时候导致程序崩溃,对用户没有半点好处。最好在程序中检测错误,如果可能的话,输出kdWarning或者kdError再行恢复。

Q:调试我的应用程序可以使用什么工具?

kdDebug()函数是一种简单、高效的应用程序调试方式。

gdb,GNU调试器是逐步执行和检查变量的最快方法(最好用5.0版本,该版本比4.1.x好多了)。
kdbg是采用KDE GUI的gdb前端。它支持多种Qt类型(包括QString)。

Memory leak tracer :参看kdesdk/kmtrace。README解释得很全。

kdcop和dcop可以让用户浏览dcop接口、方便地执行dcop调用。

请查看该页面和kdesdk,那里有用的脚本很多。
Q:我在gdb下如何打印qstring?

请查看kdesdk,在你的~/.gdbinit中加入以下命令:

source /path/to/kde/sources/kdesdk/scripts/kde-devel-gdb

然后就可以在gdb中打印qstring myqstring察看其内容。

比如,QString myqstring = QString::fromLatin1(&quot;contents&quot;); 可以使用以下的命令来检查:

(gdb) printqstring myqstring
$1 = 99 ''c''
$2 = 111 ''o''
$3 = 110 ''n''
$4 = 116 ''t''
$5 = 101 ''e''
$6 = 110 ''n''
$7 = 116 ''t''
$8 = 115 ''s''

请参看kde-devel-gdb文件了解其它定义宏。

Q:当我调试kpart应用程序的时候我没有符号(symbol),我该怎么办?

你必须在主程序之后停止下来装载共享库的调试符号。之后,你就可以正常调试了。你甚至可以创建gdb宏以便停在被装载的part后面。以kword为例,我编写的代码如下所示:

define startkword
break main
run
break ''KoDocument::KoDocument(int, QWidget *, char const *, QObject *,
char const *, bool)''
cont

Q:我怎么调试ioslave?

请参看kdebase/kioslave/DEBUG.howto。