commit cf8ecfcf6482d1fd77518a81f00f3f08a2a5f231 Author: Admin Date: Fri Jan 16 20:24:38 2026 -0600 Bot Discord - Commit completo con todos los cambios diff --git a/.env b/.env new file mode 100755 index 0000000..1a9c7de --- /dev/null +++ b/.env @@ -0,0 +1,7 @@ +# Auto-generado desde variables de entorno +# NO editar manualmente - los cambios se perderán al reiniciar + +APP_ENV=pruebas +APP_DEBUG=false + +APP_ENVIRONMENT=pruebas diff --git a/.env.example b/.env.example new file mode 100755 index 0000000..44670c8 --- /dev/null +++ b/.env.example @@ -0,0 +1,23 @@ +# Configuración de la aplicación +APP_ENV=development +APP_DEBUG=true +APP_URL=http://localhost + +# Configuración de la base de datos +DB_HOST=localhost +DB_PORT=3306 +DB_NAME=nombre_base_datos +DB_USER=usuario +DB_PASS=contraseña +DB_DIALECT=mysql + +# Configuración de JWT +JWT_SECRET=clave_secreta_segura +JWT_ALGORITHM=HS256 +JWT_EXPIRATION=3600 + +# Configuración de Discord +DISCORD_GUILD_ID=tu_guild_id +DISCORD_CLIENT_ID=tu_client_id +DISCORD_CLIENT_SECRET=tu_client_secret +DISCORD_BOT_TOKEN=tu_bot_token diff --git a/.env.pruebas b/.env.pruebas new file mode 100755 index 0000000..f089916 --- /dev/null +++ b/.env.pruebas @@ -0,0 +1,49 @@ +# Configuración de la aplicación +APP_ENV=production +APP_DEBUG=false +APP_URL=https://ponsprueba.ddns.net + +# Configuración de la base de datos +DB_HOST=10.10.4.17 +DB_PORT=3391 +DB_NAME=bot2 +DB_USER=nickpons666 +DB_PASS=MiPo6425@@ +DB_DIALECT=mysql + +# Configuración de JWT +JWT_SECRET=19c5020fa8207d2c3b9e82f430784667e001f1eb733848922f7bcb9be98f93c2 +JWT_ALGORITHM=HS256 +JWT_EXPIRATION=3600 + +# Configuración de Discord +DISCORD_GUILD_ID=1338327171013541999 +DISCORD_CLIENT_ID=1385790344594985061 +DISCORD_CLIENT_SECRET=hK9SNiYdenHQVxakt8Mx3RoMkZ5oOJvk +DISCORD_BOT_TOKEN=MTM4NTc5MDM0NDU5NDk4NTA2MQ.GvobiS.TRQM9dX7vDjmuGVa3Ckp6YRtGEWxdW0gBDbvCI + +# Configuración de Telegram +TELEGRAM_BOT_TOKEN=8469229183:AAEVIV5e7rjDXKNgFTX0dnCW6JWB88X4p2I +TELEGRAM_WEBHOOK_TOKEN=webhook_secure_token_12345 +TEST_ENV_LOAD=caos_cargado + +LIBRETRANSLATE_URL=http://10.10.4.17:5000 + +N8N_URL=https://n8n-dragon.ddns.net +N8N_TOKEN=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiI4MWY4YjU3YS0wMTg2LTQ1NTctOWZlMC1jYWUxNjZlYzZlMTkiLCJpc3MiOiJuOG4iLCJhdWQiOiJwdWJsaWMtYXBpIiwiaWF0IjoxNzU1OTMwODM5fQ.2tLbddyhMTKplp9n-qVNiAgQCUj2YEvVASwLnNjgCt0 + +# ----------------------------------------- +# --- Configuración para la migración a n8n --- +# ----------------------------------------- +# URL base de esta aplicación, para que n8n pueda llamarla. +APP_BASE_URL=https://ponsprueba.ddns.net + +# Clave secreta para la comunicación segura entre n8n y api_handler.php. +# DEBE SER UNA CADENA LARGA Y ALEATORIA. Genera una con: openssl rand -hex 32 +INTERNAL_API_KEY="b5dda33b8eb062e06e100c98a8947c0248b6e38973dfd689e81f725af238d23c" + +# URL completa del webhook de n8n que procesa la cola de mensajes (process_queue_workflow). +# La obtienes del nodo Webhook en tu flujo de n8n. +N8N_PROCESS_QUEUE_WEBHOOK_URL="https://n8n-dragon.ddns.net/webhooktest/ia" +N8N_IA_WEBHOOK_URL="https://n8n-dragon.ddns.net/webhook/ia" +N8N_IA_WEBHOOK_URL_DISCORD="https://n8n-dragon.ddns.net/webhook/42e803ae-8aee-4b1c-858a-6c6d3fbb6230" diff --git a/.env.reod b/.env.reod new file mode 100755 index 0000000..17ff6a1 --- /dev/null +++ b/.env.reod @@ -0,0 +1,49 @@ +# Configuración de la aplicación +APP_ENV=production +APP_DEBUG=false +APP_URL=https://reod-dragon.ddns.net + +# Configuración de la base de datos +DB_HOST=10.10.4.17 +DB_PORT=3390 +DB_NAME=bot +DB_USER=nickpons666 +DB_PASS=MiPo6425@@ +DB_DIALECT=mysql + +# Configuración de JWT +JWT_SECRET=19c5020fa8207d2c3b9e82f430784667e001f1eb733848922f7bcb9be98f93c2 +JWT_ALGORITHM=HS256 +JWT_EXPIRATION=3600 + +# Configuración de Discord +DISCORD_GUILD_ID=1338327171013541999 +DISCORD_CLIENT_ID=1385790344594985061 +DISCORD_CLIENT_SECRET=hK9SNiYdenHQVxakt8Mx3RoMkZ5oOJvk +DISCORD_BOT_TOKEN=MTM4NTc5MDM0NDU5NDk4NTA2MQ.GvobiS.TRQM9dX7vDjmuGVa3Ckp6YRtGEWxdW0gBDbvCI + +# Configuración de Telegram +TELEGRAM_BOT_TOKEN=8469229183:AAEVIV5e7rjDXKNgFTX0dnCW6JWB88X4p2I +TELEGRAM_WEBHOOK_TOKEN=webhook_secure_token_12345 +TEST_ENV_LOAD=caos_cargado + +LIBRETRANSLATE_URL=http://10.10.4.17:5000 + +N8N_URL=https://n8n-dragon.ddns.net +N8N_TOKEN=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiI4MWY4YjU3YS0wMTg2LTQ1NTctOWZlMC1jYWUxNjZlYzZlMTkiLCJpc3MiOiJuOG4iLCJhdWQiOiJwdWJsaWMtYXBpIiwiaWF0IjoxNzU1OTMwODM5fQ.2tLbddyhMTKplp9n-qVNiAgQCUj2YEvVASwLnNjgCt0 + +# ----------------------------------------- +# --- Configuración para la migración a n8n --- +# ----------------------------------------- +# URL base de esta aplicación, para que n8n pueda llamarla. +APP_BASE_URL=https://reod-dragon.ddns.net + +# Clave secreta para la comunicación segura entre n8n y api_handler.php. +# DEBE SER UNA CADENA LARGA Y ALEATORIA. Genera una con: openssl rand -hex 32 +INTERNAL_API_KEY="b5dda33b8eb062e06e100c98a8947c0248b6e38973dfd689e81f725af238d23c" + +# URL completa del webhook de n8n que procesa la cola de mensajes (process_queue_workflow). +# La obtienes del nodo Webhook en tu flujo de n8n. +N8N_PROCESS_QUEUE_WEBHOOK_URL="https://n8n-dragon.ddns.net/webhook/telegram-unified" +N8N_IA_WEBHOOK_URL="https://n8n-dragon.ddns.net/webhook/ia" +N8N_IA_WEBHOOK_URL_DISCORD="https://n8n-dragon.ddns.net/webhook/42e803ae-8aee-4b1c-858a-6c6d3fbb6230" \ No newline at end of file diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..9f2a7f1 --- /dev/null +++ b/.gitignore @@ -0,0 +1,40 @@ +# Dependencias +vendor/ +composer.lock + +# Logs +logs/ +*.log + +# Directorios de caché +.cache/ +*.cache + +# Directorios de datos +uploads/ +videos/ +galeria/ + +# Archivos de configuración local +.env.local +.env.*.local + +# Archivos de editor +.vscode/ +.idea/ +*.swp +*.swo +*~ +.DS_Store + +# Archivos temporales +*.tmp +*.bak +process_queue.php.backup_* + +# Node modules (si es que hay) +node_modules/ + +# Build outputs +dist/ +build/ diff --git a/.htaccess b/.htaccess new file mode 100755 index 0000000..adba128 --- /dev/null +++ b/.htaccess @@ -0,0 +1,114 @@ +# Configuración básica +Options -Indexes +FollowSymLinks -MultiViews + +# Habilitar reescritura de URLs + + RewriteEngine On + + # Asegurar que el servidor siga los enlaces simbólicos + Options +FollowSymLinks + + # Regla para el webhook de Telegram - debe ser lo primero + RewriteCond %{REQUEST_URI} ^/telegram_bot_webhook\.php [NC] + RewriteRule ^ - [L] + + # Reglas para otros archivos de webhook + RewriteRule ^(telegram_webhook|test_webhook|set_webhook)\.php$ - [L,NC] + + # Excluir archivos específicos de la verificación de sesión + RewriteCond %{REQUEST_URI} !^/login\.php [NC] + RewriteCond %{REQUEST_URI} !^/assets/ [NC] + RewriteCond %{REQUEST_URI} !^/translate_proxy\.php [NC] + RewriteCond %{REQUEST_URI} !\.(css|js|jpe?g|png|gif|ico|svg|woff2?|ttf|eot|json|txt|map)$ [NC] + + # Para el resto de las rutas, redirigir a login.php si no hay sesión + RewriteCond %{REQUEST_FILENAME} !-f + RewriteCond %{REQUEST_FILENAME} !-d + RewriteCond %{REQUEST_URI} !^/translate_proxy\.php [NC] + RewriteRule ^(.*)$ /login.php [L,QSA] + + +# Configuración de seguridad + + # Protección básica de cabeceras + Header always set X-Frame-Options "SAMEORIGIN" + Header always set X-XSS-Protection "1; mode=block" + Header always set X-Content-Type-Options "nosniff" + + # Habilita la política de seguridad de contenido (CSP) - Ajusta según sea necesario + # Header set Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' 'unsafe-eval'; style-src 'self' 'unsafe-inline'; img-src 'self' data: https:; font-src 'self' data:;" + + # Habilita HSTS (solo para HTTPS) + # Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains; preload" + + # Configuración de referrer policy + Header always set Referrer-Policy "strict-origin-when-cross-origin" + + # Eliminar cabeceras que revelan información + Header unset X-Powered-By + Header unset X-Pingback + Header unset Server + Header unset X-AspNet-Version + Header unset X-AspNetMvc-Version + + +# Proteger archivos sensibles + + + Require all denied + + + Order deny,allow + Deny from all + + + +# Deshabilitar la visualización de directorios +Options -Indexes + +# Prevenir acceso a archivos ocultos + + Require all denied + + +# Configuración de caché para mejorar el rendimiento + + ExpiresActive On + ExpiresByType image/jpg "access plus 1 year" + ExpiresByType image/jpeg "access plus 1 year" + ExpiresByType image/gif "access plus 1 year" + ExpiresByType image/png "access plus 1 year" + ExpiresByType text/css "access plus 1 month" + ExpiresByType application/pdf "access plus 1 month" + ExpiresByType text/x-javascript "access plus 1 month" + ExpiresByType application/x-shockwave-flash "access plus 1 month" + ExpiresByType image/x-icon "access plus 1 year" + ExpiresDefault "access plus 2 days" + + +# Comprimir archivos para mejorar el rendimiento + + AddOutputFilterByType DEFLATE text/plain + AddOutputFilterByType DEFLATE text/html + AddOutputFilterByType DEFLATE text/xml + AddOutputFilterByType DEFLATE text/css + AddOutputFilterByType DEFLATE application/xml + AddOutputFilterByType DEFLATE application/xhtml+xml + AddOutputFilterByType DEFLATE application/rss+xml + AddOutputFilterByType DEFLATE application/javascript + AddOutputFilterByType DEFLATE application/x-javascript + AddOutputFilterByType DEFLATE image/svg+xml + + +# Configuración de PHP + + php_flag display_errors off + php_value max_execution_time 30 + php_value max_input_time 60 + php_value max_input_vars 1000 + php_value memory_limit 128M + php_value post_max_size 32M + php_value upload_max_filesize 32M + php_flag log_errors on + php_value error_log /var/log/php_errors.log + diff --git a/admin/activity.php b/admin/activity.php new file mode 100755 index 0000000..9bf0db0 --- /dev/null +++ b/admin/activity.php @@ -0,0 +1,84 @@ +query("SELECT COUNT(*) FROM activity_log"); +$total_records = $total_stmt->fetchColumn(); +$total_pages = ceil($total_records / $limit); + +// Fetch activity logs +$stmt = $pdo->prepare("SELECT * FROM activity_log ORDER BY timestamp DESC LIMIT :limit OFFSET :offset"); +$stmt->bindParam(':limit', $limit, PDO::PARAM_INT); +$stmt->bindParam(':offset', $offset, PDO::PARAM_INT); +$stmt->execute(); +$logs = $stmt->fetchAll(PDO::FETCH_ASSOC); + +require_once __DIR__ . '/../templates/header.php'; +?> + +
+

Registro de Actividad

+ +
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
UsuarioAcciónDetallesFecha y Hora
No hay registros de actividad.
+
+
+ + + +
+ + diff --git a/admin/comandos.php b/admin/comandos.php new file mode 100755 index 0000000..7a0fabd --- /dev/null +++ b/admin/comandos.php @@ -0,0 +1,54 @@ +query("SELECT name, telegram_command FROM recurrent_messages WHERE telegram_command IS NOT NULL AND telegram_command != '' ORDER BY name ASC"); + $commands = $stmt->fetchAll(PDO::FETCH_ASSOC); +} catch (PDOException $e) { + die("Error: No se pudieron cargar los comandos."); +} + +require_once __DIR__ . '/../templates/header.php'; +?> + +
+

Lista de Comandos de Telegram

+

Esta es una lista de todos los comandos de plantilla que has configurado. Los usuarios pueden usar estos comandos en Telegram para recibir el mensaje correspondiente.

+ +
+ + + +
+ + + + + + + + + + + + + + + +
Comando de TelegramNombre de la Plantilla
+ # +
+
+ +
+
+ + diff --git a/admin/get_user_groups.php b/admin/get_user_groups.php new file mode 100755 index 0000000..f0deab9 --- /dev/null +++ b/admin/get_user_groups.php @@ -0,0 +1,45 @@ + 'Unauthorized']); + exit(); +} + +$recipientId = $_GET['recipient_id'] ?? null; + +if (!$recipientId) { + echo json_encode(['error' => 'Recipient ID missing']); + exit(); +} + +try { + // Obtener el nombre del usuario + $stmt = $pdo->prepare("SELECT name FROM recipients WHERE id = ?"); + $stmt->execute([$recipientId]); + $userName = $stmt->fetchColumn(); + + // Obtener los grupos a los que pertenece el usuario + $stmt = $pdo->prepare(" + SELECT tgm.chat_id, r.name as group_name + FROM telegram_group_members tgm + JOIN recipients r ON tgm.chat_id = r.platform_id AND r.platform = 'telegram' AND r.type = 'channel' + WHERE tgm.recipient_id = ? + "); + $stmt->execute([$recipientId]); + $groups = $stmt->fetchAll(PDO::FETCH_ASSOC); + + echo json_encode(['success' => true, 'userName' => $userName, 'groups' => $groups]); + +} catch (PDOException $e) { + error_log("Error fetching user groups: " . $e->getMessage()); + echo json_encode(['error' => 'Database error']); +} catch (Exception $e) { + error_log("Error: " . $e->getMessage()); + echo json_encode(['error' => 'Server error']); +} +?> \ No newline at end of file diff --git a/admin/languages.php b/admin/languages.php new file mode 100755 index 0000000..2340d82 --- /dev/null +++ b/admin/languages.php @@ -0,0 +1,214 @@ +query("SELECT * FROM supported_languages ORDER BY language_name ASC"); + $languages = $stmt->fetchAll(PDO::FETCH_ASSOC); +} catch (PDOException $e) { + $languages = []; + $errorMessage = "Error al cargar los idiomas: " . $e->getMessage(); +} + +?> + +
+

Gestionar Idiomas de Traducción

+

Activa o desactiva los idiomas a los que el bot traducirá automáticamente los mensajes.

+ + +
+ + +
+
+
Idiomas Soportados
+ +
+
+
+ +
No se encontraron idiomas.
+ + +
+
+
+
+ +
+
+ + +
+
+
+ +
+ + () +
+
+
+
+ > + +
+
+ + +
+
+
+
+
+ + + + \ No newline at end of file diff --git a/admin/recipients.php b/admin/recipients.php new file mode 100755 index 0000000..ecd46e7 --- /dev/null +++ b/admin/recipients.php @@ -0,0 +1,538 @@ + null, + 'name' => '', + 'platform_id' => '', + 'type' => 'channel', + 'platform' => 'discord', + 'language_code' => 'es' +]; + +// Handle form submissions +if ($_SERVER['REQUEST_METHOD'] === 'POST') { + $current_user_id = $_SESSION['user_id']; + $current_username = $_SESSION['username']; + $action = $_POST['action'] ?? null; + + // Action: Add or Update Recipient + if (isset($_POST['add_recipient']) || isset($_POST['update_recipient'])) { + $platform = $_POST['platform'] ?? 'discord'; + $type = $_POST['type'] ?? 'channel'; + $name = $_POST['name'] ?? ''; + $platform_id = $_POST['platform_id'] ?? ''; + $language_code = $_POST['language_code'] ?? 'es'; + $id = $_POST['id'] ?? null; + + if (empty($name) || empty($platform_id) || empty($type) || empty($platform)) { + $error = "Todos los campos son obligatorios."; + } elseif (!is_numeric($platform_id)) { + $error = "El ID de Plataforma debe ser un número."; + } else { + try { + if (isset($_POST['update_recipient'])) { // UPDATE + $stmt = $pdo->prepare("UPDATE recipients SET name = ?, platform_id = ?, type = ?, platform = ?, language_code = ? WHERE id = ?"); + $stmt->execute([$name, $platform_id, $type, $platform, $language_code, $id]); + $details = 'Admin ' . $current_username . ' updated recipient: ' . $name . ' (' . $platform . ':' . $platform_id . ')'; + log_activity($current_user_id, 'Recipient Updated', $details); + header('Location: recipients.php?success=updated'); + exit(); + } else { // ADD + $stmt = $pdo->prepare("INSERT INTO recipients (name, platform_id, type, platform, language_code) VALUES (?, ?, ?, ?, ?)"); + $stmt->execute([$name, $platform_id, $type, $platform, $language_code]); + $new_recipient_id = $pdo->lastInsertId(); + $details = 'Admin ' . $current_username . ' added new recipient: ' . $name . ' (' . $platform . ':' . $platform_id . ')'; + log_activity($current_user_id, 'Recipient Added', $details); + $success = "Destinatario añadido con éxito."; + } + } catch (PDOException $e) { + if ($e->errorInfo[1] == 1062) { + $error = "El ID de Plataforma ('$platform_id') ya existe."; + } else { + $error = "Error en la base de datos: " . $e->getMessage(); + } + // Keep form data on error + $edit_mode = isset($_POST['update_recipient']); + $edit_recipient = ['id' => $id, 'name' => $name, 'platform_id' => $platform_id, 'type' => $type, 'platform' => $platform, 'language_code' => $language_code]; + } + } + } + // Action: Delete Single Recipient + elseif (isset($_POST['delete_recipient'])) { + $id_to_delete = $_POST['id_to_delete']; + try { + $stmt_recipient = $pdo->prepare("SELECT name, platform, platform_id FROM recipients WHERE id = ?"); + $stmt_recipient->execute([$id_to_delete]); + $recipient_info = $stmt_recipient->fetch(PDO::FETCH_ASSOC); + $details = 'Admin ' . $current_username . ' deleted recipient: ' . ($recipient_info['name'] ?? 'Unknown') . ' (' . ($recipient_info['platform'] ?? 'N/A') . ':' . ($recipient_info['platform_id'] ?? 'N/A') . ')'; + + $stmt = $pdo->prepare("DELETE FROM recipients WHERE id = ?"); + $stmt->execute([$id_to_delete]); + log_activity($current_user_id, 'Recipient Deleted', $details); + $success = "Destinatario eliminado con éxito."; + } catch (PDOException $e) { + $error = "Error al eliminar. Es posible que el destinatario esté en uso."; + } + } + // Action: Kick Telegram User + elseif ($action === 'kick_telegram_user') { + $recipient_id_to_kick = $_POST['recipient_id_to_kick'] ?? null; + $chat_id_to_kick_from = $_POST['chat_id_to_kick_from'] ?? null; + + if ($recipient_id_to_kick && $chat_id_to_kick_from) { + try { + // Get recipient's platform_id (Telegram user ID) + $stmt = $pdo->prepare("SELECT platform_id, name FROM recipients WHERE id = ? AND platform = 'telegram' AND type = 'user'"); + $stmt->execute([$recipient_id_to_kick]); + $recipient_info = $stmt->fetch(PDO::FETCH_ASSOC); + $telegram_user_id = $recipient_info['platform_id'] ?? null; + $recipient_name = $recipient_info['name'] ?? 'Unknown'; + + if ($telegram_user_id) { + // Get bot token + $botToken = $_ENV['TELEGRAM_BOT_TOKEN'] ?? ''; + if (empty($botToken)) { + throw new Exception("Token de bot de Telegram no configurado."); + } + + // Telegram API URL for banning a chat member + $telegramApiUrl = "https://api.telegram.org/bot{$botToken}/banChatMember"; + $params = [ + 'chat_id' => $chat_id_to_kick_from, + 'user_id' => $telegram_user_id, + 'until_date' => time() + 30 // Ban for 30 seconds to ensure they are removed, then they can rejoin + ]; + + $options = [ + 'http' => [ + 'header' => "Content-type: application/x-www-form-urlencoded\r\n", + 'method' => 'POST', + 'content' => http_build_query($params), + ], + ]; + $context = stream_context_create($options); + $result = file_get_contents($telegramApiUrl, false, $context); + $response = json_decode($result, true); + + if ($response && $response['ok']) { + // If successful, unban immediately to allow re-entry + $unbanTelegramApiUrl = "https://api.telegram.org/bot{$botToken}/unbanChatMember"; + $unbanParams = [ + 'chat_id' => $chat_id_to_kick_from, + 'user_id' => $telegram_user_id, + 'only_if_banned' => true // Only try to unban if they are actually banned + ]; + $unbanOptions = [ + 'http' => [ + 'header' => "Content-type: application/x-www-form-urlencoded\r\n", + 'method' => 'POST', + 'content' => http_build_query($unbanParams), + ], + ]; + $unbanContext = stream_context_create($unbanOptions); + $unbanResult = file_get_contents($unbanTelegramApiUrl, false, $unbanContext); + $unbanResponse = json_decode($unbanResult, true); + + if ($unbanResponse && $unbanResponse['ok']) { + $success = "Usuario de Telegram expulsado del grupo (permite reingreso) y eliminado de la base de datos."; + } else { + // Log unban error but still proceed with local deletion as kick was successful + error_log("Error al desbanear usuario de Telegram después de la expulsión: " . ($unbanResponse['description'] ?? 'Error desconocido')); + $success = "Usuario de Telegram expulsado del grupo (error al permitir reingreso) y eliminado de la base de datos."; + } + + // Delete from local DB regardless of unban success, as the kick itself was successful + $stmt = $pdo->prepare("DELETE FROM recipients WHERE id = ?"); + $stmt->execute([$recipient_id_to_kick]); + $details = 'Admin ' . $current_username . ' kicked Telegram user: ' . $recipient_name . ' (ID: ' . $telegram_user_id . ') from group ID: ' . $chat_id_to_kick_from; + log_activity($current_user_id, 'Telegram User Kicked', $details); + + } else { + $error = "Error al expulsar usuario de Telegram: " . ($response['description'] ?? 'Error desconocido'); + } + } else { + $error = "Usuario de Telegram no encontrado o no es un usuario válido para expulsar."; + } + } catch (Exception $e) { + $error = "Error al procesar la expulsión: " . $e->getMessage(); + } + } else { + $error = "Faltan parámetros para expulsar al usuario de Telegram."; + } + } + // Action: Delete Multiple Recipients + elseif ($action === 'delete_selected' && !empty($_POST['selected_recipients'])) { + $deleted_count = 0; + $error_count = 0; + + foreach ($_POST['selected_recipients'] as $recipient_id) { + try { + $stmt_recipient = $pdo->prepare("SELECT name, platform, platform_id FROM recipients WHERE id = ?"); + $stmt_recipient->execute([$recipient_id]); + $recipient_info = $stmt_recipient->fetch(PDO::FETCH_ASSOC); + $details = 'Admin ' . $current_username . ' deleted recipient: ' . ($recipient_info['name'] ?? 'Unknown') . ' (' . ($recipient_info['platform'] ?? 'N/A') . ':' . ($recipient_info['platform_id'] ?? 'N/A') . ')'; + + $stmt = $pdo->prepare("DELETE FROM recipients WHERE id = ?"); + $stmt->execute([$recipient_id]); + log_activity($current_user_id, 'Recipient Deleted', $details); + $deleted_count++; + } catch (PDOException $e) { + $error_count++; + error_log("Error al eliminar destinatario ID $recipient_id: " . $e->getMessage()); + } + } + + if ($deleted_count > 0) { + $success = "Se eliminaron $deleted_count destinatarios correctamente."; + if ($error_count > 0) { + $error = "Hubo errores al eliminar $error_count destinatarios."; + } + header('Location: recipients.php?success=deleted_multiple&deleted=' . $deleted_count . '&errors=' . $error_count); + exit(); + } else if ($error_count > 0) { + $error = "No se pudo eliminar ningún destinatario. Por favor, inténtalo de nuevo."; + } + } +} + +// Handle entering edit mode via GET request +if (isset($_GET['action']) && $_GET['action'] === 'edit' && isset($_GET['id'])) { + $edit_mode = true; + $stmt = $pdo->prepare("SELECT * FROM recipients WHERE id = ?"); + $stmt->execute([$_GET['id']]); + $recipient_to_edit = $stmt->fetch(); + if ($recipient_to_edit) { + $edit_recipient = $recipient_to_edit; + } +} + +// Fetch all recipients to display +$recipients = $pdo->query("SELECT * FROM recipients ORDER BY platform, type, name ASC")->fetchAll(); + +$pageTitle = 'Gestionar Destinatarios'; +require_once __DIR__ . '/../templates/header.php'; + +// Display feedback messages +if (isset($error)) echo "
$error
"; +if (isset($success)) echo "
$success
"; + +if (isset($_GET['success'])) { + if ($_GET['success'] === 'deleted_multiple') { + $deleted = isset($_GET['deleted']) ? (int)$_GET['deleted'] : 0; + $errors = isset($_GET['errors']) ? (int)$_GET['errors'] : 0; + + if ($deleted > 0) { + echo '
Se eliminaron ' . $deleted . ' destinatarios correctamente.
'; + } + if ($errors > 0) { + echo '
Hubo errores al eliminar ' . $errors . ' destinatarios.
'; + } + } else { + echo "
Operación completada con éxito.
"; + } +} +?> + +
+

