On 3/8/23 16:56, aapost wrote:
Thomas > Cameron

def set_entries_enabled_state(enabled = True):
     state = 'normal' if enabled else 'disabled'
     for e in (e1, e2, e3):
         e.config(state=state)

def config_b_and_entries(enabled = True):
     state = 'normal' if enabled else 'disabled'
     b.config(state = state)
     set_entries_enabled_state(enabled)

I admit adding commenting might be useful to clearly express intent for patterns I don't commonly see. But when you are managing a bunch of widgets and experimenting with the design, the variable name word salad approach 'in the name of readability' starts to melt your brain a bit and it all starts too look like a wall of..:

the_thing.the_things_thing.do_this_thing_to_that_other_thing_but_only_if_this_one_time()

So the button b in the example only needs a reference to a callable configured, set with the command= parameter in .config()

The code:

def func():
  pass
b.config(command=func)

Is equivalent. So that if the button is clicked, code at func (or the lambda) gets called.

In both cases (as per my intent), care about the return values of the expressions does not matter and I am fairly certain regardless of what the callable returns, it does not get evaluated/assigned/considered anywhere. (at least that is how I have been considering it, a void foo(void) if you will..). Now as far as the tuple, yes, left to right evaluation is what I expect, (hope anyway, lol),

meaning (3, False, 1, x := 5+9, print("hello{}".format(x)))
would return a tuple of (3, False, 1, 14, None) which gets assigned to nothing and the string "hello14" printed to console.

Now.. When you want to assign a callable that requires args, the main examples people give are a combo of them both,

def func(x,y,z):
  pass
x = y = x = "something"
b.config(command=lambda x,y,z: func(x,y,z))

So as far as the examples given above (which I can't really parse), if you meant for passing in a bool value, to do so would require something like:

b.config(command=lambda enabled: config_b_and_entries(enabled))

Which that type of thing to me gets even harder to grok after a while, and I guess for me I find having to go to a different scope or a separate file to parse a bunch of definitions like these:

def set_entries_enabled_state(enabled = True):

def config_b_and_entries(enabled = True):

ends up taking me out of an object oriented focus / headspace of the layout at hand.


And it is sort of like.. Ok I can either

b.config(command=lambda: (
    a.expr,
    b.expr.update({something: "morecomplicated"}),
    c.expr
    )
)

OR..

b.config(command=lambda a=a, b=b, c=c, s=something: foo(a, b, c, s))

somewhere else:
def foo(a, b, c, something):
    a.expr
    b.expr.update({something: "morecomplicated"})
    c.expr


When you are trying to add a bit of dynamic feel to the tediousness of the widget management, keeping things kind of contained to their object just feels more natural to me (at the moment anyway).. (all the packing, unpacking, making collections of widgets within frames appear or go away based on states, colour changes based on input, dynamic widget generation and where their relative attachment should go, etc)

I read a lot of sentiment against complicated lambdas suggesting one should go for more functions, but I guess I feel pushing a more complicated lambda to contain behavior more closely to an instance feels more intuitive at the moment (and the sentiment against it doesn't really resonate with me), so long as it isn't introducing some inherent behavioral flaw or bug I am blind to..

Of course I might change my mind at some point during a refactor and think "what the hell is that, why didn't I just..".. Which will probably come in a few weeks. lol

One additional note on the Thread comment, I haven't really needed to dig in to that too deeply, but Threading is amazing for tkinter UI troubleshooting,

if you add something like:
t = threading.Thread(target=maintk.mainloop)
and run it with python -i
so long has you have attached every widget to some relative position on to the root (maintk in this case), you can interact with any object/widget directly live to see what is going on or what a change does.

--
https://mail.python.org/mailman/listinfo/python-list

Reply via email to