/*
|----------------------------------------------------------------------------|
|                                Player                                  |
|----------------------------------------------------------------------------|
*/

var Player = Class.create({
    initialize: function(mediaURL, deliveryType) {
        var oThis = this;

        this.mediaURL = mediaURL;
        this.deliveryType = deliveryType;

        // setup players and overlays
        this.videoPlayer = $('videoPlayer');
        this.audioPlayer = $('audioPlayer');
        this.videoOverlays = $$('.video_overlay');

        // setup control fields
        this.selectedIds = new Array();
        this.selectedLocale = '';

        // setup sliders
        this.volumeSlider = this.setupVolumeSlider();
        this.timeSlider = this.setupTimeSlider();

        // setup playList elements controls
        this.playListElements = this.setupPlayListElements();

        // setup info elements
        this.infoElements = $$('.info_element');

        // setup timer elements
        this.timerElements = $$('.timer_element');

        // setup audio elements
        this.audioElements = this.setupAudioElements();

        // setup player controls
        this.setupPlayerControls();

        // check player version
        this.checkPlayerVersion();

        // set initial state
        if (this.hasPlayer()) {
            this.videoPlayer.attachEvent('PlayStateChange', function(newState) { oThis.playStateChange(newState); });
            this.synchronizer = new Synchronizer(this.videoPlayer, this.audioPlayer, this.timeSlider);
        }
        this.selectPlayListElement(this.playListElements.first().id);
    },

    hasPlayer: function() {
        return (this.videoPlayer.versionInfo && this.audioPlayer.versionInfo);
    },

    checkPlayerVersion: function() {
        var wmpVersionInfo = this.videoPlayer.versionInfo;

        if( wmpVersionInfo != undefined && wmpVersionInfo.substring(0, 2) < 9) {
            this.setErrorOverlay('wrong_player');
            return false;
        }
        return true;
    },

    setupVolumeSlider: function() {
        var oThis = this;
        var volumeSlider = new Slider($("volume-slider-container"), $("volume-slider-input"));
        volumeSlider.setValue(50);
        if (this.hasPlayer()) {
            volumeSlider.onchange = function() {
                oThis.audioPlayer.settings.volume = oThis.volumeSlider.getValue();
                oThis.videoPlayer.settings.volume = 100 - oThis.volumeSlider.getValue();
            };
        }
        return volumeSlider;
    },

    setupTimeSlider: function() {
        var oThis = this;
        var timeSlider = new Slider($("time-slider-container"), $("time-slider-input"));
        if (this.hasPlayer()) {
            timeSlider.onchange = function() {
                var time = oThis.timeSlider.getValue()/100;
                oThis.videoPlayer.controls.currentPosition = time;
                oThis.audioPlayer.controls.currentPosition = time;
//                $('counter').innerHTML = formatCounter(time*100);
                if (oThis.videoPlayer.playState == 3)
                    oThis.pause();

                if (oThis.videoPlayer.playState == 2) {
                    oThis.videoPlayer.controls.play();
                    oThis.videoPlayer.controls.pause();
                }
            };
        }
        return timeSlider;
    },

    setupPlayListElements: function() {
        var oThis = this;
        var playListElements = $$('.playlist_element');
        playListElements.each(function(element) {
            element.onmouseover = function() { this.addClassName('over'); };
            element.onmouseout = function() { this.removeClassName('over'); };
            element.onclick = function() {
                oThis.selectPlayListElement(this.id);
                oThis.stop();
                oThis.play();
            };
        });

        $('maximize_playlist_control').onclick = function() {
            oThis.togglePlaylistSize();
        };
        $('restore_playlist_control').onclick = function() {
            oThis.togglePlaylistSize();
        };

        return playListElements;
    },

    setupAudioElements: function() {
        var oThis = this;
        var audioElements = $$('.audio_element');
        audioElements.each(function(element) {
            var selects = element.getElementsByTagName('select');
            if (selects.length > 0) {
                selects[0].onchange = function() {
                    oThis.selectAudioElement(this);
                    oThis.stop();
                    oThis.play();
                };
            }
        });
        return audioElements;
    },

    setupPlayerControls: function() {
        var oThis = this;
        this.playAllButtons = $$('.playall_button');
        this.playAllButtons.each(function(element) {
            element.onclick = function() {
                oThis.selectAllPlayListElements();
                oThis.stop();
                oThis.play();
            };
        });

        this.playButtons = $$('.play_button');
        this.playButtons.each(function(element) {
            element.onclick = function() { oThis.play(); };
        });

        this.pauseButtons = $$('.pause_button');
        this.pauseButtons.each(function(element) {
            element.onclick = function() { oThis.pause(); };
        });

        this.fullScreenButtons = $$('.fullscreen_button');
        this.fullScreenButtons.each(function(element) {
            element.onclick = function() { oThis.fullScreen(); };
        });
    },

    togglePlaylistSize: function() {
        var playerElement = $('visor');
        var playlistElement = $('player');
        var maximize_control = $('maximize_playlist_control');
        var restore_control = $('restore_playlist_control');

        if (playerElement.visible()) {
            playerElement.hide();
            playlistElement.addClassName('max_playlist');
            maximize_control.hide();
            restore_control.show();
        } else {
            playlistElement.removeClassName('max_playlist');
            playerElement.show();
            maximize_control.show();
            restore_control.hide();
        }
    },

    selectPlayListElement: function(id) {
        // if playlist maximized, do nothing
        if (!$('visor').visible())
            return;

        // select playlist element
        this.playListElements.each(function(element) {
            if (element.id == id) {
                element.addClassName('current');
            } else {
                element.removeClassName('current');
            }
        });

        // select info element
        this.infoElements.each(function(element) {
            if (element.id == 'info_for_' + id)
                element.appear({ duration: 2.0 });
            else if (element.visible())
                element.hide();
        });

        // select timer element
        this.timerElements.each(function(element) {
            if (element.id == 'timer_for_' + id)
                element.show();
            else if (element.visible())
                element.hide();
        });

        // select audios element
        this.audioElements.each(function(element) {
            if (element.id == 'audio_for_' + id)
                element.show();
            else if (element.visible())
                element.hide();
        });

        this.selectedIds = [ id ];
    },

    selectAllPlayListElements: function() {
        var oThis = this;
        
        // if playlist maximized, restore it
        if (!$('visor').visible())
            oThis.togglePlaylistSize();

        /*
         *  reload playlistElements and audioElements in case some elements were deleted
         *  or re-arranged
         */
        this.playListElements = this.setupPlayListElements();
        this.audioElements = this.setupAudioElements();

        // unselect playlist element
        this.playListElements.each(function(element) {
            if (element.id == "playlist")
                element.addClassName('current');
            else
                element.removeClassName('current');
        });

        // select info element
        this.infoElements.each(function(element) {
            if (element.id == 'info_for_playlist')
                element.style.display = '';
            else
                element.style.display = 'none';
        });

        // select timer element
        this.timerElements.each(function(element) {
            if (element.id == 'timer_for_playlist')
                element.show();
            else if (element.visible())
                element.hide();
        });

        // select audios element
        this.audioElements.each(function(element) {
            if (element.id == 'audio_for_playlist')
                element.show();
            else if (element.visible())
                element.hide();
        });

        this.playListElements.each(function(element) {
            oThis.selectedIds.push(element.id);
        });
    },

    selectAudioElement: function(element) {
        // select same index on all selects
        this.audioElements.each(function(iterator) {
            var selects = iterator.getElementsByTagName('select');
            if (selects.length > 0) {
                var select = selects[0];
                if (select != element) {
                    select.options.selectedIndex = element.selectedIndex;
                }
            }
        });

        // set locale
        this.selectedLocale = $F(element);
    },

    play: function() {
        if (this.hasPlayer()) {
            log('PLAYER play(), playState: ' + this.videoPlayer.playState);
            switch (this.videoPlayer.playState) {
                case Player.PAUSE_STATE:
                    this.doPlay();
                    break;
                case Player.STOP_STATE:
                case Player.READY_STATE:
                case Player.INIT_STATE:
                    var videoURL = this.mediaURL + '?method=getVideoASX&' + this.selectedIds.serialize('selection') + '&type=' + this.deliveryType;
                    this.videoPlayer.url = videoURL;
                    log('PLAYER videoURL: ' + this.videoPlayer.url);
                    var audioURL = this.mediaURL + '?method=getAudioASX&' + this.selectedIds.serialize('selection') + '&locale=' + this.selectedLocale + '&type=' + this.deliveryType;
                    this.audioPlayer.url = audioURL;
                    log('PLAYER audioURL: ' + this.audioPlayer.url);
                    this.onPlay();
                    break;
                default:
                    break;
            }
        }
    },

    onPlay: function() {
        // override on subclass
        this.doPlay();
    },

    updateUserStateElements: function(json) {
        var oThis = this;

        // update time left element
        var timeLeftElement = $('timeLeftSpan');
        if (timeLeftElement) {
            if (json.timeConsumed > 0) {
                timeLeftElement.pulsate({ pulses: 2, duration: 2.0, beforeUpdate: function() {
                    timeLeftElement.innerHTML = json.timeLeft;
                } });
            }

            // tag playlist element as visited
            this.playListElements.each(function(element) {
                if (oThis.selectedIds.contains(element.id) && !element.hasClassName('visited'))
                    element.morph('visited', { duration: 2.0 });
            });
        }
    },

    setOverlay: function(name, defaultName) {
        // select overlay for new state
        this.videoOverlays.each(function(element) { element.hide(); });
        if (!this.videoPlayer.visible()) {
            var element = $$('.video_overlay').find(function(element) { return element.id == 'overlay_for_' + name; });
            if (element == undefined) {
                element = $$('.video_overlay').find(function(element) { return element.id == 'overlay_for_' + defaultName; });
            }
            element.show();
        }
    },

    setErrorOverlay: function(error) {
        this.setOverlay('error_' + error, 'error_default');
    },

    setStateOverlay: function(state) {
        this.setOverlay('state_' + state, 'state_default');
    },

    doPlay: function() {
        this.synchronizer.start();
        try {
            this.videoPlayer.controls.play();
            this.audioPlayer.controls.play();
            log('PLAY');
        } catch(err) { };
    },

    pause: function() {
        log('PAUSE');
        if (this.hasPlayer()) {
            this.synchronizer.stop();
            this.videoPlayer.controls.pause();
            this.audioPlayer.controls.pause();
        }
    },

    stop: function() {
        log('STOP');
        if (this.hasPlayer()) {
            this.synchronizer.stop();
            this.videoPlayer.controls.stop();
            this.audioPlayer.controls.stop();
        }
    },

    fullScreen: function() {
        if (this.hasPlayer()) {
            if (this.videoPlayer.playState == Player.PLAY_STATE ||
                this.videoPlayer.playState == Player.PAUSE_STATE) {
                this.videoPlayer.fullScreen = true;
            }
        }
    },

    playStateChange: function(newState) {
        log('playStateChange: ' + newState);

        // toggle visibility of video
        switch (newState) {
            case Player.PAUSE_STATE :
            case Player.PLAY_STATE :
                this.videoPlayer.style.display = '';
                break;
            case Player.STOP_STATE :
            case Player.BUFFERING_STATE :
            case Player.WAITING_STATE :
            case Player.MEDIA_ENDED_STATE :
            case Player.TRANSITIONING_STATE :
            case Player.READY_STATE :
            case Player.RECONNECTING_STATE :
            default :
                this.videoPlayer.style.display = 'none';
        }

        // select overlay for new state
        this.setStateOverlay(newState);
    }
});

/*
 * Constants
 */
Player.INIT_STATE = 0;
Player.STOP_STATE = 1;
Player.PAUSE_STATE = 2;
Player.PLAY_STATE = 3;
Player.BUFFERING_STATE = 6;
Player.WAITING_STATE = 7;
Player.MEDIA_ENDED_STATE = 8;
Player.TRANSITIONING_STATE = 9;
Player.READY_STATE = 10;
Player.RECONNECTING_STATE = 11;
