1 # -*- coding: utf-8 -*-
3 # WAF build script - this file is part of Geany, a fast and lightweight IDE
5 # Copyright 2008-2012 Enrico Tröger <enrico(dot)troeger(at)uvena(dot)de>
6 # Copyright 2008-2012 Nick Treleaven <nick(dot)treleaven(at)btinternet(dot)com>
8 # This program is free software; you can redistribute it and/or modify
9 # it under the terms of the GNU General Public License as published by
10 # the Free Software Foundation; either version 2 of the License, or
11 # (at your option) any later version.
13 # This program is distributed in the hope that it will be useful,
14 # but WITHOUT ANY WARRANTY; without even the implied warranty of
15 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 # GNU General Public License for more details.
18 # You should have received a copy of the GNU General Public License
19 # along with this program; if not, write to the Free Software
20 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
23 This is a WAF build script (http://code.google.com/p/waf/).
24 It can be used as an alternative build system to autotools
25 for Geany. It does not (yet) cover all of the autotools tests and
26 configure options but all important things are working.
27 "make dist" should be done with autotools, most other targets and
28 functions should work better (regarding performance and flexibility)
31 Missing features: --enable-binreloc, make targets: dist, pdf (in doc/)
32 Known issues: Dependency handling is buggy, e.g. if src/document.h is
33 changed, depending source files are not rebuilt (maybe Waf bug).
35 The code of this file itself loosely follows PEP 8 with some exceptions
36 (line width 100 characters and some other minor things).
38 Requires WAF 1.6.1 and Python 2.5 (or later).
45 from waflib import Logs, Options, Scripting, Utils
46 from waflib.Configure import ConfigurationContext
47 from waflib.Errors import WafError
48 from waflib.TaskGen import feature, before_method
53 LINGUAS_FILE = 'po/LINGUAS'
54 MINIMUM_GTK_VERSION = '2.16.0'
55 MINIMUM_GTK3_VERSION = '3.0.0'
56 MINIMUM_GLIB_VERSION = '2.20.0'
62 mio_sources = set(['tagmanager/mio/mio.c'])
65 'tagmanager/ctags/abaqus.c',
66 'tagmanager/ctags/args.c',
67 'tagmanager/ctags/abc.c',
68 'tagmanager/ctags/actionscript.c',
69 'tagmanager/ctags/asciidoc.c',
70 'tagmanager/ctags/asm.c',
71 'tagmanager/ctags/basic.c',
72 'tagmanager/ctags/c.c',
73 'tagmanager/ctags/cobol.c',
74 'tagmanager/ctags/conf.c',
75 'tagmanager/ctags/css.c',
76 'tagmanager/ctags/ctags.c',
77 'tagmanager/ctags/diff.c',
78 'tagmanager/ctags/docbook.c',
79 'tagmanager/ctags/entry.c',
80 'tagmanager/ctags/fortran.c',
81 'tagmanager/ctags/get.c',
82 'tagmanager/ctags/haskell.c',
83 'tagmanager/ctags/haxe.c',
84 'tagmanager/ctags/html.c',
85 'tagmanager/ctags/js.c',
86 'tagmanager/ctags/keyword.c',
87 'tagmanager/ctags/latex.c',
88 'tagmanager/ctags/lregex.c',
89 'tagmanager/ctags/lua.c',
90 'tagmanager/ctags/make.c',
91 'tagmanager/ctags/markdown.c',
92 'tagmanager/ctags/matlab.c',
93 'tagmanager/ctags/nsis.c',
94 'tagmanager/ctags/nestlevel.c',
95 'tagmanager/ctags/objc.c',
96 'tagmanager/ctags/options.c',
97 'tagmanager/ctags/parse.c',
98 'tagmanager/ctags/pascal.c',
99 'tagmanager/ctags/r.c',
100 'tagmanager/ctags/perl.c',
101 'tagmanager/ctags/php.c',
102 'tagmanager/ctags/python.c',
103 'tagmanager/ctags/read.c',
104 'tagmanager/ctags/rest.c',
105 'tagmanager/ctags/ruby.c',
106 'tagmanager/ctags/sh.c',
107 'tagmanager/ctags/sort.c',
108 'tagmanager/ctags/sql.c',
109 'tagmanager/ctags/strlist.c',
110 'tagmanager/ctags/txt2tags.c',
111 'tagmanager/ctags/tcl.c',
112 'tagmanager/ctags/vhdl.c',
113 'tagmanager/ctags/verilog.c',
114 'tagmanager/ctags/vstring.c'])
116 tagmanager_sources = set([
117 'tagmanager/src/tm_file_entry.c',
118 'tagmanager/src/tm_project.c',
119 'tagmanager/src/tm_source_file.c',
120 'tagmanager/src/tm_symbol.c',
121 'tagmanager/src/tm_tag.c',
122 'tagmanager/src/tm_tagmanager.c',
123 'tagmanager/src/tm_work_object.c',
124 'tagmanager/src/tm_workspace.c'])
126 scintilla_sources = set(['scintilla/gtk/scintilla-marshal.c'])
128 geany_sources = set([
129 'src/about.c', 'src/build.c', 'src/callbacks.c', 'src/dialogs.c', 'src/document.c',
130 'src/editor.c', 'src/encodings.c', 'src/filetypes.c', 'src/geanyentryaction.c',
131 'src/geanymenubuttonaction.c', 'src/geanyobject.c', 'src/geanywraplabel.c',
132 'src/highlighting.c', 'src/keybindings.c',
133 'src/keyfile.c', 'src/log.c', 'src/main.c', 'src/msgwindow.c', 'src/navqueue.c', 'src/notebook.c',
134 'src/plugins.c', 'src/pluginutils.c', 'src/prefix.c', 'src/prefs.c', 'src/printing.c', 'src/project.c',
135 'src/sciwrappers.c', 'src/search.c', 'src/socket.c', 'src/stash.c',
137 'src/templates.c', 'src/toolbar.c', 'src/tools.c', 'src/sidebar.c',
138 'src/ui_utils.c', 'src/utils.c'])
141 'hicolor/16x16/apps': ['16x16/classviewer-class.png',
142 '16x16/classviewer-macro.png',
143 '16x16/classviewer-member.png',
144 '16x16/classviewer-method.png',
145 '16x16/classviewer-namespace.png',
146 '16x16/classviewer-other.png',
147 '16x16/classviewer-struct.png',
148 '16x16/classviewer-var.png',
150 'hicolor/16x16/actions': ['16x16/geany-build.png',
151 '16x16/geany-close-all.png',
152 '16x16/geany-save-all.png'],
153 'hicolor/24x24/actions': ['24x24/geany-build.png',
154 '24x24/geany-close-all.png',
155 '24x24/geany-save-all.png'],
156 'hicolor/32x32/actions': ['32x32/geany-build.png',
157 '32x32/geany-close-all.png',
158 '32x32/geany-save-all.png'],
159 'hicolor/48x48/actions': ['48x48/geany-build.png',
160 '48x48/geany-close-all.png',
161 '48x48/geany-save-all.png'],
162 'hicolor/48x48/apps': ['48x48/geany.png'],
163 'hicolor/scalable/apps': ['scalable/geany.svg'],
164 'hicolor/scalable/actions': ['scalable/geany-build.svg',
165 'scalable/geany-close-all.svg',
166 'scalable/geany-save-all.svg'],
167 'Tango/16x16/actions': ['tango/16x16/geany-save-all.png'],
168 'Tango/24x24/actions': ['tango/24x24/geany-save-all.png'],
169 'Tango/32x32/actions': ['tango/32x32/geany-save-all.png'],
170 'Tango/48x48/actions': ['tango/48x48/geany-save-all.png'],
171 'Tango/scalable/actions': ['tango/scalable/geany-save-all.svg']
173 geany_icons_indexes = {
174 'hicolor': ['index.theme'],
175 'Tango': ['tango/index.theme']
181 conf.check_waf_version(mini='1.6.1')
183 conf.load('compiler_c')
184 is_win32 = _target_is_win32(conf)
186 conf.check_cc(header_name='fcntl.h', mandatory=False)
187 conf.check_cc(header_name='fnmatch.h', mandatory=False)
188 conf.check_cc(header_name='glob.h', mandatory=False)
189 conf.check_cc(header_name='sys/time.h', mandatory=False)
190 conf.check_cc(header_name='sys/types.h', mandatory=False)
191 conf.check_cc(header_name='sys/stat.h', mandatory=False)
192 conf.define('HAVE_STDLIB_H', 1) # are there systems without stdlib.h?
193 conf.define('STDC_HEADERS', 1) # an optimistic guess ;-)
194 _add_to_env_and_define(conf, 'HAVE_REGCOMP', 1) # needed for CTags
196 conf.check_cc(function_name='fgetpos', header_name='stdio.h', mandatory=False)
197 conf.check_cc(function_name='ftruncate', header_name='unistd.h', mandatory=False)
198 conf.check_cc(function_name='gethostname', header_name='unistd.h', mandatory=False)
199 conf.check_cc(function_name='mkstemp', header_name='stdlib.h', mandatory=False)
200 conf.check_cc(function_name='strstr', header_name='string.h')
202 # check sunOS socket support
203 if Options.platform == 'sunos':
204 conf.check_cc(function_name='socket', lib='socket',
205 header_name='sys/socket.h', uselib_store='SUNOS_SOCKET', mandatory=True)
207 # check for cxx after the header and function checks have been done to ensure they are
208 # checked with cc not cxx
209 conf.load('compiler_cxx')
212 _load_intltool_if_available(conf)
214 # GTK / GIO version check
215 gtk_package_name = 'gtk+-3.0' if conf.options.use_gtk3 else 'gtk+-2.0'
216 minimum_gtk_version = MINIMUM_GTK3_VERSION if conf.options.use_gtk3 else MINIMUM_GTK_VERSION
217 conf.check_cfg(package=gtk_package_name, atleast_version=minimum_gtk_version, uselib_store='GTK',
218 mandatory=True, args='--cflags --libs')
219 conf.check_cfg(package='glib-2.0', atleast_version=MINIMUM_GLIB_VERSION, uselib_store='GLIB',
220 mandatory=True, args='--cflags --libs')
221 conf.check_cfg(package='gmodule-2.0', uselib_store='GMODULE',
222 mandatory=True, args='--cflags --libs')
223 conf.check_cfg(package='gio-2.0', uselib_store='GIO', args='--cflags --libs', mandatory=True)
224 gtk_version = conf.check_cfg(modversion=gtk_package_name, uselib_store='GTK') or 'Unknown'
225 conf.check_cfg(package='gthread-2.0', uselib_store='GTHREAD', args='--cflags --libs')
226 # remember GTK version for the build step
227 conf.env['gtk_package_name'] = gtk_package_name
228 conf.env['minimum_gtk_version'] = minimum_gtk_version
229 conf.env['use_gtk3'] = conf.options.use_gtk3
233 if conf.env['PREFIX'].lower() == tempfile.gettempdir().lower():
234 # overwrite default prefix on Windows (tempfile.gettempdir() is the Waf default)
235 new_prefix = os.path.join(str(conf.root), '%s-%s' % (APPNAME, VERSION))
236 _add_to_env_and_define(conf, 'PREFIX', new_prefix, quote=True)
237 _add_to_env_and_define(conf, 'BINDIR', os.path.join(new_prefix, 'bin'), quote=True)
238 _add_to_env_and_define(conf, 'DOCDIR', os.path.join(conf.env['PREFIX'], 'doc'), quote=True)
239 _add_to_env_and_define(conf, 'LIBDIR', conf.env['PREFIX'], quote=True)
240 conf.define('LOCALEDIR', os.path.join('share' 'locale'), quote=True)
241 # overwrite LOCALEDIR to install message catalogues properly
242 conf.env['LOCALEDIR'] = os.path.join(conf.env['PREFIX'], 'share/locale')
243 # DATADIR is defined in objidl.h, so we remove it from config.h but keep it in env
244 conf.undefine('DATADIR')
245 conf.env['DATADIR'] = os.path.join(conf.env['PREFIX'], 'data')
246 conf.env.append_value('LINKFLAGS_cprogram', ['-mwindows'])
247 conf.env.append_value('LIB_WIN32', ['wsock32', 'uuid', 'ole32', 'iberty'])
249 conf.env['cshlib_PATTERN'] = '%s.so'
250 # DATADIR and LOCALEDIR are defined by the intltool tool
251 # but they are not added to the environment, so we need to
252 _add_define_to_env(conf, 'DATADIR')
253 _add_define_to_env(conf, 'LOCALEDIR')
254 docdir = os.path.join(conf.env['DATADIR'], 'doc', 'geany')
255 libdir = os.path.join(conf.env['PREFIX'], 'lib')
256 mandir = os.path.join(conf.env['DATADIR'], 'man')
257 _define_from_opt(conf, 'DOCDIR', conf.options.docdir, docdir)
258 _define_from_opt(conf, 'LIBDIR', conf.options.libdir, libdir)
259 _define_from_opt(conf, 'MANDIR', conf.options.mandir, mandir)
261 revision = _get_git_rev(conf)
263 conf.define('ENABLE_NLS', 1)
264 conf.define('GEANY_LOCALEDIR', '' if is_win32 else conf.env['LOCALEDIR'], quote=True)
265 conf.define('GEANY_DATADIR', 'data' if is_win32 else conf.env['DATADIR'], quote=True)
266 conf.define('GEANY_DOCDIR', conf.env['DOCDIR'], quote=True)
267 conf.define('GEANY_LIBDIR', '' if is_win32 else conf.env['LIBDIR'], quote=True)
268 conf.define('GEANY_PREFIX', '' if is_win32 else conf.env['PREFIX'], quote=True)
269 conf.define('PACKAGE', APPNAME, quote=True)
270 conf.define('VERSION', VERSION, quote=True)
271 conf.define('REVISION', revision or '-1', quote=True)
273 conf.define('GETTEXT_PACKAGE', APPNAME, quote=True)
277 conf.options.no_vte = True
279 _define_from_opt(conf, 'HAVE_PLUGINS', not conf.options.no_plugins, None)
280 _define_from_opt(conf, 'HAVE_SOCKET', not conf.options.no_socket, None)
281 _define_from_opt(conf, 'HAVE_VTE', not conf.options.no_vte, None)
283 conf.write_config_header('config.h', remove=False)
285 # some more compiler flags
286 conf.env.append_value('CFLAGS', ['-DHAVE_CONFIG_H'])
287 if revision is not None:
288 conf.env.append_value('CFLAGS', ['-g', '-DGEANY_DEBUG'])
290 conf.env.append_value('CFLAGS', ['-DGTK'])
291 conf.env.append_value('CXXFLAGS',
292 ['-DNDEBUG', '-DGTK', '-DSCI_LEXER', '-DG_THREADS_IMPL_NONE'])
295 Logs.pprint('BLUE', 'Summary:')
296 conf.msg('Install Geany ' + VERSION + ' in', conf.env['PREFIX'])
297 conf.msg('Using GTK version', gtk_version)
298 conf.msg('Build with plugin support', conf.options.no_plugins and 'no' or 'yes')
299 conf.msg('Use virtual terminal support', conf.options.no_vte and 'no' or 'yes')
300 if revision is not None:
301 conf.msg('Compiling Git revision', revision)
305 opt.load('compiler_cc')
306 opt.load('compiler_cxx')
310 opt.add_option('--disable-plugins', action='store_true', default=False,
311 help='compile without plugin support [default: No]', dest='no_plugins')
312 opt.add_option('--disable-socket', action='store_true', default=False,
313 help='compile without support to detect a running instance [[default: No]',
315 opt.add_option('--disable-vte', action='store_true', default=False,
316 help='compile without support for an embedded virtual terminal [[default: No]',
318 opt.add_option('--enable-gtk3', action='store_true', default=False,
319 help='compile with GTK3 support (experimental) [[default: No]',
322 opt.add_option('--mandir', type='string', default='',
323 help='man documentation', dest='mandir')
324 opt.add_option('--docdir', type='string', default='',
325 help='documentation root', dest='docdir')
326 opt.add_option('--libdir', type='string', default='',
327 help='object code libraries', dest='libdir')
329 opt.add_option('--hackingdoc', action='store_true', default=False,
330 help='generate HTML documentation from HACKING file', dest='hackingdoc')
334 is_win32 = _target_is_win32(bld)
336 if bld.cmd == 'clean':
337 _remove_linguas_file()
338 if bld.cmd in ('install', 'uninstall'):
339 bld.add_post_fun(_post_install)
341 def build_plugin(plugin_name, install=True):
343 instpath = '${PREFIX}/lib' if is_win32 else '${LIBDIR}/geany'
348 features = ['c', 'cshlib'],
349 source = 'plugins/%s.c' % plugin_name,
350 includes = ['.', 'src/', 'scintilla/include', 'tagmanager/src'],
351 defines = 'G_LOG_DOMAIN="%s"' % plugin_name,
352 target = plugin_name,
353 uselib = ['GTK', 'GLIB', 'GMODULE'],
354 install_path = instpath)
358 features = ['c', 'cstlib'],
359 source = ctags_sources,
362 includes = ['.', 'tagmanager', 'tagmanager/ctags'],
363 defines = 'G_LOG_DOMAIN="CTags"',
365 install_path = None) # do not install this library
369 features = ['c', 'cstlib'],
370 source = tagmanager_sources,
372 target = 'tagmanager',
373 includes = ['.', 'tagmanager', 'tagmanager/ctags'],
374 defines = 'G_LOG_DOMAIN="Tagmanager"',
375 uselib = ['GTK', 'GLIB'],
376 install_path = None) # do not install this library
380 features = ['c', 'cstlib'],
381 source = mio_sources,
384 includes = ['.', 'tagmanager/mio/'],
385 defines = 'G_LOG_DOMAIN="MIO"',
386 uselib = ['GTK', 'GLIB'],
387 install_path = None) # do not install this library
390 files = bld.srcnode.ant_glob('scintilla/**/*.cxx', src=True, dir=False)
391 scintilla_sources.update(files)
393 features = ['c', 'cxx', 'cxxstlib'],
395 target = 'scintilla',
396 source = scintilla_sources,
397 includes = ['.', 'scintilla/include', 'scintilla/src', 'scintilla/lexlib'],
398 uselib = ['GTK', 'GLIB', 'GMODULE'],
399 install_path = None) # do not install this library
402 if bld.env['HAVE_VTE'] == 1:
403 geany_sources.add('src/vte.c')
405 geany_sources.add('src/win32.c')
406 geany_sources.add('geany_private.rc')
409 features = ['c', 'cxx', 'cprogram'],
412 source = geany_sources,
413 includes = ['.', 'scintilla/include', 'tagmanager/src'],
414 defines = ['G_LOG_DOMAIN="Geany"', 'GEANY_PRIVATE'],
415 uselib = ['GTK', 'GLIB', 'GMODULE', 'GIO', 'GTHREAD', 'WIN32', 'SUNOS_SOCKET'],
416 use = ['scintilla', 'ctags', 'tagmanager', 'mio'])
420 source = ['plugins/genapi.py', 'src/plugins.c'],
421 name = 'geanyfunctions.h',
422 before = ['c', 'cxx'],
423 cwd = '%s/plugins' % bld.path.abspath(),
424 rule = '%s genapi.py -q' % sys.executable)
427 if bld.env['HAVE_PLUGINS'] == 1:
428 build_plugin('classbuilder')
429 build_plugin('demoplugin', False)
430 build_plugin('export')
431 build_plugin('filebrowser')
432 build_plugin('htmlchars')
433 build_plugin('saveactions')
434 build_plugin('splitwindow')
437 if bld.env['INTLTOOL']:
439 features = ['linguas', 'intltool_po'],
441 install_path = '${LOCALEDIR}',
446 source = 'geany.pc.in',
447 dct = {'VERSION': VERSION,
448 'DEPENDENCIES': '%s >= %s glib-2.0 >= %s' % \
449 (bld.env['gtk_package_name'],
450 bld.env['minimum_gtk_version'],
451 MINIMUM_GLIB_VERSION),
452 'prefix': bld.env['PREFIX'],
453 'exec_prefix': '${prefix}',
454 'libdir': '${exec_prefix}/lib',
455 'includedir': '${prefix}/include',
456 'datarootdir': '${prefix}/share',
457 'datadir': '${datarootdir}',
458 'localedir': '${datarootdir}/locale'})
462 if bld.env['INTLTOOL']:
464 features = 'intltool_in',
465 source = 'geany.desktop.in',
466 flags = ['-d', '-q', '-u', '-c'],
467 install_path = '${DATADIR}/applications')
472 source = 'doc/geany.1.in',
474 dct = {'VERSION': VERSION,
475 'GEANY_DATA_DIR': bld.env['DATADIR'] + '/geany'},
476 install_path = '${MANDIR}/man1')
481 source = 'geany.spec.in',
482 target = 'geany.spec',
484 dct = {'VERSION': VERSION})
489 source = 'doc/Doxyfile.in',
490 target = 'doc/Doxyfile',
492 dct = {'VERSION': VERSION})
499 bld.install_files('${PREFIX}/include/geany', '''
500 src/document.h src/editor.h src/encodings.h src/filetypes.h src/geany.h
501 src/highlighting.h src/keybindings.h src/msgwindow.h src/plugindata.h
502 src/prefs.h src/project.h src/search.h src/stash.h src/support.h
503 src/templates.h src/toolbar.h src/ui_utils.h src/utils.h src/build.h src/gtkcompat.h
504 plugins/geanyplugin.h plugins/geanyfunctions.h''')
505 bld.install_files('${PREFIX}/include/geany/scintilla', '''
506 scintilla/include/SciLexer.h scintilla/include/Scintilla.h
507 scintilla/include/Scintilla.iface scintilla/include/ScintillaWidget.h ''')
508 bld.install_files('${PREFIX}/include/geany/tagmanager', '''
509 tagmanager/src/tm_file_entry.h tagmanager/src/tm_project.h
510 tagmanager/src/tm_source_file.h
511 tagmanager/src/tm_symbol.h tagmanager/src/tm_tag.h
512 tagmanager/src/tm_tagmanager.h tagmanager/src/tm_work_object.h
513 tagmanager/src/tm_workspace.h ''')
515 base_dir = '${PREFIX}' if is_win32 else '${DOCDIR}'
516 ext = '.txt' if is_win32 else ''
517 html_dir = '' if is_win32 else 'html/'
518 html_name = 'Manual.html' if is_win32 else 'index.html'
519 for filename in 'AUTHORS ChangeLog COPYING README NEWS THANKS TODO'.split():
520 basename = _uc_first(filename, bld)
521 destination_filename = '%s%s' % (basename, ext)
522 destination = os.path.join(base_dir, destination_filename)
523 bld.install_as(destination, filename)
525 start_dir = bld.path.find_dir('doc/images')
526 bld.install_files('${DOCDIR}/%simages' % html_dir, start_dir.ant_glob('*.png'), cwd=start_dir)
527 bld.install_as('${DOCDIR}/%s' % _uc_first('manual.txt', bld), 'doc/geany.txt')
528 bld.install_as('${DOCDIR}/%s%s' % (html_dir, html_name), 'doc/geany.html')
529 bld.install_as('${DOCDIR}/ScintillaLicense.txt', 'scintilla/License.txt')
531 bld.install_as('${DOCDIR}/ReadMe.I18n.txt', 'README.I18N')
532 bld.install_as('${DOCDIR}/Hacking.txt', 'HACKING')
534 data_dir = '' if is_win32 else 'geany'
535 start_dir = bld.path.find_dir('data')
536 bld.install_as('${DATADIR}/%s/GPL-2' % data_dir, 'COPYING')
537 bld.install_files('${DATADIR}/%s' % data_dir, start_dir.ant_glob('filetype*'), cwd=start_dir)
538 bld.install_files('${DATADIR}/%s' % data_dir, start_dir.ant_glob('*.tags'), cwd=start_dir)
539 bld.install_files('${DATADIR}/%s' % data_dir, 'data/geany.glade')
540 bld.install_files('${DATADIR}/%s' % data_dir, 'data/snippets.conf')
541 bld.install_files('${DATADIR}/%s' % data_dir, 'data/ui_toolbar.xml')
542 if bld.env['use_gtk3']:
543 bld.install_files('${DATADIR}/%s' % data_dir, 'data/geany.css')
545 bld.install_files('${DATADIR}/%s' % data_dir, 'data/geany.gtkrc')
547 start_dir = bld.path.find_dir('data/colorschemes')
548 template_dest = '${DATADIR}/%s/colorschemes' % data_dir
549 bld.install_files(template_dest, start_dir.ant_glob('*'), cwd=start_dir)
550 start_dir = bld.path.find_dir('data/templates')
551 template_dest = '${DATADIR}/%s/templates' % data_dir
552 bld.install_files(template_dest, start_dir.ant_glob('**/*'), cwd=start_dir, relative_trick=True)
554 for dest, srcs in geany_icons.items():
555 dest_dir = os.path.join('${PREFIX}/share/icons' if is_win32 else '${DATADIR}/icons', dest)
556 bld.install_files(dest_dir, srcs, cwd=bld.path.find_dir('icons'))
557 # install theme indexes on Windows
559 for dest, srcs in geany_icons_indexes.items():
560 bld.install_files(os.path.join('${PREFIX}/share/icons', dest), srcs, cwd=bld.path.find_dir('icons'))
564 Scripting.distclean(ctx)
565 _remove_linguas_file()
568 def _remove_linguas_file():
569 # remove LINGUAS file as well
571 os.unlink(LINGUAS_FILE)
577 @before_method('apply_intltool_po')
578 def write_linguas_file(self):
579 if os.path.exists(LINGUAS_FILE):
582 if 'LINGUAS' in self.env:
583 files = self.env['LINGUAS']
584 for po_filename in files.split(' '):
585 if os.path.exists('po/%s.po' % po_filename):
586 linguas += '%s ' % po_filename
588 files = os.listdir('%s/po' % self.path.abspath())
590 for filename in files:
591 if filename.endswith('.po'):
592 linguas += '%s ' % filename[:-3]
593 file_h = open(LINGUAS_FILE, 'w')
594 file_h.write('# This file is autogenerated. Do not edit.\n%s\n' % linguas)
598 def _post_install(ctx):
599 is_win32 = _target_is_win32(ctx)
602 for d in 'hicolor', 'Tango':
603 theme_dir = Utils.subst_vars('${DATADIR}/icons/' + d, ctx.env)
604 icon_cache_updated = False
605 if not ctx.options.destdir:
606 ctx.exec_command('gtk-update-icon-cache -q -f -t %s' % theme_dir)
607 Logs.pprint('GREEN', 'GTK icon cache updated.')
608 icon_cache_updated = True
609 if not icon_cache_updated:
610 Logs.pprint('YELLOW', 'Icon cache not updated. After install, run this:')
611 Logs.pprint('YELLOW', 'gtk-update-icon-cache -q -f -t %s' % theme_dir)
615 """update the message catalogs for internationalization"""
616 potfile = '%s.pot' % APPNAME
617 os.chdir('%s/po' % top)
620 old_size = os.stat(potfile).st_size
623 ctx.exec_command('intltool-update --pot -g %s' % APPNAME)
624 size_new = os.stat(potfile).st_size
625 if size_new != old_size:
626 Logs.pprint('CYAN', 'Updated POT file.')
627 Logs.pprint('CYAN', 'Updating translations')
628 ret = ctx.exec_command('intltool-update -r -g %s' % APPNAME)
630 Logs.pprint('RED', 'Updating translations failed')
632 Logs.pprint('CYAN', 'POT file is up to date.')
634 Logs.pprint('RED', 'Failed to generate pot file.')
638 """generate API reference documentation"""
639 basedir = ctx.path.abspath()
640 doxygen = _find_program(ctx, 'doxygen')
641 doxyfile = '%s/%s/doc/Doxyfile' % (basedir, out)
643 Logs.pprint('CYAN', 'Generating API documentation')
644 ret = ctx.exec_command('%s %s' % (doxygen, doxyfile))
646 raise WafError('Generating API documentation failed')
647 # update hacking.html
648 cmd = _find_rst2html(ctx)
649 ctx.exec_command('%s -stg --stylesheet=geany.css %s %s' % (cmd, '../HACKING', 'hacking.html'))
654 """generate HTML documentation"""
655 # first try rst2html.py as it is the upstream default, fall back to rst2html
656 cmd = _find_rst2html(ctx)
658 Logs.pprint('CYAN', 'Generating HTML documentation')
659 ctx.exec_command('%s -stg --stylesheet=geany.css %s %s' % (cmd, 'geany.txt', 'geany.html'))
663 def _find_program(ctx, cmd, **kw):
667 ctx = ConfigurationContext()
670 return ctx.find_program(cmd, **kw)
673 def _find_rst2html(ctx):
674 cmds = ['rst2html.py', 'rst2html']
676 cmd = _find_program(ctx, command, mandatory=False)
681 'rst2html.py could not be found. Please install the Python docutils package.')
685 def _add_define_to_env(conf, key):
686 value = conf.get_define(key)
688 value = value.replace('"', '')
689 conf.env[key] = value
692 def _add_to_env_and_define(conf, key, value, quote=False):
693 conf.define(key, value, quote)
694 conf.env[key] = value
697 def _define_from_opt(conf, define_name, opt_value, default_value, quote=1):
698 value = default_value
700 if isinstance(opt_value, bool):
704 if value is not None:
705 _add_to_env_and_define(conf, define_name, value, quote)
707 conf.undefine(define_name)
710 def _get_git_rev(conf):
711 if not os.path.isdir('.git'):
715 cmd = 'git rev-parse --short --revs-only HEAD'
716 revision = conf.cmd_and_log(cmd).strip()
723 def _load_intltool_if_available(conf):
725 conf.load('intltool')
726 if 'LINGUAS' in os.environ:
727 conf.env['LINGUAS'] = os.environ['LINGUAS']
729 # on Windows, we don't hard depend on intltool, on all other platforms raise an error
730 if not _target_is_win32(conf):
734 def _target_is_win32(ctx):
735 if 'is_win32' in ctx.env:
737 return ctx.env['is_win32']
739 if sys.platform == 'win32':
742 if ctx.env and 'CC' in ctx.env:
743 env_cc = ctx.env['CC']
744 if not isinstance(env_cc, str):
745 env_cc = ''.join(env_cc)
746 is_win32 = (env_cc.find('mingw') != -1)
749 # cache for future checks
750 ctx.env['is_win32'] = is_win32
754 def _uc_first(string, ctx):
755 if _target_is_win32(ctx):
756 return string.title()