Просмотр исходного кода

add optional (since it uses a session cookie) language selection

El RIDO 11 лет назад
Родитель
Сommit
a111357fae
12 измененных файлов с 388 добавлено и 39 удалено
  1. 5 0
      cfg/conf.ini
  2. 5 5
      css/zerobin.css
  3. 1 1
      i18n/de.json
  4. 1 1
      i18n/fr.json
  5. 181 0
      i18n/languages.json
  6. 1 1
      i18n/pl.json
  7. 21 2
      js/zerobin.js
  8. 130 24
      lib/i18n.php
  9. 10 0
      lib/zerobin.php
  10. 12 1
      tpl/bootstrap-compact.html
  11. 12 1
      tpl/bootstrap.html
  12. 9 3
      tpl/page.html

+ 5 - 0
cfg/conf.ini

@@ -43,6 +43,11 @@ template = "bootstrap"
 ; use "1.7" if you are upgrading from a ZeroBin Alpha 0.19 installation
 ; use "1.7" if you are upgrading from a ZeroBin Alpha 0.19 installation
 base64version = "2.1.9"
 base64version = "2.1.9"
 
 
+; by default ZeroBin will guess the visitors language based on the browsers
+; settings. Optionally you can enable the language selection menu, which uses
+; a session cookie to store the choice until the browser is closed.
+languageselection = false
+
 [expire]
 [expire]
 ; expire value that is selected per default
 ; expire value that is selected per default
 ; make sure the value exists in [expire_options]
 ; make sure the value exists in [expire_options]

+ 5 - 5
css/zerobin.css

