
import wx

class Sizer(object):
    """Sizer

    This is a Mix-In class to add Pseudo support to a wx sizer.  Just create
    a new class that derives from this class and the wx sizer and intercepts
    any Methods that add to the wx sizer"""
    def __init__(self):
        self.children = [] # list of child Pseudo Controls
    
    # Sizer doesn't use the x1,y1,x2,y2 so allow it to 
    # be called with or without the coordinates
    def Draw(self, dc, x1=0, y1=0, x2=0, y2=0):
        for item in self.children:
            # use sizer coordinates rather than
            # what is passed in
            ix,iy = tuple(item.GetPosition())
            w,h = tuple(item.GetSize())
            c = item.GetUserData()
            c.Draw(dc, ix, iy, ix+w, iy+h)
            
    def GetBestSize(self):
        # this should be handled by the wx.Sizer based class
        return self.GetMinSize()


# Pseudo BoxSizer
class BoxSizer(Sizer, wx.BoxSizer):
    def __init__(self, orient=wx.HORIZONTAL):
        wx.BoxSizer.__init__(self, orient)
        Sizer.__init__(self)

    #-------------------------------------------
    # sizer overrides (only called from Python)
    #-------------------------------------------
    # no support for user data if it's a pseudocontrol
    # since that is already used
    def Add(self, item, proportion=0, flag=0, border=0, userData=None):
        # check to see if it's a pseudo object or sizer
        if isinstance(item, Sizer):
            szitem = wx.BoxSizer.Add(self, item, proportion, flag, border, item)
            self.children.append(szitem)
        elif isinstance(item, Control): # Control should be what ever class your controls come from
            sz = item.GetBestSize()
            # add a spacer to track this object
            szitem = wx.BoxSizer.Add(self, sz, proportion, flag, border, item)
            self.children.append(szitem)
        else:
            wx.BoxSizer.Add(self, item, proportion, flag, border, userData)

    def Prepend(self, item, proportion=0, flag=0, border=0, userData=None):
        # check to see if it's a pseudo object or sizer
        if isinstance(item, Sizer):
            szitem = wx.BoxSizer.Prepend(self, item, proportion, flag, border, item)
            self.children.append(szitem)
        elif isinstance(item, Control): # Control should be what ever class your controls come from
            sz = item.GetBestSize()
            # add a spacer to track this object
            szitem = wx.BoxSizer.Prepend(self, sz, proportion, flag, border, item)
            self.children.insert(0,szitem)
        else:
            wx.BoxSizer.Prepend(self, item, proportion, flag, border, userData)

    def Insert(self, before, item, proportion=0, flag=0, border=0, userData=None):
        # check to see if it's a pseudo object or sizer
        if isinstance(item, Sizer):
            szitem = wx.BoxSizer.Insert(self, before, item, proportion, flag, border, item)
            self.children.append(szitem)
        elif isinstance(item, Control): # Control should be what ever class your controls come from
            sz = item.GetBestSize()
            # add a spacer to track this object
            szitem = wx.BoxSizer.Insert(self, before, sz, proportion, flag, border, item)
            self.children.insert(before,szitem)
        else:
            wx.BoxSizer.Insert(self, before, item, proportion, flag, border, userData)

# Pseudo GridBagSizer
class GridBagSizer(Sizer, wx.GridBagSizer):
    def __init__(self, vgap=0, hgap=0, gridLineWidth=2):
        wx.GridBagSizer.__init__(self, vgap, hgap)
        Sizer.__init__(self)

    #-------------------------------------------
    # sizer overrides (only called from Python)
    #-------------------------------------------
    # no support for user data if it's a pseudocontrol
    # since that is already used
    def Add(self, window, pos, span=wx.DefaultSpan, flag=0, border=0, userData=None):
        # check to see if it's a pseudo object or sizer
        if isinstance(window, Sizer):
            szitem = wx.GridBagSizer.Add(self, window, pos, span, flag, border, window)
            self.children.append(szitem)
        elif isinstance(window, Control):# Control should be what ever class your controls come from
            sz = window.GetBestSize()
            # add a spacer to track this object
            szitem = wx.GridBagSizer.Add(self, sz, pos, span, flag, border, window)
            self.children.append(szitem)
        else:
            wx.GridBagSizer.Add(self, window, pos, span, flag, border, userData)
