Search code examples
widgetwxpythonpanel

wxpython How to change the values of widgets in other panel


My frame was split in three panels, In PanelTwo, There is a TextCtrl, In PanelThree , There is a TextCtrl too, When I input something in the TextCtrl of PanelTwo, I need change the value of the TextCtrl in PanelThree, How to do it?

# -*- coding: utf-8 -*-
import wx
import sys


class PanelOne(wx.Panel):
    """"""
 
    #----------------------------------------------------------------------
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)
        self.SetBackgroundColour("blue")
        font = wx.Font(12, wx.DECORATIVE, wx.NORMAL, wx.BOLD)
        button1 = wx.Button(self, -1, label='Button1')
        button2 = wx.Button(self, -1, label='Button2')
        button1.SetFont(font)
        button2.SetFont(font)
        

        vbox = wx.BoxSizer(wx.VERTICAL)
        vbox.Add(button1, 1, wx.EXPAND)
        vbox.Add(button2, 1, wx.EXPAND)
        self.SetSizer(vbox)
        
class PanelTwo(wx.Panel):
    """"""
    
    #----------------------------------------------------------------------
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)
        textctrl = wx.TextCtrl(self, -1, pos=(200,120), style=wx.TE_PROCESS_ENTER|wx.CENTER)    
        textctrl.Bind(wx.EVT_KEY_DOWN, self.OnEnter)
        
    def OnEnter(self, event):
        keycode = event.GetKeyCode()
        if keycode == wx.WXK_RETURN or keycode == wx.WXK_NUMPAD_ENTER:
            """Here, I want to Print some message in PanelThree textctrl """
        event.Skip()

class PanelThree(wx.Panel):
    """"""
 
    #----------------------------------------------------------------------
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)
        self.SetBackgroundColour("white")
        
        text = wx.TextCtrl(self, -1, 
                            style = wx.TE_MULTILINE|wx.TE_READONLY|
                            wx.HSCROLL)
        vbox = wx.BoxSizer(wx.VERTICAL)
        vbox.Add(text, 1, wx.EXPAND)
        self.SetSizer(vbox)
        
 
########################################################################
class MainPanel(wx.Panel):
    """"""
 
    #----------------------------------------------------------------------
    def __init__(self, parent):
        """Constructor"""
        wx.Panel.__init__(self, parent)
 
        topSplitter = wx.SplitterWindow(self, size=(800,600))
        vSplitter = wx.SplitterWindow(topSplitter)
 
        self.panelOne = PanelOne(vSplitter)
        self.panelTwo = PanelTwo(vSplitter)
        self.panelThree = PanelThree(topSplitter)
        
        vSplitter.SplitVertically(self.panelOne, self.panelTwo)
        vSplitter.SetSashGravity(0.3)

        topSplitter.SplitHorizontally(vSplitter, self.panelThree)
        topSplitter.SetSashGravity(0.5)
 
        sizer = wx.BoxSizer(wx.VERTICAL)
        sizer.Add(topSplitter, 1, wx.EXPAND)
        
        

########################################################################
class MainFrame(wx.Frame):
    """"""
 
    #----------------------------------------------------------------------
    def __init__(self):
        """Constructor"""
        wx.Frame.__init__(self, None, title='my program',
                          size=(800,600))
        panel = MainPanel(self)
        self.Show()
 
#----------------------------------------------------------------------
if __name__ == "__main__":
    app = wx.App(False)
    frame = MainFrame()
    app.MainLoop()