@@ -126,7 +126,7 @@ h3.title {
 
 
 #copyhint { color: #666; font-size: 0.85em; }
 #copyhint { color: #666; font-size: 0.85em; }
 
 
-button, .button, #expiration, #formatter {
+button, .button {
 	color: #fff;
 	color: #fff;
 	background-color: #323b47;
 	background-color: #323b47;
 	background-repeat: no-repeat;
 	background-repeat: no-repeat;
@@ -134,7 +134,7 @@ button, .button, #expiration, #formatter {
 	padding: 4px 8px;
 	padding: 4px 8px;
 	font-size: 1em;
 	font-size: 1em;
 	margin-right: 5px;
 	margin-right: 5px;
-	display: inline;
+	display: inline-block;
 	background-image: linear-gradient(bottom, #323b47 0, #51606e 100%);
 	background-image: linear-gradient(bottom, #323b47 0, #51606e 100%);
 	background-image: -o-linear-gradient(bottom, #323b47 0, #51606e 100%);
 	background-image: -o-linear-gradient(bottom, #323b47 0, #51606e 100%);
 	background-image: -moz-linear-gradient(bottom, #323b47 0, #51606e 100%);
 	background-image: -moz-linear-gradient(bottom, #323b47 0, #51606e 100%);
@@ -185,7 +185,7 @@ button img {
 	top: 2px;
 	top: 2px;
 }
 }
 
 
-#expiration, #formatter, #rawtextbutton, #burnafterreadingoption, #opendisc { 
+.button { 
 	background-color: #414d5a; 
 	background-color: #414d5a; 
 	padding: 6px 8px;
 	padding: 6px 8px;
 	margin: 0 5px 0 0;
 	margin: 0 5px 0 0;
@@ -193,14 +193,14 @@ button img {
 	bottom: 1px; /* WTF ? Why is this shifted by 1 pixel ? */
 	bottom: 1px; /* WTF ? Why is this shifted by 1 pixel ? */
 }
 }
 
 
-#expiration select, #formatter select {
+.button select {
 	color: #eee;
 	color: #eee;
 	background: transparent;
 	background: transparent;
 	border: none;
 	border: none;
 }
 }
 
 
 
 
-#expiration select option, #formatter select option {
+.button select option {
 	color:#eee;
 	color:#eee;
 	background: #414d5a;
 	background: #414d5a;
 }
 }

+ 1 - 1
i18n/de.json

@@ -130,7 +130,7 @@
     "Markdown": "Markdown",
     "Markdown": "Markdown",
     "Download attachment": "Anhang herunterladen",
     "Download attachment": "Anhang herunterladen",
     "Cloned file attached.": "Kopierte Datei angehängt.",
     "Cloned file attached.": "Kopierte Datei angehängt.",
-    "Attach a file:": "Datei anhängen:",
+    "Attach a file": "Datei anhängen",
     "Remove attachment": "Anhang entfernen",
     "Remove attachment": "Anhang entfernen",
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
         "Dein Browser unterstützt das hochladen von verschlüsselten Dateien nicht. Bitte verwende einen neueren Browser.",
         "Dein Browser unterstützt das hochladen von verschlüsselten Dateien nicht. Bitte verwende einen neueren Browser.",

+ 1 - 1
i18n/fr.json

@@ -139,7 +139,7 @@
     "Markdown": "Markdown",
     "Markdown": "Markdown",
     "Download attachment": "Télécharger la pièce jointe",
     "Download attachment": "Télécharger la pièce jointe",
     "Cloned file attached.": "Cloner le fichier attaché.",
     "Cloned file attached.": "Cloner le fichier attaché.",
-    "Attach a file:": "Attacher un fichier :",
+    "Attach a file": "Attacher un fichier ",
     "Remove attachment": "Enlever l'attachement",
     "Remove attachment": "Enlever l'attachement",
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
         "Votre navigateur ne supporte pas l'envoi de fichiers chiffrés. Merci d'utiliser un navigateur plus récent.",
         "Votre navigateur ne supporte pas l'envoi de fichiers chiffrés. Merci d'utiliser un navigateur plus récent.",

+ 181 - 0
i18n/languages.json

@@ -0,0 +1,181 @@
+{
+    "ab": ["аҧсуа бызшәа", "Abkhaz"],
+    "aa": ["Afaraf", "Afar"],
+    "af": ["Afrikaans", "Afrikaans"],
+    "ak": ["Akan", "Akan"],
+    "sq": ["Shqip", "Albanian"],
+    "am": ["አማርኛ", "Amharic"],
+    "ar": ["العربية", "Arabic"],
+    "an": ["aragonés", "Aragonese"],
+    "hy": ["Հայերեն", "Armenian"],
+    "as": ["অসমীয়া", "Assamese"],
+    "ac": ["Ástralic", "Australian"],
+    "av": ["авар мацӀ", "Avaric"],
+    "ae": ["avesta", "Avestan"],
+    "ay": ["aymar aru", "Aymara"],
+    "az": ["azərbaycan dili", "Azerbaijani"],
+    "bm": ["bamanankan", "Bambara"],
+    "ba": ["башҡорт теле", "Bashkir"],
+    "eu": ["euskara", "Basque"],
+    "be": ["беларуская мова", "Belarusian"],
+    "bn": ["বাংলা", "Bengali"],
+    "bh": ["भोजपुरी", "Bihari"],
+    "bi": ["Bislama", "Bislama"],
+    "bs": ["bosanski jezik", "Bosnian"],
+    "br": ["brezhoneg", "Breton"],
+    "bg": ["български език", "Bulgarian"],
+    "my": ["ဗမာစာ", "Burmese"],
+    "ca": ["català", "Catalan"],
+    "ch": ["Chamoru", "Chamorro"],
+    "ce": ["нохчийн мотт", "Chechen"],
+    "ny": ["chiCheŵa", "Chichewa"],
+    "zh": ["中文", "Chinese"],
+    "cv": ["чӑваш чӗлхи", "Chuvash"],
+    "kw": ["Kernewek", "Cornish"],
+    "co": ["corsu", "Corsican"],
+    "cr": ["ᓀᐦᐃᔭᐍᐏᐣ", "Cree"],
+    "hr": ["hrvatski jezik", "Croatian"],
+    "cs": ["čeština", "Czech"],
+    "da": ["dansk", "Danish"],
+    "dv": ["ދިވެހި", "Divehi"],
+    "nl": ["Nederlands", "Dutch"],
+    "dz": ["རྫོང་ཁ", "Dzongkha"],
+    "en": ["English", "English"],
+    "eo": ["Esperanto", "Esperanto"],
+    "et": ["eesti", "Estonian"],
+    "ee": ["Eʋegbe", "Ewe"],
+    "fo": ["føroyskt", "Faroese"],
+    "fj": ["vosa Vakaviti", "Fijian"],
+    "fi": ["suomi", "Finnish"],
+    "fr": ["français", "French"],
+    "ff": ["Fulfulde", "Fula"],
+    "gl": ["galego", "Galician"],
+    "ka": ["ქართული", "Georgian"],
+    "de": ["Deutsch", "German"],
+    "el": ["ελληνικά", "Greek"],
+    "gn": ["Avañe'ẽ", "Guaraní"],
+    "gu": ["ગુજરાતી", "Gujarati"],
+    "ht": ["Kreyòl ayisyen", "Haitian"],
+    "ha": ["هَوُسَ", "Hausa"],
+    "he": ["עברית", "Hebrew"],
+    "hz": ["Otjiherero", "Herero"],
+    "hi": ["हिन्दी", "Hindi"],
+    "ho": ["Hiri Motu", "Hiri Motu"],
+    "hu": ["magyar", "Hungarian"],
+    "ia": ["Interlingua", "Interlingua"],
+    "ie": ["Interlingue", "Interlingue"],
+    "ga": ["Gaeilge", "Irish"],
+    "ig": ["Asụsụ Igbo", "Igbo"],
+    "ik": ["Iñupiaq", "Inupiaq"],
+    "io": ["Ido", "Ido"],
+    "is": ["Íslenska", "Icelandic"],
+    "it": ["italiano", "Italian"],
+    "iu": ["ᐃᓄᒃᑎᑐᑦ", "Inuktitut"],
+    "ja": ["日本語", "Japanese"],
+    "jv": ["basa Jawa", "Javanese"],
+    "kl": ["kalaallisut", "Greenlandic"],
+    "kn": ["ಕನ್ನಡ", "Kannada"],
+    "kr": ["Kanuri", "Kanuri"],
+    "ks": ["कश्मीरी", "Kashmiri"],
+    "kk": ["қазақ тілі", "Kazakh"],
+    "km": ["ខ្មែរ", "Khmer"],
+    "ki": ["Gĩkũyũ", "Kikuyu"],
+    "rw": ["Ikinyarwanda", "Kinyarwanda"],
+    "ky": ["Кыргызча", "Kyrgyz"],
+    "kv": ["коми кыв", "Komi"],
+    "kg": ["Kikongo", "Kongo"],
+    "ko": ["한국어", "Korean"],
+    "ku": ["Kurdî", "Kurdish"],
+    "kj": ["Kuanyama", "Kwanyama"],
+    "la": ["lingua latina", "Latin"],
+    "lb": ["Lëtzebuergesch", "Luxembourgish"],
+    "lg": ["Luganda", "Ganda"],
+    "li": ["Limburgs", "Limburgish"],
+    "ln": ["Lingála", "Lingala"],
+    "lo": ["ພາສາລາວ", "Lao"],
+    "lt": ["lietuvių kalba", "Lithuanian"],
+    "lu": ["Tshiluba", "Luba-Katanga"],
+    "lv": ["latviešu valoda", "Latvian"],
+    "gv": ["Gaelg", "Manx"],
+    "mk": ["македонски јазик", "Macedonian"],
+    "mg": ["fiteny malagasy", "Malagasy"],
+    "ms": ["بهاس ملايو‎", "Malay"],
+    "ml": ["മലയാളം", "Malayalam"],
+    "mt": ["Malti", "Maltese"],
+    "mi": ["te reo Māori", "Māori"],
+    "mr": ["मराठी", "Marathi"],
+    "mh": ["Kajin M̧ajeļ", "Marshallese"],
+    "mn": ["Монгол хэл", "Mongolian"],
+    "na": ["Ekakairũ Naoero", "Nauru"],
+    "nv": ["Diné bizaad", "Navajo"],
+    "nd": ["isiNdebele", "Northern Ndebele"],
+    "ne": ["नेपाली", "Nepali"],
+    "ng": ["Owambo", "Ndonga"],
+    "no": ["Norsk", "Norwegian"],
+    "ii": ["ꆈꌠ꒿", "Nuosu"],
+    "nr": ["isiNdebele", "Southern Ndebele"],
+    "oc": ["occitan", "Occitan"],
+    "oj": ["ᐊᓂᔑᓈᐯᒧᐎᓐ", "Ojibwe"],
+    "om": ["Afaan Oromoo", "Oromo"],
+    "or": ["ଓଡ଼ିଆ", "Oriya"],
+    "os": ["ирон æвзаг", "Ossetian"],
+    "pa": ["ਪੰਜਾਬੀ", "Punjabi"],
+    "pi": ["पाऴि", "Pāli"],
+    "fa": ["فارسی", "Persian"],
+    "pl": ["polszczyzna", "Polish"],
+    "ps": ["پښتو", "Pashto"],
+    "pt": ["português", "Portuguese"],
+    "qu": ["Runa Simi", "Quechua"],
+    "rm": ["rumantsch grischun", "Romansh"],
+    "rn": ["Ikirundi", "Kirundi"],
+    "ro": ["limba română", "Romanian"],
+    "ru": ["Русский", "Russian"],
+    "sc": ["sardu", "Sardinian"],
+    "sd": ["सिन्धी", "Sindhi"],
+    "se": ["Davvisámegiella", "Northern Sami"],
+    "sm": ["gagana fa'a Samoa", "Samoan"],
+    "sg": ["yângâ tî sängö", "Sango"],
+    "sr": ["српски језик", "Serbian"],
+    "gd": ["Gàidhlig", "Gaelic"],
+    "sn": ["chiShona", "Shona"],
+    "si": ["සිංහල", "Sinhalese"],
+    "sk": ["slovenčina", "Slovak"],
+    "sl": ["slovenščina", "Slovene"],
+    "so": ["Soomaaliga", "Somali"],
+    "st": ["Sesotho", "Southern Sotho"],
+    "es": ["español", "Spanish"],
+    "su": ["Basa Sunda", "Sundanese"],
+    "sw": ["Kiswahili", "Swahili"],
+    "ss": ["SiSwati", "Swati"],
+    "sv": ["svenska", "Swedish"],
+    "ta": ["தமிழ்", "Tamil"],
+    "te": ["తెలుగు", "Telugu"],
+    "tg": ["тоҷикӣ", "Tajik"],
+    "th": ["ไทย", "Thai"],
+    "ti": ["ትግርኛ", "Tigrinya"],
+    "bo": ["བོད་ཡིག", "Tibetan"],
+    "tk": ["Түркмен", "Turkmen"],
+    "tl": ["ᜏᜒᜃᜅ᜔ ᜆᜄᜎᜓᜄ᜔", "Tagalog"],
+    "tn": ["Setswana", "Tswana"],
+    "to": ["faka Tonga", "Tonga"],
+    "tr": ["Türkçe", "Turkish"],
+    "ts": ["Xitsonga", "Tsonga"],
+    "tt": ["татар теле", "Tatar"],
+    "ty": ["Reo Tahiti", "Tahitian"],
+    "ug": ["ئۇيغۇرچە‎", "Uyghur"],
+    "uk": ["українська мова", "Ukrainian"],
+    "ur": ["اردو", "Urdu"],
+    "uz": ["Oʻzbek‎", "Uzbek"],
+    "ve": ["Tshivenḓa", "Venda"],
+    "vi": ["Việt Nam", "Vietnamese"],
+    "vo": ["Volapük", "Volapük"],
+    "wa": ["walon", "Walloon"],
+    "cy": ["Cymraeg", "Welsh"],
+    "wo": ["Wollof", "Wolof"],
+    "fy": ["Frysk", "Western Frisian"],
+    "xh": ["isiXhosa", "Xhosa"],
+    "yi": ["ייִדיש", "Yiddish"],
+    "yo": ["Yorùbá", "Yoruba"],
+    "za": ["Saɯ cueŋƅ", "Zhuang"],
+    "zu": ["isiZulu", "Zulu"]
+}

+ 1 - 1
i18n/pl.json

@@ -130,7 +130,7 @@
     "Markdown": "Markdown",
     "Markdown": "Markdown",
     "Download attachment": "Download attachment",
     "Download attachment": "Download attachment",
     "Cloned file attached.": "Cloned file attached.",
     "Cloned file attached.": "Cloned file attached.",
-    "Attach a file:": "Attach a file:",
+    "Attach a file": "Attach a file",
     "Remove attachment": "Remove attachment",
     "Remove attachment": "Remove attachment",
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
     "Your browser does not support uploading encrypted files. Please use a newer browser.":
         "Your browser does not support uploading encrypted files. Please use a newer browser.",
         "Your browser does not support uploading encrypted files. Please use a newer browser.",

+ 21 - 2
js/zerobin.js

@@ -266,7 +266,25 @@ $(function() {
                 }
                 }
                 return val;
                 return val;
             });
             });
-        }
+        },
+        
+        /**
+         * get value of cookie, if it was set, empty string otherwise
+         * From: http://www.w3schools.com/js/js_cookies.asp
+         *
+         * @param string cname
+         * @return string
+         */
+        getCookie: function(cname) {
+            var name = cname + '=';
+            var ca = document.cookie.split(';');
+            for(var i = 0; i < ca.length; ++i) {
+                var c = ca[i];
+                while (c.charAt(0) == ' ') c = c.substring(1);
+                if (c.indexOf(name) == 0) return c.substring(name.length, c.length);
+            }
+            return '';
+        } 
     };
     };
 
 
     /**
     /**
@@ -361,7 +379,8 @@ $(function() {
          */
          */
         loadTranslations: function(callback)
         loadTranslations: function(callback)
         {
         {
-            var language = (navigator.language || navigator.userLanguage).substring(0, 2);
+            var selectedLang = helper.getCookie('lang');
+            var language = selectedLang.length > 0 ? selectedLang : (navigator.language || navigator.userLanguage).substring(0, 2);
             // note that 'en' is built in, so no translation is necessary
             // note that 'en' is built in, so no translation is necessary
             if (this.supportedLanguages.indexOf(language) == -1)
             if (this.supportedLanguages.indexOf(language) == -1)
             {
             {

+ 130 - 24
lib/i18n.php

@@ -26,6 +26,33 @@ class i18n
      */
      */
     protected static $_language = 'en';
     protected static $_language = 'en';
 
 
+    /**
+     * language labels
+     *
+     * @access protected
+     * @static
+     * @var    array
+     */
+    protected static $_languageLabels = array();
+
+    /**
+     * available languages
+     *
+     * @access protected
+     * @static
+     * @var    array
+     */
+    protected static $_availableLanguages = array();
+
+    /**
+     * path to language files
+     *
+     * @access protected
+     * @static
+     * @var    string
+     */
+    protected static $_path = '';
+
     /**
     /**
      * translation cache
      * translation cache
      *
      *
@@ -94,36 +121,57 @@ class i18n
      *
      *
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      *
      *
-     * @access protected
+     * @access public
      * @static
      * @static
      * @return void
      * @return void
      */
      */
     public static function loadTranslations()
     public static function loadTranslations()
     {
     {
-        // find a matching translation file
-        $availableLanguages = array();
-        $path = PUBLIC_PATH . DIRECTORY_SEPARATOR . 'i18n';
-        $i18n = dir($path);
-        while (false !== ($file = $i18n->read()))
+        $availableLanguages = self::getAvailableLanguages();
+
+        // check if the lang cookie was set and that language exists
+        if (array_key_exists('lang', $_COOKIE) && in_array($_COOKIE['lang'], $availableLanguages))
         {
         {
-            if (preg_match('/^([a-z]{2}).json$/', $file, $match) === 1)
-            {
-                $availableLanguages[] = $match[1];
-            }
+            $match = $_COOKIE['lang'];
+        }
+        // find a translation file matching the browsers language preferences
+        else
+        {
+            $match = self::_getMatchingLanguage(
+                self::getBrowserLanguages(), $availableLanguages
+            );
         }
         }
 
 
-        $match = self::_getMatchingLanguage(
-            self::getBrowserLanguages(), $availableLanguages
-        );
         // load translations
         // load translations
-        if ($match != 'en')
+        self::$_language = $match;
+        self::$_translations = ($match == 'en') ? array() : json_decode(
+            file_get_contents(self::_getPath($match . '.json')),
+            true
+        );
+    }
+
+    /**
+     * get list of available translations based on files found
+     *
+     * @access public
+     * @static
+     * @return array
+     */
+    public static function getAvailableLanguages()
+    {
+        if (count(self::$_availableLanguages) == 0)
         {
         {
-            self::$_language = $match;
-            self::$_translations = json_decode(
-                file_get_contents($path . DIRECTORY_SEPARATOR . $match . '.json'),
-                true
-            );
+            $i18n = dir(self::_getPath());
+            while (false !== ($file = $i18n->read()))
+            {
+                if (preg_match('/^([a-z]{2}).json$/', $file, $match) === 1)
+                {
+                    self::$_availableLanguages[] = $match[1];
+                }
+            }
+            self::$_availableLanguages[] = 'en';
         }
         }
+        return self::$_availableLanguages;
     }
     }
 
 
     /**
     /**
@@ -131,6 +179,8 @@ class i18n
      *
      *
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      *
      *
+     * @access public
+     * @static
      * @return array
      * @return array
      */
      */
     public static function getBrowserLanguages()
     public static function getBrowserLanguages()
@@ -165,12 +215,64 @@ class i18n
         return $languages;
         return $languages;
     }
     }
 
 
+    /**
+     * get currently loaded language
+     *
+     * @access public
+     * @static
+     * @return string
+     */
+    public static function getLanguage()
+    {
+        return self::$_language;
+    }
+
+    /**
+     * get list of language labels
+     *
+     * Only for given language codes, otherwise all labels.
+     *
+     * @access public
+     * @static
+     * @param  array $languages
+     * @return array
+     */
+    public static function getLanguageLabels($languages = array())
+    {
+        $file = self::_getPath('languages.json');
+        if (count(self::$_languageLabels) == 0 && is_readable($file))
+        {
+            self::$_languageLabels = json_decode(file_get_contents($file), true);
+        }
+        if (count($languages) == 0) return self::$_languageLabels;
+        return array_intersect_key(self::$_languageLabels, array_flip($languages));
+    }
+
+    /**
+     * get language file path
+     *
+     * @access protected
+     * @static
+     * @param  string $file
+     * @return string
+     */
+    protected static function _getPath($file = '')
+    {
+        if (strlen(self::$_path) == 0)
+        {
+            self::$_path = PUBLIC_PATH . DIRECTORY_SEPARATOR . 'i18n';
+        }
+        return self::$_path . (strlen($file) ? DIRECTORY_SEPARATOR . $file : '');
+    }
+
     /**
     /**
      * determines the plural form to use based on current language and given number
      * determines the plural form to use based on current language and given number
      *
      *
      * From: http://localization-guide.readthedocs.org/en/latest/l10n/pluralforms.html
      * From: http://localization-guide.readthedocs.org/en/latest/l10n/pluralforms.html
      *
      *
-     * @param int $n
+     * @access protected
+     * @static
+     * @param  int $n
      * @return int
      * @return int
      */
      */
     protected static function _getPluralForm($n)
     protected static function _getPluralForm($n)
@@ -191,8 +293,10 @@ class i18n
      *
      *
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      *
      *
-     * @param array $acceptedLanguages
-     * @param array $availableLanguages
+     * @access protected
+     * @static
+     * @param  array $acceptedLanguages
+     * @param  array $availableLanguages
      * @return string
      * @return string
      */
      */
     protected static function _getMatchingLanguage($acceptedLanguages, $availableLanguages) {
     protected static function _getMatchingLanguage($acceptedLanguages, $availableLanguages) {
@@ -247,8 +351,10 @@ class i18n
      *
      *
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      * From: http://stackoverflow.com/questions/3770513/detect-browser-language-in-php#3771447
      *
      *
-     * @param string $a
-     * @param string $b
+     * @access protected
+     * @static
+     * @param  string $a
+     * @param  string $b
      * @return float
      * @return float
      */
      */
     protected static function _matchLanguage($a, $b) {
     protected static function _matchLanguage($a, $b) {

+ 10 - 0
lib/zerobin.php

@@ -659,6 +659,14 @@ class zerobin
         // translate all the formatter options
         // translate all the formatter options
         $formatters = array_map(array('i18n', 'translate'), $this->_conf['formatter_options']);
         $formatters = array_map(array('i18n', 'translate'), $this->_conf['formatter_options']);
 
 
+        // set language cookie if that functionality was enabled
+        $languageselection = '';
+        if ($this->_getMainConfig('languageselection', false))
+        {
+            $languageselection = i18n::getLanguage();
+            setcookie('lang', $languageselection);
+        }
+
         $page = new RainTPL;
         $page = new RainTPL;
         $page::$path_replace = false;
         $page::$path_replace = false;
         // we escape it here because ENT_NOQUOTES can't be used in RainTPL templates
         // we escape it here because ENT_NOQUOTES can't be used in RainTPL templates
@@ -678,6 +686,8 @@ class zerobin
         $page->assign('PASSWORD', $this->_getMainConfig('password', true));
         $page->assign('PASSWORD', $this->_getMainConfig('password', true));
         $page->assign('FILEUPLOAD', $this->_getMainConfig('fileupload', false));
         $page->assign('FILEUPLOAD', $this->_getMainConfig('fileupload', false));
         $page->assign('BASE64JSVERSION', $this->_getMainConfig('base64version', '2.1.9'));
         $page->assign('BASE64JSVERSION', $this->_getMainConfig('base64version', '2.1.9'));
+        $page->assign('LANGUAGESELECTION', $languageselection);
+        $page->assign('LANGUAGES', i18n::getLanguageLabels(i18n::getAvailableLanguages()));
         $page->assign('EXPIRE', $expire);
         $page->assign('EXPIRE', $expire);
         $page->assign('EXPIREDEFAULT', $this->_conf['expire']['default']);
         $page->assign('EXPIREDEFAULT', $this->_conf['expire']['default']);
         $page->draw($this->_getMainConfig('template', 'page'));
         $page->draw($this->_getMainConfig('template', 'page'));

+ 12 - 1
tpl/bootstrap-compact.html

@@ -118,7 +118,18 @@
 							</ul>
 							</ul>
 						</li>{/if}
 						</li>{/if}
 					</ul>
 					</ul>
-					<ul class="nav navbar-nav pull-right">
+					<ul class="nav navbar-nav pull-right">{if="strlen($LANGUAGESELECTION)"}
+						<li id="language" class="dropdown">
+							<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false"><span class="glyphicon glyphicon-flag" aria-hidden="true"></span> {$LANGUAGES[$LANGUAGESELECTION][0]} <span class="caret"></span></a>
+							<ul class="dropdown-menu">
+{loop="LANGUAGES"}
+								<li>
+									<a href="#" class="reloadlink" onclick="document.cookie='lang={$key}';">
+										{$value[0]} ({$value[1]})
+									</a>
+								</li>{/loop}
+							</ul>
+						</li>{/if}
 						<li>
 						<li>
 							<button id="newbutton" type="button" class="reloadlink hidden btn btn-default navbar-btn">
 							<button id="newbutton" type="button" class="reloadlink hidden btn btn-default navbar-btn">
 								<span class="glyphicon glyphicon-file" aria-hidden="true"></span> {function="t('New')"}
 								<span class="glyphicon glyphicon-file" aria-hidden="true"></span> {function="t('New')"}

+ 12 - 1
tpl/bootstrap.html

@@ -116,7 +116,18 @@
 							</ul>
 							</ul>
 						</li>
 						</li>
 					</ul>
 					</ul>
-					<ul class="nav navbar-nav pull-right">
+					<ul class="nav navbar-nav pull-right">{if="strlen($LANGUAGESELECTION)"}
+						<li id="language" class="dropdown">
+							<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false"><span class="glyphicon glyphicon-flag" aria-hidden="true"></span> {$LANGUAGES[$LANGUAGESELECTION][0]} <span class="caret"></span></a>
+							<ul class="dropdown-menu">
+{loop="LANGUAGES"}
+								<li>
+									<a href="#" class="reloadlink" onclick="document.cookie='lang={$key}';">
+										{$value[0]} ({$value[1]})
+									</a>
+								</li>{/loop}
+							</ul>
+						</li>{/if}
 						<li>
 						<li>
 							<button id="newbutton" type="button" class="reloadlink hidden btn btn-default navbar-btn">
 							<button id="newbutton" type="button" class="reloadlink hidden btn btn-default navbar-btn">
 								<span class="glyphicon glyphicon-file" aria-hidden="true"></span> {function="t('New')"}
 								<span class="glyphicon glyphicon-file" aria-hidden="true"></span> {function="t('New')"}

+ 9 - 3
tpl/page.html

@@ -46,7 +46,7 @@
 					<button id="sendbutton" class="hidden"><img src="img/icon_send.png" width="18" height="15" alt="" />{function="t('Send')"}</button>
 					<button id="sendbutton" class="hidden"><img src="img/icon_send.png" width="18" height="15" alt="" />{function="t('Send')"}</button>
 					<button id="clonebutton" class="hidden"><img src="img/icon_clone.png" width="15" height="17" alt="" />{function="t('Clone')"}</button>
 					<button id="clonebutton" class="hidden"><img src="img/icon_clone.png" width="15" height="17" alt="" />{function="t('Clone')"}</button>
 					<button id="rawtextbutton" class="hidden"><img src="img/icon_raw.png" width="15" height="15" alt="" />{function="t('Raw text')"}</button>
 					<button id="rawtextbutton" class="hidden"><img src="img/icon_raw.png" width="15" height="15" alt="" />{function="t('Raw text')"}</button>
-					<div id="expiration" class="hidden">{function="t('Expires')"}:
+					<div id="expiration" class="hidden button">{function="t('Expires')"}:
 						<select id="pasteExpiration" name="pasteExpiration">
 						<select id="pasteExpiration" name="pasteExpiration">
 {loop="EXPIRE"}
 {loop="EXPIRE"}
 							<option value="{$key}"{if="$key == $EXPIREDEFAULT"} selected="selected"{/if}>{$value}</option>{/loop}
 							<option value="{$key}"{if="$key == $EXPIREDEFAULT"} selected="selected"{/if}>{$value}</option>{/loop}
@@ -69,7 +69,13 @@
 {loop="FORMATTER"}
 {loop="FORMATTER"}
 							<option value="{$key}"{if="$key == $FORMATTERDEFAULT"} selected="selected"{/if}>{$value}</option>{/loop}
 							<option value="{$key}"{if="$key == $FORMATTERDEFAULT"} selected="selected"{/if}>{$value}</option>{/loop}
 						</select>
 						</select>
-					</div>
+					</div>{if="strlen($LANGUAGESELECTION)"}
+					<div id="language" class="button">
+						<select name="lang">
+{loop="LANGUAGES"}
+							<option class="reloadlink" onclick="document.cookie='lang={$key}';" value="{$key}"{if="$key == $LANGUAGESELECTION"} selected="selected"{/if}>{$value[0]} ({$value[1]})</option>{/loop}
+						</select>
+					</div>{/if}
 				</div>
 				</div>
 				<div id="pasteresult" class="hidden">
 				<div id="pasteresult" class="hidden">
 					<div id="deletelink"></div>
 					<div id="deletelink"></div>
@@ -78,7 +84,7 @@
 				<div id="attachment" class="hidden"><a>{function="t('Download attachment')"}</a></div>
 				<div id="attachment" class="hidden"><a>{function="t('Download attachment')"}</a></div>
 				<div id="attach" class="hidden">
 				<div id="attach" class="hidden">
 					<span id="clonedfile" class="hidden">{function="t('Cloned file attached.')"}</span>
 					<span id="clonedfile" class="hidden">{function="t('Cloned file attached.')"}</span>
-					<span id="filewrap">{function="t('Attach a file:')"} <input type="file" id="file" name="file" /></span>
+					<span id="filewrap">{function="t('Attach a file')"}: <input type="file" id="file" name="file" /></span>
 					<button id="fileremovebutton">{function="t('Remove attachment')"}</button>
 					<button id="fileremovebutton">{function="t('Remove attachment')"}</button>
 				</div>{/if}
 				</div>{/if}
 				<div id="image" class="hidden"></div>
 				<div id="image" class="hidden"></div>