Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorSimon Schampijer <simon@schampijer.de>2008-08-14 16:54:10 (GMT)
committer Simon Schampijer <simon@schampijer.de>2008-08-14 16:54:10 (GMT)
commit57deb085513c05e738a81a9ebe89bde47778c1f0 (patch)
tree2d4c0ad31a328a78c7bf78234e9d5674420a9a13 /src
parent54bdb6ab0b7de69cc75c0fde5040cea51be90694 (diff)
Revert "Merge branch 'master' of git://dev.laptop.org/sugar"
This reverts commit 54bdb6ab0b7de69cc75c0fde5040cea51be90694.
Diffstat (limited to 'src')
-rw-r--r--src/Makefile.am3
-rw-r--r--src/config.py.in5
-rw-r--r--src/controlpanel/gui.py4
-rw-r--r--src/controlpanel/view/power.py3
-rwxr-xr-xsrc/emulator.py59
-rw-r--r--src/hardware/keydialog.py4
-rw-r--r--src/hardware/nminfo.py13
-rw-r--r--src/intro/Makefile.am10
-rw-r--r--src/intro/intro.py (renamed from src/intro/window.py)67
-rw-r--r--src/logsmanager.py1
-rw-r--r--src/main.py16
-rw-r--r--src/model/MeshModel.py18
-rw-r--r--src/model/homemodel.py6
-rw-r--r--src/uicheck.py83
-rw-r--r--src/view/ActivityHost.py2
-rw-r--r--src/view/Shell.py1
-rw-r--r--src/view/devices/network/Makefile.am1
-rw-r--r--src/view/devices/network/wired.py25
-rw-r--r--src/view/devices/speaker.py6
-rw-r--r--src/view/home/MeshBox.py16
-rw-r--r--src/view/home/activitieslist.py23
-rw-r--r--src/view/home/favoritesview.py4
-rw-r--r--src/view/home/grid.py2
-rw-r--r--src/view/pulsingicon.py306
24 files changed, 323 insertions, 355 deletions
diff --git a/src/Makefile.am b/src/Makefile.am
index 48fb84f..daf31ae 100644
--- a/src/Makefile.am
+++ b/src/Makefile.am
@@ -7,7 +7,6 @@ sugar_PYTHON = \
logsmanager.py \
main.py \
session.py \
- shellservice.py \
- uicheck.py
+ shellservice.py
EXTRA_DIST = $(bin_SCRIPTS) $(conf_DATA)
diff --git a/src/config.py.in b/src/config.py.in
index a69f18f..fb26181 100644
--- a/src/config.py.in
+++ b/src/config.py.in
@@ -14,9 +14,6 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
-# pylint: disable-msg=C0301
-
prefix = '@prefix@'
data_path = '@prefix@/share/sugar/data'
-shell_path = '@prefix@/share/sugar/shell'
-
+shell_path = '@prefix@/share/sugar/shell' \ No newline at end of file
diff --git a/src/controlpanel/gui.py b/src/controlpanel/gui.py
index d5dac7a..b72cbc6 100644
--- a/src/controlpanel/gui.py
+++ b/src/controlpanel/gui.py
@@ -333,7 +333,9 @@ class ModelWrapper(object):
self._options[method[4:]] = None
def __getattr__(self, name):
- return getattr(self._module, name)
+ if name.startswith('get_') or name.startswith('set_') or \
+ name.startswith('read_'):
+ return getattr(self._module, name)
def undo(self):
for key in self._options.keys():
diff --git a/src/controlpanel/view/power.py b/src/controlpanel/view/power.py
index 5bc8ab1..38d2b24 100644
--- a/src/controlpanel/view/power.py
+++ b/src/controlpanel/view/power.py
@@ -86,8 +86,7 @@ class Power(SectionView):
box_extreme_pm = gtk.HBox(spacing=style.DEFAULT_SPACING)
label_extreme_pm = gtk.Label(
- _('Extreme power management (disables' \
- 'wireless radio, increases battery life)'))
+ _('Extreme power management (disables wireless radio, increases battery life)'))
label_extreme_pm.set_alignment(0, 0.5)
self._extreme_button = gtk.CheckButton()
self._extreme_button.set_alignment(0, 0)
diff --git a/src/emulator.py b/src/emulator.py
index ac1f4e2..39acd2b 100755
--- a/src/emulator.py
+++ b/src/emulator.py
@@ -15,9 +15,9 @@
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
import os
+import sys
+import socket
import logging
-import subprocess
-import time
from optparse import OptionParser
log = logging.getLogger( 'sugar-emulator' )
@@ -30,8 +30,40 @@ import gobject
from sugar import env
-def _run_xephyr(display, dpi):
- log.info('Starting Xephyr on display %s', display)
+def _get_display_number():
+ """Find a free display number trying to connect to 6000+ ports"""
+ log.info("Attempting to find free port for X11 (Xephyr)")
+ retries = 20
+ display_number = 1
+ display_is_free = False
+
+ while not display_is_free and retries > 0:
+ lockstr = "/tmp/.X%d-lock" % display_number
+ if not os.path.exists(lockstr):
+ s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+ try:
+ s.connect(('127.0.0.1', 6000 + display_number))
+ s.close()
+ except socket.error:
+ display_is_free = True
+ break
+
+ display_number += 1
+ retries -= 1
+
+ if display_is_free:
+ log.info(
+ ' Found free port: #%s (%s)',
+ display_number, display_number+6000
+ )
+ return display_number
+ else:
+ logging.error('Cannot find a free display.')
+ sys.exit(0)
+
+def _start_xephyr(dpi=None):
+ display = _get_display_number()
+ log.info('Starting the Xephyr nested X display on display %s', display)
cmd = [ 'Xephyr' ]
cmd.append(':%d' % display)
@@ -56,25 +88,6 @@ def _run_xephyr(display, dpi):
os.environ['DISPLAY'] = ":%d" % (display)
os.environ['SUGAR_EMULATOR_PID'] = str(pid)
-def _check_xephyr(display):
- result = subprocess.call(['xdpyinfo', '-display', ':%d' % display],
- stdout=open(os.devnull, "w"),
- stderr=open(os.devnull, "w"))
- return result == 0
-
-def _start_xephyr(dpi=None):
- for display in range(100, 110):
- if not _check_xephyr(display):
- _run_xephyr(display, dpi)
-
- tries = 10
- while tries > 0:
- if _check_xephyr(display):
- return
- else:
- tries -= 1
- time.sleep(0.1)
-
def _start_matchbox():
log.info('Starting the matchbox window manager')
cmd = ['matchbox-window-manager']
diff --git a/src/hardware/keydialog.py b/src/hardware/keydialog.py
index 8c8c36a..92f6776 100644
--- a/src/hardware/keydialog.py
+++ b/src/hardware/keydialog.py
@@ -206,7 +206,7 @@ class WEPKeyDialog(KeyDialog):
def create_security(self):
(we_cipher, key, auth_alg) = self._get_security()
- from hardware.nminfo import Security
+ from nminfo import Security
return Security.new_from_args(we_cipher, (key, auth_alg))
def _update_response_sensitivity(self, ignored=None):
@@ -298,7 +298,7 @@ class WPAKeyDialog(KeyDialog):
def create_security(self):
(we_cipher, key, wpa_ver) = self._get_security()
- from hardware.nminfo import Security
+ from nminfo import Security
return Security.new_from_args(we_cipher,
(key, wpa_ver, IW_AUTH_KEY_MGMT_PSK))
diff --git a/src/hardware/nminfo.py b/src/hardware/nminfo.py
index a703ff6..e561ff1 100644
--- a/src/hardware/nminfo.py
+++ b/src/hardware/nminfo.py
@@ -1,3 +1,5 @@
+# vi: ts=4 ai noet
+#
# Copyright (C) 2006-2007 Red Hat, Inc.
#
# This program is free software; you can redistribute it and/or modify
@@ -14,20 +16,19 @@
# along with this program; if not, write to the Free Software
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+import dbus
+import dbus.service
import time
import os
import binascii
import ConfigParser
import logging
+import nmclient
+import keydialog
import gtk
-import dbus
-import dbus.service
-
from sugar import env
-from hardware import keydialog
-
IW_AUTH_KEY_MGMT_802_1X = 0x1
IW_AUTH_KEY_MGMT_PSK = 0x2
@@ -483,8 +484,6 @@ class NMInfo(object):
def get_key_for_network(self, dev_op, net_op, ssid, attempt,
new_key, async_cb, async_err_cb):
- from hardware import nmclient
-
if not isinstance(ssid, unicode):
raise ValueError("Invalid arguments; ssid must be unicode.")
if self._allowed_networks.has_key(ssid) and not new_key:
diff --git a/src/intro/Makefile.am b/src/intro/Makefile.am
index 025f4e6..3b92ea0 100644
--- a/src/intro/Makefile.am
+++ b/src/intro/Makefile.am
@@ -3,8 +3,8 @@ image_DATA = default-picture.png
EXTRA_DIST = $(conf_DATA) $(image_DATA)
sugardir = $(pkgdatadir)/shell/intro
-sugar_PYTHON = \
- __init__.py \
- colorpicker.py \
- glive.py \
- window.py
+sugar_PYTHON = \
+ __init__.py \
+ colorpicker.py \
+ intro.py \
+ glive.py
diff --git a/src/intro/window.py b/src/intro/intro.py
index fd8e00c..342ce1d 100644
--- a/src/intro/window.py
+++ b/src/intro/intro.py
@@ -15,51 +15,23 @@
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
import os
-import logging
from gettext import gettext as _
import gtk
import gobject
import hippo
+import logging
from sugar import env
from sugar.graphics import style
from sugar.graphics.icon import Icon
from sugar.graphics.entry import CanvasEntry
-from sugar.graphics.xocolor import XoColor
from sugar.profile import get_profile
-from intro import colorpicker
+import colorpicker
_BACKGROUND_COLOR = style.COLOR_WHITE
-def create_profile(name, color=None, pixbuf=None):
- if not pixbuf:
- path = os.path.join(os.path.dirname(__file__), 'default-picture.png')
- pixbuf = gtk.gdk.pixbuf_new_from_file(path)
-
- if not color:
- color = XoColor()
-
- icon_path = os.path.join(env.get_profile_path(), "buddy-icon.jpg")
- pixbuf.save(icon_path, "jpeg", {"quality":"85"})
-
- profile = get_profile()
- profile.nick_name = name
- profile.color = color
- profile.save()
-
- # Generate keypair
- import commands
- keypath = os.path.join(env.get_profile_path(), "owner.key")
- if not os.path.isfile(keypath):
- cmd = "ssh-keygen -q -t dsa -f %s -C '' -N ''" % keypath
- (s, o) = commands.getstatusoutput(cmd)
- if s != 0:
- logging.error("Could not generate key pair: %d %s" % (s, o))
- else:
- logging.error("Keypair exists, skip generation.")
-
class _Page(hippo.CanvasBox):
__gproperties__ = {
'valid' : (bool, None, None, False,
@@ -138,7 +110,8 @@ class _ColorPage(_Page):
class _IntroBox(hippo.CanvasBox):
__gsignals__ = {
'done': (gobject.SIGNAL_RUN_FIRST, gobject.TYPE_NONE,
- ([gobject.TYPE_PYOBJECT, gobject.TYPE_PYOBJECT]))
+ ([gobject.TYPE_PYOBJECT, gobject.TYPE_PYOBJECT,
+ gobject.TYPE_PYOBJECT]))
}
PAGE_NAME = 0
@@ -233,10 +206,12 @@ class _IntroBox(hippo.CanvasBox):
self.done()
def done(self):
+ path = os.path.join(os.path.dirname(__file__), 'default-picture.png')
+ pixbuf = gtk.gdk.pixbuf_new_from_file(path)
name = self._name_page.get_name()
color = self._color_page.get_color()
- self.emit('done', name, color)
+ self.emit('done', pixbuf, name, color)
class IntroWindow(gtk.Window):
def __init__(self):
@@ -251,14 +226,32 @@ class IntroWindow(gtk.Window):
self._canvas.show()
self.connect('key-press-event', self.__key_press_cb)
- def _done_cb(self, box, name, color):
+ def _done_cb(self, box, pixbuf, name, color):
self.hide()
- gobject.idle_add(self._create_profile_cb, name, color)
+ gobject.idle_add(self._create_profile, pixbuf, name, color)
+
+ def _create_profile(self, pixbuf, name, color):
+ # Save the buddy icon
+ icon_path = os.path.join(env.get_profile_path(), "buddy-icon.jpg")
+ pixbuf.save(icon_path, "jpeg", {"quality":"85"})
+
+ profile = get_profile()
+ profile.nick_name = name
+ profile.color = color
+ profile.save()
+
+ # Generate keypair
+ import commands
+ keypath = os.path.join(env.get_profile_path(), "owner.key")
+ if not os.path.isfile(keypath):
+ cmd = "ssh-keygen -q -t dsa -f %s -C '' -N ''" % keypath
+ (s, o) = commands.getstatusoutput(cmd)
+ if s != 0:
+ logging.error("Could not generate key pair: %d %s" % (s, o))
+ else:
+ logging.error("Keypair exists, skip generation.")
- def _create_profile_cb(self, name, color):
- create_profile(name, color)
gtk.main_quit()
-
return False
def __key_press_cb(self, widget, event):
diff --git a/src/logsmanager.py b/src/logsmanager.py
index 9360211..f0fa981 100644
--- a/src/logsmanager.py
+++ b/src/logsmanager.py
@@ -20,6 +20,7 @@ import time
from sugar import env
_MAX_BACKUP_DIRS = 3
+"""The maximum number of "old" log directories we should keep around."""
def setup():
"""Clean up the log directory, moving old logs into a numbered backup
diff --git a/src/main.py b/src/main.py
index c0ecce1..b37d75c 100644
--- a/src/main.py
+++ b/src/main.py
@@ -18,6 +18,10 @@ import os
import gettext
import logging
+# HACK we need to import numpy before gtk otherwise we traceback in
+# some locales. See http://dev.laptop.org/ticket/5559.
+import numpy
+
import pygtk
pygtk.require('2.0')
import gtk
@@ -31,8 +35,7 @@ from sugar.profile import get_profile
import view.Shell
from shellservice import ShellService
from hardware import hardwaremanager
-from intro.window import IntroWindow
-from intro.window import create_profile
+from intro import intro
from session import get_session_manager
import logsmanager
import config
@@ -110,12 +113,9 @@ def main():
# Do initial setup if needed
if not get_profile().is_valid():
- if 'SUGAR_PROFILE_NAME' in os.environ:
- create_profile(os.environ['SUGAR_PROFILE_NAME'])
- else:
- win = IntroWindow()
- win.show_all()
- gtk.main()
+ win = intro.IntroWindow()
+ win.show_all()
+ gtk.main()
# set timezone
if os.environ.has_key('TZ'):
diff --git a/src/model/MeshModel.py b/src/model/MeshModel.py
index 2f77d01..fa33035 100644
--- a/src/model/MeshModel.py
+++ b/src/model/MeshModel.py
@@ -169,7 +169,7 @@ class MeshModel(gobject.GObject):
return self._buddies.values()
def _buddy_activity_changed_cb(self, model, cur_activity):
- if not self._buddies.has_key(model.get_buddy().object_path()):
+ if not self._buddies.has_key(model.get_key()):
return
if cur_activity and self._activities.has_key(cur_activity.props.id):
activity_model = self._activities[cur_activity.props.id]
@@ -178,13 +178,13 @@ class MeshModel(gobject.GObject):
self.emit('buddy-moved', model, None)
def _buddy_appeared_cb(self, pservice, buddy):
- if self._buddies.has_key(buddy.object_path()):
+ if self._buddies.has_key(buddy.props.key):
return
model = BuddyModel(buddy=buddy)
model.connect('current-activity-changed',
self._buddy_activity_changed_cb)
- self._buddies[buddy.object_path()] = model
+ self._buddies[buddy.props.key] = model
self.emit('buddy-added', model)
cur_activity = buddy.props.current_activity
@@ -192,10 +192,10 @@ class MeshModel(gobject.GObject):
self._buddy_activity_changed_cb(model, cur_activity)
def _buddy_disappeared_cb(self, pservice, buddy):
- if not self._buddies.has_key(buddy.object_path()):
+ if not self._buddies.has_key(buddy.props.key):
return
- self.emit('buddy-removed', self._buddies[buddy.object_path()])
- del self._buddies[buddy.object_path()]
+ self.emit('buddy-removed', self._buddies[buddy.props.key])
+ del self._buddies[buddy.props.key]
def _activity_appeared_cb(self, pservice, act):
self._check_activity(act)
@@ -225,9 +225,9 @@ class MeshModel(gobject.GObject):
for buddy in self._pservice.get_buddies():
cur_activity = buddy.props.current_activity
- object_path = buddy.object_path()
- if cur_activity == activity and object_path in self._buddies:
- buddy_model = self._buddies[object_path]
+ key = buddy.props.key
+ if cur_activity == activity and self._buddies.has_key(key):
+ buddy_model = self._buddies[key]
self.emit('buddy-moved', buddy_model, model)
def _activity_disappeared_cb(self, pservice, act):
diff --git a/src/model/homemodel.py b/src/model/homemodel.py
index 49f2a23..8267584 100644
--- a/src/model/homemodel.py
+++ b/src/model/homemodel.py
@@ -20,7 +20,7 @@ import gobject
import wnck
from sugar import wm
-from sugar.activity import get_registry
+from sugar import activity
from model.homeactivity import HomeActivity
@@ -161,7 +161,7 @@ class HomeModel(gobject.GObject):
service_name = wm.get_bundle_id(window)
if service_name:
- registry = get_registry()
+ registry = activity.get_registry()
activity_info = registry.get_activity(service_name)
else:
activity_info = None
@@ -244,7 +244,7 @@ class HomeModel(gobject.GObject):
logging.error('Model for window %d does not exist.' % xid)
def notify_launch(self, activity_id, service_name):
- registry = get_registry()
+ registry = activity.get_registry()
activity_info = registry.get_activity(service_name)
if not activity_info:
raise ValueError("Activity service name '%s'" \
diff --git a/src/uicheck.py b/src/uicheck.py
deleted file mode 100644
index 105c014..0000000
--- a/src/uicheck.py
+++ /dev/null
@@ -1,83 +0,0 @@
-# Copyright (C) 2008, Red Hat, Inc.
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License as published by
-# the Free Software Foundation; either version 2 of the License, or
-# (at your option) any later version.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program; if not, write to the Free Software
-# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
-
-import sys
-import time
-
-import gobject
-import gtk
-import wnck
-
-checks_queue = []
-checks_failed = []
-checks_succeeded = []
-
-class Check(object):
- def __init__(self):
- self.succeeded = False
- self.start_time = None
- self.max_time = None
- self.timeout = None
-
- def start(self):
- self.start_time = time.time()
-
- def get_failed(self):
- if self.max_time and self.start_time:
- if time.time() - self.start_time > self.max_time:
- return True
- return False
-
- failed = property(get_failed)
-
-class ShellCheck(Check):
- def start(self):
- Check.start(self)
-
- self.max_time = 10
-
- screen = wnck.screen_get_default()
- screen.connect('window-opened', self._window_opened_cb)
-
- def _window_opened_cb(self, screen, window):
- if window.get_window_type() == wnck.WINDOW_DESKTOP:
- self.succeeded = True
-
-def _timeout_cb():
- if checks_queue[0].failed:
- checks_failed.append(checks_queue.pop(0))
- elif checks_queue[0].succeeded:
- checks_succeeded.append(checks_queue.pop(0))
- else:
- return True
-
- if len(checks_queue) > 0:
- checks_queue[0].start()
- else:
- gtk.main_quit()
-
- return True
-
-def main():
- checks_queue.append(ShellCheck())
-
- checks_queue[0].start()
- gobject.timeout_add(500, _timeout_cb)
-
- gtk.main()
-
- if len(checks_failed) > 0:
- sys.exit(1)
diff --git a/src/view/ActivityHost.py b/src/view/ActivityHost.py
index cf68f26..9f37c96 100644
--- a/src/view/ActivityHost.py
+++ b/src/view/ActivityHost.py
@@ -17,7 +17,7 @@
import gtk
import logging
-from view import OverlayWindow
+import OverlayWindow
class ActivityHost:
def __init__(self, model):
diff --git a/src/view/Shell.py b/src/view/Shell.py
index 514b500..146889b 100644
--- a/src/view/Shell.py
+++ b/src/view/Shell.py
@@ -15,6 +15,7 @@
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
from gettext import gettext as _
+from sets import Set
import logging
import tempfile
import os
diff --git a/src/view/devices/network/Makefile.am b/src/view/devices/network/Makefile.am
index 518362a..0d215f0 100644
--- a/src/view/devices/network/Makefile.am
+++ b/src/view/devices/network/Makefile.am
@@ -2,4 +2,5 @@ sugardir = $(pkgdatadir)/shell/view/devices/network
sugar_PYTHON = \
__init__.py \
mesh.py \
+ wired.py \
wireless.py
diff --git a/src/view/devices/network/wired.py b/src/view/devices/network/wired.py
new file mode 100644
index 0000000..6843e0d
--- /dev/null
+++ b/src/view/devices/network/wired.py
@@ -0,0 +1,25 @@
+# Copyright (C) 2006-2007, Red Hat, Inc.
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License as published by
+# the Free Software Foundation; either version 2 of the License, or
+# (at your option) any later version.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program; if not, write to the Free Software
+# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
+
+from view.devices import deviceview
+
+class DeviceView(deviceview.DeviceView):
+
+ FRAME_POSITION_RELATIVE = 300
+
+ def __init__(self, model):
+ deviceview.DeviceView.__init__(self, model)
+ self.props.icon_name = 'network-wired'
diff --git a/src/view/devices/speaker.py b/src/view/devices/speaker.py
index 818ba9a..df4995c 100644
--- a/src/view/devices/speaker.py
+++ b/src/view/devices/speaker.py
@@ -49,9 +49,6 @@ class DeviceView(TrayIcon):
model.connect('notify::muted', self.__speaker_status_changed_cb)
self.connect('expose-event', self.__expose_event_cb)
- self._icon_widget.connect('button-press-event',
- self.__update_mute_status)
-
self._update_info()
def _update_info(self):
@@ -67,9 +64,6 @@ class DeviceView(TrayIcon):
self.icon.props.icon_name = get_icon_state(name, current_level, step=-1)
self.icon.props.xo_color = xo_color
- def __update_mute_status(self, *args):
- self._model.props.muted = not self._model.props.muted
-
def __expose_event_cb(self, *args):
self._update_info()
diff --git a/src/view/home/MeshBox.py b/src/view/home/MeshBox.py
index 684ae13..c2b4efd 100644
--- a/src/view/home/MeshBox.py
+++ b/src/view/home/MeshBox.py
@@ -556,22 +556,22 @@ class MeshBox(gtk.VBox):
if hasattr(icon, 'set_filter'):
icon.set_filter(self._query)
- self._buddies[buddy_model.get_buddy().object_path()] = icon
+ self._buddies[buddy_model.get_key()] = icon
def _remove_alone_buddy(self, buddy_model):
- icon = self._buddies[buddy_model.get_buddy().object_path()]
+ icon = self._buddies[buddy_model.get_key()]
self._layout.remove(icon)
- del self._buddies[buddy_model.get_buddy().object_path()]
+ del self._buddies[buddy_model.get_key()]
icon.destroy()
def _remove_buddy(self, buddy_model):
- object_path = buddy_model.get_buddy().object_path()
- if self._buddies.has_key(object_path):
+ key = buddy_model.get_key()
+ if self._buddies.has_key(key):
self._remove_alone_buddy(buddy_model)
else:
for activity in self._activities.values():
- if activity.has_buddy_icon(object_path):
- activity.remove_buddy_icon(object_path)
+ if activity.has_buddy_icon(key):
+ activity.remove_buddy_icon(key)
def _move_buddy(self, buddy_model, activity_model):
self._remove_buddy(buddy_model)
@@ -582,7 +582,7 @@ class MeshBox(gtk.VBox):
activity = self._activities[activity_model.get_id()]
icon = BuddyIcon(buddy_model, style.STANDARD_ICON_SIZE)
- activity.add_buddy_icon(buddy_model.get_buddy().object_path(), icon)
+ activity.add_buddy_icon(buddy_model.get_key(), icon)
if hasattr(icon, 'set_filter'):
icon.set_filter(self._query)
diff --git a/src/view/home/activitieslist.py b/src/view/home/activitieslist.py
index 720eb2e..2f0860c 100644
--- a/src/view/home/activitieslist.py
+++ b/src/view/home/activitieslist.py
@@ -256,16 +256,21 @@ class ActivityEntry(hippo.CanvasBox, hippo.CanvasItem):
return self._title.lower().find(query) > -1
class FavoriteIcon(CanvasIcon):
+ __gproperties__ = {
+ 'favorite' : (bool, None, None, False,
+ gobject.PARAM_READWRITE)
+ }
+
def __init__(self, favorite):
CanvasIcon.__init__(self, icon_name='emblem-favorite',
box_width=style.GRID_CELL_SIZE*3/5,
size=style.SMALL_ICON_SIZE)
self._favorite = None
- self.set_favorite(favorite)
+ self._set_favorite(favorite)
self.connect('button-release-event', self.__release_event_cb)
self.connect('motion-notify-event', self.__motion_notify_event_cb)
- def set_favorite(self, favorite):
+ def _set_favorite(self, favorite):
if favorite == self._favorite:
return
@@ -276,11 +281,17 @@ class FavoriteIcon(CanvasIcon):
self.props.stroke_color = style.COLOR_BUTTON_GREY.get_svg()
self.props.fill_color = style.COLOR_WHITE.get_svg()
- def get_favorite(self):
- return self._favorite
+ def do_set_property(self, pspec, value):
+ if pspec.name == 'favorite':
+ self._set_favorite(value)
+ else:
+ CanvasIcon.do_set_property(self, pspec, value)
- favorite = gobject.property(
- type=bool, default=False, getter=get_favorite, setter=set_favorite)
+ def do_get_property(self, pspec):
+ if pspec.name == 'favorite':
+ return self._favorite
+ else:
+ return CanvasIcon.do_get_property(self, pspec)
def __release_event_cb(self, icon, event):
self.props.favorite = not self.props.favorite
diff --git a/src/view/home/favoritesview.py b/src/view/home/favoritesview.py
index 530026c..b549b12 100644
--- a/src/view/home/favoritesview.py
+++ b/src/view/home/favoritesview.py
@@ -36,6 +36,7 @@ from view.palettes import CurrentActivityPalette, ActivityPalette
from view.home.MyIcon import MyIcon
from view.home import favoriteslayout
from model import shellmodel
+from model.shellmodel import ShellModel
from hardware import schoolserver
from hardware.schoolserver import RegisterError
from controlpanel.gui import ControlPanel
@@ -287,8 +288,7 @@ class FavoritesView(hippo.Canvas):
alert.props.msg = _('%s') % e
else:
alert.props.title = _('Registration Successful')
- alert.props.msg = _('You are now registered ' \
- 'with your school server.')
+ alert.props.msg = _('You are now registered with your school server.')
palette = self._my_icon.get_palette()
palette.menu.remove(menuitem)
diff --git a/src/view/home/grid.py b/src/view/home/grid.py
index ab4927f..abea706 100644
--- a/src/view/home/grid.py
+++ b/src/view/home/grid.py
@@ -153,7 +153,7 @@ class Grid(gobject.GObject):
return weight
def __solve_collisions_cb(self):
- for i_ in range(_MAX_COLLISIONS_PER_REFRESH):
+ for i in range(_MAX_COLLISIONS_PER_REFRESH):
collision = self._collisions.pop(0)
old_rect = self._child_rects[collision]
diff --git a/src/view/pulsingicon.py b/src/view/pulsingicon.py
index 499ae99..c733043 100644
--- a/src/view/pulsingicon.py
+++ b/src/view/pulsingicon.py
@@ -24,129 +24,126 @@ from sugar.graphics.style import Color
_INTERVAL = 100
_STEP = math.pi / 10 # must be a fraction of pi, for clean caching
-class Pulser(object):
- def __init__(self, icon):
- self._pulse_hid = None
- self._icon = icon
- self._level = 0
- self._phase = 0
-
- def start(self, restart=False):
- if restart:
- self._phase = 0
- if self._pulse_hid is None:
- self._pulse_hid = gobject.timeout_add(_INTERVAL, self.__pulse_cb)
-
- def stop(self):
- if self._pulse_hid is not None:
- gobject.source_remove(self._pulse_hid)
- self._pulse_hid = None
- self._icon.xo_color = self._icon.base_color
-
- def update(self):
- if self._icon.pulsing:
- base_color = self._icon.base_color
- pulse_color = self._icon.pulse_color
-
- base_stroke = self._get_as_rgba(base_color.get_stroke_color())
- pulse_stroke = self._get_as_rgba(pulse_color.get_stroke_color())
- base_fill = self._get_as_rgba(base_color.get_fill_color())
- pulse_fill = self._get_as_rgba(pulse_color.get_fill_color())
-
- self._icon.stroke_color = \
- self._get_color(base_stroke, pulse_stroke).get_svg()
- self._icon.fill_color = \
- self._get_color(base_fill, pulse_fill).get_svg()
- else:
- self._icon.xo_color = self._icon.base_color
-
- def _get_as_rgba(self, html_color):
- if html_color == 'none':
- return Color('#FFFFFF', alpha=1.0).get_rgba()
- else:
- return Color(html_color).get_rgba()
-
- def _get_color(self, orig_color, target_color):
- next_point = (orig_color[0] +
- self._level * (target_color[0] - orig_color[0]),
- orig_color[1] +
- self._level * (target_color[1] - orig_color[1]),
- orig_color[2] +
- self._level * (target_color[2] - orig_color[2]))
-
- return Color('#%02x%02x%02x' % (int(next_point[0] * 255),
- int(next_point[1] * 255),
- int(next_point[2] * 255)))
-
- def __pulse_cb(self):
- self._phase += _STEP
- self._level = (math.sin(self._phase) + 1) / 2
- self.update()
-
- return True
+def _get_as_rgba(self, html_color):
+ if html_color == 'none':
+ return Color('#FFFFFF', alpha=1.0).get_rgba()
+ else:
+ return Color(html_color).get_rgba()
+
+def _update_colors(self):
+ if self._pulsing:
+ base_stroke = self._get_as_rgba(self._base_color.get_stroke_color())
+ pulse_stroke = self._get_as_rgba(self._pulse_color.get_stroke_color())
+ base_fill = self._get_as_rgba(self._base_color.get_fill_color())
+ pulse_fill = self._get_as_rgba(self._pulse_color.get_fill_color())
+
+ self.props.stroke_color = \
+ self._get_color(base_stroke, pulse_stroke).get_svg()
+ self.props.fill_color = \
+ self._get_color(base_fill, pulse_fill).get_svg()
+ else:
+ self.props.xo_color = self._base_color
+
+def _get_color(self, orig_color, target_color):
+ next_point = (orig_color[0] +
+ self._level * (target_color[0] - orig_color[0]),
+ orig_color[1] +
+ self._level * (target_color[1] - orig_color[1]),
+ orig_color[2] +
+ self._level * (target_color[2] - orig_color[2]))
+ return Color('#%02x%02x%02x' % (int(next_point[0] * 255),
+ int(next_point[1] * 255),
+ int(next_point[2] * 255)))
class PulsingIcon(Icon):
__gtype_name__ = 'SugarPulsingIcon'
+ __gproperties__ = {
+ 'base-color' : (object, None, None, gobject.PARAM_READWRITE),
+ 'pulse-color' : (object, None, None, gobject.PARAM_READWRITE),
+ 'pulsing' : (bool, None, None, False, gobject.PARAM_READWRITE),
+ 'paused' : (bool, None, None, False, gobject.PARAM_READWRITE)
+ }
+
def __init__(self, **kwargs):
- self._pulser = Pulser(self)
self._base_color = None
self._pulse_color = None
+ self._pulse_hid = None
self._paused = False
self._pulsing = False
+ self._level = 0
+ self._phase = 0
Icon.__init__(self, **kwargs)
self._palette = None
self.connect('destroy', self.__destroy_cb)
- def set_pulse_color(self, pulse_color):
- self._pulse_color = pulse_color
- self._pulser.update()
-
- def get_pulse_color(self):
- return self._pulse_color
+ def __destroy_cb(self, icon):
+ if self._palette is not None:
+ self._palette.destroy()
- pulse_color = gobject.property(
- type=object, getter=get_pulse_color, setter=set_pulse_color)
+ # Hack for sharing code between CanvasPulsingIcon and PulsingIcon
+ _get_as_rgba = _get_as_rgba
+ _update_colors = _update_colors
+ _get_color = _get_color
- def set_base_color(self, base_color):
- self._base_color = base_color
- self._pulser.update()
+ def _start_pulsing(self, restart=False):
+ if restart:
+ self._phase = 0
+ if self._pulse_hid is None:
+ self._pulse_hid = gobject.timeout_add(_INTERVAL, self.__pulse_cb)
- def get_base_color(self):
- return self._base_color
+ def _stop_pulsing(self):
+ if self._pulse_hid is not None:
+ gobject.source_remove(self._pulse_hid)
+ self._pulse_hid = None
+ self.props.xo_color = self._base_color
- base_color = gobject.property(
- type=object, getter=get_base_color, setter=set_base_color)
+ def __pulse_cb(self):
+ self._phase += _STEP
+ self._level = (math.sin(self._phase) + 1) / 2
+ self._update_colors()
- def set_paused(self, paused):
- self._paused = paused
+ return True
- if self._paused:
- self._pulser.stop()
+ def do_set_property(self, pspec, value):
+ if pspec.name == 'base-color':
+ if self._base_color != value:
+ self._base_color = value
+ self._update_colors()
+ elif pspec.name == 'pulse-color':
+ if self._pulse_color != value:
+ self._pulse_color = value
+ self._update_colors()
+ elif pspec.name == 'pulsing':
+ if self._pulsing != value:
+ self._pulsing = value
+ if self._pulsing:
+ self._start_pulsing(restart=True)
+ else:
+ self._stop_pulsing()
+ elif pspec.name == 'paused':
+ if self._paused != value:
+ self._paused = value
+ if self._paused:
+ self._stop_pulsing()
+ else:
+ self._start_pulsing(restart=False)
else:
- self._pulser.start(restart=False)
-
- def get_paused(self):
- return self._paused
-
- paused = gobject.property(
- type=bool, default=False, getter=get_paused, setter=set_paused)
-
- def set_pulsing(self, pulsing):
- self._pulsing = pulsing
-
- if self._pulsing:
- self._pulser.start(restart=True)
+ Icon.do_set_property(self, pspec, value)
+
+ def do_get_property(self, pspec):
+ if pspec.name == 'base-color':
+ return self._base_color
+ elif pspec.name == 'pulse-color':
+ return self._pulse_color
+ elif pspec.name == 'pulsing':
+ return self._pulsing
+ elif pspec.name == 'paused':
+ return self._paused
else:
- self._pulser.stop()
-
- def get_pulsing(self):
- return self._pulsing
-
- pulsing = gobject.property(
- type=bool, default=False, getter=get_pulsing, setter=set_pulsing)
+ return Icon.do_get_property(self, pspec)
def _get_palette(self):
return self._palette
@@ -158,66 +155,85 @@ class PulsingIcon(Icon):
palette = property(_get_palette, _set_palette)
- def __destroy_cb(self, icon):
- if self._palette is not None:
- self._palette.destroy()
-
class CanvasPulsingIcon(CanvasIcon):
__gtype_name__ = 'SugarCanvasPulsingIcon'
+ __gproperties__ = {
+ 'base-color' : (object, None, None, gobject.PARAM_WRITABLE),
+ 'pulse-color' : (object, None, None, gobject.PARAM_WRITABLE),
+ 'pulsing' : (bool, None, None, False, gobject.PARAM_WRITABLE),
+ 'paused' : (bool, None, None, False, gobject.PARAM_WRITABLE)
+ }
+
def __init__(self, **kwargs):
- self._pulser = Pulser(self)
self._base_color = None
self._pulse_color = None
+ self._pulse_hid = None
self._paused = False
self._pulsing = False
+ self._level = 0
+ self._phase = 0
CanvasIcon.__init__(self, **kwargs)
- def set_pulse_color(self, pulse_color):
- self._pulse_color = pulse_color
- self._pulser.update()
-
- def get_pulse_color(self):
- return self._pulse_color
+ # Hack for sharing code between CanvasPulsingIcon and PulsingIcon
+ _get_as_rgba = _get_as_rgba
+ _update_colors = _update_colors
+ _get_color = _get_color
- pulse_color = gobject.property(
- type=object, getter=get_pulse_color, setter=set_pulse_color)
-
- def set_base_color(self, base_color):
- self._base_color = base_color
- self._pulser.update()
+ def _start_pulsing(self, restart=False):
+ if restart:
+ self._phase = 0
+ if self._pulse_hid is None:
+ self._pulse_hid = gobject.timeout_add(_INTERVAL, self.__pulse_cb)
- def get_base_color(self):
- return self._base_color
+ def _stop_pulsing(self):
+ if self._pulse_hid is not None:
+ gobject.source_remove(self._pulse_hid)
+ self._pulse_hid = None
+ self.props.xo_color = self._base_color
- base_color = gobject.property(
- type=object, getter=get_base_color, setter=set_base_color)
+ def __pulse_cb(self):
+ self._phase += _STEP
+ self._level = (math.sin(self._phase) + 1) / 2
+ self._update_colors()
- def set_paused(self, paused):
- self._paused = paused
+ return True
- if self._paused:
- self._pulser.stop()
+ def do_set_property(self, pspec, value):
+ if pspec.name == 'base-color':
+ if self._base_color != value:
+ self._base_color = value
+ self._update_colors()
+ elif pspec.name == 'pulse-color':
+ if self._pulse_color != value:
+ self._pulse_color = value
+ self._update_colors()
+ elif pspec.name == 'pulsing':
+ if self._pulsing != value:
+ self._pulsing = value
+ if self._pulsing:
+ self._start_pulsing(restart=True)
+ else:
+ self._stop_pulsing()
+ elif pspec.name == 'paused':
+ if self._paused != value:
+ self._paused = value
+ if self._paused:
+ self._stop_pulsing()
+ else:
+ self._start_pulsing(restart=False)
else:
- self._pulser.start(restart=False)
-
- def get_paused(self):
- return self._paused
-
- paused = gobject.property(
- type=bool, default=False, getter=get_paused, setter=set_paused)
-
- def set_pulsing(self, pulsing):
- self._pulsing = pulsing
-
- if self._pulsing:
- self._pulser.start(restart=True)
+ CanvasIcon.do_set_property(self, pspec, value)
+
+ def do_get_property(self, pspec):
+ if pspec.name == 'base-color':
+ return self._base_color
+ elif pspec.name == 'pulse-color':
+ return self._pulse_color
+ elif pspec.name == 'pulsing':
+ return self._pulsing
+ elif pspec.name == 'paused':
+ return self._paused
else:
- self._pulser.stop()
-
- def get_pulsing(self):
- return self._pulsing
-
- pulsing = gobject.property(
- type=bool, default=False, getter=get_pulsing, setter=set_pulsing)
+ return CanvasIcon.do_get_property(self, pspec)