栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 面试经验 > 面试问答

使用Tkinter画布小部件添加放大和缩小?

面试问答 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

使用Tkinter画布小部件添加放大和缩小?

据我所知,内置的Tkinter Canvas类缩放不会自动缩放图像。如果无法使用自定义窗口小部件,则可以缩放原始图像,并在调用缩放功能时将其替换在画布上。

下面的代码片段可以合并到您的原始类中。它执行以下操作:

  1. 缓存的结果
    Image.open()
  2. 添加了一个
    redraw()
    计算缩放图像的功能,并将其添加到画布上,还删除了先前绘制的图像(如果有)。
  3. 将鼠标坐标用作图像放置的一部分。我只是传递
    x and y
    给该
    create_image
    函数以显示图像位置如何随着鼠标移动而移动。您可以将其替换为自己的中心/偏移量计算。
  4. 这使用了Linux鼠标滚轮按钮4和5(您需要将其通用化才能在Windows等系统上使用)。

(已 更新 )代码:

class GUI:    def __init__(self, root):        # ... omitted rest of initialization pre        self.canvas.config(scrollregion=self.canvas.bbox(ALL))        self.scale = 1.0        self.orig_img = Image.open(File)        self.img = None        self.img_id = None        # draw the initial image at 1x scale        self.redraw()        # ... rest of init, bind buttons, pack frame    def zoom(self,event):        if event.num == 4: self.scale *= 2        elif event.num == 5: self.scale *= 0.5        self.redraw(event.x, event.y)    def redraw(self, x=0, y=0):        if self.img_id: self.canvas.delete(self.img_id)        iw, ih = self.orig_img.size        size = int(iw * self.scale), int(ih * self.scale)        self.img = ImageTk.PhotoImage(self.orig_img.resize(size))        self.img_id = self.canvas.create_image(x, y, image=self.img)        # tell the canvas to scale up/down the vector objects as well        self.canvas.scale(ALL, x, y, self.scale, self.scale)

更新 我做了一些不同比例的测试,发现resize / create_image正在使用大量内存。我在具有32GB RAM的Mac
Pro上使用540x375 JPEG进行了测试。这是用于不同比例因子的内存:

 1x  (500,     375)      14 M 2x  (1000,    750)      19 M 4x  (2000,   1500)      42 M 8x  (4000,   3000)     181 M16x  (8000,   6000)     640 M32x  (16000, 12000)    1606 M64x  (32000, 24000)  ...  reached around ~7400 M and ran out of memory, EXC_BAD_ACCESS in _memcpy

鉴于以上所述,一种更有效的解决方案可能是确定将在其中显示图像的视口的大小,围绕鼠标坐标中心计算裁剪矩形,使用rect裁剪图像,然后仅缩放裁剪的部分。这应该使用常量内存来存储临时图像。否则,您可能需要使用第三方Tkinter控件来为您执行此裁剪/窗口缩放。

Update 2 工作但过分简化的裁剪逻辑,只是为了让您入门:

    def redraw(self, x=0, y=0):        if self.img_id: self.canvas.delete(self.img_id)        iw, ih = self.orig_img.size        # calculate crop rect        cw, ch = iw / self.scale, ih / self.scale        if cw > iw or ch > ih: cw = iw ch = ih        # crop it        _x = int(iw/2 - cw/2)        _y = int(ih/2 - ch/2)        tmp = self.orig_img.crop((_x, _y, _x + int(cw), _y + int(ch)))        size = int(cw * self.scale), int(ch * self.scale)        # draw        self.img = ImageTk.PhotoImage(tmp.resize(size))        self.img_id = self.canvas.create_image(x, y, image=self.img)        gc.collect()


转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/651823.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号