Tan
Tan

Reputation: 53

Python kivy widget position

I'm making a soccer juggling game in kivy, and I'm facing a problem. Before I start the game the soccer ball position is in the middle of the screen, but after the game is over the soccer ball position is to the side. How can I make it so that after the game is over the soccer ball is in the middle of the screen, like how it was before I started the game? Below is my code! Any help is appriciated! Thank You!

main.py

from kivy.app import App
from kivy.uix.screenmanager import Screen
from kivy.uix.image import Image
from kivy.core.audio import SoundLoader
from kivy.clock import Clock
from kivy.properties import NumericProperty
from kivy.vector import Vector


class HomeScreen(Screen):
    pass

    def play_sound(self):
        sound = SoundLoader.load('button press sound.wav.')
        if sound:
            sound.play()


sound = SoundLoader.load('Crowd sound effect.wav')
sound.loop = True
sound.play()


class GameScreen(Screen):
    pass

    def play_sound(self):
        sound = SoundLoader.load('button press sound.wav.')
        if sound:
            sound.play()


class Ball(Image):
    velocity_x = NumericProperty(0)
    velocity = NumericProperty(0)


    def on_touch_down(self, touch):
        if Vector(self.center).distance(touch.pos) <= 33:
            label = App.get_running_app().root.get_screen('game_screen').ids.score
            label.text = str(int(label.text) + 1)
            sound = SoundLoader.load('Soccer ball sound.wav')
            sound.play()
            self.source = "icons/ball.png"
            self.velocity = 300
            if self.center[0] + 3 < touch.pos[0]:  # click on right side
                self.velocity_x = -80
            elif self.center[0] - 3 > touch.pos[0]:  # click on left side
                self.velocity_x = +80
            else:  # click center
                self.velocity_x = 0
        return super().on_touch_down(touch)


    def on_touch_up(self, touch):
        if Vector(self.center).distance(touch.pos) <= 33:
            self.source = "icons/ball.png"
        return super().on_touch_up(touch)


class MainApp(App):
    GRAVITY = 300


    def move_ball(self, time_passed):
        ball = self.root.ids.game_screen.ids.ball
        ball.y = ball.y + ball.velocity * time_passed
        ball.x = ball.x + ball.velocity_x * time_passed
        ball.velocity = ball.velocity - self.GRAVITY * time_passed
        self.check_collision()

    def check_collision(self):
        ball = self.root.ids.game_screen.ids.ball
        if ball.top < 96:
            self.root.ids.game_screen.ids.score.text = "0"
            self.game_over()


    def game_over(self):
        self.root.ids.game_screen.ids.ball.pos = (0, (0.5) )
        print("game over")
        self.frames.cancel()
        self.root.ids.game_screen.ids.start_button.disabled = False
        self.root.ids.game_screen.ids.start_button.opacity = 1
        self.root.ids.game_screen.ids.over.opacity = 1


    def next_frame(self, time_passed):
        self.move_ball(time_passed)


    def start_game(self):
        #Clock.schedule_interval(self.move_ball, 1/60.)
        self.root.ids.game_screen.ids.ball.velocity = 275
        self.frames = Clock.schedule_interval(self.next_frame, 1/60.)
        self.root.ids.game_screen.ids.score.text = "0"
        self.root.ids.game_screen.ids.over.opacity = 0
        self.root.ids.game_screen.ids.ball.velocity_x = 0

    def change_screen(self, screen_name):
        self.root.current = screen_name



MainApp().run()

gamescreen.kv

    Ball:
        source: "icons/ball.png"
        size_hint: None, None
        size: 525, 525
        center_x: root.width / 2
        id: ball

Upvotes: 1

Views: 55

Answers (2)

Erling Olsen
Erling Olsen

Reputation: 740

Causing the problem is (0, (0.5)). To get that after the game is over the soccer ball is in the middle of the screen, like how it was before I started the game, the solution is simply self.root.center

after the game is over the soccer ball is in the middle of the screen, like how it was before I started the game

from kivy.app import App
from kivy.uix.screenmanager import Screen
from kivy.uix.image import Image
from kivy.core.audio import SoundLoader
from kivy.clock import Clock
from kivy.properties import NumericProperty
from kivy.vector import Vector


class HomeScreen(Screen):
    pass

    def play_sound(self):
        sound = SoundLoader.load('button press sound.wav.')
        if sound:
            sound.play()


sound = SoundLoader.load('Crowd sound effect.wav')
sound.loop = True
sound.play()


class GameScreen(Screen):
    pass

    def play_sound(self):
        sound = SoundLoader.load('button press sound.wav.')
        if sound:
            sound.play()


class Ball(Image):
    velocity_x = NumericProperty(0)
    velocity = NumericProperty(0)


    def on_touch_down(self, touch):
        if Vector(self.center).distance(touch.pos) <= 33:
            label = App.get_running_app().root.get_screen('game_screen').ids.score
            label.text = str(int(label.text) + 1)
            sound = SoundLoader.load('Soccer ball sound.wav')
            sound.play()
            self.source = "icons/ball.png"
            self.velocity = 300
            if self.center[0] + 3 < touch.pos[0]:  # click on right side
                self.velocity_x = -80
            elif self.center[0] - 3 > touch.pos[0]:  # click on left side
                self.velocity_x = +80
            else:  # click center
                self.velocity_x = 0
        return super().on_touch_down(touch)


    def on_touch_up(self, touch):
        if Vector(self.center).distance(touch.pos) <= 33:
            self.source = "icons/ball.png"
        return super().on_touch_up(touch)


class MainApp(App):
    GRAVITY = 300


    def move_ball(self, time_passed):
        ball = self.root.ids.game_screen.ids.ball
        ball.y = ball.y + ball.velocity * time_passed
        ball.x = ball.x + ball.velocity_x * time_passed
        ball.velocity = ball.velocity - self.GRAVITY * time_passed
        self.check_collision()

    def check_collision(self):
        ball = self.root.ids.game_screen.ids.ball
        if ball.top < 96:
            self.root.ids.game_screen.ids.score.text = "0"
            self.game_over()


    def game_over(self):
        self.root.ids.game_screen.ids.ball.center = self.root.center
        print("game over")
        self.frames.cancel()
        self.root.ids.game_screen.ids.start_button.disabled = False
        self.root.ids.game_screen.ids.start_button.opacity = 1
        self.root.ids.game_screen.ids.over.opacity = 1


    def next_frame(self, time_passed):
        self.move_ball(time_passed)


    def start_game(self):
        #Clock.schedule_interval(self.move_ball, 1/60.)
        self.root.ids.game_screen.ids.ball.velocity = 275
        self.frames = Clock.schedule_interval(self.next_frame, 1/60.)
        self.root.ids.game_screen.ids.score.text = "0"
        self.root.ids.game_screen.ids.over.opacity = 0
        self.root.ids.game_screen.ids.ball.velocity_x = 0

    def change_screen(self, screen_name):
        self.root.current = screen_name



MainApp().run()

Upvotes: 0

John Anderson
John Anderson

Reputation: 38822

Try replacing:

    self.root.ids.game_screen.ids.ball.pos = (0, (0.5) )

with

    self.root.ids.game_screen.ids.ball.center = self.root.center

Upvotes: 1

Related Questions