Better MVC design

Bug #1136230 reported by Sam Bull
6
This bug affects 1 person
Affects Status Importance Assigned to Milestone
Simple Game Code
In Progress
Medium
Sam Bull

Bug Description

Create a new View object which defines the pictures and fonts for a widget to display. This should be attached to the widget, so the drawing code is separate from the rest of the widget (the controller).

Sam Bull (dreamsorcerer)
Changed in simplegc:
importance: High → Medium
Revision history for this message
Sam Bull (dreamsorcerer) wrote :

Each widget should have a separate View class which defines how the widget should be displayed, and contains the images and theming options.

A rough initial design:

Created with, MyView(size).

View(size):
flags = 0 # Can use custom flags for Surface, such as SRCALPHA
states = ("state1", "state2")
elements = {"extra1": (2,2)} # ID: initial position
fonts = {"label": Font["widget"]} # This should allow for flexible fonts.

def set_image(id, image, resize): Set the image to the given Surface or image file. Specify if the widget size should be changed to the image's size, or the image resized to widget size, or image should be clipped.
def add_text(id, text, pos): Adds text to be rendered at pos (pos should support dynamic rect positioning).
def change_text(id, text=None, pos=None): Change the text and/or position of a piece of text.
def remove_text(id): Remove a piece of text.
def dotted_rect(rect): Draw dotted rect around rect area to show focus, remove dotted rect if False.

def switch(state): Switch to given state.
def render: Renders any changes since last render, and returns the image. Can use custom blit flags etc. in here.
def _prerender: Draw the base images for each state and extra element. Will have access to size, font size etc. Elements need access to widget size, font size and other element sizes. Will be called on render() if not already done, or after a resize. Will likely be broken up into further methods, one for each image.

# Need to be able to move and show/hide elements
view["extra1"].pos = (45, 2)
view["extra1"].show = True
# Maybe use full class for each image, to theme:
view["state1"].set_image(image, resize)
# Or:
for id, image in zip(ids, images): view[id].set_image(image, resize)
# Should also be able to create View with no size, then update size later, this can also be used for dynamic resizing.
view = View()
view.set_size(200, 20)

The widget can call these things to update the view, which caches the changes to be made. When the toolkit wants to blit everything, it calls render() on each widget, which will render the cached changes and return the updated image.

Revision history for this message
Sam Bull (dreamsorcerer) wrote :

To allow dynamic positioning, it might be useful to create a Pos class, which can seamlessly support absolute, relative and dynamic rect positioning (e.g. r.center = other.r.center).

Sam Bull (dreamsorcerer)
Changed in simplegc:
milestone: 0.3 → 0.4
Sam Bull (dreamsorcerer)
Changed in simplegc:
status: Triaged → In Progress
To post a comment you must log in.
This report contains Public information  
Everyone can see this information.

Other bug subscribers

Remote bug watches

Bug watches keep track of this bug in other bug trackers.