summaryrefslogtreecommitdiffstats
path: root/packaging
diff options
context:
space:
mode:
authorEduard Braun <eduard.braun2@gmx.de>2016-10-20 19:51:31 +0000
committerEduard Braun <eduard.braun2@gmx.de>2016-10-20 19:51:31 +0000
commit181667844fb6862fb0bbfee5e91601188047d7ca (patch)
treedb17a9640c12283819143afb37ea094db066db5e /packaging
parentUpdated Russian translation of the Windows installer (diff)
downloadinkscape-181667844fb6862fb0bbfee5e91601188047d7ca.tar.gz
inkscape-181667844fb6862fb0bbfee5e91601188047d7ca.zip
Packaging: Support for additional components in WIX installer
It's now possible to select specific translations and to choose wether or not to install Python, extensions and dictionaries. (bzr r15244.1.17)
Diffstat (limited to 'packaging')
-rw-r--r--packaging/wix/files.py67
-rw-r--r--packaging/wix/helpers.py42
-rw-r--r--packaging/wix/inkscape.wxs96
3 files changed, 149 insertions, 56 deletions
diff --git a/packaging/wix/files.py b/packaging/wix/files.py
index 8026a5259..7034021ac 100644
--- a/packaging/wix/files.py
+++ b/packaging/wix/files.py
@@ -3,9 +3,10 @@
from __future__ import print_function
import os
+import re
import uuid
-from helpers import get_inkscape_dist_dir
+from helpers import get_inkscape_dist_dir, get_inkscape_locales_and_names
directory_ids = {}
file_ids = {}
@@ -13,9 +14,12 @@ file_ids = {}
def indent(level):
indentstring = ''
for i in range(level):
- indentstring += ' '
+ indentstring += ' '
return indentstring
+def valid_id(identifier):
+ return identifier.replace('@','_')
+
def directory(root, breadcrumb, level, exclude=[]):
"""
list all files and directory recursivly
@@ -36,7 +40,7 @@ def directory(root, breadcrumb, level, exclude=[]):
wxs.write(indent(level + 1)+ "<File Id='file" + _id + "' Name='" + file + "' DiskId='1' Source='" + file_key + "' KeyPath='yes' />\n")
wxs.write(indent(level)+ "</Component>\n")
# then all directories
-
+
dirs = [ f for f in os.listdir(root) if os.path.isdir(os.path.join(root,f)) ]
for dir in dirs:
directory_key = breadcrumb + '__' + dir
@@ -45,15 +49,32 @@ def directory(root, breadcrumb, level, exclude=[]):
wxs.write(indent(level) + "<Directory Id='" + directory_ids[directory_key] + "' Name='" + dir + "'>\n")
directory(os.path.join(root, dir), directory_key, level + 1)
wxs.write(indent(level) + "</Directory>\n")
-
-
-def ComponentGroup(name, condition, level):
+
+def test_conditions(value, conditions):
+ """
+ check if "value" fullfills any of the "conditions", where a condition can be
+ - a string that has to be a substring of "value"
+ - a compiled regex pattern which has to match in "value"
+ """
+ if not isinstance(conditions, list):
+ conditions = [conditions]
+ for condition in conditions:
+ if isinstance(condition, basestring):
+ if condition in value:
+ return True
+ elif isinstance(condition, type(re.compile(''))):
+ if re.search(condition, value):
+ return True
+ return False
+
+
+def ComponentGroup(name, conditions, level):
"""
add componentgroup that contain all items from file_ids that match condition
remove the matched elements from file_ids
"""
global file_ids
- keys = [k for k in file_ids.keys() if condition in k]
+ keys = [k for k in file_ids.keys() if test_conditions(k, conditions)]
wxs.write(indent(level) + "<ComponentGroup Id='" + name + "'>\n")
for component in keys:
wxs.write(indent(level + 1) + "<ComponentRef Id='" + file_ids[component] + "' />\n")
@@ -61,9 +82,12 @@ def ComponentGroup(name, condition, level):
for key in keys:
del file_ids[key]
-#get directory containing the inkscape distribution files
+# get directory containing the Inkscape distribution files
inkscape_dist_dir = get_inkscape_dist_dir()
+# get locales currently supported by Inkscape (dict of the form {'de': 'German (de)'})
+locales = get_inkscape_locales_and_names()
+
with open('files.wxs', 'w') as wxs:
wxs.write("<!-- do not edit, this file is created by files.py tool any changes will be lost -->\n")
wxs.write("<Wix xmlns='http://schemas.microsoft.com/wix/2006/wi'>\n")
@@ -78,18 +102,33 @@ with open('files.wxs', 'w') as wxs:
print("found %d files" % len(file_ids.keys()))
wxs.write(indent(4) + "</Directory>\n")
wxs.write(indent(3) + "</Directory>\n")
- # link to ProgrmMenu
+ # link to ProgramMenu
wxs.write(indent(3) + "<Directory Id='ProgramMenuFolder'>\n")
wxs.write(indent(4) + "<Directory Id='ApplicationProgramsFolder' Name='$(var.FullProductName)'/>\n")
wxs.write(indent(3) + "</Directory>\n")
wxs.write(indent(3) + "<Directory Id='DesktopFolder' Name='Desktop' />\n")
wxs.write(indent(2) + "</Directory>\n")
- ComponentGroup("Examples", 'inkscape\\share\\examples', 2)
+
+ # Python
+ ComponentGroup("Python", 'inkscape\\python\\', 2)
+ # translations and localized content
+ for lang_code in sorted(locales):
+ ComponentGroup("Translation_" + valid_id(lang_code), ['\\' + lang_code + '\\',
+ re.compile(r'\.' + lang_code + r'\.[a-z]+$')], 2)
+ # other components
+ ComponentGroup("Extensions", 'inkscape\\share\\extensions\\', 2)
+ ComponentGroup("Examples", 'inkscape\\share\\examples\\', 2)
ComponentGroup("Tutorials", 'inkscape\\share\\tutorials\\', 2)
- ComponentGroup("Translations", '\\locale\\', 2)
+ ComponentGroup("Dictionaries", 'inkscape\\lib\\aspell-0.60\\', 2)
+ # everything that is left (which should be the Inkscape core unless inkscape_dist_dir contains unnecessary files or we defined our components poorly)
ComponentGroup("AllOther", '', 2)
+
+ # create a FeatureGroup for translations
+ wxs.write(indent(2) + "<FeatureGroup Id='Translations'>\n")
+ for lang_code in sorted(locales):
+ wxs.write(indent(3) + "<Feature Id='Translation_" + valid_id(lang_code) + "' Level='1' Title='" + locales[lang_code] + "' AllowAdvertise='no'>\n")
+ wxs.write(indent(4) + "<ComponentGroupRef Id='Translation_" + valid_id(lang_code) + "' />\n")
+ wxs.write(indent(3) + "</Feature>\n")
+ wxs.write(indent(2) + "</FeatureGroup>\n")
wxs.write(indent(1) + "</Fragment>\n")
wxs.write("</Wix>\n")
-
-
-
diff --git a/packaging/wix/helpers.py b/packaging/wix/helpers.py
index 5fe9e6a52..7bd706398 100644
--- a/packaging/wix/helpers.py
+++ b/packaging/wix/helpers.py
@@ -3,9 +3,11 @@
from __future__ import print_function
import os
+import re
import sys
-# check where to look for the inkscape files to bundle
+
+# check where to look for the Inkscape files to bundle
# - btool builds used [root]/inkscape
# - cmake builds use [root]/build/inkscape unless "DESTDIR" is specified
def get_inkscape_dist_dir():
@@ -20,4 +22,40 @@ def get_inkscape_dist_dir():
if not os.path.isdir(sourcedir):
print("could not find inkscape distribution files, please set environment variable 'INKSCAPE_DIST_PATH'")
sys.exit(1)
- return sourcedir \ No newline at end of file
+ return sourcedir
+
+
+# get the full list of available Inkscape UI translations (by looking at available .po files in the /po directory)
+def get_inkscape_locales():
+ files = os.listdir('..\\..\\po')
+ po_files = [file for file in files if file.endswith('.po')]
+ locales = [po_file[0:-3] for po_file in po_files if po_file.endswith('.po')]
+
+ return locales
+
+
+# get the list of available Inkscape UI translations (by parsing inkscape-preferences.cpp)
+def get_inkscape_locales_and_names():
+ re_languages = re.compile(r'Glib::ustring languages\[\] = \{(.+?)\};', re.DOTALL)
+ re_langValues = re.compile(r'Glib::ustring langValues\[\] = \{(.+?)\};', re.DOTALL)
+ re_quotes = re.compile(r'"(.*?)"')
+
+ # get the raw array contents from inkscape-preferences.cpp
+ with open('..\\..\\src\\ui\\dialog\\inkscape-preferences.cpp', 'r') as f:
+ languages = re.search(re_languages, f.read())
+ f.seek(0)
+ langValues = re.search(re_langValues, f.read())
+
+ # split array elements and extract strings
+ if languages and langValues:
+ languages = languages.group(1).split(',')
+ langValues = langValues.group(1).split(',')
+ languages = [re.search(re_quotes, language).group(1) for language in languages]
+ langValues = [re.search(re_quotes, langValue).group(1) for langValue in langValues]
+
+ # return the results as a dict (remove first element which is "System default")
+ if languages and langValues:
+ return dict(zip(langValues[1:], languages[1:]))
+ else:
+ print("Could not get the list of Inkscape translations from inkscape-preferences.cpp")
+ sys.exit(1)
diff --git a/packaging/wix/inkscape.wxs b/packaging/wix/inkscape.wxs
index 4766ec717..db055a46a 100644
--- a/packaging/wix/inkscape.wxs
+++ b/packaging/wix/inkscape.wxs
@@ -2,21 +2,21 @@
<Wix xmlns='http://schemas.microsoft.com/wix/2006/wi' xmlns:util="http://schemas.microsoft.com/wix/UtilExtension">
<?include version.wxi?>
- <!-- change Product Id for every new version and subversion, do not change UpgradeCode -->
+ <!-- change Product Id for every new version and subversion, do not change UpgradeCode -->
<Product Name="$(var.FullProductName)" Id='81922150-317e-4bb0-a31d-ff1c14f707c5' UpgradeCode='4d5fedaa-84a0-48be-bd2a-08246398361a' Language='1033' Codepage='1252' Version='$(var.ProductVersion)' Manufacturer='inkscape.org'>
<Package Id='*' Keywords='Installer' Description="Inkscape Installer" Comments='inkscape is registered trademark of inkscape.org' Manufacturer='inkscape.org' InstallerVersion='$(var.InstallerVersion)' Platform='$(var.Platform)' Languages='1033' Compressed='yes' SummaryCodepage='1252' />
-
- <Media Id='1' Cabinet='Sample.cab' EmbedCab='yes' DiskPrompt="CD-ROM #1" CompressionLevel="high"/>
+
+ <Media Id='1' Cabinet='Sample.cab' EmbedCab='yes' DiskPrompt="CD-ROM #1" CompressionLevel="none"/>
<Property Id='DiskPrompt' Value="inkscape Installation [1]" />
<Property Id='ALLUSERS' Value="2" />
-
- <MajorUpgrade DowngradeErrorMessage="A newer version is already installed." />
-
+
+ <MajorUpgrade DowngradeErrorMessage="A newer version is already installed." />
+
<DirectoryRef Id="ApplicationProgramsFolder">
<Component Id="ApplicationShortcut" Guid="37de8ea4-e83a-4e40-8f9c-c6066b78d935" Win64='$(var.Win64)' >
- <Shortcut Id="ApplicationStartMenuShortcut"
+ <Shortcut Id="ApplicationStartMenuShortcut"
Name="$(var.FullProductName)"
Description="Inkscape Vector Graphics Application"
Target="[INSTALLDIR]inkscape.exe"
@@ -32,7 +32,7 @@
<DirectoryRef Id="DesktopFolder">
<Component Id="DesktopShortcut" Guid="3afc08a7-05a1-40cf-90c2-0d6c042bfc41" Win64='$(var.Win64)'>
<!-- Shortcut Id="desktopFoobar10" Directory="DesktopFolder" Target="[INSTALLDIR]inkscape.exe" Name="$(var.FullProductName)" WorkingDirectory='INSTALLDIR' Icon="file_inkscape_exe" IconIndex="0" / -->
- <Shortcut Id="desktopFoobar10" Directory="DesktopFolder" Target="[INSTALLDIR]inkscape.exe" Name="$(var.FullProductName)" WorkingDirectory='INSTALLDIR' />
+ <Shortcut Id="DesktopShortcut" Directory="DesktopFolder" Target="[INSTALLDIR]inkscape.exe" Name="$(var.FullProductName)" WorkingDirectory='INSTALLDIR' />
<RemoveFolder Id="DesktopFolder" On="uninstall"/>
<RegistryValue Root="HKCU" Key="Software\inkscape.org\Inkscape" Name="desktop_installed" Type="integer" Value="1" KeyPath="yes"/>
</Component>
@@ -47,60 +47,76 @@
<Extension Id='svgz' ContentType='image/svg+xml'>
<Verb Id='open' Command='Open with Inkscape' TargetFile='file_inkscape_exe' Argument='"%1"' />
</Extension>
-
</ProgId>
</Component>
</DirectoryRef>
-
-
- <Feature Id='Complete' Title="$(var.FullProductName)" Description='The complete Package' Display='expand' Level='1' ConfigurableDirectory='INSTALLDIR' Absent="disallow" AllowAdvertise='no'>
- <!--
- <Feature Id='MainProgram' Level='1' Title='inkscape Application' Description='the inkscape Application' Absent="disallow" AllowAdvertise='no'>
- <ComponentRef Id='MainExecutable' />
- </Feature>
--->
- <!--
- <Feature Id='MainProgram' Level='1' Title='inkscape Application' Description='the inkscape Application' Absent="disallow" AllowAdvertise='no'>
- -->
+ <Feature Id='Inkscape' Level='1' Absent="disallow" Display="expand" ConfigurableDirectory='INSTALLDIR' AllowAdvertise='no'
+ Title="$(var.FullProductName)"
+ Description='Inkscape core files, shortcuts and file extension'>
+ <!-- core files, i.e. everything that does not fit into any of the other features -->
<ComponentGroupRef Id='AllOther' />
- <!--
- </Feature>
- -->
- <!-- shortcuts -->
- <Feature Id='ApplicationShortcut' Level='1' Title='Start Menu entry' Description='an entry in the start Menu' AllowAdvertise='no'>
+ <!-- shortcuts and file extensions -->
+ <Feature Id='ApplicationShortcut' Level='1' AllowAdvertise='no'
+ Title='Start Menu entry'
+ Description='Create a link in the start menu.'>
<ComponentRef Id='ApplicationShortcut' />
</Feature>
-
- <Feature Id='DesktopShortcut' Level='1' Title='Desktop link' Description='an link on the desktop' AllowAdvertise='no'>
+ <Feature Id='DesktopShortcut' Level='1' AllowAdvertise='no'
+ Title='Desktop shortcut'
+ Description='Create a link on the desktop.' >
<ComponentRef Id='DesktopShortcut' />
</Feature>
-
- <Feature Id='RegisterExtension' Level='1' Title='Register file extension' Description='register .svg and .svgz file extension in explorer context menu' AllowAdvertise='no'>
+ <Feature Id='RegisterExtension' Level='1' AllowAdvertise='no'
+ Title='Register file extensions'
+ Description='Register SVG files (.svg and .svgz) with Inkscape and add entries in Explorer context menu.'>
<ComponentRef Id='RegisterExtension' />
</Feature>
+ </Feature>
- <Feature Id='Examples' Level='1' Title='Examples' Description='examples as svg' AllowAdvertise='no'>
- <ComponentGroupRef Id='Examples' />
- </Feature>
+ <Feature Id='Python' Level='1' ConfigurableDirectory='INSTALLDIR' AllowAdvertise='no'
+ Title='Python 2.7'
+ Description='Bundled Distribution of Python 2.7 including modules required to run Inkscape extensions.'>
+ <ComponentGroupRef Id='Python' />
+ </Feature>
- <Feature Id='Translations' Level='1' Title='Translations' Description='translations' AllowAdvertise='no'>
- <ComponentGroupRef Id='Translations' />
+ <Feature Id='Additional' Level='1' ConfigurableDirectory='INSTALLDIR' AllowAdvertise='no'
+ Title="Additional files"
+ Description='Additional components to enhance Inkscape functionality and provide supplemental documentation.'>
+ <Feature Id='Extensions' Level='1' AllowAdvertise='no'
+ Title='Extensions (recommended)'
+ Description='Inkscape extensions (including many import and export plugins). Requires Python.'>
+ <ComponentGroupRef Id='Extensions' />
</Feature>
-
- <Feature Id='Tutorials' Level='1' Title='Tutorials' Description='tutorials as svg' AllowAdvertise='no'>
+ <Feature Id='Dictionaries' Level='1' AllowAdvertise='no'
+ Title='Dictionaries'
+ Description='GNU Aspell dictionaries of some common languages for spell checking in Inkscape' >
+ <ComponentGroupRef Id='Dictionaries' />
+ </Feature>
+ <Feature Id='Examples' Level='1' AllowAdvertise='no'
+ Title='Examples'
+ Description='Example files highlighting some of the features of the SVG file format and Inkscape functionality.' >
+ <ComponentGroupRef Id='Examples' />
+ </Feature>
+ <Feature Id='Tutorials' Level='1' AllowAdvertise='no'
+ Title='Tutorials'
+ Description='Tutorials on how to use specific Inkscape features.' >
<ComponentGroupRef Id='Tutorials' />
</Feature>
- <!--
- <ComponentRef Id='ProgramMenuDir' />
--->
</Feature>
+
+ <Feature Id='Translations' Level='1' ConfigurableDirectory='INSTALLDIR' AllowAdvertise='no'
+ Title='Translations'
+ Description='Translations and localized content for Inkscape. Note: Some translations might be incomplete, translators welcome!' >
+ <FeatureGroupRef Id='Translations' />
+ </Feature>
+
<!-- set license text -->
<WixVariable Id="WixUILicenseRtf" Value="gpl-2.0.rtf" />
<!-- set dialog custom bitmaps -->
<WixVariable Id="WixUIDialogBmp" Value="Bitmaps\dialog.bmp"/>
- <WixVariable Id="WixUIBannerBmp" Value="Bitmaps\banner.bmp"/>
+ <WixVariable Id="WixUIBannerBmp" Value="Bitmaps\banner.bmp"/>
<UIRef Id="WixUI_Mondo" />
<UIRef Id="WixUI_ErrorProgressText" />