/**
 * Contacter
 * Voice feedback form for your website for saving and transcribing user voice messages to text.
 * Exclusively on https://1.envato.market/contacter
 *
 * @encoding        UTF-8
 * @version         1.7.8
 * @copyright       (C) 2018 - 2023 Merkulove ( https://merkulov.design/ ). All rights reserved.
 * @license         Envato License https://1.envato.market/KYbje
 * @contributors    Dmitry Merkulov (dmitry@merkulov.design)
 * @support         help@merkulov.design
 **/

( function ( $ ) {

    "use strict";

    $( document ).ready( function () {

        // noinspection JSUnresolvedVariable
        /** Data from WordPress. */
        let mdpContacter = window.mdpContacter;

        /** Show Developer tab on multiple logo clicks. */
        $( '.mdc-list .mdc-list-item.mdp-plugin-title' ).on( 'click', function () {

            let count = $( this ).data( 'count' );

            if ( typeof count === 'undefined' ) {
                count = 0;

                setTimeout( function () {
                    $( '.mdc-list .mdc-list-item.mdp-plugin-title' ).removeData( 'count' );
                }, 2000 );
            }

            count++;
            $( this ).data( 'count', count );

            if ( count > 3 ) {

                $( '.mdc-list > .mdc-list-item.mdp-developer' ).removeClass( 'mdc-hidden' ).addClass( 'mdc-list-item--activated' );

                $( '.mdc-list .mdc-list-item.mdp-plugin-title' ).removeData( 'count' );

            }

        } );

        /** The "Select Key File" button. */
        $( '.mdp-select-key-file-btn' ).on( 'click', function( e ) {
            e.preventDefault();
            let button = $( this );
            let key_uploader = wp.media( {
                title: 'Select or Upload API Key File',
                button: {
                    text: 'Use this API Key'
                },
                library: {
                    type: [ 'application/json', 'text/plain', 'json', 'text' ]
                },
                multiple: false  // Select only one file.
            } )
                .on('select', function() {
                    let attachment = key_uploader.state().get('selection').first().toJSON();
                    $( button ).prev().val( attachment.id );
                    $( button ).next().text( attachment.filename );

                    $( '#submit' ).trigger( 'click' );
                } )
                .open();
        } );

        /**
         * Show/hide Download Link fields.
         **/
        let downloadLinkSwitcher = $( '#mdp_contacter_general_settings_show_download_link' );
        function ShowDownloadLinkFields() {

            if ( downloadLinkSwitcher.prop( 'checked' ) === true ) {

                downloadLinkSwitcher.closest( 'tr' ).next().show( 300 );

            } else {

                downloadLinkSwitcher.closest( 'tr' ).next().hide( 300 );

            }

            /** To fix input label. */
            let index = $( '#mdp_contacter_general_settings_download_link_text' ).parent().data( 'mdc-index' );
            // noinspection SillyAssignmentJS
            window.MerkulovMaterial[index].value = window.MerkulovMaterial[index].value;

        }

        if ( downloadLinkSwitcher.length ) {
            downloadLinkSwitcher.on( 'click', ShowDownloadLinkFields );
            ShowDownloadLinkFields();
        }

        /**
         * Show/hide Custom file name pattern fields.
         **/
        let fileNameSwitcher = $( '#mdp_contacter_general_settings_file_name' );
        function ShowFileNameFields() {

            if ( fileNameSwitcher.prop( 'checked' ) === true ) {

                fileNameSwitcher.closest( 'tr' ).next().show( 300 );

            } else {

                fileNameSwitcher.closest( 'tr' ).next().hide( 300 );

            }

            /** To fix input label. */
            let index = $( '#mdp_contacter_general_settings_file_name_pattern' ).parent().data( 'mdc-index' );
            // noinspection SillyAssignmentJS
            window.MerkulovMaterial[index].value = window.MerkulovMaterial[index].value;

        }

        if ( fileNameSwitcher.length ) {
            fileNameSwitcher.on( 'click', ShowFileNameFields );
            ShowFileNameFields();
        }

        /**
         * Show/hide Speech Recognition fields.
         **/
        let SpeechSwitcher = $( '#mdp_contacter_general_settings_speech_recognition' );
        function ShowSpeechRecognitionFields() {

            if ( SpeechSwitcher.prop( 'checked' ) === true ) {

                SpeechSwitcher.closest( 'tr' ).next().show( 300 ).next().show( 300 ).next().show( 300 );

                if ( ! $( '#mdp-contacter-general-settings-dnd-api-key' ).val() ) {
                    SpeechSwitcher.closest( 'tr' ).next().show().next().hide().next().hide();
                }

            } else {

                SpeechSwitcher.closest( 'tr' ).next().hide( 300 ).next().hide( 300 ).next().hide( 300 );

            }
        }

        if ( SpeechSwitcher.length ) {
            SpeechSwitcher.on( 'click', ShowSpeechRecognitionFields );
            ShowSpeechRecognitionFields();
        }

        /**
         * Show/hide Float Button fields.
         **/
        let FButtonSwitcher = $( '#mdp_contacter_floatbutton_settings_show_fbutton' );
        function ShowFButtonSwitcherFields() {

            if ( FButtonSwitcher.prop( 'checked' ) === true ) {
                FButtonSwitcher.closest( 'tr' )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 )
                    .next().show( 300 );
            } else {
                FButtonSwitcher.closest( 'tr' )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 )
                    .next().hide( 300 );
            }
        }

        if ( FButtonSwitcher.length ) {
            FButtonSwitcher.on( 'click', ShowFButtonSwitcherFields );
            ShowFButtonSwitcherFields();
        }

        /**
         * Show/Hide Icon picker for float button depends on the icon position select.
         */
        const fbuttonIcon = '#mdp_contacter_floatbutton_settings_fbutton_icon';
        if ( $( fbuttonIcon + '_position' ).val() === 'none' ) {
            $( fbuttonIcon ).closest( 'tr' ).hide();
        }
        $( fbuttonIcon + '_position' ).change(function() {
            this.value === "none" ?
                $( fbuttonIcon ).closest( 'tr' ).hide( 300 ):
                $( fbuttonIcon ).closest( 'tr' ).show( 300 );
        });

        /** Drag & Drop JSON reader. */
        let $dropZone = $( '#mdp-api-key-drop-zone' );
        $dropZone.on( 'dragenter', function() {
            hideMessage();
            $( this ).addClass( 'mdp-hover' );
        } );

        $dropZone.on('dragleave', function() {
            $( this ).removeClass( 'mdp-hover' );
        } );

        /** Setup DnD listeners. */
        $dropZone.on( 'dragover', handleDragOver );

        /** Text Input to store key file. */
        let $key_input = $( '#mdp-contacter-general-settings-dnd-api-key' );

        /**
         * Read dragged file by JS.
         **/
        $dropZone.on( 'drop', function ( e ) {

            e.stopPropagation();
            e.preventDefault();

            // Show busy spinner.
            $( this ).removeClass( 'mdp-hover' );
            $dropZone.addClass( 'mdp-busy' );

            let file = e.originalEvent.dataTransfer.files[0]; // FileList object.

            /** Check is one valid JSON file. */
            if ( ! checkKeyFile( file ) ) {
                $dropZone.removeClass( 'mdp-busy' );
                return;
            }

            /** Read key file to input. */
            readFile( file )

        } );

        /**
         * Read key file to input.
         **/
        function readFile( file ) {

            let reader = new FileReader();

            /** Closure to capture the file information. */
            reader.onload = ( function( theFile ) {

                return function( e ) {

                    let json_content = e.target.result;

                    /** Check if a string is a valid JSON string. */
                    if ( ! isJSON( json_content ) ) {

                        showErrorMessage( '<b>Error</b>: Uploaded file is empty or not a valid JSON file.' );

                        $dropZone.removeClass( 'mdp-busy' );
                        $( this ).addClass( 'mdp-error' );
                        return;

                    }

                    /** Check if the key has required field. */
                    let key = JSON.parse( json_content );
                    if ( typeof( key.private_key ) === 'undefined' ){

                        showErrorMessage( '<b>Error</b>: Your API key file looks like not valid. Please make sure you use the correct key.' );

                        $dropZone.removeClass( 'mdp-busy' );
                        $( this ).addClass( 'mdp-error' );
                        return;

                    }

                    /** Encode and Save to Input. */
                    $key_input.val( btoa( json_content ) );

                    /** Hide error messages. */
                    hideMessage();

                    /** If we have long valid key in input. */
                    if ( $key_input.val().length > 1000 ) {

                        $( '#submit' ).click(); // Save settings.

                    } else {

                        showErrorMessage( '<b>Error</b>: Your API key file looks like not valid. Please make sure you use the correct key.' );
                        $dropZone.removeClass( 'mdp-busy' );
                        $( this ).addClass( 'mdp-error' );

                    }

                };

            } )( file );

            /** Read file as text. */
            reader.readAsText( file );

        }

        /**
         * Show upload form on click.
         **/
        let $file_input = $( '#mdp-dnd-file-input' );
        $dropZone.on( 'click', function () {

            $file_input.click();

        } );

        $file_input.on( 'change', function ( e ) {

            $dropZone.addClass( 'mdp-busy' );

            let file = e.target.files[0];

            /** Check is one valid JSON file. */
            if ( ! checkKeyFile( file ) ) {
                $dropZone.removeClass( 'mdp-busy' );
                return;
            }

            /** Read key file to input. */
            readFile( file );

        } );

        /** Show Error message under drop zone. */
        function showErrorMessage( msg ) {

            let $msgBox = $dropZone.next();

            $msgBox.addClass( 'mdp-error' ).html( msg );

        }

        /** Hide message under drop zone. */
        function hideMessage() {

            let $msgBox = $dropZone.next();

            $msgBox.removeClass( 'mdp-error' ).html( '' );

        }

        /**
         * Check if a string is a valid JSON string.
         *
         * @param str - JSON string to check.
         **/
        function isJSON( str ) {

            try {

                JSON.parse( str );

            } catch ( e ) {

                return false;

            }

            return true;

        }

        function handleDragOver( e ) {

            e.stopPropagation();
            e.preventDefault();

        }

        /**
         * Check file is a single valid JSON file.
         *
         * @param file - JSON file to check.
         **/
        function checkKeyFile( file ) {

            /** Select only one file. */
            if ( null == file ) {

                showErrorMessage( '<b>Error</b>: Failed to read file. Please try again.' );

                return false;

            }

            /** Process json file only. */
            if ( ! file.type.match( 'application/json' ) ) {

                showErrorMessage( '<b>Error</b>: API Key must be a valid JSON file.' );

                return false;

            }

            return true;
        }

        /** Reset Key File. */
        $( '.mdp-contacter-reset-key-btn' ).on( 'click', function () {

            $key_input.val( '' );
            $( '#submit' ).trigger( 'click' );

        } );

        // mdp_contacter_unsaved = false;

    } );

} ( jQuery ) );
