pygtkmvc-users Mailing List for Pygtkmvc
Brought to you by:
cavada
You can subscribe to this list here.
2008 |
Jan
|
Feb
|
Mar
|
Apr
(2) |
May
|
Jun
|
Jul
(3) |
Aug
(8) |
Sep
(3) |
Oct
(3) |
Nov
|
Dec
|
---|---|---|---|---|---|---|---|---|---|---|---|---|
2009 |
Jan
|
Feb
|
Mar
(1) |
Apr
(1) |
May
(6) |
Jun
(4) |
Jul
(9) |
Aug
(2) |
Sep
(11) |
Oct
(6) |
Nov
(2) |
Dec
(16) |
2010 |
Jan
(3) |
Feb
(8) |
Mar
(13) |
Apr
(13) |
May
(6) |
Jun
(2) |
Jul
(5) |
Aug
(3) |
Sep
(6) |
Oct
(7) |
Nov
|
Dec
(4) |
2011 |
Jan
|
Feb
|
Mar
(19) |
Apr
|
May
|
Jun
|
Jul
|
Aug
(1) |
Sep
|
Oct
|
Nov
(3) |
Dec
|
2012 |
Jan
|
Feb
|
Mar
|
Apr
|
May
(10) |
Jun
|
Jul
|
Aug
|
Sep
|
Oct
|
Nov
|
Dec
|
2013 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
(3) |
Aug
|
Sep
(1) |
Oct
|
Nov
|
Dec
|
2014 |
Jan
|
Feb
|
Mar
|
Apr
|
May
|
Jun
|
Jul
|
Aug
(7) |
Sep
|
Oct
|
Nov
|
Dec
|
From: Tobias W. <to...@po...> - 2014-08-10 18:47:32
|
On 10.08.2014, at 13:29, Philipp Burch <ph...@hb...> wrote: > self._otherObserver.observe(self._valueChangedDynObs, 'value', assign = True) I can't think of why this would be useful. If it really works under some circumstances, that's by accident. X.observe is only for methods of X. > #self._otherObserver.observe(valueChangedDynObsGlob, > # 'value', assign = True) That's a function, not a method, even if the first argument is named self. > Please don't get me wrong, I don't think that those are critical limitations. MVC is a pattern to help you write reusable components. That it prevents one object from reaching into another, and globals from reaching everywhere, is not a limitation but its primary feature. |
From: Philipp B. <ph...@hb...> - 2014-08-10 18:40:27
|
Hi Tobias! On 10.08.2014 20:23, to...@ce... wrote: > On 10.08.2014, at 13:29, Philipp Burch <ph...@hb...> wrote: > >> self._otherObserver.observe(self._valueChangedDynObs, 'value', assign = True) > > I can't think of why this would be useful. If it really works under some circumstances, that's by accident. X.observe is only for methods of X. > >> #self._otherObserver.observe(valueChangedDynObsGlob, >> # 'value', assign = True) > > That's a function, not a method, even if the first argument is named self. > >> Please don't get me wrong, I don't think that those are critical limitations. > > > MVC is a pattern to help you write reusable components. That it prevents one object from reaching into another, and globals from reaching everywhere, is not a limitation but its primary feature. Okok, got your point. I just shouldn't do such fancy things. A "reusable component" does not necessarily consist of a single class, though. I would've needed less time to figure out what I'm doing wrong if there had been an explicit hint in the docs or an assertion that really prevents that case instead of failing somewhere else. So maybe this post will at least save someone else who's seeing the same behaviour some time. Oh and just in case: I crafted this example code to make clear what I mean after I discovered what's going on, this is obviously not exactly my use case. Kind regards, Philipp |
From: <to...@ce...> - 2014-08-10 18:23:17
|
On 10.08.2014, at 13:29, Philipp Burch <ph...@hb...> wrote: > self._otherObserver.observe(self._valueChangedDynObs, 'value', assign = True) I can't think of why this would be useful. If it really works under some circumstances, that's by accident. X.observe is only for methods of X. > #self._otherObserver.observe(valueChangedDynObsGlob, > # 'value', assign = True) That's a function, not a method, even if the first argument is named self. > Please don't get me wrong, I don't think that those are critical limitations. MVC is a pattern to help you write reusable components. That it prevents one object from reaching into another, and globals from reaching everywhere, is not a limitation but its primary feature. |
From: Philipp B. <ph...@hb...> - 2014-08-10 11:29:37
|
Greetings, seems like I don't use gtkmvc in a usual way, as I've hit an assertion failure again... This time it concerns the use of a dynamic observer that has its notification function registered dynamically and not with a decorator. Check the following example: -------- 8< ---------- 8< ----------- 8< ----------- #!/usr/bin/python # Tests the behaviour of dynamically registered notification functions # for observers. import gtkmvc def valueChangedDynObsGlob(self, model, prop_name, info): print 'dynamically, other observer, global function: new = ', info.new # When deriving from Model instead of ModelMT, EFFECT 1 goes away and the # dynamically registered other observer works independently of the model # observing itself or not. class MyModel(gtkmvc.ModelMT): __observables__ = [ 'value' ] value = 0 def __init__(self): gtkmvc.ModelMT.__init__(self) self.value = 0 # Observe model from ourselves dynamically. # EFFECT 1: # If this is uncommented, also the dynamically registered other # observer works. #self.observe(self._valueChangedDynSelf, # 'value', assign = True) #self.observe_model(self) # Observe model from other observer dynamically. self._otherObserver = gtkmvc.Observer() self._otherObserver.observe(self._valueChangedDynObs, 'value', assign = True) # EFFECT 2: # Fails, global function does not have im_self. #self._otherObserver.observe(valueChangedDynObsGlob, # 'value', assign = True) self._otherObserver.observe_model(self) # Observe model from ourselves statically. @gtkmvc.ModelMT.observe('value', assign = True) def _valueChangedStatSelf(self, model, prop_name, info): print 'statically, own observer: new =', info.new def _valueChangedDynSelf(self, model, prop_name, info): print 'dynamically, own observer: new =', info.new def _valueChangedDynObs(self, model, prop_name, info): print 'dynamically, other observer: new = ', info.new if __name__ == '__main__': m = MyModel() m.value = 5 -------- 8< ---------- 8< ----------- 8< ----------- Four notification functions listen to changes of the value property of MyModel. The first one uses the @ModelMT.observe decorator and works just fine if self.observe_model(self) is uncommented in MyModel.__init__(). The second one is dynamically registered using self.observe() (BEFORE registering the model, as stated in the manual) and works as well, if the block in MyModel.__init__() is uncommented. The third one uses an observer that is independent of the observer integrated in the model and also uses dynamic registration of the notification function. This works if, at the same time, the model also observes itself. If self.observe_model(self) is commented, the following assertion failure occurs: -------- 8< ---------- 8< ----------- 8< ----------- Traceback (most recent call last): File "./dynamic_observertest.py", line 57, in <module> m.value = 5 File "/usr/lib/pymodules/python2.7/gtkmvc/support/metaclasses.py", line 671, in _setter _inner_setter(self, val) File "/usr/lib/pymodules/python2.7/gtkmvc/support/metaclasses.py", line 641, in _setter self.notify_property_value_change(prop_name, old, val) File "/usr/lib/pymodules/python2.7/gtkmvc/model.py", line 499, in notify_property_value_change self, prop_name, info) File "/usr/lib/pymodules/python2.7/gtkmvc/model_mt.py", line 69, in __notify_observer__ assert self.__observer_threads.has_key(observer) AssertionError -------- 8< ---------- 8< ----------- 8< ----------- It works if the model is derived from Model instead of ModelMT, so it is really only this thread checking causing the problem. As far as I can tell, there is the requirement that a notification method belongs to the observer object which happens to call it, is this correct? At least when using the multithreaded variant. But there is something suspicious: The assertion does not trigger a failure if the model observes itself at the same time. I think the reason for that is that __observer_threads of the model contains the notification methods instance object because of self.observe_model(self). So the assertion is happy as the key exists in the dictionary, but it does not refer to the right observer's thread. The fourth notification function is a global function, which I suspect can't work in any case, as it does not have an im_self property. This triggers an AttributeError. Please don't get me wrong, I don't think that those are critical limitations. But I'd like to see a note about that in the user manual, probably just next to the warning about dynamic observer registration not being fully supported yet. Something like "When using a multithreaded model (deriving from ModelMT), every change notification function must belong to its observer object even if dynamically registered. Also note that every change notification function must be a class method, it is not possible to use a global callback." Maybe it could be formulated a bit clearer... Cheers, Philipp |
From: Philipp B. <ph...@hb...> - 2014-08-10 08:23:16
|
Hi Tobias (?) On 10.08.2014 03:45, to...@ce... wrote: > On 09.08.2014, at 18:56, Philipp Burch <ph...@hb...> wrote: > > Hi, > and thank you for your kind words. > >> Interesting is that the assertion failure is not triggered when I use a concrete property instead > > I don't think we can support notifications other than "assign" for logical properties. GTKMVC needs a better error message for that. > > Remember that in Python `m.someList.append(1)` means `tmp = m.someList; tmp.append(1)`. For concrete properties the model maintains a connection to the value it returns, so it can notify you of the "append" even though that line contains no m. > > Logical properties exist for calculated values, so GTKMVC must assume that the getter returns a different instance every time. Should the model track all of those? If append is called on two, should notifications go out in the order of the calls, or the order they were retrieved? > > Maybe we can find a solution depending on why you want to use logical properties. > Thanks for your quick response! Actually, I haven't thought about what it would mean for gtkmvc to support those notifications for complex logical properties. Thanks for pointing out the problem with all the new instances, that sounds sensible. Maybe the assertion could be replaced by an exception with a more detailed error message, but it would also help to see that limitation in the docs. Maybe I have overlooked it, but I really searched through the manual and did not find a hint about that. The reason I even tried to use a complex object in a logical property is because I wanted to have getters and setters for everything. But by letting a model observe itself, this should not be strictly necessary, so I guess I'll use concrete props unless I really have a calculated value and everything should be fine :) Best regards, Philipp |
From: <to...@ce...> - 2014-08-10 02:03:26
|
On 09.08.2014, at 18:56, Philipp Burch <ph...@hb...> wrote: Hi, and thank you for your kind words. > Interesting is that the assertion failure is not triggered when I use a concrete property instead I don't think we can support notifications other than "assign" for logical properties. GTKMVC needs a better error message for that. Remember that in Python `m.someList.append(1)` means `tmp = m.someList; tmp.append(1)`. For concrete properties the model maintains a connection to the value it returns, so it can notify you of the "append" even though that line contains no m. Logical properties exist for calculated values, so GTKMVC must assume that the getter returns a different instance every time. Should the model track all of those? If append is called on two, should notifications go out in the order of the calls, or the order they were retrieved? Maybe we can find a solution depending on why you want to use logical properties. |
From: Philipp B. <ph...@hb...> - 2014-08-09 16:56:46
|
Hi everyone, I've discovered gtkmvc a few days ago as I'm starting a somewhat larger project in python with much more GUI than what I've done before. That lib seems to be a valuable tool for the project. During some tests, I found some strange behaviour when defining logical observable properties of a complex type (namely a list). Consider this example: ------- 8< ------------ 8< ------------- 8< --------------- #!/usr/bin/python import gtkmvc class MyModel(gtkmvc.Model): __observables__ = ['someList'] #someList = [] def __init__(self): gtkmvc.Model.__init__(self) self.register_observer(self) self._someList = [] @gtkmvc.Model.getter def someList(self): return self._someList @gtkmvc.Model.setter def someList(self, value): self._someList = value @gtkmvc.Model.observe('someList', assign = True, before = True) def someListChanged(self, model, prop_name, info): print 'someListChanged, info =', str(info) if __name__ == '__main__': m = MyModel() m.someList.append(1) # Nothing happens. m.someList.append(2) # Nothing happens. m.someList = [0] # Triggers someListChanged with correct info. m.someList.append(3) # Assertion failure. ------- 8< ------------ 8< ------------- 8< --------------- When running this file, I get an assertion failure: ------- 8< ------------ 8< ------------- 8< --------------- someListChanged, info = {'prop_name': 'someList', 'old': [1, 2], 'new': [0], 'model': <__main__.MyModel object at 0x7fb8de36aa50>, 'assign': True} Traceback (most recent call last): File "./logicalprop.py", line 34, in <module> m.someList.append(3) # Assertion failure. File "/usr/lib/pymodules/python2.7/gtkmvc/support/wrappers.py", line 99, in _wrapper_fun self._notify_method_before(self._obj, name, args, kwargs) File "/usr/lib/pymodules/python2.7/gtkmvc/support/wrappers.py", line 63, in _notify_method_before args, kwargs) File "/usr/lib/pymodules/python2.7/gtkmvc/model.py", line 514, in notify_method_before_change assert(self.__instance_notif_before.has_key(prop_name)) AssertionError ------- 8< ------------ 8< ------------- 8< --------------- I have version 1.99.1-1build1 from the Ubuntu repositories installed. Interesting is that the assertion failure is not triggered when I use a concrete property instead (comment the getter&setter, uncomment the class attribute someList). In this case, someListChanged() is called four times and everything seems to be fine. Am I overlooking something in my code, or what could be the reason for that effect? I think I can work around it using concrete properties for those container types, but maybe it will come back and bite me at a later time... Thanks for the great work! Kind regards, Philipp |
From: Roberto C. <ca...@fb...> - 2013-09-10 14:57:06
|
On 09/10/2013 02:43 PM, qu9542 wrote: > first of all, I love pygtkmvc, thanks for this great work. > my question is will pygtkmvc upgrade to new pyGObject (gtk+3.x)? > In short, the answer is no, at least until gtk3 will be wisely used by the community. At the moment gtk3 is not diffusely used. Consider that there is no official installer for windows - after almost 3 years it was released! When starting a new project, would you consider using gtk3 or stick on gtk2, when one important reason for choosing gtk is portability? Even worse, would you consider gtk or maybe a radical switch to QT or other modern/portable framework? Will gtk3 be ready for android? I think gtk is in a very dangerous phase now: either there is a serious pushing of gtk3 made by the community, or it will be relegated to a very little share. About the future, I have some whirling ideas about a new simple framework for python, which would take some ideas from gtkmvc, but more focused on reactive gui programming paradigm. Will the framework be gtk3 or qt I don't know at the moment. I do like gtk3, but really I need to understand what gtk guys are planning to do for the future in order to decide. Hope to be able to concretely write some code into a new project sooner or later. r. |
From: Baskhuu J. <bas...@gm...> - 2013-07-25 01:54:21
|
Thank you On Wed, Jul 24, 2013 at 10:27 PM, <to...@ce...> wrote: > On 23.07.2013, at 16:49, Baskhuu Jacara <bas...@gm...> wrote: > > > Then I made login screen and successfully logged in my database. So now > I want to switch POS main screen. > > > > How do I switch from first controller to second controller? > > Assuming your screens are windows, and only the first is instantiated > before entering the mainloop: > > def on_login_button: > if successful: > v = MainView() > m = MainModel() > c = MainCtrl(v, m) > v.show() > self.view["window"].destroy() > > (off the top of my head; I'm on the move) -- Хүндэтгэсэн *Басхүү.Л* * * Хувь заяа бол магадлалын асуудал биш. Энэ бол сонголт. Түүнийг хүлээх биш, бүтээх учиртай. Хэрэв боломж хаалгыг чинь тогшихгүй байвал эхлээд хаалгаа барь. |
From: <to...@ce...> - 2013-07-24 14:49:30
|
On 23.07.2013, at 16:49, Baskhuu Jacara <bas...@gm...> wrote: > Then I made login screen and successfully logged in my database. So now I want to switch POS main screen. > > How do I switch from first controller to second controller? Assuming your screens are windows, and only the first is instantiated before entering the mainloop: def on_login_button: if successful: v = MainView() m = MainModel() c = MainCtrl(v, m) v.show() self.view["window"].destroy() (off the top of my head; I'm on the move) |
From: Baskhuu J. <bas...@gm...> - 2013-07-23 14:49:32
|
I need some help. I'm trying make simple POS client app using gtkmvc. Then I made login screen and successfully logged in my database. So now I want to switch POS main screen. How do I switch from first controller to second controller? -- Jacara |
From: Roberto C. <ca...@fb...> - 2012-05-28 10:43:27
|
On 05/28/2012 09:16 AM, Roberto Cavada wrote: > I also have been working in the WE on a complete example. I should be > able to commit it today. Done. See rev. 391 r. |
From: Roberto C. <ca...@fb...> - 2012-05-28 07:32:02
|
On 05/26/2012 10:38 PM, Steve McGrath wrote: > Roberto, Tobias, thanks. I spent some time last night working on > moving my toolbar and menubar to a UIManager, and it's working > perfectly. I added a new subview which creates a UIManager and > populates it with ActionGroups stored in the other views' Glade files. > Works great. I just had to stop thinking about it and start coding it. That's great! I also have been working in the WE on a complete example. I should be able to commit it today. Cheers, r. |
From: Steve M. <smc...@gm...> - 2012-05-26 20:38:07
|
Roberto, Tobias, thanks. I spent some time last night working on moving my toolbar and menubar to a UIManager, and it's working perfectly. I added a new subview which creates a UIManager and populates it with ActionGroups stored in the other views' Glade files. Works great. I just had to stop thinking about it and start coding it. Thanks again, -Steve McGrath -- If it ain't broke, you're not using a new enough version |
From: Steve M. <smc...@gm...> - 2012-05-25 22:52:17
|
On Fri, May 25, 2012 at 5:40 PM, <to...@ce...> wrote: > On 25.05.2012, at 17:26, Steve McGrath wrote: > >> This part seems to work alright, except that if a subview's controls have accelerator keys defined, I get this warning: "GtkWarning: IA__gtk_window_add_accel_group: assertion `GTK_IS_WINDOW (window)' failed" > > Accelerators only work if they're assigned to a window, since this is where keyboard events come in from the OS. > > Some of your files don't contain windows. I didn't know this was possible, I presume you started with one and then used "remove parent" in Glade. > > This is why GtkBuilder fails to set up the accelerator. Using the common tab in Glade does not make any intermediate steps (like an ActionGroup) available, so it is not possible to fix this in code. > > Even if you had dummy windows in the subview files, reparenting the widgets into the main window would break the accelerators. > > The bottom line is, the common tab will never work with subviews. You'll have to do it manually in code (like examples/uimanager) or wait for us to finish extending GTKMVC. > Ah. Actually I had just cut & pasted the subsections out of my main glade file into their own glade projects. Glade didn't complain, so I never thought to think about whether or not it was a good idea. I was guessing the problem had something to do with the subview not having its own window. I suppose I'll work on integrating UIManager into the mix, and figure out my accelerator keys from there. -Steve -- If it ain't broke, you're not using a new enough version |
From: <to...@ce...> - 2012-05-25 22:40:22
|
On 25.05.2012, at 17:26, Steve McGrath wrote: > This part seems to work alright, except that if a subview's controls have accelerator keys defined, I get this warning: "GtkWarning: IA__gtk_window_add_accel_group: assertion `GTK_IS_WINDOW (window)' failed" Accelerators only work if they're assigned to a window, since this is where keyboard events come in from the OS. Some of your files don't contain windows. I didn't know this was possible, I presume you started with one and then used "remove parent" in Glade. This is why GtkBuilder fails to set up the accelerator. Using the common tab in Glade does not make any intermediate steps (like an ActionGroup) available, so it is not possible to fix this in code. Even if you had dummy windows in the subview files, reparenting the widgets into the main window would break the accelerators. The bottom line is, the common tab will never work with subviews. You'll have to do it manually in code (like examples/uimanager) or wait for us to finish extending GTKMVC. |
From: <to...@ce...> - 2012-05-25 22:05:29
|
On 25.05.2012, at 23:23, Steve McGrath wrote: > Any small example of how to connect all the "plumbing" of UIManager in a gtkmvc application would be useful indeed. https://sourceforge.net/apps/trac/pygtkmvc/browser/trunk/gtkmvco/examples/uimanager Didn't plan to commit these, but there you are. |
From: Steve M. <smc...@gm...> - 2012-05-25 21:23:38
|
On Fri, May 25, 2012 at 3:27 PM, <to...@ce...> wrote: > On 25.05.2012, at 17:26, Steve McGrath wrote: > >> except that if a subview's controls have accelerator keys defined, I get this warning: "GtkWarning: IA__gtk_window_add_accel_group: assertion `GTK_IS_WINDOW (window)' failed" > > You used the Common tab in Glade's inspector? Libglade or GtkBuilder? Yes, I defined the accelerator keys for a couple buttons using the common properties in Glade. I'm using GtkBuilder format for all my UI definitions. >> I'd like to find a way to define pieces of the toolbar/menubar in each subview, and connect their signals directly to handlers in the subcontrollers. > > That's how examples/converter works. I'll have to take a look at that one, thanks. >> Does anyone have any insight or examples? > > If you can show your code I'll write one ;) If you want to take a look, my code can be seen on github at https://github.com/smcgrath/azathoth-client/tree/gtkmvc-refactor For context, this application is used to monitor and control a robot over a wi-fi connection. It's kind of a mess because I got a little ways into it and decided to refactor everything into the gtkmvc framework before proceeding any further. Roberto: Thank you, I think this explanation is a bit more clear than the old message from you that I quoted. Part of the problem I think is more generally GTK-related, in that I haven't worked with the UIManager or Actions/ActionGroups yet. So far I've always defined toolbars and menubars traditionally, as object hierarchies within my main window's glade file. Any small example of how to connect all the "plumbing" of UIManager in a gtkmvc application would be useful indeed. Thanks much, -Steve McGrath -- If it ain't broke, you're not using a new enough version |
From: Roberto C. <rob...@gm...> - 2012-05-25 21:00:34
|
2012/5/25 Steve McGrath <smc...@gm...> > I'm having some trouble getting my head around a few things though. Is > there any published code out there using this pattern? I'm not > entirely certain how to break everything down, especially dealing with > the menu and toolbars. > Typically in large applications you have: - One view (possibly with a controller associated) for toolbars and menubars (BarsView and possible BarsCtrl) - M views to decompose the rest of the application presentation - N controllers (N <= M) to decompose the controllers of the M views Now you want some (not necessarily all) controls in the menu and toolbars to be handled in the N controllers, to keep locality. The way I always solve this problem is: 1. Each of the M views contains its own actions to be later associated to the UI manager allocated in BarsView 2. The signal handlers of the actions are located in the N controllers, attached automatically when views and controllers are connected each other. 3. BarsView creates and handles the UIManager. This Bars view has the visibility of all M views (throught the ApplicationView which stays at top-level and has to be passed down to BarsView's constructor. In this way the BarsView can access the actions allocated in the M views to associate them in the UIManager. Let me think what you think about this, and if it is not clear enough I will try to make an example. r. |
From: <to...@ce...> - 2012-05-25 20:44:10
|
On 25.05.2012, at 17:26, Steve McGrath wrote: > Is there any published code out there using this pattern? I don't think so. The repository contains a UIManager example, but it's using a new View class we're working on. > This part seems to work alright, And it sounds good! > except that if a subview's controls have accelerator keys defined, I get this warning: "GtkWarning: IA__gtk_window_add_accel_group: assertion `GTK_IS_WINDOW (window)' failed" You used the Common tab in Glade's inspector? Libglade or GtkBuilder? > I'd like to find a way to define pieces of the toolbar/menubar in each subview, and connect their signals directly to handlers in the subcontrollers. That's how examples/converter works. > Does anyone have any insight or examples? If you can show your code I'll write one ;) Tobias |
From: Steve M. <smc...@gm...> - 2012-05-25 15:26:25
|
Greetings, I've been trying to figure out the best way to deal with subviews using gtkmvc with gtkbuilder, and I came across this message on the mailing list archive: >> I personally use always the third. My latest preferences actually go to: >> >> 1. Separate glade 'builder' files per each view >> 2. Subview instantiated and connected in parent views >> 3. menu and toolbars not designed in glade, but constructed in ui manager >> 3.1 The top-level view has the space to accomodate the "tools" subview >> (menu and toolbars) >> 3.2 There is a glade (builder) file associated to one or more views to >> represent menu ad toolbars. The glade file contains actions, action >> groups and one uimanager object. >> 3.3 The view(s) for the menu and toolbars sets up the action groups, the >> actions, the accelerators, and using the uimanager instance create menus >> and toolbars out of xml files. The view has also the methods for >> dynamically change menu and toolbars throught visibility and sensitivity >> of actions and action groups. >> >> Cheers, >> r. I'm having some trouble getting my head around a few things though. Is there any published code out there using this pattern? I'm not entirely certain how to break everything down, especially dealing with the menu and toolbars. Right now, I have three views with their own glade files. There is a main window, and two subviews which each contain a set of controls to pack into a vbox in the main window. The top level objects in each subview's glade file are containers, one uses a vbox, one uses a table. In my main view's constructor, I pack them into the main window's vbox. This part seems to work alright, except that if a subview's controls have accelerator keys defined, I get this warning: "GtkWarning: IA__gtk_window_add_accel_group: assertion `GTK_IS_WINDOW (window)' failed" My motivation for creating the subviews was so that I could create matching subcontrollers, to split up my controller class before it got too big and messy. This leads me to the toolbar/menu problem. Some toolbar and menu actions should be handled directly be the various subcontrollers, so defining them in the main view and and using the main controller to pass events down to the subcontrollers seems inelegant. I'd like to find a way to define pieces of the toolbar/menubar in each subview, and connect their signals directly to handlers in the subcontrollers. Does anyone have any insight or examples? Thanks, -Steve McGrath -- If it ain't broke, you're not using a new enough version |
From: haiyan qu <quh...@gm...> - 2011-11-22 16:03:07
|
Hi Towb, Your suggestion works beautifully. Thanks a lot for your quick & prompt answer, and kindly point out other problems in my code. Your comment helped my understanding with both MVC and glade/gtk in general. now the pygtk-demo->Dialog&MessageBox works in pygtkmvc framework, I attached the working code. All right, I will move on to the next example in pygtk-demo. :) You make my day!! Thanks again & best regards! Q |
From: <to...@ce...> - 2011-11-22 09:43:15
|
On 22.11.2011, at 01:41, haiyan qu wrote: > When I try to launch “window2” from the main window “window1”, I didn't get “window2”, instead I got a duplicate “window1”. The top argument only really works with the old libglade. For GtkBuilder it is best to put each window into its own file. Your code creates a window2 every time you want a window1, and vice versa. The reason you only ever see a window1 is that window2 is not set visible in Glade. Two other things: The type of window2 is set to popup. GTK is a little confusing: popup means something like a context menu that is really part of another window, not a dialog. The copied MessageDialog constructor still gets self, only self isn't a window like in the original demo, but a controller. I attached a version with these small changes. You can use diff to examine them. Also attached is a copy & paste port I made from the original demo. Note that dialogs to modify variables are a pattern people use when direct modification is too much work. GTKMVC does that work for you, so our applications usually use less windows, and adapters instead of manually setting and getting text when OK is clicked. |
From: haiyan qu <quh...@gm...> - 2011-11-22 00:41:14
|
Greeting, I am a beginner of pygtkmvc. So this may be a dumb question. I am trying to convert all pygtk-demo examples to pygtkmvc framework, I believe this will be my best practice for learning pygtkmvc. I have a problem when I am converting pygtk-demo->Dialog&MessageBox. This example involved 2 dialogs, parent dialog will launch child dialog. I created both parent and child dialog in Glade as “window1” and “window2” When I try to launch “window2” from the main window “window1”, I didn't get “window2”, instead I got a duplicate “window1”. Below are my 2 views from same .galde file, different top. class MyView1 (View): builder = "test.glade" top = 'window1' class MyView2 (View): builder = "test.glade" top = 'window2' When I click a button from view1, I want to launch view2. Unfortunately, view1 is opened again. def on_button_dialog_clicked(self, user_data): v2 = MyView2() c2 = MyControllerAdap2(self.model, v2) Any comment is very appreciated! example code (main.py and test.glade) is attached. demo.py is the original code from pygtk-demo (without using pygtkmvc framework) Thanks in advance and best regards! Q |
From: <to...@ce...> - 2011-08-17 11:08:10
|
mHi, how is everyone doing? I took the liberty to write up what happened in SVN since the last release: https://sourceforge.net/apps/trac/pygtkmvc/changeset/361 And here is what's left to be done: https://sourceforge.net/apps/trac/pygtkmvc/report/1 Several old tickets are blocked by lack of feedback, so don't hold back ;) Tobias |