Gestionar Destinatarios

+ + +
+
+
+
+
+
+ +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + +
+
+ + + + + +
+ + + +
+
+
+
+ + +
+
+
Lista de Destinatarios
+
+ + +
+
+
+
+ + +
+ + + + + + + + + + + + + + + + + + + + + + + + + + + +
PlataformaNombreID de PlataformaTipoIdiomaAñadido enAcciones
+ + + + +
+ + + + + + + + + + + +
+
+
+ +
+
+
+ + + + + + + \ No newline at end of file diff --git a/admin/set_test_webhook.php b/admin/set_test_webhook.php new file mode 100755 index 0000000..3526ca0 --- /dev/null +++ b/admin/set_test_webhook.php @@ -0,0 +1,65 @@ + $webhookUrl, 'allowed_updates' => json_encode(['message', 'callback_query'])]; + +$ch = curl_init($apiUrl); +curl_setopt_array($ch, [ + CURLOPT_RETURNTRANSFER => true, + CURLOPT_POST => true, + CURLOPT_POSTFIELDS => $postData, + CURLOPT_SSL_VERIFYPEER => true, +]); + +$response = curl_exec($ch); +$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); +$error = curl_error($ch); +curl_close($ch); + +// Mostrar resultados +echo "\nRespuesta de la API de Telegram (HTTP $httpCode):\n"; +if ($error) { + echo "Error: $error\n"; +} else { + $result = json_decode($response, true); + if (json_last_error() === JSON_ERROR_NONE) { + if ($result['ok'] ?? false) { + echo "✅ Webhook configurado correctamente.\n"; + echo "URL: " . ($result['result']['url'] ?? 'N/A') . "\n"; + echo "Tiene certificado: " . ($result['result']['has_custom_certificate'] ? 'Sí' : 'No') . "\n"; + echo "Updates pendientes: " . ($result['result']['pending_update_count'] ?? '0') . "\n"; + } else { + echo "❌ Error al configurar el webhook: " . ($result['description'] ?? 'Error desconocido') . "\n"; + } + } else { + echo "Respuesta no válida: " . substr($response, 0, 200) . "...\n"; + } +} + +echo "\nPara verificar la configuración actual del webhook, ejecuta:\n"; +echo "curl -s 'https://api.telegram.org/bot{$botToken}/getWebhookInfo' | jq\n\n"; diff --git a/admin/sync_languages.php b/admin/sync_languages.php new file mode 100755 index 0000000..b4c55ea --- /dev/null +++ b/admin/sync_languages.php @@ -0,0 +1,66 @@ + false, 'error' => 'Error fatal en el servidor: ' . $error['message'] . ' en ' . $error['file'] . ' línea ' . $error['line']]); + } +}); + +// Solo para administradores +if (!isset($_SESSION['role']) || $_SESSION['role'] !== 'admin') { + echo json_encode(['success' => false, 'error' => 'Acceso denegado.']); + exit; +} + +try { + // 1. Verificar que la URL de LibreTranslate esté configurada + if (empty($_ENV['LIBRETRANSLATE_URL'])) { + throw new Exception("La variable de entorno LIBRETRANSLATE_URL no está configurada en tu archivo .env"); + } + + $translator = new Translate(); + $libreLanguages = $translator->getSupportedLanguages(); + + if ($libreLanguages === null) { + throw new Exception("No se pudo obtener la lista de idiomas de LibreTranslate. Revisa que la URL ('" . htmlspecialchars($_ENV['LIBRETRANSLATE_URL']) . "') sea correcta y que el servicio esté funcionando."); + } + + if (empty($libreLanguages)) { + throw new Exception("LibreTranslate devolvió una lista de idiomas vacía."); + } + + $newLanguagesCount = 0; + $sql = "INSERT IGNORE INTO supported_languages (language_code, language_name, is_active) VALUES (?, ?, 0)"; + $stmt = $pdo->prepare($sql); + + foreach ($libreLanguages as $lang) { + if (isset($lang['code']) && isset($lang['name'])) { + $stmt->execute([$lang['code'], $lang['name']]); + if ($stmt->rowCount() > 0) { + $newLanguagesCount++; + } + } + } + + echo json_encode(['success' => true, 'new_languages' => $newLanguagesCount]); + +} catch (Throwable $e) { // Captura Throwable para errores y excepciones + error_log("Error en sync_languages.php: " . $e->getMessage()); + echo json_encode(['success' => false, 'error' => $e->getMessage()]); +} +?> \ No newline at end of file diff --git a/admin/test_discord_connection.php b/admin/test_discord_connection.php new file mode 100755 index 0000000..c5ce8e0 --- /dev/null +++ b/admin/test_discord_connection.php @@ -0,0 +1,408 @@ + [ + "Authorization: Bot " . DISCORD_BOT_TOKEN, + "Content-Type: application/json" + ], + CURLOPT_RETURNTRANSFER => true + ]); + + $response = curl_exec($ch); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + + if ($httpCode === 200) { + $guild = json_decode($response, true); + + $ch = curl_init("https://discord.com/api/v10/users/@me"); + curl_setopt_array($ch, [ + CURLOPT_HTTPHEADER => ["Authorization: Bot " . DISCORD_BOT_TOKEN], + CURLOPT_RETURNTRANSFER => true + ]); + + $botInfo = json_decode(curl_exec($ch), true); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + + if ($httpCode !== 200 || !isset($botInfo['id'])) { + throw new Exception("No se pudo obtener la información del bot de Discord. Verifica que el token sea correcto. Código HTTP: $httpCode"); + } + + $botId = $botInfo['id']; + + $ch = curl_init("https://discord.com/api/v10/guilds/{$guildId}/roles"); + curl_setopt_array($ch, [ + CURLOPT_HTTPHEADER => ["Authorization: Bot " . DISCORD_BOT_TOKEN], + CURLOPT_RETURNTRANSFER => true + ]); + + $roles = json_decode(curl_exec($ch), true); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + + if ($httpCode === 200 && is_array($roles)) { + $ch = curl_init("https://discord.com/api/v10/guilds/{$guildId}/members/{$botId}"); + curl_setopt_array($ch, [ + CURLOPT_HTTPHEADER => ["Authorization: Bot " . DISCORD_BOT_TOKEN], + CURLOPT_RETURNTRANSFER => true + ]); + + $member = json_decode(curl_exec($ch), true); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + + if ($httpCode === 404) { + throw new Exception("El bot no está en el servidor de Discord especificado."); + } elseif ($httpCode !== 200) { + throw new Exception("Error al obtener información del bot en el servidor. Código HTTP: $httpCode"); + } + + if (isset($member['roles']) && is_array($member['roles'])) { + $botRoles = array_filter($roles, fn($role) => in_array($role['id'], $member['roles'])); + $permissions = 0; + foreach ($botRoles as $role) { + $permissions |= intval($role['permissions']); + } + + $permissionsInfo = [ + 'guild_name' => $guild['name'] ?? 'Desconocido', + 'bot_has_admin' => ($permissions & 0x8) === 0x8, + 'can_kick' => ($permissions & 0x2) === 0x2, + 'can_ban' => ($permissions & 0x4) === 0x4, + 'permissions_int' => $permissions, + 'permissions_bin' => decbin($permissions), + 'roles' => array_column($botRoles, 'name') + ]; + + $success = "Permisos de Discord verificados para el servidor: " . htmlspecialchars($permissionsInfo['guild_name']); + } else { + $error = "No se pudo obtener la información de roles del bot en el servidor de Discord."; + } + } else { + $error = "No se pudieron obtener los roles del servidor de Discord. Código HTTP: $httpCode"; + } + } else { + $error = "Error al obtener información del servidor de Discord. Código HTTP: $httpCode"; + } + } catch (Exception $e) { + $error = "Error al verificar permisos de Discord: " . $e->getMessage(); + } + } + // Verificar si es una solicitud de verificación de webhook de Telegram + elseif (isset($_POST['check_telegram_webhook'])) { + try { + if (!defined('TELEGRAM_BOT_TOKEN') || empty(TELEGRAM_BOT_TOKEN)) { + throw new Exception("La constante TELEGRAM_BOT_TOKEN no está definida o está vacía."); + } + + $botToken = TELEGRAM_BOT_TOKEN; + $apiUrl = "https://api.telegram.org/bot{$botToken}/getWebhookInfo"; + + $ch = curl_init($apiUrl); + curl_setopt_array($ch, [ + CURLOPT_RETURNTRANSFER => true, + CURLOPT_CONNECTTIMEOUT => 10, // Segundos para esperar la conexión + CURLOPT_TIMEOUT => 20, // Segundos para la ejecución total de cURL + ]); + $response = curl_exec($ch); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + + if ($response === false) { + throw new Exception('Error en cURL al contactar la API de Telegram: ' . curl_error($ch)); + } + + if ($httpCode !== 200) { + throw new Exception("La API de Telegram devolvió un código HTTP {$httpCode}. Respuesta: " . $response); + } + + $result = json_decode($response, true); + + if (!$result['ok']) { + throw new Exception("Error de la API de Telegram: " . ($result['description'] ?? 'Error desconocido')); + } + + $telegramWebhookInfo = $result['result']; + $success = "Información del webhook de Telegram obtenida correctamente."; + + } catch (Exception $e) { + $error = "Error al verificar el webhook de Telegram: " . $e->getMessage(); + } + } + // Manejar la eliminación del webhook de Telegram + elseif (isset($_POST['delete_telegram_webhook'])) { + try { + if (!defined('TELEGRAM_BOT_TOKEN') || empty(TELEGRAM_BOT_TOKEN)) { + throw new Exception("La constante TELEGRAM_BOT_TOKEN no está definida o está vacía."); + } + $botToken = TELEGRAM_BOT_TOKEN; + $apiUrl = "https://api.telegram.org/bot{$botToken}/deleteWebhook"; + + $ch = curl_init($apiUrl); + curl_setopt_array($ch, [CURLOPT_RETURNTRANSFER => true]); + $response = curl_exec($ch); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + $result = json_decode($response, true); + + if ($httpCode === 200 && $result['ok']) { + $success = "Webhook de Telegram eliminado correctamente."; + } else { + throw new Exception("Error al eliminar el webhook: " . ($result['description'] ?? 'Respuesta inválida de la API.')); + } + } catch (Exception $e) { + $error = "Error al eliminar el webhook de Telegram: " . $e->getMessage(); + } + } + // Manejar la configuración del webhook de Telegram + elseif (isset($_POST['set_telegram_webhook'])) { + try { + // Las constantes son definidas en config.php + if (!defined('TELEGRAM_BOT_TOKEN') || !defined('BOT_BASE_URL') || !defined('TELEGRAM_WEBHOOK_TOKEN')) { + throw new Exception("Una o más constantes requeridas (TELEGRAM_BOT_TOKEN, BOT_BASE_URL, TELEGRAM_WEBHOOK_TOKEN) no están definidas. Revisa tu archivo .env y la configuración."); + } + + $botToken = TELEGRAM_BOT_TOKEN; + $webhookUrl = rtrim(BOT_BASE_URL, '/') . '/telegram/webhook/telegram_bot_webhook.php?auth_token=' . TELEGRAM_WEBHOOK_TOKEN; + $apiUrl = "https://api.telegram.org/bot{$botToken}/setWebhook?url=" . urlencode($webhookUrl); + + $ch = curl_init($apiUrl); + curl_setopt_array($ch, [CURLOPT_RETURNTRANSFER => true]); + $response = curl_exec($ch); + $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE); + $result = json_decode($response, true); + + if ($httpCode === 200 && $result['ok']) { + $success = "Webhook de Telegram configurado correctamente en: " . htmlspecialchars($webhookUrl); + } else { + throw new Exception("Error al configurar el webhook: " . ($result['description'] ?? 'Respuesta inválida de la API.')); + } + } catch (Exception $e) { + $error = "Error al configurar el webhook de Telegram: " . $e->getMessage(); + } + } + // Si es un envío de mensaje de prueba de Discord + elseif (isset($_POST['discord_id']) && !empty($_POST['test_content'])) { + $recipientId = trim($_POST['discord_id']); + $testContent = trim($_POST['test_content']); + $testRecipientType = $_POST['test_recipient_type'] ?? 'channel'; + + try { + $logDir = __DIR__ . '/../logs'; + if (!is_dir($logDir)) mkdir($logDir, 0755, true); + error_log("Test Discord: ID={$recipientId}, Type={$testRecipientType}, Token=" . substr(DISCORD_BOT_TOKEN, 0, 8) . "...", 3, $logDir . '/discord_api.log'); + + $discordSender = new DiscordSender(DISCORD_BOT_TOKEN); + $discordResponse = $discordSender->sendMessage($recipientId, $testContent, $testRecipientType); + $success = "Mensaje de prueba de Discord enviado con éxito."; + } catch (Exception $e) { + $error = "Error al enviar mensaje de prueba de Discord: " . $e->getMessage(); + } + } else { + $error = "Por favor, completa todos los campos requeridos."; + } +} + +// Incluir el encabezado que contiene el menú lateral +require_once __DIR__ . '/../templates/header.php'; +?> + + +
+
+

Probar Conexiones de Bots

+ + +
+ + + +
+ + +
+
+
Enviar Mensaje de Prueba a Discord
+
+
+
+
+ + +
+
+ +
+ > + + + > + +
+
+
+ + +
+ +
+
+
+ + +
+
Respuesta de la API de Discord
+
+
+ + +
+
Verificar Permisos del Bot de Discord
+
+
+ +
+ + +
+ +
+ + +
+
Resultado de la verificación de Discord:
+
    +
  • Servidor:
  • +
  • Es Administrador: + + + +
  • +
+
+ +
+
+ +
+
Verificar Estado del Webhook de Telegram
+
+

Obtén el estado actual de tu webhook directamente desde la API de Telegram para diagnosticar problemas de conexión.

+
+ + +
+ + +
+
Resultado de la verificación de Telegram:
+ +
+ No hay webhook configurado. El bot está funcionando en modo 'getUpdates'. +
+ +
    +
  • URL:
  • +
  • Actualizaciones pendientes: + + + +
  • + +
  • + Último error: +
    + Mensaje: +
  • + +
  • Último error: Ninguno reportado.
  • + +
  • Máx. Conexiones:
  • +
  • Actualizaciones permitidas: + 0): ?> + + + Todos los tipos (por defecto). + +
  • +
+ +
+ +
+
+ +
+
Gestionar Webhook de Telegram
+
+

Usa estos botones para eliminar o re-configurar el webhook de Telegram. Esto es útil para forzar a Telegram a actualizar la dirección IP de tu servidor si ha cambiado (por ejemplo, con DuckDNS).

+
+ + +
+
+ + +
+
+
+ +
+
+ + + + + + diff --git a/admin/update_language_flag.php b/admin/update_language_flag.php new file mode 100755 index 0000000..3a9c0fd --- /dev/null +++ b/admin/update_language_flag.php @@ -0,0 +1,42 @@ + false, 'error' => 'Acceso denegado.']); + exit; +} + +// Verificar que la solicitud sea AJAX y POST +if (strtolower($_SERVER['HTTP_X_REQUESTED_WITH'] ?? '') !== 'xmlhttprequest' || $_SERVER['REQUEST_METHOD'] !== 'POST') { + echo json_encode(['success' => false, 'error' => 'Solicitud no válida.']); + exit; +} + +$data = json_decode(file_get_contents('php://input'), true); + +$langId = $data['id'] ?? null; +$flagEmoji = $data['flag_emoji'] ?? ''; + +if ($langId === null) { + echo json_encode(['success' => false, 'error' => 'ID de idioma no proporcionado.']); + exit; +} + +try { + $stmt = $pdo->prepare("UPDATE supported_languages SET flag_emoji = ? WHERE id = ?"); + $stmt->execute([$flagEmoji, $langId]); + + echo json_encode(['success' => true]); + +} catch (PDOException $e) { + error_log("Error en update_language_flag.php: " . $e->getMessage()); + echo json_encode(['success' => false, 'error' => 'Error en la base de datos.']); +} +?> diff --git a/admin/update_language_status.php b/admin/update_language_status.php new file mode 100755 index 0000000..c54b6f8 --- /dev/null +++ b/admin/update_language_status.php @@ -0,0 +1,49 @@ + false, 'error' => 'Solicitud no válida.']); + exit; +} + +// Solo para administradores +if (!isset($_SESSION['role']) || $_SESSION['role'] !== 'admin') { + echo json_encode(['success' => false, 'error' => 'Acceso denegado.']); + exit; +} + +// Obtener datos del cuerpo de la solicitud +$data = json_decode(file_get_contents('php://input'), true); + +$langId = $data['id'] ?? null; +$isActive = isset($data['is_active']) ? (int)$data['is_active'] : null; + +if ($langId === null || $isActive === null) { + echo json_encode(['success' => false, 'error' => 'Datos incompletos.']); + exit; +} + +try { + $stmt = $pdo->prepare("UPDATE supported_languages SET is_active = ? WHERE id = ?"); + $stmt->execute([$isActive, $langId]); + + if ($stmt->rowCount() > 0) { + echo json_encode(['success' => true]); + } else { + // No se actualizó ninguna fila, podría ser que el ID no exista + echo json_encode(['success' => false, 'error' => 'El idioma no fue encontrado o el estado ya era el mismo.']); + } + +} catch (PDOException $e) { + // Loguear el error real en el servidor + error_log("Error en update_language_status.php: " . $e->getMessage()); + echo json_encode(['success' => false, 'error' => 'Error en la base de datos.']); +} +?> diff --git a/admin/users.php b/admin/users.php new file mode 100755 index 0000000..1de9f04 --- /dev/null +++ b/admin/users.php @@ -0,0 +1,201 @@ +prepare("SELECT id, username, role, telegram_chat_id FROM users WHERE id = ?"); + $stmt->execute([$edit_id]); + $user_to_edit = $stmt->fetch(PDO::FETCH_ASSOC); + + if ($user_to_edit) { + $edit_mode = true; + $edit_username = $user_to_edit['username']; + $edit_role = $user_to_edit['role']; + $edit_telegram_chat_id = $user_to_edit['telegram_chat_id']; + } else { + $error = "Usuario no encontrado."; + } +} + +// Handle POST actions +if ($_SERVER['REQUEST_METHOD'] === 'POST') { + // Action: Create or Update User + if (isset($_POST['save_user'])) { + $username = $_POST['username']; + $role = $_POST['role']; + $telegram_chat_id = trim($_POST['telegram_chat_id']); + $is_edit = isset($_POST['edit_id']); + + if (empty($username) || empty($role)) { + $error = "El nombre de usuario y el rol son obligatorios."; + } elseif (!empty($telegram_chat_id) && !is_numeric($telegram_chat_id)) { + $error = "El ID de Chat de Telegram debe ser un número."; + } else { + $chat_id_to_save = empty($telegram_chat_id) ? null : $telegram_chat_id; + try { + if ($is_edit) { + $edit_id = $_POST['edit_id']; + $details = 'Admin ' . $_SESSION['username'] . ' updated user: ' . $username . ' (ID: ' . $edit_id . ').'; + + if (!empty($_POST['password'])) { + $hashedPassword = password_hash($_POST['password'], PASSWORD_DEFAULT); + $stmt = $pdo->prepare("UPDATE users SET username = ?, password = ?, role = ?, telegram_chat_id = ? WHERE id = ?"); + $stmt->execute([$username, $hashedPassword, $role, $chat_id_to_save, $edit_id]); + $details .= ' Password was changed.'; + } else { + $stmt = $pdo->prepare("UPDATE users SET username = ?, role = ?, telegram_chat_id = ? WHERE id = ?"); + $stmt->execute([$username, $role, $chat_id_to_save, $edit_id]); + } + log_activity($_SESSION['user_id'], 'User Updated', $details); + header('Location: users.php?success=updated'); + exit(); + } else { + if (empty($_POST['password'])) { + $error = "La contraseña es obligatoria para nuevos usuarios."; + } else { + $hashedPassword = password_hash($_POST['password'], PASSWORD_DEFAULT); + $stmt = $pdo->prepare("INSERT INTO users (username, password, role, telegram_chat_id) VALUES (?, ?, ?, ?)"); + $stmt->execute([$username, $hashedPassword, $role, $chat_id_to_save]); + $new_user_id = $pdo->lastInsertId(); + log_activity($_SESSION['user_id'], 'User Created', 'Admin ' . $_SESSION['username'] . ' created new user: ' . $username . ' (ID: ' . $new_user_id . ')'); + header('Location: users.php?success=created'); + exit(); + } + } + } catch (PDOException $e) { + $error = ($e->errorInfo[1] == 1062) ? "El nombre de usuario ya existe." : "Error al guardar el usuario: " . $e->getMessage(); + if ($is_edit) { + $edit_mode = true; + $edit_id = $_POST['edit_id']; + $edit_username = $username; + $edit_role = $role; + $edit_telegram_chat_id = $telegram_chat_id; + } + } + } + } + // ... (Otras acciones POST como eliminar, etc. se mantienen aquí) +} + +// Fetch all users to display +$users = $pdo->query("SELECT id, username, role, created_at, telegram_chat_id FROM users ORDER BY username ASC")->fetchAll(PDO::FETCH_ASSOC); + +require_once __DIR__ . '/../templates/header.php'; +?> + +
+

