I am trying to launch a turtle game stored in one file with a message box from tkinter
stored in another py file but both in the same directory. However, I receive a _tkinter.TclError: image "pyimage2" doesn't exist
error.
I have a function inside the game code that is called upon in the launcher code. This function runs all of the code inside the main game program apart from importing modules which I have included in the function but makes no difference.
Sorry for showing all but as I don't know what the problem is I thought this was best(removed as much code irrelevant to problem as I could(Assume anything unnamed that is called is deleted as irrelevant code)
def start():
import turtle
import math
import time
counter = 0
wn = turtle.Screen()
wn.setup(800, 600)
wn.bgcolor("black")
wn.title("Trooper shooter")
wn.bgpic("background1.png")
wn.update()
turtle.register_shape("invader.gif")
turtle.register_shape("plane.gif")
turtle.register_shape("troop.gif")
turtle.register_shape("player1.gif")
turtle.register_shape("player2.gif")
turtle.register_shape("bomb.gif")
turtle.register_shape("boom.gif")
#player
soldier = turtle.Turtle()
soldier.color("blue")
soldier.shape("player1.gif")
soldier.penup()
soldier.speed(0)
soldier.setposition(0,-200)
soldier.setheading(90)
soldierspd = 20
#Bomb
Numbombs = 2
bombs = []
for i in range(Numbombs):
bombs.append(turtle.Turtle())
for bomb in bombs:
bomb.shape("bomb.gif")
bomb.penup()
bomb.speed(0)
bomb.ht()
x = -1700
y = 2700
bomb.setposition(x+30,y)
bomb.setheading(270)
bombspeed = 10
#Plane
plane = turtle.Turtle()
plane.color("red")
plane.shape("plane.gif")
plane.penup()
plane.speed(0)
plane.setposition(-270,200)
plane.setheading(360)
planespd = 20
#Plane2
plane2 = turtle.Turtle()
plane2.ht()
plane2.color("red")
plane2.shape("plane.gif")
plane2.penup()
plane2.speed(0)
plane2.setposition(-270,200)
plane2.setheading(360)
planespd2 = 20
#ParaTroopers
num = 5
Troopers = []
for i in range(num):
Troopers.append(turtle.Turtle())
for Troop in Troopers:
Troop.color("Purple")
Troop.shape("troop.gif")
Troop.penup()
Troop.speed(0)
Troop.ht()
x = -170
y = 270
Troop.setposition(x+30,y)
Troop.setheading(270)
Troopspeed = 3
#Bullet
bullet = turtle.Turtle()
bullet.color("yellow")
bullet.shape("triangle")
bullet.penup()
bullet.speed(0)
bullet.setheading(90)
bullet.shapesize(0.5, 0.5)
bullet.ht()
bulletspeed = 30
#Define bullet state
#ready = ready to fire
#fire = bullet is firing
state = "ready"
#Move player left
def Left():
x = soldier.xcor()
x -= soldierspd
soldier.setx(x)
soldier.shape("player1.gif")
if x < -280:
x = -280
soldier.setx(x)
#Move player right
def Right():
x = soldier.xcor()
x += soldierspd
soldier.setx(x)
soldier.shape("player2.gif")
if x > 280:
x = 280
soldier.setx(x)
#Shoot bullet
def Shoot():
#Declare bullet state as global
global state
if state == "ready":
state = "fire"
#Move bullet above player
x = soldier.xcor()
y = soldier.ycor()
bullet.setposition(x, y +10)
bullet.showturtle()
#HitBoxes
def checkCollision(A,B):
distance = math.sqrt(math.pow(A.xcor() - B.xcor(), 2) +
math.pow(A.ycor() - B.ycor(), 2))
if distance < 30:
return True
else:
return False
#Move plane
def MovePlane():
x = plane.xcor()
x += planespd
plane.speed(1)
plane.setx(x)
if plane.xcor() > 280:
plane.ht()
turtle.listen()
turtle.onkey(Left,"Left")
turtle.onkey(Right,"Right")
turtle.onkey(Shoot,"space")
while True:
#Move Plane
MovePlane()
#Move count
incCount()
#Show Paratrooper
x = -200
for Troop in Troopers:
if plane.xcor() > x+50:
x += 80
Troop.setx(x)
Troop.showturtle()
y = Troop.ycor()
y -= Troopspeed
Troop.sety(y)
if y < -280:
Troop.ht()
if checkCollision(bullet, Troop):
# Reset bullet
bullet.ht()
state = "ready"
bullet.setposition(0, -400)
Troop.shape("boom.gif")
# Update Scoreboard
score += 10
scorestring = "Score: %s" % score
score_pen.clear()
score_pen.write(scorestring, False, align="left", font=("Arial", 14, "normal"))
time.sleep(0.1)
Troop.setposition(1000, 1000)
#update background
if counter == 30:
wn.bgpic("background2.png")
wn.update()
if counter == 60:
wn.bgpic("background3.png")
wn.update()
if counter == 90:
wn.bgpic("background4.png")
wn.update()
if counter == 120:
wn.bgpic("background5.png")
wn.update()
if counter == 150:
wn.bgpic("background6.png")
wn.update()
wn.mainloop()
from tkinter import *
from tkinter import messagebox
import TrooperShooter
root = Tk()
launch = messagebox.askquestion("launcher","Play game?")
if launch == "yes":
TrooperShooter.start()
When the launcher is run a messagebox should appear saying do you wish to play and when "yes" is clicked the function to start the game is launched. However I receive the error:
Traceback (most recent call last):
File "C:/Users/marco/Desktop/Trooper shooter/launcher.py", line 10, in <module>
TrooperShooter.start()
File "C:\Users\marco\Desktop\Trooper shooter\TrooperShooter.py", line 18, in start
wn.bgpic("background1.png")
File "C:\Program Files (x86)\Python37-32\lib\turtle.py", line 1482, in bgpic
self._setbgpic(self._bgpic, self._bgpics[picname])
File "C:\Program Files (x86)\Python37-32\lib\turtle.py", line 738, in _setbgpic
self.cv.itemconfig(item, image=image)
File "<string>", line 1, in itemconfig
File "C:\Program Files (x86)\Python37-32\lib\tkinter\__init__.py", line 2578, in itemconfigure
return self._configure(('itemconfigure', tagOrId), cnf, kw)
File "C:\Program Files (x86)\Python37-32\lib\tkinter\__init__.py", line 1476, in _configure
self.tk.call(_flatten((self._w, cmd)) + self._options(cnf))
_tkinter.TclError: image "pyimage2" doesn't exist
Process finished with exit code 1
My first suggestion is that you use the turtle textinput()
method (new in Python 3) instead of dragging tkinter and messagebox into the picture.
But if you're going to combine tkinter and turtle, you need to do it correctly. Turtle is designed to run either standalone with its own Tk window or embedded in an existing tkinter window. You're attempting to run it standalone, embedded in a tkinter window. Ie instead of the standalone Turtle
& Screen
interface, you should be working with the embedded TurtleScreen
, RawTurtle
and ScrolledCanvas
interface.
Besides this issue, your code is generally buggy. You've lots of unfinished code. Your use of global
has to become nonlocal
when you move the entire program inside the start()
function. You're missing pieces of code necessary to run. Finally, you have a while True:
loop which has no business being in an event-driven environment like turtle. I've repaced it with a timer event.
I've reworked your code below to run as you intended. I've tossed incomplete and/or broken features to simplify the example. The startup code:
from tkinter import Tk
from tkinter import messagebox
import TrooperShooter
root = Tk()
launch = messagebox.askquestion("launcher", "Play game?")
if launch == "yes":
TrooperShooter.start(root)
TrooperShooter.py
import tkinter as tk
from turtle import TurtleScreen, ScrolledCanvas, RawTurtle
def start(root):
# Move player left
def Left():
soldier.shape("player1.gif")
x = soldier.xcor() - soldierspd
soldier.setx(x)
if x < -280:
soldier.setx(-280)
# Move player right
def Right():
soldier.shape("player2.gif")
x = soldier.xcor() + soldierspd
soldier.setx(x)
if x > 280:
soldier.setx(280)
# Shoot bullet
def Shoot():
# Declare bullet state as global
nonlocal state
if state == "ready":
state = "fire"
# Move bullet above player
x, y = soldier.position()
bullet.setposition(x, y + 10)
bullet.showturtle()
# HitBoxes
def checkCollision(a, b):
return a.distance(b) < 30
# Move plane
def MovePlane():
x = plane.xcor() + plane_speed
plane.setx(x)
if plane.xcor() > 280:
plane.hideturtle()
def action():
nonlocal state, score
# Move Plane
MovePlane()
# Show Paratrooper
x = -200
for troop in troopers:
if plane.xcor() > x + 50:
x += 80
troop.setx(x)
troop.showturtle()
y = troop.ycor() - troop_speed
troop.sety(y)
if y < -280:
troop.hideturtle()
if checkCollision(bullet, troop):
# Reset bullet
bullet.hideturtle()
state = "ready"
bullet.setposition(0, -400)
troop.shape("boom.gif")
# Update Scoreboard
score += 10
scorestring = "Score: %s" % score
score_pen.clear()
score_pen.write(scorestring, align="left", font=("Arial", 14, "normal"))
troop.setposition(1000, 1000)
if state == "fire":
y = bullet.ycor()
if y > 300:
state = 'ready'
bullet.hideturtle()
else:
bullet.sety(y+ bullet_speed)
screen.ontimer(action, 100)
score = 0
# Define bullet state
# ready = ready to fire
# fire = bullet is firing
state = "ready"
root.geometry("800x600")
root.title("Trooper shooter")
canvas = ScrolledCanvas(root)
canvas.pack(fill=tk.BOTH, expand=tk.YES)
screen = TurtleScreen(canvas)
screen.bgcolor("black")
screen.bgpic("background1.png")
screen.register_shape("invader.gif")
screen.register_shape("plane.gif")
screen.register_shape("troop.gif")
screen.register_shape("player1.gif")
screen.register_shape("player2.gif")
screen.register_shape("boom.gif")
# Player
soldier = RawTurtle(screen)
soldier.color("blue")
soldier.shape("player1.gif")
soldier.penup()
soldier.speed('fastest')
soldier.setposition(0, -200)
soldier.setheading(90)
soldierspd = 20
# Score
score_pen = RawTurtle(screen)
score_pen.speed('fastest')
score_pen.hideturtle()
# Plane
plane = RawTurtle(screen)
plane.color("red")
plane.shape("plane.gif")
plane.penup()
plane.speed('fastest')
plane.setposition(-270, 200)
plane.setheading(360)
plane_speed = 20
# ParaTroopers
number_troops = 5
troopers = []
for _ in range(number_troops):
troop = RawTurtle(screen)
troop.color("Purple")
troop.shape("troop.gif")
troop.penup()
troop.speed('fastest')
troop.hideturtle()
x, y = -170, 270
troop.setposition(x + 30, y)
troop.setheading(270)
troopers.append(troop)
troop_speed = 3
# Bullet
bullet = RawTurtle(screen)
bullet.color("yellow")
bullet.shape("triangle")
bullet.penup()
bullet.speed('fastest')
bullet.setheading(90)
bullet.shapesize(0.5)
bullet.hideturtle()
bullet_speed = 30
screen.onkey(Left, "Left")
screen.onkey(Right, "Right")
screen.onkey(Shoot, "space")
screen.listen()
action()
screen.mainloop()
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.