狗宁 发表于 2020-10-9 10:28:00

用Tkinter写了个记事本小程序,有点问题不知道怎么解决。。。

代码如下
from tkinter import *
from tkinter import filedialog,messagebox
from tkinter.ttk import Scrollbar,Checkbutton,Label,Button
import os
import sys
class Notepad(Tk):
    def __init__(self):
      super().__init__()
      self.file_name = None
      self.set_windows()
      self.creat_menu_bar()
      self.create_body()
    def set_windows(self):
      self.title("notepad--")
      max_width, max_hight = self.maxsize()
      algin_center = "500x300+%d+%d" % ((max_hight-500)/2, (max_hight-300)/2)
      self.geometry(algin_center)
    def creat_menu_bar(self):
      menu_bar = Menu(self)
      file_menu = Menu(menu_bar,tearoff=0)
      menu_bar.add_cascade(label='文件',menu = file_menu)
      file_menu.add_command(label='打开(O)... ', accelerator='Ctrl+O', command=self.open_file)
      file_menu.add_command(label='保存(S) ', accelerator='Ctrl+S', command=self.save_file)
      file_menu.add_command(label='另存为...', accelerator='Shift+Ctrl+N', command=self.save_as)
      file_menu.add_separator()
      file_menu.add_command(label='Exit ', accelerator='Alt+F4', command=self.exit)
      editor_menu = Menu(menu_bar, tearoff=0)
      menu_bar.add_cascade(label='编辑', menu=editor_menu)
      editor_menu.add_command(label='查找(F) ', accelerator='Ctrl+F', command=self.find_text_dialog)
      self['menu'] = menu_bar
    # 界面主图
    def create_body(self):
      # 文本编辑warp表示如何换行(word表示按单词自动换行)
      self.context_text = Text(self, wrap="word",undo=True)
      # 热键绑定
      self.context_text.bind("<Control-s>", self.save_file)
      self.context_text.bind("<Control-f>", self.search_result)
      self.context_text.pack(fill='both',expand="yes")
      # 设置文本输入
      self.context_text.tag_config("active_line",background="#EEEEE0")
    # 写入文件
    def open_file(self,event=None):
      # 打开文件并进行设置
      input_file = filedialog.askopenfilename(filetypes=[("所有文件","*.*"),("文本文档","*.txt")])
      if input_file:
            self.title("{}***Notepad".format(os.path.basename(input_file)))
            self.file_name = input_file
            self.context_text.delete(1.0,END)
            with open(input_file,'r') as f:
                self.context_text.insert(1.0,f.read())
    def write_to_file(self,file_name):
      try:
            content = self.context_text.get(1.0,END)
            with open(file_name,'w') as f1:
                f1.write(content)
            self.title("{}---Notepad".format(os.path.basename(file_name)))
      except IOError:
            messagebox.showerror("error",'fail save')
    # 保存文件
    def save_file(self,event=None):
      if not self.file_name:
            self.save_as()
      else:
            self.write_to_file(self.file_name)
    # 新建
    def new_file(self,event=None):
      self.title("new--Notepad")
      self.context_text.delete
      self.file_name = None
    # 另存为
    def save_as(self,event=None):
      input_file = filedialog.asksaveasfile(filetypes=[("所有文件", "*.*"), ("文本文档", "*.txt")])
      if input_file:
            self.file_name = input_file
            self.write_to_file(self.file_name)
    # 退出
    def exit(self,event=None):
      if messagebox.askokcancel("exit","sure?"):
            self.destroy()
      return "break"
    def find_text_dialog(self):
      search_dialog = Toplevel(self)
      search_dialog.title('search...')
      search_dialog.iconbitmap('./img/head.ico')
      max_width, max_hight = self.maxsize()
      algin_center = "300x60+%d+%d" % ((max_hight - 300) / 2, (max_hight - 60) / 2)
      search_dialog.geometry(algin_center)
      search_dialog.resizable(FALSE,FALSE)
      Label(search_dialog,text='find all').grid(row=0,column=0,sticky='e')
      search_text = Entry(search_dialog,width=25)
      search_text.grid(row=0,column=1,padx=2,pady=2,sticky="we")
      search_text.focus_set()
      ignore_case_value = IntVar()
      Checkbutton(search_dialog,text='忽略大小写',variable=ignore_case_value).grid(row=1,column=1,sticky='e',padx=2,pady=2)
      Button(search_dialog,text="search",command=lambda :self.search_result(search_text.get(),ignore_case_value.get(),
      search_dialog,search_text)).grid(row=1,column=2,sticky="w"+"e",padx=2,pady=2)

      def close_search_dialog():
            self.context_text.tag_remove('match',1.0,END)
            search_dialog.destroy()
      search_dialog.protocol("WM_DELETE_WINDOW",close_search_dialog)
      return "break"

    def search_result(self,key,ignore_case,search_dialog,search_box):
      self.context_text.tag_remove('match',1.0,END)
      match_found = 0
      if key:
            start_pos = 1.0
            while True:
                start_pos = self.context_text.search(key,start_pos,nocase=ignore_case,stopindex=END)
                if not start_pos:
                  break
                end_pos = "{}+{}c".format(start_pos,len(key))
                self.context_text.tag_add('match',start_pos,end_pos)
                match_found += 1
                start_pos= end_pos
            self.context_text.tag_config('match',foreground='red',background='yellow')
      search_box.focus_set()
      search_dialog.title("发现%s个匹配" % match_found)
    # def reolace_text(self):
if __name__ == '__main__':
    app = Notepad()
    app.mainloop()

在保存和另存为文件的时候会弹个错误,从来没见过,希望有大佬帮忙处理一下!!
TypeError: expected str, bytes or os.PathLike object, not _io.TextIOWrapper

疾风怪盗 发表于 2020-10-9 10:40:52

tkinter.filedialog.asksaveasfilename():选择以什么文件名保存,返回文件名
tkinter.filedialog.asksaveasfile():选择以什么文件保存,创建文件并返回文件流对象

干嘛要返回文件流对象?改一下
然后建议保存时直接添加后缀.txt
    def save_as(self,event=None):
      input_file = filedialog.asksaveasfilename(filetypes=[("所有文件", "*.*"), ("文本文档", "*.txt")])
      print(input_file)
      if input_file:
            self.file_name = input_file+'.txt'
            self.write_to_file(self.file_name)

狗宁 发表于 2020-10-9 10:53:28

疾风怪盗 发表于 2020-10-9 10:40
tkinter.filedialog.asksaveasfilename():选择以什么文件名保存,返回文件名
tkinter.filedialog.asksavea ...

原来是这样啊,懂了懂了,谢谢大佬
页: [1]
查看完整版本: 用Tkinter写了个记事本小程序,有点问题不知道怎么解决。。。