2017-10-19 14 views
0

의 난 그냥 일주일 전에 Tkinter를시작하고 내가 파이썬 작성된 자동 코드 생성 스크립트에 GUI를 연결하기 위해 노력하고, 이벤트를 트리거합니다. 나는이 포럼에서 많은 도움을 얻어 거의 모든 사건을 다루었지만이 특별한 사건은 저를 곤혹스럽게합니다.Tkinter를 -이 항목 위젯에 기록 할 때 순서에 관계없이

2 개의 입력 위젯이 필요하며 입력이 완료되면 바로 그 관계를 계산합니다 (즉, 함수를 트리거하는 버튼 위젯 없음). 나는 그것이 이벤트로 끝나야 만한다는 것을 깨닫는다. 그래서 나는 노력하고있는 다음의 것을 생각해 낸다. 그러나 나는 그것에 관해 'pythonic'이 아닐 것 같은 느낌이 든다.

from Tkinter import * 

root = Tk() 
root.title("Test") 

def OnValidate(S): 
    if S.isdigit(): 
     return True 
    else: 
     return False 

def insert_text_widg(widg,msg): 
    widg.delete(1.0,END) 
    widg.insert(INSERT,msg) 

# Checks the required conditions 
def check_var1(event): 
    try: 
     temp1=int(var1_ent.get()) 
     temp2=int(var2_ent.get()) 
    except ValueError: 
     return 
    if(temp2 > temp1): 
     insert_text_widg(log_text,"ERROR: Var2 cannot be greater than Var1") 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='indian red',fg='white') 
    elif ((temp1 - temp2) % 2) == 1: 
     insert_text_widg(log_text,"ERROR: Difference cannot be odd") 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='indian red',fg='white') 
    else: 
     log_text.delete(1.0,END) 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='white',fg='black') 

# Duplicate of check_var1 
def check_var2(event): 
    try: 
     temp2=int(var2_ent.get()) 
     temp1=int(var1_ent.get()) 
    except ValueError: 
     return 
    if(temp2 > temp1): 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='indian red',fg='white') 
     insert_text_widg(log_text,"ERROR: Var2 cannot be greater than Var1") 
    elif ((temp1 - temp2) % 2) == 1: 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='indian red',fg='white') 
     insert_text_widg(log_text,"ERROR: Difference cannot be odd") 
    else: 
     log_text.delete(1.0,END) 
     for ent in [var1_ent,var2_ent]: 
      ent.configure(bg='white',fg='black') 


# App Configuration 
vcmd = (root.register(OnValidate),'%S') 

var1_lab = Label(root,text='Var1 :') 
var1_lab.pack() 

var1_ent = Entry(root,validate="key",validatecommand=vcmd) 
var1_ent.bind("<KeyRelease>",check_var1) 
var1_ent.pack() 

var2_lab = Label(root,text='Var2 :') 
var2_lab.pack() 

var2_ent = Entry(root,validate="key",validatecommand=vcmd) 
var2_ent.bind("<KeyRelease>",check_var2) 
var2_ent.pack() 

log_text = Text(root) 
log_text.pack() 

root.mainloop() 

은 본질적으로 내가 하나에 병합 찾고 같은 일을 두 가지 기능 (check_var1() & check_var2())이 있습니다. Entry 위젯 중 하나가 변경 사항을 등록하는 즉시 점검을 수행해야합니다.

그래서 짧은에, 나는 그들이에 입력되는의 순서에 관계없이, 즉시 두 항목 위젯에 입력으로() 함수 check_var1를 호출 할 수있는 방법을 싶습니다.

어떤 도움이나 옳은 방향으로 찔러 주시면 대단히 감사하겠습니다.

+0

왜 사용하지 말아 : var2_ent.bind ("", check_var1을) ??? –

+0

주된 문제점은 사용자가 입력을 입력하는 순서입니다. 나는 당신의 제안을 시도했지만 Var1이 비어있을 때 사용자가 먼저 Var2를 입력하고 리턴하면 예외가 잡힌다. 어쩌면 나는 예외를 잘못 처리하고 있는가? – amuneeb

답변

0

내가 정확히 무엇을 필요로하는지 이해한다면 .trace() 기능을 사용하는 것이 가장 좋을 것 같습니다.

이렇게하면 변수에 쓰거나 읽을 때마다 콜백을 발생시킬 수 있습니다.

이 경우 두 개의 변수 var1var2 (간단히하기 위해)을 만들고이 값에 StringVar()을 할당합니다.

Entry 위젯의 textvariable 속성을 각각 var1var2으로 설정합니다.

우리는 다음 .trace() 자체를 설정해야합니다, 그래서 우리는 콜백 함수에게 두 변수에 기록 될 때마다 실행합니다 ("w" 쓰기를 의미) var1.trace("w", callback)var2.trace("w", callback)를 호출합니다.

즉, Entry이 먼저 수정 되더라도 우리는 콜백을 받고 더 중요한 것은 모든 수정에 대한 콜백을 얻음을 의미합니다.

는 작업, 예를 들어 아래를 참조

from tkinter import * 

class App: 
    def __init__(self, root): 
     self.root = root 
     self.var1 = StringVar() 
     self.var2 = StringVar() 
     self.var1.trace("w", self.callback) 
     self.var2.trace("w", self.callback) 
     self.entry1 = Entry(self.root, text="Ok", textvariable=self.var1) 
     self.entry2 = Entry(self.root, text="Ok", textvariable=self.var2) 
     self.label = Label(self.root) 
     self.entry1.pack() 
     self.entry2.pack() 
     self.label.pack() 
    def callback(self, *args): 
     self.label.configure(text=self.entry1.get()+self.entry2.get()) 

root = Tk() 
App(root) 
root.mainloop() 
+1

정말 고마워요. – amuneeb