gpt4 book ai didi

python - 在多个标签中多次更改图像的最佳方法是什么?

转载 作者:太空宇宙 更新时间:2023-11-03 21:02:53 25 4
gpt4 key购买 nike

我需要一些关于如何完成这个项目的建议。我多年前就有过一些编程经验,但最近几周才开始接触 Python。

这个 Python 3 程序有一个 tkinter 屏幕,上面有 150 个图标。这些图标是标签小部件,根据从文本文件读入程序的设备状态显示三个 20x20 png 图形之一。每个图标每天需要更改几次。

在这种情况下,任何关于哪种方法可以工作并显示这些图标的建议将不胜感激。

我已经尝试过几次了。理想情况下, StringVar()/textvariable 类型方法会很好(这对于更改标签中的文本非常有用),但我找不到类似的图像方法。简单地将相同的标签一遍又一遍地推到屏幕上是行不通的,因为程序最终会“内存不足”崩溃。

编辑:我已经使用键/值对解决了这个问题,因此每个循环都不会创建新标签。该方法适用于单个实例,但是一旦我将其放入此循环结构中,它就会崩溃并显示“TypeError:'str'对象不支持项目分配”。我创建了这个简单的例程,它反射(reflect)了我在较大项目中遇到的问题。我怎样才能让它发挥作用?

import tkinter as tk
import time

window = tk.Tk()
window.title("PiStatus")
window.geometry("500x500+0+0")

ct = 0
# You can use any small images for this, mine are 20x20 pixels.
pc_on_icon = tk.PhotoImage(file="1.png")
pc_active_icon = tk.PhotoImage(file="2.png")
pc_off_icon = tk.PhotoImage(file="0.png")

# This loop creates the base 15x10 grid of labels, each with a unique name.
for ypos in range(10):
for xpos in range(15):
label_name = "icon" + str(xpos) + "-" + str(ypos)
label_name = tk.Label(window, image=pc_on_icon)
label_name.grid(row=ypos, column=xpos)

while True:

# These statements cycle through the 3 images
if ct == 0:
turn = pc_off_icon
elif ct == 1:
turn = pc_on_icon
else:
turn = pc_active_icon

# This loop references each label giving it a different image each time around.
for ypos in range(10):
for xpos in range(15):
label_name = "icon" + str(xpos) + "-" + str(ypos)
label_name['image'] = turn # This is where the error occurs.

ct += 1

if ct == 3:
ct = 0

window.update()

window.mainloop()

最佳答案

我们可以创建一个自定义小部件来封装为一个特定设备显示多个状态图标的功能。我们将其命名为 MultiStateIcon 并从 tk.Frame 派生。

此小部件将保存一组子 tk.Label 小部件,每个可能的状态/图像一个。所有标签都将填充重叠,但只有一个(对应于当前状态的标签)可见(其他标签可以使用 pack_forget() 隐藏)。

然后您只需创建一个 MultiStateIcon 网格(或您想要的任何布局),然后按照文本文件指示更改它们的状态。

<小时/>

为了演示,我让应用程序定期(每 10 毫秒)将一个随机选择的设备的状态设置为随机选择的状态。

示例脚本:

import Tkinter as tk
import PIL.Image, PIL.ImageTk
from random import randrange


class MultiStateIcon(tk.Frame):
def __init__(self, parent, images, *args, **kwargs):
tk.Frame.__init__(self, parent, *args, **kwargs)

self.images = images
self.labels = []

for image in images:
l = tk.Label(self, image = image)
l.pack()
self.labels.append(l)

self.set_state(0)

def set_state(self, n):
for i in range(len(self.labels)):
if i == n:
self.labels[i].pack()
else:
self.labels[i].pack_forget()

class TestApp(tk.Tk):
def __init__(self, image_paths, *args, **kwargs):
tk.Tk.__init__(self, *args, **kwargs)

self.title("Test")
self.frame = tk.Frame(self)
self.frame.pack()

self.images = []
for image_path in image_paths:
img = PIL.ImageTk.PhotoImage(PIL.Image.open(image_path))
self.images.append(img)

self.icons = []
for r in range(10):
for c in range(15):
icon_lbl = MultiStateIcon(self.frame, self.images)
icon_lbl.grid(row=r, column=c)
self.icons.append(icon_lbl)

self.after(1000, self.change_random_icon)

def change_random_icon(self):
n = randrange(0, len(self.icons))
state = randrange(0, len(self.images))
self.icons[n].set_state(state)
self.after(10, self.change_random_icon)

def run():
app = TestApp(["multiicon_0.png", "multiicon_1.png", "multiicon_2.png"])
app.mainloop()

run()

我使用的图像:

应用程序的屏幕截图(一张是一开始的,另一张是一段时间后的——内存使用情况似乎很稳定):

关于python - 在多个标签中多次更改图像的最佳方法是什么?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55616948/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com