Administrar Usuarios

+ +
+ + + +
+
+
+
+
+
+ + + +
+
+ + +
+
+ + > +
+
+ + +
+
+ + +
+
+ + + Cancelar + +
+
+
+
+
+ + +
+
Lista de Usuarios
+
+
+ + + + + + + + + + + + + + + + + + + + + + + +
IDUsuarioRolID Chat TelegramCreado enAcciones
+ + + + No vinculado + + + + + + +
+
+
+
+
+ + + diff --git a/admin_send_message.php b/admin_send_message.php new file mode 100755 index 0000000..af6ee19 --- /dev/null +++ b/admin_send_message.php @@ -0,0 +1,52 @@ + false, 'error' => 'Acceso denegado.']); + exit; +} + +$chatId = $_POST['chat_id'] ?? null; +$message = $_POST['message'] ?? null; + +if (!$chatId || !$message) { + http_response_code(400); + echo json_encode(['success' => false, 'error' => 'Faltan parámetros: chat_id y message son requeridos.']); + exit; +} + +try { + $telegram = new TelegramSender($_ENV['TELEGRAM_BOT_TOKEN'], $pdo); + + // Se envía el mensaje. La clase TelegramSender se encargará de: + // 1. Formatear el texto si es necesario. + // 2. Añadir el botón de traducción (true). + // 3. Registrar la interacción en la base de datos. + $result = $telegram->sendMessage( + $chatId, + htmlspecialchars($message), // Usamos htmlspecialchars para seguridad básica + ['parse_mode' => 'HTML'], + true, // Añadir botón de traducción + 'es' // El mensaje del admin se asume que es en español + ); + + if ($result) { + echo json_encode(['success' => true]); + } else { + // El error específico ya se loguea dentro de TelegramSender + http_response_code(500); + echo json_encode(['success' => false, 'error' => 'El servicio de Telegram no pudo enviar el mensaje.']); + } + +} catch (Exception $e) { + custom_log("Error fatal en admin_send_message.php: " . $e->getMessage()); + http_response_code(500); + echo json_encode(['success' => false, 'error' => 'Error interno del servidor al procesar la solicitud.']); +} diff --git a/assets/css/font/summernote.ttf b/assets/css/font/summernote.ttf new file mode 100755 index 0000000..b8266cd Binary files /dev/null and b/assets/css/font/summernote.ttf differ diff --git a/assets/css/font/summernote.woff b/assets/css/font/summernote.woff new file mode 100755 index 0000000..1c795a5 Binary files /dev/null and b/assets/css/font/summernote.woff differ diff --git a/assets/css/font/summernote.woff2 b/assets/css/font/summernote.woff2 new file mode 100755 index 0000000..d3a8164 Binary files /dev/null and b/assets/css/font/summernote.woff2 differ diff --git a/assets/css/style.css b/assets/css/style.css new file mode 100755 index 0000000..5be209f --- /dev/null +++ b/assets/css/style.css @@ -0,0 +1,162 @@ +/* General Styles */ +body { + overflow-x: hidden; +} + +/* Estilos para el chat */ +#chat-history { + height: 70vh; + overflow-y: auto; + padding: 1rem; + display: flex; + flex-direction: column; + gap: 0.75rem; +} + +.message { + max-width: 80%; + padding: 0.75rem 1rem; + border-radius: 1rem; + word-wrap: break-word; + position: relative; + line-height: 1.4; +} + +/* Mensajes entrantes */ +.message.in { + background-color: #f0f0f0; + color: #333; + align-self: flex-start; + border-bottom-left-radius: 0.25rem; +} + +/* Mensajes salientes */ +.message.out { + background-color: #007bff; + color: white; + align-self: flex-end; + border-bottom-right-radius: 0.25rem; +} + +/* Estilo para el nombre del remitente en grupos */ +.message-sender { + font-weight: bold; + font-size: 0.85rem; + margin-bottom: 0.25rem; +} + +/* Estilo para el texto del mensaje */ +.message-text { + word-wrap: break-word; +} + +/* Estilo para el contenedor del formulario de mensajes */ +#message-form-container { + padding: 1rem; + border-top: 1px solid #dee2e6; + background-color: #f8f9fa; +} + +/* Estilos para la lista de usuarios */ +.user-list { + max-height: 80vh; + overflow-y: auto; +} + +.user-list .list-group-item { + cursor: pointer; + transition: background-color 0.2s; +} + +.user-list .list-group-item:hover { + background-color: #f8f9fa; +} + +.user-list .list-group-item.active { + background-color: #007bff; + border-color: #007bff; +} + +#wrapper { + display: flex; + transition: all 0.3s ease; +} + +#sidebar-wrapper { + min-height: 100vh; + width: 250px; + margin-left: -250px; + transition: margin .25s ease-out; + position: fixed; /* Added for mobile responsiveness */ + z-index: 1000; /* Added for mobile responsiveness */ +} + +#wrapper.toggled #sidebar-wrapper { + margin-left: 0; +} + +#page-content-wrapper { + min-width: 100vw; + flex-grow: 1; /* Added for mobile responsiveness */ +} + +#wrapper.toggled #page-content-wrapper { + min-width: calc(100vw - 250px); +} + +.sidebar-heading { + padding: 0.875rem 1.25rem; + font-size: 1.2rem; +} + +@media (min-width: 768px) { + #sidebar-wrapper { + margin-left: 0; + position: relative; /* Changed for desktop */ + z-index: 1; /* Changed for desktop */ + } + + #page-content-wrapper { + min-width: 0; + width: 100%; + } + + #wrapper.toggled #sidebar-wrapper { + margin-left: -250px; + } +} + +/* Overlay for mobile when sidebar is open */ +.overlay { + position: fixed; + top: 0; + left: 0; + width: 100%; + height: 100%; + background: rgba(0, 0, 0, 0.5); + z-index: 999; + display: none; + opacity: 0; /* Initial opacity */ + transition: opacity 0.3s ease-in-out; /* Smooth transition */ +} + +.overlay.show { + display: block; + opacity: 1; /* Full opacity when shown */ +} + +/* Estilos para el logo en el sidebar */ +#sidebar-logo { + width: 40px; /* Tamaño fijo para el ancho */ + height: auto; /* Mantiene la proporción de aspecto */ + vertical-align: middle; /* Alinea verticalmente con el texto */ + margin-left: 8px; /* Espaciado a la izquierda del logo */ +} + +.sidebar-heading { + display: flex; + align-items: center; /* Centra verticalmente el texto y el logo */ + padding: 0.875rem 1.25rem; + font-size: 1.2rem; + white-space: nowrap; /* Evita que el texto se rompa en varias líneas */ +} \ No newline at end of file diff --git a/assets/css/summernote-bs5.min.css b/assets/css/summernote-bs5.min.css new file mode 100755 index 0000000..4ed1593 --- /dev/null +++ b/assets/css/summernote-bs5.min.css @@ -0,0 +1 @@ +@font-face{font-display:auto;font-family:summernote;font-style:normal;font-weight:400;src:url(font/summernote.eot?#iefix) format("embedded-opentype"),url(font/summernote.woff2) format("woff2"),url(font/summernote.woff) format("woff"),url(font/summernote.ttf) format("truetype")}[class*=" note-icon"]:before,[class^=note-icon]:before{display:inline-block;font-family:summernote;font-size:inherit;font-style:normal;text-decoration:inherit;text-rendering:auto;text-transform:none;vertical-align:middle;-moz-osx-font-smoothing:grayscale;-webkit-font-smoothing:antialiased;speak:none}.note-icon-fw{text-align:center;width:1.25em}.note-icon-border{border:.08em solid #eee;border-radius:.1em;padding:.2em .25em .15em}.note-icon-pull-left{float:left}.note-icon-pull-right{float:right}.note-icon.note-icon-pull-left{margin-right:.3em}.note-icon.note-icon-pull-right{margin-left:.3em}.note-icon-align:before{content:"\ea01"}.note-icon-align-center:before{content:"\ea02"}.note-icon-align-indent:before{content:"\ea03"}.note-icon-align-justify:before{content:"\ea04"}.note-icon-align-left:before{content:"\ea05"}.note-icon-align-outdent:before{content:"\ea06"}.note-icon-align-right:before{content:"\ea07"}.note-icon-arrow-circle-down:before{content:"\ea08"}.note-icon-arrow-circle-left:before{content:"\ea09"}.note-icon-arrow-circle-right:before{content:"\ea0a"}.note-icon-arrow-circle-up:before{content:"\ea0b"}.note-icon-arrows-alt:before{content:"\ea0c"}.note-icon-arrows-h:before{content:"\ea0d"}.note-icon-arrows-v:before{content:"\ea0e"}.note-icon-bold:before{content:"\ea0f"}.note-icon-caret:before{content:"\ea10"}.note-icon-chain-broken:before{content:"\ea11"}.note-icon-circle:before{content:"\ea12"}.note-icon-close:before{content:"\ea13"}.note-icon-code:before{content:"\ea14"}.note-icon-col-after:before{content:"\ea15"}.note-icon-col-before:before{content:"\ea16"}.note-icon-col-remove:before{content:"\ea17"}.note-icon-eraser:before{content:"\ea18"}.note-icon-float-left:before{content:"\ea19"}.note-icon-float-none:before{content:"\ea1a"}.note-icon-float-right:before{content:"\ea1b"}.note-icon-font:before{content:"\ea1c"}.note-icon-frame:before{content:"\ea1d"}.note-icon-italic:before{content:"\ea1e"}.note-icon-link:before{content:"\ea1f"}.note-icon-magic:before{content:"\ea20"}.note-icon-menu-check:before{content:"\ea21"}.note-icon-minus:before{content:"\ea22"}.note-icon-orderedlist:before{content:"\ea23"}.note-icon-pencil:before{content:"\ea24"}.note-icon-picture:before{content:"\ea25"}.note-icon-question:before{content:"\ea26"}.note-icon-redo:before{content:"\ea27"}.note-icon-rollback:before{content:"\ea28"}.note-icon-row-above:before{content:"\ea29"}.note-icon-row-below:before{content:"\ea2a"}.note-icon-row-remove:before{content:"\ea2b"}.note-icon-special-character:before{content:"\ea2c"}.note-icon-square:before{content:"\ea2d"}.note-icon-strikethrough:before{content:"\ea2e"}.note-icon-subscript:before{content:"\ea2f"}.note-icon-summernote:before{content:"\ea30"}.note-icon-superscript:before{content:"\ea31"}.note-icon-table:before{content:"\ea32"}.note-icon-text-height:before{content:"\ea33"}.note-icon-trash:before{content:"\ea34"}.note-icon-underline:before{content:"\ea35"}.note-icon-undo:before{content:"\ea36"}.note-icon-unorderedlist:before{content:"\ea37"}.note-icon-video:before{content:"\ea38"}.note-editor{position:relative}.note-editor .note-dropzone{background-color:#fff;color:#87cefa;display:none;opacity:.95;position:absolute;z-index:100}.note-editor .note-dropzone .note-dropzone-message{display:table-cell;font-size:28px;font-weight:700;text-align:center;vertical-align:middle}.note-editor .note-dropzone.hover{color:#098ddf}.note-editor.dragover .note-dropzone{display:table}.note-editor .note-editing-area{position:relative}.note-editor .note-editing-area .note-editable{outline:none}.note-editor .note-editing-area .note-editable sup{vertical-align:super}.note-editor .note-editing-area .note-editable sub{vertical-align:sub}.note-editor .note-editing-area .note-editable img.note-float-left{margin-right:10px}.note-editor .note-editing-area .note-editable img.note-float-right{margin-left:10px}.note-editor.note-airframe,.note-editor.note-frame{border:1px solid rgba(0,0,0,.196)}.note-editor.note-airframe.codeview .note-editing-area .note-editable,.note-editor.note-frame.codeview .note-editing-area .note-editable{display:none}.note-editor.note-airframe.codeview .note-editing-area .note-codable,.note-editor.note-frame.codeview .note-editing-area .note-codable{display:block}.note-editor.note-airframe .note-editing-area,.note-editor.note-frame .note-editing-area{overflow:hidden}.note-editor.note-airframe .note-editing-area .note-editable,.note-editor.note-frame .note-editing-area .note-editable{overflow:auto;padding:10px;word-wrap:break-word}.note-editor.note-airframe .note-editing-area .note-editable[contenteditable=false],.note-editor.note-frame .note-editing-area .note-editable[contenteditable=false]{background-color:hsla(0,0%,50%,.114)}.note-editor.note-airframe .note-editing-area .note-codable,.note-editor.note-frame .note-editing-area .note-codable{background-color:#222;border:none;border-radius:0;box-shadow:none;-ms-box-sizing:border-box;box-sizing:border-box;color:#ccc;display:none;font-family:Menlo,Monaco,monospace,sans-serif;font-size:14px;margin-bottom:0;outline:none;padding:10px;resize:none;width:100%}.note-editor.note-airframe.fullscreen,.note-editor.note-frame.fullscreen{left:0;position:fixed;top:0;width:100%!important;z-index:1050}.note-editor.note-airframe.fullscreen .note-resizebar,.note-editor.note-frame.fullscreen .note-resizebar{display:none}.note-editor.note-airframe .note-status-output,.note-editor.note-frame .note-status-output{border:0;border-top:1px solid #e2e2e2;color:#000;display:block;font-size:14px;height:20px;line-height:1.42857143;margin-bottom:0;width:100%}.note-editor.note-airframe .note-status-output:empty,.note-editor.note-frame .note-status-output:empty{border-top:0 solid transparent;height:0}.note-editor.note-airframe .note-status-output .pull-right,.note-editor.note-frame .note-status-output .pull-right{float:right!important}.note-editor.note-airframe .note-status-output .text-muted,.note-editor.note-frame .note-status-output .text-muted{color:#777}.note-editor.note-airframe .note-status-output .text-primary,.note-editor.note-frame .note-status-output .text-primary{color:#286090}.note-editor.note-airframe .note-status-output .text-success,.note-editor.note-frame .note-status-output .text-success{color:#3c763d}.note-editor.note-airframe .note-status-output .text-info,.note-editor.note-frame .note-status-output .text-info{color:#31708f}.note-editor.note-airframe .note-status-output .text-warning,.note-editor.note-frame .note-status-output .text-warning{color:#8a6d3b}.note-editor.note-airframe .note-status-output .text-danger,.note-editor.note-frame .note-status-output .text-danger{color:#a94442}.note-editor.note-airframe .note-status-output .alert,.note-editor.note-frame .note-status-output .alert{background-color:#f5f5f5;border-radius:0;color:#000;margin:-7px 0 0;padding:7px 10px 2px}.note-editor.note-airframe .note-status-output .alert .note-icon,.note-editor.note-frame .note-status-output .alert .note-icon{margin-right:5px}.note-editor.note-airframe .note-status-output .alert-success,.note-editor.note-frame .note-status-output .alert-success{background-color:#dff0d8!important;color:#3c763d!important}.note-editor.note-airframe .note-status-output .alert-info,.note-editor.note-frame .note-status-output .alert-info{background-color:#d9edf7!important;color:#31708f!important}.note-editor.note-airframe .note-status-output .alert-warning,.note-editor.note-frame .note-status-output .alert-warning{background-color:#fcf8e3!important;color:#8a6d3b!important}.note-editor.note-airframe .note-status-output .alert-danger,.note-editor.note-frame .note-status-output .alert-danger{background-color:#f2dede!important;color:#a94442!important}.note-editor.note-airframe .note-statusbar,.note-editor.note-frame .note-statusbar{background-color:hsla(0,0%,50%,.114);border-bottom-left-radius:4px;border-bottom-right-radius:4px;border-top:1px solid rgba(0,0,0,.196)}.note-editor.note-airframe .note-statusbar .note-resizebar,.note-editor.note-frame .note-statusbar .note-resizebar{cursor:ns-resize;height:9px;padding-top:1px;width:100%}.note-editor.note-airframe .note-statusbar .note-resizebar .note-icon-bar,.note-editor.note-frame .note-statusbar .note-resizebar .note-icon-bar{border-top:1px solid rgba(0,0,0,.196);margin:1px auto;width:20px}.note-editor.note-airframe .note-statusbar.locked .note-resizebar,.note-editor.note-frame .note-statusbar.locked .note-resizebar{cursor:default}.note-editor.note-airframe .note-statusbar.locked .note-resizebar .note-icon-bar,.note-editor.note-frame .note-statusbar.locked .note-resizebar .note-icon-bar{display:none}.note-editor.note-airframe .note-placeholder,.note-editor.note-frame .note-placeholder{padding:10px}.note-editor.note-airframe{border:0}.note-editor.note-airframe .note-editing-area .note-editable{padding:0}.note-popover.popover{display:none;max-width:none}.note-popover.popover .popover-content a{display:inline-block;max-width:200px;overflow:hidden;text-overflow:ellipsis;vertical-align:middle;white-space:nowrap}.note-popover.popover .arrow{left:20px!important}.note-toolbar{position:relative}.note-editor .note-toolbar,.note-popover .popover-content{margin:0;padding:0 0 5px 5px}.note-editor .note-toolbar>.note-btn-group,.note-popover .popover-content>.note-btn-group{margin-left:0;margin-right:5px;margin-top:5px}.note-editor .note-toolbar .note-btn-group .note-table,.note-popover .popover-content .note-btn-group .note-table{min-width:0;padding:5px}.note-editor .note-toolbar .note-btn-group .note-table .note-dimension-picker,.note-popover .popover-content .note-btn-group .note-table .note-dimension-picker{font-size:18px}.note-editor .note-toolbar .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-mousecatcher,.note-popover .popover-content .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-mousecatcher{cursor:pointer;height:10em;position:absolute!important;width:10em;z-index:3}.note-editor .note-toolbar .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-unhighlighted,.note-popover .popover-content .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-unhighlighted{background:url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABIAAAASAgMAAAAroGbEAAAACVBMVEUAAIj4+Pjp6ekKlAqjAAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfYAR0BKhmnaJzPAAAAG0lEQVQI12NgAAOtVatWMTCohoaGUY+EmIkEAEruEzK2J7tvAAAAAElFTkSuQmCC") repeat;height:5em;position:relative!important;width:5em;z-index:1}.note-editor .note-toolbar .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-highlighted,.note-popover .popover-content .note-btn-group .note-table .note-dimension-picker .note-dimension-picker-highlighted{background:url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAABIAAAASAgMAAAAroGbEAAAACVBMVEUAAIjd6vvD2f9LKLW+AAAAAXRSTlMAQObYZgAAAAFiS0dEAIgFHUgAAAAJcEhZcwAACxMAAAsTAQCanBgAAAAHdElNRQfYAR0BKwNDEVT0AAAAG0lEQVQI12NgAAOtVatWMTCohoaGUY+EmIkEAEruEzK2J7tvAAAAAElFTkSuQmCC") repeat;height:1em;position:absolute!important;width:1em;z-index:2}.note-editor .note-toolbar .note-style .dropdown-style blockquote,.note-editor .note-toolbar .note-style .dropdown-style pre,.note-popover .popover-content .note-style .dropdown-style blockquote,.note-popover .popover-content .note-style .dropdown-style pre{margin:0;padding:5px 10px}.note-editor .note-toolbar .note-style .dropdown-style h1,.note-editor .note-toolbar .note-style .dropdown-style h2,.note-editor .note-toolbar .note-style .dropdown-style h3,.note-editor .note-toolbar .note-style .dropdown-style h4,.note-editor .note-toolbar .note-style .dropdown-style h5,.note-editor .note-toolbar .note-style .dropdown-style h6,.note-editor .note-toolbar .note-style .dropdown-style p,.note-popover .popover-content .note-style .dropdown-style h1,.note-popover .popover-content .note-style .dropdown-style h2,.note-popover .popover-content .note-style .dropdown-style h3,.note-popover .popover-content .note-style .dropdown-style h4,.note-popover .popover-content .note-style .dropdown-style h5,.note-popover .popover-content .note-style .dropdown-style h6,.note-popover .popover-content .note-style .dropdown-style p{margin:0;padding:0}.note-editor .note-toolbar .note-color-all .note-dropdown-menu,.note-popover .popover-content .note-color-all .note-dropdown-menu{min-width:337px}.note-editor .note-toolbar .note-color .dropdown-toggle,.note-popover .popover-content .note-color .dropdown-toggle{padding-left:5px;width:20px}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette{display:inline-block;margin:0;width:160px}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette:first-child,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette:first-child{margin:0 5px}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-palette-title,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-palette-title{border-bottom:1px solid #eee;font-size:12px;margin:2px 7px;text-align:center}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-reset,.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-select,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-reset,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-select{border-radius:5px;cursor:pointer;font-size:11px;margin:3px;padding:0 3px;width:100%}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-reset:hover,.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-select:hover,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-reset:hover,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-select:hover{background:#eee}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-row,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-row{height:20px}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-color-select-btn,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-color-select-btn{display:none}.note-editor .note-toolbar .note-color .note-dropdown-menu .note-palette .note-holder-custom .note-color-btn,.note-popover .popover-content .note-color .note-dropdown-menu .note-palette .note-holder-custom .note-color-btn{border:1px solid #eee}.note-editor .note-toolbar .note-para .note-dropdown-menu,.note-popover .popover-content .note-para .note-dropdown-menu{min-width:228px;padding:5px}.note-editor .note-toolbar .note-para .note-dropdown-menu>div+div,.note-popover .popover-content .note-para .note-dropdown-menu>div+div{margin-left:5px}.note-editor .note-toolbar .note-dropdown-menu,.note-popover .popover-content .note-dropdown-menu{min-width:160px}.note-editor .note-toolbar .note-dropdown-menu.right,.note-popover .popover-content .note-dropdown-menu.right{left:auto;right:0}.note-editor .note-toolbar .note-dropdown-menu.right:before,.note-popover .popover-content .note-dropdown-menu.right:before{left:auto!important;right:9px}.note-editor .note-toolbar .note-dropdown-menu.right:after,.note-popover .popover-content .note-dropdown-menu.right:after{left:auto!important;right:10px}.note-editor .note-toolbar .note-dropdown-menu.note-check a i,.note-popover .popover-content .note-dropdown-menu.note-check a i{color:#00bfff;visibility:hidden}.note-editor .note-toolbar .note-dropdown-menu.note-check a.checked i,.note-popover .popover-content .note-dropdown-menu.note-check a.checked i{visibility:visible}.note-editor .note-toolbar .note-fontsize-10,.note-popover .popover-content .note-fontsize-10{font-size:10px}.note-editor .note-toolbar .note-color-palette,.note-popover .popover-content .note-color-palette{line-height:1}.note-editor .note-toolbar .note-color-palette div .note-color-btn,.note-popover .popover-content .note-color-palette div .note-color-btn{border:0;border-radius:0;height:20px;margin:0;padding:0;width:20px}.note-editor .note-toolbar .note-color-palette div .note-color-btn:hover,.note-popover .popover-content .note-color-palette div .note-color-btn:hover{transform:scale(1.2);transition:all .2s}.note-modal .modal-dialog{border-radius:5px;box-shadow:0 3px 9px rgba(0,0,0,.5);outline:0}.note-modal .form-group{margin-left:0;margin-right:0}.note-modal .note-modal-form{margin:0}.note-modal .note-image-dialog .note-dropzone{border:4px dashed #d3d3d3;color:#d3d3d3;font-size:30px;line-height:4;margin-bottom:10px;min-height:100px;text-align:center}@-moz-document url-prefix(){.note-modal .note-image-input{height:auto}}.note-placeholder{color:gray;display:none;position:absolute}.note-handle .note-control-selection{border:1px solid #000;display:none;position:absolute}.note-handle .note-control-selection>div{position:absolute}.note-handle .note-control-selection .note-control-selection-bg{background-color:#000;-ms-filter:progid:DXImageTransform.Microsoft.Alpha(opacity=30);filter:alpha(opacity=30);height:100%;-webkit-opacity:.3;-khtml-opacity:.3;-moz-opacity:.3;opacity:.3;width:100%}.note-handle .note-control-selection .note-control-handle,.note-handle .note-control-selection .note-control-holder,.note-handle .note-control-selection .note-control-sizing{border:1px solid #000;height:7px;width:7px}.note-handle .note-control-selection .note-control-sizing{background-color:#000}.note-handle .note-control-selection .note-control-nw{border-bottom:none;border-right:none;left:-5px;top:-5px}.note-handle .note-control-selection .note-control-ne{border-bottom:none;border-left:none;right:-5px;top:-5px}.note-handle .note-control-selection .note-control-sw{border-right:none;border-top:none;bottom:-5px;left:-5px}.note-handle .note-control-selection .note-control-se{bottom:-5px;cursor:se-resize;right:-5px}.note-handle .note-control-selection .note-control-se.note-control-holder{border-left:none;border-top:none;cursor:default}.note-handle .note-control-selection .note-control-selection-info{background-color:#000;border-radius:5px;bottom:0;color:#fff;-ms-filter:progid:DXImageTransform.Microsoft.Alpha(opacity=70);filter:alpha(opacity=70);font-size:12px;margin:5px;-webkit-opacity:.7;-khtml-opacity:.7;-moz-opacity:.7;opacity:.7;padding:5px;right:0}.note-hint-popover{min-width:100px;padding:2px}.note-hint-popover .popover-content{max-height:150px;overflow:auto;padding:3px}.note-hint-popover .popover-content .note-hint-group .note-hint-item{display:block!important;padding:3px}.note-hint-popover .popover-content .note-hint-group .note-hint-item.active,.note-hint-popover .popover-content .note-hint-group .note-hint-item:hover{background-color:#428bca;clear:both;color:#fff;cursor:pointer;display:block;font-weight:400;line-height:1.4;outline:0;text-decoration:none;white-space:nowrap}body .note-fullscreen-body,html .note-fullscreen-body{overflow:hidden!important}.note-editable ol li,.note-editable ul li{list-style-position:inside}.note-toolbar{background:hsla(0,0%,50%,.114)}.note-btn-group .note-btn{border-color:rgba(0,0,0,.196);font-size:13px;padding:.28rem .65rem} \ No newline at end of file diff --git a/assets/images/logo.png b/assets/images/logo.png new file mode 100755 index 0000000..c9d1011 Binary files /dev/null and b/assets/images/logo.png differ diff --git a/assets/js/jquery-3.6.0.min.js b/assets/js/jquery-3.6.0.min.js new file mode 100755 index 0000000..c4c6022 --- /dev/null +++ b/assets/js/jquery-3.6.0.min.js @@ -0,0 +1,2 @@ +/*! jQuery v3.6.0 | (c) OpenJS Foundation and other contributors | jquery.org/license */ +!function(e,t){"use strict";"object"==typeof module&&"object"==typeof module.exports?module.exports=e.document?t(e,!0):function(e){if(!e.document)throw new Error("jQuery requires a window with a document");return t(e)}:t(e)}("undefined"!=typeof window?window:this,function(C,e){"use strict";var t=[],r=Object.getPrototypeOf,s=t.slice,g=t.flat?function(e){return t.flat.call(e)}:function(e){return t.concat.apply([],e)},u=t.push,i=t.indexOf,n={},o=n.toString,v=n.hasOwnProperty,a=v.toString,l=a.call(Object),y={},m=function(e){return"function"==typeof e&&"number"!=typeof e.nodeType&&"function"!=typeof e.item},x=function(e){return null!=e&&e===e.window},E=C.document,c={type:!0,src:!0,nonce:!0,noModule:!0};function b(e,t,n){var r,i,o=(n=n||E).createElement("script");if(o.text=e,t)for(r in c)(i=t[r]||t.getAttribute&&t.getAttribute(r))&&o.setAttribute(r,i);n.head.appendChild(o).parentNode.removeChild(o)}function w(e){return null==e?e+"":"object"==typeof e||"function"==typeof e?n[o.call(e)]||"object":typeof e}var f="3.6.0",S=function(e,t){return new S.fn.init(e,t)};function p(e){var t=!!e&&"length"in e&&e.length,n=w(e);return!m(e)&&!x(e)&&("array"===n||0===t||"number"==typeof t&&0+~]|"+M+")"+M+"*"),U=new RegExp(M+"|>"),X=new RegExp(F),V=new RegExp("^"+I+"$"),G={ID:new RegExp("^#("+I+")"),CLASS:new RegExp("^\\.("+I+")"),TAG:new RegExp("^("+I+"|[*])"),ATTR:new RegExp("^"+W),PSEUDO:new RegExp("^"+F),CHILD:new RegExp("^:(only|first|last|nth|nth-last)-(child|of-type)(?:\\("+M+"*(even|odd|(([+-]|)(\\d*)n|)"+M+"*(?:([+-]|)"+M+"*(\\d+)|))"+M+"*\\)|)","i"),bool:new RegExp("^(?:"+R+")$","i"),needsContext:new RegExp("^"+M+"*[>+~]|:(even|odd|eq|gt|lt|nth|first|last)(?:\\("+M+"*((?:-\\d)?\\d*)"+M+"*\\)|)(?=[^-]|$)","i")},Y=/HTML$/i,Q=/^(?:input|select|textarea|button)$/i,J=/^h\d$/i,K=/^[^{]+\{\s*\[native \w/,Z=/^(?:#([\w-]+)|(\w+)|\.([\w-]+))$/,ee=/[+~]/,te=new RegExp("\\\\[\\da-fA-F]{1,6}"+M+"?|\\\\([^\\r\\n\\f])","g"),ne=function(e,t){var n="0x"+e.slice(1)-65536;return t||(n<0?String.fromCharCode(n+65536):String.fromCharCode(n>>10|55296,1023&n|56320))},re=/([\0-\x1f\x7f]|^-?\d)|^-$|[^\0-\x1f\x7f-\uFFFF\w-]/g,ie=function(e,t){return t?"\0"===e?"\ufffd":e.slice(0,-1)+"\\"+e.charCodeAt(e.length-1).toString(16)+" ":"\\"+e},oe=function(){T()},ae=be(function(e){return!0===e.disabled&&"fieldset"===e.nodeName.toLowerCase()},{dir:"parentNode",next:"legend"});try{H.apply(t=O.call(p.childNodes),p.childNodes),t[p.childNodes.length].nodeType}catch(e){H={apply:t.length?function(e,t){L.apply(e,O.call(t))}:function(e,t){var n=e.length,r=0;while(e[n++]=t[r++]);e.length=n-1}}}function se(t,e,n,r){var i,o,a,s,u,l,c,f=e&&e.ownerDocument,p=e?e.nodeType:9;if(n=n||[],"string"!=typeof t||!t||1!==p&&9!==p&&11!==p)return n;if(!r&&(T(e),e=e||C,E)){if(11!==p&&(u=Z.exec(t)))if(i=u[1]){if(9===p){if(!(a=e.getElementById(i)))return n;if(a.id===i)return n.push(a),n}else if(f&&(a=f.getElementById(i))&&y(e,a)&&a.id===i)return n.push(a),n}else{if(u[2])return H.apply(n,e.getElementsByTagName(t)),n;if((i=u[3])&&d.getElementsByClassName&&e.getElementsByClassName)return H.apply(n,e.getElementsByClassName(i)),n}if(d.qsa&&!N[t+" "]&&(!v||!v.test(t))&&(1!==p||"object"!==e.nodeName.toLowerCase())){if(c=t,f=e,1===p&&(U.test(t)||z.test(t))){(f=ee.test(t)&&ye(e.parentNode)||e)===e&&d.scope||((s=e.getAttribute("id"))?s=s.replace(re,ie):e.setAttribute("id",s=S)),o=(l=h(t)).length;while(o--)l[o]=(s?"#"+s:":scope")+" "+xe(l[o]);c=l.join(",")}try{return H.apply(n,f.querySelectorAll(c)),n}catch(e){N(t,!0)}finally{s===S&&e.removeAttribute("id")}}}return g(t.replace($,"$1"),e,n,r)}function ue(){var r=[];return function e(t,n){return r.push(t+" ")>b.cacheLength&&delete e[r.shift()],e[t+" "]=n}}function le(e){return e[S]=!0,e}function ce(e){var t=C.createElement("fieldset");try{return!!e(t)}catch(e){return!1}finally{t.parentNode&&t.parentNode.removeChild(t),t=null}}function fe(e,t){var n=e.split("|"),r=n.length;while(r--)b.attrHandle[n[r]]=t}function pe(e,t){var n=t&&e,r=n&&1===e.nodeType&&1===t.nodeType&&e.sourceIndex-t.sourceIndex;if(r)return r;if(n)while(n=n.nextSibling)if(n===t)return-1;return e?1:-1}function de(t){return function(e){return"input"===e.nodeName.toLowerCase()&&e.type===t}}function he(n){return function(e){var t=e.nodeName.toLowerCase();return("input"===t||"button"===t)&&e.type===n}}function ge(t){return function(e){return"form"in e?e.parentNode&&!1===e.disabled?"label"in e?"label"in e.parentNode?e.parentNode.disabled===t:e.disabled===t:e.isDisabled===t||e.isDisabled!==!t&&ae(e)===t:e.disabled===t:"label"in e&&e.disabled===t}}function ve(a){return le(function(o){return o=+o,le(function(e,t){var n,r=a([],e.length,o),i=r.length;while(i--)e[n=r[i]]&&(e[n]=!(t[n]=e[n]))})})}function ye(e){return e&&"undefined"!=typeof e.getElementsByTagName&&e}for(e in d=se.support={},i=se.isXML=function(e){var t=e&&e.namespaceURI,n=e&&(e.ownerDocument||e).documentElement;return!Y.test(t||n&&n.nodeName||"HTML")},T=se.setDocument=function(e){var t,n,r=e?e.ownerDocument||e:p;return r!=C&&9===r.nodeType&&r.documentElement&&(a=(C=r).documentElement,E=!i(C),p!=C&&(n=C.defaultView)&&n.top!==n&&(n.addEventListener?n.addEventListener("unload",oe,!1):n.attachEvent&&n.attachEvent("onunload",oe)),d.scope=ce(function(e){return a.appendChild(e).appendChild(C.createElement("div")),"undefined"!=typeof e.querySelectorAll&&!e.querySelectorAll(":scope fieldset div").length}),d.attributes=ce(function(e){return e.className="i",!e.getAttribute("className")}),d.getElementsByTagName=ce(function(e){return e.appendChild(C.createComment("")),!e.getElementsByTagName("*").length}),d.getElementsByClassName=K.test(C.getElementsByClassName),d.getById=ce(function(e){return a.appendChild(e).id=S,!C.getElementsByName||!C.getElementsByName(S).length}),d.getById?(b.filter.ID=function(e){var t=e.replace(te,ne);return function(e){return e.getAttribute("id")===t}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&E){var n=t.getElementById(e);return n?[n]:[]}}):(b.filter.ID=function(e){var n=e.replace(te,ne);return function(e){var t="undefined"!=typeof e.getAttributeNode&&e.getAttributeNode("id");return t&&t.value===n}},b.find.ID=function(e,t){if("undefined"!=typeof t.getElementById&&E){var n,r,i,o=t.getElementById(e);if(o){if((n=o.getAttributeNode("id"))&&n.value===e)return[o];i=t.getElementsByName(e),r=0;while(o=i[r++])if((n=o.getAttributeNode("id"))&&n.value===e)return[o]}return[]}}),b.find.TAG=d.getElementsByTagName?function(e,t){return"undefined"!=typeof t.getElementsByTagName?t.getElementsByTagName(e):d.qsa?t.querySelectorAll(e):void 0}:function(e,t){var n,r=[],i=0,o=t.getElementsByTagName(e);if("*"===e){while(n=o[i++])1===n.nodeType&&r.push(n);return r}return o},b.find.CLASS=d.getElementsByClassName&&function(e,t){if("undefined"!=typeof t.getElementsByClassName&&E)return t.getElementsByClassName(e)},s=[],v=[],(d.qsa=K.test(C.querySelectorAll))&&(ce(function(e){var t;a.appendChild(e).innerHTML="",e.querySelectorAll("[msallowcapture^='']").length&&v.push("[*^$]="+M+"*(?:''|\"\")"),e.querySelectorAll("[selected]").length||v.push("\\["+M+"*(?:value|"+R+")"),e.querySelectorAll("[id~="+S+"-]").length||v.push("~="),(t=C.createElement("input")).setAttribute("name",""),e.appendChild(t),e.querySelectorAll("[name='']").length||v.push("\\["+M+"*name"+M+"*="+M+"*(?:''|\"\")"),e.querySelectorAll(":checked").length||v.push(":checked"),e.querySelectorAll("a#"+S+"+*").length||v.push(".#.+[+~]"),e.querySelectorAll("\\\f"),v.push("[\\r\\n\\f]")}),ce(function(e){e.innerHTML="";var t=C.createElement("input");t.setAttribute("type","hidden"),e.appendChild(t).setAttribute("name","D"),e.querySelectorAll("[name=d]").length&&v.push("name"+M+"*[*^$|!~]?="),2!==e.querySelectorAll(":enabled").length&&v.push(":enabled",":disabled"),a.appendChild(e).disabled=!0,2!==e.querySelectorAll(":disabled").length&&v.push(":enabled",":disabled"),e.querySelectorAll("*,:x"),v.push(",.*:")})),(d.matchesSelector=K.test(c=a.matches||a.webkitMatchesSelector||a.mozMatchesSelector||a.oMatchesSelector||a.msMatchesSelector))&&ce(function(e){d.disconnectedMatch=c.call(e,"*"),c.call(e,"[s!='']:x"),s.push("!=",F)}),v=v.length&&new RegExp(v.join("|")),s=s.length&&new RegExp(s.join("|")),t=K.test(a.compareDocumentPosition),y=t||K.test(a.contains)?function(e,t){var n=9===e.nodeType?e.documentElement:e,r=t&&t.parentNode;return e===r||!(!r||1!==r.nodeType||!(n.contains?n.contains(r):e.compareDocumentPosition&&16&e.compareDocumentPosition(r)))}:function(e,t){if(t)while(t=t.parentNode)if(t===e)return!0;return!1},j=t?function(e,t){if(e===t)return l=!0,0;var n=!e.compareDocumentPosition-!t.compareDocumentPosition;return n||(1&(n=(e.ownerDocument||e)==(t.ownerDocument||t)?e.compareDocumentPosition(t):1)||!d.sortDetached&&t.compareDocumentPosition(e)===n?e==C||e.ownerDocument==p&&y(p,e)?-1:t==C||t.ownerDocument==p&&y(p,t)?1:u?P(u,e)-P(u,t):0:4&n?-1:1)}:function(e,t){if(e===t)return l=!0,0;var n,r=0,i=e.parentNode,o=t.parentNode,a=[e],s=[t];if(!i||!o)return e==C?-1:t==C?1:i?-1:o?1:u?P(u,e)-P(u,t):0;if(i===o)return pe(e,t);n=e;while(n=n.parentNode)a.unshift(n);n=t;while(n=n.parentNode)s.unshift(n);while(a[r]===s[r])r++;return r?pe(a[r],s[r]):a[r]==p?-1:s[r]==p?1:0}),C},se.matches=function(e,t){return se(e,null,null,t)},se.matchesSelector=function(e,t){if(T(e),d.matchesSelector&&E&&!N[t+" "]&&(!s||!s.test(t))&&(!v||!v.test(t)))try{var n=c.call(e,t);if(n||d.disconnectedMatch||e.document&&11!==e.document.nodeType)return n}catch(e){N(t,!0)}return 0":{dir:"parentNode",first:!0}," ":{dir:"parentNode"},"+":{dir:"previousSibling",first:!0},"~":{dir:"previousSibling"}},preFilter:{ATTR:function(e){return e[1]=e[1].replace(te,ne),e[3]=(e[3]||e[4]||e[5]||"").replace(te,ne),"~="===e[2]&&(e[3]=" "+e[3]+" "),e.slice(0,4)},CHILD:function(e){return e[1]=e[1].toLowerCase(),"nth"===e[1].slice(0,3)?(e[3]||se.error(e[0]),e[4]=+(e[4]?e[5]+(e[6]||1):2*("even"===e[3]||"odd"===e[3])),e[5]=+(e[7]+e[8]||"odd"===e[3])):e[3]&&se.error(e[0]),e},PSEUDO:function(e){var t,n=!e[6]&&e[2];return G.CHILD.test(e[0])?null:(e[3]?e[2]=e[4]||e[5]||"":n&&X.test(n)&&(t=h(n,!0))&&(t=n.indexOf(")",n.length-t)-n.length)&&(e[0]=e[0].slice(0,t),e[2]=n.slice(0,t)),e.slice(0,3))}},filter:{TAG:function(e){var t=e.replace(te,ne).toLowerCase();return"*"===e?function(){return!0}:function(e){return e.nodeName&&e.nodeName.toLowerCase()===t}},CLASS:function(e){var t=m[e+" "];return t||(t=new RegExp("(^|"+M+")"+e+"("+M+"|$)"))&&m(e,function(e){return t.test("string"==typeof e.className&&e.className||"undefined"!=typeof e.getAttribute&&e.getAttribute("class")||"")})},ATTR:function(n,r,i){return function(e){var t=se.attr(e,n);return null==t?"!="===r:!r||(t+="","="===r?t===i:"!="===r?t!==i:"^="===r?i&&0===t.indexOf(i):"*="===r?i&&-1:\x20\t\r\n\f]*)[\x20\t\r\n\f]*\/?>(?:<\/\1>|)$/i;function j(e,n,r){return m(n)?S.grep(e,function(e,t){return!!n.call(e,t,e)!==r}):n.nodeType?S.grep(e,function(e){return e===n!==r}):"string"!=typeof n?S.grep(e,function(e){return-1)[^>]*|#([\w-]+))$/;(S.fn.init=function(e,t,n){var r,i;if(!e)return this;if(n=n||D,"string"==typeof e){if(!(r="<"===e[0]&&">"===e[e.length-1]&&3<=e.length?[null,e,null]:q.exec(e))||!r[1]&&t)return!t||t.jquery?(t||n).find(e):this.constructor(t).find(e);if(r[1]){if(t=t instanceof S?t[0]:t,S.merge(this,S.parseHTML(r[1],t&&t.nodeType?t.ownerDocument||t:E,!0)),N.test(r[1])&&S.isPlainObject(t))for(r in t)m(this[r])?this[r](t[r]):this.attr(r,t[r]);return this}return(i=E.getElementById(r[2]))&&(this[0]=i,this.length=1),this}return e.nodeType?(this[0]=e,this.length=1,this):m(e)?void 0!==n.ready?n.ready(e):e(S):S.makeArray(e,this)}).prototype=S.fn,D=S(E);var L=/^(?:parents|prev(?:Until|All))/,H={children:!0,contents:!0,next:!0,prev:!0};function O(e,t){while((e=e[t])&&1!==e.nodeType);return e}S.fn.extend({has:function(e){var t=S(e,this),n=t.length;return this.filter(function(){for(var e=0;e\x20\t\r\n\f]*)/i,he=/^$|^module$|\/(?:java|ecma)script/i;ce=E.createDocumentFragment().appendChild(E.createElement("div")),(fe=E.createElement("input")).setAttribute("type","radio"),fe.setAttribute("checked","checked"),fe.setAttribute("name","t"),ce.appendChild(fe),y.checkClone=ce.cloneNode(!0).cloneNode(!0).lastChild.checked,ce.innerHTML="",y.noCloneChecked=!!ce.cloneNode(!0).lastChild.defaultValue,ce.innerHTML="",y.option=!!ce.lastChild;var ge={thead:[1,"","
"],col:[2,"","
"],tr:[2,"","
"],td:[3,"","
"],_default:[0,"",""]};function ve(e,t){var n;return n="undefined"!=typeof e.getElementsByTagName?e.getElementsByTagName(t||"*"):"undefined"!=typeof e.querySelectorAll?e.querySelectorAll(t||"*"):[],void 0===t||t&&A(e,t)?S.merge([e],n):n}function ye(e,t){for(var n=0,r=e.length;n",""]);var me=/<|&#?\w+;/;function xe(e,t,n,r,i){for(var o,a,s,u,l,c,f=t.createDocumentFragment(),p=[],d=0,h=e.length;d\s*$/g;function je(e,t){return A(e,"table")&&A(11!==t.nodeType?t:t.firstChild,"tr")&&S(e).children("tbody")[0]||e}function De(e){return e.type=(null!==e.getAttribute("type"))+"/"+e.type,e}function qe(e){return"true/"===(e.type||"").slice(0,5)?e.type=e.type.slice(5):e.removeAttribute("type"),e}function Le(e,t){var n,r,i,o,a,s;if(1===t.nodeType){if(Y.hasData(e)&&(s=Y.get(e).events))for(i in Y.remove(t,"handle events"),s)for(n=0,r=s[i].length;n").attr(n.scriptAttrs||{}).prop({charset:n.scriptCharset,src:n.url}).on("load error",i=function(e){r.remove(),i=null,e&&t("error"===e.type?404:200,e.type)}),E.head.appendChild(r[0])},abort:function(){i&&i()}}});var _t,zt=[],Ut=/(=)\?(?=&|$)|\?\?/;S.ajaxSetup({jsonp:"callback",jsonpCallback:function(){var e=zt.pop()||S.expando+"_"+wt.guid++;return this[e]=!0,e}}),S.ajaxPrefilter("json jsonp",function(e,t,n){var r,i,o,a=!1!==e.jsonp&&(Ut.test(e.url)?"url":"string"==typeof e.data&&0===(e.contentType||"").indexOf("application/x-www-form-urlencoded")&&Ut.test(e.data)&&"data");if(a||"jsonp"===e.dataTypes[0])return r=e.jsonpCallback=m(e.jsonpCallback)?e.jsonpCallback():e.jsonpCallback,a?e[a]=e[a].replace(Ut,"$1"+r):!1!==e.jsonp&&(e.url+=(Tt.test(e.url)?"&":"?")+e.jsonp+"="+r),e.converters["script json"]=function(){return o||S.error(r+" was not called"),o[0]},e.dataTypes[0]="json",i=C[r],C[r]=function(){o=arguments},n.always(function(){void 0===i?S(C).removeProp(r):C[r]=i,e[r]&&(e.jsonpCallback=t.jsonpCallback,zt.push(r)),o&&m(i)&&i(o[0]),o=i=void 0}),"script"}),y.createHTMLDocument=((_t=E.implementation.createHTMLDocument("").body).innerHTML="
",2===_t.childNodes.length),S.parseHTML=function(e,t,n){return"string"!=typeof e?[]:("boolean"==typeof t&&(n=t,t=!1),t||(y.createHTMLDocument?((r=(t=E.implementation.createHTMLDocument("")).createElement("base")).href=E.location.href,t.head.appendChild(r)):t=E),o=!n&&[],(i=N.exec(e))?[t.createElement(i[1])]:(i=xe([e],t,o),o&&o.length&&S(o).remove(),S.merge([],i.childNodes)));var r,i,o},S.fn.load=function(e,t,n){var r,i,o,a=this,s=e.indexOf(" ");return-1").append(S.parseHTML(e)).find(r):e)}).always(n&&function(e,t){a.each(function(){n.apply(this,o||[e.responseText,t,e])})}),this},S.expr.pseudos.animated=function(t){return S.grep(S.timers,function(e){return t===e.elem}).length},S.offset={setOffset:function(e,t,n){var r,i,o,a,s,u,l=S.css(e,"position"),c=S(e),f={};"static"===l&&(e.style.position="relative"),s=c.offset(),o=S.css(e,"top"),u=S.css(e,"left"),("absolute"===l||"fixed"===l)&&-1<(o+u).indexOf("auto")?(a=(r=c.position()).top,i=r.left):(a=parseFloat(o)||0,i=parseFloat(u)||0),m(t)&&(t=t.call(e,n,S.extend({},s))),null!=t.top&&(f.top=t.top-s.top+a),null!=t.left&&(f.left=t.left-s.left+i),"using"in t?t.using.call(e,f):c.css(f)}},S.fn.extend({offset:function(t){if(arguments.length)return void 0===t?this:this.each(function(e){S.offset.setOffset(this,t,e)});var e,n,r=this[0];return r?r.getClientRects().length?(e=r.getBoundingClientRect(),n=r.ownerDocument.defaultView,{top:e.top+n.pageYOffset,left:e.left+n.pageXOffset}):{top:0,left:0}:void 0},position:function(){if(this[0]){var e,t,n,r=this[0],i={top:0,left:0};if("fixed"===S.css(r,"position"))t=r.getBoundingClientRect();else{t=this.offset(),n=r.ownerDocument,e=r.offsetParent||n.documentElement;while(e&&(e===n.body||e===n.documentElement)&&"static"===S.css(e,"position"))e=e.parentNode;e&&e!==r&&1===e.nodeType&&((i=S(e).offset()).top+=S.css(e,"borderTopWidth",!0),i.left+=S.css(e,"borderLeftWidth",!0))}return{top:t.top-i.top-S.css(r,"marginTop",!0),left:t.left-i.left-S.css(r,"marginLeft",!0)}}},offsetParent:function(){return this.map(function(){var e=this.offsetParent;while(e&&"static"===S.css(e,"position"))e=e.offsetParent;return e||re})}}),S.each({scrollLeft:"pageXOffset",scrollTop:"pageYOffset"},function(t,i){var o="pageYOffset"===i;S.fn[t]=function(e){return $(this,function(e,t,n){var r;if(x(e)?r=e:9===e.nodeType&&(r=e.defaultView),void 0===n)return r?r[i]:e[t];r?r.scrollTo(o?r.pageXOffset:n,o?n:r.pageYOffset):e[t]=n},t,e,arguments.length)}}),S.each(["top","left"],function(e,n){S.cssHooks[n]=Fe(y.pixelPosition,function(e,t){if(t)return t=We(e,n),Pe.test(t)?S(e).position()[n]+"px":t})}),S.each({Height:"height",Width:"width"},function(a,s){S.each({padding:"inner"+a,content:s,"":"outer"+a},function(r,o){S.fn[o]=function(e,t){var n=arguments.length&&(r||"boolean"!=typeof e),i=r||(!0===e||!0===t?"margin":"border");return $(this,function(e,t,n){var r;return x(e)?0===o.indexOf("outer")?e["inner"+a]:e.document.documentElement["client"+a]:9===e.nodeType?(r=e.documentElement,Math.max(e.body["scroll"+a],r["scroll"+a],e.body["offset"+a],r["offset"+a],r["client"+a])):void 0===n?S.css(e,t,i):S.style(e,t,n,i)},s,n?e:void 0,n)}})}),S.each(["ajaxStart","ajaxStop","ajaxComplete","ajaxError","ajaxSuccess","ajaxSend"],function(e,t){S.fn[t]=function(e){return this.on(t,e)}}),S.fn.extend({bind:function(e,t,n){return this.on(e,null,t,n)},unbind:function(e,t){return this.off(e,null,t)},delegate:function(e,t,n,r){return this.on(t,e,n,r)},undelegate:function(e,t,n){return 1===arguments.length?this.off(e,"**"):this.off(t,e||"**",n)},hover:function(e,t){return this.mouseenter(e).mouseleave(t||e)}}),S.each("blur focus focusin focusout resize scroll click dblclick mousedown mouseup mousemove mouseover mouseout mouseenter mouseleave change select submit keydown keypress keyup contextmenu".split(" "),function(e,n){S.fn[n]=function(e,t){return 0(()=>{"use strict";var e={7e3:(t,e,o)=>{var n=o(8938),i=o.n(n);i().summernote=i().summernote||{lang:{}},i().extend(!0,i().summernote.lang,{"en-US":{font:{bold:"Bold",italic:"Italic",underline:"Underline",clear:"Remove Font Style",height:"Line Height",name:"Font Family",strikethrough:"Strikethrough",subscript:"Subscript",superscript:"Superscript",size:"Font Size",sizeunit:"Font Size Unit"},image:{image:"Picture",insert:"Insert Image",resizeFull:"Resize full",resizeHalf:"Resize half",resizeQuarter:"Resize quarter",resizeNone:"Original size",floatLeft:"Float Left",floatRight:"Float Right",floatNone:"Remove float",shapeRounded:"Shape: Rounded",shapeCircle:"Shape: Circle",shapeThumbnail:"Shape: Thumbnail",shapeNone:"Shape: None",dragImageHere:"Drag image or text here",dropImage:"Drop image or Text",selectFromFiles:"Select from files",maximumFileSize:"Maximum file size",maximumFileSizeError:"Maximum file size exceeded.",url:"Image URL",remove:"Remove Image",original:"Original"},video:{video:"Video",videoLink:"Video Link",insert:"Insert Video",url:"Video URL",providers:"(YouTube, Google Drive, Vimeo, Vine, Instagram, DailyMotion, Youku, Peertube)"},link:{link:"Link",insert:"Insert Link",unlink:"Unlink",edit:"Edit",textToDisplay:"Text to display",url:"To what URL should this link go?",openInNewWindow:"Open in new window"},table:{table:"Table",addRowAbove:"Add row above",addRowBelow:"Add row below",addColLeft:"Add column left",addColRight:"Add column right",delRow:"Delete row",delCol:"Delete column",delTable:"Delete table"},hr:{insert:"Insert Horizontal Rule"},style:{style:"Style",p:"Normal",blockquote:"Quote",pre:"Code",h1:"Header 1",h2:"Header 2",h3:"Header 3",h4:"Header 4",h5:"Header 5",h6:"Header 6"},lists:{unordered:"Unordered list",ordered:"Ordered list"},options:{help:"Help",fullscreen:"Full Screen",codeview:"Code View"},paragraph:{paragraph:"Paragraph",outdent:"Outdent",indent:"Indent",left:"Align left",center:"Align center",right:"Align right",justify:"Justify full"},color:{recent:"Recent Color",more:"More Color",background:"Background Color",foreground:"Text Color",transparent:"Transparent",setTransparent:"Set transparent",reset:"Reset",resetToDefault:"Reset to default",cpSelect:"Select"},shortcut:{shortcuts:"Keyboard shortcuts",close:"Close",textFormatting:"Text formatting",action:"Action",paragraphFormatting:"Paragraph formatting",documentStyle:"Document Style",extraKeys:"Extra keys"},help:{escape:"Escape",insertParagraph:"Insert Paragraph",undo:"Undo the last command",redo:"Redo the last command",tab:"Tab",untab:"Untab",bold:"Set a bold style",italic:"Set a italic style",underline:"Set a underline style",strikethrough:"Set a strikethrough style",removeFormat:"Clean a style",justifyLeft:"Set left align",justifyCenter:"Set center align",justifyRight:"Set right align",justifyFull:"Set full align",insertUnorderedList:"Toggle unordered list",insertOrderedList:"Toggle ordered list",outdent:"Outdent on current paragraph",indent:"Indent on current paragraph",formatPara:"Change current block's format as a paragraph(P tag)",formatH1:"Change current block's format as H1",formatH2:"Change current block's format as H2",formatH3:"Change current block's format as H3",formatH4:"Change current block's format as H4",formatH5:"Change current block's format as H5",formatH6:"Change current block's format as H6",insertHorizontalRule:"Insert horizontal rule","linkDialog.show":"Show Link Dialog"},history:{undo:"Undo",redo:"Redo"},specialChar:{specialChar:"SPECIAL CHARACTERS",select:"Select Special characters"},output:{noSelection:"No Selection Made!"}}})},8938:e=>{e.exports=t}},o={};function n(t){var i=o[t];if(void 0!==i)return i.exports;var r=o[t]={exports:{}};return e[t](r,r.exports,n),r.exports}n.n=t=>{var e=t&&t.__esModule?()=>t.default:()=>t;return n.d(e,{a:e}),e},n.d=(t,e)=>{for(var o in e)n.o(e,o)&&!n.o(t,o)&&Object.defineProperty(t,o,{enumerable:!0,get:e[o]})},n.o=(t,e)=>Object.prototype.hasOwnProperty.call(t,e);var i=n(8938),r=n.n(i),a=(n(7e3),["sans-serif","serif","monospace","cursive","fantasy"]);function s(t){return-1===r().inArray(t.toLowerCase(),a)?"'".concat(t,"'"):t}var l,c=navigator.userAgent,u=/MSIE|Trident/i.test(c);if(u){var d=/MSIE (\d+[.]\d+)/.exec(c);d&&(l=parseFloat(d[1])),(d=/Trident\/.*rv:([0-9]{1,}[.0-9]{0,})/.exec(c))&&(l=parseFloat(d[1]))}var f=/Edge\/\d+/.test(c),h="ontouchstart"in window||navigator.MaxTouchPoints>0||navigator.msMaxTouchPoints>0,p=u?"DOMCharacterDataModified DOMSubtreeModified DOMNodeInserted":"input";const m={isMac:navigator.appVersion.indexOf("Mac")>-1,isMSIE:u,isEdge:f,isFF:!f&&/firefox/i.test(c),isPhantom:/PhantomJS/i.test(c),isWebkit:!f&&/webkit/i.test(c),isChrome:!f&&/chrome/i.test(c),isSafari:!f&&/safari/i.test(c)&&!/chrome/i.test(c),browserVersion:l,isSupportTouch:h,isFontInstalled:function(){var t=document.createElement("canvas"),e=t.getContext("2d",{willReadFrequently:!0});function o(t,o){return e.clearRect(0,0,40,20),e.font="20px "+s(t)+', "'+o+'"',e.fillText("mw",20,10),e.getImageData(0,0,40,20).data.join("")}return t.width=40,t.height=20,e.textAlign="center",e.fillStyle="black",e.textBaseline="middle",function(t){var e="Comic Sans MS"===t?"Courier New":"Comic Sans MS";return o(e,e)!==o(t,e)}}(),isW3CRangeSupport:!!document.createRange,inputEventName:p,genericFontFamilies:a,validFontName:s};var v=0;const g={eq:function(t){return function(e){return t===e}},eq2:function(t,e){return t===e},peq2:function(t){return function(e,o){return e[t]===o[t]}},ok:function(){return!0},fail:function(){return!1},self:function(t){return t},not:function(t){return function(){return!t.apply(t,arguments)}},and:function(t,e){return function(o){return t(o)&&e(o)}},invoke:function(t,e){return function(){return t[e].apply(t,arguments)}},resetUniqueId:function(){v=0},uniqueId:function(t){var e=++v+"";return t?t+e:e},rect2bnd:function(t){var e=r()(document);return{top:t.top+e.scrollTop(),left:t.left+e.scrollLeft(),width:t.right-t.left,height:t.bottom-t.top}},invertObject:function(t){var e={};for(var o in t)Object.prototype.hasOwnProperty.call(t,o)&&(e[t[o]]=o);return e},namespaceToCamel:function(t,e){return(e=e||"")+t.split(".").map((function(t){return t.substring(0,1).toUpperCase()+t.substring(1)})).join("")},debounce:function(t,e,o){var n;return function(){var i=this,r=arguments,a=o&&!n;clearTimeout(n),n=setTimeout((function(){n=null,o||t.apply(i,r)}),e),a&&t.apply(i,r)}},isValidUrl:function(t){return/[-a-zA-Z0-9@:%._\+~#=]{2,256}\.[a-z]{2,6}\b([-a-zA-Z0-9@:%_\+.~#?&//=]*)/gi.test(t)}};function b(t){return t[0]}function y(t){return t[t.length-1]}function k(t){return t.slice(1)}function w(t,e){if(t&&t.length&&e){if(t.indexOf)return-1!==t.indexOf(e);if(t.contains)return t.contains(e)}return!1}const C={head:b,last:y,initial:function(t){return t.slice(0,t.length-1)},tail:k,prev:function(t,e){if(t&&t.length&&e){var o=t.indexOf(e);return-1===o?null:t[o-1]}return null},next:function(t,e){if(t&&t.length&&e){var o=t.indexOf(e);return-1===o?null:t[o+1]}return null},find:function(t,e){for(var o=0,n=t.length;o";function U(t){return E(t)?t.nodeValue.length:t?t.childNodes.length:0}function W(t){var e=U(t);return 0===e||(!E(t)&&1===e&&t.innerHTML===M||!(!C.all(t.childNodes,E)||""!==t.innerHTML))}function K(t){P(t)||U(t)||(t.innerHTML=M)}function q(t,e){for(;t;){if(e(t))return t;if(x(t))break;t=t.parentNode}return null}function V(t,e){e=e||g.fail;var o=[];return q(t,(function(t){return x(t)||o.push(t),e(t)})),o}function _(t,e){e=e||g.fail;for(var o=[];t&&!e(t);)o.push(t),t=t.nextSibling;return o}function G(t,e){var o=e.nextSibling,n=e.parentNode;return o?n.insertBefore(t,o):n.appendChild(t),t}function Z(t,e,o){return r().each(e,(function(e,n){!o&&$(t)&&null===t.firstChild&&F(n)&&t.appendChild(ut("br")),t.appendChild(n)})),t}function Y(t){return 0===t.offset}function X(t){return t.offset===U(t.node)}function Q(t){return Y(t)||X(t)}function J(t,e){for(;t&&t!==e;){if(0!==et(t))return!1;t=t.parentNode}return!0}function tt(t,e){if(!e)return!1;for(;t&&t!==e;){if(et(t)!==U(t.parentNode)-1)return!1;t=t.parentNode}return!0}function et(t){for(var e=0;t=t.previousSibling;)e+=1;return e}function ot(t){return!!(t&&t.childNodes&&t.childNodes.length)}function nt(t,e){var o,n;if(0===t.offset){if(x(t.node))return null;o=t.node.parentNode,n=et(t.node)}else ot(t.node)?n=U(o=t.node.childNodes[t.offset-1]):(o=t.node,n=e?0:t.offset-1);return{node:o,offset:n}}function it(t,e){var o,n;if(U(t.node)===t.offset){if(x(t.node))return null;var i=at(t.node);i?(o=i,n=0):(o=t.node.parentNode,n=et(t.node)+1)}else ot(t.node)?(o=t.node.childNodes[t.offset],n=0):(o=t.node,n=e?U(t.node):t.offset+1);return{node:o,offset:n}}function rt(t,e){var o,n=0;if(U(t.node)===t.offset){if(x(t.node))return null;o=t.node.parentNode,n=et(t.node)+1,x(o)&&(o=t.node.nextSibling,n=0)}else ot(t.node)?(o=t.node.childNodes[t.offset],n=0):(o=t.node,n=e?U(t.node):t.offset+1);return{node:o,offset:n}}function at(t){if(t.nextSibling&&t.parent===t.nextSibling.parent)return E(t.nextSibling)?t.nextSibling:at(t.nextSibling)}function st(t,e){return t.node===e.node&&t.offset===e.offset}function lt(t,e){var o=e&&e.isSkipPaddingBlankHTML,n=e&&e.isNotSplitEdgePoint,i=e&&e.isDiscardEmptySplits;if(i&&(o=!0),Q(t)&&(E(t.node)||n)){if(Y(t))return t.node;if(X(t))return t.node.nextSibling}if(E(t.node))return t.node.splitText(t.offset);var r=_(t.node.childNodes[t.offset]),a=G(t.node.cloneNode(!1),t.node);return Z(a,r),o||(K(t.node),K(a)),i&&(W(t.node)&&dt(t.node),W(a))?(dt(a),t.node.nextSibling):a}function ct(t,e,o){var n=V(e.node,g.eq(t));if(!n.length)return null;if(1===n.length)return lt(e,o);if(n.length>2){var i=n.slice(0,n.length-1).find((function(t){return t.nextSibling}));if(i&&0!=e.offset&&X(e)){var r,a=i.nextSibling;1==a.nodeType?(n=V(r=a.childNodes[0],g.eq(t)),e={node:r,offset:0}):3!=a.nodeType||a.data.match(/[\n\r]/g)||(n=V(r=a,g.eq(t)),e={node:r,offset:0})}}return n.reduce((function(t,n){return t===e.node&&(t=lt(e,o)),lt({node:n,offset:t?et(t):U(n)},o)}))}function ut(t){return document.createElement(t)}function dt(t,e){if(t&&t.parentNode){if(t.removeNode)return t.removeNode(e);var o=t.parentNode;if(!e){for(var n=[],i=0,r=t.childNodes.length;i".concat(M,"

"),makePredByNodeName:T,isEditable:x,isControlSizing:function(t){return t&&r()(t).hasClass("note-control-sizing")},isText:E,isElement:function(t){return t&&1===t.nodeType},isVoid:P,isPara:N,isPurePara:function(t){return N(t)&&!$(t)},isHeading:function(t){return t&&/^H[1-7]/.test(t.nodeName.toUpperCase())},isInline:L,isBlock:g.not(L),isBodyInline:function(t){return L(t)&&!q(t,N)},isBody:O,isParaInline:function(t){return L(t)&&!!q(t,N)},isPre:I,isList:F,isTable:R,isData:A,isCell:H,isBlockquote:j,isBodyContainer:z,isAnchor:B,isDiv:T("DIV"),isLi:$,isBR:T("BR"),isSpan:T("SPAN"),isB:T("B"),isU:T("U"),isS:T("S"),isI:T("I"),isImg:T("IMG"),isTextarea:ft,deepestChildIsEmpty:function(t){do{if(null===t.firstElementChild||""===t.firstElementChild.innerHTML)break}while(t=t.firstElementChild);return W(t)},isEmpty:W,isEmptyAnchor:g.and(B,W),isClosestSibling:function(t,e){return t.nextSibling===e||t.previousSibling===e},withClosestSiblings:function(t,e){e=e||g.ok;var o=[];return t.previousSibling&&e(t.previousSibling)&&o.push(t.previousSibling),o.push(t),t.nextSibling&&e(t.nextSibling)&&o.push(t.nextSibling),o},nodeLength:U,isLeftEdgePoint:Y,isRightEdgePoint:X,isEdgePoint:Q,isLeftEdgeOf:J,isRightEdgeOf:tt,isLeftEdgePointOf:function(t,e){return Y(t)&&J(t.node,e)},isRightEdgePointOf:function(t,e){return X(t)&&tt(t.node,e)},prevPoint:nt,nextPoint:it,nextPointWithEmptyNode:rt,isSamePoint:st,isVisiblePoint:function(t){if(E(t.node)||!ot(t.node)||W(t.node))return!0;var e=t.node.childNodes[t.offset-1],o=t.node.childNodes[t.offset];return!((e&&!P(e)||o&&!P(o))&&!R(o))},prevPointUntil:function(t,e){for(;t;){if(e(t))return t;t=nt(t)}return null},nextPointUntil:function(t,e){for(;t;){if(e(t))return t;t=it(t)}return null},isCharPoint:function(t){if(!E(t.node))return!1;var e=t.node.nodeValue.charAt(t.offset-1);return e&&" "!==e&&e!==S},isSpacePoint:function(t){if(!E(t.node))return!1;var e=t.node.nodeValue.charAt(t.offset-1);return" "===e||e===S},walkPoint:function(t,e,o,n){for(var i=t;i&&i.node&&(o(i),!st(i,e));){i=rt(i,n&&t.node!==i.node&&e.node!==i.node)}},ancestor:q,singleChildAncestor:function(t,e){for(t=t.parentNode;t&&1===U(t);){if(e(t))return t;if(x(t))break;t=t.parentNode}return null},listAncestor:V,lastAncestor:function(t,e){var o=V(t);return C.last(o.filter(e))},listNext:_,listPrev:function(t,e){e=e||g.fail;for(var o=[];t&&!e(t);)o.push(t),t=t.previousSibling;return o},listDescendant:function(t,e){var o=[];return e=e||g.ok,function n(i){t!==i&&e(i)&&o.push(i);for(var r=0,a=i.childNodes.length;r-1)return n;return null},wrap:function(t,e){var o=t.parentNode,n=r()("<"+e+">")[0];return o.insertBefore(n,t),n.appendChild(t),n},insertAfter:G,appendChildNodes:Z,position:et,hasChildren:ot,makeOffsetPath:function(t,e){return V(e,g.eq(t)).map(et).reverse()},fromOffsetPath:function(t,e){for(var o=t,n=0,i=e.length;n\s]*)(.*?)(\s*\/?>)/g,(function(t,e,o){o=o.toUpperCase();var n=/^DIV|^TD|^TH|^P|^LI|^H[1-7]/.test(o)&&!!e,i=/^BLOCKQUOTE|^TABLE|^TBODY|^TR|^HR|^UL|^OL/.test(o);return t+(n||i?"\n":"")}))).trim()}return o},value:ht,posFromPlaceholder:function(t){var e=r()(t),o=e.offset(),n=e.outerHeight(!0);return{left:o.left,top:o.top+n}},attachEvents:function(t,e){Object.keys(e).forEach((function(o){t.on(o,e[o])}))},detachEvents:function(t,e){Object.keys(e).forEach((function(o){t.off(o,e[o])}))},isCustomStyleTag:function(t){return t&&!E(t)&&C.contains(t.classList,"note-styletag")}};function mt(t){return mt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},mt(t)}function vt(t,e){for(var o=0;o1,i=n&&C.head(o),r=n?C.last(o):C.head(o),a=this.modules[i||"editor"];return!i&&this[r]?this[r].apply(this,e):a&&a[r]&&a.shouldInitialize()?a[r].apply(a,e):void 0}}],e&&vt(t.prototype,e),o&&vt(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function yt(t){return yt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},yt(t)}function kt(t){return kt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},kt(t)}function wt(t,e){for(var o=0;o=0)break;n=a[o]}if(0!==o&&pt.isText(a[o-1])){var s=document.body.createTextRange(),l=null;s.moveToElementText(n||i),s.collapse(!n),l=n?n.nextSibling:i.firstChild;var c=t.duplicate();c.setEndPoint("StartToStart",s);for(var u=c.text.replace(/[\r\n]/g,"").length;u>l.nodeValue.length&&l.nextSibling;)u-=l.nodeValue.length,l=l.nextSibling;l.nodeValue;e&&l.nextSibling&&pt.isText(l.nextSibling)&&u===l.nodeValue.length&&(u-=l.nodeValue.length,l=l.nextSibling),i=l,o=u}return{cont:i,offset:o}}function xt(t){var e=document.body.createTextRange(),o=function t(e,o){var n,i;if(pt.isText(e)){var r=pt.listPrev(e,g.not(pt.isText)),a=C.last(r).previousSibling;n=a||e.parentNode,o+=C.sum(C.tail(r),pt.nodeLength),i=!a}else{if(n=e.childNodes[o]||e,pt.isText(n))return t(n,0);o=0,i=!1}return{node:n,collapseToStart:i,offset:o}}(t.node,t.offset);return e.moveToElementText(o.node),e.collapse(o.collapseToStart),e.moveStart("character",o.offset),e}r().fn.extend({summernote:function(){var t=yt(C.head(arguments)),e="string"===t,o="object"===t,n=r().extend({},r().summernote.options,o?C.head(arguments):{});n.langInfo=r().extend(!0,{},r().summernote.lang["en-US"],r().summernote.lang[n.lang]),n.icons=r().extend(!0,{},r().summernote.options.icons,n.icons),n.tooltip="auto"===n.tooltip?!m.isSupportTouch:n.tooltip,this.each((function(t,e){var o=r()(e);if(!o.data("summernote")){var i=new bt(o,n);o.data("summernote",i),o.data("summernote").triggerEvent("init",i.layoutInfo)}}));var i=this.first();if(i.length){var a=i.data("summernote");if(e)return a.invoke.apply(a,C.from(arguments));n.focus&&a.invoke("editor.focus")}return this}});var Tt=function(){function t(e,o,n,i){!function(t,e){if(!(t instanceof e))throw new TypeError("Cannot call a class as a function")}(this,t),this.sc=e,this.so=o,this.ec=n,this.eo=i,this.isOnEditable=this.makeIsOn(pt.isEditable),this.isOnList=this.makeIsOn(pt.isList),this.isOnAnchor=this.makeIsOn(pt.isAnchor),this.isOnCell=this.makeIsOn(pt.isCell),this.isOnData=this.makeIsOn(pt.isData)}return e=t,o=[{key:"nativeRange",value:function(){if(m.isW3CRangeSupport){var t=document.createRange();return t.setStart(this.sc,this.so),t.setEnd(this.ec,this.eo),t}var e=xt({node:this.sc,offset:this.so});return e.setEndPoint("EndToEnd",xt({node:this.ec,offset:this.eo})),e}},{key:"getPoints",value:function(){return{sc:this.sc,so:this.so,ec:this.ec,eo:this.eo}}},{key:"getStartPoint",value:function(){return{node:this.sc,offset:this.so}}},{key:"getEndPoint",value:function(){return{node:this.ec,offset:this.eo}}},{key:"select",value:function(){var t=this.nativeRange();if(m.isW3CRangeSupport){var e=document.getSelection();e.rangeCount>0&&e.removeAllRanges(),e.addRange(t)}else t.select();return this}},{key:"scrollIntoView",value:function(t){var e=r()(t).height();return t.scrollTop+e0?o.so-1:0];if(e){var i=pt.listPrev(e,pt.isParaInline).reverse();if((i=i.concat(pt.listNext(e.nextSibling,pt.isParaInline))).length){var r=pt.wrap(C.head(i),"p");pt.appendChildNodes(r,C.tail(i))}}return this.normalize()}},{key:"insertNode",value:function(t){var e=arguments.length>1&&void 0!==arguments[1]&&arguments[1],o=this;(pt.isText(t)||pt.isInline(t))&&(o=this.wrapBodyInlineWithPara().deleteContents());var n=pt.splitPoint(o.getStartPoint(),pt.isInline(t));return n.rightNode?(n.rightNode.parentNode.insertBefore(t,n.rightNode),pt.isEmpty(n.rightNode)&&(e||pt.isPara(t))&&n.rightNode.parentNode.removeChild(n.rightNode)):n.container.appendChild(t),t}},{key:"pasteHTML",value:function(t){t=((t||"")+"").trim(t);var e=r()("
").html(t)[0],o=C.from(e.childNodes),n=this,i=!1;return n.so>=0&&(o=o.reverse(),i=!0),o=o.map((function(t){return n.insertNode(t,!pt.isInline(t))})),i&&(o=o.reverse()),o}},{key:"toString",value:function(){var t=this.nativeRange();return m.isW3CRangeSupport?t.toString():t.text}},{key:"getWordRange",value:function(e){var o=this.getEndPoint();if(!pt.isCharPoint(o))return this;var n=pt.prevPointUntil(o,(function(t){return!pt.isCharPoint(t)}));return e&&(o=pt.nextPointUntil(o,(function(t){return!pt.isCharPoint(t)}))),new t(n.node,n.offset,o.node,o.offset)}},{key:"getWordsRange",value:function(e){var o=this.getEndPoint(),n=function(t){return!pt.isCharPoint(t)&&!pt.isSpacePoint(t)};if(n(o))return this;var i=pt.prevPointUntil(o,n);return e&&(o=pt.nextPointUntil(o,n)),new t(i.node,i.offset,o.node,o.offset)}},{key:"getWordsMatchRange",value:function(e){var o=this.getEndPoint(),n=pt.prevPointUntil(o,(function(n){if(!pt.isCharPoint(n)&&!pt.isSpacePoint(n))return!0;var i=new t(n.node,n.offset,o.node,o.offset),r=e.exec(i.toString());return r&&0===r.index})),i=new t(n.node,n.offset,o.node,o.offset),r=i.toString(),a=e.exec(r);return a&&a[0].length===r.length?i:null}},{key:"bookmark",value:function(t){return{s:{path:pt.makeOffsetPath(t,this.sc),offset:this.so},e:{path:pt.makeOffsetPath(t,this.ec),offset:this.eo}}}},{key:"paraBookmark",value:function(t){return{s:{path:C.tail(pt.makeOffsetPath(C.head(t),this.sc)),offset:this.so},e:{path:C.tail(pt.makeOffsetPath(C.last(t),this.ec)),offset:this.eo}}}},{key:"getClientRects",value:function(){return this.nativeRange().getClientRects()}}],o&&wt(e.prototype,o),n&&wt(e,n),Object.defineProperty(e,"prototype",{writable:!1}),e;var e,o,n}();const Et={create:function(t,e,o,n){if(4===arguments.length)return new Tt(t,e,o,n);if(2===arguments.length)return new Tt(t,e,o=t,n=e);var i=this.createFromSelection();if(!i&&1===arguments.length){var r=arguments[0];return pt.isEditable(r)&&(r=r.lastChild),this.createFromBodyElement(r,pt.emptyPara===arguments[0].innerHTML)}return i},createFromBodyElement:function(t){var e=arguments.length>1&&void 0!==arguments[1]&&arguments[1];return this.createFromNode(t).collapse(e)},createFromSelection:function(){var t,e,o,n;if(m.isW3CRangeSupport){var i=document.getSelection();if(!i||0===i.rangeCount)return null;if(pt.isBody(i.anchorNode))return null;var r=i.getRangeAt(0);t=r.startContainer,e=r.startOffset,o=r.endContainer,n=r.endOffset}else{var a=document.selection.createRange(),s=a.duplicate();s.collapse(!1);var l=a;l.collapse(!0);var c=St(l,!0),u=St(s,!1);pt.isText(c.node)&&pt.isLeftEdgePoint(c)&&pt.isTextNode(u.node)&&pt.isRightEdgePoint(u)&&u.node.nextSibling===c.node&&(c=u),t=c.cont,e=c.offset,o=u.cont,n=u.offset}return new Tt(t,e,o,n)},createFromNode:function(t){var e=t,o=0,n=t,i=pt.nodeLength(n);return pt.isVoid(e)&&(o=pt.listPrev(e).length-1,e=e.parentNode),pt.isBR(n)?(i=pt.listPrev(n).length-1,n=n.parentNode):pt.isVoid(n)&&(i=pt.listPrev(n).length,n=n.parentNode),this.create(e,o,n,i)},createFromNodeBefore:function(t){return this.createFromNode(t).collapse(!0)},createFromNodeAfter:function(t){return this.createFromNode(t).collapse()},createFromBookmark:function(t,e){var o=pt.fromOffsetPath(t,e.s.path),n=e.s.offset,i=pt.fromOffsetPath(t,e.e.path),r=e.e.offset;return new Tt(o,n,i,r)},createFromParaBookmark:function(t,e){var o=t.s.offset,n=t.e.offset,i=pt.fromOffsetPath(C.head(e),t.s.path),r=pt.fromOffsetPath(C.last(e),t.e.path);return new Tt(i,o,r,n)}};var Pt={BACKSPACE:8,TAB:9,ENTER:13,ESCAPE:27,SPACE:32,DELETE:46,LEFT:37,UP:38,RIGHT:39,DOWN:40,NUM0:48,NUM1:49,NUM2:50,NUM3:51,NUM4:52,NUM5:53,NUM6:54,NUM7:55,NUM8:56,B:66,E:69,I:73,J:74,K:75,L:76,R:82,S:83,U:85,V:86,Y:89,Z:90,SLASH:191,LEFTBRACKET:219,BACKSLASH:220,RIGHTBRACKET:221,HOME:36,END:35,PAGEUP:33,PAGEDOWN:34};const Nt={isEdit:function(t){return C.contains([Pt.BACKSPACE,Pt.TAB,Pt.ENTER,Pt.SPACE,Pt.DELETE],t)},isRemove:function(t){return C.contains([Pt.BACKSPACE,Pt.DELETE],t)},isMove:function(t){return C.contains([Pt.LEFT,Pt.UP,Pt.RIGHT,Pt.DOWN],t)},isNavigation:function(t){return C.contains([Pt.HOME,Pt.END,Pt.PAGEUP,Pt.PAGEDOWN],t)},nameFromCode:g.invertObject(Pt),code:Pt};function It(t){return It="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},It(t)}function $t(t,e){for(var o=0;o0&&(this.stackOffset--,this.applySnapshot(this.stack[this.stackOffset]))}},{key:"redo",value:function(){this.stack.length-1>this.stackOffset&&(this.stackOffset++,this.applySnapshot(this.stack[this.stackOffset]))}},{key:"recordUndo",value:function(){this.stackOffset++,this.stack.length>this.stackOffset&&(this.stack=this.stack.slice(0,this.stackOffset)),this.stack.push(this.makeSnapshot()),this.stack.length>this.context.options.historyLimit&&(this.stack.shift(),this.stackOffset-=1)}}])&&$t(t.prototype,e),o&&$t(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Lt(t){return Lt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Lt(t)}function Ft(t,e){for(var o=0;o-1;o["list-style"]=n?"unordered":"ordered"}else o["list-style"]="none";var i=pt.ancestor(t.sc,pt.isPara);if(i&&i.style["line-height"])o["line-height"]=i.style.lineHeight;else{var a=parseInt(o["line-height"],10)/parseInt(o["font-size"],10);o["line-height"]=a.toFixed(1)}return o.anchor=t.isOnAnchor()&&pt.ancestor(t.sc,pt.isAnchor),o.ancestors=pt.listAncestor(t.sc,pt.isEditable),o.range=t,o}}],e&&Ft(t.prototype,e),o&&Ft(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function jt(t){return jt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},jt(t)}function zt(t,e){for(var o=0;o25?e-25:""}))}))})),o.select()}},{key:"toggleList",value:function(t,e){var o=this,n=Et.create(e).wrapBodyInlineWithPara(),i=n.nodes(pt.isPara,{includeAncestor:!0}),a=n.paraBookmark(i),s=C.clusterBy(i,g.peq2("parentNode"));if(C.find(i,pt.isPurePara)){var l=[];r().each(s,(function(e,n){l=l.concat(o.wrapList(n,t))})),i=l}else{var c=n.nodes(pt.isList,{includeAncestor:!0}).filter((function(e){return!r().nodeName(e,t)}));c.length?r().each(c,(function(e,o){pt.replace(o,t)})):i=this.releaseList(s,!0)}Et.createFromParaBookmark(a,i).select()}},{key:"wrapList",value:function(t,e){var o=C.head(t),n=C.last(t),i=pt.isList(o.previousSibling)&&o.previousSibling,r=pt.isList(n.nextSibling)&&n.nextSibling,a=i||pt.insertAfter(pt.create(e||"UL"),n);return t=t.map((function(t){return pt.isPurePara(t)?pt.replace(t,"LI"):t})),pt.appendChildNodes(a,t,!0),r&&(pt.appendChildNodes(a,C.from(r.childNodes),!0),pt.remove(r)),t}},{key:"releaseList",value:function(t,e){var o=this,n=[];return r().each(t,(function(t,i){var a=C.head(i),s=C.last(i),l=e?pt.lastAncestor(a,pt.isList):a.parentNode,c=l.parentNode;if("LI"===l.parentNode.nodeName)i.map((function(t){var e=o.findNextSiblings(t);c.nextSibling?c.parentNode.insertBefore(t,c.nextSibling):c.parentNode.appendChild(t),e.length&&(o.wrapList(e,l.nodeName),t.appendChild(e[0].parentNode))})),0===l.children.length&&c.removeChild(l),0===c.childNodes.length&&c.parentNode.removeChild(c);else{var u=l.childNodes.length>1?pt.splitTree(l,{node:s.parentNode,offset:pt.position(s)+1},{isSkipPaddingBlankHTML:!0}):null,d=pt.splitTree(l,{node:a.parentNode,offset:pt.position(a)},{isSkipPaddingBlankHTML:!0});i=e?pt.listDescendant(d,pt.isLi):C.from(d.childNodes).filter(pt.isLi),!e&&pt.isList(l.parentNode)||(i=i.map((function(t){return pt.replace(t,"P")}))),r().each(C.from(i).reverse(),(function(t,e){pt.insertAfter(e,l)}));var f=C.compact([l,d,u]);r().each(f,(function(t,e){var o=[e].concat(pt.listDescendant(e,pt.isList));r().each(o.reverse(),(function(t,e){pt.nodeLength(e)||pt.remove(e,!0)}))}))}n=n.concat(i)})),n}},{key:"appendToPrevious",value:function(t){return t.previousSibling?pt.appendChildNodes(t.previousSibling,[t]):this.wrapList([t],"LI")}},{key:"findList",value:function(t){return t?C.find(t.children,(function(t){return["OL","UL"].indexOf(t.nodeName)>-1})):null}},{key:"findNextSiblings",value:function(t){for(var e=[];t.nextSibling;)e.push(t.nextSibling),t=t.nextSibling;return e}}],e&&zt(t.prototype,e),o&&zt(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Mt(t){return Mt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Mt(t)}function Ut(t,e){for(var o=0;o1,i=e.rowSpan>1,a=t.rowIndex===r.rowPos&&e.cellIndex===r.colPos;l(t.rowIndex,o,t,e,i,n,!1);var s=e.attributes.rowSpan?parseInt(e.attributes.rowSpan.value,10):0;if(s>1)for(var c=1;c1)for(var p=1;p=o.cellIndex&&o.cellIndex<=e&&!n&&r.colPos++}function h(e){switch(o){case t.where.Column:if(e.isColSpan)return t.resultAction.SubtractSpanCount;break;case t.where.Row:if(!e.isVirtual&&e.isRowSpan)return t.resultAction.AddCell;if(e.isRowSpan)return t.resultAction.SubtractSpanCount}return t.resultAction.RemoveCell}function p(e){switch(o){case t.where.Column:if(e.isColSpan)return t.resultAction.SumSpanCount;if(e.isRowSpan&&e.isVirtual)return t.resultAction.Ignore;break;case t.where.Row:if(e.isRowSpan)return t.resultAction.SumSpanCount;if(e.isColSpan&&e.isVirtual)return t.resultAction.Ignore}return t.resultAction.AddCell}this.getActionList=function(){for(var e=o===t.where.Row?r.rowPos:-1,i=o===t.where.Column?r.colPos:-1,l=0,u=!0;u;){var d=e>=0?e:l,f=i>=0?i:l,m=a[d];if(!m)return u=!1,s;var v=m[f];if(!v)return u=!1,s;var g=t.resultAction.Ignore;switch(n){case t.requestAction.Add:g=p(v);break;case t.requestAction.Delete:g=h(v)}s.push(c(v,g,d,f)),l++}return s},e&&e.tagName&&("td"===e.tagName.toLowerCase()||"th"===e.tagName.toLowerCase())&&(r.colPos=e.cellIndex,e.parentElement&&e.parentElement.tagName&&"tr"===e.parentElement.tagName.toLowerCase()&&(r.rowPos=e.parentElement.rowIndex)),function(){for(var t=i.rows,e=0;e"),s=new Gt(o,Gt.where.Row,Gt.requestAction.Add,r()(n).closest("table")[0]).getActionList(),l=0;l"+pt.blank+"");break;case Gt.resultAction.SumSpanCount:if("top"===e&&(c.baseCell.parent?c.baseCell.closest("tr").rowIndex:0)<=n[0].rowIndex){var d=r()("
").append(r()(""+pt.blank+"").removeAttr("rowspan")).html();a.append(d);break}var f=parseInt(c.baseCell.rowSpan,10);f++,c.baseCell.setAttribute("rowSpan",f)}}if("top"===e)n.before(a);else{if(o.rowSpan>1){var h=n[0].rowIndex+(o.rowSpan-2);return void r()(r()(n).parent().find("tr")[h]).after(r()(a))}n.after(a)}}},{key:"addCol",value:function(t,e){var o=pt.ancestor(t.commonAncestor(),pt.isCell),n=r()(o).closest("tr");r()(n).siblings().push(n);for(var i=new Gt(o,Gt.where.Column,Gt.requestAction.Add,r()(n).closest("table")[0]).getActionList(),a=0;a"+pt.blank+""):r()(s.baseCell).before(""+pt.blank+"");break;case Gt.resultAction.SumSpanCount:if("right"===e){var c=parseInt(s.baseCell.colSpan,10);c++,s.baseCell.setAttribute("colSpan",c)}else r()(s.baseCell).before(""+pt.blank+"")}}}},{key:"recoverAttributes",value:function(t){var e="";if(!t)return e;for(var o=t.attributes||[],n=0;n1,d=u?parseInt(l.rowSpan,10):0;switch(a[s].action){case Gt.resultAction.Ignore:continue;case Gt.resultAction.AddCell:var f=o.next("tr")[0];if(!f)continue;var h=o[0].cells[n];u&&(d>2?(d--,f.insertBefore(h,f.cells[n]),f.cells[n].setAttribute("rowSpan",d),f.cells[n].innerHTML=""):2===d&&(f.insertBefore(h,f.cells[n]),f.cells[n].removeAttribute("rowSpan"),f.cells[n].innerHTML=""));continue;case Gt.resultAction.SubtractSpanCount:u&&(d>2?(d--,l.setAttribute("rowSpan",d),c.rowIndex!==i&&l.cellIndex===n&&(l.innerHTML="")):2===d&&(l.removeAttribute("rowSpan"),c.rowIndex!==i&&l.cellIndex===n&&(l.innerHTML="")));continue;case Gt.resultAction.RemoveCell:continue}}o.remove()}},{key:"deleteCol",value:function(t){for(var e=pt.ancestor(t.commonAncestor(),pt.isCell),o=r()(e).closest("tr"),n=o.children("td, th").index(r()(e)),i=new Gt(e,Gt.where.Column,Gt.requestAction.Delete,r()(o).closest("table")[0]).getActionList(),a=0;a1){var l=s.colSpan?parseInt(s.colSpan,10):0;l>2?(l--,s.setAttribute("colSpan",l),s.cellIndex===n&&(s.innerHTML="")):2===l&&(s.removeAttribute("colSpan"),s.cellIndex===n&&(s.innerHTML=""))}continue;case Gt.resultAction.RemoveCell:pt.remove(i[a].baseCell,!0);continue}}},{key:"createTable",value:function(t,e,o){for(var n,i=[],a=0;a"+pt.blank+"");n=i.join("");for(var s,l=[],c=0;c"+n+"");s=l.join("");var u=r()(""+s+"
");return o&&o.tableClassName&&u.addClass(o.tableClassName),u[0]}},{key:"deleteTable",value:function(t){var e=pt.ancestor(t.commonAncestor(),pt.isCell);r()(e).closest("table").remove()}}],e&&Vt(t.prototype,e),o&&Vt(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Yt(t){return Yt="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Yt(t)}function Xt(t,e){for(var o=0;o0&&o.isLimited(u))){var d=c.toString()!==i;"string"==typeof n&&(n=n.trim()),n=o.options.onCreateLink?o.options.onCreateLink(n):o.checkLinkUrl(n);var f=[];if(d){var h=(c=c.deleteContents()).insertNode(r()("").text(i)[0]);f.push(h)}else f=o.style.styleNodes(c,{nodeName:"A",expandClosestSibling:!0,onlyPartialContains:!0});r().each(f,(function(t,o){r()(o).attr("href",n),a?(r()(o).attr("target","_blank"),s&&e.push("noreferrer"),l&&e.push("noopener"),e.length&&r()(o).attr("rel",e.join(" "))):r()(o).removeAttr("target")})),o.setLastRange(o.createRangeFromList(f).select())}})),this.color=this.wrapCommand((function(t){var e=t.foreColor,o=t.backColor;e&&document.execCommand("foreColor",!1,e),o&&document.execCommand("backColor",!1,o)})),this.foreColor=this.wrapCommand((function(t){document.execCommand("foreColor",!1,t)})),this.insertTable=this.wrapCommand((function(t){var e=t.split("x");o.getLastRange().deleteContents().insertNode(o.table.createTable(e[0],e[1],o.options))})),this.removeMedia=this.wrapCommand((function(){var t=r()(o.restoreTarget()).parent();t.closest("figure").length?t.closest("figure").remove():t=r()(o.restoreTarget()).detach(),o.setLastRange(Et.createFromSelection(t).select()),o.context.triggerEvent("media.delete",t,o.$editable)})),this.floatMe=this.wrapCommand((function(t){var e=r()(o.restoreTarget());e.toggleClass("note-float-left","left"===t),e.toggleClass("note-float-right","right"===t),e.css("float","none"===t?"":t)})),this.resize=this.wrapCommand((function(t){var e=r()(o.restoreTarget());0===(t=parseFloat(t))?e.css("width",""):e.css({width:100*t+"%",height:""})}))},e=[{key:"initialize",value:function(){var t=this;this.$editable.on("keydown",(function(e){if(e.keyCode===Nt.code.ENTER&&t.context.triggerEvent("enter",e),t.context.triggerEvent("keydown",e),t.snapshot=t.history.makeSnapshot(),t.hasKeyShortCut=!1,e.isDefaultPrevented()||(t.options.shortcuts?t.hasKeyShortCut=t.handleKeyMap(e):t.preventDefaultEditableShortCuts(e)),t.isLimited(1,e)){var o=t.getLastRange();if(o.eo-o.so==0)return!1}t.setLastRange(),t.options.recordEveryKeystroke&&!1===t.hasKeyShortCut&&t.history.recordUndo()})).on("keyup",(function(e){t.setLastRange(),t.context.triggerEvent("keyup",e)})).on("focus",(function(e){t.setLastRange(),t.context.triggerEvent("focus",e)})).on("blur",(function(e){t.context.triggerEvent("blur",e)})).on("mousedown",(function(e){t.context.triggerEvent("mousedown",e)})).on("mouseup",(function(e){t.setLastRange(),t.history.recordUndo(),t.context.triggerEvent("mouseup",e)})).on("scroll",(function(e){t.context.triggerEvent("scroll",e)})).on("paste",(function(e){t.setLastRange(),t.context.triggerEvent("paste",e)})).on("copy",(function(e){t.context.triggerEvent("copy",e)})).on("input",(function(){t.isLimited(0)&&t.snapshot&&t.history.applySnapshot(t.snapshot)})),this.$editable.attr("spellcheck",this.options.spellCheck),this.$editable.attr("autocorrect",this.options.spellCheck),this.options.disableGrammar&&this.$editable.attr("data-gramm",!1),this.$editable.html(pt.html(this.$note)||pt.emptyPara),this.$editable.on(m.inputEventName,g.debounce((function(){t.context.triggerEvent("change",t.$editable.html(),t.$editable)}),10)),this.$editable.on("focusin",(function(e){t.context.triggerEvent("focusin",e)})).on("focusout",(function(e){t.context.triggerEvent("focusout",e)})),this.options.airMode?this.options.overrideContextMenu&&this.$editor.on("contextmenu",(function(e){return t.context.triggerEvent("contextmenu",e),!1})):(this.options.width&&this.$editor.outerWidth(this.options.width),this.options.height&&this.$editable.outerHeight(this.options.height),this.options.maxHeight&&this.$editable.css("max-height",this.options.maxHeight),this.options.minHeight&&this.$editable.css("min-height",this.options.minHeight)),this.history.recordUndo(),this.setLastRange()}},{key:"destroy",value:function(){this.$editable.off()}},{key:"handleKeyMap",value:function(t){var e=this.options.keyMap[m.isMac?"mac":"pc"],o=[];t.metaKey&&o.push("CMD"),t.ctrlKey&&!t.altKey&&o.push("CTRL"),t.shiftKey&&o.push("SHIFT");var n=Nt.nameFromCode[t.keyCode];n&&o.push(n);var i=e[o.join("+")];if("TAB"!==n||this.options.tabDisable)if(i){if(!1!==this.context.invoke(i))return t.preventDefault(),!0}else Nt.isEdit(t.keyCode)&&(Nt.isRemove(t.keyCode)&&this.context.invoke("removed"),this.afterCommand());else this.afterCommand();return!1}},{key:"preventDefaultEditableShortCuts",value:function(t){(t.ctrlKey||t.metaKey)&&C.contains([66,73,85],t.keyCode)&&t.preventDefault()}},{key:"isLimited",value:function(t,e){return t=t||0,(void 0===e||!(Nt.isMove(e.keyCode)||Nt.isNavigation(e.keyCode)||e.ctrlKey||e.metaKey||C.contains([Nt.code.BACKSPACE,Nt.code.DELETE],e.keyCode)))&&this.options.maxTextLength>0&&this.$editable.text().length+t>this.options.maxTextLength}},{key:"checkLinkUrl",value:function(t){return Jt.test(t)?"mailto://"+t:te.test(t)?"tel://"+t:ee.test(t)?t:"http://"+t}},{key:"createRange",value:function(){return this.focus(),this.setLastRange(),this.getLastRange()}},{key:"createRangeFromList",value:function(t){var e=Et.createFromNodeBefore(C.head(t)).getStartPoint(),o=Et.createFromNodeAfter(C.last(t)).getEndPoint();return Et.create(e.node,e.offset,o.node,o.offset)}},{key:"setLastRange",value:function(t){t?this.lastRange=t:(this.lastRange=Et.create(this.editable),0===r()(this.lastRange.sc).closest(".note-editable").length&&(this.lastRange=Et.createFromBodyElement(this.editable)))}},{key:"getLastRange",value:function(){return this.lastRange||this.setLastRange(),this.lastRange}},{key:"saveRange",value:function(t){t&&this.getLastRange().collapse().select()}},{key:"restoreRange",value:function(){this.lastRange&&(this.lastRange.select(),this.focus())}},{key:"saveTarget",value:function(t){this.$editable.data("target",t)}},{key:"clearTarget",value:function(){this.$editable.removeData("target")}},{key:"restoreTarget",value:function(){return this.$editable.data("target")}},{key:"currentStyle",value:function(){var t=Et.create();return t&&(t=t.normalize()),t?this.style.current(t):this.style.fromNode(this.$editable)}},{key:"styleFromNode",value:function(t){return this.style.fromNode(t)}},{key:"undo",value:function(){this.context.triggerEvent("before.command",this.$editable.html()),this.history.undo(),this.context.triggerEvent("change",this.$editable.html(),this.$editable)}},{key:"commit",value:function(){this.context.triggerEvent("before.command",this.$editable.html()),this.history.commit(),this.context.triggerEvent("change",this.$editable.html(),this.$editable)}},{key:"redo",value:function(){this.context.triggerEvent("before.command",this.$editable.html()),this.history.redo(),this.context.triggerEvent("change",this.$editable.html(),this.$editable)}},{key:"beforeCommand",value:function(){this.context.triggerEvent("before.command",this.$editable.html()),document.execCommand("styleWithCSS",!1,this.options.styleWithCSS),this.focus()}},{key:"afterCommand",value:function(t){this.normalizeContent(),this.history.recordUndo(),t||this.context.triggerEvent("change",this.$editable.html(),this.$editable)}},{key:"tab",value:function(){var t=this.getLastRange();if(t.isCollapsed()&&t.isOnCell())this.table.tab(t);else{if(0===this.options.tabSize)return!1;this.isLimited(this.options.tabSize)||(this.beforeCommand(),this.typing.insertTab(t,this.options.tabSize),this.afterCommand())}}},{key:"untab",value:function(){var t=this.getLastRange();if(t.isCollapsed()&&t.isOnCell())this.table.tab(t,!0);else if(0===this.options.tabSize)return!1}},{key:"wrapCommand",value:function(t){return function(){this.beforeCommand(),t.apply(this,arguments),this.afterCommand()}}},{key:"removed",value:function(t,e,o){(t=Et.create()).isCollapsed()&&t.isOnCell()&&(o=(e=t.ec).tagName)&&1===e.childElementCount&&"BR"===e.childNodes[0].tagName&&("P"===o?e.remove():["TH","TD"].indexOf(o)>=0&&e.firstChild.remove())}},{key:"insertImage",value:function(t,e){var o,n=this;return(o=t,r().Deferred((function(t){var e=r()("");e.one("load",(function(){e.off("error abort"),t.resolve(e)})).one("error abort",(function(){e.off("load").detach(),t.reject(e)})).css({display:"none"}).appendTo(document.body).attr("src",o)})).promise()).then((function(t){n.beforeCommand(),"function"==typeof e?e(t):("string"==typeof e&&t.attr("data-filename",e),t.css("width",Math.min(n.$editable.width(),t.width()))),t.show(),n.getLastRange().insertNode(t[0]),n.setLastRange(Et.createFromNodeAfter(t[0]).select()),n.afterCommand()})).fail((function(t){n.context.triggerEvent("image.upload.error",t)}))}},{key:"insertImagesAsDataURL",value:function(t){var e=this;r().each(t,(function(t,o){var n=o.name;e.options.maximumImageFileSize&&e.options.maximumImageFileSize":t),e&&e.length&&(e[0].tagName.toUpperCase()!==t.toUpperCase()&&(e=e.find(t)),e&&e.length)){var o=this.createRange(),n=r()([o.sc,o.ec]).closest(t);n.removeClass();var i=e[0].className||"";i&&n.addClass(i)}}},{key:"formatPara",value:function(){this.formatBlock("P")}},{key:"fontStyling",value:function(t,e){var o=this.getLastRange();if(""!==o){var n=this.style.styleNodes(o);if(this.$editor.find(".note-status-output").html(""),r()(n).css(t,e),o.isCollapsed()){var i=C.head(n);i&&!pt.nodeLength(i)&&(i.innerHTML=pt.ZERO_WIDTH_NBSP_CHAR,Et.createFromNode(i.firstChild).select(),this.setLastRange(),this.$editable.data("bogus",i))}else o.select()}else{var a=r().now();this.$editor.find(".note-status-output").html('
'+this.lang.output.noSelection+"
"),setTimeout((function(){r()("#note-status-output-"+a).remove()}),5e3)}}},{key:"unlink",value:function(){var t=this.getLastRange();if(t.isOnAnchor()){var e=pt.ancestor(t.sc,pt.isAnchor);(t=Et.createFromNode(e)).select(),this.setLastRange(),this.beforeCommand(),document.execCommand("unlink"),this.afterCommand()}}},{key:"getLinkInfo",value:function(){this.hasFocus()||this.focus();var t=this.getLastRange().expand(pt.isAnchor),e=r()(C.head(t.nodes(pt.isAnchor))),o={range:t,text:t.toString(),url:e.length?e.attr("href"):""};return e.length&&(o.isNewWindow="_blank"===e.attr("target")),o}},{key:"addRow",value:function(t){var e=this.getLastRange(this.$editable);e.isCollapsed()&&e.isOnCell()&&(this.beforeCommand(),this.table.addRow(e,t),this.afterCommand())}},{key:"addCol",value:function(t){var e=this.getLastRange(this.$editable);e.isCollapsed()&&e.isOnCell()&&(this.beforeCommand(),this.table.addCol(e,t),this.afterCommand())}},{key:"deleteRow",value:function(){var t=this.getLastRange(this.$editable);t.isCollapsed()&&t.isOnCell()&&(this.beforeCommand(),this.table.deleteRow(t),this.afterCommand())}},{key:"deleteCol",value:function(){var t=this.getLastRange(this.$editable);t.isCollapsed()&&t.isOnCell()&&(this.beforeCommand(),this.table.deleteCol(t),this.afterCommand())}},{key:"deleteTable",value:function(){var t=this.getLastRange(this.$editable);t.isCollapsed()&&t.isOnCell()&&(this.beforeCommand(),this.table.deleteTable(t),this.afterCommand())}},{key:"resizeTo",value:function(t,e,o){var n;if(o){var i=t.y/t.x,r=e.data("ratio");n={width:r>i?t.x:t.y/r,height:r>i?t.x*r:t.y}}else n={width:t.x,height:t.y};e.css(n)}},{key:"hasFocus",value:function(){return this.$editable.is(":focus")}},{key:"focus",value:function(){this.hasFocus()||this.$editable.trigger("focus")}},{key:"isEmpty",value:function(){return pt.isEmpty(this.$editable[0])||pt.emptyPara===this.$editable.html()}},{key:"empty",value:function(){this.context.invoke("code",pt.emptyPara)}},{key:"normalizeContent",value:function(){this.$editable[0].normalize()}}],e&&Xt(t.prototype,e),o&&Xt(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function ne(t){return ne="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},ne(t)}function ie(t,e){for(var o=0;o0&&this.options.allowClipboardImagePasting&&(this.context.invoke("editor.insertImagesOrCallback",n),t.preventDefault()),i.length>0&&this.context.invoke("editor.isLimited",i.length)&&t.preventDefault()}else if(window.clipboardData){var r=window.clipboardData.getData("text");this.context.invoke("editor.isLimited",r.length)&&t.preventDefault()}setTimeout((function(){e.context.invoke("editor.afterCommand")}),10)}}}])&&ie(t.prototype,e),o&&ie(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function se(t){return se="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},se(t)}function le(t,e){for(var o=0;o','
',""].join("")).prependTo(this.$editor)},e=[{key:"initialize",value:function(){this.options.disableDragAndDrop?(this.documentEventHandlers.onDrop=function(t){t.preventDefault()},this.$eventListener=this.$dropzone,this.$eventListener.on("drop",this.documentEventHandlers.onDrop)):this.attachDragAndDropEvent()}},{key:"attachDragAndDropEvent",value:function(){var t=this,e=r()(),o=this.$dropzone.find(".note-dropzone-message");this.documentEventHandlers.onDragenter=function(n){var i=t.context.invoke("codeview.isActivated"),r=t.$editor.width()>0&&t.$editor.height()>0;i||e.length||!r||(t.$editor.addClass("dragover"),t.$dropzone.width(t.$editor.width()),t.$dropzone.height(t.$editor.height()),o.text(t.lang.image.dragImageHere)),e=e.add(n.target)},this.documentEventHandlers.onDragleave=function(o){(e=e.not(o.target)).length&&"BODY"!==o.target.nodeName||(e=r()(),t.$editor.removeClass("dragover"))},this.documentEventHandlers.onDrop=function(){e=r()(),t.$editor.removeClass("dragover")},this.$eventListener.on("dragenter",this.documentEventHandlers.onDragenter).on("dragleave",this.documentEventHandlers.onDragleave).on("drop",this.documentEventHandlers.onDrop),this.$dropzone.on("dragenter",(function(){t.$dropzone.addClass("hover"),o.text(t.lang.image.dropImage)})).on("dragleave",(function(){t.$dropzone.removeClass("hover"),o.text(t.lang.image.dragImageHere)})),this.$dropzone.on("drop",(function(e){var o=e.originalEvent.dataTransfer;e.preventDefault(),o&&o.files&&o.files.length?(t.$editable.trigger("focus"),t.context.invoke("editor.insertImagesOrCallback",o.files)):r().each(o.types,(function(e,n){if(!(n.toLowerCase().indexOf("_moz_")>-1)){var i=o.getData(n);n.toLowerCase().indexOf("text")>-1?t.context.invoke("editor.pasteHTML",i):r()(i).each((function(e,o){t.context.invoke("editor.insertNode",o)}))}}))})).on("dragover",!1)}},{key:"destroy",value:function(){var t=this;Object.keys(this.documentEventHandlers).forEach((function(e){t.$eventListener.off(e.slice(2).toLowerCase(),t.documentEventHandlers[e])})),this.documentEventHandlers={}}}],e&&le(t.prototype,e),o&&le(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function de(t){return de="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},de(t)}function fe(t,e){var o="undefined"!=typeof Symbol&&t[Symbol.iterator]||t["@@iterator"];if(!o){if(Array.isArray(t)||(o=function(t,e){if(t){if("string"==typeof t)return he(t,e);var o={}.toString.call(t).slice(8,-1);return"Object"===o&&t.constructor&&(o=t.constructor.name),"Map"===o||"Set"===o?Array.from(t):"Arguments"===o||/^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(o)?he(t,e):void 0}}(t))||e&&t&&"number"==typeof t.length){o&&(t=o);var n=0,i=function(){};return{s:i,n:function(){return n>=t.length?{done:!0}:{done:!1,value:t[n++]}},e:function(t){throw t},f:i}}throw new TypeError("Invalid attempt to iterate non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method.")}var r,a=!0,s=!1;return{s:function(){o=o.call(t)},n:function(){var t=o.next();return a=t.done,t},e:function(t){s=!0,r=t},f:function(){try{a||null==o.return||o.return()}finally{if(s)throw r}}}}function he(t,e){(null==e||e>t.length)&&(e=t.length);for(var o=0,n=Array(e);o.*?(?:<\/iframe>)?)/gi,(function(t){if(/<.+src(?==?('|"|\s)?)[\s\S]+src(?=('|"|\s)?)[^>]*?>/i.test(t))return"";var o,n=fe(e);try{for(n.s();!(o=n.n()).done;){var i=o.value;if(new RegExp('src="(https?:)?//'+i.replace(/[-\/\\^$*+?.()|[\]{}]/g,"\\$&")+'/(.+)"').test(t))return t}}catch(t){n.e(t)}finally{n.f()}return""}))}return t}},{key:"activate",value:function(){var t=this,e=this.CodeMirrorConstructor;if(this.$codable.val(pt.html(this.$editable,this.options.prettifyHtml)),this.$codable.height(this.$editable.height()),this.context.invoke("toolbar.updateCodeview",!0),this.context.invoke("airPopover.updateCodeview",!0),this.$editor.addClass("codeview"),this.$codable.trigger("focus"),e){var o=e.fromTextArea(this.$codable[0],this.options.codemirror);if(this.options.codemirror.tern){var n=new e.TernServer(this.options.codemirror.tern);o.ternServer=n,o.on("cursorActivity",(function(t){n.updateArgHints(t)}))}o.on("blur",(function(e){t.context.triggerEvent("blur.codeview",o.getValue(),e)})),o.on("change",(function(){t.context.triggerEvent("change.codeview",o.getValue(),o)})),o.setSize(null,this.$editable.outerHeight()),this.$codable.data("cmEditor",o)}else this.$codable.on("blur",(function(e){t.context.triggerEvent("blur.codeview",t.$codable.val(),e)})),this.$codable.on("input",(function(){t.context.triggerEvent("change.codeview",t.$codable.val(),t.$codable)}))}},{key:"deactivate",value:function(){if(this.CodeMirrorConstructor){var t=this.$codable.data("cmEditor");this.$codable.val(t.getValue()),t.toTextArea()}var e=this.purify(pt.value(this.$codable,this.options.prettifyHtml)||pt.emptyPara),o=this.$editable.html()!==e;this.$editable.html(e),this.$editable.height(this.options.height?this.$codable.height():"auto"),this.$editor.removeClass("codeview"),o&&this.context.triggerEvent("change",this.$editable.html(),this.$editable),this.$editable.trigger("focus"),this.context.invoke("toolbar.updateCodeview",!1),this.context.invoke("airPopover.updateCodeview",!1)}},{key:"destroy",value:function(){this.isActivated()&&this.deactivate()}}],e&&pe(t.prototype,e),o&&pe(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function ge(t){return ge="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},ge(t)}function be(t,e){for(var o=0;o0?Math.max(r,t.options.minheight):r,r=t.options.maxHeight>0?Math.min(r,t.options.maxHeight):r,a=t.options.minheight>0?Math.max(a,t.options.minheight):a,a=t.options.maxHeight>0?Math.min(a,t.options.maxHeight):a,t.$editable.height(r),t.$codable.height(a)};t.$document.on("mousemove touchmove",i).one("mouseup touchend",(function(){t.$document.off("mousemove touchmove",i)}))}))}},{key:"destroy",value:function(){this.$statusbar.off(),this.$statusbar.addClass("locked")}}])&&be(t.prototype,e),o&&be(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function we(t){return we="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},we(t)}function Ce(t,e){for(var o=0;o','
','
','
','
','
','
',this.options.disableResizeImage?"":'
',"
",""].join("")).prependTo(this.$editingArea),this.$handle.on("mousedown",(function(e){if(pt.isControlSizing(e.target)){e.preventDefault(),e.stopPropagation();var o=t.$handle.find(".note-control-selection").data("target"),n=o.offset(),i=t.$document.scrollTop(),r=function(e){t.context.invoke("editor.resizeTo",{x:e.clientX-n.left,y:e.clientY-(n.top-i)},o,!e.shiftKey),t.update(o[0],e)};t.$document.on("mousemove",r).one("mouseup",(function(e){e.preventDefault(),t.$document.off("mousemove",r),t.context.invoke("editor.afterCommand")})),o.data("ratio")||o.data("ratio",o.height()/o.width())}})),this.$handle.on("wheel",(function(e){e.preventDefault(),t.update()}))}},{key:"destroy",value:function(){this.$handle.remove()}},{key:"update",value:function(t,e){if(this.context.isDisabled())return!1;var o=pt.isImg(t),n=this.$handle.find(".note-control-selection");if(this.context.invoke("imagePopover.update",t,e),o){var i=r()(t),a=this.$editingArea[0].getBoundingClientRect(),s=t.getBoundingClientRect();n.css({display:"block",left:s.left-a.left,top:s.top-a.top,width:s.width,height:s.height}).data("target",i);var l=new Image;l.src=i.attr("src");var c=s.width+"x"+s.height+" ("+this.lang.image.original+": "+l.width+"x"+l.height+")";n.find(".note-control-selection-info").text(c),this.context.invoke("editor.saveTarget",t)}else this.hide();return o}},{key:"hide",value:function(){this.context.invoke("editor.clearTarget"),this.$handle.children().hide()}}],e&&Ee(t.prototype,e),o&&Ee(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Ie(t){return Ie="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Ie(t)}function $e(t,e){for(var o=0;o").html(n).attr("href",o)[0];this.context.options.linkTargetBlank&&r()(i).attr("target","_blank"),this.lastWordRange.insertNode(i),this.lastWordRange=null,this.context.invoke("editor.focus"),this.context.triggerEvent("change",this.$editable.html(),this.$editable)}}}},{key:"handleKeydown",value:function(t){if(C.contains([Nt.code.ENTER,Nt.code.SPACE],t.keyCode)){var e=this.context.invoke("editor.createRange").getWordRange();this.lastWordRange=e}}},{key:"handleKeyup",value:function(t){(Nt.code.SPACE===t.keyCode||Nt.code.ENTER===t.keyCode&&!t.shiftKey)&&this.replace()}}])&&$e(t.prototype,e),o&&$e(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Fe(t){return Fe="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Fe(t)}function De(t,e){for(var o=0;o'),this.$placeholder.on("click",(function(){t.context.invoke("focus")})).html(this.options.placeholder).prependTo(this.$editingArea),this.update()}},{key:"destroy",value:function(){this.$placeholder.remove()}},{key:"update",value:function(){var t=!this.context.invoke("codeview.isActivated")&&this.context.invoke("editor.isEmpty");this.$placeholder.toggle(t)}}])&&We(t.prototype,e),o&&We(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function Ve(t){return Ve="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},Ve(t)}function _e(t,e){for(var o=0;o','
'+this.lang.color.background+"
","
",'","
",'
\x3c!-- back colors --\x3e
',"
",'",'',"
",'
',""].join(""):"")+(n?['
','
'+this.lang.color.foreground+"
","
",'","
",'
\x3c!-- fore colors --\x3e
',"
",'",'',"
",'
',"
"].join(""):""),callback:function(t){t.find(".note-holder").each((function(t,e){var o=r()(e);o.append(i.ui.palette({colors:i.options.colors,colorsName:i.options.colorsName,eventName:o.data("event"),container:i.options.container,tooltip:i.options.tooltip}).render())}));var e=[["#FFFFFF","#FFFFFF","#FFFFFF","#FFFFFF","#FFFFFF","#FFFFFF","#FFFFFF","#FFFFFF"]];t.find(".note-holder-custom").each((function(t,o){var n=r()(o);n.append(i.ui.palette({colors:e,colorsName:e,eventName:n.data("event"),container:i.options.container,tooltip:i.options.tooltip}).render())})),t.find("input[type=color]").each((function(e,o){r()(o).on("change",(function(){var e=t.find("#"+r()(this).data("event")).find(".note-color-btn").first(),o=this.value.toUpperCase();e.css("background-color",o).attr("aria-label",o).attr("data-value",o).attr("data-original-title",o),e.trigger("click")}))}))},click:function(e){e.stopPropagation();var o=r()("."+t).find(".note-dropdown-menu"),n=r()(e.target),a=n.data("event"),s=n.attr("data-value");if("openPalette"===a){var l=o.find("#"+s),c=r()(o.find("#"+l.data("event")).find(".note-color-row")[0]),u=c.find(".note-color-btn").last().detach(),d=l.val();u.css("background-color",d).attr("aria-label",d).attr("data-value",d).attr("data-original-title",d),c.prepend(u),l.trigger("click")}else{if(C.contains(["backColor","foreColor"],a)){var f="backColor"===a?"background-color":"color",h=n.closest(".note-color").find(".note-recent-color"),p=n.closest(".note-color").find(".note-current-color-button");h.css(f,s),p.attr("data-"+a,s)}i.context.invoke("editor."+a,s)}}})]}).render()}},{key:"addToolbarButtons",value:function(){var t=this;this.context.memo("button.style",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents(t.ui.icon(t.options.icons.magic),t.options),tooltip:t.lang.style.style,data:{toggle:"dropdown"}}),t.ui.dropdown({className:"dropdown-style",items:t.options.styleTags,title:t.lang.style.style,template:function(e){"string"==typeof e&&(e={tag:e,title:Object.prototype.hasOwnProperty.call(t.lang.style,e)?t.lang.style[e]:e});var o=e.tag,n=e.title;return"<"+o+(e.style?' style="'+e.style+'" ':"")+(e.className?' class="'+e.className+'"':"")+">"+n+""},click:t.context.createInvokeHandler("editor.formatBlock")})]).render()}));for(var e=function(){var e=t.options.styleTags[o];t.context.memo("button.style."+e,(function(){return t.button({className:"note-btn-style-"+e,contents:'
'+e.toUpperCase()+"
",tooltip:t.lang.style[e],click:t.context.createInvokeHandler("editor.formatBlock")}).render()}))},o=0,n=this.options.styleTags.length;o',t.options),tooltip:t.lang.font.name,data:{toggle:"dropdown"}}),t.ui.dropdownCheck({className:"dropdown-fontname",checkClassName:t.options.icons.menuCheck,items:t.options.fontNames.filter(t.isFontInstalled.bind(t)),title:t.lang.font.name,template:function(t){return''+t+""},click:t.context.createInvokeHandlerAndUpdateState("editor.fontName")})]).render()})),this.context.memo("button.fontsize",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents('',t.options),tooltip:t.lang.font.size,data:{toggle:"dropdown"}}),t.ui.dropdownCheck({className:"dropdown-fontsize",checkClassName:t.options.icons.menuCheck,items:t.options.fontSizes,title:t.lang.font.size,click:t.context.createInvokeHandlerAndUpdateState("editor.fontSize")})]).render()})),this.context.memo("button.fontsizeunit",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents('',t.options),tooltip:t.lang.font.sizeunit,data:{toggle:"dropdown"}}),t.ui.dropdownCheck({className:"dropdown-fontsizeunit",checkClassName:t.options.icons.menuCheck,items:t.options.fontSizeUnits,title:t.lang.font.sizeunit,click:t.context.createInvokeHandlerAndUpdateState("editor.fontSizeUnit")})]).render()})),this.context.memo("button.color",(function(){return t.colorPalette("note-color-all",t.lang.color.recent,!0,!0)})),this.context.memo("button.forecolor",(function(){return t.colorPalette("note-color-fore",t.lang.color.foreground,!1,!0)})),this.context.memo("button.backcolor",(function(){return t.colorPalette("note-color-back",t.lang.color.background,!0,!1)})),this.context.memo("button.ul",(function(){return t.button({contents:t.ui.icon(t.options.icons.unorderedlist),tooltip:t.lang.lists.unordered+t.representShortcut("insertUnorderedList"),click:t.context.createInvokeHandler("editor.insertUnorderedList")}).render()})),this.context.memo("button.ol",(function(){return t.button({contents:t.ui.icon(t.options.icons.orderedlist),tooltip:t.lang.lists.ordered+t.representShortcut("insertOrderedList"),click:t.context.createInvokeHandler("editor.insertOrderedList")}).render()}));var i=this.button({contents:this.ui.icon(this.options.icons.alignLeft),tooltip:this.lang.paragraph.left+this.representShortcut("justifyLeft"),click:this.context.createInvokeHandler("editor.justifyLeft")}),a=this.button({contents:this.ui.icon(this.options.icons.alignCenter),tooltip:this.lang.paragraph.center+this.representShortcut("justifyCenter"),click:this.context.createInvokeHandler("editor.justifyCenter")}),s=this.button({contents:this.ui.icon(this.options.icons.alignRight),tooltip:this.lang.paragraph.right+this.representShortcut("justifyRight"),click:this.context.createInvokeHandler("editor.justifyRight")}),l=this.button({contents:this.ui.icon(this.options.icons.alignJustify),tooltip:this.lang.paragraph.justify+this.representShortcut("justifyFull"),click:this.context.createInvokeHandler("editor.justifyFull")}),c=this.button({contents:this.ui.icon(this.options.icons.outdent),tooltip:this.lang.paragraph.outdent+this.representShortcut("outdent"),click:this.context.createInvokeHandler("editor.outdent")}),u=this.button({contents:this.ui.icon(this.options.icons.indent),tooltip:this.lang.paragraph.indent+this.representShortcut("indent"),click:this.context.createInvokeHandler("editor.indent")});this.context.memo("button.justifyLeft",g.invoke(i,"render")),this.context.memo("button.justifyCenter",g.invoke(a,"render")),this.context.memo("button.justifyRight",g.invoke(s,"render")),this.context.memo("button.justifyFull",g.invoke(l,"render")),this.context.memo("button.outdent",g.invoke(c,"render")),this.context.memo("button.indent",g.invoke(u,"render")),this.context.memo("button.paragraph",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents(t.ui.icon(t.options.icons.alignLeft),t.options),tooltip:t.lang.paragraph.paragraph,data:{toggle:"dropdown"}}),t.ui.dropdown([t.ui.buttonGroup({className:"note-align",children:[i,a,s,l]}),t.ui.buttonGroup({className:"note-list",children:[c,u]})])]).render()})),this.context.memo("button.height",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents(t.ui.icon(t.options.icons.textHeight),t.options),tooltip:t.lang.font.height,data:{toggle:"dropdown"}}),t.ui.dropdownCheck({items:t.options.lineHeights,checkClassName:t.options.icons.menuCheck,className:"dropdown-line-height",title:t.lang.font.height,click:t.context.createInvokeHandler("editor.lineHeight")})]).render()})),this.context.memo("button.table",(function(){return t.ui.buttonGroup([t.button({className:"dropdown-toggle",contents:t.ui.dropdownButtonContents(t.ui.icon(t.options.icons.table),t.options),tooltip:t.lang.table.table,data:{toggle:"dropdown"}}),t.ui.dropdown({title:t.lang.table.table,className:"note-table",items:['
','
','
','
',"
",'
1 x 1
'].join("")})],{callback:function(e){e.find(".note-dimension-picker-mousecatcher").css({width:t.options.insertTableMaxSize.col+"em",height:t.options.insertTableMaxSize.row+"em"}).on("mousedown",t.context.createInvokeHandler("editor.insertTable")).on("mousemove",t.tableMoveHandler.bind(t))}}).render()})),this.context.memo("button.link",(function(){return t.button({contents:t.ui.icon(t.options.icons.link),tooltip:t.lang.link.link+t.representShortcut("linkDialog.show"),click:t.context.createInvokeHandler("linkDialog.show")}).render()})),this.context.memo("button.picture",(function(){return t.button({contents:t.ui.icon(t.options.icons.picture),tooltip:t.lang.image.image,click:t.context.createInvokeHandler("imageDialog.show")}).render()})),this.context.memo("button.video",(function(){return t.button({contents:t.ui.icon(t.options.icons.video),tooltip:t.lang.video.video,click:t.context.createInvokeHandler("videoDialog.show")}).render()})),this.context.memo("button.hr",(function(){return t.button({contents:t.ui.icon(t.options.icons.minus),tooltip:t.lang.hr.insert+t.representShortcut("insertHorizontalRule"),click:t.context.createInvokeHandler("editor.insertHorizontalRule")}).render()})),this.context.memo("button.fullscreen",(function(){return t.button({className:"btn-fullscreen note-codeview-keep",contents:t.ui.icon(t.options.icons.arrowsAlt),tooltip:t.lang.options.fullscreen,click:t.context.createInvokeHandler("fullscreen.toggle")}).render()})),this.context.memo("button.codeview",(function(){return t.button({className:"btn-codeview note-codeview-keep",contents:t.ui.icon(t.options.icons.code),tooltip:t.lang.options.codeview,click:t.context.createInvokeHandler("codeview.toggle")}).render()})),this.context.memo("button.redo",(function(){return t.button({contents:t.ui.icon(t.options.icons.redo),tooltip:t.lang.history.redo+t.representShortcut("redo"),click:t.context.createInvokeHandler("editor.redo")}).render()})),this.context.memo("button.undo",(function(){return t.button({contents:t.ui.icon(t.options.icons.undo),tooltip:t.lang.history.undo+t.representShortcut("undo"),click:t.context.createInvokeHandler("editor.undo")}).render()})),this.context.memo("button.help",(function(){return t.button({contents:t.ui.icon(t.options.icons.question),tooltip:t.lang.options.help,click:t.context.createInvokeHandler("helpDialog.show")}).render()}))}},{key:"addImagePopoverButtons",value:function(){var t=this;this.context.memo("button.resizeFull",(function(){return t.button({contents:'100%',tooltip:t.lang.image.resizeFull,click:t.context.createInvokeHandler("editor.resize","1")}).render()})),this.context.memo("button.resizeHalf",(function(){return t.button({contents:'50%',tooltip:t.lang.image.resizeHalf,click:t.context.createInvokeHandler("editor.resize","0.5")}).render()})),this.context.memo("button.resizeQuarter",(function(){return t.button({contents:'25%',tooltip:t.lang.image.resizeQuarter,click:t.context.createInvokeHandler("editor.resize","0.25")}).render()})),this.context.memo("button.resizeNone",(function(){return t.button({contents:t.ui.icon(t.options.icons.rollback),tooltip:t.lang.image.resizeNone,click:t.context.createInvokeHandler("editor.resize","0")}).render()})),this.context.memo("button.floatLeft",(function(){return t.button({contents:t.ui.icon(t.options.icons.floatLeft),tooltip:t.lang.image.floatLeft,click:t.context.createInvokeHandler("editor.floatMe","left")}).render()})),this.context.memo("button.floatRight",(function(){return t.button({contents:t.ui.icon(t.options.icons.floatRight),tooltip:t.lang.image.floatRight,click:t.context.createInvokeHandler("editor.floatMe","right")}).render()})),this.context.memo("button.floatNone",(function(){return t.button({contents:t.ui.icon(t.options.icons.rollback),tooltip:t.lang.image.floatNone,click:t.context.createInvokeHandler("editor.floatMe","none")}).render()})),this.context.memo("button.removeMedia",(function(){return t.button({contents:t.ui.icon(t.options.icons.trash),tooltip:t.lang.image.remove,click:t.context.createInvokeHandler("editor.removeMedia")}).render()}))}},{key:"addLinkPopoverButtons",value:function(){var t=this;this.context.memo("button.linkDialogShow",(function(){return t.button({contents:t.ui.icon(t.options.icons.link),tooltip:t.lang.link.edit,click:t.context.createInvokeHandler("linkDialog.show")}).render()})),this.context.memo("button.unlink",(function(){return t.button({contents:t.ui.icon(t.options.icons.unlink),tooltip:t.lang.link.unlink,click:t.context.createInvokeHandler("editor.unlink")}).render()}))}},{key:"addTablePopoverButtons",value:function(){var t=this;this.context.memo("button.addRowUp",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.rowAbove),tooltip:t.lang.table.addRowAbove,click:t.context.createInvokeHandler("editor.addRow","top")}).render()})),this.context.memo("button.addRowDown",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.rowBelow),tooltip:t.lang.table.addRowBelow,click:t.context.createInvokeHandler("editor.addRow","bottom")}).render()})),this.context.memo("button.addColLeft",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.colBefore),tooltip:t.lang.table.addColLeft,click:t.context.createInvokeHandler("editor.addCol","left")}).render()})),this.context.memo("button.addColRight",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.colAfter),tooltip:t.lang.table.addColRight,click:t.context.createInvokeHandler("editor.addCol","right")}).render()})),this.context.memo("button.deleteRow",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.rowRemove),tooltip:t.lang.table.delRow,click:t.context.createInvokeHandler("editor.deleteRow")}).render()})),this.context.memo("button.deleteCol",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.colRemove),tooltip:t.lang.table.delCol,click:t.context.createInvokeHandler("editor.deleteCol")}).render()})),this.context.memo("button.deleteTable",(function(){return t.button({className:"btn-md",contents:t.ui.icon(t.options.icons.trash),tooltip:t.lang.table.delTable,click:t.context.createInvokeHandler("editor.deleteTable")}).render()}))}},{key:"build",value:function(t,e){for(var o=0,n=e.length;o3&&c3&&ul&&ac)&&(this.isFollowing=!1,this.$toolbar.css({position:"relative",top:0,width:"100%",zIndex:"auto"}),this.$editable.css({marginTop:""}))}},{key:"changeContainer",value:function(t){t?this.$toolbar.prependTo(this.$editor):this.options.toolbarContainer&&this.$toolbar.appendTo(this.options.toolbarContainer),this.options.followingToolbar&&this.followScroll()}},{key:"updateFullscreen",value:function(t){this.ui.toggleBtnActive(this.$toolbar.find(".btn-fullscreen"),t),this.changeContainer(t)}},{key:"updateCodeview",value:function(t){this.ui.toggleBtnActive(this.$toolbar.find(".btn-codeview"),t),t?this.deactivate():this.activate()}},{key:"activate",value:function(t){var e=this.$toolbar.find("button");t||(e=e.not(".note-codeview-keep")),this.ui.toggleBtn(e,!0)}},{key:"deactivate",value:function(t){var e=this.$toolbar.find("button");t||(e=e.not(".note-codeview-keep")),this.ui.toggleBtn(e,!1)}}])&&Xe(t.prototype,e),o&&Xe(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function to(t){return to="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},to(t)}function eo(t,e){for(var o=0;o','"),''),"",'
','"),''),"
",this.options.disableLinkTarget?"":r()("
").append(this.ui.checkbox({className:"sn-checkbox-open-in-new-window",text:this.lang.link.openInNewWindow,checked:!0}).render()).html()].join(""),o='');this.$dialog=this.ui.dialog({className:"link-dialog",title:this.lang.link.insert,fade:this.options.dialogsFade,body:e,footer:o}).render().appendTo(t)}},{key:"destroy",value:function(){this.ui.hideDialog(this.$dialog),this.$dialog.remove()}},{key:"bindEnterKey",value:function(t,e){t.on("keypress",(function(t){t.keyCode===Nt.code.ENTER&&(t.preventDefault(),e.trigger("click"))}))}},{key:"checkLinkUrl",value:function(t){return no.test(t)?"mailto://"+t:io.test(t)?"tel://"+t:ro.test(t)?t:"http://"+t}},{key:"onCheckLinkUrl",value:function(t){var e=this;t.on("blur",(function(t){t.target.value=""==t.target.value?"":e.checkLinkUrl(t.target.value)}))}},{key:"toggleLinkBtn",value:function(t,e,o){this.ui.toggleBtn(t,e.val()&&o.val())}},{key:"showLinkDialog",value:function(t){var e=this;return r().Deferred((function(o){var n=e.$dialog.find(".note-link-text"),i=e.$dialog.find(".note-link-url"),r=e.$dialog.find(".note-link-btn"),a=e.$dialog.find(".sn-checkbox-open-in-new-window input[type=checkbox]");e.ui.onDialogShown(e.$dialog,(function(){e.context.triggerEvent("dialog.shown"),!t.url&&g.isValidUrl(t.text)&&(t.url=e.checkLinkUrl(t.text)),n.on("input paste propertychange",(function(){var o=n.val(),a=document.createElement("div");a.innerText=o,o=a.innerHTML,t.text=o,e.toggleLinkBtn(r,n,i)})).val(t.text),i.on("input paste propertychange",(function(){t.text||n.val(i.val()),e.toggleLinkBtn(r,n,i)})).val(t.url),m.isSupportTouch||i.trigger("focus"),e.toggleLinkBtn(r,n,i),e.bindEnterKey(i,r),e.bindEnterKey(n,r),e.onCheckLinkUrl(i);var s=void 0!==t.isNewWindow?t.isNewWindow:e.context.options.linkTargetBlank;a.prop("checked",s),r.one("click",(function(r){r.preventDefault(),o.resolve({range:t.range,url:i.val(),text:n.val(),isNewWindow:a.is(":checked")}),e.ui.hideDialog(e.$dialog)}))})),e.ui.onDialogHidden(e.$dialog,(function(){n.off(),i.off(),r.off(),"pending"===o.state()&&o.reject()})),e.ui.showDialog(e.$dialog)})).promise()}},{key:"show",value:function(){var t=this,e=this.context.invoke("editor.getLinkInfo");this.context.invoke("editor.saveRange"),this.showLinkDialog(e).then((function(e){t.context.invoke("editor.restoreRange"),t.context.invoke("editor.createLink",e)})).fail((function(){t.context.invoke("editor.restoreRange")}))}}])&&eo(t.prototype,e),o&&eo(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function so(t){return so="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},so(t)}function lo(t,e){for(var o=0;o ')}}).render().appendTo(this.options.container);var t=this.$popover.find(".popover-content,.note-popover-content");this.context.invoke("buttons.build",t,this.options.popover.link),this.$popover.on("mousedown",(function(t){t.preventDefault()}))}},{key:"destroy",value:function(){this.$popover.remove()}},{key:"update",value:function(){if(this.context.invoke("editor.hasFocus")){var t=this.context.invoke("editor.getLastRange");if(t.isCollapsed()&&t.isOnAnchor()){var e=pt.ancestor(t.sc,pt.isAnchor),o=r()(e).attr("href");this.$popover.find("a").attr("href",o).text(o);var n=pt.posFromPlaceholder(e),i=r()(this.options.container).offset();n.top-=i.top,n.left-=i.left,this.$popover.css({display:"block",left:n.left,top:n.top})}else this.hide()}else this.hide()}},{key:"hide",value:function(){this.$popover.hide()}}])&&lo(t.prototype,e),o&&lo(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function fo(t){return fo="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},fo(t)}function ho(t,e){for(var o=0;o")}var n=this.options.dialogsInBody?this.$body:this.options.container,i=['
','",'',t,"
",'
','",'',"
"].join(""),r='');this.$dialog=this.ui.dialog({title:this.lang.image.insert,fade:this.options.dialogsFade,body:i,footer:r}).render().appendTo(n)}},{key:"destroy",value:function(){this.ui.hideDialog(this.$dialog),this.$dialog.remove()}},{key:"bindEnterKey",value:function(t,e){t.on("keypress",(function(t){t.keyCode===Nt.code.ENTER&&(t.preventDefault(),e.trigger("click"))}))}},{key:"show",value:function(){var t=this;this.context.invoke("editor.saveRange"),this.showImageDialog().then((function(e){t.ui.hideDialog(t.$dialog),t.context.invoke("editor.restoreRange"),"string"==typeof e?t.options.callbacks.onImageLinkInsert?t.context.triggerEvent("image.link.insert",e):t.context.invoke("editor.insertImage",e):t.context.invoke("editor.insertImagesOrCallback",e)})).fail((function(){t.context.invoke("editor.restoreRange")}))}},{key:"showImageDialog",value:function(){var t=this;return r().Deferred((function(e){var o=t.$dialog.find(".note-image-input"),n=t.$dialog.find(".note-image-url"),i=t.$dialog.find(".note-image-btn");t.ui.onDialogShown(t.$dialog,(function(){t.context.triggerEvent("dialog.shown"),o.replaceWith(o.clone().on("change",(function(t){e.resolve(t.target.files||t.target.value)})).val("")),n.on("input paste propertychange",(function(){t.ui.toggleBtn(i,n.val())})).val(""),m.isSupportTouch||n.trigger("focus"),i.on("click",(function(t){t.preventDefault(),e.resolve(n.val())})),t.bindEnterKey(n,i)})),t.ui.onDialogHidden(t.$dialog,(function(){o.off(),n.off(),i.off(),"pending"===e.state()&&e.reject()})),t.ui.showDialog(t.$dialog)}))}}])&&ho(t.prototype,e),o&&ho(t,o),Object.defineProperty(t,"prototype",{writable:!1}),t;var t,e,o}();function vo(t){return vo="function"==typeof Symbol&&"symbol"==typeof Symbol.iterator?function(t){return typeof t}:function(t){return t&&"function"==typeof Symbol&&t.constructor===Symbol&&t!==Symbol.prototype?"symbol":typeof t},vo(t)}function go(t,e){for(var o=0;o','"),''),""].join(""),o='');this.$dialog=this.ui.dialog({title:this.lang.video.insert,fade:this.options.dialogsFade,body:e,footer:o}).render().appendTo(t)}},{key:"destroy",value:function(){this.ui.hideDialog(this.$dialog),this.$dialog.remove()}},{key:"bindEnterKey",value:function(t,e){t.on("keypress",(function(t){t.keyCode===Nt.code.ENTER&&(t.preventDefault(),e.trigger("click"))}))}},{key:"createVideoNode",value:function(t){var e,o=t.match(/(?:youtu\.be\/|youtube\.com\/(?:[^\/\n\s]+\/\S+\/|(?:v|e(?:mbed)?)\/|\S*?[?&]v=|shorts\/|live\/))([^&\n?]+)(?:.*[?&]t=([^&\n]+))?.*/),n=t.match(/(?:\.|\/\/)drive\.google\.com\/file\/d\/(.[a-zA-Z0-9_-]*)\/view/),i=t.match(/(?:www\.|\/\/)instagram\.com\/(reel|p)\/(.[a-zA-Z0-9_-]*)/),a=t.match(/\/\/vine\.co\/v\/([a-zA-Z0-9]+)/),s=t.match(/\/\/(player\.)?vimeo\.com\/([a-z]*\/)*(\d+)[?]?.*/),l=t.match(/.+dailymotion.com\/(video|hub)\/([^_]+)[^#]*(#video=([^_&]+))?/),c=t.match(/\/\/v\.youku\.com\/v_show\/id_(\w+)=*\.html/),u=t.match(/\/\/(.*)\/videos\/watch\/([^?]*)(?:\?(?:start=(\w*))?(?:&stop=(\w*))?(?:&loop=([10]))?(?:&autoplay=([10]))?(?:&muted=([10]))?)?/),d=t.match(/\/\/v\.qq\.com.*?vid=(.+)/),f=t.match(/\/\/v\.qq\.com\/x?\/?(page|cover).*?\/([^\/]+)\.html\??.*/),h=t.match(/^.+.(mp4|m4v)$/),p=t.match(/^.+.(ogg|ogv)$/),m=t.match(/^.+.(webm)$/),v=t.match(/(?:www\.|\/\/)facebook\.com\/([^\/]+)\/videos\/([0-9]+)/);if(o&&11===o[1].length){var g=o[1],b=0;if(void 0!==o[2]){var y=o[2].match(/^(?:(\d+)h)?(?:(\d+)m)?(?:(\d+)s)?$/);if(y)for(var k=[3600,60,1],w=0,C=k.length;w").attr("frameborder",0).attr("src","//www.youtube.com/embed/"+g+(b>0?"?start="+b:"")).attr("width","640").attr("height","360")}else if(n&&n[0].length)e=r()("