Solution

  • Iam not sure if this is the best way to do it. Anyways, I've modified your code as below:

    # -*- coding: utf-8 -*-
    import wx
    import sys
    
    
    class PanelOne(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            self.SetBackgroundColour("blue")
            font = wx.Font(12, wx.DECORATIVE, wx.NORMAL, wx.BOLD)
            button1 = wx.Button(self, -1, label='Button1')
            button2 = wx.Button(self, -1, label='Button2')
            button1.SetFont(font)
            button2.SetFont(font)
    
    
            vbox = wx.BoxSizer(wx.VERTICAL)
            vbox.Add(button1, 1, wx.EXPAND)
            vbox.Add(button2, 1, wx.EXPAND)
            self.SetSizer(vbox)
    
    class PanelTwo(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            self.textctrl = wx.TextCtrl(self, -1, pos=(200,120), style=wx.TE_PROCESS_ENTER|wx.CENTER)    
    
    
    
    class PanelThree(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            self.SetBackgroundColour("white")
    
            self.text = wx.TextCtrl(self, -1, 
                                style = wx.TE_MULTILINE|wx.TE_READONLY|
                                wx.HSCROLL)
            vbox = wx.BoxSizer(wx.VERTICAL)
            vbox.Add(self.text, 1, wx.EXPAND)
            self.SetSizer(vbox)
    
    
    ########################################################################
    class MainPanel(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
    
            topSplitter = wx.SplitterWindow(self, size=(800,600))
            vSplitter = wx.SplitterWindow(topSplitter)
    
            self.panelOne = PanelOne(vSplitter)
            self.panelTwo = PanelTwo(vSplitter)
            self.panelThree = PanelThree(topSplitter)
    
            self.panelTwo.textctrl.Bind(wx.EVT_KEY_DOWN, self.OnEnter)
    
            vSplitter.SplitVertically(self.panelOne, self.panelTwo)
            vSplitter.SetSashGravity(0.3)
    
            topSplitter.SplitHorizontally(vSplitter, self.panelThree)
            topSplitter.SetSashGravity(0.5)
    
            sizer = wx.BoxSizer(wx.VERTICAL)
            sizer.Add(topSplitter, 1, wx.EXPAND)
    
        def OnEnter(self, event):
            keycode = event.GetKeyCode()
            if keycode == wx.WXK_RETURN or keycode == wx.WXK_NUMPAD_ENTER:
                """Here, I want to Print some message in PanelThree textctrl """
                self.panelThree.text.SetValue("ENTER PRESSED")
            else:
                self.panelThree.text.SetValue("")
            event.Skip()
    
    
    
    ########################################################################
    class MainFrame(wx.Frame):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self):
            """Constructor"""
            wx.Frame.__init__(self, None, title='my program',
                              size=(800,600))
            panel = MainPanel(self)
            self.Show()
    
    #----------------------------------------------------------------------
    if __name__ == "__main__":
        app = wx.App(False)
        frame = MainFrame()
        app.MainLoop()
    

    EDIT:

    However, referring to GreenAsJade's answer to this question, using pubsub seems to be a cleaner way of achieving it.

    # -*- coding: utf-8 -*-
    import wx
    import sys
    from wx.lib.pubsub import pub
    
    class PanelOne(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            self.SetBackgroundColour("blue")
            font = wx.Font(12, wx.DECORATIVE, wx.NORMAL, wx.BOLD)
            button1 = wx.Button(self, -1, label='Button1')
            button2 = wx.Button(self, -1, label='Button2')
            button1.SetFont(font)
            button2.SetFont(font)
    
    
            vbox = wx.BoxSizer(wx.VERTICAL)
            vbox.Add(button1, 1, wx.EXPAND)
            vbox.Add(button2, 1, wx.EXPAND)
            self.SetSizer(vbox)
    
    class PanelTwo(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            textctrl = wx.TextCtrl(self, -1, pos=(200,120), style=wx.TE_PROCESS_ENTER|wx.CENTER)    
            textctrl.Bind(wx.EVT_KEY_DOWN, self.OnEnter)
    
        def OnEnter(self, event):
            keycode = event.GetKeyCode()
            pub.sendMessage("CHANGE_TEXT",value="")
            if keycode == wx.WXK_RETURN or keycode == wx.WXK_NUMPAD_ENTER:
                """Here, I want to Print some message in PanelThree textctrl """
                pub.sendMessage("CHANGE_TEXT", value = "Enter Pressed")
            event.Skip()
    
    class PanelThree(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
            self.SetBackgroundColour("white")
    
            self.text = wx.TextCtrl(self, -1, 
                                style = wx.TE_MULTILINE|wx.TE_READONLY|
                                wx.HSCROLL)
            vbox = wx.BoxSizer(wx.VERTICAL)
            vbox.Add(self.text, 1, wx.EXPAND)
            self.SetSizer(vbox)
            pub.subscribe(self.PrintMessage, "CHANGE_TEXT")
    
        def PrintMessage(self, value):
            self.text.SetValue(value)
    
    
    
    ########################################################################
    class MainPanel(wx.Panel):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self, parent):
            """Constructor"""
            wx.Panel.__init__(self, parent)
    
            topSplitter = wx.SplitterWindow(self, size=(800,600))
            vSplitter = wx.SplitterWindow(topSplitter)
    
            self.panelOne = PanelOne(vSplitter)
            self.panelTwo = PanelTwo(vSplitter)
            self.panelThree = PanelThree(topSplitter)
    
            vSplitter.SplitVertically(self.panelOne, self.panelTwo)
            vSplitter.SetSashGravity(0.3)
    
            topSplitter.SplitHorizontally(vSplitter, self.panelThree)
            topSplitter.SetSashGravity(0.5)
    
            sizer = wx.BoxSizer(wx.VERTICAL)
            sizer.Add(topSplitter, 1, wx.EXPAND)
    
    
    
    ########################################################################
    class MainFrame(wx.Frame):
        """"""
    
        #----------------------------------------------------------------------
        def __init__(self):
            """Constructor"""
            wx.Frame.__init__(self, None, title='my program',
                              size=(800,600))
            panel = MainPanel(self)
            self.Show()
    
    #----------------------------------------------------------------------
    if __name__ == "__main__":
        app = wx.App(False)
        frame = MainFrame()
        app.MainLoop()