My recent interactions with the launcher have led me to frustration. I updated a number of tickets on the subject, and also created an aggragator to track them all (http://dev.laptop.org/ticket/8090). The attached patch is an attempt to solve nearly all of the known problems. Testing would be very much appreciated.
The only known issue I've found with this patch is that you can't click on the activity level button (in the Frame) while a launcher is the selected activity (though you can click on the launcher icon directly). Marco understands this issue, but feels we might be better off working in a fix separately, since it could be more invasive. Apart from that know bug, I believe that this new launcher yields expected behavior everywhere; if you disagree, or find other bugs, let me know! - Eben
diff --git a/src/model/homeactivity.py b/src/model/homeactivity.py index fa50932..34ebda3 100644 --- a/src/model/homeactivity.py +++ b/src/model/homeactivity.py @@ -73,9 +73,11 @@ class HomeActivity(gobject.GObject): dbus_interface="org.freedesktop.DBus") def set_window(self, window): - """An activity is 'launched' once we get its window.""" - if self._window or self._xid: - raise RuntimeError("Activity is already launched!") + """Set the window for the activity + + We allow resetting the window for an activity so that we + can replace the launcher once we get its real window. + """ if not window: raise ValueError("window must be valid") diff --git a/src/model/homemodel.py b/src/model/homemodel.py index 49f2a23..a35dcc9 100644 --- a/src/model/homemodel.py +++ b/src/model/homemodel.py @@ -175,8 +175,10 @@ class HomeModel(gobject.GObject): home_activity.set_window(window) - home_activity.props.launching = False - self.emit('launch-completed', home_activity) + # We only emit launch-completed if this is not a launcher window + if service_name: + home_activity.props.launching = False + self.emit('launch-completed', home_activity) if self._active_activity is None: self._set_active_activity(home_activity) diff --git a/src/view/Shell.py b/src/view/Shell.py index 514b500..77280ac 100644 --- a/src/view/Shell.py +++ b/src/view/Shell.py @@ -53,6 +53,7 @@ class Shell(gobject.GObject): self._model = shellmodel.get_instance() self._hosts = {} + self._launchers = {} self._screen = wnck.screen_get_default() self._screen_rotation = 0 @@ -63,8 +64,6 @@ class Shell(gobject.GObject): self.home_window = HomeWindow() self.home_window.show() - self._launch_window = LaunchWindow() - home_model = self._model.get_home() home_model.connect('launch-started', self.__launch_started_cb) home_model.connect('launch-failed', self.__launch_failed_cb) @@ -94,17 +93,24 @@ class Shell(gobject.GObject): def __launch_started_cb(self, home_model, home_activity): if home_activity.get_type() != 'org.laptop.JournalActivity': - self._launch_window.show() + launch_window = LaunchWindow(home_activity) + launch_window.show() + self._launchers[home_activity.get_activity_id()] = launch_window + self._model.set_zoom_level(shellmodel.ShellModel.ZOOM_ACTIVITY) def __launch_failed_cb(self, home_model, home_activity): - self._launch_window.hide() + launch_window = self._launchers[home_activity.get_activity_id()] + if launch_window: + launch_window.destroy() def __launch_completed_cb(self, home_model, home_activity): - self._launch_window.hide() - activity_host = ActivityHost(home_activity) self._hosts[activity_host.get_xid()] = activity_host + launch_window = self._launchers[home_activity.get_activity_id()] + if launch_window: + launch_window.destroy() + def _activity_removed_cb(self, home_model, home_activity): xid = home_activity.get_xid() if self._hosts.has_key(xid): diff --git a/src/view/launchwindow.py b/src/view/launchwindow.py index ee3ccfa..2c4d73a 100644 --- a/src/view/launchwindow.py +++ b/src/view/launchwindow.py @@ -19,6 +19,7 @@ import hippo import gobject import logging +from sugar import wm from sugar.graphics import style from sugar.graphics import animator from sugar.graphics.xocolor import XoColor @@ -27,14 +28,15 @@ from model import shellmodel from view.pulsingicon import CanvasPulsingIcon class LaunchWindow(hippo.CanvasWindow): - def __init__(self): + def __init__(self, home_activity): gobject.GObject.__init__( - self, type_hint=gtk.gdk.WINDOW_TYPE_HINT_SPLASHSCREEN) + self, type_hint=gtk.gdk.WINDOW_TYPE_HINT_NORMAL) - self._box = LaunchBox() + self._activity_id = home_activity.get_activity_id() + self._box = LaunchBox(home_activity) self.set_root(self._box) - self.connect('focus-out-event', self.__focus_out_event_cb) + self.connect('realize', self.__realize_cb) screen = gtk.gdk.screen_get_default() screen.connect('size-changed', self.__size_changed_cb) @@ -48,18 +50,21 @@ class LaunchWindow(hippo.CanvasWindow): def _update_size(self): self.resize(gtk.gdk.screen_width(), gtk.gdk.screen_height()) - def __focus_out_event_cb(self, widget, event): - self.hide() - + def __realize_cb(self, widget): + wm.set_activity_id(widget.window, str(self._activity_id)) + def __size_changed_cb(self, screen): self._update_size() class LaunchBox(hippo.CanvasBox): - def __init__(self): + def __init__(self, home_activity): gobject.GObject.__init__(self, orientation=hippo.ORIENTATION_VERTICAL, background_color=style.COLOR_WHITE.get_int()) - self._activity_icon = CanvasPulsingIcon() + self._home_activity = home_activity + self._activity_icon = CanvasPulsingIcon( + file_name=home_activity.get_icon_path(), + pulse_color=home_activity.get_icon_color()) self.append(self._activity_icon, hippo.PACK_EXPAND) # FIXME support non-xo colors in CanvasPulsingIcon @@ -72,14 +77,8 @@ class LaunchBox(hippo.CanvasBox): self._home = shellmodel.get_instance().get_home() self._home.connect('active-activity-changed', self.__active_activity_changed_cb) - self._home.connect('launch-failed', self.__launch_ended_cb) - self._home.connect('launch-completed', self.__launch_ended_cb) - - self._update_icon() def zoom_in(self): - logging.debug('zooming in to activity') - self._activity_icon.props.size = style.STANDARD_ICON_SIZE self._animator.remove_all() @@ -87,9 +86,6 @@ class LaunchBox(hippo.CanvasBox): style.STANDARD_ICON_SIZE, style.XLARGE_ICON_SIZE)) self._animator.start() - - logging.debug('starting pulse') - self._activity_icon.props.pulsing = True def suspend(self): @@ -98,25 +94,12 @@ class LaunchBox(hippo.CanvasBox): def resume(self): self._activity_icon.props.paused = False - def _update_icon(self): - activity = self._home.get_active_activity() - if activity is not None: - self._activity_icon.props.file_name = activity.get_icon_path() - self._activity_icon.props.pulse_color = activity.get_icon_color() - else: - self._activity_icon.props.file_name = None - - if activity is not None and activity.props.launching: + def __active_activity_changed_cb(self, model, activity): + if activity == self._home_activity: self.resume() else: self.suspend() - def __active_activity_changed_cb(self, model, activity): - self._update_icon() - - def __launch_ended_cb(self, model, activity): - self._update_icon() - class _Animation(animator.Animation): def __init__(self, icon, start_size, end_size): animator.Animation.__init__(self, 0.0, 1.0)
_______________________________________________ Sugar mailing list Sugar@lists.laptop.org http://lists.laptop.org/listinfo/sugar