执行EVT_KILL_FOCUS事件后,为什么TextCtrl中闪烁的光标消失?

时间:2018-01-24 11:28:40

标签: python python-2.7 wxpython wxwidgets wxtextctrl

我有一个TextCtrl,它有一个EVT_KILL_FOCUS事件,我用它来验证字段的内容,在值错误时提醒用户。打开MessageBox后,我清除了该字段,并将焦点设置为我再次离开验证的字段。问题是应该出现在字段内的文本闪烁光标消失,我不知道为什么或如何修复它。此行为导致用户不知道焦点位于哪个字段中。

有没有人有任何想法?

    ...
    self.txtCode = wx.TextCtrl(self, value='')
    self.txtCode.Bind(wx.EVT_KILL_FOCUS, self.__onTxtCodeKillFocus)
    self.txtCode.Bind(wx.EVT_CHAR_HOOK, self.__onTxtCodeTabKey)

def __validateTxtCodeContent(self):
    if self.txtCode.GetValue() == "":
        self.MessageBox(self, "Error Text", _("Warning"))
        return False
    return True

def __onTxtCodeKillFocus(self, event):
    event.Skip()
    if self.__validateTxtCodeContent() == False:
        self.txtCode.SetValue("")
        self.txtCode.SetFocus()

def __onTxtCodeTabKey(self, event):
    key = event.GetKeyCode()
    shift = event.ShiftDown()

    # 9 = TAB, 13 = ENTER
    if key != 9 and key != 13:
        event.Skip()
        return
    elif key == 9:
        if self.__validateTxtCodeContent():
            if shift:
                self.btnSave.SetFocus()
            else:
                self.txtDescription.SetFocus()
        else:
            self.txtCode.SetValue("")
            self.txtCode.SetFocus()
    else:
        return False

我的验证不仅适用于空字段,而且例如只有空字段。

重要说明:在EVT_CHAR_HOOK事件中,也会发生此行为。

我也尝试过使用它:

self.txtCode.SetValue("")
self.txtCode.SetFocus()
self.txtCode.SetInsertionPointEnd() 
self.txtCode.Refresh()

但它效果不佳。

2 个答案:

答案 0 :(得分:1)

您无法从SetFocus()处理程序中调用KILL_FOCUS。最直接的解决方法是使用CallAfter()稍稍调用它,但即使这会“起作用”,这也是一个非常糟糕的主意,因为你不应该阻止用户离开窗口 - 而且没有办法完全阻止它发生。

只需将代码标记为无效(例如更改其背景),但在丢失代码时不要尝试保留焦点。

P.S。在许多情况下,从焦点事件处理程序调用{​​{1}}也可能是一个坏主意,最好使用MessageBox()wxLogWarning()来延迟显示消息框,直到下一个事件循环迭代。 / p>

答案 1 :(得分:0)

除了瓦迪姆已经说过的话:

  • 你可以对击球进行验证" OK"按钮或对话框/面板即将关闭时

  • 您可以使用wxValidator根据您手头的任务验证用户输入。