如何逐个字符显示标签文本?
Posted
技术标签:
【中文标题】如何逐个字符显示标签文本?【英文标题】:How do I display Label text character-by-character? 【发布时间】:2020-10-02 23:28:44 【问题描述】:我一直在尝试在 Kivy 上编写一个基于文本的小型冒险游戏。这意味着,将有大量文本供用户阅读,如果不是一次显示 Label 中的所有文本,而是以简单的方式逐个字符显示,这会更容易阅读“动画”。在这个“动画”结束时,将显示整个文本。
在普通的 Python 中,我想要的应该是这样的:
text1 = "Now tell me, what is your astrological sign?\n"
for character in text1:
sys.stdout.write(character)
sys.stdout.flush()
time.sleep(0.05)
在 Kivy 中,这似乎要困难得多,因为 sleep 函数只是“休眠”整个应用程序。我四处寻找,并没有真正找到任何关于这个特定问题的东西。其他一些人通过使用 Kivy Clock 对象解决了他们对 time.sleep 的需求,但即使在这里我也只能让文本一次显示一个字符(参见下面的代码),这绝对不是我想要的时间>。我希望所有字符加起来,并在这个“动画”结束时让整个标签文本站在那里。
from kivy.app import App
from kivy.lang import Builder
from kivy.properties import StringProperty
import time
from kivy.clock import Clock
kv = '''
BoxLayout:
orientation: 'vertical'
Label:
text: app.text
Button:
text: 'click me'
on_press: app.clicked()
'''
class MyApp(App):
text = StringProperty("hello world")
lst = [1,2,3,4,5,6,7,8,9,10]
def build(self):
return Builder.load_string(kv)
def clicked(self):
Clock.schedule_interval(self.clicked2, 0.5)
def clicked2(self, count):
if len(self.lst) == 0:
return False
self.text = "clicked!" + str(self.lst[len(self.lst)-1])
self.lst.pop()
if __name__ == '__main__':
MyApp().run()
这是我目前能想到的最好的,但同样,这甚至不是我真正想要的。
有没有人有更多经验可以帮助我解决这个问题?将不胜感激,谢谢!
【问题讨论】:
【参考方案1】:我已经认识你了,回答你的问题。但是,我将使用scope variable
向您展示更短的代码。要使用它声明nonlocal [var]
例子:
def A(i=0):
def c():
nonlocal i; i += 1
print(i) #0
c(); print(i) #1
c(); print(i) #2
c(); print(i) #3
A()
我在下面的代码中使用like:
from kivy.lang import Builder
from kivy.properties import StringProperty
import time
from kivy.clock import Clock
from kivy.app import App
kv = '''
BoxLayout:
orientation: 'vertical'
Label:
text: app.text
text_size: self.size
valign: "middle"
padding: root.width/20, root.height/20
Button:
text: 'click me'
on_press: app.clicked()
'''
class MyApp(App):
text = StringProperty("hello world")
blabla = "Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like Aldus PageMaker including versions of Lorem Ipsum"
def build(self): return Builder.load_string(kv)
def clicked(self, i=0):
def clicked2():
nonlocal i; i += 1
if i > len(self.blabla): return False
self.text = self.blabla[:i]
Clock.schedule_interval(lambda count: clicked2(), 0.05)
if __name__ == '__main__': MyApp().run()
【讨论】:
这真的很酷,感谢您的意见!我之前也尝试过使用全局变量,但直到现在我才听说过非局部变量。使用嵌套函数的好主意!另一个我没有想到的想法。谢谢你的帖子:)【参考方案2】:我成功了!下面的代码正是我想要的。我只是使用字符串索引和列表来使用 Clock.schedule_interval() 函数对其进行迭代。
我在 kv 中添加了“valign”和一些填充以使其看起来更好。并且 text_size: self_sice 可以在文本分布在多行时使文本换行。
from kivy.lang import Builder
from kivy.properties import StringProperty
import time
from kivy.clock import Clock
kv = '''
BoxLayout:
orientation: 'vertical'
Label:
text: app.text
text_size: self.size
valign: "middle"
padding: root.width/20, root.height/20
Button:
text: 'click me'
on_press: app.clicked()
'''
class MyApp(App):
text = StringProperty("hello world")
blabla = "Lorem Ipsum is simply dummy text of the printing and typesetting industry. Lorem Ipsum has been the industry's standard dummy text ever since the 1500s, when an unknown printer took a galley of type and scrambled it to make a type specimen book. It has survived not only five centuries, but also the leap into electronic typesetting, remaining essentially unchanged. It was popularised in the 1960s with the release of Letraset sheets containing Lorem Ipsum passages, and more recently with desktop publishing software like Aldus PageMaker including versions of Lorem Ipsum"
lst = []
for x in range(len(blabla)+1):
print(x)
lst.append(x)
lst.reverse()
def build(self):
return Builder.load_string(kv)
def clicked(self):
Clock.schedule_interval(self.clicked2, 0.05)
def clicked2(self,count):
if len(self.lst) == 0:
return False
self.text = str(self.blabla[:self.lst[len(self.lst)-1]])
self.lst.pop()
if __name__ == '__main__':
MyApp().run()
【讨论】:
以上是关于如何逐个字符显示标签文本?的主要内容,如果未能解决你的问题,请参考以下文章