Python 什么';这是获取Tkinter文本小部件的最有效方法;插入后的总显示行数?

Python 什么';这是获取Tkinter文本小部件的最有效方法;插入后的总显示行数?,python,python-3.x,tkinter,Python,Python 3.x,Tkinter,是否有一种比我(在Python 3.4.2中)提出的这个临时函数更有效的方法来获取插入文本后留在tkinterText小部件中的显示行总数(不仅仅是可见行): 无论如何,这段代码是有效的,但效率相当低。我用它来计算在剩余文档中自动滚动所剩的时间。使用箭头键移动文本插入时,效率低下会导致问题(箭头键调用此函数以显示当前的准确时间)。这会使插入的移动速度慢得多,更新速度也慢得多,甚至会使插入崩溃/冻结 我知道有更有效的方法来获取文本小部件中的总行数。但是,我需要显示行,因为使用autoscroll进

是否有一种比我(在Python 3.4.2中)提出的这个临时函数更有效的方法来获取插入文本后留在
tkinter
Text
小部件中的显示行总数(不仅仅是可见行):

无论如何,这段代码是有效的,但效率相当低。我用它来计算在剩余文档中自动滚动所剩的时间。使用箭头键移动文本插入时,效率低下会导致问题(箭头键调用此函数以显示当前的准确时间)。这会使插入的移动速度慢得多,更新速度也慢得多,甚至会使插入崩溃/冻结

我知道有更有效的方法来获取文本小部件中的总行数。但是,我需要显示行,因为使用autoscroll进行阅读通常是在打开wordwrap的情况下完成的

我的autoscroll功能从“每隔这么多秒插入一个用户选择的行数”(该秒数也是由用户选择的)。这不是通过滚动条完成的。

好吧,我找到了答案(是的,这是故意的答案;这不是我问题的一部分)

以下代码将更有效地给出文本插入后剩余的显示行数:

def get_display_lines(start="insert", end="end-1c")
    try:
        count=myTextWidget.count(start, end, "displaylines")[0]
    except TypeError:
        count=0
    return count
虽然这要高效得多,但它仍然不是完全高效的,并且在处理大文件时会遇到问题(如果在autoscroll期间经常使用箭头键)。count()方法返回一个元组;因此,零指数。因为这并不总是包含一个数字(比如插入在文档末尾),这就是为什么我使用try/except块(尽管您可以用很多其他方法来实现这一点;但是您可以随意选择)

因为这对于大型文件来说效率不高,所以您可能只需要保留一次当前行,保存它们,并在更新状态时增加/减少此变量(当然,这需要编辑一系列函数,但效率更高)。不过,您需要在编辑过程中更新总数(幸运的是,在自动滚动时,这种情况不太常见)


由于与许多其他函数混在一起会带来很大的开销,并且会增加编辑代码的复杂性,因此我建议只在autoscroll间隔更新代码,而不是在用户手动移动光标时更新。另外,为了提高效率,不要让它在statusbar update方法中计算剩余的行数(更不用说剩余的时间了),而只需从计时器调用的方法中在保存的变量中计算,然后在statusbar中打印变量。

如果您只关心滚动文档的时间,如果数据在滚动时没有改变(即:没有添加新行),您可以简单地计算文档占用多少像素(只需执行一次),以及当前在文档中的位置。这将告诉你还有多少像素。从这一点,你应该能够计算出大概需要多少时间


您可以使用
myTextWidget.count(“1.0”、“end”、“ypixels”
)获取文本小部件中使用的像素总数。然后,您可以使用
myTextWidget.dlineinfo(“插入”)获取当前行的y坐标
。根据这两个数字,您可以计算插入点距离小部件末端的百分比。

为了提高效率,当用户移动光标时,您可以使用
after
在一秒钟左右的时间内更新间隔。每当他们移动光标时,您都会取消该作业并重新安排时间。这样,如果他们正在移动光标,则快速移动光标可以将计算推迟到暂停一小段时间。@BryanOakley
'displaylines'
返回的数字似乎更像现在的字符数,而不是行数?@Engineer\u Chris:
displaylines
不太可能工作不正常或改变其行为ior。它已经成为tkinter的一部分十多年了,tk团队非常重视测试和向后兼容性。@BryanOakley啊,我现在明白了。
displaylines
在显示窗口前后行为都会发生变化。
update
需要调用(或其他等效方法)要设置行的格式,则
displaylines
知道要返回多少行
def get_display_lines(start="insert", end="end-1c")
    try:
        count=myTextWidget.count(start, end, "displaylines")[0]
    except TypeError:
        count=0
    return count