OO design, Python, and GUIs

C

Christopher Culver

I'm creating a home-library management program with Python 2.2, PyGTK, and
Glade. While I've been many little programs before, this is my first large
application in Python. My question is how I should organise the OO design
of such a program. There should be, I gather, a core class "MainClass",
which coordinates everything, other specialised classes which report to
MainClass, and the GUI should ideally be in its own class "GuiClass".

Now GuiClass at the moment doesn't know anything about MainClass. When the
program is started, an instance "mainClass" is created, which in turn
creates an instance "guiClass". But how can guiClass report anything to
the mainClass? For example, when the user selects a new file in the GUI,
how can I send the chosen pathname to mainClass?

I imagine that I have to initalise the GuiClass instance in such a way
that it knows about mainClass enough to be able to call its methods, but
I've been unable find out how mainClass could pass itself to the GuiClass
__init__.

Be gentle, I'm somewhat of a newbie. If there's documentation out there on
this, I'll happily take a look.

Christopher Culver
 
P

Peter Maas

Christopher said:
I'm creating a home-library management program with Python 2.2, PyGTK, and
Glade. While I've been many little programs before, this is my first large
application in Python. My question is how I should organise the OO design
of such a program. There should be, I gather, a core class "MainClass",
which coordinates everything, other specialised classes which report to
MainClass, and the GUI should ideally be in its own class "GuiClass".

There is a start up module that will talk to you first, I'd call it
homelib.py. It does the necessary initialisations like loading the
GUI resources, opening the database etc. If you want to encapsulate
this in a class you could call it main or start. I wouldn't give the
feature providing classes generic names like "main". They do something
special, so I would give them names that tell something about their
resonsibilities, e.g. library, libraryItem, book, magazine, storage,
editView, listView etc. Aggregate related classes in a module, related
modules in a package (if you have lots of modules).

The feature modules would be imported by the start up module. It
wouldn't be bad to have a rough plan of your software before you
start to write code. The building blocks (packages, modules) of
your app have "uses" relations. If module a uses b then a has to
import b. A layered approach would probably be helpful:

u | startup, user interface
t |-------------------------------
i | engine (provides the features)
l |-------------------------------
s | storage (file, db, network)

Each layer uses its neighbour below, all layers use utils. The layers
could be distributed across several programs (multi-tiered app) but
that's not necessary, of course.

Mit freundlichen Gruessen,

Peter Maas
 
K

Kevin Dahlhausen

I'm creating a home-library management program with Python 2.2, PyGTK, and
Glade. While I've been many little programs before, this is my first large
application in Python. My question is how I should organise the OO design
of such a program.

One solution is to use a layered architeture:

.---------------.
| Presentation |
'------+--------'
|
.---------------.
| Application |
'------+--------'
|
.---------------.
| Persistence |
'---------------'

Each layer would be a python package (or multiple
packages if your app is large). The presentation
layer contains your gui classes. The application
layer contains classes that implement the behavior
of the application. The persistence layer handles
storage of your domain objects. Some people would
add a 'domain layer' between the application and
the persistence layer. I suppose that depends on
the size of your project, but for something small
it's overkill and your domain objects are very
likely generated by an oo-rdb mapper tool anyway.

People have differing opinions over whether or not
your gui classes should directly make use of the
domain classes. Technically, layers in this
architecture should not know about layers other
than the immediate one above or below. Java
people like to create structures to pass data
between layers. I think it's not a very good use
of time and prefer to use the domain objects - the
domain should be one thing not changing that much
(a book's a book, right)?

A decent discussion of this architecture is at:
http://www.therationaledge.com/content/oct_01/t_layeringStrategies_pe.html

The best thing to pull from this is to keep the gui
stuff in its own package python package and put
a little effort into keeping the gui out of
your main application code. This will give you
more options in the future - perhaps you'll find
you'd like a web version of the library, or that
FLTK is a sharper looking gui, or you'd like have
a text reader read the list.
 
A

Alan Gauld

of such a program. There should be, I gather, a core class "MainClass",
which coordinates everything, other specialised classes which report to
MainClass, and the GUI should ideally be in its own class "GuiClass".

That's one solution, it could also be a set of classes - one per
window or "form".
Now GuiClass at the moment doesn't know anything about MainClass. When the
program is started, an instance "mainClass" is created, which in turn
creates an instance "guiClass". But how can guiClass report anything to
the mainClass?

If when you create the guiClass you pass a refernce to mainClass
into the constructor the gui can send messages back to it:

class mainClass:
def __init__(self):
...
self.gui = guiClass(self)
...

class guiClass:
def __init__(self, application):
self.application = application
...
def someCommand(self): # called by a widget somewhere
self.application.someMethod(self.widgetValue)
...

So when the widgets call someCommand it sends the gui
data(widgetValue) back to the mainClass instance which it stores
in its self.application member.

You need to define the protocol between the two classes.
There are some fancier variations on this to improve reuse of
Gui elements, do a search on Model View Controller or MVC on
Google for other ideas.
I imagine that I have to initalise the GuiClass instance in such a way
that it knows about mainClass enough to be able to call its methods, but
I've been unable find out how mainClass could pass itself to the GuiClass
__init__.

The self value in the mainClass methods is a reference to the
mainClass instance. Just pass self to the GUI init.

Alan G.
Author of the Learn to Program website
http://www.freenetpages.co.uk/hp/alan.gauld
 

Ask a Question

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

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,581
Members
45,057
Latest member
KetoBeezACVGummies

Latest Threads

Top