from PyQt5.QtGui import *
from PyQt5.QtWidgets import *
from PyQt5.QtCore import *
from MainWindow import Ui_MainWindow

import vlc

import logging
LOGLEVEL = logging.DEBUG

import midi
import playlist
import control

class MainWindow(QMainWindow, Ui_MainWindow):
    def __init__(self, *args, **kwargs):
        super(MainWindow, self).__init__(*args, **kwargs)
        self.setupUi(self)

        self.midiEnabled = False
        self.player = vlc.MediaListPlayer()
        self.playlist = playlist.Playlist(self)
        self.control = control.Control(self)

        """
        self.player.durationChanged.connect(self.updateDuration)
        self.player.positionChanged.connect(self.updatePosition)

        self.player.positionChanged.connect(self.positionChanged)

        self.abListModel = AbListModel()
        self.abListView.setModel(self.abListModel)
        self.abListView.selectionModel().selectionChanged.connect(self.abListSelectionChanged)

        self.saveAbButton.pressed.connect(self.addAb)
        self.internalState = dict()

        self.saveSessionButton.pressed.connect(self.saveSession)
        self.loadSessionButton.pressed.connect(self.loadSession)

        self.abRepeatButton.clicked.connect(self.abRepeatToggleClick)

        self.initMidiButton.pressed.connect(self.initMidi)
        """

        self.show()

    def playlistPositionChanged(self, i):
        if i > -1:
            ix = self.playlistModel.index(i)
            self.songListView.setCurrentIndex(ix)

    def abListSelectionChanged(self, ix):
        if len(ix.indexes()) > 0:
            i = ix.indexes()[0].row()
            ab = self.abListModel.abList[i]
            self.aSlider.setValue(ab[0])
            self.bSlider.setValue(ab[1])

    def addAb(self, song=None, a=None, b=None):
        currentSong = song or self.playlist.currentMedia().canonicalUrl().path()
        abState = [a or self.aSlider.value(), b or self.bSlider.value()]
        self.abListModel.abList.append(abState)
        self.abListModel.layoutChanged.emit()


        if self.midiEnabled:
            midi.button_on(midi.lp_key[0][1], (midi.GREEN if self.player.state() == QMediaPlayer.PlayingState else midi.RED))

    def updateDuration(self, duration):
        self.aSlider.setMaximum(duration)
        self.bSlider.setMaximum(duration)

    def updatePosition(self, position):
        # Disable the events to prevent updating triggering a setPosition event (can cause stuttering).
        self.songSlider.blockSignals(True)
        self.songSlider.setValue(position)
        self.songSlider.blockSignals(False)

    def positionChanged(self, position):
        if self.abRepeatButton.isChecked() and position > self.bSlider.value():
            self.player.setPosition(self.aSlider.value())

    def loadSession(self):
        path, _ = QFileDialog.getOpenFileName(self, "Open file", "", "session (*.json)")
        if path:
            import json
            with open(path, "r") as f:
                session = json.load(f)
                self.reset()
                
                for song in session:
                    self.addSong(song)
                    self.abListModel.abList = self.internalState[song]

                    for ab in session[song]:
                        self.addAb(song=song, a=ab[0], b=ab[1])

    def saveSession(self):
        path, _ = QFileDialog.getSaveFileName(self, "Save file", "", "session (*.json)")
        if path:
            import json
            with open(path, "w") as f:
                json.dump(self.internalState, f)

    def abRepeatToggleClick(self):
        midi.button_on(midi.lp_key[1][1], (midi.GREEN if self.abRepeatButton.isChecked() else midi.RED))

    def initMidi(self):
        if self.midiEnabled:
            return

        try:
            midi.midi_init()
        except Exception as e:
            print(e)
            return
        
        self.midiEnabled = True

        # play pause
        midi.button_on(midi.lp_key[0][1], (midi.GREEN if self.player.state() == QMediaPlayer.PlayingState else midi.RED))
        midi.on_press(midi.lp_key[0][1], self.playPauseButton.click)

        # next song
        midi.button_on(midi.lp_key[0][2], midi.YELLOW)
        midi.on_press(midi.lp_key[0][2], self.playlist.next)

        # previous song
        midi.button_on(midi.lp_key[0][0], midi.YELLOW)
        midi.on_press(midi.lp_key[0][0], self.playlist.previous)

        # a/b repeat
        midi.button_on(midi.lp_key[1][1], (midi.GREEN if self.abRepeatButton.isChecked() else midi.RED))
        midi.on_press(midi.lp_key[1][1], self.abRepeatButton.click)

        # next ab
        # TODO continue here
        midi.button_on(midi.lp_key[1][2], midi.YELLOW)
        #midi.on_press(midi.lp_key[1][2], nextAb)
        

    def reset(self):
        self.playlist.clear()
        self.playlistModel.layoutChanged.emit()
        self.abListModel.abList.clear()
        self.abListModel.layoutChanged.emit()

if __name__ == '__main__':
    logging.basicConfig(level=LOGLEVEL)

    app = QApplication([])
    app.setApplicationName("Solo Tool")
    app.setStyle("Fusion")

    # Fusion dark palette from https://gist.github.com/QuantumCD/6245215.
    palette = QPalette()
    palette.setColor(QPalette.Window, QColor(53, 53, 53))
    palette.setColor(QPalette.WindowText, Qt.white)
    palette.setColor(QPalette.Base, QColor(25, 25, 25))
    palette.setColor(QPalette.AlternateBase, QColor(53, 53, 53))
    palette.setColor(QPalette.ToolTipBase, Qt.white)
    palette.setColor(QPalette.ToolTipText, Qt.white)
    palette.setColor(QPalette.Text, Qt.white)
    palette.setColor(QPalette.Button, QColor(53, 53, 53))
    palette.setColor(QPalette.ButtonText, Qt.white)
    palette.setColor(QPalette.BrightText, Qt.red)
    palette.setColor(QPalette.Link, QColor(42, 130, 218))
    palette.setColor(QPalette.Highlight, QColor(42, 130, 218))
    palette.setColor(QPalette.HighlightedText, Qt.black)
    app.setPalette(palette)
    app.setStyleSheet("QToolTip { color: #ffffff; background-color: #2a82da; border: 1px solid white; }")

    window = MainWindow()
    app.exec_()