['name' => 'English', 'native' => 'English'], 'de' => ['name' => 'German', 'native' => 'Deutsch'], 'he' => ['name' => 'Hebrew', 'native' => 'עברית', 'dir' => 'rtl'], 'hi' => ['name' => 'Hindi', 'native' => 'हिन्दी'], 'id' => ['name' => 'Indonesian', 'native' => 'Bahasa Indonesia'], 'it' => ['name' => 'Italian', 'native' => 'Italiano'], 'ar' => ['name' => 'Arabic', 'native' => 'العربية', 'dir' => 'rtl'], 'lg' => ['name' => 'Luganda', 'native' => 'Luganda'], 'ms' => ['name' => 'Malay', 'native' => 'Bahasa Melayu'], 'fil' => ['name' => 'Filipino', 'native' => 'Filipino'], 'pt' => ['name' => 'Portuguese', 'native' => 'Português'], 'fr' => ['name' => 'French', 'native' => 'Français'], 'si' => ['name' => 'Sinhala', 'native' => 'සිංහල'], 'es' => ['name' => 'Spanish', 'native' => 'Español'], 'sw' => ['name' => 'Swahili', 'native' => 'Kiswahili'], 'th' => ['name' => 'Thai', 'native' => 'ไทย'], 'tr' => ['name' => 'Turkish', 'native' => 'Türkçe'], 'vi' => ['name' => 'Vietnamese', 'native' => 'Tiếng Việt'], 'ja' => ['name' => 'Japanese', 'native' => '日本語'], 'zh' => ['name' => 'Simplified Chinese', 'native' => '简体中文'], 'zh-hant' => ['name' => 'Traditional Chinese', 'native' => '繁體中文'], 'ko' => ['name' => 'Korean', 'native' => '한국어'], ]; } function aismart_ui_language_normalize($code) { $code = strtolower(str_replace('_', '-', trim((string) $code))); if ($code === '' || $code === 'all') { return ''; } $aliases = [ 'zh-hans' => 'zh', 'zh-cn' => 'zh', 'zh-sg' => 'zh', 'zh-my' => 'zh', 'zh-hant' => 'zh-hant', 'zh-tw' => 'zh-hant', 'zh-hk' => 'zh-hant', 'zh-mo' => 'zh-hant', 'tl' => 'fil', 'iw' => 'he', 'in' => 'id', ]; if (isset($aliases[$code])) { return $aliases[$code]; } $catalog = aismart_ui_language_catalog(); if (isset($catalog[$code])) { return $code; } $primary = strtok($code, '-'); return isset($catalog[$primary]) ? $primary : ''; } /** * Language chosen by an active multilingual plugin, then the WordPress user language. * In wp-admin, WPML's admin-bar switcher and Polylang's language filter set these values. */ function aismart_ui_language_detect() { if (defined('ICL_SITEPRESS_VERSION')) { $code = aismart_ui_language_normalize(apply_filters('wpml_current_language', null)); if ($code !== '') { return ['code' => $code, 'source' => 'wpml']; } } if (function_exists('pll_current_language')) { $code = aismart_ui_language_normalize(pll_current_language('locale') ?: pll_current_language('slug')); if ($code !== '') { return ['code' => $code, 'source' => 'polylang']; } } $code = aismart_ui_language_normalize(function_exists('get_user_locale') ? get_user_locale() : get_locale()); return ['code' => $code !== '' ? $code : 'en', 'source' => 'wordpress']; } function aismart_ui_language_multilingual_plugin() { if (defined('ICL_SITEPRESS_VERSION')) { return 'WPML'; } return function_exists('pll_current_language') ? 'Polylang' : ''; } function aismart_ui_language_user_allowed() { return is_user_logged_in() && (current_user_can('manage_options') || current_user_can('use_aismart_studio') || current_user_can('aismart_manage_video_studio')); } function aismart_ui_language_preference() { $preference = (string) get_user_meta(get_current_user_id(), AISMART_UI_LANGUAGE_META, true); return isset(aismart_ui_language_catalog()[$preference]) ? $preference : 'auto'; } function aismart_ui_language_state() { $catalog = aismart_ui_language_catalog(); $preference = aismart_ui_language_preference(); $detected = aismart_ui_language_detect(); $code = $preference === 'auto' ? $detected['code'] : $preference; if (!isset($catalog[$code])) { $code = 'en'; } return [ 'code' => $code, 'preference' => $preference, 'detected' => $detected, 'multilingualPlugin' => aismart_ui_language_multilingual_plugin(), 'dir' => $catalog[$code]['dir'] ?? 'ltr', ]; } function aismart_ui_language_bundle_file($code) { return dirname(__DIR__) . '/languages/ui/' . $code . '.json'; } function aismart_ui_language_switch_url($code, $redirect) { return add_query_arg([ 'action' => 'aismart_ui_language', 'lang' => rawurlencode($code), 'redirect_to' => rawurlencode($redirect), '_wpnonce' => wp_create_nonce('aismart_ui_language'), ], admin_url('admin-post.php')); } function aismart_ui_language_is_plugin_screen() { $page = isset($_GET['page']) ? sanitize_key(wp_unslash((string) $_GET['page'])) : ''; return is_admin() && strpos($page, 'aismart') === 0; } function aismart_ui_language_assets() { static $done = false; if ($done || !aismart_ui_language_user_allowed()) { return; } $done = true; $root = dirname(__DIR__); $url = plugin_dir_url($root . '/aismart-token.php'); $state = aismart_ui_language_state(); $file = aismart_ui_language_bundle_file($state['code']); $bundle = $state['code'] !== 'en' && is_readable($file) ? add_query_arg('ver', (string) filemtime($file), $url . 'languages/ui/' . $state['code'] . '.json') : ''; $languages = []; foreach (aismart_ui_language_catalog() as $code => $language) { $languages[] = ['code' => $code, 'name' => $language['name'], 'native' => $language['native']]; } wp_enqueue_style('dashicons'); wp_enqueue_style('aismart-ui-language', $url . 'assets/ui-language.css', [], (string) filemtime($root . '/assets/ui-language.css')); wp_enqueue_script('aismart-ui-language', $url . 'assets/ui-language.js', [], (string) filemtime($root . '/assets/ui-language.js'), false); wp_add_inline_script('aismart-ui-language', 'window.AISmartUiLanguage = ' . wp_json_encode([ 'code' => $state['code'], 'dir' => $state['dir'], 'preference' => $state['preference'], 'detected' => $state['detected'], 'multilingualPlugin' => $state['multilingualPlugin'], 'bundleUrl' => $bundle, 'pluginScreen' => aismart_ui_language_is_plugin_screen(), 'languages' => $languages, 'switchUrl' => add_query_arg([ 'action' => 'aismart_ui_language', '_wpnonce' => wp_create_nonce('aismart_ui_language'), ], admin_url('admin-post.php')), ]) . ';', 'before'); } add_action('admin_enqueue_scripts', 'aismart_ui_language_assets', 5); add_action('wp_enqueue_scripts', 'aismart_ui_language_assets', 5); add_action('elementor/editor/after_enqueue_scripts', 'aismart_ui_language_assets', 5); function aismart_ui_language_admin_bar($admin_bar) { if (!aismart_ui_language_user_allowed() || !is_object($admin_bar)) { return; } $catalog = aismart_ui_language_catalog(); $state = aismart_ui_language_state(); $current = (is_ssl() ? 'https://' : 'http://') . wp_unslash((string) ($_SERVER['HTTP_HOST'] ?? '')) . wp_unslash((string) ($_SERVER['REQUEST_URI'] ?? '/')); $current = esc_url_raw($current); $auto = $state['preference'] === 'auto'; $admin_bar->add_node([ 'id' => 'aismart-ui-language', 'parent' => 'top-secondary', 'title' => 'Studio: ' . esc_html($catalog[$state['code']]['native']) . '' . ($auto ? ' (Auto)' : '') . '', 'href' => false, 'meta' => ['title' => 'AISmart Studio language'], ]); $plugin = $state['multilingualPlugin']; $detected = $catalog[$state['detected']['code']]['native'] ?? 'English'; $admin_bar->add_node([ 'id' => 'aismart-ui-language-auto', 'parent' => 'aismart-ui-language', 'title' => '' . '' . esc_html($plugin !== '' ? 'Auto: follow ' . $plugin : 'Auto: follow WordPress language') . '' . ' (' . esc_html($detected) . ')', 'href' => aismart_ui_language_switch_url('auto', $current), ]); foreach ($catalog as $code => $language) { $selected = !$auto && $state['preference'] === $code; $admin_bar->add_node([ 'id' => 'aismart-ui-language-' . $code, 'parent' => 'aismart-ui-language', 'title' => '' . '' . esc_html($language['native']) . ($language['native'] !== $language['name'] ? ' · ' . esc_html($language['name']) : '') . '', 'href' => aismart_ui_language_switch_url($code, $current), ]); } } add_action('admin_bar_menu', 'aismart_ui_language_admin_bar', 95); function aismart_ui_language_save() { if (!aismart_ui_language_user_allowed()) { wp_die('You are not allowed to change the AISmart Studio language.', 'Forbidden', ['response' => 403]); } check_admin_referer('aismart_ui_language'); $language = strtolower(sanitize_text_field(wp_unslash((string) ($_GET['lang'] ?? '')))); if ($language !== 'auto' && !isset(aismart_ui_language_catalog()[$language])) { wp_die('This language is not available.', 'Invalid language', ['response' => 400]); } if ($language === 'auto') { delete_user_meta(get_current_user_id(), AISMART_UI_LANGUAGE_META); } else { update_user_meta(get_current_user_id(), AISMART_UI_LANGUAGE_META, $language); } wp_safe_redirect(wp_validate_redirect(wp_unslash((string) ($_GET['redirect_to'] ?? '')), admin_url())); exit; } add_action('admin_post_aismart_ui_language', 'aismart_ui_language_save');