Add transifex system Add entry system for different string entry type, use ruamel for yaml. The Transifex system currently only supports yaml format.
guix-full.manifest
17 | 17 | "python-neovim" | |
18 | 18 | "python-polib" | |
19 | 19 | "python-pyqt" | |
20 | + | "python-ruamel.yaml" | |
20 | 21 | "python-sphinx" | |
21 | 22 | "python-twine" | |
22 | 23 | "qt" |
guix.manifest
6 | 6 | "python-lxml" | |
7 | 7 | "python-polib" | |
8 | 8 | "python-pyqt" | |
9 | + | "python-ruamel.yaml" | |
9 | 10 | "python-sphinx" | |
10 | 11 | "python-twine")) |
i18n/offlate_fr.ts
3 | 3 | <context> | |
4 | 4 | <name>NewWindow</name> | |
5 | 5 | <message> | |
6 | - | <location filename="../offlate/window.py" line="190"/> | |
6 | + | <location filename="../offlate/window.py" line="202"/> | |
7 | 7 | <source>The Translation Project</source> | |
8 | 8 | <translation>Le Projet de Traduction</translation> | |
9 | 9 | </message> | |
10 | 10 | <message> | |
11 | - | <location filename="../offlate/window.py" line="193"/> | |
11 | + | <location filename="../offlate/window.py" line="207"/> | |
12 | 12 | <source>Cancel</source> | |
13 | 13 | <translation>Annuler</translation> | |
14 | 14 | </message> | |
15 | 15 | <message> | |
16 | - | <location filename="../offlate/window.py" line="194"/> | |
16 | + | <location filename="../offlate/window.py" line="208"/> | |
17 | 17 | <source>OK</source> | |
18 | 18 | <translation>OK</translation> | |
19 | 19 | </message> | |
20 | + | <message> | |
21 | + | <location filename="../offlate/window.py" line="193"/> | |
22 | + | <source>Project information</source> | |
23 | + | <translation type="unfinished"></translation> | |
24 | + | </message> | |
25 | + | <message> | |
26 | + | <location filename="../offlate/window.py" line="199"/> | |
27 | + | <source>Name:</source> | |
28 | + | <translation type="unfinished"></translation> | |
29 | + | </message> | |
30 | + | <message> | |
31 | + | <location filename="../offlate/window.py" line="200"/> | |
32 | + | <source>Target Language:</source> | |
33 | + | <translation type="unfinished"></translation> | |
34 | + | </message> | |
35 | + | <message> | |
36 | + | <location filename="../offlate/window.py" line="203"/> | |
37 | + | <source>Transifex</source> | |
38 | + | <translation type="unfinished"></translation> | |
39 | + | </message> | |
40 | + | <message> | |
41 | + | <location filename="../offlate/window.py" line="220"/> | |
42 | + | <source>Organization</source> | |
43 | + | <translation type="unfinished"></translation> | |
44 | + | </message> | |
20 | 45 | </context> | |
21 | 46 | <context> | |
22 | 47 | <name>ProjectView</name> | |
23 | 48 | <message> | |
24 | - | <location filename="../offlate/window.py" line="103"/> | |
49 | + | <location filename="../offlate/window.py" line="110"/> | |
25 | 50 | <source>Singular</source> | |
26 | 51 | <translation>Singulier</translation> | |
27 | 52 | </message> | |
28 | 53 | <message> | |
29 | - | <location filename="../offlate/window.py" line="104"/> | |
54 | + | <location filename="../offlate/window.py" line="111"/> | |
30 | 55 | <source>Plural</source> | |
31 | 56 | <translation>Pluriel</translation> | |
32 | 57 | </message> | |
… | |||
34 | 59 | <context> | |
35 | 60 | <name>SettingsWindow</name> | |
36 | 61 | <message> | |
37 | - | <location filename="../offlate/window.py" line="254"/> | |
62 | + | <location filename="../offlate/window.py" line="298"/> | |
38 | 63 | <source>Cancel</source> | |
39 | 64 | <translation>Annuler</translation> | |
40 | 65 | </message> | |
41 | 66 | <message> | |
42 | - | <location filename="../offlate/window.py" line="255"/> | |
67 | + | <location filename="../offlate/window.py" line="299"/> | |
43 | 68 | <source>OK</source> | |
44 | 69 | <translation>OK</translation> | |
45 | 70 | </message> | |
46 | 71 | <message> | |
47 | - | <location filename="../offlate/window.py" line="283"/> | |
72 | + | <location filename="../offlate/window.py" line="360"/> | |
48 | 73 | <source>Email:</source> | |
49 | 74 | <translation>Adresse de courriel :</translation> | |
50 | 75 | </message> | |
51 | 76 | <message> | |
52 | - | <location filename="../offlate/window.py" line="284"/> | |
77 | + | <location filename="../offlate/window.py" line="361"/> | |
53 | 78 | <source>Server:</source> | |
54 | 79 | <translation>Serveur :</translation> | |
55 | 80 | </message> | |
56 | 81 | <message> | |
57 | - | <location filename="../offlate/window.py" line="285"/> | |
82 | + | <location filename="../offlate/window.py" line="362"/> | |
58 | 83 | <source>User Name:</source> | |
59 | 84 | <translation>Nom d'utilisateur :</translation> | |
60 | 85 | </message> | |
86 | + | <message> | |
87 | + | <location filename="../offlate/window.py" line="310"/> | |
88 | + | <source>Transifex</source> | |
89 | + | <translation type="unfinished"></translation> | |
90 | + | </message> | |
91 | + | <message> | |
92 | + | <location filename="../offlate/window.py" line="322"/> | |
93 | + | <source>You can get a token from <a href="#">https://www.transifex.com/user/settings/api/</a></source> | |
94 | + | <translation type="unfinished"></translation> | |
95 | + | </message> | |
96 | + | <message> | |
97 | + | <location filename="../offlate/window.py" line="325"/> | |
98 | + | <source>Token:</source> | |
99 | + | <translation type="unfinished"></translation> | |
100 | + | </message> | |
101 | + | <message> | |
102 | + | <location filename="../offlate/window.py" line="339"/> | |
103 | + | <source>Translation Project</source> | |
104 | + | <translation type="unfinished"></translation> | |
105 | + | </message> | |
61 | 106 | </context> | |
62 | 107 | <context> | |
63 | 108 | <name>Window</name> | |
64 | 109 | <message> | |
65 | - | <location filename="../offlate/window.py" line="356"/> | |
110 | + | <location filename="../offlate/window.py" line="433"/> | |
66 | 111 | <source>Exit application</source> | |
67 | 112 | <translation>Quitter l'application</translation> | |
68 | 113 | </message> | |
69 | 114 | <message> | |
70 | - | <location filename="../offlate/window.py" line="361"/> | |
115 | + | <location filename="../offlate/window.py" line="438"/> | |
71 | 116 | <source>Save current project</source> | |
72 | 117 | <translation>Sauvegarder le projet actuel</translation> | |
73 | 118 | </message> | |
74 | 119 | <message> | |
75 | - | <location filename="../offlate/window.py" line="366"/> | |
120 | + | <location filename="../offlate/window.py" line="443"/> | |
76 | 121 | <source>New project</source> | |
77 | 122 | <translation>Nouveau projet</translation> | |
78 | 123 | </message> | |
79 | 124 | <message> | |
80 | - | <location filename="../offlate/window.py" line="371"/> | |
125 | + | <location filename="../offlate/window.py" line="448"/> | |
81 | 126 | <source>Get modifications from upstream</source> | |
82 | 127 | <translation>R??cup??rer les modifications en amont</translation> | |
83 | 128 | </message> | |
84 | 129 | <message> | |
85 | - | <location filename="../offlate/window.py" line="375"/> | |
130 | + | <location filename="../offlate/window.py" line="452"/> | |
86 | 131 | <source>Close current project</source> | |
87 | 132 | <translation>Fermer le projet actuel</translation> | |
88 | 133 | </message> | |
89 | 134 | <message> | |
90 | - | <location filename="../offlate/window.py" line="380"/> | |
135 | + | <location filename="../offlate/window.py" line="457"/> | |
91 | 136 | <source>Send modifications upstream</source> | |
92 | 137 | <translation>Envoyer les modifications en amont</translation> | |
93 | 138 | </message> | |
94 | 139 | <message> | |
95 | - | <location filename="../offlate/window.py" line="385"/> | |
140 | + | <location filename="../offlate/window.py" line="462"/> | |
96 | 141 | <source>Set parameters</source> | |
97 | 142 | <translation>Configurer les param??tres</translation> | |
98 | 143 | </message> | |
99 | 144 | <message> | |
100 | - | <location filename="../offlate/window.py" line="388"/> | |
145 | + | <location filename="../offlate/window.py" line="465"/> | |
101 | 146 | <source>Show Translated</source> | |
102 | 147 | <translation>Montrer traduites</translation> | |
103 | 148 | </message> | |
104 | 149 | <message> | |
105 | - | <location filename="../offlate/window.py" line="391"/> | |
150 | + | <location filename="../offlate/window.py" line="468"/> | |
106 | 151 | <source>Show Fuzzy</source> | |
107 | 152 | <translation>Montrer floues</translation> | |
108 | 153 | </message> | |
109 | 154 | <message> | |
110 | - | <location filename="../offlate/window.py" line="394"/> | |
155 | + | <location filename="../offlate/window.py" line="471"/> | |
111 | 156 | <source>Show Empty Translation</source> | |
112 | 157 | <translation>Montrer les traductions vides</translation> | |
113 | 158 | </message> | |
114 | 159 | <message> | |
115 | - | <location filename="../offlate/window.py" line="404"/> | |
160 | + | <location filename="../offlate/window.py" line="481"/> | |
116 | 161 | <source>&File</source> | |
117 | 162 | <translation>&Fichier</translation> | |
118 | 163 | </message> | |
119 | 164 | <message> | |
120 | - | <location filename="../offlate/window.py" line="410"/> | |
165 | + | <location filename="../offlate/window.py" line="487"/> | |
121 | 166 | <source>&Project</source> | |
122 | 167 | <translation>&Projet</translation> | |
123 | 168 | </message> | |
124 | 169 | <message> | |
125 | - | <location filename="../offlate/window.py" line="417"/> | |
170 | + | <location filename="../offlate/window.py" line="494"/> | |
126 | 171 | <source>&Edit</source> | |
127 | 172 | <translation>&??dition</translation> | |
128 | 173 | </message> | |
129 | 174 | <message> | |
130 | - | <location filename="../offlate/window.py" line="420"/> | |
175 | + | <location filename="../offlate/window.py" line="497"/> | |
131 | 176 | <source>&View</source> | |
132 | 177 | <translation>&Affichage</translation> | |
133 | 178 | </message> | |
134 | 179 | <message> | |
135 | - | <location filename="../offlate/window.py" line="400"/> | |
180 | + | <location filename="../offlate/window.py" line="477"/> | |
136 | 181 | <source>Open</source> | |
137 | 182 | <translation>Ouvrir</translation> | |
138 | 183 | </message> | |
139 | 184 | <message> | |
140 | - | <location filename="../offlate/window.py" line="354"/> | |
185 | + | <location filename="../offlate/window.py" line="431"/> | |
141 | 186 | <source>Exit</source> | |
142 | 187 | <translation>Quitter</translation> | |
143 | 188 | </message> | |
144 | 189 | <message> | |
145 | - | <location filename="../offlate/window.py" line="359"/> | |
190 | + | <location filename="../offlate/window.py" line="436"/> | |
146 | 191 | <source>Save</source> | |
147 | 192 | <translation>Sauvegarder</translation> | |
148 | 193 | </message> | |
149 | 194 | <message> | |
150 | - | <location filename="../offlate/window.py" line="364"/> | |
195 | + | <location filename="../offlate/window.py" line="441"/> | |
151 | 196 | <source>New</source> | |
152 | 197 | <translation>Nouveau</translation> | |
153 | 198 | </message> | |
154 | 199 | <message> | |
155 | - | <location filename="../offlate/window.py" line="369"/> | |
200 | + | <location filename="../offlate/window.py" line="446"/> | |
156 | 201 | <source>Update</source> | |
157 | 202 | <translation>Mettre ?? jour</translation> | |
158 | 203 | </message> | |
159 | 204 | <message> | |
160 | - | <location filename="../offlate/window.py" line="374"/> | |
205 | + | <location filename="../offlate/window.py" line="451"/> | |
161 | 206 | <source>Close</source> | |
162 | 207 | <translation>Fermer</translation> | |
163 | 208 | </message> | |
164 | 209 | <message> | |
165 | - | <location filename="../offlate/window.py" line="378"/> | |
210 | + | <location filename="../offlate/window.py" line="455"/> | |
166 | 211 | <source>Send</source> | |
167 | 212 | <translation>Envoyer</translation> | |
168 | 213 | </message> | |
169 | 214 | <message> | |
170 | - | <location filename="../offlate/window.py" line="383"/> | |
215 | + | <location filename="../offlate/window.py" line="460"/> | |
171 | 216 | <source>Settings</source> | |
172 | 217 | <translation>Param??tres</translation> | |
173 | 218 | </message> | |
174 | 219 | </context> | |
220 | + | <context> | |
221 | + | <name>self.qd</name> | |
222 | + | <message> | |
223 | + | <location filename="../offlate/window.py" line="24"/> | |
224 | + | <source>Please enter your password:</source> | |
225 | + | <translation type="unfinished"></translation> | |
226 | + | </message> | |
227 | + | </context> | |
175 | 228 | </TS> |
offlate/data.json
1 | - | [{"name": "a2ps", "system": 0}, {"name": "aegis", "system": 0}, {"name": "anubis", "system": 0}, {"name": "aspell", "system": 0}, {"name": "bash", "system": 0}, {"name": "bfd", "system": 0}, {"name": "binutils", "system": 0}, {"name": "bison", "system": 0}, {"name": "bison-runtime", "system": 0}, {"name": "buzztrax", "system": 0}, {"name": "ccd2cue", "system": 0}, {"name": "ccide", "system": 0}, {"name": "cflow", "system": 0}, {"name": "clisp", "system": 0}, {"name": "coreutils", "system": 0}, {"name": "cpio", "system": 0}, {"name": "cppi", "system": 0}, {"name": "cpplib", "system": 0}, {"name": "cryptsetup", "system": 0}, {"name": "datamash", "system": 0}, {"name": "denemo", "system": 0}, {"name": "dfarc", "system": 0}, {"name": "dialog", "system": 0}, {"name": "dico", "system": 0}, {"name": "diffutils", "system": 0}, {"name": "dink", "system": 0}, {"name": "direvent", "system": 0}, {"name": "doodle", "system": 0}, {"name": "dos2unix", "system": 0}, {"name": "dos2unix-man", "system": 0}, {"name": "e2fsprogs", "system": 0}, {"name": "enscript", "system": 0}, {"name": "exif", "system": 0}, {"name": "fetchmail", "system": 0}, {"name": "findutils", "system": 0}, {"name": "flex", "system": 0}, {"name": "freedink", "system": 0}, {"name": "fusionforge", "system": 0}, {"name": "gas", "system": 0}, {"name": "gawk", "system": 0}, {"name": "gcal", "system": 0}, {"name": "gcc", "system": 0}, {"name": "gdbm", "system": 0}, {"name": "gettext-examples", "system": 0}, {"name": "gettext-runtime", "system": 0}, {"name": "gettext-tools", "system": 0}, {"name": "gjay", "system": 0}, {"name": "glunarclock", "system": 0}, {"name": "gnubiff", "system": 0}, {"name": "gnubik", "system": 0}, {"name": "gnucash", "system": 0}, {"name": "gnuchess", "system": 0}, {"name": "gnucobol", "system": 0}, {"name": "gnulib", "system": 0}, {"name": "gnunet", "system": 0}, {"name": "gnunet-gtk", "system": 0}, {"name": "gold", "system": 0}, {"name": "gphoto2", "system": 0}, {"name": "gprof", "system": 0}, {"name": "gramadoir", "system": 0}, {"name": "grep", "system": 0}, {"name": "grip", "system": 0}, {"name": "grub", "system": 0}, {"name": "gsasl", "system": 0}, {"name": "gss", "system": 0}, {"name": "gst-plugins-bad", "system": 0}, {"name": "gst-plugins-base", "system": 0}, {"name": "gst-plugins-good", "system": 0}, {"name": "gst-plugins-ugly", "system": 0}, {"name": "gstreamer", "system": 0}, {"name": "gtick", "system": 0}, {"name": "gtkam", "system": 0}, {"name": "gtkspell", "system": 0}, {"name": "guix", "system": 0}, {"name": "guix-packages", "system": 0}, {"name": "gutenprint", "system": 0}, {"name": "hello", "system": 0}, {"name": "help2man", "system": 0}, {"name": "help2man-texi", "system": 0}, {"name": "hylafax", "system": 0}, {"name": "idutils", "system": 0}, {"name": "jwhois", "system": 0}, {"name": "kbd", "system": 0}, {"name": "klavaro", "system": 0}, {"name": "ld", "system": 0}, {"name": "leafpad", "system": 0}, {"name": "libc", "system": 0}, {"name": "libexif", "system": 0}, {"name": "libextractor", "system": 0}, {"name": "libgnutls", "system": 0}, {"name": "libgphoto2", "system": 0}, {"name": "libgphoto2_port", "system": 0}, {"name": "libgsasl", "system": 0}, {"name": "libiconv", "system": 0}, {"name": "libidn", "system": 0}, {"name": "libidn2", "system": 0}, {"name": "lilypond", "system": 0}, {"name": "lordsawar", "system": 0}, {"name": "lprng", "system": 0}, {"name": "lynx", "system": 0}, {"name": "m4", "system": 0}, {"name": "mailfromd", "system": 0}, {"name": "mailutils", "system": 0}, {"name": "make", "system": 0}, {"name": "man-db", "system": 0}, {"name": "man-db-manpages", "system": 0}, {"name": "midi-instruments", "system": 0}, {"name": "minicom", "system": 0}, {"name": "mkisofs", "system": 0}, {"name": "muibase", "system": 0}, {"name": "myserver", "system": 0}, {"name": "nano", "system": 0}, {"name": "opcodes", "system": 0}, {"name": "parted", "system": 0}, {"name": "pies", "system": 0}, {"name": "pnmixer", "system": 0}, {"name": "popt", "system": 0}, {"name": "procps-ng", "system": 0}, {"name": "procps-ng-man", "system": 0}, {"name": "psmisc", "system": 0}, {"name": "pspp", "system": 0}, {"name": "pushover", "system": 0}, {"name": "pwdutils", "system": 0}, {"name": "pyspread", "system": 0}, {"name": "radius", "system": 0}, {"name": "recode", "system": 0}, {"name": "recutils", "system": 0}, {"name": "rpm", "system": 0}, {"name": "rush", "system": 0}, {"name": "sarg", "system": 0}, {"name": "savane", "system": 0}, {"name": "sed", "system": 0}, {"name": "sharutils", "system": 0}, {"name": "shepherd", "system": 0}, {"name": "shishi", "system": 0}, {"name": "skribilo", "system": 0}, {"name": "solfege", "system": 0}, {"name": "solfege-manual", "system": 0}, {"name": "spotmachine", "system": 0}, {"name": "sudo", "system": 0}, {"name": "sudoers", "system": 0}, {"name": "sysstat", "system": 0}, {"name": "tar", "system": 0}, {"name": "texinfo", "system": 0}, {"name": "texinfo_document", "system": 0}, {"name": "tigervnc", "system": 0}, {"name": "tin", "system": 0}, {"name": "tin-man", "system": 0}, {"name": "tracgoogleappsauthplugin", "system": 0}, {"name": "trader", "system": 0}, {"name": "util-linux", "system": 0}, {"name": "ve", "system": 0}, {"name": "vmm", "system": 0}, {"name": "vorbis-tools", "system": 0}, {"name": "wastesedge", "system": 0}, {"name": "wcd", "system": 0}, {"name": "wcd-man", "system": 0}, {"name": "wdiff", "system": 0}, {"name": "wget", "system": 0}, {"name": "wyslij-po", "system": 0}, {"name": "xboard", "system": 0}, {"name": "xdg-user-dirs", "system": 0}, {"name": "xkeyboard-config", "system": 0}] | |
1 | > | ||
2 | 0 | > | \ No newline at end of file |
1 | + | [{"name": "a2ps", "system": 0}, {"name": "aegis", "system": 0}, {"name": "anubis", "system": 0}, {"name": "aspell", "system": 0}, {"name": "bash", "system": 0}, {"name": "bfd", "system": 0}, {"name": "binutils", "system": 0}, {"name": "bison", "system": 0}, {"name": "bison-runtime", "system": 0}, {"name": "buzztrax", "system": 0}, {"name": "ccd2cue", "system": 0}, {"name": "ccide", "system": 0}, {"name": "cflow", "system": 0}, {"name": "clisp", "system": 0}, {"name": "coreutils", "system": 0}, {"name": "cpio", "system": 0}, {"name": "cppi", "system": 0}, {"name": "cpplib", "system": 0}, {"name": "cryptsetup", "system": 0}, {"name": "datamash", "system": 0}, {"name": "denemo", "system": 0}, {"name": "dfarc", "system": 0}, {"name": "dialog", "system": 0}, {"name": "dico", "system": 0}, {"name": "diffutils", "system": 0}, {"name": "dink", "system": 0}, {"name": "direvent", "system": 0}, {"name": "doodle", "system": 0}, {"name": "dos2unix", "system": 0}, {"name": "dos2unix-man", "system": 0}, {"name": "e2fsprogs", "system": 0}, {"name": "enscript", "system": 0}, {"name": "exif", "system": 0}, {"name": "fetchmail", "system": 0}, {"name": "findutils", "system": 0}, {"name": "flex", "system": 0}, {"name": "freedink", "system": 0}, {"name": "fusionforge", "system": 0}, {"name": "gas", "system": 0}, {"name": "gawk", "system": 0}, {"name": "gcal", "system": 0}, {"name": "gcc", "system": 0}, {"name": "gdbm", "system": 0}, {"name": "gettext-examples", "system": 0}, {"name": "gettext-runtime", "system": 0}, {"name": "gettext-tools", "system": 0}, {"name": "gjay", "system": 0}, {"name": "glunarclock", "system": 0}, {"name": "gnubiff", "system": 0}, {"name": "gnubik", "system": 0}, {"name": "gnucash", "system": 0}, {"name": "gnuchess", "system": 0}, {"name": "gnucobol", "system": 0}, {"name": "gnulib", "system": 0}, {"name": "gnunet", "system": 0}, {"name": "gnunet-gtk", "system": 0}, {"name": "gold", "system": 0}, {"name": "gphoto2", "system": 0}, {"name": "gprof", "system": 0}, {"name": "gramadoir", "system": 0}, {"name": "grep", "system": 0}, {"name": "grip", "system": 0}, {"name": "grub", "system": 0}, {"name": "gsasl", "system": 0}, {"name": "gss", "system": 0}, {"name": "gst-plugins-bad", "system": 0}, {"name": "gst-plugins-base", "system": 0}, {"name": "gst-plugins-good", "system": 0}, {"name": "gst-plugins-ugly", "system": 0}, {"name": "gstreamer", "system": 0}, {"name": "gtick", "system": 0}, {"name": "gtkam", "system": 0}, {"name": "gtkspell", "system": 0}, {"name": "guix", "system": 0}, {"name": "guix-packages", "system": 0}, {"name": "gutenprint", "system": 0}, {"name": "hello", "system": 0}, {"name": "help2man", "system": 0}, {"name": "help2man-texi", "system": 0}, {"name": "hylafax", "system": 0}, {"name": "idutils", "system": 0}, {"name": "jwhois", "system": 0}, {"name": "kbd", "system": 0}, {"name": "klavaro", "system": 0}, {"name": "ld", "system": 0}, {"name": "leafpad", "system": 0}, {"name": "libc", "system": 0}, {"name": "libexif", "system": 0}, {"name": "libextractor", "system": 0}, {"name": "libgnutls", "system": 0}, {"name": "libgphoto2", "system": 0}, {"name": "libgphoto2_port", "system": 0}, {"name": "libgsasl", "system": 0}, {"name": "libiconv", "system": 0}, {"name": "libidn", "system": 0}, {"name": "libidn2", "system": 0}, {"name": "lilypond", "system": 0}, {"name": "lordsawar", "system": 0}, {"name": "lprng", "system": 0}, {"name": "lynx", "system": 0}, {"name": "m4", "system": 0}, {"name": "mailfromd", "system": 0}, {"name": "mailutils", "system": 0}, {"name": "make", "system": 0}, {"name": "man-db", "system": 0}, {"name": "man-db-manpages", "system": 0}, {"name": "midi-instruments", "system": 0}, {"name": "minicom", "system": 0}, {"name": "mkisofs", "system": 0}, {"name": "muibase", "system": 0}, {"name": "myserver", "system": 0}, {"name": "nano", "system": 0}, {"name": "opcodes", "system": 0}, {"name": "parted", "system": 0}, {"name": "pies", "system": 0}, {"name": "pnmixer", "system": 0}, {"name": "popt", "system": 0}, {"name": "procps-ng", "system": 0}, {"name": "procps-ng-man", "system": 0}, {"name": "psmisc", "system": 0}, {"name": "pspp", "system": 0}, {"name": "pushover", "system": 0}, {"name": "pwdutils", "system": 0}, {"name": "pyspread", "system": 0}, {"name": "radius", "system": 0}, {"name": "recode", "system": 0}, {"name": "recutils", "system": 0}, {"name": "rpm", "system": 0}, {"name": "rush", "system": 0}, {"name": "sarg", "system": 0}, {"name": "savane", "system": 0}, {"name": "sed", "system": 0}, {"name": "sharutils", "system": 0}, {"name": "shepherd", "system": 0}, {"name": "shishi", "system": 0}, {"name": "skribilo", "system": 0}, {"name": "solfege", "system": 0}, {"name": "solfege-manual", "system": 0}, {"name": "spotmachine", "system": 0}, {"name": "sudo", "system": 0}, {"name": "sudoers", "system": 0}, {"name": "sysstat", "system": 0}, {"name": "tar", "system": 0}, {"name": "texinfo", "system": 0}, {"name": "texinfo_document", "system": 0}, {"name": "tigervnc", "system": 0}, {"name": "tin", "system": 0}, {"name": "tin-man", "system": 0}, {"name": "tracgoogleappsauthplugin", "system": 0}, {"name": "trader", "system": 0}, {"name": "util-linux", "system": 0}, {"name": "ve", "system": 0}, {"name": "vmm", "system": 0}, {"name": "vorbis-tools", "system": 0}, {"name": "wastesedge", "system": 0}, {"name": "wcd", "system": 0}, {"name": "wcd-man", "system": 0}, {"name": "wdiff", "system": 0}, {"name": "wget", "system": 0}, {"name": "wyslij-po", "system": 0}, {"name": "xboard", "system": 0}, {"name": "xdg-user-dirs", "system": 0}, {"name": "xkeyboard-config", "system": 0}, {"name": "id-editor", "system": 1, "organisation": "openstreetmap"}] |
offlate/manager.py
1 | 1 | from pathlib import Path | |
2 | 2 | from .systems.tp import TPProject | |
3 | + | from .systems.transifex import TransifexProject | |
3 | 4 | ||
4 | 5 | import json | |
5 | 6 | import os | |
… | |||
39 | 40 | if not "TP" in self.settings.conf: | |
40 | 41 | self.settings.conf["TP"] = {} | |
41 | 42 | self.project_list[p['name']] = \ | |
42 | - | TPProject(self.settings.conf["TP"], p['name'], p['lang']) | |
43 | - | self.project_list[p['name']].open(self.basedir+'/'+p['name'], p['info']['version']) | |
44 | - | except Exception: | |
43 | + | TPProject(self.settings.conf["TP"], p['name'], p['lang'], p['info']) | |
44 | + | self.project_list[p['name']].open(self.basedir+'/'+p['name']) | |
45 | + | if p['system'] == 1: | |
46 | + | if not "Transifex" in self.settings.conf: | |
47 | + | self.settings.conf['Transifex'] = {} | |
48 | + | self.project_list[p['name']] = \ | |
49 | + | TransifexProject(self.settings.conf['Transifex'], p['name'], p['lang'], p['info']) | |
50 | + | self.project_list[p['name']].open(self.basedir+'/'+p['name']) | |
51 | + | except Exception as e: | |
52 | + | print(e) | |
45 | 53 | with open(self.basedir + '/projects.json', 'w') as f: | |
46 | 54 | f.write(json.dumps([])) | |
47 | 55 | ||
48 | - | def createProject(self, name, lang, system): | |
56 | + | def createProject(self, name, lang, system, data): | |
49 | 57 | projectpath = self.basedir + '/' + name | |
50 | 58 | Path(projectpath).mkdir(parents=True) | |
51 | 59 | if system == 0: #TP | |
… | |||
56 | 64 | self.project_list[name] = proj | |
57 | 65 | self.projects.append({"name": name, "lang": lang, "system": system, | |
58 | 66 | "info": {"version": proj.version}}) | |
67 | + | if system == 1: #Transifex | |
68 | + | if not 'Transifex' in self.settings.conf: | |
69 | + | self.settings.conf['Transifex'] = {} | |
70 | + | proj = TransifexProject(self.settings.conf['Transifex'], name, lang, data) | |
71 | + | proj.initialize(projectpath) | |
72 | + | self.project_list[name] = proj | |
73 | + | self.projects.append({"name": name, "lang": lang, "system": system, | |
74 | + | "info": data}) | |
59 | 75 | self.writeProjects() | |
60 | 76 | ||
61 | 77 | def writeProjects(self): |
offlate/systems/entry.py unknown status 1
1 | + | class Entry: | |
2 | + | def __init__(self, msgids, msgstrs, fuzzy, obsolete): | |
3 | + | self.msgids = msgids | |
4 | + | self.msgstrs = msgstrs | |
5 | + | self.fuzzy = fuzzy | |
6 | + | self.obsolete = obsolete | |
7 | + | ||
8 | + | def isTranslated(self): | |
9 | + | for msgstr in self.msgstrs: | |
10 | + | if msgstr == '': | |
11 | + | return False | |
12 | + | return True | |
13 | + | ||
14 | + | def isFuzzy(self): | |
15 | + | return self.fuzzy | |
16 | + | ||
17 | + | def isObsolete(self): | |
18 | + | return self.obsolete | |
19 | + | ||
20 | + | def update(self, index, content): | |
21 | + | self.msgstrs[index] = content | |
22 | + | ||
23 | + | class POEntry(Entry): | |
24 | + | def __init__(self, entry): | |
25 | + | msgids = [entry.msgid] | |
26 | + | msgstrs = [entry.msgstr] | |
27 | + | if 0 in entry.msgstr_plural: | |
28 | + | msgstrs = [] | |
29 | + | for msgstr in entry.msgstr_plural: | |
30 | + | msgstrs.append(entry.msgstr_plural[msgstr]) | |
31 | + | msgids = [entry.msgid, entry.msgid_plural] | |
32 | + | Entry.__init__(self, msgids, msgstrs, "fuzzy" in entry.flags, entry.obsolete) | |
33 | + | self.entry = entry | |
34 | + | ||
35 | + | def update(self, index, content): | |
36 | + | Entry.update(self, index, content) | |
37 | + | if 0 in self.entry.msgstr_plural: | |
38 | + | self.entry.msgstr_plural[index] = content | |
39 | + | else: | |
40 | + | self.entry.msgstr = content | |
41 | + | ||
42 | + | class JSONEntry(Entry): | |
43 | + | def __init__(self, entry): | |
44 | + | Entry.__init__(self, [entry['source_string']], [entry['translation']], False, False) | |
45 | + | self.entry = entry | |
46 | + | ||
47 | + | def update(self, index, content): | |
48 | + | Entry.update(self, index, content) | |
49 | + | self.entry['translation'] = content | |
50 | + | ||
51 | + | class YAMLEntry(Entry): | |
52 | + | def __init__(self, entry): | |
53 | + | self.key = list(entry.keys())[0] | |
54 | + | Entry.__init__(self, self.key, entry[self.key], False, False) | |
55 | + | self.entry = entry | |
56 | + | ||
57 | + | def update(self, index, content): | |
58 | + | Entry.update(self, index, content) | |
59 | + | self.entry[self.key] = content |
offlate/systems/tp.py
11 | 11 | import os | |
12 | 12 | from pathlib import Path | |
13 | 13 | ||
14 | + | from .entry import POEntry | |
15 | + | ||
14 | 16 | class TPProject: | |
15 | - | def __init__(self, conf, name, lang): | |
17 | + | def __init__(self, conf, name, lang, data = {}): | |
16 | 18 | self.uri = "https://translationproject.org" | |
17 | 19 | self.conf = conf | |
18 | 20 | self.name = name | |
19 | 21 | self.lang = lang | |
20 | 22 | self.basedir = '' | |
23 | + | self.info = data | |
24 | + | if "version" in data: | |
25 | + | self.version = data['version'] | |
21 | 26 | ||
22 | - | def open(self, basedir, version): | |
23 | - | self.version = version | |
27 | + | def open(self, basedir): | |
24 | 28 | self.basedir = basedir | |
25 | 29 | self.updateFileName() | |
26 | 30 | self.updateGettextNames() | |
… | |||
104 | 108 | newpo.save() | |
105 | 109 | ||
106 | 110 | def send(self, interface): | |
111 | + | self.save() | |
107 | 112 | msg = EmailMessage() | |
108 | 113 | msg['Subject'] = self.filename | |
109 | 114 | msg['From'] = self.conf["email"] | |
… | |||
116 | 121 | s.login(self.conf['user'], interface.askPassword()) | |
117 | 122 | s.send_message(msg) | |
118 | 123 | ||
124 | + | def save(self): | |
125 | + | self.po.save() | |
126 | + | ||
119 | 127 | def content(self): | |
120 | - | po = polib.pofile(self.popath) | |
121 | - | return po | |
128 | + | self.po = polib.pofile(self.popath) | |
129 | + | po = [POEntry(x) for x in self.po] | |
130 | + | return {'default': po} |
offlate/systems/transifex.py unknown status 1
1 | + | import requests | |
2 | + | import json | |
3 | + | from ruamel import yaml | |
4 | + | import os | |
5 | + | ||
6 | + | from requests.auth import HTTPBasicAuth | |
7 | + | ||
8 | + | from pathlib import Path | |
9 | + | ||
10 | + | from .entry import JSONEntry | |
11 | + | ||
12 | + | def yaml_rec_load(path, source, dest): | |
13 | + | ans = [] | |
14 | + | for s in source: | |
15 | + | path2 = list(path) | |
16 | + | path2.append(s) | |
17 | + | if isinstance(source[s], str): | |
18 | + | ans.append({'path': path, 'id': s, 'source_string': source[s], 'translation': dest[s]}) | |
19 | + | else: | |
20 | + | ans.extend(yaml_rec_load(path2, source[s], dest[s])) | |
21 | + | return ans | |
22 | + | ||
23 | + | class TransifexProject: | |
24 | + | def __init__(self, conf, name, lang, data = {}): | |
25 | + | self.uri = "https://www.transifex.com" | |
26 | + | self.conf = conf | |
27 | + | self.name = name | |
28 | + | self.lang = lang | |
29 | + | self.data = data | |
30 | + | self.basedir = '' | |
31 | + | self.contents = {} | |
32 | + | ||
33 | + | def open(self, basedir): | |
34 | + | self.basedir = basedir | |
35 | + | with open(self.basedir + '/project.info') as f: | |
36 | + | self.files = json.load(f) | |
37 | + | self.slugs = [x['slug'] for x in self.files] | |
38 | + | self.loadContent() | |
39 | + | ||
40 | + | def initialize(self, basedir): | |
41 | + | self.basedir = basedir | |
42 | + | self.updateFileList() | |
43 | + | with open(self.basedir + '/project.info', 'w') as f: | |
44 | + | f.write(json.dumps(self.files)) | |
45 | + | for slug in self.slugs: | |
46 | + | self.getFile(slug) | |
47 | + | self.loadContent() | |
48 | + | ||
49 | + | def update(self, callback): | |
50 | + | self.updateFileList() | |
51 | + | ||
52 | + | def updateFileList(self): | |
53 | + | self.files = [] | |
54 | + | self.slugs = [] | |
55 | + | ans = requests.get('https://api.transifex.com/organizations/'+ | |
56 | + | self.data['organization']+'/projects/'+self.name+ | |
57 | + | '/resources/?language_code='+self.lang, | |
58 | + | auth=HTTPBasicAuth('api', self.conf['token'])) | |
59 | + | if ans.status_code == 200: | |
60 | + | l = json.loads(ans.text) | |
61 | + | self.slugs = [x['slug'] for x in l] | |
62 | + | self.files = l | |
63 | + | ||
64 | + | def loadContent(self): | |
65 | + | for ff in self.files: | |
66 | + | with open(self.filename(ff['slug'], True)) as f: | |
67 | + | with open(self.filename(ff['slug'], False)) as f2: | |
68 | + | if ff['i18n_type'] == 'YML': | |
69 | + | source = yaml.safe_load(f) | |
70 | + | dest = yaml.safe_load(f2) | |
71 | + | lang1 = list(source.keys())[0] | |
72 | + | lang2 = list(dest.keys())[0] | |
73 | + | self.contents[ff['slug']] = \ | |
74 | + | yaml_rec_load([lang2], source[lang1], dest[lang2]) | |
75 | + | ||
76 | + | def getFile(self, slug): | |
77 | + | ans = requests.get('https://www.transifex.com/api/2/project/'+ | |
78 | + | self.name+'/resource/'+slug+'/content', | |
79 | + | auth=HTTPBasicAuth('api', self.conf['token'])) | |
80 | + | if ans.status_code == 200: | |
81 | + | with open(self.filename(slug, True), 'w') as f: | |
82 | + | f.write(json.loads(ans.text)['content']) | |
83 | + | ||
84 | + | ans = requests.get('https://www.transifex.com/api/2/project/'+self.name+ | |
85 | + | '/resource/'+slug+'/translation/'+self.lang+'/?mode=translator', | |
86 | + | auth=HTTPBasicAuth('api', self.conf['token'])) | |
87 | + | if ans.status_code == 200: | |
88 | + | with open(self.filename(slug, False), 'w') as f: | |
89 | + | f.write(json.loads(ans.text)['content']) | |
90 | + | else: | |
91 | + | print(ans.text) | |
92 | + | ||
93 | + | def filename(self, slug, is_source): | |
94 | + | ext = '' | |
95 | + | for ff in self.files: | |
96 | + | if ff['slug'] == slug: | |
97 | + | f = ff | |
98 | + | break | |
99 | + | if f['i18n_type'] == 'YML': | |
100 | + | ext = 'yml' | |
101 | + | return self.basedir + '/' + slug + ('.source' if is_source else '') + '.' + ext | |
102 | + | ||
103 | + | def send(self, interface): | |
104 | + | self.save() | |
105 | + | for ff in self.files: | |
106 | + | print('{} => {}'.format(ff['slug'], ff['i18n_type'])) | |
107 | + | with open(self.filename(ff['slug'], False)) as f: | |
108 | + | content = f.read() | |
109 | + | sendcontent = {"content": content} | |
110 | + | ans = requests.put('https://www.transifex.com/api/2/project/'+ | |
111 | + | self.name+'/resource/'+ff['slug']+'/translation/'+self.lang+'/', | |
112 | + | json=sendcontent, auth=HTTPBasicAuth('api', self.conf['token'])) | |
113 | + | print(ans) | |
114 | + | print(ans.text) | |
115 | + | #for slug in self.slugs: | |
116 | + | # with open(self.filename(slug)) as f: | |
117 | + | # content = json.load(f) | |
118 | + | # sendcontent = {} | |
119 | + | # for s in content: | |
120 | + | # sendcontent[s['source_string']] = s['translation'] | |
121 | + | # sendcontent = {'content': json.dumps({'content': sendcontent})} | |
122 | + | # ans = requests.put('https://www.transifex.com/api/2/project/'+ | |
123 | + | # self.name+'/resource/'+slug+'/translation/'+self.lang+'/', | |
124 | + | # json=sendcontent, auth=HTTPBasicAuth('api', self.conf['token'])) | |
125 | + | # print(ans) | |
126 | + | # print(ans.text) | |
127 | + | ||
128 | + | def save(self): | |
129 | + | for slug in self.slugs: | |
130 | + | data = {} | |
131 | + | for d in self.contents[slug]: | |
132 | + | path = d['path'] | |
133 | + | curr = data | |
134 | + | for p in path: | |
135 | + | if p in curr: | |
136 | + | curr = curr[p] | |
137 | + | else: | |
138 | + | curr[p] = {} | |
139 | + | curr = curr[p] | |
140 | + | curr[d['id']] = d['translation'] | |
141 | + | with open(self.filename(slug, False), 'w') as f: | |
142 | + | yaml.dump(data, f, Dumper=yaml.RoundTripDumper, allow_unicode=True) | |
143 | + | ||
144 | + | def content(self): | |
145 | + | contents = {} | |
146 | + | for content in self.contents: | |
147 | + | contents[content] = [JSONEntry(x) for x in self.contents[content]] | |
148 | + | return contents |
offlate/window.py
21 | 21 | ||
22 | 22 | def askPassword(self): | |
23 | 23 | self.qd = QInputDialog() | |
24 | + | self.qd.setLabelText(self.qd.tr("Please enter your password:")) | |
24 | 25 | self.qd.setTextEchoMode(QLineEdit.Password) | |
25 | 26 | self.qd.accepted.connect(self.ok) | |
26 | 27 | self.qd.exec_() | |
… | |||
31 | 32 | super(ProjectView, self).__init__(parent) | |
32 | 33 | self.project = project | |
33 | 34 | self.content = self.project.content() | |
35 | + | self.currentContent = list(self.content.keys())[0] | |
34 | 36 | self.showTranslated = showTranslated | |
35 | 37 | self.showUntranslated = showUntranslated | |
36 | 38 | self.showFuzzy = showFuzzy | |
… | |||
39 | 41 | def updateContent(self): | |
40 | 42 | self.treeWidget.clear() | |
41 | 43 | items = [] | |
42 | - | for entry in self.content: | |
43 | - | if entry.obsolete: | |
44 | + | for entry in self.content[self.currentContent]: | |
45 | + | if entry.isObsolete(): | |
44 | 46 | continue | |
45 | 47 | cont = False | |
46 | - | if self.showTranslated and entry.translated(): | |
48 | + | if self.showTranslated and entry.isTranslated(): | |
47 | 49 | cont = True | |
48 | - | if self.showUntranslated and not entry.translated(): | |
50 | + | if self.showUntranslated and not entry.isTranslated(): | |
49 | 51 | cont = True | |
50 | - | if self.showFuzzy and 'fuzzy' in entry.flags: | |
52 | + | if self.showFuzzy and entry.isFuzzy(): | |
51 | 53 | cont = True | |
52 | 54 | if not cont: | |
53 | 55 | continue | |
54 | - | msgstr = entry.msgstr | |
55 | - | if 0 in entry.msgstr_plural: | |
56 | - | msgstr = entry.msgstr_plural[0] | |
57 | - | item = QTreeWidgetItem([entry.msgid, msgstr]) | |
56 | + | item = QTreeWidgetItem([entry.msgids[0], entry.msgstrs[0]]) | |
58 | 57 | item.setData(0, Qt.UserRole, entry) | |
59 | 58 | items.append(item) | |
60 | 59 | self.treeWidget.insertTopLevelItems(0, items) | |
… | |||
68 | 67 | self.msgid = QTextEdit() | |
69 | 68 | self.msgid.setReadOnly(True) | |
70 | 69 | self.msgstr = QTextEdit() | |
70 | + | self.filechooser = QComboBox() | |
71 | + | for project in list(self.content.keys()): | |
72 | + | self.filechooser.addItem(project) | |
73 | + | self.filechooser.currentIndexChanged.connect(self.changefile) | |
74 | + | ||
75 | + | if self.filechooser.count() > 1: | |
76 | + | vbox.addWidget(self.filechooser) | |
71 | 77 | ||
72 | 78 | self.updateContent() | |
73 | 79 | vbox.addWidget(self.treeWidget, 4) | |
… | |||
79 | 85 | self.treeWidget.setColumnWidth(0, size.width()/2) | |
80 | 86 | self.treeWidget.currentItemChanged.connect(self.selectItem) | |
81 | 87 | ||
88 | + | def changefile(self): | |
89 | + | self.currentContent = list(self.content.keys())[self.filechooser.currentIndex()] | |
90 | + | self.updateContent() | |
91 | + | ||
82 | 92 | def selectItem(self, current, old): | |
83 | 93 | if current == None: | |
84 | 94 | return | |
… | |||
87 | 97 | self.hbox.removeWidget(self.msgstr) | |
88 | 98 | self.msgid.deleteLater() | |
89 | 99 | self.msgstr.deleteLater() | |
90 | - | if 0 in data.msgstr_plural: | |
100 | + | ||
101 | + | if len(data.msgstrs) > 1: | |
91 | 102 | self.msgid = QTabWidget(); | |
92 | 103 | self.msgstr = QTabWidget(); | |
93 | 104 | singular = QTextEdit() | |
94 | 105 | singular.setReadOnly(True) | |
95 | - | singular.setText(data.msgid) | |
106 | + | singular.setText(data.msgids[0]) | |
96 | 107 | plural = QTextEdit() | |
97 | 108 | plural.setReadOnly(True) | |
98 | - | plural.setText(data.msgid_plural) | |
109 | + | plural.setText(data.msgids[1]) | |
99 | 110 | self.msgid.addTab(singular, self.tr("Singular")) | |
100 | 111 | self.msgid.addTab(plural, self.tr("Plural")) | |
101 | 112 | i = 0 | |
102 | - | while i in data.msgstr_plural: | |
113 | + | for msgstr in data.msgstrs: | |
103 | 114 | form = QTextEdit() | |
104 | - | form.setText(data.msgstr_plural[i]) | |
115 | + | form.setText(msgstr) | |
105 | 116 | form.textChanged.connect(self.modify) | |
106 | 117 | self.msgstr.addTab(form, str(i)) | |
107 | 118 | i=i+1 | |
… | |||
109 | 120 | self.msgid = QTextEdit() | |
110 | 121 | self.msgid.setReadOnly(True) | |
111 | 122 | self.msgstr = QTextEdit() | |
112 | - | self.msgid.setText(data.msgid) | |
113 | - | self.msgstr.setText(data.msgstr) | |
123 | + | self.msgid.setText(data.msgids[0]) | |
124 | + | self.msgstr.setText(data.msgstrs[0]) | |
114 | 125 | self.msgstr.textChanged.connect(self.modify) | |
115 | 126 | self.hbox.addWidget(self.msgid) | |
116 | 127 | self.hbox.addWidget(self.msgstr) | |
… | |||
119 | 130 | item = self.treeWidget.currentItem() | |
120 | 131 | data = item.data(0, Qt.UserRole) | |
121 | 132 | if self.msgstr.__class__.__name__ == "QTextEdit": | |
122 | - | data.msgstr = self.msgstr.toPlainText() | |
123 | - | item.setText(1, data.msgstr) | |
133 | + | msgstr = self.msgstr.toPlainText() | |
134 | + | data.update(0, msgstr) | |
135 | + | item.setText(1, msgstr) | |
124 | 136 | else: | |
125 | 137 | i = 0 | |
126 | - | while i in data.msgstr_plural: | |
127 | - | data.msgstr_plural[i] = self.msgstr.widget(i).toPlainText() | |
138 | + | for msgstr in data.msgstrs: | |
139 | + | data.update(i, self.msgstr.widget(i).toPlainText()) | |
128 | 140 | i=i+1 | |
129 | 141 | item.setText(1, data.msgstr_plural[0]) | |
130 | 142 | ||
131 | 143 | def save(self): | |
132 | - | self.content.save() | |
144 | + | self.project.save() | |
133 | 145 | ||
134 | 146 | def send(self): | |
135 | - | self.content.save() | |
147 | + | self.project.save() | |
136 | 148 | self.project.send(Interface()) | |
137 | 149 | ||
138 | 150 | def askmerge(self, msgid, oldstr, newstr): | |
… | |||
140 | 152 | return newstr | |
141 | 153 | ||
142 | 154 | def update(self): | |
143 | - | self.content.save() | |
155 | + | self.project.save() | |
144 | 156 | self.project.update(self.askmerge) | |
145 | 157 | self.content = self.project.content() | |
146 | 158 | self.updateContent() | |
… | |||
176 | 188 | predefinedbox.addWidget(self.predefinedprojects) | |
177 | 189 | ||
178 | 190 | contentbox = QVBoxLayout() | |
191 | + | formbox = QGroupBox(self.tr("Project information")) | |
192 | + | self.formLayout = QFormLayout() | |
193 | + | formbox.setLayout(self.formLayout) | |
194 | + | ||
179 | 195 | self.nameWidget = QLineEdit() | |
180 | 196 | self.langWidget = QLineEdit() | |
181 | - | contentbox.addWidget(self.nameWidget) | |
182 | - | contentbox.addWidget(self.langWidget) | |
197 | + | self.formLayout.addRow(QLabel(self.tr("Name:")), self.nameWidget) | |
198 | + | self.formLayout.addRow(QLabel(self.tr("Target Language:")), self.langWidget) | |
183 | 199 | self.combo = QComboBox() | |
184 | 200 | self.combo.addItem(self.tr("The Translation Project")) | |
185 | - | contentbox.addWidget(self.combo) | |
201 | + | self.combo.addItem(self.tr("Transifex")) | |
202 | + | self.formLayout.addRow(self.combo) | |
203 | + | ||
186 | 204 | hhbox = QHBoxLayout() | |
187 | 205 | cancel = QPushButton(self.tr("Cancel")) | |
188 | 206 | ok = QPushButton(self.tr("OK")) | |
189 | 207 | hhbox.addWidget(cancel) | |
190 | 208 | hhbox.addWidget(ok) | |
209 | + | contentbox.addWidget(formbox) | |
191 | 210 | contentbox.addLayout(hhbox) | |
192 | 211 | hbox.addLayout(predefinedbox) | |
193 | 212 | hbox.addLayout(contentbox) | |
194 | 213 | ||
214 | + | self.additionalFields = [] | |
215 | + | self.additionalFields.append([]) | |
216 | + | self.additionalFields.append([]) | |
217 | + | self.transifexOrganisation = QLineEdit() | |
218 | + | transifexOrganisationLabel = QLabel(self.tr("Organization")) | |
219 | + | self.additionalFields[1].append({'label': transifexOrganisationLabel, | |
220 | + | 'widget': self.transifexOrganisation}) | |
221 | + | ||
195 | 222 | self.setLayout(hbox) | |
196 | 223 | ||
197 | 224 | self.predefinedprojects.currentItemChanged.connect(self.fill) | |
198 | 225 | cancel.clicked.connect(self.close) | |
199 | 226 | ok.clicked.connect(self.ok) | |
200 | 227 | self.searchfield.textChanged.connect(self.filter) | |
228 | + | self.combo.currentIndexChanged.connect(self.othersystem) | |
201 | 229 | ||
202 | 230 | def ok(self): | |
203 | 231 | self.askNew = True | |
… | |||
208 | 236 | data = item.data(Qt.UserRole) | |
209 | 237 | self.nameWidget.setText(data['name']) | |
210 | 238 | self.combo.setCurrentIndex(int(data['system'])) | |
239 | + | if data['system'] == 1: | |
240 | + | self.transifexOrganisation.setText(data['organisation']) | |
211 | 241 | ||
212 | 242 | def filter(self): | |
213 | 243 | search = self.searchfield.text() | |
… | |||
231 | 261 | def getProjectSystem(self): | |
232 | 262 | return self.combo.currentIndex() | |
233 | 263 | ||
264 | + | def getProjectInfo(self): | |
265 | + | if self.getProjectSystem() == 0: | |
266 | + | return {} | |
267 | + | if self.getProjectSystem() == 1: | |
268 | + | return {'organization': self.additionalFields[1][0]['widget'].text()} | |
269 | + | return {} | |
270 | + | ||
271 | + | def othersystem(self): | |
272 | + | for system in self.additionalFields: | |
273 | + | for widget in system: | |
274 | + | self.formLayout.takeRow(widget['widget']) | |
275 | + | widget['widget'].hide() | |
276 | + | widget['label'].hide() | |
277 | + | self.formLayout.invalidate() | |
278 | + | for widget in self.additionalFields[self.combo.currentIndex()]: | |
279 | + | self.formLayout.addRow(widget['label'], widget['widget']) | |
280 | + | widget['widget'].show() | |
281 | + | widget['label'].show() | |
282 | + | ||
234 | 283 | class SettingsWindow(QDialog): | |
235 | 284 | def __init__(self, preferences, parent = None): | |
236 | 285 | super().__init__(parent) | |
… | |||
352 | 401 | if not w.wantNew(): | |
353 | 402 | return | |
354 | 403 | self.manager.createProject(w.getProjectName(), w.getProjectLang(), | |
355 | - | w.getProjectSystem()) | |
404 | + | w.getProjectSystem(), w.getProjectInfo()) | |
356 | 405 | self.open(w.getProjectName()) | |
357 | 406 | ||
358 | 407 | def send(self): |
setup.py
5 | 5 | version="0.1.dev", | |
6 | 6 | packages=find_packages(exclude=['.guix-profile*']), | |
7 | 7 | python_requires = '>=3', | |
8 | - | install_requires=['polib'], | |
8 | + | install_requires=['polib', 'PyYAML'], | |
9 | 9 | entry_points={ | |
10 | 10 | 'gui_scripts': [ | |
11 | 11 | 'offlate=offlate.window:main', |