summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorkali <kali@leap.se>2012-11-16 22:59:16 +0900
committerkali <kali@leap.se>2012-12-20 02:51:18 +0900
commitd04c93134ad3daaee0ca280824ab3288bfc5029c (patch)
treef00606c24c2efc7fcc15ec327d50a35a2a585572
parente98c3cc5fad75bea038dc67238e5ce85d701b1e1 (diff)
initial translation example.
-rw-r--r--Makefile2
-rw-r--r--data/leap_client.pro2
-rwxr-xr-xdata/mkpyqt.py271
-rw-r--r--data/resources/locale.qrc5
-rw-r--r--data/translations/leap_client_es_ES.qmbin0 -> 1450 bytes
-rw-r--r--data/translations/leap_client_es_ES.ts26
-rw-r--r--docs/translations.txt22
-rw-r--r--src/leap/app.py16
-rw-r--r--src/leap/gui/firstrun/intro.py10
-rw-r--r--src/leap/gui/locale_rc.py132
10 files changed, 478 insertions, 8 deletions
diff --git a/Makefile b/Makefile
index 59343dfc..d36c5601 100644
--- a/Makefile
+++ b/Makefile
@@ -16,7 +16,7 @@ COMPILED_DIR = src/leap/gui
UI_FILES =
#Qt resource files to compile
#images.qrc
-RESOURCES = mainwindow.qrc
+RESOURCES = mainwindow.qrc locale.qrc
#pyuic4 and pyrcc4 binaries
PYUIC = pyuic4
diff --git a/data/leap_client.pro b/data/leap_client.pro
new file mode 100644
index 00000000..01fbafcd
--- /dev/null
+++ b/data/leap_client.pro
@@ -0,0 +1,2 @@
+SOURCES += ../src/leap/gui/firstrun/intro.py
+TRANSLATIONS += translations/leap_client_es_ES.ts
diff --git a/data/mkpyqt.py b/data/mkpyqt.py
new file mode 100755
index 00000000..1ce2cd28
--- /dev/null
+++ b/data/mkpyqt.py
@@ -0,0 +1,271 @@
+#!/usr/bin/env python
+# Copyright (c) 2007-10 Qtrac Ltd. All rights reserved.
+# This program or module is free software: you can redistribute it and/or
+# modify it under the terms of the GNU General Public License as published
+# by the Free Software Foundation, either version 2 of the License, or
+# version 3 of the License, or (at your option) any later version. It is
+# provided for educational purposes and is distributed in the hope that
+# it will be useful, but WITHOUT ANY WARRANTY; without even the implied
+# warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
+# the GNU General Public License for more details.
+
+import os
+import platform
+import stat
+import subprocess
+import sys
+import PyQt4.QtCore
+
+__version__ = "1.0.4"
+
+Windows = sys.platform.lower().startswith(("win", "microsoft"))
+if Windows:
+ PATH = os.path.join(os.path.dirname(sys.executable),
+ "Lib/site-packages/PyQt4")
+ if os.access(os.path.join(PATH, "bin"), os.R_OK):
+ PATH = os.path.join(PATH, "bin")
+else:
+ app = PyQt4.QtCore.QCoreApplication([])
+ PATH = unicode(app.applicationDirPath())
+ del app
+if sys.platform.startswith("darwin"):
+ i = PATH.find("Resources")
+ if i > -1:
+ PATH = PATH[:i] + "bin"
+PYUIC4 = os.path.join(PATH, "pyuic4") # e.g. PYUIC4 = "/usr/bin/pyuic4"
+if sys.platform.startswith("darwin"):
+ PYUIC4 = os.path.dirname(sys.executable)
+ i = PYUIC4.find("Resources")
+ if i > -1:
+ PYUIC4 = PYUIC4[:i] + "Lib/python2.5/site-packages/PyQt4/uic/pyuic.py"
+PYRCC4 = os.path.join(PATH, "pyrcc4")
+PYLUPDATE4 = os.path.join(PATH, "pylupdate4")
+LRELEASE = "lrelease"
+if Windows:
+ PYUIC4 = PYUIC4.replace("/", "\\") + ".bat"
+ PYRCC4 = PYRCC4.replace("/", "\\") + ".exe"
+ PYLUPDATE4 = PYLUPDATE4.replace("/", "\\") + ".exe"
+
+msg = []
+shell = lambda command: subprocess.Popen(['which', command],
+ stdout=subprocess.PIPE).communicate()
+
+if not os.access(PYUIC4, os.F_OK):
+ PYUIC4 = shell('pyuic4')[0].strip('\n')
+ if not os.access(PYUIC4, os.F_OK):
+ msg.append("failed to find pyuic4; tried %s" % PYUIC4)
+
+if not os.access(PYRCC4, os.F_OK):
+ PYRCC4 = shell('pyrcc4')[0].strip('\n')
+ if not os.access(PYRCC4, os.F_OK):
+ msg.append("failed to find pyrcc4; tried %s" % PYRCC4)
+
+if not os.access(PYLUPDATE4, os.F_OK):
+ PYLUPDATE4 = shell('pylupdate4')[0].strip('\n')
+ if not os.access(PYLUPDATE4, os.F_OK):
+ msg.append("failed to find pylupdate4; tried %s" % PYLUPDATE4)
+
+if msg:
+ print "\n".join(msg)
+ print "try manually editing this program to put the correct " + \
+ "paths in place"
+ sys.exit()
+
+Debug = False
+Verbose = False
+
+def usage():
+ print """usage: mkpyqt.py [options] [path]
+
+Options (which can be given in any of the forms shown):
+-b --build build [default]
+-c --clean clean
+-f --force force
+-t --translate translate
+-r --recurse recurse
+-v --verbose verbose
+-D --debug debug
+path defaults to .
+
+If executed with no arguments (or with a build argument) it does a
+build, i.e., it looks for all *.ui and *.qrc files and makes sure that
+the corresponding ui_*.py and qrc_*.py files exist and are up-to-date.
+
+If executed with clean, deletes all ui_*.py and qrc_*.py files that have
+corresponding *.ui and *.qrc files, and all *.pyc and *.pyo files.
+
+If executed with force, it does a clean followed by a build.
+
+If building and the translate option is given, after building, it runs
+pylupdate4 on all .py and .pyw files it encounters, and then runs lrelease
+on all .ts files it encounters. It does not use a .pro file so the .ts
+files must be created in the first place, e.g., using pylupdate4 on one
+of the source files and using its -ts option.
+
+WARNING: Do not give any hand-coded files names that match ui_*.py or
+qrc_*.py since these will be deleted by mkpyqt.py clean!
+
+NOTE: If any tool fails to run, e.g., pyuic4, then edit this program and
+hard-code the path; the variables with the tool paths are near the top
+of the file.
+
+mkpyqt.py v %s. Copyright (c) 2007-9 Qtrac Ltd. All rights reserved.
+""" % __version__
+ sys.exit()
+
+
+def report_failure(command, args, process):
+ msg = ""
+ ba = process.readAllStandardError()
+ if not ba.isEmpty():
+ msg = ": " + str(QString(ba))
+ print "failed", command, " ".join(args), msg
+
+
+def build(path):
+ for name in os.listdir(path):
+ source = os.path.join(path, name)
+ target = None
+ if source.endswith(".ui"):
+ target = os.path.join(path,
+ "ui_" + name.replace(".ui", ".py"))
+ command = PYUIC4
+ elif source.endswith(".qrc"):
+ target = os.path.join(path,
+ "qrc_" + name.replace(".qrc", ".py"))
+ command = PYRCC4
+ process = PyQt4.QtCore.QProcess()
+ if target is not None:
+ if not os.access(target, os.F_OK) or (
+ os.stat(source)[stat.ST_MTIME] > \
+ os.stat(target)[stat.ST_MTIME]):
+ args = ["-o", target, source]
+ if sys.platform.startswith("darwin") and command == PYUIC4:
+ command = sys.executable
+ args = [PYUIC4] + args
+ if Debug:
+ print "# %s %s" % (command, " ".join(args))
+ else:
+ process.start(command, args)
+ if not process.waitForFinished(2 * 60 * 1000):
+ report_failure(command, args, process)
+ else:
+ print source, "->", target
+ elif Verbose:
+ print source, "is up-to-date"
+
+
+def clean(path):
+ deletelist = []
+ for name in os.listdir(path):
+ target = os.path.join(path, name)
+ source = None
+ if target.endswith(".py") or target.endswith(".pyc") or \
+ target.endswith(".pyo"):
+ if name.startswith("ui_") and not name[-1] in "oc":
+ source = os.path.join(path, name[3:-3] + ".ui")
+ elif name.startswith("qrc_"):
+ if target[-1] in "oc":
+ source = os.path.join(path, name[4:-4] + ".qrc")
+ else:
+ source = os.path.join(path, name[4:-3] + ".qrc")
+ elif target[-1] in "oc":
+ source = target[:-1]
+ if source is not None:
+ if os.access(source, os.F_OK):
+ if Debug:
+ print "# delete ", target
+ else:
+ deletelist.append(target)
+ else:
+ print "will not remove '%s' since `%s' not found" % (
+ target, source)
+ if not Debug:
+ for target in deletelist:
+ if Verbose:
+ print "deleted", target
+ os.remove(target)
+
+
+def translate(path):
+ files = []
+ tsfiles = []
+ for name in os.listdir(path):
+ if name.endswith((".py", ".pyw")):
+ files.append(os.path.join(path, name))
+ elif name.endswith(".ts"):
+ tsfiles.append(os.path.join(path, name))
+ if not tsfiles:
+ return
+ verbose = "-verbose" if Verbose else ""
+ silent = "-silent" if not Verbose else ""
+ process = PyQt4.QtCore.QProcess()
+ for ts in tsfiles:
+ qm = ts[:-3] + ".qm"
+ command1 = PYLUPDATE4
+ args1 = [verbose] + files + ["-ts", ts]
+ command2 = LRELEASE
+ args2 = [silent, ts, "-qm", qm]
+ if Debug:
+ print "updated", ts
+ print "generated", qm
+ else:
+ process.start(command1, args1)
+ if not process.waitForFinished(2 * 60 * 1000):
+ report_failure(command1, args1, process)
+ process.start(command2, args2)
+ if not process.waitForFinished(2 * 60 * 1000):
+ report_failure(command2, args2, process)
+
+
+def apply(recurse, function, path):
+ if not recurse:
+ function(path)
+ else:
+ for root, dirs, files in os.walk(path):
+ for dir in dirs:
+ function(os.path.join(root, dir))
+
+
+def main():
+ global Debug, Verbose
+ function = build
+ recurse = False
+ trans = False
+ force = False
+ path = "."
+ args = sys.argv[1:]
+ while args:
+ arg = args.pop(0)
+ if arg in ("-D", "--debug", "debug"):
+ Debug = True
+ elif arg in ("-b", "--build", "build"):
+ pass # This is the default
+ elif arg in ("-c", "--clean", "clean"):
+ function = clean
+ elif arg in ("-f", "--force", "force"):
+ force = True
+ elif arg in ("-t", "--translate", "translate"):
+ trans = True
+ elif arg in ("-r", "--recurse", "recurse"):
+ recurse = True
+ elif arg in ("-v", "--verbose", "verbose"):
+ Verbose = True
+ elif arg in ("-h", "--help", "help"):
+ usage()
+ else:
+ path = arg
+ if not force:
+ apply(recurse, function, path)
+ else:
+ apply(recurse, clean, path)
+ apply(recurse, build, path)
+ if trans and (function == build or force):
+ apply(recurse, translate, path)
+
+main()
+
+# 1.0.1 Fixed bug reported by Brian Downing where paths that contained
+# spaces were not handled correctly.
+# 1.0.2 Changed default path on Windows to match PyQt 4.4
+# 1.0.3 Tried to make the paths work on Mac OS X
diff --git a/data/resources/locale.qrc b/data/resources/locale.qrc
new file mode 100644
index 00000000..a2fda78d
--- /dev/null
+++ b/data/resources/locale.qrc
@@ -0,0 +1,5 @@
+<!DOCTYPE RCC><RCC version="1.0">
+<qresource>
+<file>../translations/leap_client_es_ES.qm</file>
+</qresource>
+</RCC>
diff --git a/data/translations/leap_client_es_ES.qm b/data/translations/leap_client_es_ES.qm
new file mode 100644
index 00000000..002237e9
--- /dev/null
+++ b/data/translations/leap_client_es_ES.qm
Binary files differ
diff --git a/data/translations/leap_client_es_ES.ts b/data/translations/leap_client_es_ES.ts
new file mode 100644
index 00000000..86eee980
--- /dev/null
+++ b/data/translations/leap_client_es_ES.ts
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!DOCTYPE TS><TS version="2.0" language="es_ES" sourcelanguage="en_US">
+<context>
+ <name>IntroPage</name>
+ <message>
+ <location filename="../src/leap/gui/firstrun/intro.py" line="14"/>
+ <source>First run wizard.</source>
+ <translation>Primera conexion.</translation>
+ </message>
+ <message>
+ <location filename="../src/leap/gui/firstrun/intro.py" line="24"/>
+ <source>Now we will guide you through some configuration that is needed before you can connect for the first time.&lt;br&gt;&lt;br&gt;If you ever need to modify these options again, you can find the wizard in the &apos;&lt;i&gt;Settings&lt;/i&gt;&apos; menu from the main window.&lt;br&gt;&lt;br&gt;Do you want to &lt;b&gt;sign up&lt;/b&gt; for a new account, or &lt;b&gt;log in&lt;/b&gt; with an already existing username?&lt;br&gt;</source>
+ <translation>Vamos a reunir la informacion que necesitas antes de la primera conexion.&lt;br&gt;&lt;br&gt;Si alguna vez necesitas modificar estas opciones de nuevo, puedes encontrar este asistente en el menu &lt;i&gt;Opciones&lt;/i&gt; en la ventana principal.&lt;br&gt;&lt;br&gt;Que deseas hacer ahora? Puedes &lt;b&gt;registrar&lt;/b&gt; una nueva cuenta o &lt;b&gt;loguearte&lt;/b&gt; con una que ya tienes?&lt;br&gt;</translation>
+ </message>
+ <message>
+ <location filename="../src/leap/gui/firstrun/intro.py" line="37"/>
+ <source>Sign up for a new account.</source>
+ <translation>Registrar una cuenta nueva.</translation>
+ </message>
+ <message>
+ <location filename="../src/leap/gui/firstrun/intro.py" line="40"/>
+ <source>Log In with my credentials.</source>
+ <translation>Loguearme con mi usuario y contrasena.</translation>
+ </message>
+</context>
+</TS>
diff --git a/docs/translations.txt b/docs/translations.txt
new file mode 100644
index 00000000..8cdb2e40
--- /dev/null
+++ b/docs/translations.txt
@@ -0,0 +1,22 @@
+Translations steps
+==================
+
+1. Use .tr() on labels to be translated.
+
+Note about this: there seems to be some problems with the .tr method
+on QObjects. Investigate this.
+
+I still believe we can use a generic _ method which is smart enough to
+fallback to QObject.tr methods or lookup our own tr implementation (for our
+multilungual objects, like in exceptions or provider labels that came from json objects).
+
+2. Add source files to the project file, data/leap_client.pro (Note: investigate if we can use some form of expansion here; it's tedious to add source files one by one).
+
+3. Still in data/leap_client.pro, add a translation per each language. Translations live in data/translations.
+
+4. exec ``pylupdate4`` data/leap_client.pro to generate initial .ts file
+5. Use QtLinguist (* or whatever web service we end up using *) to translate stuff. We expect the ts to follow Qt xml format, which seems standard enough to allow some fair degree of play.
+6. Execute ``lrelease data/leap_client.pro`` to generate .qm files.
+7. Check that the .qm for the language you're working with is listed in data/resources/locale.qrc file.
+
+8. Execute ``make resources`` to re-generate locale_qrc (in src/leap/gui). This is the compiled resource file that we load in the main app entry point; and from where we load the data for the qt translator object.
diff --git a/src/leap/app.py b/src/leap/app.py
index d594c7cd..334b58c8 100644
--- a/src/leap/app.py
+++ b/src/leap/app.py
@@ -8,10 +8,11 @@ import sip
sip.setapi('QVariant', 2)
sip.setapi('QString', 2)
from PyQt4.QtGui import (QApplication, QSystemTrayIcon, QMessageBox)
-from PyQt4.QtCore import QTimer
+from PyQt4 import QtCore
from leap import __version__ as VERSION
from leap.baseapp.mainwindow import LeapWindow
+from leap.gui import locale_rc
def sigint_handler(*args, **kwargs):
@@ -62,6 +63,17 @@ def main():
logger.info('Starting app')
app = QApplication(sys.argv)
+ # To test:
+ # $ LANG=es ./app.py
+ locale = QtCore.QLocale.system().name()
+ print locale
+ qtTranslator = QtCore.QTranslator()
+ if qtTranslator.load("qt_%s" % locale, ":/translations"):
+ app.installTranslator(qtTranslator)
+ appTranslator = QtCore.QTranslator()
+ if appTranslator.load("leap_client_%s" % locale, ":/translations"):
+ app.installTranslator(appTranslator)
+
# needed for initializing qsettings
# it will write .config/leap/leap.conf
# top level app settings
@@ -83,7 +95,7 @@ def main():
# this dummy timer ensures that
# control is given to the outside loop, so we
# can hook our sigint handler.
- timer = QTimer()
+ timer = QtCore.QTimer()
timer.start(500)
timer.timeout.connect(lambda: None)
diff --git a/src/leap/gui/firstrun/intro.py b/src/leap/gui/firstrun/intro.py
index 4bb008c7..0a7484e2 100644
--- a/src/leap/gui/firstrun/intro.py
+++ b/src/leap/gui/firstrun/intro.py
@@ -11,7 +11,7 @@ class IntroPage(QtGui.QWizardPage):
def __init__(self, parent=None):
super(IntroPage, self).__init__(parent)
- self.setTitle("First run wizard.")
+ self.setTitle(self.tr("First run wizard."))
#self.setPixmap(
#QtGui.QWizard.WatermarkPixmap,
@@ -21,7 +21,7 @@ class IntroPage(QtGui.QWizardPage):
QtGui.QWizard.LogoPixmap,
QtGui.QPixmap(APP_LOGO))
- label = QtGui.QLabel(
+ label = QtGui.QLabel(self.tr(
"Now we will guide you through "
"some configuration that is needed before you "
"can connect for the first time.<br><br>"
@@ -29,16 +29,16 @@ class IntroPage(QtGui.QWizardPage):
"you can find the wizard in the '<i>Settings</i>' menu from the "
"main window.<br><br>"
"Do you want to <b>sign up</b> for a new account, or <b>log "
- "in</b> with an already existing username?<br>")
+ "in</b> with an already existing username?<br>"))
label.setWordWrap(True)
radiobuttonGroup = QtGui.QGroupBox()
self.sign_up = QtGui.QRadioButton(
- "Sign up for a new account.")
+ self.tr("Sign up for a new account."))
self.sign_up.setChecked(True)
self.log_in = QtGui.QRadioButton(
- "Log In with my credentials.")
+ self.tr("Log In with my credentials."))
radiobLayout = QtGui.QVBoxLayout()
radiobLayout.addWidget(self.sign_up)
diff --git a/src/leap/gui/locale_rc.py b/src/leap/gui/locale_rc.py
new file mode 100644
index 00000000..f165ff8e
--- /dev/null
+++ b/src/leap/gui/locale_rc.py
@@ -0,0 +1,132 @@
+# -*- coding: utf-8 -*-
+
+# Resource object code
+#
+# Created: vie nov 16 22:33:33 2012
+# by: The Resource Compiler for PyQt (Qt v4.8.2)
+#
+# WARNING! All changes made in this file will be lost!
+
+from PyQt4 import QtCore
+
+qt_resource_data = "\
+\x00\x00\x05\xaa\
+\x3c\
+\xb8\x64\x18\xca\xef\x9c\x95\xcd\x21\x1c\xbf\x60\xa1\xbd\xdd\x42\
+\x00\x00\x00\x20\x09\xfc\x2c\x8e\x00\x00\x04\xfb\x0a\x74\xb8\x1e\
+\x00\x00\x00\xd6\x0a\xfd\x99\xfe\x00\x00\x00\x51\x0c\x44\x41\xbe\
+\x00\x00\x00\x00\x69\x00\x00\x05\x69\x03\x00\x00\x00\x22\x00\x50\
+\x00\x72\x00\x69\x00\x6d\x00\x65\x00\x72\x00\x61\x00\x20\x00\x63\
+\x00\x6f\x00\x6e\x00\x65\x00\x78\x00\x69\x00\x6f\x00\x6e\x00\x2e\
+\x08\x00\x00\x00\x00\x06\x00\x00\x00\x11\x46\x69\x72\x73\x74\x20\
+\x72\x75\x6e\x20\x77\x69\x7a\x61\x72\x64\x2e\x07\x00\x00\x00\x09\
+\x49\x6e\x74\x72\x6f\x50\x61\x67\x65\x01\x03\x00\x00\x00\x4c\x00\
+\x4c\x00\x6f\x00\x67\x00\x75\x00\x65\x00\x61\x00\x72\x00\x6d\x00\
+\x65\x00\x20\x00\x63\x00\x6f\x00\x6e\x00\x20\x00\x6d\x00\x69\x00\
+\x20\x00\x75\x00\x73\x00\x75\x00\x61\x00\x72\x00\x69\x00\x6f\x00\
+\x20\x00\x79\x00\x20\x00\x63\x00\x6f\x00\x6e\x00\x74\x00\x72\x00\
+\x61\x00\x73\x00\x65\x00\x6e\x00\x61\x00\x2e\x08\x00\x00\x00\x00\
+\x06\x00\x00\x00\x1b\x4c\x6f\x67\x20\x49\x6e\x20\x77\x69\x74\x68\
+\x20\x6d\x79\x20\x63\x72\x65\x64\x65\x6e\x74\x69\x61\x6c\x73\x2e\
+\x07\x00\x00\x00\x09\x49\x6e\x74\x72\x6f\x50\x61\x67\x65\x01\x03\
+\x00\x00\x02\xaa\x00\x56\x00\x61\x00\x6d\x00\x6f\x00\x73\x00\x20\
+\x00\x61\x00\x20\x00\x72\x00\x65\x00\x75\x00\x6e\x00\x69\x00\x72\
+\x00\x20\x00\x6c\x00\x61\x00\x20\x00\x69\x00\x6e\x00\x66\x00\x6f\
+\x00\x72\x00\x6d\x00\x61\x00\x63\x00\x69\x00\x6f\x00\x6e\x00\x20\
+\x00\x71\x00\x75\x00\x65\x00\x20\x00\x6e\x00\x65\x00\x63\x00\x65\
+\x00\x73\x00\x69\x00\x74\x00\x61\x00\x73\x00\x20\x00\x61\x00\x6e\
+\x00\x74\x00\x65\x00\x73\x00\x20\x00\x64\x00\x65\x00\x20\x00\x6c\
+\x00\x61\x00\x20\x00\x70\x00\x72\x00\x69\x00\x6d\x00\x65\x00\x72\
+\x00\x61\x00\x20\x00\x63\x00\x6f\x00\x6e\x00\x65\x00\x78\x00\x69\
+\x00\x6f\x00\x6e\x00\x2e\x00\x3c\x00\x62\x00\x72\x00\x3e\x00\x3c\
+\x00\x62\x00\x72\x00\x3e\x00\x53\x00\x69\x00\x20\x00\x61\x00\x6c\
+\x00\x67\x00\x75\x00\x6e\x00\x61\x00\x20\x00\x76\x00\x65\x00\x7a\
+\x00\x20\x00\x6e\x00\x65\x00\x63\x00\x65\x00\x73\x00\x69\x00\x74\
+\x00\x61\x00\x73\x00\x20\x00\x6d\x00\x6f\x00\x64\x00\x69\x00\x66\
+\x00\x69\x00\x63\x00\x61\x00\x72\x00\x20\x00\x65\x00\x73\x00\x74\
+\x00\x61\x00\x73\x00\x20\x00\x6f\x00\x70\x00\x63\x00\x69\x00\x6f\
+\x00\x6e\x00\x65\x00\x73\x00\x20\x00\x64\x00\x65\x00\x20\x00\x6e\
+\x00\x75\x00\x65\x00\x76\x00\x6f\x00\x2c\x00\x20\x00\x70\x00\x75\
+\x00\x65\x00\x64\x00\x65\x00\x73\x00\x20\x00\x65\x00\x6e\x00\x63\
+\x00\x6f\x00\x6e\x00\x74\x00\x72\x00\x61\x00\x72\x00\x20\x00\x65\
+\x00\x73\x00\x74\x00\x65\x00\x20\x00\x61\x00\x73\x00\x69\x00\x73\
+\x00\x74\x00\x65\x00\x6e\x00\x74\x00\x65\x00\x20\x00\x65\x00\x6e\
+\x00\x20\x00\x65\x00\x6c\x00\x20\x00\x6d\x00\x65\x00\x6e\x00\x75\
+\x00\x20\x00\x3c\x00\x69\x00\x3e\x00\x4f\x00\x70\x00\x63\x00\x69\
+\x00\x6f\x00\x6e\x00\x65\x00\x73\x00\x3c\x00\x2f\x00\x69\x00\x3e\
+\x00\x20\x00\x65\x00\x6e\x00\x20\x00\x6c\x00\x61\x00\x20\x00\x76\
+\x00\x65\x00\x6e\x00\x74\x00\x61\x00\x6e\x00\x61\x00\x20\x00\x70\
+\x00\x72\x00\x69\x00\x6e\x00\x63\x00\x69\x00\x70\x00\x61\x00\x6c\
+\x00\x2e\x00\x3c\x00\x62\x00\x72\x00\x3e\x00\x3c\x00\x62\x00\x72\
+\x00\x3e\x00\x51\x00\x75\x00\x65\x00\x20\x00\x64\x00\x65\x00\x73\
+\x00\x65\x00\x61\x00\x73\x00\x20\x00\x68\x00\x61\x00\x63\x00\x65\
+\x00\x72\x00\x20\x00\x61\x00\x68\x00\x6f\x00\x72\x00\x61\x00\x3f\
+\x00\x20\x00\x50\x00\x75\x00\x65\x00\x64\x00\x65\x00\x73\x00\x20\
+\x00\x3c\x00\x62\x00\x3e\x00\x72\x00\x65\x00\x67\x00\x69\x00\x73\
+\x00\x74\x00\x72\x00\x61\x00\x72\x00\x3c\x00\x2f\x00\x62\x00\x3e\
+\x00\x20\x00\x75\x00\x6e\x00\x61\x00\x20\x00\x6e\x00\x75\x00\x65\
+\x00\x76\x00\x61\x00\x20\x00\x63\x00\x75\x00\x65\x00\x6e\x00\x74\
+\x00\x61\x00\x20\x00\x6f\x00\x20\x00\x3c\x00\x62\x00\x3e\x00\x6c\
+\x00\x6f\x00\x67\x00\x75\x00\x65\x00\x61\x00\x72\x00\x74\x00\x65\
+\x00\x3c\x00\x2f\x00\x62\x00\x3e\x00\x20\x00\x63\x00\x6f\x00\x6e\
+\x00\x20\x00\x75\x00\x6e\x00\x61\x00\x20\x00\x71\x00\x75\x00\x65\
+\x00\x20\x00\x79\x00\x61\x00\x20\x00\x74\x00\x69\x00\x65\x00\x6e\
+\x00\x65\x00\x73\x00\x3f\x00\x3c\x00\x62\x00\x72\x00\x3e\x08\x00\
+\x00\x00\x00\x06\x00\x00\x01\x5d\x4e\x6f\x77\x20\x77\x65\x20\x77\
+\x69\x6c\x6c\x20\x67\x75\x69\x64\x65\x20\x79\x6f\x75\x20\x74\x68\
+\x72\x6f\x75\x67\x68\x20\x73\x6f\x6d\x65\x20\x63\x6f\x6e\x66\x69\
+\x67\x75\x72\x61\x74\x69\x6f\x6e\x20\x74\x68\x61\x74\x20\x69\x73\
+\x20\x6e\x65\x65\x64\x65\x64\x20\x62\x65\x66\x6f\x72\x65\x20\x79\
+\x6f\x75\x20\x63\x61\x6e\x20\x63\x6f\x6e\x6e\x65\x63\x74\x20\x66\
+\x6f\x72\x20\x74\x68\x65\x20\x66\x69\x72\x73\x74\x20\x74\x69\x6d\
+\x65\x2e\x3c\x62\x72\x3e\x3c\x62\x72\x3e\x49\x66\x20\x79\x6f\x75\
+\x20\x65\x76\x65\x72\x20\x6e\x65\x65\x64\x20\x74\x6f\x20\x6d\x6f\
+\x64\x69\x66\x79\x20\x74\x68\x65\x73\x65\x20\x6f\x70\x74\x69\x6f\
+\x6e\x73\x20\x61\x67\x61\x69\x6e\x2c\x20\x79\x6f\x75\x20\x63\x61\
+\x6e\x20\x66\x69\x6e\x64\x20\x74\x68\x65\x20\x77\x69\x7a\x61\x72\
+\x64\x20\x69\x6e\x20\x74\x68\x65\x20\x27\x3c\x69\x3e\x53\x65\x74\
+\x74\x69\x6e\x67\x73\x3c\x2f\x69\x3e\x27\x20\x6d\x65\x6e\x75\x20\
+\x66\x72\x6f\x6d\x20\x74\x68\x65\x20\x6d\x61\x69\x6e\x20\x77\x69\
+\x6e\x64\x6f\x77\x2e\x3c\x62\x72\x3e\x3c\x62\x72\x3e\x44\x6f\x20\
+\x79\x6f\x75\x20\x77\x61\x6e\x74\x20\x74\x6f\x20\x3c\x62\x3e\x73\
+\x69\x67\x6e\x20\x75\x70\x3c\x2f\x62\x3e\x20\x66\x6f\x72\x20\x61\
+\x20\x6e\x65\x77\x20\x61\x63\x63\x6f\x75\x6e\x74\x2c\x20\x6f\x72\
+\x20\x3c\x62\x3e\x6c\x6f\x67\x20\x69\x6e\x3c\x2f\x62\x3e\x20\x77\
+\x69\x74\x68\x20\x61\x6e\x20\x61\x6c\x72\x65\x61\x64\x79\x20\x65\
+\x78\x69\x73\x74\x69\x6e\x67\x20\x75\x73\x65\x72\x6e\x61\x6d\x65\
+\x3f\x3c\x62\x72\x3e\x07\x00\x00\x00\x09\x49\x6e\x74\x72\x6f\x50\
+\x61\x67\x65\x01\x03\x00\x00\x00\x36\x00\x52\x00\x65\x00\x67\x00\
+\x69\x00\x73\x00\x74\x00\x72\x00\x61\x00\x72\x00\x20\x00\x75\x00\
+\x6e\x00\x61\x00\x20\x00\x63\x00\x75\x00\x65\x00\x6e\x00\x74\x00\
+\x61\x00\x20\x00\x6e\x00\x75\x00\x65\x00\x76\x00\x61\x00\x2e\x08\
+\x00\x00\x00\x00\x06\x00\x00\x00\x1a\x53\x69\x67\x6e\x20\x75\x70\
+\x20\x66\x6f\x72\x20\x61\x20\x6e\x65\x77\x20\x61\x63\x63\x6f\x75\
+\x6e\x74\x2e\x07\x00\x00\x00\x09\x49\x6e\x74\x72\x6f\x50\x61\x67\
+\x65\x01\x88\x00\x00\x00\x02\x01\x01\
+"
+
+qt_resource_name = "\
+\x00\x0c\
+\x0d\xfc\x11\x13\
+\x00\x74\
+\x00\x72\x00\x61\x00\x6e\x00\x73\x00\x6c\x00\x61\x00\x74\x00\x69\x00\x6f\x00\x6e\x00\x73\
+\x00\x14\
+\x08\xa9\x0f\x1d\
+\x00\x6c\
+\x00\x65\x00\x61\x00\x70\x00\x5f\x00\x63\x00\x6c\x00\x69\x00\x65\x00\x6e\x00\x74\x00\x5f\x00\x65\x00\x73\x00\x5f\x00\x45\x00\x53\
+\x00\x2e\x00\x71\x00\x6d\
+"
+
+qt_resource_struct = "\
+\x00\x00\x00\x00\x00\x02\x00\x00\x00\x01\x00\x00\x00\x01\
+\x00\x00\x00\x00\x00\x02\x00\x00\x00\x01\x00\x00\x00\x02\
+\x00\x00\x00\x1e\x00\x00\x00\x00\x00\x01\x00\x00\x00\x00\
+"
+
+def qInitResources():
+ QtCore.qRegisterResourceData(0x01, qt_resource_struct, qt_resource_name, qt_resource_data)
+
+def qCleanupResources():
+ QtCore.qUnregisterResourceData(0x01, qt_resource_struct, qt_resource_name, qt_resource_data)
+
+qInitResources()