Hi Ariel,<div>This patch mix many changes, not only what the title say.</div><div>Please prepare a patch only with the code needed to implement this,</div><div>and I will review it.</div><div>If you want propose other changes, send it in different patches.</div>
<div>Thanks</div><div><br></div><div>Gonzalo</div><div><br><div class="gmail_quote">On Fri, Sep 14, 2012 at 12:31 PM, Ariel Calzada <span dir="ltr"><<a href="mailto:ariel.calzada@gmail.com" target="_blank">ariel.calzada@gmail.com</a>></span> wrote:<br>
<blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">From: Ariel Calzada <<a href="mailto:ariel@activitycentral.com">ariel@activitycentral.com</a>><br>
<br>
---<br>
 activity.py            |   88 +++++++++++++++++++++++++++++++++++++++++-------<br>
 activity/<a href="http://activity.info" target="_blank">activity.info</a> |    2 +-<br>
 cardlist.py            |    3 +-<br>
 createtoolbar.py       |    3 +-<br>
 game.py                |   13 +++++--<br>
 memorizetoolbar.py     |    5 +--<br>
 model.py               |   12 ++++++-<br>
 7 files changed, 105 insertions(+), 21 deletions(-)<br>
<br>
diff --git a/activity.py b/activity.py<br>
index 1fdf8ac..f967976 100644<br>
--- a/activity.py<br>
+++ b/activity.py<br>
@@ -35,9 +35,17 @@ import gtk<br>
 import telepathy<br>
 import telepathy.client<br>
<br>
-from sugar.activity.widgets import ActivityToolbarButton<br>
-from sugar.activity.widgets import StopButton<br>
-from sugar.graphics.toolbarbox import ToolbarBox<br>
+# Toolbars<br>
+try:<br>
+    from sugar.graphics.toolbarbox import ToolbarBox<br>
+    _have_toolbox = True<br>
+except ImportError:<br>
+    _have_toolbox = False<br>
+<br>
+if _have_toolbox:<br>
+    from sugar.activity.widgets import ActivityToolbarButton<br>
+    from sugar.activity.widgets import StopButton<br>
+<br>
 from sugar.graphics.toggletoolbutton import ToggleToolButton<br>
 from sugar.activity.activity import Activity<br>
 from sugar.presence import presenceservice<br>
@@ -53,6 +61,7 @@ import createtoolbar<br>
 import cardlist<br>
 import createcardpanel<br>
 import face<br>
+import time<br>
<br>
 SERVICE = 'org.laptop.Memorize'<br>
 IFACE = SERVICE<br>
@@ -79,8 +88,33 @@ class MemorizeActivity(Activity):<br>
         toolbar_box = ToolbarBox()<br>
         self.set_toolbar_box(toolbar_box)<br>
<br>
-        self.activity_button = ActivityToolbarButton(self)<br>
-        toolbar_box.toolbar.insert(self.activity_button, -1)<br>
+        if _have_toolbox:<br>
+            toolbar_box = ToolbarBox()<br>
+<br>
+            # Activity toolbar<br>
+            activity_button = ActivityToolbarButton(self)<br>
+            toolbar_box.toolbar.insert(activity_button, 0)<br>
+            activity_button.show()<br>
+<br>
+            self.set_toolbar_box(toolbar_box)<br>
+            toolbar_box.show()<br>
+<br>
+            # Save toolbar as attribute<br>
+            self._toolbar = toolbar_box.toolbar<br>
+<br>
+        else:<br>
+            # Use pre-0.86 toolbar design<br>
+            games_toolbar = gtk.Toolbar()<br>
+            toolbar_box = activity.ActivityToolbox(self)<br>
+<br>
+            self.set_toolbox(toolbar_box)<br>
+            toolbar_box.add_toolbar(_('Game'), games_toolbar)<br>
+            toolbar_box.show()<br>
+<br>
+            toolbar_box.set_current_toolbar(1)<br>
+<br>
+            # Save toolbar as attribute<br>
+            self._toolbar = games_toolbar<br>
<br>
         self._memorizeToolbarBuilder = \<br>
                 memorizetoolbar.MemorizeToolbarBuilder(self)<br>
@@ -95,18 +129,19 @@ class MemorizeActivity(Activity):<br>
         self._createToolbarBuilder = \<br>
             createtoolbar.CreateToolbarBuilder(self)<br>
<br>
-        separator = gtk.SeparatorToolItem()<br>
-        separator.set_expand(True)<br>
-        separator.set_draw(False)<br>
-        separator.set_size_request(0, -1)<br>
-        toolbar_box.toolbar.insert(separator, -1)<br>
+        if _have_toolbox:<br>
+            separator = gtk.SeparatorToolItem()<br>
+            separator.set_expand(True)<br>
+            separator.set_draw(False)<br>
+            separator.set_size_request(0, -1)<br>
+            self._toolbar.insert(separator, -1)<br>
<br>
-        toolbar_box.toolbar.insert(StopButton(self), -1)<br>
+            self._toolbar.insert(StopButton(self), -1)<br>
<br>
         # Play game mode<br>
         self.table = cardtable.CardTable()<br>
         self.scoreboard = scoreboard.Scoreboard()<br>
