Có bất kỳ ví dụ nào về cách thiết lập đăng nhập bằng Python vào một tiện ích văn bản Tkinter không? Tôi đã thấy điều này được sử dụng trong một số ứng dụng nhưng không thể tìm ra cách để chỉ đạo việc ghi nhật ký vào bất kỳ thứ gì khác ngoài tệp nhật ký.Đăng nhập bằng Python vào tiện ích văn bản Tkinter
Trả lời
Bạn nên phân lớp logging.Handler
, ví dụ:
import logging
from Tkinter import INSERT
class WidgetLogger(logging.Handler):
def __init__(self, widget):
logging.Handler.__init__(self)
self.widget = widget
def emit(self, record):
# Append message (record) to the widget
self.widget.insert(INSERT, record + '\n')
tôi được xây dựng trên ý tưởng của Yuri, nhưng cần thiết để thực hiện một vài thay đổi để có được những điều làm việc:
import logging
import Tkinter as tk
class WidgetLogger(logging.Handler):
def __init__(self, widget):
logging.Handler.__init__(self)
self.setLevel(logging.INFO)
self.widget = widget
self.widget.config(state='disabled')
def emit(self, record):
self.widget.config(state='normal')
# Append message (record) to the widget
self.widget.insert(tk.END, self.format(record) + '\n')
self.widget.see(tk.END) # Scroll to the bottom
self.widget.config(state='disabled')
Lưu ý rằng chuyển đổi qua lại trạng thái lưng và từ 'bình thường' sang 'bị vô hiệu hóa' là cần thiết để làm cho tiện ích chỉ đọc ở chế độ chỉ đọc Text
.
Xây dựng thêm về câu trả lời của ford, đây là tiện ích con văn bản cuộn có đuôi nhật ký. Thành viên logging_handler
là những gì bạn thêm vào nhật ký của mình.
import logging
from Tkinter import END, N, S, E, W, Scrollbar, Text
import ttk
class LoggingHandlerFrame(ttk.Frame):
class Handler(logging.Handler):
def __init__(self, widget):
logging.Handler.__init__(self)
self.setFormatter(logging.Formatter("%(asctime)s: %(message)s"))
self.widget = widget
self.widget.config(state='disabled')
def emit(self, record):
self.widget.config(state='normal')
self.widget.insert(END, self.format(record) + "\n")
self.widget.see(END)
self.widget.config(state='disabled')
def __init__(self, *args, **kwargs):
ttk.Frame.__init__(self, *args, **kwargs)
self.columnconfigure(0, weight=1)
self.columnconfigure(1, weight=0)
self.rowconfigure(0, weight=1)
self.scrollbar = Scrollbar(self)
self.scrollbar.grid(row=0, column=1, sticky=(N,S,E))
self.text = Text(self, yscrollcommand=self.scrollbar.set)
self.text.grid(row=0, column=0, sticky=(N,S,E,W))
self.scrollbar.config(command=self.text.yview)
self.logging_handler = LoggingHandlerFrame.Handler(self.text)
Xây dựng trên ford quá nhưng thêm văn bản màu!
class WidgetLogger(logging.Handler):
def __init__(self, widget):
logging.Handler.__init__(self)
self.setLevel(logging.DEBUG)
self.widget = widget
self.widget.config(state='disabled')
self.widget.tag_config("INFO", foreground="black")
self.widget.tag_config("DEBUG", foreground="grey")
self.widget.tag_config("WARNING", foreground="orange")
self.widget.tag_config("ERROR", foreground="red")
self.widget.tag_config("CRITICAL", foreground="red", underline=1)
self.red = self.widget.tag_configure("red", foreground="red")
def emit(self, record):
self.widget.config(state='normal')
# Append message (record) to the widget
self.widget.insert(tk.END, self.format(record) + '\n', record.levelname)
self.widget.see(tk.END) # Scroll to the bottom
self.widget.config(state='disabled')
self.widget.update() # Refresh the widget
Ngoài các câu trả lời ở trên: mặc dù có rất nhiều các giải pháp đề xuất cho việc này (ở đây và cũng trong this other thread), tôi đã phải vật lộn khá một chút để làm công việc này bản thân mình. Cuối cùng, tôi chạy vào this text handler class by Moshe Kaplan, sử dụng tiện ích ScrolledText (có lẽ dễ dàng hơn phương thức ScrollBar).
Tôi mất một thời gian để tìm hiểu cách sử dụng lớp Moshe trong ứng dụng luồng. Cuối cùng tôi tạo ra một kịch bản demo tối thiểu cho thấy làm thế nào để làm cho nó tất cả các công việc. Vì nó có thể hữu ích cho những người khác tôi đang chia sẻ nó bên dưới. Trong trường hợp cụ thể của tôi, tôi muốn đăng nhập vào cả GUI và tệp văn bản; nếu bạn không cần điều đó, chỉ cần xóa thuộc tính tên tệp trong ghi nhật ký.basicConfig.
import time
import threading
import logging
try:
import tkinter as tk # Python 3.x
import tkinter.scrolledtext as ScrolledText
except ImportError:
import Tkinter as tk # Python 2.x
import ScrolledText
class TextHandler(logging.Handler):
# This class allows you to log to a Tkinter Text or ScrolledText widget
# Adapted from Moshe Kaplan: https://gist.github.com/moshekaplan/c425f861de7bbf28ef06
def __init__(self, text):
# run the regular Handler __init__
logging.Handler.__init__(self)
# Store a reference to the Text it will log to
self.text = text
def emit(self, record):
msg = self.format(record)
def append():
self.text.configure(state='normal')
self.text.insert(tk.END, msg + '\n')
self.text.configure(state='disabled')
# Autoscroll to the bottom
self.text.yview(tk.END)
# This is necessary because we can't modify the Text from other threads
self.text.after(0, append)
class myGUI(tk.Frame):
# This class defines the graphical user interface
def __init__(self, parent, *args, **kwargs):
tk.Frame.__init__(self, parent, *args, **kwargs)
self.root = parent
self.build_gui()
def build_gui(self):
# Build GUI
self.root.title('TEST')
self.root.option_add('*tearOff', 'FALSE')
self.grid(column=0, row=0, sticky='ew')
self.grid_columnconfigure(0, weight=1, uniform='a')
self.grid_columnconfigure(1, weight=1, uniform='a')
self.grid_columnconfigure(2, weight=1, uniform='a')
self.grid_columnconfigure(3, weight=1, uniform='a')
# Add text widget to display logging info
st = ScrolledText.ScrolledText(self, state='disabled')
st.configure(font='TkFixedFont')
st.grid(column=0, row=1, sticky='w', columnspan=4)
# Create textLogger
text_handler = TextHandler(st)
# Logging configuration
logging.basicConfig(filename='test.log',
level=logging.INFO,
format='%(asctime)s - %(levelname)s - %(message)s')
# Add the handler to logger
logger = logging.getLogger()
logger.addHandler(text_handler)
def worker():
# Skeleton worker function, runs in separate thread (see below)
while True:
# Report time/date at 2-second intervals
time.sleep(2)
timeStr = time.asctime()
msg = 'Current time: ' + timeStr
logging.info(msg)
def main():
root = tk.Tk()
myGUI(root)
t1 = threading.Thread(target=worker, args=[])
t1.start()
root.mainloop()
t1.join()
main()
Github Gist liên kết đến mã trên đây:
https://gist.github.com/bitsgalore/901d0abe4b874b483df3ddc4168754aa
- 1. Python tkinter: dừng tuyên truyền sự kiện trong thẻ tiện ích văn bản
- 2. Cách đánh dấu văn bản trong một tiện ích văn bản tkinter
- 3. Python Tkinter - Cách chèn văn bản vào đầu hộp văn bản?
- 4. Chỉ đọc Tiện ích văn bản trong python3-tkinter; nền tảng chéo
- 5. Chỉnh sửa văn bản bằng Python và nguyền rủa tiện ích Hộp văn bản?
- 6. Tạo tiện ích đăng nhập OpenID
- 7. Tkinter có tiện ích bảng không?
- 8. Đăng nhập bằng văn bản Android vào tệp
- 9. Làm cho tiện ích Tkinter lấy nét
- 10. Đặt vị trí con trỏ trong tiện ích Văn bản
- 11. Thiết lập TkHtml (tiện ích Tk) bằng Python
- 12. Đăng nhập vào trang web bằng python
- 13. ImportError khi nhập Tkinter bằng Python
- 14. cách đặt kích thước của tiện ích con trong tkinter?
- 15. Python 2.7/Windows: tiện ích tkinter/ttk với nền trong suốt, màu nền khung ttk
- 16. Đăng nhập bằng Python?
- 17. Làm cách nào để thay đổi màu của một số từ nhất định trong tiện ích văn bản tkinter?
- 18. Trình nghe Tkinter Python trong hộp văn bản
- 19. Đăng nhập vào bảng điều khiển từ tiện ích mở rộng của Firefox?
- 20. Tải mọi tiện ích con của cửa sổ Tkinter
- 21. Nút mặc định tkinter trong một tiện ích
- 22. Đăng nhập bằng Python NTLM
- 23. Nối văn bản vào tệp bằng Python
- 24. Làm cách nào để bạn đăng nhập vào Firebug từ tiện ích mở rộng?
- 25. Thanh cuộn dọc và ngang trên tiện ích Tkinter
- 26. Đăng nhập bằng Python setlevel
- 27. Mặt nạ được nhập bằng tiện ích EditText trong Android
- 28. Tiện ích văn bản crud tại chỗ của Yii
- 29. Tiện ích bảng điền từ tệp văn bản trong Qt
- 30. Nhập văn bản vào Javascript
Đối với những bạn nhận được ** 'TclStackFree: freePtr' sai ** lỗi, câu trả lời ở trên giải quyết này. Sử dụng 'self.widget.after (0, function_to_execute)' đảm bảo rằng widget được sửa đổi bởi chuỗi nó thuộc về. – Felix