/** * Converts the language codes that we get from the client (usually HTTP_ACCEPT_LANGUAGE) * into a TYPO3-readable language code * * @param string $languageCodesList List of language codes. something like 'de,en-us;q=0.9,de-de;q=0.7,es-cl;q=0.6,en;q=0.4,es;q=0.3,zh;q=0.1' * @return string A preferred language that TYPO3 supports, or "default" if none found */ public function getPreferredClientLanguage($languageCodesList) { $allLanguageCodes = array(); $selectedLanguage = 'default'; // Get all languages where TYPO3 code is the same as the ISO code foreach ($this->charSetArray as $typo3Lang => $charSet) { $allLanguageCodes[$typo3Lang] = $typo3Lang; } // Get all languages where TYPO3 code differs from ISO code // or needs the country part // the iso codes will here overwrite the default typo3 language in the key foreach ($this->locales->getIsoMapping() as $typo3Lang => $isoLang) { $isoLang = join('-', explode('_', $isoLang)); $allLanguageCodes[$typo3Lang] = $isoLang; } // Move the iso codes to the (because we're comparing the keys with "isset" later on) $allLanguageCodes = array_flip($allLanguageCodes); $preferredLanguages = GeneralUtility::trimExplode(',', $languageCodesList); // Order the preferred languages after they key $sortedPreferredLanguages = array(); foreach ($preferredLanguages as $preferredLanguage) { $quality = 1.0; if (strpos($preferredLanguage, ';q=') !== FALSE) { list($preferredLanguage, $quality) = explode(';q=', $preferredLanguage); } $sortedPreferredLanguages[$preferredLanguage] = $quality; } // Loop through the languages, with the highest priority first arsort($sortedPreferredLanguages, SORT_NUMERIC); foreach ($sortedPreferredLanguages as $preferredLanguage => $quality) { if (isset($allLanguageCodes[$preferredLanguage])) { $selectedLanguage = $allLanguageCodes[$preferredLanguage]; break; } // Strip the country code from the end list($preferredLanguage, ) = explode('-', $preferredLanguage); if (isset($allLanguageCodes[$preferredLanguage])) { $selectedLanguage = $allLanguageCodes[$preferredLanguage]; break; } } if (!$selectedLanguage || $selectedLanguage === 'en') { $selectedLanguage = 'default'; } return $selectedLanguage; }
/** * Helper function for render the main JavaScript libraries, * currently: RequireJS, jQuery, ExtJS * * @return string Content with JavaScript libraries */ protected function renderMainJavaScriptLibraries() { $out = ''; // Include RequireJS if ($this->addRequireJs) { // load the paths of the requireJS configuration $out .= GeneralUtility::wrapJS('var require = ' . json_encode($this->requireJsConfig)) . LF; // directly after that, include the require.js file $out .= '<script src="' . $this->processJsFile($this->requireJsPath . 'require.js') . '" type="text/javascript"></script>' . LF; } // Include jQuery Core for each namespace, depending on the version and source if (!empty($this->jQueryVersions)) { foreach ($this->jQueryVersions as $namespace => $jQueryVersion) { $out .= $this->renderJqueryScriptTag($jQueryVersion['version'], $jQueryVersion['source'], $namespace); } } // Include extJS if ($this->addExtJS) { // Use the base adapter all the time $out .= '<script src="' . $this->processJsFile($this->extJsPath . 'adapter/ext-base' . ($this->enableExtJsDebug ? '-debug' : '') . '.js') . '" type="text/javascript"></script>' . LF; $out .= '<script src="' . $this->processJsFile($this->extJsPath . 'ext-all' . ($this->enableExtJsDebug ? '-debug' : '') . '.js') . '" type="text/javascript"></script>' . LF; // Add extJS localization // Load standard ISO mapping and modify for use with ExtJS $localeMap = $this->locales->getIsoMapping(); $localeMap[''] = 'en'; $localeMap['default'] = 'en'; // Greek $localeMap['gr'] = 'el_GR'; // Norwegian Bokmaal $localeMap['no'] = 'no_BO'; // Swedish $localeMap['se'] = 'se_SV'; $extJsLang = isset($localeMap[$this->lang]) ? $localeMap[$this->lang] : $this->lang; $extJsLocaleFile = $this->extJsPath . 'locale/ext-lang-' . $extJsLang . '.js'; if (file_exists(PATH_site . $extJsLocaleFile)) { $out .= '<script src="' . $this->processJsFile($extJsLocaleFile) . '" type="text/javascript" charset="utf-8"></script>' . LF; } // Remove extjs from JScodeLibArray unset($this->jsFiles[$this->extJsPath . 'ext-all.js'], $this->jsFiles[$this->extJsPath . 'ext-all-debug.js']); } $this->loadJavaScriptLanguageStrings(); if (TYPO3_MODE === 'BE') { $this->addAjaxUrlsToInlineSettings(); } $inlineSettings = $this->inlineLanguageLabels ? 'TYPO3.lang = ' . json_encode($this->inlineLanguageLabels) . ';' : ''; $inlineSettings .= $this->inlineSettings ? 'TYPO3.settings = ' . json_encode($this->inlineSettings) . ';' : ''; if ($this->addExtJS) { // Set clear.gif, move it on top, add handler code $code = ''; if (!empty($this->extOnReadyCode)) { foreach ($this->extOnReadyCode as $block) { $code .= $block; } } $clearGifPath = GeneralUtility::getFileAbsFileName('EXT:backend/Resources/Public/Images/clear.gif'); $clearGifPath = htmlspecialchars(PathUtility::getAbsoluteWebPath($clearGifPath)); $out .= $this->inlineJavascriptWrap[0] . ' Ext.ns("TYPO3"); Ext.BLANK_IMAGE_URL = "' . $clearGifPath . '"; Ext.SSL_SECURE_URL = "' . $clearGifPath . '";' . LF . $inlineSettings . 'Ext.onReady(function() {' . $code . ' });' . $this->inlineJavascriptWrap[1]; $this->extOnReadyCode = []; // Include TYPO3.l10n object if (TYPO3_MODE === 'BE') { $out .= '<script src="' . $this->processJsFile('EXT:lang/Resources/Public/JavaScript/Typo3Lang.js') . '" type="text/javascript" charset="utf-8"></script>' . LF; } if ($this->extJScss) { if (isset($GLOBALS['TBE_STYLES']['extJS']['all'])) { $this->addCssLibrary($GLOBALS['TBE_STYLES']['extJS']['all'], 'stylesheet', 'all', '', true); } else { $this->addCssLibrary($this->extJsPath . 'resources/css/ext-all-notheme.css', 'stylesheet', 'all', '', true); } } if ($this->extJStheme) { if (isset($GLOBALS['TBE_STYLES']['extJS']['theme'])) { $this->addCssLibrary($GLOBALS['TBE_STYLES']['extJS']['theme'], 'stylesheet', 'all', '', true); } else { $this->addCssLibrary($this->extJsPath . 'resources/css/xtheme-blue.css', 'stylesheet', 'all', '', true); } } } else { // no extJS loaded, but still inline settings if ($inlineSettings !== '') { // make sure the global TYPO3 is available $inlineSettings = 'var TYPO3 = TYPO3 || {};' . CRLF . $inlineSettings; $out .= $this->inlineJavascriptWrap[0] . $inlineSettings . $this->inlineJavascriptWrap[1]; // Add language module only if also jquery is guaranteed to be there if (TYPO3_MODE === 'BE' && !empty($this->jQueryVersions)) { $this->loadRequireJsModule('TYPO3/CMS/Lang/Lang'); } } } return $out; }
/** * Helper function for render the main JavaScript libraries, * currently: RequireJS, jQuery, PrototypeJS, Scriptaculous, SVG, ExtJs * * @return string Content with JavaScript libraries */ protected function renderMainJavaScriptLibraries() { $out = ''; // Include RequireJS if ($this->addRequireJs) { // load the paths of the requireJS configuration $out .= GeneralUtility::wrapJS('var require = ' . json_encode($this->requireJsConfig)) . LF; // directly after that, include the require.js file $out .= '<script src="' . $this->processJsFile($this->backPath . $this->requireJsPath . 'require.js') . '" type="text/javascript"></script>' . LF; } if ($this->addSvg) { $out .= '<script src="' . $this->processJsFile($this->backPath . $this->svgPath . 'svg.js') . '" data-path="' . $this->backPath . $this->svgPath . '"' . ($this->enableSvgDebug ? ' data-debug="true"' : '') . '></script>' . LF; } // Include jQuery Core for each namespace, depending on the version and source if (!empty($this->jQueryVersions)) { foreach ($this->jQueryVersions as $namespace => $jQueryVersion) { $out .= $this->renderJqueryScriptTag($jQueryVersion['version'], $jQueryVersion['source'], $namespace); } } if ($this->addPrototype) { $out .= '<script src="' . $this->processJsFile($this->backPath . $this->prototypePath . 'prototype.js') . '" type="text/javascript"></script>' . LF; unset($this->jsFiles[$this->backPath . $this->prototypePath . 'prototype.js']); } if ($this->addScriptaculous) { $mods = array(); foreach ($this->addScriptaculousModules as $key => $value) { if ($this->addScriptaculousModules[$key]) { $mods[] = $key; } } // Resolve dependencies if (in_array('dragdrop', $mods) || in_array('controls', $mods)) { $mods = array_merge(array('effects'), $mods); } if (count($mods)) { foreach ($mods as $module) { $out .= '<script src="' . $this->processJsFile($this->backPath . $this->scriptaculousPath . $module . '.js') . '" type="text/javascript"></script>' . LF; unset($this->jsFiles[$this->backPath . $this->scriptaculousPath . $module . '.js']); } } $out .= '<script src="' . $this->processJsFile($this->backPath . $this->scriptaculousPath . 'scriptaculous.js') . '" type="text/javascript"></script>' . LF; unset($this->jsFiles[$this->backPath . $this->scriptaculousPath . 'scriptaculous.js']); } // Include extCore, but only if ExtJS is not included if ($this->addExtCore && !$this->addExtJS) { $out .= '<script src="' . $this->processJsFile($this->backPath . $this->extCorePath . 'ext-core' . ($this->enableExtCoreDebug ? '-debug' : '') . '.js') . '" type="text/javascript"></script>' . LF; unset($this->jsFiles[$this->backPath . $this->extCorePath . 'ext-core' . ($this->enableExtCoreDebug ? '-debug' : '') . '.js']); } // Include extJS if ($this->addExtJS) { // Use the base adapter all the time $out .= '<script src="' . $this->processJsFile($this->backPath . $this->extJsPath . 'adapter/' . ($this->enableExtJsDebug ? str_replace('.js', '-debug.js', $this->extJSadapter) : $this->extJSadapter)) . '" type="text/javascript"></script>' . LF; $out .= '<script src="' . $this->processJsFile($this->backPath . $this->extJsPath . 'ext-all' . ($this->enableExtJsDebug ? '-debug' : '') . '.js') . '" type="text/javascript"></script>' . LF; // Add extJS localization // Load standard ISO mapping and modify for use with ExtJS $localeMap = $this->locales->getIsoMapping(); $localeMap[''] = 'en'; $localeMap['default'] = 'en'; // Greek $localeMap['gr'] = 'el_GR'; // Norwegian Bokmaal $localeMap['no'] = 'no_BO'; // Swedish $localeMap['se'] = 'se_SV'; $extJsLang = isset($localeMap[$this->lang]) ? $localeMap[$this->lang] : $this->lang; // TODO autoconvert file from UTF8 to current BE charset if necessary!!!! $extJsLocaleFile = $this->extJsPath . 'locale/ext-lang-' . $extJsLang . '.js'; if (file_exists(PATH_typo3 . $extJsLocaleFile)) { $out .= '<script src="' . $this->processJsFile($this->backPath . $extJsLocaleFile) . '" type="text/javascript" charset="utf-8"></script>' . LF; } // Remove extjs from JScodeLibArray unset($this->jsFiles[$this->backPath . $this->extJsPath . 'ext-all.js'], $this->jsFiles[$this->backPath . $this->extJsPath . 'ext-all-debug.js']); } if (count($this->inlineLanguageLabelFiles)) { foreach ($this->inlineLanguageLabelFiles as $languageLabelFile) { $this->includeLanguageFileForInline($languageLabelFile['fileRef'], $languageLabelFile['selectionPrefix'], $languageLabelFile['stripFromSelectionName'], $languageLabelFile['$errorMode']); } } $this->inlineLanguageLabelFiles = array(); // Convert labels/settings back to UTF-8 since json_encode() only works with UTF-8: if ($this->getCharSet() !== 'utf-8') { if ($this->inlineLanguageLabels) { $this->csConvObj->convArray($this->inlineLanguageLabels, $this->getCharSet(), 'utf-8'); } if ($this->inlineSettings) { $this->csConvObj->convArray($this->inlineSettings, $this->getCharSet(), 'utf-8'); } } if (TYPO3_MODE === 'BE') { $this->addAjaxUrlsToInlineSettings(); } $inlineSettings = $this->inlineLanguageLabels ? 'TYPO3.lang = ' . json_encode($this->inlineLanguageLabels) . ';' : ''; $inlineSettings .= $this->inlineSettings ? 'TYPO3.settings = ' . json_encode($this->inlineSettings) . ';' : ''; if ($this->addExtCore || $this->addExtJS) { // Set clear.gif, move it on top, add handler code $code = ''; if (count($this->extOnReadyCode)) { foreach ($this->extOnReadyCode as $block) { $code .= $block; } } $out .= $this->inlineJavascriptWrap[0] . ' Ext.ns("TYPO3"); Ext.BLANK_IMAGE_URL = "' . htmlspecialchars(GeneralUtility::locationHeaderUrl($this->backPath . 'gfx/clear.gif')) . '";' . LF . $inlineSettings . 'Ext.onReady(function() {' . ($this->enableExtJSQuickTips ? 'Ext.QuickTips.init();' . LF : '') . $code . ' });' . $this->inlineJavascriptWrap[1]; $this->extOnReadyCode = array(); // Include TYPO3.l10n object if (TYPO3_MODE === 'BE') { $out .= '<script src="' . $this->processJsFile($this->backPath . 'sysext/lang/Resources/Public/JavaScript/Typo3Lang.js') . '" type="text/javascript" charset="utf-8"></script>' . LF; } if ($this->extJScss) { if (isset($GLOBALS['TBE_STYLES']['extJS']['all'])) { $this->addCssLibrary($this->backPath . $GLOBALS['TBE_STYLES']['extJS']['all'], 'stylesheet', 'all', '', TRUE); } else { $this->addCssLibrary($this->backPath . $this->extJsPath . 'resources/css/ext-all-notheme.css', 'stylesheet', 'all', '', TRUE); } } if ($this->extJStheme) { if (isset($GLOBALS['TBE_STYLES']['extJS']['theme'])) { $this->addCssLibrary($this->backPath . $GLOBALS['TBE_STYLES']['extJS']['theme'], 'stylesheet', 'all', '', TRUE); } else { $this->addCssLibrary($this->backPath . $this->extJsPath . 'resources/css/xtheme-blue.css', 'stylesheet', 'all', '', TRUE); } } } else { // no extJS loaded, but still inline settings if ($inlineSettings !== '') { // make sure the global TYPO3 is available $inlineSettings = 'var TYPO3 = TYPO3 || {};' . CRLF . $inlineSettings; $out .= $this->inlineJavascriptWrap[0] . $inlineSettings . $this->inlineJavascriptWrap[1]; } } return $out; }