-        self.cardlist = cardlist.CardList()<br>
+        self.cardlist = cardlist.CardList(self)<br>
         self.createcardpanel = createcardpanel.CreateCardPanel()<br>
         self.cardlist.connect('pair-selected',<br>
                 self.createcardpanel.pair_selected)<br>
@@ -124,7 +159,7 @@ class MemorizeActivity(Activity):<br>
                 self.createcardpanel.clean)<br>
         self._createToolbarBuilder.connect('create_equal_pairs',<br>
                 self.change_equal_pairs)<br>
-        self.game = game.MemorizeGame()<br>
+        self.game = game.MemorizeGame(self)<br>
<br>
         self._edit_button.connect('toggled', self._change_mode_bt)<br>
<br>
@@ -207,6 +242,7 @@ class MemorizeActivity(Activity):<br>
             self.game.add_buddy(self.owner)<br>
         else:<br>
             self.game.add_buddy(self.owner)<br>
+<br>
         self.show_all()<br>
<br>
     def _change_mode_bt(self, button):<br>
@@ -228,12 +264,17 @@ class MemorizeActivity(Activity):<br>
                               self.metadata['title'], color)<br>
<br>
     def write_file(self, file_path):<br>
+        # Wait for graphics events finish<br>
+        self.flush_events()<br>
         logging.debug('WRITE_FILE is_demo %s', self.game.model.is_demo)<br>
+        # We want to save the game-image for demo games too !!!<br>
+        """<br>
         if self.game.model.is_demo:<br>
             # if is a demo game only want keep the metadata<br>
             self._jobject.set_file_path(None)<br>
             raise NotImplementedError<br>
             return<br>
+        """<br>
         if self.cardlist.pair_list_modified:<br>
             self.cardlist.update_model(self.game.model)<br>
<br>
@@ -282,6 +323,13 @@ class MemorizeActivity(Activity):<br>
         game_zip.close()<br>
         self.metadata['mime_type'] = 'application/x-memorize-project'<br>
<br>
+        # Store the game image as a string - that is simpler instead of<br>
+        # having to deal with the dbus-converted list.<br>
+        # When reading back, we use "eval" to convert the string into<br>
+        # the correct type ("list" in this case).<br>
+        self.metadata['saved_game_data_image'] = str(self.game.model.grid)<br>
+        self.metadata['size'] = int(self.game.model.data['size'])<br>
+<br>
     def _complete_close(self):<br>
         self._remove_temp_files()<br>
         Activity._complete_close(self)<br>
@@ -447,3 +495,17 @@ class MemorizeActivity(Activity):<br>
<br>
     def _cleanup_cb(self, data=None):<br>
         self.game.audio.stop()<br>
+<br>
+    def getToolbarBox(self):<br>
+        """ Get toolbar box<br>
+        """<br>
+        return self._toolbar<br>
+<br>
+    def flush_events(self):<br>
+        """ Wait for graphics events finish<br>
+        """<br>
+        gtk.gdk.threads_enter()<br>
+        while gtk.events_pending():<br>
+            gtk.main_iteration(True)<br>
+        gtk.gdk.flush()<br>
+        gtk.gdk.threads_leave()<br>
diff --git a/activity/<a href="http://activity.info" target="_blank">activity.info</a> b/activity/<a href="http://activity.info" target="_blank">activity.info</a><br>
index b68f210..fde320e 100644<br>
--- a/activity/<a href="http://activity.info" target="_blank">activity.info</a><br>
+++ b/activity/<a href="http://activity.info" target="_blank">activity.info</a><br>
@@ -3,7 +3,7 @@ name = Memorize<br>
 bundle_id = org.laptop.Memorize<br>
 exec = sugar-activity activity.MemorizeActivity<br>
 icon = activity-memorize<br>
-activity_version = 41<br>
+activity_version = 41.3<br>
 show_launcher = yes<br>
 mime_types = application/x-memorize-project;<br>
 license = GPLv2+<br>
diff --git a/cardlist.py b/cardlist.py<br>
index 6bc781c..65e44f1 100644<br>
--- a/cardlist.py<br>
+++ b/cardlist.py<br>
@@ -40,8 +40,9 @@ class CardList(gtk.EventBox):<br>
         'update-create-toolbar': (SIGNAL_RUN_FIRST, None, 3 * [TYPE_PYOBJECT]),<br>
     }<br>
<br>
-    def __init__(self):<br>
+    def __init__(self, activity_instance):<br>
         gtk.EventBox.__init__(self)<br>
+        self._activity_instance = activity_instance<br>
         self.pairs = []<br>
         self.current_pair = None<br>
         self.current_game_key = None<br>
diff --git a/createtoolbar.py b/createtoolbar.py<br>
index 49feaf7..91394f8 100644<br>
--- a/createtoolbar.py<br>
+++ b/createtoolbar.py<br>
@@ -40,7 +40,8 @@ class CreateToolbarBuilder(gobject.GObject):<br>
     def __init__(self, activity):<br>
         gobject.GObject.__init__(self)<br>
         self.activity = activity<br>
