【问题标题】:Python Tkinter text editor does not save font to text filePython Tkinter 文本编辑器不会将字体保存到文本文件
【发布时间】:2015-02-06 23:26:36
【问题描述】:

目前,我正在使用 python 和 tkinter 开发 GUI 文本编辑器。感谢 SO 的优秀人员(感谢 Rinzler),我设法修改了文本的字体。但是,我无法将字体和字体大小保存到 txt 文件中。 我知道这应该是可能的,因为记事本可以修改和保存具有指定字体的txt 文件。

这是保存到文件的代码:

def file_saveas():
    filename = tkFileDialog.asksaveasfile(mode='w', defaultextension=".txt")
    if filename is None: # asksaveasfile return `None` if dialog closed with "cancel".
        return
    text2save = str(textPad.get(1.0, END)) # starts from `1.0`, not `0.0`
    filename.write(text2save)
    filename.close()
    print filename

这是更改字体的代码(由 Rinzler 提供):

def choose_font():
global root, textPad # I hate to use global, but for simplicity

t = Tkinter.Toplevel()
font_name = Tkinter.Label(t, text='Font Name: ')
font_name.grid(row=0, column=0, sticky='nsew')
enter_font = Tkinter.Entry(t)
enter_font.grid(row=0, column=1, sticky='nsew')
font_size = Tkinter.Label(t, text='Font Size: ')
font_size.grid(row=1, column=0, sticky='nsew')
enter_size = Tkinter.Entry(t)
enter_size.grid(row=1, column=1, sticky='nsew')

# associating a lambda with the call to text.config()
# to change the font of text (a Text widget reference)
ok_btn = Tkinter.Button(t, text='Apply Changes',
                   command=lambda: textPad.config(font=(enter_font.get(), 
                   enter_size.get())))
print font
ok_btn.grid(row=2, column=1, sticky='nsew')
done = Tkinter.Button(t, text='Get rid of Pushy!', command=t.destroy)
done.grid(row=4, column=1, sticky='nsew')
# just to make strechable widgets
# you don't strictly need this
for i in range(2):
    t.grid_rowconfigure(i, weight=1)
    t.grid_columnconfigure(i, weight=1)
t.grid_rowconfigure(2, weight=1)

最后,这是读取字体和其他配置信息的代码:

font = (fontname, size)
textPad.config(
    borderwidth=0,
    font=font ,
    foreground="green",
    background="black",
    insertbackground="white", # cursor
    selectforeground="blue", # selection
    selectbackground="#008000",
    wrap="word", 
    width=64,
    undo=True, # Tk 8.4
    )

我已经搜索了互联网,但没有找到关于为什么没有保存字体和文本大小的任何答案。任何帮助将不胜感激。

我正在使用 python 2.7.7 ,Tkinter,这是在 Windows 7 上运行的。

任何操作 rtf 文件的帮助也会有所帮助(目前,我看到的是标签而不是结束格式)。

【问题讨论】:

    标签: python-2.7 fonts tkinter text-editor rich-text-editor


    【解决方案1】:

    tkinter 不支持此功能。您必须选择支持字体(rtf、.docx、.html 等)的文件格式,将小部件中的数据转换为此格式,然后将其写入文件。

    【讨论】:

    • 感谢您的解释。但是,我尝试使用 rtf 格式并显示所有标签。我将如何以实际格式在 tkinter 中显示它?此外,当我尝试从编辑器保存 RTF 文件时,格式仍然没有保存。
    • @PseudonymEnigma:不幸的是,您将不得不解析 rtf 数据并为文本小部件重新格式化它。文本小部件无法显示任何现成的富文本格式。
    • 谢谢。我对 Tkinter 很陌生。你能告诉我我会怎么做吗?
    • @PseudonymEnigma:不,我不能,尤其是在评论框中。这是一件非常困难的事情,尽管可能有一些库可以提供帮助。你仍然需要自己做大量的工作。
    • 出于好奇,记事本怎么能修改字体?
    【解决方案2】:

    记事本只能为其编辑器窗口自定义字体和大小,它不会将其保存到文件中,它只会记住用户的自定义设置,并在您使用时将它们应用于其窗口。

    tkinter 文本小部件无法将格式保存为另一种格式,我尝试将其转换为 XML 以保存为 .docx,但我没有成功。我使用了我自己的格式,它是一个纯文本文件,开头是 tkinter Text 小部件标签的“索引”及其行和列索引,然后是文档开始位置的标记,然后是文档。但是它不能保存图像,当您在另一个文字处理器中打开它时,它会以所有格式索引打开。

    XML 是打开和保存 tkinter 文本内容的理想选择 - 使用 xml 解析器打开,然后使用递归函数随时添加带有标签的文本。 (如果你想要富文本,这和 xml 一样,是一种迭代格式 - 元素内的元素,所以可以像我在下面为 xml 描述的那样完成,但你需要编写自己的富文本解析器)

        import xml.etree.ElementTree as etree
    
        e = etree.fromstring(string)
        #create an element tree of the xml file
        insert_iter(e)
        #call the recursive insert function
        def insert_iter(element):
          #recursive insert function
          text.insert("end", element.text, tagname)
          #insert the elements text
          for child in element:
            insert_iter(child)
            #iterate through the element's child elements, calling the recursive function for each
            text.insert("end", child.tail, tagname)
            #insert the text after the child element
          text.tag_config(tagname, **attrib)
          #configure the text
    

    'attrib' 是一个字典,例如。 {"foreground":"red", "underline":True} 将使您插入的文本具有红色字体和黑色下划线, 'tagname' 是一个随机字符串,需要你的程序自动创建

    要保存文件,请创建一个函数来执行相反的操作。我不会为此使用 xml 库而烦恼 - 因为 tkinter 输出正确的格式,只需手动编写它,但一定要转义它

        from xml.sax.saxutils import escape
    
        data = text.dump("1.0", "end")
        print(data[0:500]) # print some of the output just to show how the dump method works
        output = ''
        #get contents of text widget (including all formatting, in order) and create a string to add the output file to
        for line in data:
          if line[0] == "text":
            #add the plain text to the output
            output += escape(line[1])
          elif line[0] == "tagon":
            #add a start xml tag, with attributes for the given tkinter tag
            name = 'font'
            attrib = ""
            tag = #the dictionary you stored in your program when creating this tag
            for key in tag:
              attrib += "%s='%s' "%(key, escape(tag[key]))
            output += "<%s %s>"%(name, attrib)
          elif line[0] == "tagoff":
            #add a closing xml tag
            output += '</%s>'%name
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2015-04-06
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-07-03
      • 2021-04-15
      • 2017-09-07
      相关资源
      最近更新 更多