Implicit initialization is EVIL!

Discussion in 'Python' started by rantingrick, Jul 3, 2011.

  1. rantingrick

    rantingrick Guest

    Tkinter has a major flaw and this flaw has been with us for many many
    years. What is the flaw? Well the title says it all folks... IMPLICIT
    INITIALIZATION IS EVIL. Still confused, well let me explain.

    Unlike most GUI libraries the Tkinter developers thought is would
    "just wonderful" if the root GUI window just sprang into existence if
    the programmer "somehow" forgot to create one. Does anyone remember
    the old adage...

    """ The road to hell is paved with good intentions? """

    ....as you're about to see this road is paved in gold around thee
    parts! You're probably thinking to yourself that i am stretching the
    truth for the sake of drama? Well i wish i could answer yes, but i
    cannot. So without further "a due" let me show you some code...

    ## START CODE ##
    from Tkinter import *
    label = Label(parent=None, text='This is an example of poor GUI
    design!')
    label.pack()
    label.mainloop()
    ## END CODE ##

    As you can see the root window is auto created for the caller and this
    sort of hand holding only served to confuse the hell of out new folks!
    Sure it's "cute" (and all that type of nifty swiftly crap!) but it is
    EVIL! A new user should learn from day one the hierarchy of a GUI.

    -root window
    -optional widgets
    --optional sub windows
    ---optional widgets
    ---and on and on

    root = Tk() # Or a derived class of Tk
    frame = Frame(root)
    w = Widget(frame)
    and on and on and on

    We should never propagate this sort of confusion throughout our
    community. Please remove this dangerous design pattern immediately.
     
    rantingrick, Jul 3, 2011
    #1
    1. Advertising

  2. On Mon, Jul 4, 2011 at 8:11 AM, rantingrick <> wrote:
    > A new user should learn from day one the hierarchy of a GUI.
    >
    > -root window
    > -optional widgets
    > --optional sub windows
    > ---optional widgets
    > ---and on and on


    You're forgetting all the other crucial parts of the hierarchy. A new
    user should be forced to declare a Desktop that s/he wants the window
    on, and a Screen, and choose which video driver to use too! Implicit
    acceptance of defaults is EVIL! Oh, and while you're at it, Python's
    habit of letting you skip variable declarations is EVIL too. A new
    user should learn from day one that variables need to be stored
    somewhere, so Python should stop coddling its newbies and actually get
    them to do things right:

    var(0x14205359) x # Don't forget to provide an address where the
    object will be located
    x=42

    After all, everyone's gotta learn about segfaults some day!

    Chris Angelico
     
    Chris Angelico, Jul 3, 2011
    #2
    1. Advertising

  3. rantingrick

    Roy Smith Guest

    In article <>,
    Chris Angelico <> wrote:

    > var(0x14205359) x # Don't forget to provide an address where the
    > object will be located
    > x=42
    >
    > After all, everyone's gotta learn about segfaults some day!


    0x14205359 is more likely to give a bus error (odd address) than a
    segfault :)
     
    Roy Smith, Jul 3, 2011
    #3
  4. rantingrick wrote:

    > Unlike most GUI libraries the Tkinter developers thought is would
    > "just wonderful" if the root GUI window just sprang into existence if
    > the programmer "somehow" forgot to create one.


    IMO the real problem here is the existence of a privileged
    "root" window at all. No GUI platform I know of has any
    such concept (except for a "desktop" window that represents
    the whole screen, which is not the same thing). All top-level
    windows should have equal status.

    --
    Greg
     
    Gregory Ewing, Jul 4, 2011
    #4
  5. On Mon, Jul 4, 2011 at 6:33 PM, Gregory Ewing
    <> wrote:
    > rantingrick wrote:
    >
    >> Unlike most GUI libraries the Tkinter developers thought is would
    >> "just wonderful" if the root GUI window just sprang into existence if
    >> the programmer "somehow" forgot to create one.

    >
    > IMO the real problem here is the existence of a privileged
    > "root" window at all. No GUI platform I know of has any
    > such concept (except for a "desktop" window that represents
    > the whole screen, which is not the same thing). All top-level
    > windows should have equal status.


    I don't know Tkinter, but from the look of the example code, he's
    creating a Label that's not attached to a window, and then packing it
    into nothing. The toolkit kindly creates him a window. Is that the
    "root GUI window" that he means? A basic top-level window?

    Chris Angelico
     
    Chris Angelico, Jul 4, 2011
    #5
  6. rantingrick

    rantingrick Guest

    On Jul 4, 3:33 am, Gregory Ewing <> wrote:

    > IMO the real problem here is the existence of a privileged
    > "root" window at all. No GUI platform I know of has any
    > such concept (except for a "desktop" window that represents
    > the whole screen, which is not the same thing). All top-level
    > windows should have equal status.



    I dunno, it's natural to create a parent-child hierarchy when GUI
    programming with any library. So i am not completely sure what you are
    implying here? When you close the main application widow you would
    expect all child windows to close. Or likewise when you iconify the
    main window you would expect the other windows to do the same. Sure
    you could do this yourself by sending messages to all the other
    windows but Tkinter does this for you automatically. And how does
    Tkinter know which windows to configure? A parent-child relationship
    that's how.

    >>> a = set(dir(Tkinter.Toplevel))
    >>> b = set(dir(Tkinter.Tk))
    >>> len(a), len(b)

    (222, 226)
    >>> a.difference(b)

    set(['_setup', '_do'])

    You say "root" windows are bad however any parent-child relationship
    has to BEGIN somewhere. For Tkinter the beginning of this dynasty is
    an instance of the Tkinter.Tk[1] window from which all other windows
    and widgets are made children. HOWEVER any of the windows ARE in fact
    instances of Tk.Toplevel[1]. So they ARE all equal because they all
    have the same methods available to them.

    >>> import Tkinter
    >>> Tkinter.Tk.__doc__

    'Toplevel widget of Tk which represents mostly the main window\n of
    an appliation. It has an associated Tcl interpreter.'
    >>> import inspect
    >>> inspect.getmro(Tkinter.Tk)

    (<class Tkinter.Tk at 0x02742210>, <class Tkinter.Misc at 0x02742570>,
    <class Tkinter.Wm at 0x0272F780>)
    >>> inspect.getmro(Tkinter.Toplevel)

    (<class Tkinter.Toplevel at 0x02742690>, <class Tkinter.BaseWidget at
    0x02742630>, <class Tkinter.Misc at 0x02742570>, <class Tkinter.Wm at
    0x0272F780>)

    But let's dig a little deeper here. Your comment suggests that you
    "personally" need to create multiple windows for your applications. Is
    this correct? If so i pity any users of such application as they would
    be thoroughly confused. Most applications consist of one main window
    (a Tkinter.Tk instance). The only need for extra Toplevel windows is
    in the form of modal dialogs (use tkSimpleDialog.Dialog) or tool
    windows (use Tk.Toplevel with attribute '-toolwindow'=True).

    I don't see how your statements carry any weight here. Could you
    explain please?

    [1] http://effbot.org/tkinterbook/tkinter-application-windows.htm
    [2] http://effbot.org/tkinterbook/toplevel.htm
     
    rantingrick, Jul 4, 2011
    #6
  7. rantingrick

    rantingrick Guest

    On Jul 4, 3:44 am, Chris Angelico <> wrote:

    > I don't know Tkinter, but from the look of the example code, he's
    > creating a Label that's not attached to a window, and then packing it
    > into nothing. The toolkit kindly creates him a window. Is that the
    > "root GUI window" that he means? A basic top-level window?


    Yes. But to be specific the "root" is an instance of Tkinter.Tk which
    is a toplevel that has a TCL interpreter attached.
     
    rantingrick, Jul 4, 2011
    #7
  8. rantingrick

    Robin Becker Guest

    On 03/07/2011 23:21, Chris Angelico wrote:
    ..........
    >
    > var(0x14205359) x # Don't forget to provide an address where the
    > object will be located
    > x=42

    .........
    did you forget to specify the memory bank and computer (and presumably planet
    etc etc....)
    -molly-coddled-ly yrs-
    Robin Becker
     
    Robin Becker, Jul 4, 2011
    #8
  9. On Tue, Jul 5, 2011 at 1:19 AM, rantingrick <> wrote:
    > But let's dig a little deeper here. Your comment suggests that you
    > "personally" need to create multiple windows for your applications. Is
    > this correct? If so i pity any users of such application as they would
    > be thoroughly confused. Most applications consist of one main window
    > (a Tkinter.Tk instance). The only need for extra Toplevel windows is
    > in the form of modal dialogs (use tkSimpleDialog.Dialog) or tool
    > windows (use Tk.Toplevel with attribute '-toolwindow'=True).


    Uhh, sorry. No. There are plenty of good reasons for one application
    to make multiple top-level windows, and if I ever find myself using a
    toolkit that makes this difficult, I'll either be hacking the toolkit
    or using a different one. I've been building GUI applications for far
    too long to not want features like that.

    ChrisA
     
    Chris Angelico, Jul 4, 2011
    #9
  10. rantingrick

    rantingrick Guest

    oops. should have used symmetric_difference!

    >>> a.symmetric_difference(b)

    set(['_w', '_setup', 'report_callback_exception', '_do',
    '__getattr__', 'loadtk', '_loadtk', 'readprofile'])
     
    rantingrick, Jul 4, 2011
    #10
  11. rantingrick

    rantingrick Guest

    On Jul 4, 10:40 am, Chris Angelico <> wrote:

    > Uhh, sorry. No. There are plenty of good reasons for one application
    > to make multiple top-level windows, and if I ever find myself using a
    > toolkit that makes this difficult, I'll either be hacking the toolkit
    > or using a different one. I've been building GUI applications for far
    > too long to not want features like that.


    And those reasons are...?
     
    rantingrick, Jul 4, 2011
    #11
  12. On Tue, Jul 5, 2011 at 1:46 AM, rantingrick <> wrote:
    > On Jul 4, 10:40 am, Chris Angelico <> wrote:
    >
    >> Uhh, sorry. No. There are plenty of good reasons for one application
    >> to make multiple top-level windows, and if I ever find myself using a
    >> toolkit that makes this difficult, I'll either be hacking the toolkit
    >> or using a different one. I've been building GUI applications for far
    >> too long to not want features like that.

    >
    > And those reasons are...?


    As varied as the applications that call on them. One example that
    springs to mind: Our database front end has "table view" and "record
    view", where you get one table view and from that you can view as many
    records as you like. Users may choose to effectively switch from one
    view to the other, or they may open up two or more record views and
    have them and the table view all on screen simultaneously. This is not
    a modal dialog; it's not even a modeless dialog - it's a completely
    stand-alone window that can be moved around the Z order independently
    of the parent. There's a definite ownership based on process, though;
    terminate the process (by closing the table view) and it must close
    all record views first. I've done other applications where this has
    not been the case - where all top-level windows are truly equal - but
    not in this instance.

    As an aside, that particular program is one that we are currently
    using (I glance over and can see it running on one of our terminals
    here), and the interface has not changed since about 2002 (actually
    earlier - 2002 had a major code rewrite without much UI change).
    Multiple top-level windows fulfills the Law of Least Astonishment
    admirably, and has done so for a decade.

    Chris Angelico
     
    Chris Angelico, Jul 4, 2011
    #12
  13. rantingrick

    rantingrick Guest

    On Jul 4, 11:01 am, Chris Angelico <> wrote:
    > On Tue, Jul 5, 2011 at 1:46 AM, rantingrick <> wrote:
    > > On Jul 4, 10:40 am, Chris Angelico <> wrote:

    >
    > >> Uhh, sorry. No. There are plenty of good reasons for one application
    > >> to make multiple top-level windows, and if I ever find myself using a
    > >> toolkit that makes this difficult, I'll either be hacking the toolkit
    > >> or using a different one. I've been building GUI applications for far
    > >> too long to not want features like that.

    >
    > > And those reasons are...?

    >
    > As varied as the applications that call on them. One example that
    > springs to mind: Our database front end has "table view" and "record
    > view", where you get one table view and from that you can view as many
    > records as you like. Users may choose to effectively switch from one
    > view to the other, or they may open up two or more record views and
    > have them and the table view all on screen simultaneously.


    > This is not
    > a modal dialog; it's not even a modeless dialog - it's a completely
    > stand-alone window that can be moved around the Z order independently
    > of the parent.


    You can do the exact same thing with Tkinter's windows.

    > There's a definite ownership based on process, though;
    > terminate the process (by closing the table view) and it must close
    > all record views first. I've done other applications where this has
    > not been the case - where all top-level windows are truly equal - but
    > not in this instance.


    Tkinters Toplevels ARE equal!

    However in this case you should spawn a new instance of the
    application "opened" at that particular table view. It's as simple as
    a few command line arguments in your script.

    It's like a text editor, you never want a "New" command that resets
    the current document or an open command that resets the current
    document and loads the file into the existing editor. Each application
    instance should only create one document and stick with it until it is
    closed.

    Instead you want to spawn a new instance of the editor and tell the
    editor (via command line arguments) to load file data (if applicable).
    Simple command line arguments (of which you should be using anyway)
    are the key here. All part of proper software design.
     
    rantingrick, Jul 4, 2011
    #13
  14. On Tue, Jul 5, 2011 at 3:09 AM, rantingrick <> wrote:
    > On Jul 4, 11:01 am, Chris Angelico <> wrote:
    >> This is not
    >> a modal dialog; it's not even a modeless dialog - it's a completely
    >> stand-alone window that can be moved around the Z order independently
    >> of the parent.

    >
    > You can do the exact same thing with Tkinter's windows.


    I didn't say Tkinter couldn't do this; I said that it was a good thing
    to be able to do, which you earlier decried.

    > However in this case you should spawn a new instance of the
    > application "opened" at that particular table view. It's as simple as
    > a few command line arguments in your script.


    No! Definitely not. Initializing the application includes logging in
    to the database. Suppose the user had to log in again... or, worse,
    suppose I transmitted the username and password via command line
    arguments. No, forcing programmers into a particular coding model is a
    bad idea. Let the individual programmer decide what tool is best for
    what job.

    > It's like a text editor, you never want a "New" command that resets
    > the current document or an open command that resets the current
    > document and loads the file into the existing editor. Each application
    > instance should only create one document and stick with it until it is
    > closed.


    What, never? Well, hardly ever! (As per HMS Pinafore, if you're wondering.)

    Actually, I quite frequently do want exactly that. Replace the current
    buffer with a new document. Keeping the previous document involves one
    of two choices (maybe more, but I can't think of any off hand):

    * Leave the other document visible on the screen, cluttering things up
    and forcing the user to switch to the other window, close it, and then
    return to his work; or
    * Have the new window completely and exactly mask the old one, making
    it unobvious that the previous document is actually still open,
    leaving enormous possibilities for confusion.

    Audacity takes the first option (at least, the Windows version that I
    used five years ago did). You choose New or Open, it brings up another
    window. This astonished me when I first saw it (strike one), annoys me
    85% of the time and is useful only 15% (strike two), and tends to get
    in the way of rapid keyboard-oriented navigation (strike three and
    out). I'd much rather Audacity kept all its "stuff" in one window,
    unless I explicitly asked it for another window.

    For another example, look at where web browsers are going. By your
    description, one instance of a browser should work with precisely one
    "document" (which in this case would be a web page). That's how
    browsers were in the early days, but by the early 2000s most browsers
    had some form of tabs, letting you keep that application in one
    window.

    > Instead you want to spawn a new instance of the editor and tell the
    > editor (via command line arguments) to load file data (if applicable).
    > Simple command line arguments (of which you should be using anyway)
    > are the key here. All part of proper software design.


    Of course I could spawn a new instance. But why? Why do it? And if I
    have to have a completely new copy of all the editor's state, this is
    hopelessly inefficient on memory and startup work. Why should
    File|Open incur such a cost? (Ameliorated if you fork() but that has
    its own consequences.) But the memory cost is nothing compared to the
    extra interference it puts on "mindspace".

    I currently have precisely two slots in mindspace for web browsers:
    Chrome and Firefox. Chrome currently has about a dozen tabs up;
    Firefox about the same, but most of them are long-term status reports
    that I keep handy. If I had to have 20-30 separate windows, I would
    not be able to use alt-tab to find the one I want, but would have to
    use some other kind of "window picker". How would you write a
    user-friendly picker that can cope with myriad instances of
    everything? My guess is that it'd use some kind of tree structure with
    applications at one level and windows at the next. Is this not exactly
    what we already have?

    Chris Angelico
     
    Chris Angelico, Jul 4, 2011
    #14
  15. rantingrick

    rantingrick Guest

    On Jul 4, 12:41 pm, Chris Angelico <> wrote:

    > For another example, look at where web browsers are going. By your
    > description, one instance of a browser should work with precisely one
    > "document" (which in this case would be a web page). That's how
    > browsers were in the early days, but by the early 2000s most browsers
    > had some form of tabs, letting you keep that application in one
    > window.


    Umm, if you want to see where things are "going" you should learn
    about the inner workings of chrome which actually spawns a new process
    for every tab created; which has the benefit of avoiding application
    lock up when one page decides to crash.

    > I currently have precisely two slots in mindspace for web browsers:
    > Chrome and Firefox. Chrome currently has about a dozen tabs up;
    > Firefox about the same, but most of them are long-term status reports
    > that I keep handy. If I had to have 20-30 separate windows, I would
    > not be able to use alt-tab to find the one I want, but would have to
    > use some other kind of "window picker". How would you write a
    > user-friendly picker that can cope with myriad instances of
    > everything?


    psst: it's called a notebook in GUI jargon. Again, study up on chrome
    internals.
     
    rantingrick, Jul 4, 2011
    #15
  16. On Tue, Jul 5, 2011 at 5:30 AM, rantingrick <> wrote:
    > Umm, if you want to see where things are "going" you should learn
    > about the inner workings of chrome which actually spawns a new process
    > for every tab created; which has the benefit of avoiding application
    > lock up when one page decides to crash.


    There is still one application. There's a single process which is the
    master; all the other processes die if the master dies. Chrome's
    isolation of tab-groups has nothing to do with the GUI design question
    of whether one top-level window is allowed to do more than one thing,
    which you claimed it should not.

    >> How would you write a
    >> user-friendly picker that can cope with myriad instances of
    >> everything?

    >
    > psst: it's called a notebook in GUI jargon. Again, study up on chrome
    > internals.


    No, that would not be what it would be called. Also, a notebook is a
    very specific widget, and it's not quite identical to Chrome's or
    Firefox's tabbed browsing setup; but again, that has nothing to do
    with the case. The question is one of UI design.

    ChrisA
     
    Chris Angelico, Jul 4, 2011
    #16
  17. rantingrick wrote:

    > You say "root" windows are bad however any parent-child relationship
    > has to BEGIN somewhere.


    There's no need for *toplevel* windows to be children
    of anything, though.

    > HOWEVER any of the windows ARE in fact
    > instances of Tk.Toplevel[1]. So they ARE all equal because they all
    > have the same methods available to them.


    No, they're not -- the root window is special, because
    if you kill it, the whole application exits. Often that
    is inconvenient.

    --
    Greg
     
    Gregory Ewing, Jul 5, 2011
    #17
  18. rantingrick wrote:
    > Most applications consist of one main window
    > (a Tkinter.Tk instance).


    You've obviously never used a Macintosh. On the Mac, it's
    perfectly normal for an application to open multiple
    documents, each in its own window, with no one window
    being the "main" window. Any of them can be closed (or
    even *all* of them) and the application continues to run
    until you explicitly quit it.

    --
    Greg
     
    Gregory Ewing, Jul 5, 2011
    #18
  19. Gregory Ewing wrote:

    > rantingrick wrote:
    >> Most applications consist of one main window
    >> (a Tkinter.Tk instance).

    >
    > You've obviously never used a Macintosh. On the Mac, it's
    > perfectly normal for an application to open multiple
    > documents, each in its own window, with no one window
    > being the "main" window. Any of them can be closed (or
    > even *all* of them) and the application continues to run
    > until you explicitly quit it.


    Or a Linux GUI. I have kwrite running with 15 open windows. The application
    doesn't exit until the last window is closed, and no window is privileged
    over the others.

    Even in Windows, the sort of MDI interface Rick seems to be describing is
    less common now than it used to be -- possibly even rare.

    http://en.wikipedia.org/wiki/Multiple_document_interface


    --
    Steven
     
    Steven D'Aprano, Jul 5, 2011
    #19
  20. On Wed, Jul 6, 2011 at 12:25 AM, Steven D'Aprano
    <> wrote:
    > Gregory Ewing wrote:
    >
    >> You've obviously never used a Macintosh. On the Mac, it's
    >> perfectly normal for an application to open multiple
    >> documents, each in its own window, with no one window
    >> being the "main" window. Any of them can be closed (or
    >> even *all* of them) and the application continues to run
    >> until you explicitly quit it.

    >
    > Or a Linux GUI. I have kwrite running with 15 open windows. The application
    > doesn't exit until the last window is closed, and no window is privileged
    > over the others.


    It's actually quite easy to implement this, even if you _are_ forced
    to have one primary window. You just have an invisible primary whose
    sole purpose is to "be the application", and then everything else is
    secondary windows. Kinda defeats the purpose of forcing applications
    to have one primary window, though.

    To my thinking, there will always be one primary *thread*, and GUI
    facilities are secondary to the process, never the other way around.
    When the main thread exits, the process ends.

    ChrisA
     
    Chris Angelico, Jul 5, 2011
    #20
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Russell Reagan

    Implicit conversion is evil?

    Russell Reagan, Oct 27, 2003, in forum: C++
    Replies:
    2
    Views:
    330
    Russell Reagan
    Oct 27, 2003
  2. JKop
    Replies:
    10
    Views:
    975
  3. Replies:
    12
    Views:
    1,099
    Ville Vainio
    Feb 17, 2006
  4. Matthias Kaeppler
    Replies:
    2
    Views:
    465
    Victor Bazarov
    Jul 18, 2005
  5. Steven D'Aprano

    Implicit initialization is EXCELLENT

    Steven D'Aprano, Jul 5, 2011, in forum: Python
    Replies:
    18
    Views:
    572
    Ian Kelly
    Jul 7, 2011
Loading...

Share This Page