-        self.toolbar = self.activity.get_toolbar_box().toolbar<br>
+        #self.toolbar = self.activity.get_toolbar_box().toolbar<br>
+        self.toolbar = self.activity.getToolbarBox()<br>
<br>
         self._equal_pairs = ToggleToolButton('pair-non-equals')<br>
         self._equal_pairs.set_tooltip(_('Match different tiles'))<br>
diff --git a/game.py b/game.py<br>
index 5217f7c..ff90b48 100644<br>
--- a/game.py<br>
+++ b/game.py<br>
@@ -57,7 +57,7 @@ class MemorizeGame(GObject):<br>
         'change-turn': (SIGNAL_RUN_FIRST, None, [TYPE_PYOBJECT]),<br>
         }<br>
<br>
-    def __init__(self):<br>
+    def __init__(self, activity_instance):<br>
         gobject.GObject.__init__(self)<br>
         self.myself = None<br>
         self.players_score = {}<br>
@@ -70,7 +70,7 @@ class MemorizeGame(GObject):<br>
         self.messenger = None<br>
         self.sentitive = True<br>
<br>
-        self.model = Model()<br>
+        self.model = Model(activity_instance=activity_instance)<br>
         self.flip_block = False<br>
         self._flop_cards = None<br>
<br>
@@ -109,6 +109,15 @@ class MemorizeGame(GObject):<br>
         self.change_turn()<br>
         self.model.data['running'] = 'False'<br>
<br>
+        # Card 'state' is an aawesome field.<br>
+        # Its takes on the following values ::<br>
+        #<br>
+        # 0                              ==>    for flopped cards.<br>
+        #<br>
+        # 1                              ==>    for flipped unmatched cards<br>
+        #                                       (can be a maximum of 1 such card).<br>
+        #<br>
+        # <stroke_color>, <fill_color>   ==>    for flipped matched cards<br>
         for card in self.model.grid:<br>
             if card['state'] == '1':<br>
                 self.emit('flip-card', self.model.grid.index(card), False)<br>
diff --git a/memorizetoolbar.py b/memorizetoolbar.py<br>
index c7e4366..cc28e52 100644<br>
--- a/memorizetoolbar.py<br>
+++ b/memorizetoolbar.py<br>
@@ -52,7 +52,8 @@ class MemorizeToolbarBuilder(gobject.GObject):<br>
     def __init__(self, activity):<br>
         gobject.GObject.__init__(self)<br>
         self.activity = activity<br>
-        self.toolbar = self.activity.get_toolbar_box().toolbar<br>
+        #self.toolbar = self.activity.get_toolbar_box().toolbar<br>
+        self.toolbar = self.activity.getToolbarBox()<br>
         self.jobject = None<br>
<br>
         # Change demo games button<br>
@@ -126,7 +127,7 @@ class MemorizeToolbarBuilder(gobject.GObject):<br>
         self.emit('game_changed', game_file, game_size, 'demo', title, None)<br>
<br>
     def update_toolbar(self, widget, data, grid):<br>
-        size = data.get('size')<br>
+        size = str(data.get('size'))<br>
         self._size_combo.combo.handler_block(self.size_handle_id)<br>
         size_index = self._sizes.index(size + ' X ' + size)<br>
         self._size_combo.combo.set_active(int(size_index))<br>
diff --git a/model.py b/model.py<br>
index 2567ed2..16239c4 100644<br>
--- a/model.py<br>
+++ b/model.py<br>
@@ -100,11 +100,13 @@ class Model(object):<br>
     information.<br>
     '''<br>
<br>
-    def __init__(self, game_path=None):<br>
+    def __init__(self, game_path=None, activity_instance=None):<br>
         tmp_root = join(environ['SUGAR_ACTIVITY_ROOT'], 'instance')<br>
         self.temp_folder = tempfile.mkdtemp(dir=tmp_root)<br>
         chmod(self.temp_folder, 0777)<br>
+        self._saved_game_loaded = False<br>
<br>
+        self._activity_instance = activity_instance<br>
         self.data = {}<br>
<br>
         if game_path is None:<br>
@@ -366,6 +368,14 @@ class Model(object):<br>
             temp1.extend(temp2)<br>
             random.shuffle(temp1)<br>
         self.grid = temp1<br>
+<br>
+        if not self._saved_game_loaded:<br>
+            if self._activity_instance is not None:<br>
+                if 'saved_game_data_image' in self._activity_instance.metadata.keys():<br>
+                    self.grid = eval(self._activity_instance.metadata['saved_game_data_image'])<br>
+                    self.data['size'] = int(self._activity_instance.metadata['size'])<br>
+                    self._saved_game_loaded = True<br>
+<br>
         _logger.debug('Defgrid: grid( size=%s ): %s'<br>
                       % (self.data['size'], self.grid))<br>
         _logger.debug('Defgrid: data: %s', self.data)<br>
<span class="HOEnZb"><font color="#888888">--<br>
1.7.9.5<br>
<br>
</font></span></blockquote></div><br></div>