python - 如何修改gtk textview的部分文本
问题描述
我用 Python 学习 GTK,但小部件有问题texview
。我想更改/修改缓冲区 ( textview
) 中文本的特定部分。
例如,文本缓冲区:
long_text = "line 1 word 1 word 2 word 3 \n" \
"line 2 [WORD TO REPLACE] \n" \
"line 3 \n"
[WORD TO REPLACE]
我想用a 的值替换部分Gtk.Entry
。我知道如何在缓冲区的末尾添加条目,但我无法从文本本身内部进行替换。
整个代码:
from gi.repository import Gtk
import sys
class MyWindow(Gtk.ApplicationWindow):
def __init__(self, app):
Gtk.Window.__init__(self, title="TextView Example", application=app)
self.set_default_size(300, 450)
# a scrollbar for the child widget (that is going to be the textview)
scrolled_window = Gtk.ScrolledWindow()
scrolled_window.set_border_width(5)
# we scroll only if needed
scrolled_window.set_policy(
Gtk.PolicyType.AUTOMATIC, Gtk.PolicyType.AUTOMATIC)
scrolled_window.set_min_content_height(400)
scrolled_window.set_min_content_width(400)
# a text buffer (stores text)
self.text_buffer = Gtk.TextBuffer()
#Test texte
long_text = "line 1 word 1 word 2 word 3 \n" \
"line 2 <WORD TO REPLACE> \n" \
"line 3 \n"
# a textview (displays the buffer)
self.textview = Gtk.TextView(buffer=self.text_buffer)
# wrap the text, if needed, breaking lines in between words
self.textview.set_wrap_mode(Gtk.WrapMode.WORD)
self.text_buffer = self.textview.get_buffer()
self.text_buffer.insert_at_cursor(long_text)
# textview is scrolled
scrolled_window.add(self.textview)
self.entry=Gtk.Entry()
self.entry.set_text("Entry")
btnUpdate = Gtk.Button(label="Update")
btnUpdate.connect("clicked", self.update_textview)
grid = Gtk.Grid()
grid.attach(self.entry,0,1,1,1)
grid.attach(btnUpdate,0,2,1,1)
grid.attach(scrolled_window,0,3,1,1)
self.add(grid)
def update_textview(self, widget):
self.text_buffer.insert_at_cursor(self.entry.get_text() + '\n')
class MyApplication(Gtk.Application):
def __init__(self):
Gtk.Application.__init__(self)
def do_activate(self):
win = MyWindow(self)
win.show_all()
def do_startup(self):
Gtk.Application.do_startup(self)
app = MyApplication()
exit_status = app.run(sys.argv)
sys.exit(exit_status)
欢迎任何想法。谢谢。
解决方案
这样做的方法是找到<WORD TO REPLACE>
,删除它,然后在原来的地方输入新词<WORD TO REPLACE>
。
找词
要查找单词,您可以利用Gtk.TextIter
'forward_search()
方法。它需要两个参数:要查找的字符串和如何搜索(此参数必须是 的属性Gtk.TextSearchFlags
)。我只是Gtk.TextSearchFlags.VISIBLE_ONLY
用于这个,因为我不是在寻找不可见的东西。
self.text_buffer.get_start_iter().forward_search(
"<WORD TO REPLACE>",
Gtk.TextSearchFlags.VISIBLE_ONLY
)
删除单词
该forward_search()
方法返回一个包含两项的元组:单词的开始迭代器和单词的结束迭代器(除非它没有找到任何东西,在这种情况下它返回None
;稍后会详细介绍)。这些迭代器非常方便,因为我们所要做的只是将它们传递给Gtk.TextBuffer
'sdelete()
方法。
start, end = i.forward_search("<WORD TO REPLACE>", Gtk.TextSearchFlags.VISIBLE_ONLY)
self.text_buffer.delete(start, end)
插入新词
您可以为此使用Gtk.TextBuffer
'insert()
方法。它需要三个参数:插入文本的迭代器、文本和文本的长度(您可以使用它-1
来指定任何长度)。在这里,我使用self.entry.get_text()
text 参数。
start, end = i.forward_search("<WORD TO REPLACE>", Gtk.TextSearchFlags.VISIBLE_ONLY)
self.text_buffer.delete(start, end)
self.text_buffer.insert(start, self.entry.get_text(), -1)
把它们放在一起
下面是整个update_textview()
方法的样子:
def update_textview(self, widget):
# Get the start iter of the textview
i = self.text_buffer.get_start_iter()
# Get the start and end index of <WORD TO REPLACE>
search_result = i.forward_search("<WORD TO REPLACE>", Gtk.TextSearchFlags.VISIBLE_ONLY)
# Make sure that the search actually found something
if search_result is not None:
start, end = search_result
# Delete <WORD TO REPLACE>...
self.text_buffer.delete(start, end)
# ...and insert the text from the entry.
self.text_buffer.insert(start, self.entry.get_text(), -1)
请注意,我使用它if search_result is not None
来确保搜索确实找到了一些东西。如果此语句不存在,那么如果您单击按钮if
但不存在,您会得到一个。TypeError
Update<WORD TO REPLACE>
推荐阅读
- deprecated - Authorize.Net 中是否已弃用 XML API?
- node.js - 使用Node访问另一台服务器的FTP
- python - 如何仅提取数组名称和括号内的内容,并使它们成为键值对?
- javascript - 使用量角器在不同的路径中以角度截取屏幕截图
- java - 不导入支持库
- sql - 使用 SSMA 转换 AccessDatabase
- python - 使用循环从字符串中删除标点符号时出现 KeyError
- javascript - 如何使用 Ajax 在 php while 循环中运行 SQL 查询?
- c++ - 将 mongocxx 连接到 mongodb 服务器时出错:SSL 支持不可用
- c# - C# 每行向行收件人发送电子邮件