import xbmc
import xbmcgui
import bjsonrpc
from bjsonrpc.handlers import BaseHandler
from pulsar.addon import ADDON
from pulsar.logger import log
from pulsar.config import JSONRPC_EXT_PORT
from pulsar.platform import PLATFORM
from pulsar.util import notify, GetLocalizedString
from pulsar.overlay import OverlayText

XBMC_PLAYER = xbmc.Player()

class PulsarRPCServer(BaseHandler):
    public_methods_pattern = r'^[A-Za-z]\w+$'

    _objects = {}

    def Reset(self):
        for i in self._objects:
            try:
                self._objects[i].hide()
            except:
                pass
        self._objects = {}

    def Notify(self, header, message, image):
        return notify(GetLocalizedString(message), header, 3000, image)

    def Keyboard(self, default="", heading="", hidden=False):
        keyboard = xbmc.Keyboard(default, GetLocalizedString(heading), hidden)
        keyboard.doModal()
        if keyboard.isConfirmed():
            return keyboard.getText()

    def Dialog_Select(self, title, items):
        dialog = xbmcgui.Dialog()
        return dialog.select(GetLocalizedString(title), items)

    def Player_GetPlayingFile(self, *args, **kwargs):
        return XBMC_PLAYER.getPlayingFile()

    def Player_IsPlaying(self, *args, **kwargs):
        return XBMC_PLAYER.isPlaying(*args, **kwargs)

    def Player_IsPaused(self):
        return xbmc.getCondVisibility("Player.Paused")

    def ConvertLanguage(self, *args, **kwargs):
        return xbmc.convertLanguage(*args, **kwargs)

    def GetPlatform(self):
        return PLATFORM

    def GetAddonInfo(self):
        info = {}
        for key in ("author", "changelog", "description", "disclaimer",
                    "fanart", "icon", "id", "name", "path", "profile", "stars",
                    "summary", "type", "version"):
            info[key] = ADDON.getAddonInfo(key)
        return info

    def GetLanguage(self, *args, **kwargs):
        return xbmc.getLanguage(*args, **kwargs)

    def GetLocalizedString(self, *args, **kwargs):
        return ADDON.getLocalizedString(*args, **kwargs).encode('utf-8')

    def GetSetting(self, *args, **kwargs):
        return ADDON.getSetting(*args, **kwargs)

    def SetSetting(self, *args, **kwargs):
        return ADDON.setSetting(*args, **kwargs)

    def TranslatePath(self, *args, **kwargs):
        return xbmc.translatePath(*args, **kwargs)

    def Log(self, *args, **kwargs):
        return xbmc.log(*args, **kwargs)

    def Dialog_CloseAll(self, *args, **kwargs):
        return xbmc.executebuiltin("Dialog.Close(all, true)")

    ###########################################################################
    # DialogProgress
    ###########################################################################
    def DialogProgress_Create(self, *args, **kwargs):
        dialog = xbmcgui.DialogProgress()
        self._objects[id(dialog)] = dialog
        dialog.create(*args, **kwargs)
        return id(dialog)

    def DialogProgress_IsCanceled(self, hwnd, *args, **kwargs):
        return self._objects[hwnd].iscanceled(*args, **kwargs)

    def DialogProgress_Update(self, hwnd, *args, **kwargs):
        return self._objects[hwnd].update(*args, **kwargs)

    def DialogProgress_Close(self, hwnd, *args, **kwargs):
        dialog = self._objects.pop(hwnd)
        dialog.close()
        del dialog

    # Overlay status
    def OverlayStatus_Create(self):
        overlay = OverlayText()
        overlayId = id(overlay)
        self._objects[overlayId] = overlay
        return overlayId

    def OverlayStatus_Update(self, hwnd, percent, line1, line2, line3):
        text = "\n".join([line1, line2, line3])
        self._objects[hwnd].text = text

    def OverlayStatus_Show(self, hwnd):
        self._objects[hwnd].show()

    def OverlayStatus_Hide(self, hwnd):
        self._objects[hwnd].hide()

    def OverlayStatus_Close(self, hwnd):
        overlay = self._objects.pop(hwnd)
        overlay.hide()
        del overlay


def server_thread():
    try:
        s = bjsonrpc.createserver(port=JSONRPC_EXT_PORT, handler_factory=PulsarRPCServer)
        log.info("pulsar: starting jsonrpc service")
        s.serve()
        log.info("pulsar: exiting jsonrpc service")
    except Exception:
        import traceback
        map(log.info, traceback.format_exc().split("\n"))
        raise
