【问题标题】:Background picture in turtle.TurtleScreen() does not show correctly in tkinterturtle.TurtleScreen() 中的背景图片在 tkinter 中无法正确显示
【发布时间】:2019-06-17 10:00:30
【问题描述】:

代码1:创建一个Tk()窗口、一个Frame()Canvas()来承载一个带有一定背景图片的turtle.TurtleScreen()。这些小部件的尺寸在一开始就没有定义。相反,它们是在使用 tkinter 的 .configure() 方法和 turtle 的 .screensize() 方法创建小部件之后定义的。 这里的问题是,即使乌龟的屏幕尺寸正确,背景图片也无法正确显示。

代码 2: 它的工作与代码 1 相同,只是它首先获取图像的大小并使用它来定义 Canvas 小部件的大小,然后再将其显示为turtle.TurtleScreen() 的背景图片。背景图像确实显示正确。

问题:

  1. 为什么代码 1 中会出现问题以及如何解决该问题,即在背景图像大小发生变化的情况下正确显示 turtle.TurtleScreen() 中的背景图像?
  2. 即使Canvas 是用borderwidth=0 定义的,为什么代码1 的FrameCanvas 小部件的大小比代码2 大2 像素?这与 Canvas 的默认边框宽度 = 2 有关吗?

代码 1:

import tkinter as tk
import turtle as tt


root = tk.Tk()

def getsize( widget ):
    widget.update_idletasks()
    w = widget.winfo_width()
    h = widget.winfo_height()
    print( 'w={}, h={}\n'.format(w,h) )
    return w,h

app = tk.Frame( root,  )
canvas = tk.Canvas( app, bg='yellow', borderwidth=0, )
app.grid( row=0, column=0, sticky='nsew' ) 
canvas.grid( row=0, column=0, sticky='nsew' )
print('\nFrame'); aw, ah = getsize( app )
print('canvas'); cw, ch = getsize( canvas )

pic = 'test.gif'
screen = tt.TurtleScreen( canvas )
screen.bgpic( pic )
screen.bgcolor( 'pink' )
screen.update()
print( 'Turtle :' )
print( 'screen size = ', screen.screensize() )
print( 'screen attributes = ', screen.__dict__ )
print( 'screen.bgpic() = ', screen.bgpic() )
photoimage = screen._bgpics[pic]
pw = photoimage.width()
ph = photoimage.height()
print( '\nphotoimage width={} height={}'.format( pw, ph) )

canvas.configure( width=pw+2, height=ph+2 )
screen.screensize( pw+2, ph+2 )
screen.bgpic( pic )

print('\nFrame'); aw, ah = getsize( app )
print('canvas'); cw, ch = getsize( canvas )

代码 2:

import tkinter as tk
import turtle as tt


root = tk.Tk()

pic ='test.gif'
image = tk.PhotoImage( file=pic )
iw = image.width()
ih = image.height()
print( 'image width={} height={}\n'.format( iw, ih) )

def getsize( widget ):
    widget.update_idletasks()
    w = widget.winfo_width()
    h = widget.winfo_height()
    print( 'w={}, h={}\n'.format(w,h) )
    return w,h

app = tk.Frame( root, )
canvas = tk.Canvas( app, width=iw, height=ih, bg='yellow', borderwidth=0 )
app.grid( row=0, column=0, sticky='nsew' ) 
canvas.grid( row=0, column=0, sticky='nsew' )
print('Frame'); aw, ah = getsize( app )
print('canvas'); cw, ch = getsize( canvas )

screen = tt.TurtleScreen( canvas )
screen.bgpic( pic )
screen.bgcolor( 'pink' )
screen.update()
print( 'Turtle :' )
print( 'screen size = ', screen.screensize() )
print( 'screen attributes = ', screen.__dict__ )
print( 'screen.bgpic() = ', screen.bgpic() )
photoimage = screen._bgpics[pic]
pw = photoimage.width()
ph = photoimage.height()
print( '\nphotoimage width={} height={}'.format( pw, ph) )

【问题讨论】:

    标签: python turtle-graphics tkinter-canvas


    【解决方案1】:

    回答问题 1:

    经过进一步研究,我发现TurtleScreen() 有一个名为.cv 的属性指向传递给它的tk.Canvas 小部件。与所有tk.Canvas 小部件一样,需要更新(即配置)其scrollregion 以在发生更改时显示tk.Canvas 的新可见区域。 “scrollregion”选项说明画布可以滚动的区域有多大。

    所以对代码 1 的更改,我需要替换:

    canvas.configure( width=pw+2, height=ph+2 )
    screen.screensize( pw+2, ph+2 )
    screen.bgpic( pic )
    

    canvas.configure( width=pw, height=ph, borderwidth=0 )
    w = int(screen.cv.cget("width"))
    h = int(screen.cv.cget("height"))
    screen.cv.configure(scrollregion = (-w//2, -h//2, w//2+1, h//2 ))
    print( '\nscreen.cv width={} height={}'.format( w, h) )
    

    第二季度的答案:

    报告框架和画布大小相差 2 像素是由于代码 1 中使用了 +2:

    canvas.configure( width=pw+2, height=ph+2 )
    

    相反,我应该使用:

    canvas.configure( width=pw, height=ph )
    

    似乎画布确实消耗了 1 行/列的像素来形成它的边界。

    【讨论】:

      猜你喜欢
      • 2012-01-07
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2012-08-21
      • 2014-11-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多