]> git.saurik.com Git - wxWidgets.git/blobdiff - wxPython/demo/Main.py
don't apply tab control background when using wxUniv, it renders background itself
[wxWidgets.git] / wxPython / demo / Main.py
index 9fd4ad208a4ff537ed4704ddd96eaf41bad7e0fa..458c1a713acb804719e703a2be2e3aa6989d6894 100644 (file)
@@ -47,12 +47,11 @@ import images
 _treeList = [
     # new stuff
     ('Recent Additions/Updates', [
-        'OGL',
-        'FloatCanvas',
+        'StandardPaths',
         ]),
 
     # managed windows == things with a (optional) caption you can close
-    ('Base Frames and Dialogs', [
+    ('Frames and Dialogs', [
         'Dialog',
         'Frame',
         'MDIWindows',
@@ -65,7 +64,6 @@ _treeList = [
         'ColourDialog',
         'DirDialog',
         'FileDialog',
-        'FileDialog_Save',
         'FindReplaceDialog',
         'FontDialog',
         'MessageDialog',
@@ -90,6 +88,7 @@ _treeList = [
         'CheckBox',
         'CheckListBox',
         'Choice',
+        'Choicebook',
         'ComboBox',
         'Gauge',
         'Grid',
@@ -97,6 +96,7 @@ _treeList = [
         'ListBox',
         'ListCtrl',
         'ListCtrl_virtual',
+        'ListCtrl_edit',
         'Listbook',
         'Menu',
         'Notebook',
@@ -113,6 +113,7 @@ _treeList = [
         'StaticBitmap',
         'StaticText',
         'StatusBar',
+        'StockButtons',
         'TextCtrl',
         'ToggleButton',
         'ToolBar',
@@ -163,6 +164,7 @@ _treeList = [
         'StyledTextCtrl_2',
         'TablePrint',
         'Throbber',
+        'Ticker',
         'TimeCtrl',
         'VListBox',
         ]),
@@ -189,7 +191,7 @@ _treeList = [
         'PythonEvents',
         'Threads',
         'Timer',
-        'infoframe',
+        ##'infoframe',    # needs better explaination and some fixing
         ]),
 
     # Clipboard and DnD
@@ -214,7 +216,7 @@ _treeList = [
     # Other stuff
     ('Miscellaneous', [
         'ColourDB',
-        'DialogUnits',
+        ##'DialogUnits',   # needs more explainations
         'DrawXXXList',
         'FileHistory',
         'FontEnumerator',
@@ -223,6 +225,7 @@ _treeList = [
         'PrintFramework',
         'ShapedWindow',
         'Sound',
+        'StandardPaths',
         'Unicode',
         ]),
 
@@ -249,9 +252,10 @@ class MyLog(wx.PyLog):
         self.logTime = logTime
 
     def DoLogString(self, message, timeStamp):
-        if self.logTime:
-            message = time.strftime("%X", time.localtime(timeStamp)) + \
-                      ": " + message
+        #print message, timeStamp
+        #if self.logTime:
+        #    message = time.strftime("%X", time.localtime(timeStamp)) + \
+        #              ": " + message
         if self.tc:
             self.tc.AppendText(message + '\n')
 
@@ -260,6 +264,60 @@ class MyTP(wx.PyTipProvider):
     def GetTip(self):
         return "This is my tip"
 
+#---------------------------------------------------------------------------
+# A class to be used to simply display a message in the demo pane
+# rather than running the sample itself.
+
+class MessagePanel(wx.Panel):
+    def __init__(self, parent, message, caption='', flags=0):
+        wx.Panel.__init__(self, parent)
+
+        # Make widgets
+        if flags:
+            artid = None
+            if flags & wx.ICON_EXCLAMATION:
+                artid = wx.ART_WARNING            
+            elif flags & wx.ICON_ERROR:
+                artid = wx.ART_ERROR
+            elif flags & wx.ICON_QUESTION:
+                artid = wx.ART_QUESTION
+            elif flags & wx.ICON_INFORMATION:
+                artid = wx.ART_INFORMATION
+
+            if artid is not None:
+                bmp = wx.ArtProvider.GetBitmap(artid, wx.ART_MESSAGE_BOX, (32,32))
+                icon = wx.StaticBitmap(self, -1, bmp)
+            else:
+                icon = (32,32) # make a spacer instead
+
+        if caption:
+            caption = wx.StaticText(self, -1, caption)
+            caption.SetFont(wx.Font(28, wx.SWISS, wx.NORMAL, wx.BOLD))
+
+        message = wx.StaticText(self, -1, message)
+
+        # add to sizers for layout
+        tbox = wx.BoxSizer(wx.VERTICAL)
+        if caption:
+            tbox.Add(caption)
+            tbox.Add((10,10))
+        tbox.Add(message)
+        
+        hbox = wx.BoxSizer(wx.HORIZONTAL)
+        hbox.Add((10,10), 1)
+        hbox.Add(icon)
+        hbox.Add((10,10))
+        hbox.Add(tbox)
+        hbox.Add((10,10), 1)
+
+        box = wx.BoxSizer(wx.VERTICAL)
+        box.Add((10,10), 1)
+        box.Add(hbox, 0, wx.EXPAND)
+        box.Add((10,10), 2)
+
+        self.SetSizer(box)
+        
+        
 
 #---------------------------------------------------------------------------
 # A class to be used to display source code in the demo.  Try using the
@@ -274,7 +332,7 @@ try:
 
     class DemoCodeEditor(PythonSTC):
         def __init__(self, parent):
-            PythonSTC.__init__(self, parent, -1, wx.BORDER_NONE)
+            PythonSTC.__init__(self, parent, -1, style=wx.BORDER_NONE)
             self.SetUpEditor()
 
         # Some methods to make it compatible with how the wxTextCtrl is used
@@ -395,8 +453,7 @@ try:
             # The rest remains unchanged.
 
             # Line numbers in margin
-            self.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')
-    
+            self.StyleSetSpec(wx.stc.STC_STYLE_LINENUMBER,'fore:#000000,back:#99A9C2')    
             # Highlighted brace
             self.StyleSetSpec(wx.stc.STC_STYLE_BRACELIGHT,'fore:#00009D,back:#FFFF00')
             # Unmatched brace
@@ -444,8 +501,8 @@ try:
 except ImportError:
     class DemoCodeEditor(wx.TextCtrl):
         def __init__(self, parent):
-            wx.TextCtrl.__init__(self, parent, -1, style = wx.TE_MULTILINE | 
-                                 wx.HSCROLL | wx.TE_RICH2 | wx.TE_NOHIDESEL)
+            wx.TextCtrl.__init__(self, parent, -1, style =
+                                 wx.TE_MULTILINE | wx.HSCROLL | wx.TE_RICH2 | wx.TE_NOHIDESEL)
 
         def RegisterModifiedEvent(self, eventHandler):
             self.Bind(wx.EVT_TEXT, eventHandler)
@@ -483,7 +540,9 @@ modDefault = modOriginal
 class DemoCodePanel(wx.Panel):
     """Panel for the 'Demo Code' tab"""
     def __init__(self, parent, mainFrame):
-        wx.Panel.__init__(self, parent)
+        wx.Panel.__init__(self, parent, size=(1,1))
+        if 'wxMSW' in wx.PlatformInfo:
+            self.Hide()
         self.mainFrame = mainFrame
         self.editor = DemoCodeEditor(self)
         self.editor.RegisterModifiedEvent(self.OnCodeModified)
@@ -531,6 +590,7 @@ class DemoCodePanel(wx.Panel):
     def ActiveModuleChanged(self):
         self.LoadDemoSource(self.demoModules.GetSource())
         self.UpdateControlState()
+        self.ReloadDemo()
 
         
     def LoadDemoSource(self, source):
@@ -574,12 +634,11 @@ class DemoCodePanel(wx.Panel):
             busy = wx.BusyInfo("Reloading demo module...")
             self.demoModules.SetActive(modSelected)
             self.ActiveModuleChanged()
-            self.ReloadDemo()
 
 
     def ReloadDemo(self):
         if self.demoModules.name != __name__:
-            self.mainFrame.RunModule(False)
+            self.mainFrame.RunModule()
 
                 
     def OnCodeModified(self, event):
@@ -625,7 +684,6 @@ class DemoCodePanel(wx.Panel):
         busy = wx.BusyInfo("Reloading demo module...")
         self.demoModules.LoadFromFile(modModified, modifiedFilename)
         self.ActiveModuleChanged()
-        self.ReloadDemo()
 
 
     def OnRestore(self, event): # Handles the "Delete Modified" button
@@ -634,7 +692,6 @@ class DemoCodePanel(wx.Panel):
         os.unlink(modifiedFilename) # Delete the modified copy
         busy = wx.BusyInfo("Reloading demo module...")
         self.ActiveModuleChanged()
-        self.ReloadDemo()
 
 
 #---------------------------------------------------------------------------
@@ -716,8 +773,6 @@ class DemoModules:
         # load modified module (if one exists)
         if DoesModifiedExist(name):
            self.LoadFromFile(modModified, GetModifiedFilename(name))
-           if (modDefault == modModified):
-               self.SetActive(modModified)
 
 
     def LoadFromFile(self, modID, filename):
@@ -814,35 +869,6 @@ class DemoModules:
         self.modules[modID][2] = ""
 
 
-#---------------------------------------------------------------------------
-class ReloadDemoPanel(wx.Panel):
-    """
-    Panel put into the demo tab when the demo just shows some
-    top-level window.  Enables the demo to be reloaded after being
-    closed.
-    """
-
-    infoText = "This demo runs outside the main window"
-    
-    def __init__(self, parent, codePanel, log):
-        wx.Panel.__init__(self, parent, -1)
-        self.codePanel = codePanel
-        self.log = log
-
-        self.label = wx.StaticText(self, -1, self.infoText)
-        self.btnReload = wx.Button(self, -1, "Reload Demo")
-        self.btnReload.Bind(wx.EVT_BUTTON, self.OnReload)
-
-        self.box = wx.BoxSizer(wx.VERTICAL)
-        self.box.Add(self.label, 0, wx.ALIGN_CENTER | wx.ALL, 10)
-        self.box.Add(self.btnReload, 0, wx.ALIGN_CENTER | wx.ALL, 10)
-
-        self.box.Fit(self)
-        self.SetSizer(self.box)
-        
-    def OnReload(self, event):
-        self.codePanel.ReloadDemo()
-
 #---------------------------------------------------------------------------
 
 class DemoError:
@@ -977,37 +1003,111 @@ class DemoErrorPanel(wx.Panel):
 
 #---------------------------------------------------------------------------
 
+class DemoTaskBarIcon(wx.TaskBarIcon):
+    TBMENU_RESTORE = wx.NewId()
+    TBMENU_CLOSE   = wx.NewId()
+    TBMENU_CHANGE  = wx.NewId()
+    TBMENU_REMOVE  = wx.NewId()
+    
+    def __init__(self, frame):
+        wx.TaskBarIcon.__init__(self)
+        self.frame = frame
+
+        # Set the image
+        icon = self.MakeIcon(images.getWXPdemoImage())
+        self.SetIcon(icon, "wxPython Demo")
+        self.imgidx = 1
+        
+        # bind some events
+        self.Bind(wx.EVT_TASKBAR_LEFT_DCLICK, self.OnTaskBarActivate)
+        self.Bind(wx.EVT_MENU, self.OnTaskBarActivate, id=self.TBMENU_RESTORE)
+        self.Bind(wx.EVT_MENU, self.OnTaskBarClose, id=self.TBMENU_CLOSE)
+        self.Bind(wx.EVT_MENU, self.OnTaskBarChange, id=self.TBMENU_CHANGE)
+        self.Bind(wx.EVT_MENU, self.OnTaskBarRemove, id=self.TBMENU_REMOVE)
+
+
+    def CreatePopupMenu(self):
+        """
+        This method is called by the base class when it needs to popup
+        the menu for the default EVT_RIGHT_DOWN event.  Just create
+        the menu how you want it and return it from this function,
+        the base class takes care of the rest.
+        """
+        menu = wx.Menu()
+        menu.Append(self.TBMENU_RESTORE, "Restore wxPython Demo")
+        menu.Append(self.TBMENU_CLOSE,   "Close wxPython Demo")
+        menu.AppendSeparator()
+        menu.Append(self.TBMENU_CHANGE, "Change the TB Icon")
+        menu.Append(self.TBMENU_REMOVE, "Remove the TB Icon")
+        return menu
+
+
+    def MakeIcon(self, img):
+        """
+        The various platforms have different requirements for the
+        icon size...
+        """
+        if "wxMSW" in wx.PlatformInfo:
+            img = img.Scale(16, 16)
+        elif "wxGTK" in wx.PlatformInfo:
+            img = img.Scale(22, 22)
+        # wxMac can be any size upto 128x128, so leave the source img alone....
+        icon = wx.IconFromBitmap(img.ConvertToBitmap() )
+        return icon
+    
+
+    def OnTaskBarActivate(self, evt):
+        if self.frame.IsIconized():
+            self.frame.Iconize(False)
+        if not self.frame.IsShown():
+            self.frame.Show(True)
+        self.frame.Raise()
+
+
+    def OnTaskBarClose(self, evt):
+        self.frame.Close()
+
+
+    def OnTaskBarChange(self, evt):
+        names = [ "WXPdemo", "WXP", "Mondrian", "Test2m",
+                  "Blom08m", "Blom10m", "Blom15m" ]
+        name = names[self.imgidx]
+        
+        getFunc = getattr(images, "get%sImage" % name)
+        self.imgidx += 1
+        if self.imgidx >= len(names):
+            self.imgidx = 0
+            
+        icon = self.MakeIcon(getFunc())
+        self.SetIcon(icon, "This is a new icon: " + name)
+
+
+    def OnTaskBarRemove(self, evt):
+        self.RemoveIcon()
+
+
+#---------------------------------------------------------------------------
 class wxPythonDemo(wx.Frame):
     overviewText = "wxPython Overview"
 
     def __init__(self, parent, title):
-        wx.Frame.__init__(self, parent, -1, title, size = (950, 750),
+        wx.Frame.__init__(self, parent, -1, title, size = (950, 720),
                           style=wx.DEFAULT_FRAME_STYLE | wx.NO_FULL_REPAINT_ON_RESIZE)
 
+        self.SetMinSize((640,480))
+
         self.loaded = False
         self.cwd = os.getcwd()
         self.curOverview = ""
         self.demoPage = None
         self.codePage = None
-        self.useModified = False
         self.shell = None
+        self.firstTime = True
 
-        icon = images.getMondrianIcon()
+        icon = images.getWXPdemoIcon()
         self.SetIcon(icon)
 
-        if wx.Platform != '__WXMAC__':
-            # setup a taskbar icon, and catch some events from it
-            dim = 16  # (may want to use 22 on wxGTK, but 16 looks okay too)
-            icon = wx.IconFromBitmap(
-                images.getMondrianImage().Scale(dim,dim).ConvertToBitmap() )
-            #icon = wx.Icon('bmp_source/mondrian.ico', wx.BITMAP_TYPE_ICO)
-            #icon = images.getMondrianIcon()
-            self.tbicon = wx.TaskBarIcon()
-            self.tbicon.SetIcon(icon, "wxPython Demo")
-            self.tbicon.Bind(wx.EVT_TASKBAR_LEFT_DCLICK, self.OnTaskBarActivate)
-            self.tbicon.Bind(wx.EVT_TASKBAR_RIGHT_UP, self.OnTaskBarMenu)
-            self.tbicon.Bind(wx.EVT_MENU, self.OnTaskBarActivate, id=self.TBMENU_RESTORE)
-            self.tbicon.Bind(wx.EVT_MENU, self.OnTaskBarClose, id=self.TBMENU_CLOSE)
+        self.tbicon = DemoTaskBarIcon(self)
 
         wx.CallAfter(self.ShowTip)
 
@@ -1043,7 +1143,7 @@ class wxPythonDemo(wx.Frame):
  
         item = menu.Append(-1, 'E&xit\tAlt-X', 'Get the heck outta here!')
         self.Bind(wx.EVT_MENU, self.OnFileExit, item)
-        wx.App_SetMacExitMenuItemId(item.GetId())
+        wx.App.SetMacExitMenuItemId(item.GetId())
         self.mainmenu.Append(menu, '&File')
 
         # Make a Demo menu
@@ -1083,7 +1183,7 @@ class wxPythonDemo(wx.Frame):
                                 'An interactive interpreter window with the demo app and frame objects in the namesapce')
         menu.AppendSeparator()
         helpItem = menu.Append(-1, '&About\tCtrl-H', 'wxPython RULES!!!')
-        wx.App_SetMacAboutMenuItemId(helpItem.GetId())
+        wx.App.SetMacAboutMenuItemId(helpItem.GetId())
 
         self.Bind(wx.EVT_MENU, self.OnOpenShellWindow, shellItem)
         self.Bind(wx.EVT_MENU, self.OnHelpAbout, helpItem)
@@ -1150,7 +1250,7 @@ class wxPythonDemo(wx.Frame):
             panel.Bind(wx.EVT_ERASE_BACKGROUND, EmptyHandler)
 
         if "gtk2" in wx.PlatformInfo:
-            self.ovr.NormalizeFontSizes()
+            self.ovr.SetStandardFonts()
         self.SetOverview(self.overviewText, mainOverview)
 
 
@@ -1169,12 +1269,15 @@ class wxPythonDemo(wx.Frame):
         #wx.Log_SetTraceMask(wx.TraceMessages)
 
 
+        self.Bind(wx.EVT_ACTIVATE, self.OnActivate)
+        wx.GetApp().Bind(wx.EVT_ACTIVATE_APP, self.OnAppActivate)
+
         # add the windows to the splitter and split it.
         splitter2.SplitHorizontally(self.nb, self.log, -160)
         splitter.SplitVertically(self.tree, splitter2, 200)
 
-        splitter.SetMinimumPaneSize(20)
-        splitter2.SetMinimumPaneSize(20)
+        splitter.SetMinimumPaneSize(120)
+        splitter2.SetMinimumPaneSize(60)
 
         # Make the splitter on the right expand the top window when resized
         def SplitterOnSize(evt):
@@ -1263,7 +1366,7 @@ class wxPythonDemo(wx.Frame):
                 if os.path.exists(GetOriginalFilename(demoName)):
                     wx.LogMessage("Loading demo %s.py..." % demoName)
                     self.demoModules = DemoModules(demoName)
-                    self.RunModule(True)
+                    self.LoadDemoSource()
                     self.tree.Refresh()
                 else:
                     self.SetOverview("wxPython", mainOverview)
@@ -1279,16 +1382,15 @@ class wxPythonDemo(wx.Frame):
         self.codePage.LoadDemo(self.demoModules)
         
     #---------------------------------------------
-    def RunModule(self, loadSource):
+    def RunModule(self):
         """Runs the active module"""
 
         module = self.demoModules.GetActive()
         self.ShutdownDemoModule()
         overviewText = ""
         
-        # o If the demo returns a window it is placed in a tab.
-        # o Otherwise, a placeholder tab is created, informing the user that the
-        #   demo runs outside the main window, and allowing it to be reloaded.
+        # o The RunTest() for all samples must now return a window that can
+        #   be palced in a tab in the main notebook.
         # o If an error occurs (or has occured before) an error tab is created.
         
         if module is not None:
@@ -1298,21 +1400,27 @@ class wxPythonDemo(wx.Frame):
 
             try:
                 self.demoPage = module.runTest(self, self.nb, self)
-                if self.demoPage is None:
-                    self.demoPage = ReloadDemoPanel(self.nb, self.codePage, self)
             except:
                 self.demoPage = DemoErrorPanel(self.nb, self.codePage,
-                                               DemoError(sys.exc_info()), self)                
+                                               DemoError(sys.exc_info()), self)
+
+            assert self.demoPage is not None, "runTest must return a window!"
+            
         else:
             # There was a previous error in compiling or exec-ing
             self.demoPage = DemoErrorPanel(self.nb, self.codePage,
                                            self.demoModules.GetErrorInfo(), self)
-
-        if loadSource:
-            self.LoadDemoSource()
-        self.UpdateNotebook()
+            
         self.SetOverview(self.demoModules.name + " Overview", overviewText)
 
+        if self.firstTime:
+            # cahnge to the demo page the first time a module is run
+            self.UpdateNotebook(2)
+            self.firstTime = False
+        else:
+            # otherwise just stay on the same tab in case the user has changed to another one
+            self.UpdateNotebook()
+
     #---------------------------------------------
     def ShutdownDemoModule(self):
         if self.demoPage:
@@ -1479,6 +1587,7 @@ class wxPythonDemo(wx.Frame):
         self.demoPage = None
         self.codePage = None
         self.mainmenu = None
+        self.tbicon.Destroy()
         self.Destroy()
 
 
@@ -1516,38 +1625,10 @@ class wxPythonDemo(wx.Frame):
             self.tree.EnsureVisible(selectedDemo)
 
 
-    #---------------------------------------------
-    def OnTaskBarActivate(self, evt):
-        if self.IsIconized():
-            self.Iconize(False)
-        if not self.IsShown():
-            self.Show(True)
-        self.Raise()
-
-    #---------------------------------------------
-
-    TBMENU_RESTORE = 1000
-    TBMENU_CLOSE   = 1001
-
-    def OnTaskBarMenu(self, evt):
-        menu = wx.Menu()
-        menu.Append(self.TBMENU_RESTORE, "Restore wxPython Demo")
-        menu.Append(self.TBMENU_CLOSE,   "Close")
-        self.tbicon.PopupMenu(menu)
-        menu.Destroy()
-
-    #---------------------------------------------
-    def OnTaskBarClose(self, evt):
-        self.Close()
-
-        # because of the way wx.TaskBarIcon.PopupMenu is implemented we have to
-        # prod the main idle handler a bit to get the window to actually close
-        wx.GetApp().ProcessIdle()
-
 
     #---------------------------------------------
     def OnIconfiy(self, evt):
-        wx.LogMessage("OnIconfiy: %d" % evt.Iconized())
+        wx.LogMessage("OnIconfiy: %s" % evt.Iconized())
         evt.Skip()
 
     #---------------------------------------------
@@ -1555,8 +1636,15 @@ class wxPythonDemo(wx.Frame):
         wx.LogMessage("OnMaximize")
         evt.Skip()
 
+    #---------------------------------------------
+    def OnActivate(self, evt):
+        wx.LogMessage("OnActivate: %s" % evt.GetActive())
+        evt.Skip()
 
-
+    #---------------------------------------------
+    def OnAppActivate(self, evt):
+        wx.LogMessage("OnAppActivate: %s" % evt.GetActive())
+        evt.Skip()
 
 #---------------------------------------------------------------------------
 #---------------------------------------------------------------------------
@@ -1607,7 +1695,7 @@ def main():
         os.chdir(demoPath)
     except:
         pass
-    app = MyApp(0) ##wx.Platform == "__WXMAC__")
+    app = MyApp(False)
     app.MainLoop()
 
 #---------------------------------------------------------------------------