Search code examples
pythonpython-3.xkivykivy-languagekivymd

How to change on_release function of a button using a method?


I am currently designing an Android music player app. It worked all fine on playing songs. Now, what I want is that when we click on the play button it changes its image to pause and first time clicked it will play the song. When we click on it when its image is pause image, then the song pauses. In simple words, I want to change the on_release action of the button and the image on it when we click on it.

You don't have to worry about how to play and pause. I just want to know how to change the button functionality and the image on it when we click on it.

My current program looks like this:

from kivy.lang import Builder
from kivymd.uix.list import OneLineListItem
from kivymd.app import MDApp
from kivy.core.audio import SoundLoader
import os

helper_string = """
Screen:
    BoxLayout:
        orientation: "vertical"
        ScrollView:
            MDList:
                id: scroll
        MDRoundImageButton:
            id: play_button
            source: "F:/playbutton.png"
            pos_hint: {"center_x":0.5,"center_y":0.5}
            on_release: app.song_player_on_release_play_button()

"""


class MainApp(MDApp):
    def build(self):
        screen = Builder.load_string(helper_string)
        return screen

    def on_start(self):
        for root, dirs, files in os.walk('C:/'):
            for file in files:
                if file.endswith('.mp3'):
                    required_file = file
                    the_location = os.path.abspath(required_file)
                    self.root.ids.scroll.add_widget(OneLineListItem(text=required_file, on_release=self.play_song))
                    # print(required_file)

    def play_song(self, onelinelistitem):
        SongList = []
        # print('play:', onelinelistitem.text)
        the_song_path = onelinelistitem.secondary_text
        SongList.append(the_song_path)
        if len(SongList) == 1:
            sound = SoundLoader.load(SongList[0])
            if sound:
                sound.play()
            print(the_song_path)
        if len(SongList) > 1:
            SoundLoader.load(SongList[0]).stop()
            sound = SoundLoader.load(SongList[1])
            if sound:
                sound.play()
            print(the_song_path)

    def song_player_on_release_play_button(self):
        self.root.ids.play_button.source = "F:/pause button.png"
        self.root.ids.play_button.on_release = self.song_player_on_release_pause_button()

    def song_player_on_release_pause_button(self):
        self.root.ids.play_button.on_release = self.song_player_on_release_play_button()
        self.root.ids.play_button.source = "F:/playbutton.png"


MainApp().run()

In this above code, I thought that if I use the self.root.ids.play_button.on_release, then it will change the on release functionality, but it did not work. Now, I am stuck on this: how can I change the button functionality and the image on it?

I am new to programming and I am using kivy and kivymd in Python to make this app.

If you are testing this, please change the image name or download the images that I originally used:

pause button:
pause button

Play button:
Play button

Again, I want them to change the on_release action on each other, which means that when we click on the pause it prints pause, change the button image to play. Then, when we click on the play it prints play and changes the button image to pause and this goes on forever...


Solution

  • You don't need to define two functions for this. In one function you can change the play or pause images like below.

        def song_player_on_release_play_button(self, *args):
            if self.root.ids.play_button.source = "F:/playbutton.png":
                self.root.ids.play_button.source = "F:/pause button.png"
            else:
                self.root.ids.play_button.source = "F:/playbutton.png"