Merge lp:~oubiwann/ubuntu-accomplishments-system/941201-missing-deps into lp:~jonobacon/ubuntu-accomplishments-system/trophyinfo

Proposed by Duncan McGreggor
Status: Superseded
Proposed branch: lp:~oubiwann/ubuntu-accomplishments-system/941201-missing-deps
Merge into: lp:~jonobacon/ubuntu-accomplishments-system/trophyinfo
Diff against target: 2835 lines (+499/-1289)
27 files modified
AUTHORS (+2/-1)
accomplishments/config.py (+1/-54)
accomplishments/daemon/app.py (+111/-101)
accomplishments/daemon/dbusapi.py (+2/-2)
accomplishments/daemon/tests/tests.py (+17/-15)
accomplishments/exceptions.py (+32/-0)
accomplishments/gui/AboutTrophyinfoDialog.py (+9/-7)
accomplishments/gui/PreferencesTrophyinfoDialog.py (+8/-4)
accomplishments/gui/TrophyinfoWindow.py (+46/-48)
accomplishments/gui/base/AboutDialog.py (+5/-5)
accomplishments/gui/base/Builder.py (+9/-9)
accomplishments/gui/base/PreferencesDialog.py (+10/-9)
accomplishments/gui/base/Window.py (+17/-12)
accomplishments/gui/base/__init__.py (+2/-3)
accomplishments/gui/base/helpers.py (+10/-36)
accomplishments/main.py (+6/-27)
accomplishments/util/__init__.py (+88/-0)
accomplishments/util/dist.py (+75/-0)
bin/rundaemon.sh (+2/-2)
bin/trophyinfo (+10/-6)
daemon/libaccomplishments-daemon/trophy-accomplished.svg (+0/-854)
data/ui/TrophyinfoWindow.ui (+1/-1)
install_deps.sh (+3/-0)
setup.py (+6/-75)
tests/test_example.py (+13/-7)
tests/test_lint.py (+13/-10)
trophyinfo.desktop.in (+1/-1)
To merge this branch: bzr merge lp:~oubiwann/ubuntu-accomplishments-system/941201-missing-deps
Reviewer Review Type Date Requested Status
Jono Bacon Pending
Review via email: mp+95840@code.launchpad.net

This proposal has been superseded by a proposal from 2012-03-05.

Description of the change

This branch just adds a convenience script for installing deps.

It should be merged *after* the following:
  https://code.launchpad.net/~oubiwann/ubuntu-accomplishments-system/941255-unified-source-dir/+merge/95839

The reason for this is that the current branch has merged the "unified-source-dir" branch already, and that would circumvent the other branch :-)

To post a comment you must log in.

Unmerged revisions

72. By Duncan McGreggor

Added more deps.

71. By Duncan McGreggor

Merged sibling branch.

70. By Duncan McGreggor

Added more deps.

69. By Duncan McGreggor

Added a convenience install script.

68. By Duncan McGreggor

