How do I iterate through all wx.CheckBox instances? - python

I have a wx frame where I have a quite a few checkboxes. Ever so often when the user changes the settings in a drop down menu (wx.ComboBox) I'd like to clear all the checkboxes. Currently, I've implemented a method that gets called when a change in the ComboBox happens and it clears each check box manually, i.e.:
def ClearCheckBoxes(self):
self.cb_EnableControl.SetValue(0)
self.cb_EnableRun.SetValue(0)
self.cb_EnablePower.SetValue(0)
...
...
Although I only have about 10 of these, my ClearCheckBoxes method would be much cleaner if it were something like this:
def ClearCheckBoxes(self):
for CheckBox in self.AllCheckBoxes:
CheckBox.SetValue(0)
Also, I suppose I could create a list (i.e. AllCheckBoxes) and add all the checkboxes to the list as I create them, and then it would only be a matter of iterating through the list. But the point here is that I'd like to know if there was an pre-defined way of doing this.
Thanks

for control in self.GetChildren():
if isinstance(control, wx.CheckBox):
control.SetValue(False)

Have you tried something super ugly like:
[checkbox.SetValue(0) for checkbox in dir(self) where type(checkbox) == type(wx.Checkbox)]

Related

Kivy: Reset/Default values to all widgets on a screen?

Is there a way to return all values of all widgets on a screen to their default values (ex. TextInputs text: '') or do I have to write a function to go through each one, one by one, to clear them?
I don't think Kivy properties retain any concept of a default value, so you'll have to handle this yourself.
What you can do is clear all widgets on a screen using .clear_widgets() function. I don't think there's any way to reset all values. Another way to change the values is like if you have a textfield then you can do textfield.text = '' but you have to go through each widget to reset it

Traitlets List won't run callback if the list is modified in-place

I have a class with a list trait that I'd like to use to call a function any time the list is modified.
class MyClass(traitlets.HasTraits):
MyTrait = traitlets.List([0]*8, minlen=8, maxlen=8)
Foo = MyClass()
def Bar(change):
print(change['new'])
Foo.observe(Bar, names='MyTrait')
The problem I have is that if I do something like the following, Bar doesn't get called:
Foo.MyTrait[0] = 5
If I want Bar to get called, I have to do something like this:
MyTraitCopy = Foo.MyTrait.copy()
MyTraitCopy[0] = 5
Foo.MyTrait = MyTraitCopy
This doesn't seem like the right way to do this. Is there a better way to register a callback to a change in a member of a List trait?
I've been playing with the widgets a lot recently, and traitlets does not seem to be able to observe such changes, there is the same problem with dictionnaries (see https://github.com/ipython/traitlets/issues/496 for more details).
In my project I had to detect the change of a dictionnary values with few keys. I added a counter key to the dictionnary and I recreated the dict each time it was updated... But copying seems to be the only way for now.

How to increment QLineEdit name to access value?

This seems like a really simple question, but has me stumped. I've got a UI that has multiple QLineEdits for names, start, and end times. For example:
clipName1, clipStart1, clipEnd1
clipName2, clipStart2, clipEnd2
clipName2, clipStart3, clipEnd3
These are not dynamically built on the fly. They are static. I wish to access the values from these by going through a loop. I am not sure how I can append an integer onto the variable name and still be able to access the value. I've tried this which I know doesn't work:
clipTotal = 4
for i in range(1, clipTotal+1):
clipName = self.clipName+str(i)+.text()
Answer provided by ekhumoro in comments above:
clipName = getattr(self, 'clipName%d' % i).text()

A better way of specifying the fields in a gtk.ListStore

I have a ListStore with a lot of fields, most of them the same:
store = gtk.ListStore(str,str,str,str,str,str,str,str,
gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,
gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,
gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,
gtk.gdk.Pixbuf,gtk.gdk.Pixbuf,str,)
Is there a better way than this horrible mass of repetition?
EDIT: So this ended up:
store = gtk.ListStore( *(8*(str,)+14*(gtk.gdk.Pixbuf,)+(str,)) )
Less readable I guess but more programatically adaptable
If you have control over the ListStore code, pack them into a namedtuple and make sure they dont shadow the built-in names.
If you don't have control over the ListStore code, pack them into a tuple and unpack the arguments via gtk.ListStore(*yourtuple).

Is it considered bad practice to use a widgets title attribute to refer to it?

Would it be considered bad practice to use a widgets title attribute to refer it?
For example I have a number of custom radioBoxCtrls on a panel
I only ever need to get/set all the values at once
so the container class(a panel) for the radioBoxCtrls objects has the following methods
get_options()
set_options()
To set options for all the radioBoxCtrls a dictionary is passed to the set_options() method.
Each key, value pair in the dictionary is a title of a radioBoxCtrl and the title of the button on the radioBoxCtrl that should be set
def set_options(self, options={}):
"""
This method sets which radio button is selected
on each RadioBoxCtrl object
#param options: A dictionary
Each key is the title of a RadioBoxCtrl
each keys value is the button on the radio box that is to be selected
"""
for option_box in self.option_boxes:
if option_box.title in options.keys()
option_box.set_selected_button(options[option_box.title])
def get_options(self):
"""
This method returns a dictionary of the selected options
Each key is the title of a RadioBoxCtrl object
and each keys value is the name of the button selected on the radio box
"""
options = defaultdict(list)
for option_box in self.option_boxes:
options[option_box.title]=option_box.get_selected_btn()
return options
So (in an attempt to be clear) when I call the set method from my controller
I pass in a dictionary like so:
options = {"Name of radioBoxCtrl": "Option 2", ... }
self.gui.optionsPanel.set_options(options)
Why the hell do you want do that? (you may ask)
Short answer: mvc
I want to create a suitable layer of abstraction. All that my controller needs to know with
regard to the options is how to get them to pass to the model when some processing needs to be done and how set them when a config file is loaded...
I thought it would simplify things if I could just call one method to set and vice-versa -but Im not so sure now!
I realize that this is probably more of question on the acceptability of refering to objects by some string attribute they posses, which in my case just happens to be the title.. so feel free to answer it accordingly..
Please feel free to improve the title of question(I wasnt really sure how to word it) and add tags.
Thanks
I can't tell whether the gurus would call it bad practive. I just know I'd never do it - it is slower, more error-prone, possibly makes it very hard to change a title's name (admittedly, only if you hardcode it everywhere) and (arguably) very inelegant. At least you should associate te options with the widget's identity, which still smells imho, but at least has a few problems less. Maybe that whole part of the application should be refactored to be less centralized so the issue disappears completely.
Edit on how to refactor: Honestly, I can't tell - I know little about the application. The obvious approach would be subclassing all widgets and making them responsible for somehow getting the options and changing accordingly. But I can't tell whether that's really feasible.

Categories

Resources