Merged sibling branch.

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1=== modified file 'AUTHORS'
2--- AUTHORS 2012-01-22 23:09:09 +0000
3+++ AUTHORS 2012-03-05 04:37:19 +0000
4@@ -1,1 +1,2 @@
5-Copyright (C) YYYY <Your Name> <Your E-mail>
6+Copyright (c) 2012 Duncan McGreggor <duncan@dreamhost.com>
7+Copyright (c) YYYY <Your Name> <Your E-mail>
8
9=== renamed directory 'trophyinfo' => 'accomplishments'
10=== added file 'accomplishments/__init__.py'
11=== renamed file 'trophyinfo_lib/trophyinfoconfig.py' => 'accomplishments/config.py'
12--- trophyinfo_lib/trophyinfoconfig.py 2012-01-22 23:09:09 +0000
13+++ accomplishments/config.py 2012-03-05 04:37:19 +0000
14@@ -3,61 +3,8 @@
15 # This file is in the public domain
16 ### END LICENSE
17
18-# THIS IS Trophyinfo CONFIGURATION FILE
19-# YOU CAN PUT THERE SOME GLOBAL VALUE
20-# Do not touch unless you know what you're doing.
21-# you're warned :)
22-
23-__all__ = [
24- 'project_path_not_found',
25- 'get_data_file',
26- 'get_data_path',
27- ]
28-
29 # Where your project will look for your data (for instance, images and ui
30 # files). By default, this is ../data, relative your trunk layout
31-__trophyinfo_data_directory__ = '../data/'
32+__trophyinfo_data_directory__ = 'data'
33 __license__ = ''
34 __version__ = 'VERSION'
35-
36-import os
37-
38-import gettext
39-from gettext import gettext as _
40-gettext.textdomain('trophyinfo')
41-
42-class project_path_not_found(Exception):
43- """Raised when we can't find the project directory."""
44-
45-
46-def get_data_file(*path_segments):
47- """Get the full path to a data file.
48-
49- Returns the path to a file underneath the data directory (as defined by
50- `get_data_path`). Equivalent to os.path.join(get_data_path(),
51- *path_segments).
52- """
53- return os.path.join(get_data_path(), *path_segments)
54-
55-
56-def get_data_path():
57- """Retrieve trophyinfo data path
58-
59- This path is by default <trophyinfo_lib_path>/../data/ in trunk
60- and /usr/share/trophyinfo in an installed version but this path
61- is specified at installation time.
62- """
63-
64- # Get pathname absolute or relative.
65- path = os.path.join(
66- os.path.dirname(__file__), __trophyinfo_data_directory__)
67-
68- abs_data_path = os.path.abspath(path)
69- if not os.path.exists(abs_data_path):
70- raise project_path_not_found
71-
72- return abs_data_path
73-
74-
75-def get_version():
76- return __version__
77
78=== renamed directory 'daemon' => 'accomplishments/daemon'
79=== added file 'accomplishments/daemon/__init__.py'
80=== renamed file 'daemon/libaccomplishments-daemon/daemon.py' => 'accomplishments/daemon/app.py'
81--- daemon/libaccomplishments-daemon/daemon.py 2012-02-24 06:08:50 +0000
82+++ accomplishments/daemon/app.py 2012-03-05 04:37:19 +0000
83@@ -3,12 +3,28 @@
84 Provides a D-Bus API to record accomplishments as achieved (trophies) and
85 to enumerate achieved and unachieved accomplishments.
86 """
87+import ConfigParser
88+import Image, ImageEnhance
89+from StringIO import StringIO
90+import datetime
91+import getpass
92+import glob
93+import gobject
94+import gpgme
95+import json
96+import logging
97+from optparse import OptionParser
98+import os
99+import pwd
100+import subprocess
101+import time
102+
103+import dbus
104+from dbus.mainloop.glib import DBusGMainLoop
105+import dbus.service
106
107 from twisted.internet import glib2reactor
108 glib2reactor.install()
109-from dbus.mainloop.glib import DBusGMainLoop
110-DBusGMainLoop(set_as_default=True)
111-
112 from twisted.internet import defer, reactor
113 from twisted.internet.protocol import ProcessProtocol
114 from twisted.python import filepath
115@@ -17,35 +33,25 @@
116 from ubuntuone.couch import auth
117
118 import xdg.BaseDirectory
119-import os
120-import glob
121-import getpass
122-import ConfigParser
123-import gobject
124-import pwd
125-import subprocess
126-import time
127-import dbus
128-import dbus.service
129-import json
130-import logging
131-import gpgme
132-import Image, ImageEnhance
133-from StringIO import StringIO
134-import datetime
135-import xdg.BaseDirectory
136-from dbus.mainloop.glib import DBusGMainLoop
137-from optparse import OptionParser
138+
139 try:
140 import pynotify
141 except ImportError:
142 pynotify = None
143
144+import accomplishments
145+from accomplishments import exceptions
146+
147+
148+DBusGMainLoop(set_as_default=True)
149 MATRIX_USERNAME = "openiduser155707"
150 LOCAL_USERNAME = getpass.getuser()
151 SCRIPT_DELAY = 900
152
153+
154 class SubprocessReturnCodeProtocol(ProcessProtocol):
155+ """
156+ """
157 def connectionMade(self):
158 self.returnCodeDeferred = defer.Deferred()
159
160@@ -58,16 +64,12 @@
161 def errReceived(self, data):
162 print data
163
164-class NoSuchAccomplishment(ValueError):
165- "No such accomplishment has been registered"
166-
167-class AccomplishmentLocked(ValueError):
168- "This accomplishment requires other things to be accomplished first"
169
170 class Accomplishments(object):
171 """The main accomplishments daemon
172- No D-Bus required, so that it can be used for testing."""
173-
174+
175+ No D-Bus required, so that it can be used for testing.
176+ """
177 def __init__(self, service, show_notifications=None):
178 self.accomplishments_path = None
179 self.scripts_path = None
180@@ -79,9 +81,9 @@
181 self.dir_config = None
182 self.dir_data = None
183 self.dir_cache = None
184-
185+
186 # create config / data dirs if they don't exist
187-
188+
189 self.dir_config = os.path.join(xdg.BaseDirectory.xdg_config_home, "accomplishments")
190 self.dir_data = os.path.join(xdg.BaseDirectory.xdg_data_home, "accomplishments")
191 self.dir_cache = os.path.join(xdg.BaseDirectory.xdg_cache_home, "accomplishments")
192@@ -93,20 +95,20 @@
193 os.makedirs(self.dir_data)
194
195 if not os.path.exists(self.dir_cache):
196- os.makedirs(self.dir_cache)
197+ os.makedirs(self.dir_cache)
198
199 # set up logging
200 logdir = os.path.join(self.dir_cache, "logs")
201-
202+
203 if not os.path.exists(logdir):
204 os.makedirs(logdir)
205-
206+
207 #self.logging = logging
208 logging.basicConfig(filename=(os.path.join(logdir, 'daemon.log')), level=logging.INFO)
209
210 now = datetime.datetime.now()
211 logging.info("------------------- Ubuntu Accomplishments Daemon Log - %s -------------------", str(now))
212-
213+
214 self._loadConfigFile()
215
216 print "Accomplishments path: " + self.accomplishments_path
217@@ -119,7 +121,7 @@
218
219 self.wait_until_a_sig_file_arrives()
220 self.generate_all_trophies()
221-
222+
223 reactor.callLater(5, self.run_scripts, False)
224
225 @defer.inlineCallbacks
226@@ -127,7 +129,7 @@
227 path, info = yield self.sd.wait_for_signals(signal_ok="DownloadFinished", success_filter=lambda path, info: path.startswith(self.trophies_path) and path.endswith(".asc"))
228 logging.info("Trophy signature recieved...")
229 accomname = os.path.splitext(os.path.splitext(os.path.split(path)[1])[0])[0]
230- data = self.listAccomplishmentInfo(accomname)
231+ data = self.listAccomplishmentInfo(accomname)
232 iconpath = os.path.join(os.path.join(os.path.join(self.accomplishments_path, data[0]["application"]), "trophyimages"), data[0]["icon"])
233
234 item = os.path.split(path)[1][:-11]
235@@ -135,7 +137,7 @@
236
237 data = self.listAccomplishmentInfo(item)
238
239- if self.show_notifications == True and pynotify and (
240+ if self.show_notifications == True and pynotify and (
241 pynotify.is_initted() or pynotify.init("icon-summary-body")):
242 self.service.trophy_received("foo")
243 trophy_icon_path = "file://%s" % os.path.realpath(os.path.join(os.path.split(__file__)[0], "trophy-accomplished.svg"))
244@@ -148,7 +150,7 @@
245
246 def _get_accomplishments_files_list(self):
247 logging.info("Looking for accomplishments files in " + self.accomplishments_path)
248- accom_files = os.path.join(self.accomplishments_path,
249+ accom_files = os.path.join(self.accomplishments_path,
250 "*", "*.accomplishment")
251 return glob.glob(accom_files)
252
253@@ -164,10 +166,10 @@
254
255 def _get_trophies_files_list(self):
256 logging.info("Get trophies files list")
257-
258+
259 trophy_files = os.path.join(self.trophies_path, "*", "*.trophy")
260 unverif_list = glob.glob(trophy_files)
261-
262+
263 verif_list = []
264
265 for t in unverif_list:
266@@ -191,14 +193,14 @@
267 else:
268 result = {'timestamp': sig[0].timestamp, 'signer': sig[0].fpr}
269 logging.info("...Verified!")
270- verif_list.append(t)
271+ verif_list.append(t)
272 else:
273 logging.info(".asc does not exist for this trophy")
274
275 logging.info("Verifying trophy signature")
276-
277+
278 return verif_list
279-
280+
281 def _load_trophy_file(self, f):
282 logging.info("Load trophy file: " + f)
283 config = ConfigParser.RawConfigParser()
284@@ -210,41 +212,45 @@
285
286 def listAllAccomplishments(self):
287 logging.info("List all accomplishments")
288- fs = [self._load_accomplishment_file(f) for f in
289+ fs = [self._load_accomplishment_file(f) for f in
290 self._get_accomplishments_files_list()]
291 return fs
292
293 def generate_all_trophies(self):
294 paths = []
295 final = []
296-
297- files = self._get_accomplishments_files_list()
298-
299+
300+ files = self._get_accomplishments_files_list()
301+
302 for f in files:
303 paths.append(os.path.split(f)[0])
304
305 paths = list(set(paths))
306-
307+
308 for p in paths:
309 app = os.path.split(p)[1]
310 app_trophyimagespath = os.path.join(p, "trophyimages")
311 cache_trophyimagespath = os.path.join(os.path.join(self.dir_cache, "trophyimages"), app)
312 if not os.path.exists(cache_trophyimagespath):
313 os.makedirs(cache_trophyimagespath)
314-
315+
316 # first delete existing images
317 lockedlist=glob.glob(cache_trophyimagespath + "/*locked*")
318-
319+
320 opplist=glob.glob(cache_trophyimagespath + "/*opportunity*")
321-
322+
323 for l in lockedlist:
324 os.remove(l)
325
326 for o in opplist:
327 os.remove(o)
328-
329+
330 # now generate our trophy images
331- self.generate_trophy_images(app_trophyimagespath, cache_trophyimagespath, "lock.png")
332+ lock_image_path = os.path.join(
333+ os.path.dirname(accomplishments.__path__[0]),
334+ "data/media/lock.png")
335+ self.generate_trophy_images(
336+ app_trophyimagespath, cache_trophyimagespath, lock_image_path)
337
338 def reduce_trophy_opacity(self, im, opacity):
339 """Returns an image with reduced opacity."""
340@@ -257,25 +263,25 @@
341 alpha = ImageEnhance.Brightness(alpha).enhance(opacity)
342 im.putalpha(alpha)
343 return im
344-
345+
346 def generate_trophy_images(self, infolder, outfolder, watermark):
347 mark = Image.open(watermark)
348 for root, dirs, files in os.walk(infolder):
349- for name in files:
350+ for name in files:
351 try:
352 im = Image.open(os.path.join(root, name))
353 filename = os.path.join(outfolder, name)
354 filecore = os.path.splitext(filename)[0]
355 filetype = os.path.splitext(filename)[1]
356-
357+
358 im.save(filename)
359
360 # Opacity set to 1.0 until we figure out a better way of showing opportunities
361 reduced = self.reduce_trophy_opacity(im, 1.0)
362 reduced.save(filecore + "-opportunity" + filetype)
363-
364+
365 if im.mode != 'RGBA':
366- im = im.convert('RGBA')
367+ im = im.convert('RGBA')
368 layer = Image.new('RGBA', im.size, (0,0,0,0))
369 position = (im.size[0]-mark.size[0], im.size[1]-mark.size[1])
370 layer.paste(mark, position)
371@@ -283,14 +289,18 @@
372 except Exception, (msg):
373 print msg
374
375-
376 def verifyU1Account(self):
377 # check if this machine has an Ubuntu One account
378 logging.info("Check if this machine has an Ubuntu One account...")
379- u1email = json.loads(auth.request(url='https://one.ubuntu.com/api/account/')[1])['email']
380+ u1auth_response = auth.request(
381+ url='https://one.ubuntu.com/api/account/')
382+ u1email = None
383+ if not isinstance(u1auth_response, basestring):
384+ u1email = json.loads(u1auth_response[1])['email']
385
386 if u1email is None:
387 logging.info("...No.")
388+ logging.info(u1auth_response)
389 self.has_u1 = False
390 return False
391 else:
392@@ -332,7 +342,7 @@
393 # Writing our configuration file to 'example.cfg'
394 with open(cfile, 'wb') as configfile:
395 config.write(configfile)
396-
397+
398 self._loadConfigFile()
399
400 def _writeConfigFile(self):
401@@ -351,7 +361,7 @@
402 with open(cfile, 'wb') as configfile:
403 # Writing our configuration file to 'example.cfg'
404 config.write(configfile)
405-
406+
407 self.accomplishments_path = os.path.join(self.accomplishments_path, "accomplishments")
408 logging.info("...done.")
409
410@@ -362,27 +372,27 @@
411 try:
412 data = self._load_accomplishment_file(accom_file)
413 except KeyError:
414- raise NoSuchAccomplishment()
415-
416+ raise exceptions.NoSuchAccomplishment()
417+
418 needsinfolist = []
419-
420+
421 for k in data:
422 if "needs-information" in k:
423 needsinfolist.append(data[k])
424-
425+
426 for n in needsinfolist:
427 values = self.getExtraInformation(app, n)
428 data[n] = values[0][n]
429-
430+
431 if "depends" in data:
432 for dependency in data["depends"].split(","):
433 dapp, dname = dependency.split("/")
434 dtrophy_file = os.path.join(
435- self.trophies_path, dapp,
436+ self.trophies_path, dapp,
437 "%s.trophy" % dname)
438 if not os.path.exists(dtrophy_file):
439- raise AccomplishmentLocked()
440-
441+ raise exceptions.AccomplishmentLocked()
442+
443 cp = ConfigParser.RawConfigParser()
444 cp.add_section("trophy")
445 del data["_filename"]
446@@ -393,7 +403,7 @@
447 os.makedirs(os.path.join(self.trophies_path, app))
448 except OSError:
449 pass # already exists
450- trophy_file = os.path.join(self.trophies_path, app,
451+ trophy_file = os.path.join(self.trophies_path, app,
452 "%s.trophy" % accomplishment_name)
453 fp = open(trophy_file, "w")
454 cp.write(fp)
455@@ -401,10 +411,10 @@
456
457 if not data["needs-signing"] or data["needs-signing"] == False:
458 self.trophy_received()
459- if self.show_notifications == True and pynotify and (
460+ if self.show_notifications == True and pynotify and (
461 pynotify.is_initted() or pynotify.init("icon-summary-body")):
462 trophy_icon_path = "file://%s" % os.path.realpath(os.path.join(os.path.split(__file__)[0], "trophy-accomplished.svg"))
463- n = pynotify.Notification("You have accomplished something!",
464+ n = pynotify.Notification("You have accomplished something!",
465 data["title"], trophy_icon_path)
466 n.show()
467
468@@ -413,7 +423,7 @@
469
470 def listAllTrophies(self):
471 logging.info("List all trophies")
472- fs = [self._load_trophy_file(f) for f in
473+ fs = [self._load_trophy_file(f) for f in
474 self._get_trophies_files_list()]
475 return fs
476
477@@ -528,9 +538,9 @@
478 except IOError as e:
479 infofile = os.path.join(accomextrainfo, accomconfig.get("accomplishment", "needs-information"))
480 infoconfig = ConfigParser.RawConfigParser()
481- infoconfig.read(infofile)
482+ infoconfig.read(infofile)
483 d = {"application" : accomconfig.get("accomplishment", "application"), "needs-information" : accomconfig.get("accomplishment", "needs-information"), "label" : infoconfig.get("label", self.lang), "description" : infoconfig.get("description", self.lang)}
484- infoneeded.append(d)
485+ infoneeded.append(d)
486
487 # uniqify all the data required
488 final = []
489@@ -563,9 +573,9 @@
490 config = ConfigParser.RawConfigParser()
491 config.read(infofile)
492 final = config.get("general", "name")
493-
494+
495 data["application-human"] = final
496-
497+
498 # If the trophy file exists, this must be accomplished and not locked
499 trophy_file = os.path.join(self.trophies_path, app, "%s.trophy" % name)
500 got = os.path.exists(trophy_file + ".asc")
501@@ -590,7 +600,7 @@
502 for dependency in dependencies:
503 dapp, dname = dependency.split("/")
504 daccomplishment_file = os.path.join(
505- self.accomplishments_path, dapp,
506+ self.accomplishments_path, dapp,
507 "%s.accomplishment" % dname)
508 daccomplishment_data = things[daccomplishment_file]
509 if daccomplishment_data["accomplished"] == False:
510@@ -629,7 +639,7 @@
511 for i in files:
512 if search in i:
513 match = i
514-
515+
516 config = ConfigParser.RawConfigParser()
517 config.read(match)
518 data.append(dict(config._sections["accomplishment"]))
519@@ -640,7 +650,7 @@
520 print "--- Starting Running Scripts ---"
521 logging.info("--- Starting Running Scripts ---")
522 self.service.scriptrunner_start()
523-
524+
525 # Is the user currently logged in and running a gnome session?
526 username = pwd.getpwuid(uid).pw_name
527 try:
528@@ -670,9 +680,9 @@
529 except dbus.exceptions.DBusException:
530 logging.info("User %s does not have the accomplishments daemon available" % username)
531 return
532-
533+
534 accoms = self.listAllAvailableAccomplishmentsWithScripts()
535-
536+
537 for accom in accoms:
538 print "Running: " + accom["_script"]
539 logging.info("Running: " + accom["_script"])
540@@ -701,14 +711,14 @@
541 pprotocol = SubprocessReturnCodeProtocol()
542 reactor.spawnProcess(pprotocol, command[0], command, env=os.environ)
543 return pprotocol.returnCodeDeferred
544-
545+
546 def run_scripts_for_all_active_users(self):
547- for uid in [x.pw_uid for x in pwd.getpwall()
548+ for uid in [x.pw_uid for x in pwd.getpwall()
549 if x.pw_dir.startswith('/home/') and x.pw_shell != '/bin/false']:
550 os.seteuid(0)
551 self.run_scripts_for_user(uid)
552
553- def run_scripts(self, run_by_client):
554+ def run_scripts(self, run_by_client):
555 uid = os.getuid()
556 if uid == 0:
557 logging.info("Run scripts for all active users")
558@@ -722,7 +732,7 @@
559
560 def createExtraInformationFile(self, app, item, data):
561 logging.info("Creating Extra Information file: %s, %s, %s", app, item, data)
562-
563+
564 extrainfodir = os.path.join(self.trophies_path, ".extrainformation/")
565
566 if not os.path.isdir(extrainfodir):
567@@ -765,58 +775,58 @@
568 # because doing that confuses everything, so we create our own
569 # private Accomplishments object and use it.
570 self.ad = Accomplishments(self, self.show_notifications)
571-
572- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
573+
574+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
575 in_signature="", out_signature="aa{sv}")
576 def listAllAccomplishments(self):
577 return self.ad.listAllAccomplishments()
578
579- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
580+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
581 in_signature="", out_signature="aa{sv}")
582 def listAllTrophies(self):
583 return self.ad.listAllTrophies()
584
585- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
586+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
587 in_signature="", out_signature="aa{sv}")
588 def listAllAccomplishmentsAndStatus(self):
589 return self.ad.listAllAccomplishmentsAndStatus()
590
591- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
592+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
593 in_signature="", out_signature="aa{sv}")
594 def listAllAvailableAccomplishmentsWithScripts(self):
595 return self.ad.listAllAvailableAccomplishmentsWithScripts()
596
597- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
598+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
599 in_signature="", out_signature="aa{sv}")
600 def getAllExtraInformationRequired(self):
601 return self.ad.getAllExtraInformationRequired()
602
603- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
604+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
605 in_signature="", out_signature="aa{sv}")
606 def listAccomplishmentInfo(self, accomplishment):
607 return self.ad.listAccomplishmentInfo(accomplishment)
608
609- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
610+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
611 in_signature="b", out_signature="")
612 def run_scripts(self, run_by_client):
613 return self.ad.run_scripts(run_by_client)
614
615- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
616+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
617 in_signature="", out_signature="aa{sv}")
618 def getExtraInformation(self, app, info):
619 return self.ad.getExtraInformation(app, info)
620
621- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
622+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
623 in_signature="", out_signature="")
624 def createExtraInformationFile(self, app, item, data):
625 return self.ad.createExtraInformationFile(app, item, data)
626
627- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
628+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
629 in_signature="ss", out_signature="")
630 def accomplish(self, app, accomplishment_name):
631 trophy = self.ad.accomplish(app, accomplishment_name)
632
633- @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
634+ @dbus.service.method(dbus_interface='org.ubuntu.accomplishments',
635 in_signature="s", out_signature="b")
636 def registerTrophyDir(self, trophydir):
637 return self.ad.registerTrophyDir(trophydir)
638@@ -844,7 +854,7 @@
639 @dbus.service.signal(dbus_interface='org.ubuntu.accomplishments')
640 def scriptrunner_finish(self):
641 pass
642-
643+
644 if __name__ == "__main__":
645 parser = OptionParser()
646 parser.set_defaults(suppress_notifications=False)
647
648=== renamed file 'daemon/libaccomplishments/__init__.py' => 'accomplishments/daemon/dbusapi.py'
649--- daemon/libaccomplishments/__init__.py 2012-01-27 06:28:24 +0000
650+++ accomplishments/daemon/dbusapi.py 2012-03-05 04:37:19 +0000
651@@ -1,10 +1,10 @@
652 # A stupid Python-specific wrapper for the libaccomplishments-daemon D-Bus API
653-# This should not be a Python library. It should be a
654+# This should not be a Python library. It should be a
655 # GObject-introspection-capable C thing so anyone can use it. But someone else
656 # needs to write that because I'm crap at Vala.
657-
658 import dbus
659
660+
661 def Accomplishments():
662 obj = dbus.SessionBus().get_object("org.ubuntu.accomplishments", "/")
663 return dbus.Interface(obj, "org.ubuntu.accomplishments")
664
665=== renamed directory 'daemon/libaccomplishments-daemon/tests' => 'accomplishments/daemon/tests'
666=== modified file 'accomplishments/daemon/tests/tests.py'
667--- daemon/libaccomplishments-daemon/tests/tests.py 2012-01-27 06:28:24 +0000
668+++ accomplishments/daemon/tests/tests.py 2012-03-05 04:37:19 +0000
669@@ -1,5 +1,6 @@
670-"Tests for libaccomplishments-daemon"
671-
672+"""
673+Tests for accomplishments daemon.
674+"""
675 import unittest
676 import sys, os
677 import tempfile
678@@ -9,7 +10,8 @@
679 import subprocess
680
681 sys.path.append(os.path.join(os.path.split(__file__)[0], ".."))
682-import daemon
683+from accomplishments.daemon import app
684+
685
686 class TestDaemon(unittest.TestCase):
687 def setUp(self):
688@@ -19,7 +21,7 @@
689 os.mkdir(os.path.join(self.td, "scripts"))
690 os.mkdir(os.path.join(self.td, "scripts", "app1"))
691 os.mkdir(os.path.join(self.td, "trophies"))
692- fp = open(os.path.join(self.td, "accomplishments", "app1",
693+ fp = open(os.path.join(self.td, "accomplishments", "app1",
694 "first.accomplishment"), "w")
695 fp.write("""[accomplishment]
696 application=app1
697@@ -27,7 +29,7 @@
698 description=An example accomplishment for the test suite
699 """)
700 fp.close()
701- fp = open(os.path.join(self.td, "accomplishments", "app1",
702+ fp = open(os.path.join(self.td, "accomplishments", "app1",
703 "second.accomplishment"), "w")
704 fp.write("""[accomplishment]
705 application=app1
706@@ -36,7 +38,7 @@
707 depends=app1/first
708 """)
709 fp.close()
710- fp = open(os.path.join(self.td, "accomplishments", "app1",
711+ fp = open(os.path.join(self.td, "accomplishments", "app1",
712 "third.accomplishment"), "w")
713 fp.write("""[accomplishment]
714 application=app1
715@@ -44,11 +46,11 @@
716 description=Another example accomplishment for the test suite, no dependency
717 """)
718 fp.close()
719- fp = open(os.path.join(self.td, "scripts", "app1",
720+ fp = open(os.path.join(self.td, "scripts", "app1",
721 "third.py"), "w")
722 fp.write("""print 'hello'""")
723 fp.close()
724- self.d = daemon.Accomplishments(
725+ self.d = app.Accomplishments(
726 accomplishments_path=os.path.join(self.td, "accomplishments"),
727 trophies_path=os.path.join(self.td, "trophies"),
728 scripts_path=os.path.join(self.td, "scripts"))
729@@ -62,12 +64,12 @@
730 self.assertTrue("title" in accoms[0])
731 fn = accoms[0].get("_filename", "")
732 self.assertTrue(
733- fn.endswith("app1/first.accomplishment") or
734- fn.endswith("app1/second.accomplishment") or
735+ fn.endswith("app1/first.accomplishment") or
736+ fn.endswith("app1/second.accomplishment") or
737 fn.endswith("app1/third.accomplishment"))
738
739 def test_bad_accomplishment_award_rejected(self):
740- self.assertRaises(daemon.NoSuchAccomplishment, self.d.accomplish,
741+ self.assertRaises(app.NoSuchAccomplishment, self.d.accomplish,
742 "app1", "nonexistent")
743
744 def test_accomplish(self):
745@@ -117,7 +119,7 @@
746 self.assert_("Found an accomplishment that shouldn't exist")
747
748 def test_cannot_accomplished_locked(self):
749- self.assertRaises(daemon.AccomplishmentLocked, self.d.accomplish, "app1", "second")
750+ self.assertRaises(app.AccomplishmentLocked, self.d.accomplish, "app1", "second")
751
752 def test_all_available_accomplishments_with_scripts(self):
753 asa = self.d.listAllAvailableAccomplishmentsWithScripts()
754@@ -129,8 +131,8 @@
755 def setUp(self):
756 TestDaemon.setUp(self)
757 env = os.environ.copy()
758- path = os.path.join(os.path.split(__file__)[0], "..", "daemon.py")
759- self.p = subprocess.Popen(['python', path,
760+ path = os.path.join(os.path.split(__file__)[0], "..", "app.py")
761+ self.p = subprocess.Popen(['python', path,
762 "--accomplishments-path=%s" % os.path.join(self.td, "accomplishments"),
763 "--trophies-path=%s" % os.path.join(self.td, "trophies"),
764 "--scripts-path=%s" % os.path.join(self.td, "scripts"),
765@@ -144,7 +146,7 @@
766 self.d = dbus.Interface(obj, "org.ubuntu.accomplishments")
767
768 def test_bad_accomplishment_award_rejected(self):
769- self.assertRaises(dbus.DBusException, self.d.accomplish,
770+ self.assertRaises(dbus.DBusException, self.d.accomplish,
771 "app1", "nonexistent")
772
773 def test_cannot_accomplished_locked(self):
774
775=== added file 'accomplishments/exceptions.py'
776--- accomplishments/exceptions.py 1970-01-01 00:00:00 +0000
777+++ accomplishments/exceptions.py 2012-03-05 04:37:19 +0000
778@@ -0,0 +1,32 @@
779+class Error(Exception):
780+ """
781+ A base class for exceptions.
782+ """
783+ def __init__(self, msg=None):
784+ if msg == None:
785+ msg = self.__doc__.strip()
786+ super(Error, self).__init__(msg)
787+
788+
789+class PathNotFound(Error):
790+ """
791+ Could not find the specified directory.
792+ """
793+
794+
795+class VersionError(Error):
796+ """
797+ There is a problem with the software version.
798+ """
799+
800+
801+class NoSuchAccomplishment(Error):
802+ """
803+ No such accomplishment has been registered.
804+ """
805+
806+
807+class AccomplishmentLocked(Error):
808+ """
809+ This accomplishment requires other things to be accomplished first.
810+ """
811
812=== added directory 'accomplishments/gui'
813=== renamed file 'trophyinfo/AboutTrophyinfoDialog.py' => 'accomplishments/gui/AboutTrophyinfoDialog.py'
814--- trophyinfo/AboutTrophyinfoDialog.py 2012-01-22 23:09:09 +0000
815+++ accomplishments/gui/AboutTrophyinfoDialog.py 2012-03-05 04:37:19 +0000
816@@ -5,20 +5,22 @@
817
818 import gettext
819 from gettext import gettext as _
820+import logging
821+
822+from accomplishments.gui.base.AboutDialog import AboutDialog
823+
824+
825 gettext.textdomain('trophyinfo')
826-
827-import logging
828 logger = logging.getLogger('trophyinfo')
829
830-from trophyinfo_lib.AboutDialog import AboutDialog
831
832-# See trophyinfo_lib.AboutDialog.py for more details about how this class works.
833+# See trophyinfo/gui/base/AboutDialog.py for more details about how this class
834+# works.
835 class AboutTrophyinfoDialog(AboutDialog):
836+
837 __gtype_name__ = "AboutTrophyinfoDialog"
838-
839+
840 def finish_initializing(self, builder): # pylint: disable=E1002
841 """Set up the about dialog"""
842 super(AboutTrophyinfoDialog, self).finish_initializing(builder)
843-
844 # Code for other initialization actions should be added here.
845-
846
847=== renamed file 'trophyinfo/PreferencesTrophyinfoDialog.py' => 'accomplishments/gui/PreferencesTrophyinfoDialog.py'
848--- trophyinfo/PreferencesTrophyinfoDialog.py 2012-01-22 23:09:09 +0000
849+++ accomplishments/gui/PreferencesTrophyinfoDialog.py 2012-03-05 04:37:19 +0000
850@@ -9,18 +9,22 @@
851 # data/glib-2.0/schemas/net.launchpad.trophyinfo.gschema.xml
852 # See http://developer.gnome.org/gio/stable/GSettings.html for more info.
853
854-from gi.repository import Gio # pylint: disable=E0611
855
856 import gettext
857 from gettext import gettext as _
858+import logging
859+
860+from gi.repository import Gio # pylint: disable=E0611
861+
862+from accomplishments.gui.base.PreferencesDialog import PreferencesDialog
863+
864+
865 gettext.textdomain('trophyinfo')
866-
867-import logging
868 logger = logging.getLogger('trophyinfo')
869
870-from trophyinfo_lib.PreferencesDialog import PreferencesDialog
871
872 class PreferencesTrophyinfoDialog(PreferencesDialog):
873+
874 __gtype_name__ = "PreferencesTrophyinfoDialog"
875
876 def finish_initializing(self, builder): # pylint: disable=E1002
877
878=== renamed file 'trophyinfo/TrophyinfoWindow.py' => 'accomplishments/gui/TrophyinfoWindow.py'
879--- trophyinfo/TrophyinfoWindow.py 2012-03-04 10:42:54 +0000
880+++ accomplishments/gui/TrophyinfoWindow.py 2012-03-05 04:37:19 +0000
881@@ -2,33 +2,31 @@
882 ### BEGIN LICENSE
883 # This file is in the public domain
884 ### END LICENSE
885-
886 import gettext
887 from gettext import gettext as _
888-gettext.textdomain('trophyinfo')
889-
890-from dbus.mainloop.glib import DBusGMainLoop
891-DBusGMainLoop(set_as_default=True)
892-
893-from gi.repository import Gtk, GdkPixbuf, WebKit # pylint: disable=E0611
894 import logging
895 import os
896 import sys
897 import webbrowser
898+
899 import dbus
900 import dbus.service
901-
902-sys.path.append("./daemon/")
903-
904+from dbus.mainloop.glib import DBusGMainLoop
905+
906+from gi.repository import Gtk, GdkPixbuf, WebKit # pylint: disable=E0611
907+
908+from accomplishments.daemon import dbusapi
909+from accomplishments.gui.base import Window
910+from accomplishments.gui.base.helpers import get_media_file
911+from accomplishments.gui.AboutTrophyinfoDialog import AboutTrophyinfoDialog
912+from accomplishments.gui.PreferencesTrophyinfoDialog import (
913+ PreferencesTrophyinfoDialog)
914+
915+
916+gettext.textdomain('trophyinfo')
917+DBusGMainLoop(set_as_default=True)
918 logger = logging.getLogger('trophyinfo')
919-import libaccomplishments
920-
921-
922-from trophyinfo_lib import Window
923-from trophyinfo.AboutTrophyinfoDialog import AboutTrophyinfoDialog
924-from trophyinfo.PreferencesTrophyinfoDialog import PreferencesTrophyinfoDialog
925-
926-from trophyinfo_lib.helpers import get_media_file
927+
928
929 COL_TITLE = 0
930 COL_PIXBUF = 1
931@@ -37,10 +35,12 @@
932 COL_APPLICATION = 4
933 COL_ACCOMPLISHMENT = 5
934
935+
936 # See trophyinfo_lib.Window.py for more details about how this class works
937 class TrophyinfoWindow(Window):
938+
939 __gtype_name__ = "TrophyinfoWindow"
940-
941+
942 def finish_initializing(self, builder): # pylint: disable=E1002
943 """Set up the main window"""
944 super(TrophyinfoWindow, self).finish_initializing(builder)
945@@ -52,7 +52,7 @@
946
947 self.accomdb = []
948
949- self.libaccom = libaccomplishments.Accomplishments()
950+ self.libaccom = dbusapi.Accomplishments()
951
952 self.tb_mytrophies = self.builder.get_object("tb_mytrophies")
953 self.tb_opportunities = self.builder.get_object("tb_opportunities")
954@@ -74,11 +74,11 @@
955 self.scrolledwindow = self.builder.get_object("scrolledwindow")
956 self.webkitview = self.builder.get_object("webkitview")
957 self.webkitbox = self.builder.get_object("webkitbox")
958-
959+
960 # make the toolbar black in Ubuntu
961 context = self.toolbar.get_style_context()
962 context.add_class(Gtk.STYLE_CLASS_PRIMARY_TOOLBAR)
963-
964+
965 self.trophystore = Gtk.ListStore(str, GdkPixbuf.Pixbuf, bool, bool, str, str) # title, icon accomplished, locked, app, accomplishment
966 self.trophystore.set_sort_column_id(COL_TITLE, Gtk.SortType.ASCENDING)
967 self.trophy_icon.set_model(self.trophystore)
968@@ -98,8 +98,7 @@
969 #scrolledwindow = self.builder.get_object("scrolledwindow")
970 self.webview = WebKit.WebView()
971 self.scrolledwindow.add(self.webview)
972-
973-
974+
975 #scrolledwindow.pack_start(self.webview)
976
977 self.webview.show()
978@@ -117,7 +116,7 @@
979 self.opp_combo_cat.add_attribute(self.cat_combo_renderer_text, "text", 1)
980
981 self.populate_opp_combos()
982- self.update_views(None)
983+ self.update_views(None)
984
985 self.has_u1 = self.libaccom.getConfigValue("config", "has_u1")
986 self.has_verif = self.libaccom.getConfigValue("config", "has_verif")
987@@ -137,7 +136,7 @@
988
989
990 dbus.mainloop.glib.DBusGMainLoop(set_as_default=True)
991-
992+
993 bus = dbus.SessionBus()
994 try:
995 object = bus.get_object("org.ubuntu.accomplishments","/org/ubuntu/accomplishments")
996@@ -165,13 +164,13 @@
997 self.spinner.start()
998 self.spinner.show()
999 self.statusbox.show()
1000-
1001+
1002 def scriptrunner_finish(self):
1003 self.statusbar.set_text("")
1004 self.spinner.stop()
1005 self.spinner.hide()
1006 self.statusbox.hide()
1007-
1008+
1009 def approve_u1_trophies(self):
1010
1011 self.u1_button.set_label("Register with Ubuntu One")
1012@@ -220,7 +219,7 @@
1013 def register_with_verif(self, widget):
1014 self.u1_button.set_label("Approve verified trophies")
1015
1016- if widget is not None:
1017+ if widget is not None:
1018 self.u1_button.disconnect(self.u1_button_sig)
1019
1020 self.u1_button_sig = self.u1_button.connect("clicked", self.create_trophy_share)
1021@@ -234,14 +233,14 @@
1022
1023 status_trophies = 0
1024 status_opps = 0
1025-
1026+
1027 show_locked = True
1028-
1029+
1030 if self.opp_showlocked.get_active():
1031 show_locked = True
1032 else:
1033 show_locked = False
1034-
1035+
1036 trophymodel = self.trophy_icon.get_model()
1037 oppmodel = self.opp_icon.get_model()
1038
1039@@ -262,15 +261,15 @@
1040
1041 if cattree_iter == None:
1042 cat = ""
1043- catname = ""
1044+ catname = ""
1045 else:
1046 cat, catname = catmodel[cattree_iter][:2]
1047
1048 # update opportunities
1049- for acc in self.accomdb:
1050+ for acc in self.accomdb:
1051 icon = None
1052 icon = GdkPixbuf.Pixbuf.new_from_file_at_size(str(acc["iconpath"]), 120, 120)
1053-
1054+
1055 if str(acc["accomplished"]) == '1':
1056 trophymodel.append([acc["title"], icon, bool(acc["accomplished"]), acc["locked"], acc["application"], acc["accomplishment"]])
1057 status_trophies = status_trophies + 1
1058@@ -301,13 +300,13 @@
1059 self._load_accomplishments()
1060
1061 temp = []
1062-
1063+
1064 for i in self.accomdb:
1065 temp.append({i["application"] : i["application-human"] })
1066
1067- # uniqify the values
1068+ # uniqify the values
1069 result = [dict(tupleized) for tupleized in set(tuple(item.items()) for item in temp)]
1070-
1071+
1072 # set up app
1073 self.opp_app_store.append(["", "All"])
1074
1075@@ -318,7 +317,7 @@
1076
1077 self.opp_combo_app.set_active(0)
1078 self.opp_combo_app.show()
1079-
1080+
1081 # set up cat
1082
1083 self.opp_combo_cat.set_model(self.opp_cat_store)
1084@@ -371,7 +370,7 @@
1085 self.update_views(None)
1086 self.notebook.set_current_page(2)
1087
1088-
1089+
1090 def get_icon(self, name):
1091 theme = Gtk.IconTheme.get_default()
1092 return theme.load_icon(name, 48, 0)
1093@@ -379,14 +378,14 @@
1094
1095 def check_for_extra_info_required(self):
1096 infoneeded = self.libaccom.getAllExtraInformationRequired()
1097-
1098+
1099 if len(infoneeded) == 0:
1100 self.notebook.set_current_page(0)
1101 else:
1102 self.gather_auth_info(infoneeded)
1103
1104 def gather_auth_info(self, infoneeded):
1105- self.additional_notebook.set_current_page(0)
1106+ self.additional_notebook.set_current_page(0)
1107
1108 table = Gtk.Table(len(infoneeded), 2, False)
1109 self.auth_viewport.add(table)
1110@@ -399,7 +398,7 @@
1111 label = Gtk.Label(i["label"])
1112 table.attach(label, 0, 1, ii, (ii+1))
1113 entry = Gtk.Entry()
1114- table.attach(entry, 1, 2,ii, (ii+1))
1115+ table.attach(entry, 1, 2,ii, (ii+1))
1116 ii = ii + 1
1117 d = {"application" : i["application"], "needs-information" : i["needs-information"], "entry" : entry}
1118 self.auth_widget_lookup.append(d)
1119@@ -412,7 +411,7 @@
1120 for i in self.auth_widget_lookup:
1121 self.libaccom.createExtraInformationFile(i["application"], i["needs-information"], i["entry"].get_text())
1122 self.additional_expander.set_visible(False)
1123-
1124+
1125 self.notebook.set_current_page(2)
1126
1127 def _load_accomplishments(self):
1128@@ -446,8 +445,8 @@
1129 html = None
1130
1131 title = a[0]["title"]
1132-
1133- application = a[0]["application"]
1134+
1135+ application = a[0]["application"]
1136
1137 for accom in self.accomdb:
1138 if title in accom["title"]:
1139@@ -465,7 +464,7 @@
1140 html = html + "<td><img src='" + str(iconpath) + "' height='100'></td>"
1141
1142 html = html + "<td><strong>Trophy Information:</strong><br/><hr />"
1143-
1144+
1145 if "description" in a[0]:
1146 description = a[0]["description"]
1147 html = html + description
1148@@ -535,4 +534,3 @@
1149 self.notebook.set_current_page(0)
1150 self.webview.load_html_string(html, "file:///")
1151 self.webview.show()
1152-
1153
1154=== added file 'accomplishments/gui/__init__.py'
1155=== renamed directory 'trophyinfo_lib' => 'accomplishments/gui/base'
1156=== modified file 'accomplishments/gui/base/AboutDialog.py'
1157--- trophyinfo_lib/AboutDialog.py 2012-01-22 23:09:09 +0000
1158+++ accomplishments/gui/base/AboutDialog.py 2012-03-05 04:37:19 +0000
1159@@ -2,18 +2,19 @@
1160 ### BEGIN LICENSE
1161 # This file is in the public domain
1162 ### END LICENSE
1163-
1164 from gi.repository import Gtk # pylint: disable=E0611
1165
1166 from . helpers import get_builder
1167
1168+
1169 class AboutDialog(Gtk.AboutDialog):
1170+
1171 __gtype_name__ = "AboutDialog"
1172
1173 def __new__(cls):
1174- """Special static method that's automatically called by Python when
1175+ """Special static method that's automatically called by Python when
1176 constructing a new instance of this class.
1177-
1178+
1179 Returns a fully instantiated AboutDialog object.
1180 """
1181 builder = get_builder('AboutTrophyinfoDialog')
1182@@ -28,10 +29,9 @@
1183 and creating a AboutDialog object with it in order
1184 to finish initializing the start of the new AboutTrophyinfoDialog
1185 instance.
1186-
1187+
1188 Put your initialization code in here and leave __init__ undefined.
1189 """
1190 # Get a reference to the builder and set up the signals.
1191 self.builder = builder
1192 self.ui = builder.get_ui(self)
1193-
1194
1195=== modified file 'accomplishments/gui/base/Builder.py'
1196--- trophyinfo_lib/Builder.py 2012-01-22 23:09:09 +0000
1197+++ accomplishments/gui/base/Builder.py 2012-03-05 04:37:19 +0000
1198@@ -2,18 +2,18 @@
1199 ### BEGIN LICENSE
1200 # This file is in the public domain
1201 ### END LICENSE
1202-
1203 '''Enhances builder connections, provides object to access glade objects'''
1204-
1205-from gi.repository import GObject, Gtk # pylint: disable=E0611
1206-
1207+import functools
1208 import inspect
1209-import functools
1210 import logging
1211-logger = logging.getLogger('trophyinfo_lib')
1212-
1213 from xml.etree.cElementTree import ElementTree
1214
1215+from gi.repository import GObject, Gtk # pylint: disable=E0611
1216+
1217+
1218+logger = logging.getLogger('trophyinfo')
1219+
1220+
1221 # this module is big so uses some conventional prefixes and postfixes
1222 # *s list, except self.widgets is a dictionary
1223 # *_dict dictionary
1224@@ -162,7 +162,7 @@
1225 cannot_message = """cannot bind ui.%s, name already exists
1226 consider using a pythonic name instead of design name '%s'"""
1227 consider_message = """consider using a pythonic name instead of design name '%s'"""
1228-
1229+
1230 for (widget_name, widget) in widget_dict.items():
1231 pyname = make_pyname(widget_name)
1232 if pyname != widget_name:
1233@@ -195,7 +195,7 @@
1234 return pyname
1235
1236
1237-# Until bug https://bugzilla.gnome.org/show_bug.cgi?id=652127 is fixed, we
1238+# Until bug https://bugzilla.gnome.org/show_bug.cgi?id=652127 is fixed, we
1239 # need to reimplement inspect.getmembers. GObject introspection doesn't
1240 # play nice with it.
1241 def getmembers(obj, check):
1242
1243=== modified file 'accomplishments/gui/base/PreferencesDialog.py'
1244--- trophyinfo_lib/PreferencesDialog.py 2012-01-22 23:09:09 +0000
1245+++ accomplishments/gui/base/PreferencesDialog.py 2012-03-05 04:37:19 +0000
1246@@ -2,23 +2,25 @@
1247 ### BEGIN LICENSE
1248 # This file is in the public domain
1249 ### END LICENSE
1250-
1251-"""this dialog adjusts values in gsettings
1252-"""
1253+"""this dialog adjusts values in gsettings"""
1254+import logging
1255
1256 from gi.repository import Gtk # pylint: disable=E0611
1257-import logging
1258-logger = logging.getLogger('trophyinfo_lib')
1259
1260 from . helpers import get_builder, show_uri, get_help_uri
1261
1262+
1263+logger = logging.getLogger('trophyinfo')
1264+
1265+
1266 class PreferencesDialog(Gtk.Dialog):
1267+
1268 __gtype_name__ = "PreferencesDialog"
1269
1270 def __new__(cls):
1271- """Special static method that's automatically called by Python when
1272+ """Special static method that's automatically called by Python when
1273 constructing a new instance of this class.
1274-
1275+
1276 Returns a fully instantiated PreferencesDialog object.
1277 """
1278 builder = get_builder('PreferencesTrophyinfoDialog')
1279@@ -33,7 +35,7 @@
1280 and creating a PreferencesDialog object with it in order to
1281 finish initializing the start of the new PerferencesTrophyinfoDialog
1282 instance.
1283-
1284+
1285 Put your initialization code in here and leave __init__ undefined.
1286 """
1287
1288@@ -48,4 +50,3 @@
1289
1290 def on_btn_help_clicked(self, widget, data=None):
1291 show_uri(self, "ghelp:%s" % get_help_uri('preferences'))
1292-
1293
1294=== modified file 'accomplishments/gui/base/Window.py'
1295--- trophyinfo_lib/Window.py 2012-01-22 23:09:09 +0000
1296+++ accomplishments/gui/base/Window.py 2012-03-05 04:37:19 +0000
1297@@ -2,19 +2,23 @@
1298 ### BEGIN LICENSE
1299 # This file is in the public domain
1300 ### END LICENSE
1301+import logging
1302
1303 from gi.repository import Gio, Gtk # pylint: disable=E0611
1304-import logging
1305-logger = logging.getLogger('trophyinfo_lib')
1306
1307 from . helpers import get_builder, show_uri, get_help_uri
1308
1309+
1310+logger = logging.getLogger('trophyinfo')
1311+
1312+
1313 # This class is meant to be subclassed by TrophyinfoWindow. It provides
1314 # common functions and some boilerplate.
1315 class Window(Gtk.Window):
1316+
1317 __gtype_name__ = "Window"
1318
1319- # To construct a new instance of this method, the following notable
1320+ # To construct a new instance of this method, the following notable
1321 # methods are called in this order:
1322 # __new__(cls)
1323 # __init__(self)
1324@@ -23,11 +27,11 @@
1325 #
1326 # For this reason, it's recommended you leave __init__ empty and put
1327 # your initialization code in finish_initializing
1328-
1329+
1330 def __new__(cls):
1331- """Special static method that's automatically called by Python when
1332+ """Special static method that's automatically called by Python when
1333 constructing a new instance of this class.
1334-
1335+
1336 Returns a fully instantiated BaseTrophyinfoWindow object.
1337 """
1338 builder = get_builder('TrophyinfoWindow')
1339@@ -53,9 +57,11 @@
1340 self.settings.connect('changed', self.on_preferences_changed)
1341
1342 # Optional Launchpad integration
1343- # This shouldn't crash if not found as it is simply used for bug reporting.
1344- # See https://wiki.ubuntu.com/UbuntuDevelopment/Internationalisation/Coding
1345- # for more information about Launchpad integration.
1346+ # This shouldn't crash if not found as it is simply used for bug
1347+ # reporting. See the following for more information about Launchpad
1348+ # integration:
1349+ #
1350+ # https://wiki.ubuntu.com/UbuntuDevelopment/Internationalisation/Coding
1351 try:
1352 from gi.repository import LaunchpadIntegration # pylint: disable=E0611
1353 LaunchpadIntegration.add_items(self.ui.helpMenu, 1, True, True)
1354@@ -69,7 +75,7 @@
1355 # http://owaislone.org/quickly-add-indicator/
1356 # https://wiki.ubuntu.com/DesktopExperienceTeam/ApplicationIndicators
1357 try:
1358- from trophyinfo import indicator
1359+ from accomplishments import indicator
1360 # self is passed so methods of this class can be called from indicator.py
1361 # Comment this next line out to disable appindicator
1362 self.indicator = indicator.new_application_indicator(self)
1363@@ -118,10 +124,9 @@
1364
1365 def on_preferences_dialog_destroyed(self, widget, data=None):
1366 '''only affects gui
1367-
1368+
1369 logically there is no difference between the user closing,
1370 minimising or ignoring the preferences dialog'''
1371 logger.debug('on_preferences_dialog_destroyed')
1372 # to determine whether to create or present preferences_dialog
1373 self.preferences_dialog = None
1374-
1375
1376=== modified file 'accomplishments/gui/base/__init__.py'
1377--- trophyinfo_lib/__init__.py 2012-01-22 23:09:09 +0000
1378+++ accomplishments/gui/base/__init__.py 2012-03-05 04:37:19 +0000
1379@@ -3,10 +3,9 @@
1380 # This file is in the public domain
1381 ### END LICENSE
1382
1383-'''facade - makes trophyinfo_lib package easy to refactor
1384+'''facade - makes the accomplishments.gui.base subpackage easy to refactor
1385
1386 while keeping its api constant'''
1387-from . helpers import set_up_logging
1388 from . Window import Window
1389-from . trophyinfoconfig import get_version
1390
1391+from accomplishments.util import get_version, set_up_logging
1392
1393=== modified file 'accomplishments/gui/base/helpers.py'
1394--- trophyinfo_lib/helpers.py 2012-01-22 23:09:09 +0000
1395+++ accomplishments/gui/base/helpers.py 2012-03-05 04:37:19 +0000
1396@@ -2,22 +2,23 @@
1397 ### BEGIN LICENSE
1398 # This file is in the public domain
1399 ### END LICENSE
1400-
1401 """Helpers for an Ubuntu application."""
1402-import logging
1403 import os
1404-
1405-from . trophyinfoconfig import get_data_file
1406-from . Builder import Builder
1407-
1408 import gettext
1409 from gettext import gettext as _
1410+
1411+from accomplishments.util import get_data_file
1412+
1413+from . Builder import Builder
1414+
1415+
1416 gettext.textdomain('trophyinfo')
1417
1418+
1419 def get_builder(builder_file_name):
1420- """Return a fully-instantiated Gtk.Builder instance from specified ui
1421+ """Return a fully-instantiated Gtk.Builder instance from specified ui
1422 file
1423-
1424+
1425 :param builder_file_name: The name of the builder file, without extension.
1426 Assumed to be in the 'ui' directory under the data path.
1427 """
1428@@ -40,34 +41,6 @@
1429
1430 return "file:///"+media_filename
1431
1432-class NullHandler(logging.Handler):
1433- def emit(self, record):
1434- pass
1435-
1436-def set_up_logging(opts):
1437- # add a handler to prevent basicConfig
1438- root = logging.getLogger()
1439- null_handler = NullHandler()
1440- root.addHandler(null_handler)
1441-
1442- formatter = logging.Formatter("%(levelname)s:%(name)s: %(funcName)s() '%(message)s'")
1443-
1444- logger = logging.getLogger('trophyinfo')
1445- logger_sh = logging.StreamHandler()
1446- logger_sh.setFormatter(formatter)
1447- logger.addHandler(logger_sh)
1448-
1449- lib_logger = logging.getLogger('trophyinfo_lib')
1450- lib_logger_sh = logging.StreamHandler()
1451- lib_logger_sh.setFormatter(formatter)
1452- lib_logger.addHandler(lib_logger_sh)
1453-
1454- # Set the logging level to show debug messages.
1455- if opts.verbose:
1456- logger.setLevel(logging.DEBUG)
1457- logger.debug('logging enabled')
1458- if opts.verbose > 1:
1459- lib_logger.setLevel(logging.DEBUG)
1460
1461 def get_help_uri(page=None):
1462 # help_uri from source tree - default language
1463@@ -89,6 +62,7 @@
1464 screen = parent.get_screen()
1465 Gtk.show_uri(screen, link, Gtk.get_current_event_time())
1466
1467+
1468 def alias(alternative_function_name):
1469 '''see http://www.drdobbs.com/web-development/184406073#l9'''
1470 def decorator(function):
1471
1472=== renamed file 'trophyinfo/__init__.py' => 'accomplishments/main.py'
1473--- trophyinfo/__init__.py 2012-02-16 01:45:30 +0000
1474+++ accomplishments/main.py 2012-03-05 04:37:19 +0000
1475@@ -2,37 +2,16 @@
1476 ### BEGIN LICENSE
1477 # This file is in the public domain
1478 ### END LICENSE
1479-
1480-import optparse
1481-
1482-import gettext
1483-from gettext import gettext as _
1484-gettext.textdomain('trophyinfo')
1485-
1486 from gi.repository import Gtk # pylint: disable=E0611
1487
1488-from trophyinfo import TrophyinfoWindow
1489-
1490-from trophyinfo_lib import set_up_logging, get_version
1491-
1492-def parse_options():
1493- """Support for command line options"""
1494- parser = optparse.OptionParser(version="%%prog %s" % get_version())
1495- parser.add_option(
1496- "-v", "--verbose", action="count", dest="verbose",
1497- help=_("Show debug messages (-vv debugs trophyinfo_lib also)"))
1498- parser.add_option(
1499- "-c", "--clear-trophies", action="count", dest="clear",
1500- help=_("Clear your trophies collection"))
1501- (options, args) = parser.parse_args()
1502-
1503- set_up_logging(options)
1504+from accomplishments import util
1505+from accomplishments.gui import TrophyinfoWindow
1506+
1507
1508 def main():
1509- 'constructor for your class instances'
1510- parse_options()
1511-
1512- # Run the application.
1513+ options = util.parse_options()
1514+ util.set_up_logging(options)
1515+ # Run the application.
1516 window = TrophyinfoWindow.TrophyinfoWindow()
1517 window.show()
1518 Gtk.main()
1519
1520=== added directory 'accomplishments/util'
1521=== added file 'accomplishments/util/__init__.py'
1522--- accomplishments/util/__init__.py 1970-01-01 00:00:00 +0000
1523+++ accomplishments/util/__init__.py 2012-03-05 04:37:19 +0000
1524@@ -0,0 +1,88 @@
1525+import logging
1526+import optparse
1527+import os
1528+
1529+import gettext
1530+from gettext import gettext as _
1531+
1532+import accomplishments
1533+from accomplishments import config
1534+from accomplishments import exceptions
1535+
1536+
1537+gettext.textdomain('trophyinfo')
1538+
1539+
1540+def get_version():
1541+ return config.__version__
1542+
1543+
1544+class NullHandler(logging.Handler):
1545+ """
1546+ """
1547+ def emit(self, record):
1548+ pass
1549+
1550+
1551+def set_up_logging(opts):
1552+ # add a handler to prevent basicConfig
1553+ root = logging.getLogger()
1554+ null_handler = NullHandler()
1555+ root.addHandler(null_handler)
1556+
1557+ formatter = logging.Formatter(
1558+ "%(levelname)s:%(name)s: %(funcName)s() '%(message)s'")
1559+
1560+ logger = logging.getLogger('trophyinfo')
1561+ logger_sh = logging.StreamHandler()
1562+ logger_sh.setFormatter(formatter)
1563+ logger.addHandler(logger_sh)
1564+
1565+ # Set the logging level to show debug messages.
1566+ if opts.verbose:
1567+ logger.setLevel(logging.DEBUG)
1568+ logger.debug('logging enabled')
1569+ if opts.verbose > 1:
1570+ lib_logger.setLevel(logging.DEBUG)
1571+
1572+
1573+def get_data_path():
1574+ """Retrieve trophyinfo data path
1575+
1576+ This path is by default <trophyinfo_lib_path>/../data/ in trunk
1577+ and /usr/share/trophyinfo in an installed version but this path
1578+ is specified at installation time.
1579+ """
1580+
1581+ # Get pathname absolute or relative.
1582+ path = os.path.join(
1583+ os.path.dirname(accomplishments.__path__[0]),
1584+ config.__trophyinfo_data_directory__)
1585+ abs_data_path = os.path.abspath(path)
1586+ if not os.path.exists(abs_data_path):
1587+ msg = "Could not find the project data directory."
1588+ raise exceptions.PathNotFound(msg)
1589+ return abs_data_path
1590+
1591+
1592+def get_data_file(*path_segments):
1593+ """Get the full path to a data file.
1594+
1595+ Returns the path to a file underneath the data directory (as defined by
1596+ `get_data_path`). Equivalent to os.path.join(get_data_path(),
1597+ *path_segments).
1598+ """
1599+ return os.path.join(get_data_path(), *path_segments)
1600+
1601+
1602+def parse_options():
1603+ """Support for command line options"""
1604+ parser = optparse.OptionParser(version="%%prog %s" % get_version())
1605+ parser.add_option(
1606+ "-v", "--verbose", action="count", dest="verbose",
1607+ help=_("Show debug messages (-vv debugs trophyinfo_lib also)"))
1608+ parser.add_option(
1609+ "-c", "--clear-trophies", action="count", dest="clear",
1610+ help=_("Clear your trophies collection"))
1611+ (options, args) = parser.parse_args()
1612+ return options
1613
1614=== added file 'accomplishments/util/dist.py'
1615--- accomplishments/util/dist.py 1970-01-01 00:00:00 +0000
1616+++ accomplishments/util/dist.py 2012-03-05 04:37:19 +0000
1617@@ -0,0 +1,75 @@
1618+import os
1619+import sys
1620+
1621+try:
1622+ import DistUtilsExtra.auto
1623+except ImportError:
1624+ DistUtilsExtra = None
1625+
1626+from accomplishments import exceptions
1627+
1628+
1629+if not DistUtilsExtra:
1630+ msg = ('To build trophyinfo you need '
1631+ 'https://launchpad.net/python-distutils-extra')
1632+ print >> sys.stderr, msg
1633+ sys.exit(1)
1634+elif DistUtilsExtra.auto.__version__ < '2.18':
1635+ raise exceptions.VersionError('needs DistUtilsExtra.auto >= 2.18')
1636+
1637+
1638+def update_config(values = {}):
1639+ oldvalues = {}
1640+ try:
1641+ fin = file('trophyinfo_lib/trophyinfoconfig.py', 'r')
1642+ fout = file(fin.name + '.new', 'w')
1643+
1644+ for line in fin:
1645+ fields = line.split(' = ') # Separate variable from value
1646+ if fields[0] in values:
1647+ oldvalues[fields[0]] = fields[1].strip()
1648+ line = "%s = %s\n" % (fields[0], values[fields[0]])
1649+ fout.write(line)
1650+
1651+ fout.flush()
1652+ fout.close()
1653+ fin.close()
1654+ os.rename(fout.name, fin.name)
1655+ except (OSError, IOError), e:
1656+ print ("ERROR: Can't find trophyinfo_lib/trophyinfoconfig.py")
1657+ sys.exit(1)
1658+ return oldvalues
1659+
1660+
1661+def update_desktop_file(datadir):
1662+ try:
1663+ fin = file('trophyinfo.desktop.in', 'r')
1664+ fout = file(fin.name + '.new', 'w')
1665+
1666+ for line in fin:
1667+ if 'Icon=' in line:
1668+ line = "Icon=%s\n" % (datadir + 'media/trophyinfo.svg')
1669+ fout.write(line)
1670+ fout.flush()
1671+ fout.close()
1672+ fin.close()
1673+ os.rename(fout.name, fin.name)
1674+ except (OSError, IOError), e:
1675+ print ("ERROR: Can't find trophyinfo.desktop.in")
1676+ sys.exit(1)
1677+
1678+
1679+class InstallAndUpdateDataDirectory(DistUtilsExtra.auto.install_auto):
1680+
1681+ def run(self):
1682+ values = {
1683+ '__trophyinfo_data_directory__': "'%s'" % (
1684+ self.prefix + '/share/trophyinfo/'),
1685+ '__version__': "'%s'" % self.distribution.get_version()}
1686+ previous_values = update_config(values)
1687+ update_desktop_file(self.prefix + '/share/trophyinfo/')
1688+ DistUtilsExtra.auto.install_auto.run(self)
1689+ update_config(previous_values)
1690+
1691+
1692+setup = DistUtilsExtra.auto.setup
1693
1694=== renamed file 'daemon/rundaemon.sh' => 'bin/rundaemon.sh'
1695--- daemon/rundaemon.sh 2012-02-22 05:33:30 +0000
1696+++ bin/rundaemon.sh 2012-03-05 04:37:19 +0000
1697@@ -4,12 +4,12 @@
1698 export PYTHONPATH=$PYTHONPATH:.
1699
1700 echo Importing the validation key...
1701-gpg --import validation-key.pub
1702+gpg --import ./data/daemon/validation-key.pub
1703
1704 echo Starting the accomplishments daemon...
1705 echo "(this would be done by D-Bus activation in the real world)"
1706
1707-python ./libaccomplishments-daemon/daemon.py
1708+python ./accomplishments/daemon/app.py
1709 DAEMON=$!
1710
1711
1712
1713=== modified file 'bin/trophyinfo'
1714--- bin/trophyinfo 2012-01-22 23:09:09 +0000
1715+++ bin/trophyinfo 2012-03-05 04:37:19 +0000
1716@@ -3,14 +3,16 @@
1717 ### BEGIN LICENSE
1718 # This file is in the public domain
1719 ### END LICENSE
1720-
1721 import sys
1722 import os
1723
1724 import gettext
1725 from gettext import gettext as _
1726+
1727+from accomplishments.main import main
1728+
1729+
1730 gettext.textdomain('trophyinfo')
1731-
1732 # Add project root directory (enable symlink and trunk execution)
1733 PROJECT_ROOT_DIRECTORY = os.path.abspath(
1734 os.path.dirname(os.path.dirname(os.path.realpath(sys.argv[0]))))
1735@@ -22,12 +24,14 @@
1736 opt_path = path.replace('/usr', '/opt/extras.ubuntu.com/trophyinfo')
1737 python_path.insert(0, opt_path)
1738 sys.path.insert(0, opt_path)
1739-if (os.path.exists(os.path.join(PROJECT_ROOT_DIRECTORY, 'trophyinfo'))
1740+if (os.path.exists(os.path.join(PROJECT_ROOT_DIRECTORY, 'accomplishments'))
1741 and PROJECT_ROOT_DIRECTORY not in sys.path):
1742 python_path.insert(0, PROJECT_ROOT_DIRECTORY)
1743 sys.path.insert(0, PROJECT_ROOT_DIRECTORY)
1744 if python_path:
1745- os.putenv('PYTHONPATH', "%s:%s" % (os.getenv('PYTHONPATH', ''), ':'.join(python_path))) # for subprocesses
1746+ os.putenv(
1747+ 'PYTHONPATH',
1748+ "%s:%s" % (os.getenv('PYTHONPATH', ''),
1749+ ':'.join(python_path))) # for subprocesses
1750
1751-import trophyinfo
1752-trophyinfo.main()
1753+main()
1754
1755=== removed directory 'daemon/libaccomplishments'
1756=== removed directory 'daemon/libaccomplishments-daemon'
1757=== removed file 'daemon/libaccomplishments-daemon/trophy-accomplished.svg'
1758--- daemon/libaccomplishments-daemon/trophy-accomplished.svg 2012-01-28 20:03:46 +0000
1759+++ daemon/libaccomplishments-daemon/trophy-accomplished.svg 1970-01-01 00:00:00 +0000
1760@@ -1,854 +0,0 @@
1761-<?xml version="1.0" encoding="UTF-8" standalone="no"?>
1762-<!-- Created with Inkscape (http://www.inkscape.org/) -->
1763-
1764-<svg
1765- xmlns:dc="http://purl.org/dc/elements/1.1/"
1766- xmlns:cc="http://creativecommons.org/ns#"
1767- xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
1768- xmlns:svg="http://www.w3.org/2000/svg"
1769- xmlns="http://www.w3.org/2000/svg"
1770- xmlns:xlink="http://www.w3.org/1999/xlink"
1771- xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
1772- xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
1773- width="200"
1774- height="300"
1775- id="svg2"
1776- version="1.1"
1777- inkscape:version="0.48.2 r9819"
1778- sodipodi:docname="trophy-accomplished.svg">
1779- <title
1780- id="title3265">Trophy</title>
1781- <defs
1782- id="defs4">
1783- <linearGradient
1784- id="linearGradient4099"
1785- inkscape:collect="always">
1786- <stop
1787- id="stop4101"
1788- offset="0"
1789- style="stop-color:#ffc022;stop-opacity:1" />
1790- <stop
1791- id="stop4103"
1792- offset="1"
1793- style="stop-color:#ffffff;stop-opacity:0;" />
1794- </linearGradient>
1795- <linearGradient
1796- inkscape:collect="always"
1797- id="linearGradient4088">
1798- <stop
1799- style="stop-color:#ffffff;stop-opacity:1;"
1800- offset="0"
1801- id="stop4090" />
1802- <stop
1803- style="stop-color:#ffffff;stop-opacity:0;"
1804- offset="1"
1805- id="stop4092" />
1806- </linearGradient>
1807- <linearGradient
1808- inkscape:collect="always"
1809- id="linearGradient4070">
1810- <stop
1811- style="stop-color:#f0be63;stop-opacity:1;"
1812- offset="0"
1813- id="stop4072" />
1814- <stop
1815- style="stop-color:#b88100;stop-opacity:1"
1816- offset="1"
1817- id="stop4074" />
1818- </linearGradient>
1819- <linearGradient
1820- inkscape:collect="always"
1821- id="linearGradient3277">
1822- <stop
1823- style="stop-color:#804d00;stop-opacity:1;"
1824- offset="0"
1825- id="stop3279" />
1826- <stop
1827- style="stop-color:#b98304;stop-opacity:1"
1828- offset="1"
1829- id="stop3281" />
1830- </linearGradient>
1831- <linearGradient
1832- inkscape:collect="always"
1833- id="linearGradient3267">
1834- <stop
1835- style="stop-color:#692017;stop-opacity:1;"
1836- offset="0"
1837- id="stop3269" />
1838- <stop
1839- style="stop-color:#46150f;stop-opacity:1"
1840- offset="1"
1841- id="stop3271" />
1842- </linearGradient>
1843- <linearGradient
1844- inkscape:collect="always"
1845- id="linearGradient3961">
1846- <stop
1847- style="stop-color:#804d00;stop-opacity:1;"
1848- offset="0"
1849- id="stop3963" />
1850- <stop
1851- style="stop-color:#b88100;stop-opacity:1"
1852- offset="1"
1853- id="stop3965" />
1854- </linearGradient>
1855- <linearGradient
1856- inkscape:collect="always"
1857- id="linearGradient3953">
1858- <stop
1859- style="stop-color:#804d00;stop-opacity:1;"
1860- offset="0"
1861- id="stop3955" />
1862- <stop
1863- style="stop-color:#ffc022;stop-opacity:1"
1864- offset="1"
1865- id="stop3957" />
1866- </linearGradient>
1867- <linearGradient
1868- inkscape:collect="always"
1869- id="linearGradient3945">
1870- <stop
1871- style="stop-color:#804d00;stop-opacity:1;"
1872- offset="0"
1873- id="stop3947" />
1874- <stop
1875- style="stop-color:#ffc022;stop-opacity:1"
1876- offset="1"
1877- id="stop3949" />
1878- </linearGradient>
1879- <linearGradient
1880- inkscape:collect="always"
1881- id="linearGradient3918">
1882- <stop
1883- style="stop-color:#fcca77;stop-opacity:1;"
1884- offset="0"
1885- id="stop3920" />
1886- <stop
1887- style="stop-color:#fcca77;stop-opacity:0;"
1888- offset="1"
1889- id="stop3922" />
1890- </linearGradient>
1891- <linearGradient
1892- inkscape:collect="always"
1893- id="linearGradient3908">
1894- <stop
1895- style="stop-color:#f6c374;stop-opacity:1;"
1896- offset="0"
1897- id="stop3910" />
1898- <stop
1899- style="stop-color:#b88100;stop-opacity:1"
1900- offset="1"
1901- id="stop3912" />
1902- </linearGradient>
1903- <linearGradient
1904- inkscape:collect="always"
1905- id="linearGradient3896">
1906- <stop
1907- style="stop-color:#e7bc77;stop-opacity:1;"
1908- offset="0"
1909- id="stop3898" />
1910- <stop
1911- style="stop-color:#e7bc77;stop-opacity:0;"
1912- offset="1"
1913- id="stop3900" />
1914- </linearGradient>
1915- <linearGradient
1916- inkscape:collect="always"
1917- id="linearGradient3886">
1918- <stop
1919- style="stop-color:#fed78a;stop-opacity:1;"
1920- offset="0"
1921- id="stop3888" />
1922- <stop
1923- style="stop-color:#fed78a;stop-opacity:0;"
1924- offset="1"
1925- id="stop3890" />
1926- </linearGradient>
1927- <linearGradient
1928- inkscape:collect="always"
1929- id="linearGradient3872">
1930- <stop
1931- style="stop-color:#dcac62;stop-opacity:1;"
1932- offset="0"
1933- id="stop3874" />
1934- <stop
1935- style="stop-color:#b88100;stop-opacity:1"
1936- offset="1"
1937- id="stop3876" />
1938- </linearGradient>
1939- <linearGradient
1940- inkscape:collect="always"
1941- id="linearGradient3854">
1942- <stop
1943- style="stop-color:#b88100;stop-opacity:1;"
1944- offset="0"
1945- id="stop3856" />
1946- <stop
1947- style="stop-color:#fecd7b;stop-opacity:1"
1948- offset="1"
1949- id="stop3858" />
1950- </linearGradient>
1951- <linearGradient
1952- inkscape:collect="always"
1953- id="linearGradient3842">
1954- <stop
1955- style="stop-color:#804d00;stop-opacity:1;"
1956- offset="0"
1957- id="stop3844" />
1958- <stop
1959- style="stop-color:#804d00;stop-opacity:0;"
1960- offset="1"
1961- id="stop3846" />
1962- </linearGradient>
1963- <linearGradient
1964- inkscape:collect="always"
1965- xlink:href="#linearGradient3842"
1966- id="linearGradient3848"
1967- x1="-216.17264"
1968- y1="218.98633"
1969- x2="-217.1828"
1970- y2="249.29091"
1971- gradientUnits="userSpaceOnUse"
1972- gradientTransform="matrix(0.5,0,0,0.5,-209.64022,192.29962)" />
1973- <linearGradient
1974- inkscape:collect="always"
1975- xlink:href="#linearGradient3854"
1976- id="linearGradient3860"
1977- x1="-211.12189"
1978- y1="245.25031"
1979- x2="-201.02036"
1980- y2="389.70212"
1981- gradientUnits="userSpaceOnUse"
1982- gradientTransform="matrix(0.5,0,0,0.5,-209.64022,192.29962)" />
1983- <filter
1984- inkscape:collect="always"
1985- id="filter3862"
1986- x="-0.13795282"
1987- width="1.2759056"
1988- y="-0.051161319"
1989- height="1.1023226"
1990- color-interpolation-filters="sRGB">
1991- <feGaussianBlur
1992- inkscape:collect="always"
1993- stdDeviation="3.2515796"
1994- id="feGaussianBlur3864" />
1995- </filter>
1996- <filter
1997- inkscape:collect="always"
1998- id="filter3866"
1999- x="-0.12734108"
2000- width="1.2546821"
2001- y="-0.047225833"
2002- height="1.0944517"
2003- color-interpolation-filters="sRGB">
2004- <feGaussianBlur
2005- inkscape:collect="always"
2006- stdDeviation="3.0014581"
2007- id="feGaussianBlur3868" />
2008- </filter>
2009- <radialGradient
2010- inkscape:collect="always"
2011- xlink:href="#linearGradient3872"
2012- id="radialGradient3878"
2013- cx="-197.15332"
2014- cy="316.23712"
2015- fx="-197.15332"
2016- fy="316.23712"
2017- r="42.421329"
2018- gradientTransform="matrix(-1.1182277,0.0551342,-0.09068266,-2.5015192,-384.72423,1069.5515)"
2019- gradientUnits="userSpaceOnUse" />
2020- <filter
2021- inkscape:collect="always"
2022- id="filter3880"
2023- color-interpolation-filters="sRGB">
2024- <feGaussianBlur
2025- inkscape:collect="always"
2026- stdDeviation="2.7321539"
2027- id="feGaussianBlur3882" />
2028- </filter>
2029- <radialGradient
2030- inkscape:collect="always"
2031- xlink:href="#linearGradient3886"
2032- id="radialGradient3892"
2033- cx="-199.00005"
2034- cy="379.85995"
2035- fx="-199.00005"
2036- fy="379.85995"
2037- r="38.890873"
2038- gradientTransform="matrix(0.15584403,-1.7142858,0.9570922,0.08700819,-531.54808,4.3965634)"
2039- gradientUnits="userSpaceOnUse" />
2040- <radialGradient
2041- inkscape:collect="always"
2042- xlink:href="#linearGradient3896"
2043- id="radialGradient3902"
2044- cx="-273.75134"
2045- cy="320.53235"
2046- fx="-273.75134"
2047- fy="320.53235"
2048- r="49.711224"
2049- gradientTransform="matrix(-0.48768998,-1.5849921,0.8254465,-0.2539842,-744.60397,11.938684)"
2050- gradientUnits="userSpaceOnUse" />
2051- <radialGradient
2052- inkscape:collect="always"
2053- xlink:href="#linearGradient3896"
2054- id="radialGradient3906"
2055- gradientUnits="userSpaceOnUse"
2056- gradientTransform="matrix(0.48768998,-1.5849921,-0.8254465,-0.2539842,133.90024,12.443759)"
2057- cx="-273.75134"
2058- cy="320.53235"
2059- fx="-273.75134"
2060- fy="320.53235"
2061- r="49.711224" />
2062- <radialGradient
2063- inkscape:collect="always"
2064- xlink:href="#linearGradient3908"
2065- id="radialGradient3914"
2066- cx="-188.89853"
2067- cy="456.47113"
2068- fx="-188.89853"
2069- fy="456.47113"
2070- r="62.046875"
2071- gradientTransform="matrix(-0.0895426,6.0823415e-8,-4.0337866e-7,-0.59384305,-321.00376,691.05285)"
2072- gradientUnits="userSpaceOnUse" />
2073- <radialGradient
2074- inkscape:collect="always"
2075- xlink:href="#linearGradient3918"
2076- id="radialGradient3924"
2077- cx="-192.93913"
2078- cy="403.7388"
2079- fx="-192.93913"
2080- fy="403.7388"
2081- r="62.046875"
2082- gradientTransform="matrix(-4.9230025e-8,0.3500303,-0.59384305,-8.35212e-8,-66.352315,456.20047)"
2083- gradientUnits="userSpaceOnUse" />
2084- <radialGradient
2085- inkscape:collect="always"
2086- xlink:href="#linearGradient3945"
2087- id="radialGradient3951"
2088- cx="-196.83202"
2089- cy="310.99088"
2090- fx="-196.83202"
2091- fy="310.99088"
2092- r="49.663921"
2093- gradientTransform="matrix(-0.11552005,0.44604223,-1.5340915,-0.54706546,257.51838,583.13425)"
2094- gradientUnits="userSpaceOnUse" />
2095- <radialGradient
2096- inkscape:collect="always"
2097- xlink:href="#linearGradient3953"
2098- id="radialGradient3959"
2099- cx="-226.07143"
2100- cy="271.32739"
2101- fx="-226.07143"
2102- fy="271.32739"
2103- r="5.2734375"
2104- gradientTransform="matrix(-1.7273801e-7,4.0634919,-2.7259259,-1.158765e-7,513.5469,1182.7873)"
2105- gradientUnits="userSpaceOnUse" />
2106- <radialGradient
2107- inkscape:collect="always"
2108- xlink:href="#linearGradient3961"
2109- id="radialGradient3967"
2110- cx="-193.85033"
2111- cy="285.24863"
2112- fx="-193.85033"
2113- fy="285.24863"
2114- r="6.2866349"
2115- gradientTransform="matrix(1.5443388,0.31346969,-0.12981992,0.948631,142.5512,75.37164)"
2116- gradientUnits="userSpaceOnUse" />
2117- <linearGradient
2118- inkscape:collect="always"
2119- xlink:href="#linearGradient3854"
2120- id="linearGradient4091"
2121- gradientUnits="userSpaceOnUse"
2122- x1="-211.12189"
2123- y1="245.25031"
2124- x2="-201.02036"
2125- y2="389.70212"
2126- gradientTransform="matrix(0.6338819,0,0,0.6089088,221.83905,644.83223)" />
2127- <radialGradient
2128- inkscape:collect="always"
2129- xlink:href="#linearGradient3908"
2130- id="radialGradient4093"
2131- gradientUnits="userSpaceOnUse"
2132- gradientTransform="matrix(-0.09790279,7.1628508e-8,-4.410403e-7,-0.69933743,83.202705,1239.4944)"
2133- cx="-188.89853"
2134- cy="456.47113"
2135- fx="-188.89853"
2136- fy="456.47113"
2137- r="62.046875" />
2138- <radialGradient
2139- inkscape:collect="always"
2140- xlink:href="#linearGradient3872"
2141- id="radialGradient4095"
2142- gradientUnits="userSpaceOnUse"
2143- gradientTransform="matrix(-1.1182277,0.0551342,-0.09068266,-2.5015192,-764.72423,1065.2658)"
2144- cx="-197.15332"
2145- cy="316.23712"
2146- fx="-197.15332"
2147- fy="316.23712"
2148- r="42.421329" />
2149- <radialGradient
2150- inkscape:collect="always"
2151- xlink:href="#linearGradient3886"
2152- id="radialGradient4097"
2153- gradientUnits="userSpaceOnUse"
2154- gradientTransform="matrix(0.15584403,-1.7142858,0.9570922,0.08700819,-531.54808,4.3965634)"
2155- cx="-199.00005"
2156- cy="379.85995"
2157- fx="-199.00005"
2158- fy="379.85995"
2159- r="38.890873" />
2160- <radialGradient
2161- inkscape:collect="always"
2162- xlink:href="#linearGradient3896"
2163- id="radialGradient4099"
2164- gradientUnits="userSpaceOnUse"
2165- gradientTransform="matrix(-0.6182757,-1.9302312,1.0464712,-0.30930642,-456.36859,425.1855)"
2166- cx="-273.75134"
2167- cy="320.53235"
2168- fx="-273.75134"
2169- fy="320.53235"
2170- r="49.711224" />
2171- <radialGradient
2172- inkscape:collect="always"
2173- xlink:href="#linearGradient3896"
2174- id="radialGradient4101"
2175- gradientUnits="userSpaceOnUse"
2176- gradientTransform="matrix(0.6182757,-1.9302312,-1.0464712,-0.30930642,657.36721,425.80059)"
2177- cx="-273.75134"
2178- cy="320.53235"
2179- fx="-273.75134"
2180- fy="320.53235"
2181- r="49.711224" />
2182- <radialGradient
2183- inkscape:collect="always"
2184- xlink:href="#linearGradient3918"
2185- id="radialGradient4103"
2186- gradientUnits="userSpaceOnUse"
2187- gradientTransform="matrix(-6.2412045e-8,0.41681683,-0.7528527,-9.9457215e-8,403.49427,962.83622)"
2188- cx="-192.93913"
2189- cy="403.7388"
2190- fx="-192.93913"
2191- fy="403.7388"
2192- r="62.046875" />
2193- <radialGradient
2194- inkscape:collect="always"
2195- xlink:href="#linearGradient3953"
2196- id="radialGradient4105"
2197- gradientUnits="userSpaceOnUse"
2198- gradientTransform="matrix(-1.0731693e-7,2.5245251,-1.6935357,-7.199058e-8,-66.303286,853.92148)"
2199- cx="-226.07143"
2200- cy="271.32739"
2201- fx="-226.07143"
2202- fy="271.32739"
2203- r="5.2734375" />
2204- <radialGradient
2205- inkscape:collect="always"
2206- xlink:href="#linearGradient3961"
2207- id="radialGradient4107"
2208- gradientUnits="userSpaceOnUse"
2209- gradientTransform="matrix(0.9594512,0.19474928,-0.08065321,0.58935591,-260.62434,178.25247)"
2210- cx="-193.85033"
2211- cy="285.24863"
2212- fx="-193.85033"
2213- fy="285.24863"
2214- r="6.2866349" />
2215- <linearGradient
2216- inkscape:collect="always"
2217- xlink:href="#linearGradient3842"
2218- id="linearGradient4163"
2219- gradientUnits="userSpaceOnUse"
2220- x1="-216.17264"
2221- y1="218.98633"
2222- x2="-217.1828"
2223- y2="249.29091"
2224- gradientTransform="matrix(0.63675565,0,0,0.59461726,-397.39056,671.91253)" />
2225- <linearGradient
2226- inkscape:collect="always"
2227- xlink:href="#linearGradient3854"
2228- id="linearGradient4165"
2229- gradientUnits="userSpaceOnUse"
2230- x1="-211.12189"
2231- y1="245.25031"
2232- x2="-201.02036"
2233- y2="389.70212"
2234- gradientTransform="matrix(0.63675565,0,0,0.59461726,-397.39056,671.91253)" />
2235- <radialGradient
2236- inkscape:collect="always"
2237- xlink:href="#linearGradient3908"
2238- id="radialGradient4167"
2239- gradientUnits="userSpaceOnUse"
2240- gradientTransform="matrix(-0.11403351,7.2333305e-8,-5.1370729e-7,-0.70621865,-539.21329,1265.047)"
2241- cx="-188.89853"
2242- cy="456.47113"
2243- fx="-188.89853"
2244- fy="456.47113"
2245- r="62.046875" />
2246- <radialGradient
2247- inkscape:collect="always"
2248- xlink:href="#linearGradient3872"
2249- id="radialGradient4169"
2250- gradientUnits="userSpaceOnUse"
2251- gradientTransform="matrix(-1.1182277,0.0551342,-0.09068266,-2.5015192,-679.00994,1500.9801)"
2252- cx="-197.15332"
2253- cy="316.23712"
2254- fx="-197.15332"
2255- fy="316.23712"
2256- r="42.421329" />
2257- <radialGradient
2258- inkscape:collect="always"
2259- xlink:href="#linearGradient3886"
2260- id="radialGradient4171"
2261- gradientUnits="userSpaceOnUse"
2262- gradientTransform="matrix(0.15584403,-1.7142858,0.9570922,0.08700819,-531.54808,4.3965634)"
2263- cx="-199.00005"
2264- cy="379.85995"
2265- fx="-199.00005"
2266- fy="379.85995"
2267- r="38.890873" />
2268- <radialGradient
2269- inkscape:collect="always"
2270- xlink:href="#linearGradient3896"
2271- id="radialGradient4173"
2272- gradientUnits="userSpaceOnUse"
2273- gradientTransform="matrix(-0.6210787,-1.8849273,1.0512155,-0.30204677,-1078.6729,457.42109)"
2274- cx="-273.75134"
2275- cy="320.53235"
2276- fx="-273.75134"
2277- fy="320.53235"
2278- r="49.711224" />
2279- <radialGradient
2280- inkscape:collect="always"
2281- xlink:href="#linearGradient3896"
2282- id="radialGradient4175"
2283- gradientUnits="userSpaceOnUse"
2284- gradientTransform="matrix(0.6210787,-1.8849273,-1.0512155,-0.30204677,40.112094,458.02174)"
2285- cx="-273.75134"
2286- cy="320.53235"
2287- fx="-273.75134"
2288- fy="320.53235"
2289- r="49.711224" />
2290- <radialGradient
2291- inkscape:collect="always"
2292- xlink:href="#linearGradient3918"
2293- id="radialGradient4177"
2294- gradientUnits="userSpaceOnUse"
2295- gradientTransform="matrix(-6.2694994e-8,0.41626811,-0.75626583,-9.9326294e-8,-214.9118,985.75254)"
2296- cx="-192.93913"
2297- cy="403.7388"
2298- fx="-192.93913"
2299- fy="403.7388"
2300- r="62.046875" />
2301- <radialGradient
2302- inkscape:collect="always"
2303- xlink:href="#linearGradient3953"
2304- id="radialGradient4179"
2305- gradientUnits="userSpaceOnUse"
2306- gradientTransform="matrix(-1.0629016e-7,2.5003717,-1.6773327,-7.1301808e-8,-68.017833,1423.1127)"
2307- cx="-226.07143"
2308- cy="271.32739"
2309- fx="-226.07143"
2310- fy="271.32739"
2311- r="5.2734375" />
2312- <radialGradient
2313- inkscape:collect="always"
2314- xlink:href="#linearGradient3961"
2315- id="radialGradient4181"
2316- gradientUnits="userSpaceOnUse"
2317- gradientTransform="matrix(0.9502716,0.192886,-0.07988155,0.58371719,-260.25926,813.70895)"
2318- cx="-193.85033"
2319- cy="285.24863"
2320- fx="-193.85033"
2321- fy="285.24863"
2322- r="6.2866349" />
2323- <radialGradient
2324- inkscape:collect="always"
2325- xlink:href="#linearGradient3961"
2326- id="radialGradient4187"
2327- gradientUnits="userSpaceOnUse"
2328- gradientTransform="matrix(0.7721694,0.15673485,-0.06490996,0.4743155,-118.68886,249.90306)"
2329- cx="-193.85033"
2330- cy="285.24863"
2331- fx="-193.85033"
2332- fy="285.24863"
2333- r="6.2866349" />
2334- <radialGradient
2335- inkscape:collect="always"
2336- xlink:href="#linearGradient3953"
2337- id="radialGradient4189"
2338- gradientUnits="userSpaceOnUse"
2339- gradientTransform="matrix(-8.6369005e-8,2.031746,-1.3629629,-5.793825e-8,47.13323,783.69327)"
2340- cx="-226.07143"
2341- cy="271.32739"
2342- fx="-226.07143"
2343- fy="271.32739"
2344- r="5.2734375" />
2345- <linearGradient
2346- inkscape:collect="always"
2347- xlink:href="#linearGradient3267"
2348- id="linearGradient3275"
2349- x1="65.5"
2350- y1="987.36218"
2351- x2="64.5"
2352- y2="1039.3622"
2353- gradientUnits="userSpaceOnUse"
2354- gradientTransform="matrix(0.98544976,0,0,1.0180642,0.72159872,-21.779314)" />
2355- <linearGradient
2356- inkscape:collect="always"
2357- xlink:href="#linearGradient3277"
2358- id="linearGradient3283"
2359- x1="107.5"
2360- y1="780.36218"
2361- x2="106.5"
2362- y2="788.86218"
2363- gradientUnits="userSpaceOnUse" />
2364- <linearGradient
2365- inkscape:collect="always"
2366- xlink:href="#linearGradient4070"
2367- id="linearGradient4076"
2368- x1="98.5"
2369- y1="993.86218"
2370- x2="64.5"
2371- y2="995.36218"
2372- gradientUnits="userSpaceOnUse"
2373- gradientTransform="matrix(1,0,0,1.216216,0,-213.44294)" />
2374- <linearGradient
2375- inkscape:collect="always"
2376- xlink:href="#linearGradient4088"
2377- id="linearGradient4094"
2378- x1="100"
2379- y1="127"
2380- x2="98.5"
2381- y2="99"
2382- gradientUnits="userSpaceOnUse" />
2383- <linearGradient
2384- inkscape:collect="always"
2385- xlink:href="#linearGradient4099"
2386- id="linearGradient4097"
2387- gradientUnits="userSpaceOnUse"
2388- x1="92.166664"
2389- y1="123.31897"
2390- x2="90.139999"
2391- y2="74.939651" />
2392- <filter
2393- inkscape:collect="always"
2394- id="filter4115"
2395- x="-0.28636364"
2396- width="1.5727273"
2397- y="-0.067379679"
2398- height="1.1347594">
2399- <feGaussianBlur
2400- inkscape:collect="always"
2401- stdDeviation="2.1477273"
2402- id="feGaussianBlur4117" />
2403- </filter>
2404- <filter
2405- inkscape:collect="always"
2406- id="filter4125"
2407- x="-0.13295501"
2408- width="1.26591"
2409- y="-4.0853449"
2410- height="9.1706899">
2411- <feGaussianBlur
2412- inkscape:collect="always"
2413- stdDeviation="9.3622488"
2414- id="feGaussianBlur4127" />
2415- </filter>
2416- </defs>
2417- <sodipodi:namedview
2418- id="base"
2419- pagecolor="#ffffff"
2420- bordercolor="#666666"
2421- borderopacity="1.0"
2422- inkscape:pageopacity="0.0"
2423- inkscape:pageshadow="2"
2424- inkscape:zoom="2"
2425- inkscape:cx="125.59398"
2426- inkscape:cy="57.960461"
2427- inkscape:document-units="px"
2428- inkscape:current-layer="layer1"
2429- showgrid="false"
2430- inkscape:window-width="1600"
2431- inkscape:window-height="876"
2432- inkscape:window-x="0"
2433- inkscape:window-y="24"
2434- inkscape:window-maximized="1" />
2435- <metadata
2436- id="metadata7">
2437- <rdf:RDF>
2438- <cc:Work
2439- rdf:about="">
2440- <dc:format>image/svg+xml</dc:format>
2441- <dc:type
2442- rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
2443- <dc:title>Trophy</dc:title>
2444- <dc:date>2011-02-16</dc:date>
2445- <dc:creator>
2446- <cc:Agent>
2447- <dc:title>netalloy</dc:title>
2448- </cc:Agent>
2449- </dc:creator>
2450- <dc:subject>
2451- <rdf:Bag>
2452- <rdf:li>trophy</rdf:li>
2453- <rdf:li>sports</rdf:li>
2454- <rdf:li>prize</rdf:li>
2455- <rdf:li>winner</rdf:li>
2456- <rdf:li>racing</rdf:li>
2457- <rdf:li>motorsports</rdf:li>
2458- <rdf:li>victory</rdf:li>
2459- <rdf:li>achievement</rdf:li>
2460- <rdf:li>award</rdf:li>
2461- <rdf:li>cup</rdf:li>
2462- <rdf:li>merit</rdf:li>
2463- <rdf:li>No.1</rdf:li>
2464- </rdf:Bag>
2465- </dc:subject>
2466- <dc:description>motorsports clip art by NetAlloy</dc:description>
2467- <cc:license
2468- rdf:resource="http://creativecommons.org/licenses/publicdomain/" />
2469- </cc:Work>
2470- <cc:License
2471- rdf:about="http://creativecommons.org/licenses/publicdomain/">
2472- <cc:permits
2473- rdf:resource="http://creativecommons.org/ns#Reproduction" />
2474- <cc:permits
2475- rdf:resource="http://creativecommons.org/ns#Distribution" />
2476- <cc:permits
2477- rdf:resource="http://creativecommons.org/ns#DerivativeWorks" />
2478- </cc:License>
2479- </rdf:RDF>
2480- </metadata>
2481- <g
2482- inkscape:label="Layer 1"
2483- inkscape:groupmode="layer"
2484- id="layer1"
2485- transform="translate(0,-752.36218)">
2486- <path
2487- inkscape:connector-curvature="0"
2488- id="path4047"
2489- d="m 173.24805,767.86986 c -1.45786,0.004 -2.96097,0.0757 -4.45699,0.19029 -2.99202,0.22916 -5.92202,0.64168 -8.28008,1.12267 -1.17902,0.2405 -2.22151,0.49034 -3.07036,0.76114 -0.84885,0.27079 -1.45084,0.44702 -2.11955,1.04656 -1.6129,1.4461 -2.37386,3.34018 -2.7138,5.23281 -0.33994,1.89263 -0.31746,3.82765 -0.31694,5.67046 5e-4,1.84282 -0.031,3.59015 -0.35656,4.98544 -0.3256,1.39529 -0.85654,2.39935 -1.94127,3.15872 -0.5849,0.40946 -2.95543,0.64126 -5.05124,0.41862 -2.09582,-0.22264 -3.88253,-0.66599 -3.88253,-0.66599 l -0.79235,2.93037 c 0,0 1.97944,0.49154 4.33813,0.74211 2.35869,0.25057 5.13106,0.49392 7.25002,-0.98948 1.8008,-1.26066 2.7376,-3.07787 3.16941,-4.92835 0.43182,-1.85049 0.41651,-3.78937 0.41599,-5.65144 -5e-4,-1.86207 0.007,-3.65198 0.27732,-5.15669 0.27026,-1.50472 0.76495,-2.66222 1.74318,-3.53929 -0.17038,0.15276 0.30964,-0.16339 0.99044,-0.38057 0.68079,-0.21717 1.61541,-0.46097 2.7138,-0.68502 2.19678,-0.44809 5.03128,-0.8471 7.88391,-1.06559 2.85263,-0.21849 5.73444,-0.23769 8.00276,0.019 2.26832,0.25672 3.81231,0.95158 4.08061,1.29394 3.54594,4.52465 4.15268,12.33478 2.19878,21.74946 -1.9539,9.41467 -6.38474,20.32746 -12.26165,30.92115 -11.75383,21.18738 -31.53134,39.03872 -45.91613,43.74427 l 1.01025,2.87329 c 16.12505,-5.27483 35.69932,-23.59574 47.67911,-45.19043 5.9899,-10.79735 10.53819,-21.92689 12.57859,-31.7584 2.04041,-9.83152 1.67802,-18.48622 -2.77323,-24.16607 -1.35081,-1.72366 -3.62221,-2.17969 -6.21996,-2.47369 -1.29889,-0.147 -2.7218,-0.21284 -4.17966,-0.20931 z"
2490- style="font-size:medium;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-indent:0;text-align:start;text-decoration:none;line-height:normal;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;text-anchor:start;baseline-shift:baseline;color:#000000;fill:#b88100;fill-opacity:1;stroke:none;stroke-width:0;marker:none;visibility:visible;display:inline;overflow:visible;enable-background:accumulate;font-family:Sans;-inkscape-font-specification:Sans"
2491- sodipodi:nodetypes="csscssccssccssscccssscsssccsssscc" />
2492- <path
2493- inkscape:connector-curvature="0"
2494- id="path4061"
2495- d="m 174.04495,768.48495 c 1.51962,-0.004 2.98217,0.0616 4.33607,0.20688 2.7078,0.29058 5.07542,0.74131 6.48346,2.44492 4.63982,5.61381 5.01755,14.16788 2.89071,23.88508 -2.12683,9.7172 -6.84716,20.71732 -13.0908,31.38913 -12.48729,21.3436 -32.82669,39.42822 -49.63484,44.64171 l -1.05305,-2.83988 c 14.99417,-4.65083 35.52477,-22.27135 47.77652,-43.21237 6.12588,-10.47052 10.74442,-21.25641 12.78109,-30.56161 2.03667,-9.3052 1.40423,-17.02452 -2.29192,-21.49657 -0.27967,-0.33838 -1.88907,-1.02515 -4.25348,-1.27888 -2.36441,-0.25374 -5.3683,-0.23476 -8.34178,-0.0187 -2.97347,0.21595 -5.92804,0.61032 -8.21788,1.0532 -1.14492,0.22144 -2.11914,0.4624 -2.82877,0.67705 -0.70964,0.21466 -1.20999,0.52713 -1.0324,0.37615 -1.01967,0.86687 -1.53531,2.0109 -1.81702,3.49813 -0.28171,1.48722 -0.26897,3.25632 -0.26842,5.09673 5e-4,1.84042 -0.004,3.75676 -0.45426,5.58573 -0.4501,1.82896 -1.42659,3.62504 -3.30368,4.87105 -2.20872,1.46614 -5.09854,1.22563 -7.55715,0.97797 -2.4586,-0.24766 -4.5219,-0.73348 -4.5219,-0.73348 l 0.82592,-2.8963 c 0,0 1.8624,0.4382 4.047,0.65825 2.1846,0.22005 4.65555,-0.009 5.26523,-0.41376 1.13067,-0.75054 1.70476,-1.74292 2.04415,-3.12198 0.33938,-1.37907 0.3722,-3.10609 0.37166,-4.92748 -5e-4,-1.82138 -0.0446,-3.7339 0.30972,-5.60453 0.35434,-1.87062 1.14754,-3.74267 2.82877,-5.17196 0.69703,-0.59258 1.34517,-0.76675 2.22998,-1.03439 0.88481,-0.26765 1.95081,-0.51459 3.17978,-0.75229 2.45795,-0.47539 5.51209,-0.88312 8.63085,-1.10962 1.55939,-0.11325 3.14682,-0.18458 4.66644,-0.18807 z"
2496- style="font-size:medium;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-indent:0;text-align:start;text-decoration:none;line-height:normal;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;text-anchor:start;baseline-shift:baseline;color:#000000;fill:url(#radialGradient4101);fill-opacity:1;stroke:none;stroke-width:0;marker:none;visibility:visible;display:inline;overflow:visible;enable-background:accumulate;font-family:Sans;-inkscape-font-specification:Sans"
2497- sodipodi:nodetypes="cssssccsssscsscsccssccscsccsssscc" />
2498- <path
2499- inkscape:connector-curvature="0"
2500- id="path4045"
2501- d="m 26.345915,767.86986 c -1.45786,-0.004 -2.86098,0.0623 -4.15985,0.20931 -2.59776,0.294 -4.86915,0.75004 -6.21997,2.4737 -4.45125,5.67984 -4.81363,14.33455 -2.77323,24.16606 2.0404,9.83152 6.56889,20.96106 12.55878,31.7584 11.97979,21.5947 31.57388,39.91561 47.69893,45.19044 l 1.01025,-2.87329 c -14.38479,-4.70555 -34.1623,-22.5569 -45.91613,-43.74428 -5.87692,-10.59369 -10.30776,-21.50647 -12.26166,-30.92115 -1.95389,-9.41467 -1.34715,-17.2248 2.19878,-21.74946 0.2683,-0.34236 1.81229,-1.03721 4.08062,-1.29393 2.26832,-0.25672 5.15013,-0.23752 8.00275,-0.019 2.85263,0.21849 5.68713,0.6175 7.88391,1.06559 1.09839,0.22405 2.03301,0.46785 2.71381,0.68503 0.68079,0.21717 1.16081,0.53332 0.99044,0.38056 0.97822,0.87707 1.47291,2.03457 1.74317,3.53929 0.27026,1.50471 0.25804,3.29462 0.25752,5.15669 -5e-4,1.86207 0.004,3.80095 0.43579,5.65144 0.43181,1.85048 1.36861,3.66769 3.16941,4.92835 2.11896,1.4834 4.89134,1.24005 7.25002,0.98948 2.35869,-0.25057 4.33813,-0.74211 4.33813,-0.74211 l -0.79235,-2.93037 c 0,0 -1.78671,0.44335 -3.88252,0.66599 -2.09582,0.22264 -4.46635,-0.009 -5.05125,-0.41862 -1.08473,-0.75937 -1.63548,-1.76343 -1.96107,-3.15872 -0.3256,-1.39529 -0.35708,-3.14262 -0.35656,-4.98544 5e-4,-1.84281 0.0428,-3.77783 -0.29713,-5.67046 -0.33994,-1.89263 -1.10091,-3.78671 -2.71381,-5.23281 -0.6687,-0.59954 -1.2905,-0.77577 -2.13935,-1.04656 -0.84885,-0.2708 -1.87153,-0.52064 -3.05056,-0.76114 -2.35806,-0.48099 -5.28806,-0.89351 -8.28008,-1.12267 -1.49601,-0.11458 -3.01893,-0.18676 -4.47679,-0.19029 z"
2502- style="font-size:medium;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-indent:0;text-align:start;text-decoration:none;line-height:normal;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;text-anchor:start;baseline-shift:baseline;color:#000000;fill:#b88100;fill-opacity:1;stroke:none;stroke-width:0;marker:none;visibility:visible;display:inline;overflow:visible;enable-background:accumulate;font-family:Sans;-inkscape-font-specification:Sans"
2503- sodipodi:nodetypes="cssssccsssscsscsccssccscscsscsscc" />
2504- <path
2505- style="font-size:medium;font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;text-indent:0;text-align:start;text-decoration:none;line-height:normal;letter-spacing:normal;word-spacing:normal;text-transform:none;direction:ltr;block-progression:tb;writing-mode:lr-tb;text-anchor:start;baseline-shift:baseline;color:#000000;fill:url(#radialGradient4099);fill-opacity:1;stroke:none;stroke-width:0;marker:none;visibility:visible;display:inline;overflow:visible;enable-background:accumulate;font-family:Sans;-inkscape-font-specification:Sans"
2506- d="m 26.953645,767.86986 c -1.51962,-0.004 -2.98218,0.0616 -4.33607,0.20688 -2.70781,0.29058 -5.07543,0.74132 -6.48346,2.44492 -4.63982,5.61381 -5.01756,14.16788 -2.89072,23.88508 2.12684,9.7172 6.84716,20.71732 13.09081,31.38913 12.48728,21.3436 32.82669,41.42822 49.63484,46.64171 l 1.05305,-2.83988 c -14.99417,-4.65083 -35.52478,-24.27135 -47.77653,-45.21237 -6.12588,-10.47052 -10.74442,-21.25641 -12.78108,-30.56161 -2.03667,-9.3052 -1.40423,-17.02452 2.29192,-21.49657 0.27966,-0.33837 1.88907,-1.02515 4.25348,-1.27888 2.36441,-0.25374 5.3683,-0.23476 8.34177,-0.0188 2.97347,0.21595 5.92805,0.61032 8.21789,1.0532 1.14492,0.22144 2.11914,0.4624 2.82877,0.67705 0.70963,0.21466 1.20999,0.52713 1.03239,0.37615 1.01967,0.86687 1.53532,2.01091 1.81703,3.49813 0.28171,1.48722 0.26897,3.25632 0.26842,5.09674 -5e-4,1.84041 0.004,3.75675 0.45426,5.58572 0.4501,1.82896 1.42658,3.62504 3.30367,4.87105 2.20873,1.46614 5.09855,1.22563 7.55715,0.97797 2.45861,-0.24766 4.52191,-0.73348 4.52191,-0.73348 l -0.82592,-2.8963 c 0,0 -1.8624,0.4382 -4.047,0.65825 -2.1846,0.22005 -4.65555,-0.009 -5.26523,-0.41376 -1.13067,-0.75054 -1.70476,-1.74292 -2.04415,-3.12198 -0.33939,-1.37907 -0.37221,-3.10609 -0.37166,-4.92747 5e-4,-1.82139 0.0446,-3.73391 -0.30972,-5.60454 -0.35434,-1.87062 -1.14755,-3.74267 -2.82877,-5.17196 -0.69703,-0.59257 -1.34517,-0.76675 -2.22999,-1.03439 -0.8848,-0.26765 -1.9508,-0.51459 -3.17977,-0.75229 -2.45796,-0.47539 -5.51209,-0.88312 -8.63085,-1.10962 -1.55939,-0.11325 -3.14683,-0.18458 -4.66644,-0.18808 z"
2507- id="path4059"
2508- inkscape:connector-curvature="0"
2509- sodipodi:nodetypes="cssssccssssssccsccssccscsccscssc" />
2510- <path
2511- sodipodi:nodetypes="ccccc"
2512- inkscape:connector-curvature="0"
2513- id="path4035"
2514- d="m 46.349625,1001.9294 107.049755,-0.7859 4.40793,14.147 -113.976505,0 z"
2515- style="fill:#310e0a;fill-opacity:1;stroke:#918d89;stroke-width:0;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:4;stroke-opacity:1;stroke-dashoffset:0" />
2516- <path
2517- id="path4037"
2518- d="m 94.943815,783.09258 0.0792,0.19028 c -5.04828,0.11159 -10.93977,0.2564 -14.69814,0.41863 -8.8353,0.38138 -26.24667,3.69151 -26.24667,3.69151 l -1.28757,3.69151 c 0,0 18.71785,-3.31402 28.18793,-3.69151 6.34248,-0.25282 14.72066,-0.75449 18.83818,-1.00851 4.129675,0.25472 12.485715,0.75608 18.818375,1.00851 9.47009,0.37749 28.16813,3.69151 28.16813,3.69151 l -1.26777,-3.69151 c 0,0 -17.41137,-3.31013 -26.24667,-3.69151 -3.75837,-0.16223 -9.64987,-0.30704 -14.69815,-0.41863 l 0.0792,-0.19028 c 0,0 -3.03839,0.0607 -4.853155,0.0951 -1.82773,-0.0347 -4.87297,-0.0951 -4.87297,-0.0951 z"
2519- style="fill:url(#linearGradient3283);fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
2520- inkscape:connector-curvature="0" />
2521- <path
2522- sodipodi:nodetypes="cccsccsccccc"
2523- inkscape:connector-curvature="0"
2524- id="path4039"
2525- d="m 97.499155,786.17518 0,0.19029 c -13.34789,0.34054 -25.52406,-0.8199 -43.42091,5.34698 0,0 -1.42233,31.08928 3.20903,47.97059 3.45424,12.59074 9.33588,27.35141 19.19473,36.28716 14.01122,10.98765 34.003185,10.62835 46.629945,0 9.85885,-8.93575 15.7603,-23.69642 19.21455,-36.28716 4.63135,-16.88131 3.20902,-47.97059 3.20902,-47.97059 -17.90592,-6.17001 -30.08487,-5.02377 -43.44072,-5.36601 l 0,-0.17126 c -0.77367,0.0449 -1.53535,0.0837 -2.297825,0.11417 -0.75725,-0.0304 -1.5295,-0.0696 -2.29782,-0.11417 z"
2526- style="fill:url(#linearGradient4091);fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
2527- <path
2528- sodipodi:nodetypes="cccccscccccccscccccc"
2529- inkscape:connector-curvature="0"
2530- id="path4041"
2531- d="m 91.760723,881.00795 1.657135,8.00254 1.65713,18.48211 -4.971395,4.30611 3.860948,4.9349 c 0,0 4.877148,23.3695 -5.456109,32.21224 -2.352979,2.01359 -2.13973,-1.17515 -2.13973,-1.17515 l -5.754587,3.50737 -15.367504,7.94529 c 10.325113,10.32254 22.173616,8.74714 33.911413,8.04064 11.738196,0.70646 23.603026,2.28231 33.928496,-8.04064 l -15.36751,-7.94529 -5.75459,-3.50737 c 0,0 0.21327,3.18874 -2.13971,1.17515 -10.333269,-8.84274 -5.45613,-32.21224 -5.45613,-32.21224 l 3.86094,-4.9349 -4.9714,-4.30611 1.65715,-18.48211 1.65714,-8.00254 c -13.444745,5.18428 -4.56111,2.20785 -14.811687,0 z"
2532- style="fill:url(#radialGradient4093);fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
2533- <path
2534- sodipodi:nodetypes="ccccccc"
2535- inkscape:connector-curvature="0"
2536- id="path4043"
2537- d="m 65.764065,958.9648 -12.8197,0.23685 -3.84391,22.13575 c 36.98708,1.3293 64.853805,0.2823 102.333815,0 l -5.76487,-22.13575 c -5.23853,-0.10412 -17.16597,0.12787 -12.3197,-1.23685 -19.43083,10.21076 -52.626825,13.28829 -67.585635,1 z"
2538- style="fill:#3a0704;fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none" />
2539- <path
2540- inkscape:connector-curvature="0"
2541- id="path4049"
2542- d="m 90.378491,945.37519 c -2.648588,0.72535 -4.290176,1.74429 -4.290176,2.87329 0,2.20644 6.295636,3.99597 14.054025,3.99597 7.75841,0 14.03556,-1.78953 14.03556,-3.99597 0,-1.129 -1.64159,-2.14794 -4.29019,-2.87329 -0.51543,0.44332 -1.09484,0.85369 -1.73826,1.21782 1.19966,0.46694 1.92318,1.03328 1.92318,1.65547 0,1.55925 -4.44757,2.8162 -9.93029,2.8162 -5.482709,0 -9.930279,-1.25695 -9.930279,-2.8162 0,-0.62219 0.705041,-1.18853 1.904694,-1.65547 -0.643408,-0.36413 -1.222842,-0.7745 -1.738264,-1.21782 z"
2543- style="fill:#804d00;fill-opacity:1;stroke:#918d89;stroke-width:0;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0" />
2544- <path
2545- sodipodi:nodetypes="cccc"
2546- inkscape:connector-curvature="0"
2547- id="path4051"
2548- d="m -592.13203,378.34534 c -24.34186,-21.17521 -40.34192,-23.95756 -46.46702,-141.42136 l 6.06092,-2.0203 c 0.99724,55.24396 -7.934,101.34849 40.4061,143.44166 z"
2549- style="fill:#804d00;fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;filter:url(#filter3862)"
2550- transform="matrix(0.6338819,0,0,0.6089088,462.71418,647.44183)" />
2551- <path
2552- style="fill:#804d00;fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;filter:url(#filter3866)"
2553- d="m -561.82747,388.44686 c 24.34186,-21.17521 50.44345,-33.04893 56.56855,-150.51273 l -6.06092,-2.0203 c -0.99724,55.24396 -2.16753,110.43986 -50.50763,152.53303 z"
2554- id="path4053"
2555- inkscape:connector-curvature="0"
2556- sodipodi:nodetypes="cccc"
2557- transform="matrix(0.6338819,0,0,0.6089088,462.71418,647.44183)" />
2558- <path
2559- sodipodi:nodetypes="ccccc"
2560- inkscape:connector-curvature="0"
2561- id="path4055"
2562- d="m -614.35539,236.18319 13.13199,83.57331 60.60915,-1.14485 10.10152,-84.71813 c -29.79783,-11.81867 -56.63225,-3.48616 -83.84266,2.28967 z"
2563- style="fill:url(#radialGradient4095);fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;filter:url(#filter3880)"
2564- transform="matrix(0.6338819,0,0,0.6089088,462.71418,647.44183)" />
2565- <path
2566- style="fill:url(#radialGradient4103);fill-opacity:1;stroke:#000000;stroke-width:0;stroke-linecap:butt;stroke-linejoin:miter;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none"
2567- d="m 90.579445,880.00795 1.92146,8.09195 1.92145,18.68854 -5.76436,4.35422 4.47679,4.99003 c 0,0 5.63478,21.09474 -6.99251,30.5182 -2.87535,2.14582 -2.61476,-1.25232 -2.61476,-1.25232 l -7.03213,3.7377 -16.65921,9.9608 c 11.97203,10.43788 25.71044,8.84487 39.32049,8.13048 13.610525,0.71436 27.367855,2.30777 39.340295,-8.13048 l -16.65921,-9.9608 -7.03212,-3.7377 c 0,0 0.26058,3.39814 -2.61477,1.25232 -12.627295,-9.42346 -6.99252,-30.5182 -6.99252,-30.5182 l 4.47679,-4.99003 -5.76436,-4.35422 1.92146,-18.68854 1.92145,-8.09195 c -15.589255,5.24222 -5.28862,2.2325 -17.174235,0 z"
2568- id="path4063"
2569- inkscape:connector-curvature="0"
2570- sodipodi:nodetypes="cccccscccccccscccccc" />
2571- <rect
2572- ry="0.50903207"
2573- y="980.23029"
2574- x="49.593613"
2575- height="28.179085"
2576- width="101.59111"
2577- id="rect4065"
2578- style="fill:url(#linearGradient3275);fill-opacity:1;stroke:#918d89;stroke-width:0;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0" />
2579- <rect
2580- style="fill:#692017;fill-opacity:1;stroke:#918d89;stroke-width:0;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
2581- id="rect4067"
2582- width="113.9765"
2583- height="10.686725"
2584- x="43.690475"
2585- y="1014.6754"
2586- ry="0" />
2587- <text
2588- transform="scale(1.1209551,0.8920964)"
2589- sodipodi:linespacing="125%"
2590- id="text4155"
2591- y="1556.0684"
2592- x="55.365215"
2593- style="font-size:20.11759758px;font-style:normal;font-weight:normal;line-height:125%;letter-spacing:0px;word-spacing:0px;opacity:0.37560975;fill:#ffc022;fill-opacity:1;stroke:none;font-family:Sans"
2594- xml:space="preserve"><tspan
2595- style="fill:#ffc022;fill-opacity:1"
2596- y="1556.0684"
2597- x="55.365215"
2598- id="tspan4157"
2599- sodipodi:role="line" /></text>
2600- <path
2601- style="fill:url(#linearGradient4076);fill-opacity:1;stroke:#918d89;stroke-width:0;stroke-linecap:round;stroke-linejoin:bevel;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none;stroke-dashoffset:0"
2602- d="m 73.006446,984.36218 c 0.0042,0.043 0.03324,0.083 0.03324,0.12641 0,1.994 2.059387,3.64041 -3.039682,3.88693 l 0,6.85744 c 0,0.14259 0.231841,0.25282 0.531748,0.25282 -0.299907,0 -0.531748,0.10702 -0.531748,0.25281 l 0,7.01541 c 5.099069,0.2521 3.039682,1.9425 3.039682,3.9818 0,0.044 -0.03007,0.083 -0.03324,0.1264 l 50.682054,0 c -0.0633,-0.169 -0.13295,-0.3463 -0.13295,-0.5214 0,-1.7131 -0.88561,-3.1523 3.44445,-3.6658 l 0,-6.93641 c 0,-0.14582 -0.23184,-0.25281 -0.53175,-0.25281 0.29991,0 0.53175,-0.11019 0.53175,-0.25282 l 0,-6.77843 c -4.33006,-0.50201 -3.44445,-1.91169 -3.44445,-3.58674 0,-0.1713 0.0696,-0.34032 0.13295,-0.50561 z"
2603- id="rect3285"
2604- inkscape:connector-curvature="0"
2605- sodipodi:nodetypes="cscscscsccscscscscc" />
2606- <path
2607- style="opacity:0.22439025000000001;fill:none;stroke:#000000;stroke-width:1px;stroke-linecap:butt;stroke-linejoin:miter;stroke-opacity:1;filter:url(#filter4115)"
2608- d="m 95.5,194 2.5,-11.5 1,-16.5 -3,-4.5 2,-3 L 95.5,132 C 86.96546,129.38739 82.88593,124.10178 81,117.5"
2609- id="path4105"
2610- inkscape:connector-curvature="0"
2611- transform="translate(0,752.36218)"
2612- sodipodi:nodetypes="ccccccc" />
2613- </g>
2614-</svg>
2615
2616=== added directory 'data/daemon'
2617=== renamed file 'daemon/validation-key.pub' => 'data/daemon/validation-key.pub'
2618=== renamed file 'daemon/lock.png' => 'data/media/lock.png'
2619=== modified file 'data/ui/TrophyinfoWindow.ui'
2620--- data/ui/TrophyinfoWindow.ui 2012-02-22 04:59:12 +0000
2621+++ data/ui/TrophyinfoWindow.ui 2012-03-05 04:37:19 +0000
2622@@ -20,7 +20,7 @@
2623 <property name="can_focus">False</property>
2624 <property name="title" translatable="yes">Accomplishment Information</property>
2625 <property name="window_position">center</property>
2626- <property name="icon">trophy-accomplished.svg</property>
2627+ <property name="icon">../media/trophy-accomplished.svg</property>
2628 <property name="icon_name">distributor-logo</property>
2629 <child>
2630 <object class="GtkVBox" id="vbox1">
2631
2632=== added file 'install_deps.sh'
2633--- install_deps.sh 1970-01-01 00:00:00 +0000
2634+++ install_deps.sh 2012-03-05 04:37:19 +0000
2635@@ -0,0 +1,3 @@
2636+sudo apt-get install -y python-distutils-extra python-gpgme quickly \
2637+ quickly-ubuntu-template pylint python-twisted python-imaging \
2638+ python-ubuntuone-client python-ubuntuone-devtools
2639
2640=== modified file 'setup.py'
2641--- setup.py 2012-01-30 06:58:49 +0000
2642+++ setup.py 2012-03-05 04:37:19 +0000
2643@@ -3,86 +3,17 @@
2644 ### BEGIN LICENSE
2645 # This file is in the public domain
2646 ### END LICENSE
2647-
2648-###################### DO NOT TOUCH THIS (HEAD TO THE SECOND PART) ######################
2649-
2650-import os
2651-import sys
2652-
2653-try:
2654- import DistUtilsExtra.auto
2655-except ImportError:
2656- print >> sys.stderr, 'To build trophyinfo you need https://launchpad.net/python-distutils-extra'
2657- sys.exit(1)
2658-assert DistUtilsExtra.auto.__version__ >= '2.18', 'needs DistUtilsExtra.auto >= 2.18'
2659-
2660-def update_config(values = {}):
2661-
2662- oldvalues = {}
2663- try:
2664- fin = file('trophyinfo_lib/trophyinfoconfig.py', 'r')
2665- fout = file(fin.name + '.new', 'w')
2666-
2667- for line in fin:
2668- fields = line.split(' = ') # Separate variable from value
2669- if fields[0] in values:
2670- oldvalues[fields[0]] = fields[1].strip()
2671- line = "%s = %s\n" % (fields[0], values[fields[0]])
2672- fout.write(line)
2673-
2674- fout.flush()
2675- fout.close()
2676- fin.close()
2677- os.rename(fout.name, fin.name)
2678- except (OSError, IOError), e:
2679- print ("ERROR: Can't find trophyinfo_lib/trophyinfoconfig.py")
2680- sys.exit(1)
2681- return oldvalues
2682-
2683-
2684-def update_desktop_file(datadir):
2685-
2686- try:
2687- fin = file('trophyinfo.desktop.in', 'r')
2688- fout = file(fin.name + '.new', 'w')
2689-
2690- for line in fin:
2691- if 'Icon=' in line:
2692- line = "Icon=%s\n" % (datadir + 'media/trophyinfo.svg')
2693- fout.write(line)
2694- fout.flush()
2695- fout.close()
2696- fin.close()
2697- os.rename(fout.name, fin.name)
2698- except (OSError, IOError), e:
2699- print ("ERROR: Can't find trophyinfo.desktop.in")
2700- sys.exit(1)
2701-
2702-
2703-class InstallAndUpdateDataDirectory(DistUtilsExtra.auto.install_auto):
2704- def run(self):
2705- values = {'__trophyinfo_data_directory__': "'%s'" % (self.prefix + '/share/trophyinfo/'),
2706- '__version__': "'%s'" % self.distribution.get_version()}
2707- previous_values = update_config(values)
2708- update_desktop_file(self.prefix + '/share/trophyinfo/')
2709- DistUtilsExtra.auto.install_auto.run(self)
2710- update_config(previous_values)
2711-
2712-
2713-
2714-##################################################################################
2715-###################### YOU SHOULD MODIFY ONLY WHAT IS BELOW ######################
2716-##################################################################################
2717-
2718-DistUtilsExtra.auto.setup(
2719+from accomplishments.util import dist
2720+
2721+
2722+dist.setup(
2723 name='trophyinfo',
2724- version='0.1',
2725+ version='0.2',
2726 license='GPL-3',
2727 author='Jono Bacon',
2728 author_email='jono@ubuntu.com',
2729 description='Trophy viewer for Ubuntu Accomplishments.',
2730 long_description='Trophy viewer for Ubuntu Accomplishments.',
2731 url='https://launchpad.net/ubuntuaccomplishments',
2732- cmdclass={'install': InstallAndUpdateDataDirectory}
2733+ cmdclass={'install': dist.InstallAndUpdateDataDirectory}
2734 )
2735-
2736
2737=== modified file 'tests/test_example.py'
2738--- tests/test_example.py 2012-01-22 23:09:09 +0000
2739+++ tests/test_example.py 2012-03-05 04:37:19 +0000
2740@@ -3,18 +3,23 @@
2741 ### BEGIN LICENSE
2742 # This file is in the public domain
2743 ### END LICENSE
2744-
2745+import os
2746 import sys
2747-import os.path
2748+
2749+sys.path.insert(
2750+ 0, os.path.realpath(os.path.join(os.path.dirname(__file__), "..")))
2751+
2752 import unittest
2753-sys.path.insert(0, os.path.realpath(os.path.join(os.path.dirname(__file__), "..")))
2754-
2755-from trophyinfo import AboutTrophyinfoDialog
2756+
2757+from accomplishments.gui import AboutTrophyinfoDialog
2758+
2759
2760 class TestExample(unittest.TestCase):
2761+
2762 def setUp(self):
2763 self.AboutTrophyinfoDialog_members = [
2764- 'AboutTrophyinfoDialog', 'get_builder', 'gettext', 'Gtk']
2765+ 'AboutDialog', 'AboutTrophyinfoDialog', 'gettext', 'logger',
2766+ 'logging']
2767
2768 def test_AboutTrophyinfoDialog_members(self):
2769 all_members = dir(AboutTrophyinfoDialog)
2770@@ -22,5 +27,6 @@
2771 public_members.sort()
2772 self.assertEqual(self.AboutTrophyinfoDialog_members, public_members)
2773
2774-if __name__ == '__main__':
2775+
2776+if __name__ == '__main__':
2777 unittest.main()
2778
2779=== modified file 'tests/test_lint.py'
2780--- tests/test_lint.py 2012-01-22 23:09:09 +0000
2781+++ tests/test_lint.py 2012-03-05 04:37:19 +0000
2782@@ -3,28 +3,31 @@
2783 ### BEGIN LICENSE
2784 # This file is in the public domain
2785 ### END LICENSE
2786-
2787+import subprocess
2788 import unittest
2789-import subprocess
2790+
2791
2792 class TestPylint(unittest.TestCase):
2793+
2794 def test_project_errors_only(self):
2795- '''run pylint in error only mode
2796-
2797- your code may well work even with pylint errors
2798- but have some unusual code'''
2799- return_code = subprocess.call(["pylint", '-E', 'trophyinfo'])
2800+ '''Run pylint in error only mode
2801+
2802+ Your code may well work even with pylint errors but have some unusual
2803+ code.
2804+ '''
2805+ return_code = subprocess.call(["pylint", '-E', 'accomplishments'])
2806 # not needed because nosetests displays pylint console output
2807 #self.assertEqual(return_code, 0)
2808
2809- # un-comment the following for loads of diagnostics
2810+ # un-comment the following for loads of diagnostics
2811 #~ def test_project_full_report(self):
2812 #~ '''Only for the brave
2813-#~
2814+ #~
2815 #~ you will have to make judgement calls about your code standards
2816 #~ that differ from the norm'''
2817 #~ return_code = subprocess.call(["pylint", 'trophyinfo'])
2818
2819+
2820 if __name__ == '__main__':
2821- 'you will get better results with nosetests'
2822+ # you will get better results with nosetests
2823 unittest.main()
2824
2825=== modified file 'trophyinfo.desktop.in'
2826--- trophyinfo.desktop.in 2012-01-22 23:09:09 +0000
2827+++ trophyinfo.desktop.in 2012-03-05 04:37:19 +0000
2828@@ -3,6 +3,6 @@
2829 _Comment=Trophyinfo application
2830 Categories=GNOME;Utility;
2831 Exec=trophyinfo
2832-Icon=trophyinfo
2833+Icon=/home/oubiwann/lab/ubuntu-accomplishments-system/941201-missing-deps/.venv/share/trophyinfo/media/trophyinfo.svg
2834 Terminal=false
2835 Type=Application

Subscribers

People subscribed via source and target branches