1a3e17609a9500f847fc4fd9efebf4578ccec2d3
[framework/web/web-ui-fw.git] / src / loader / loader.js
1 /**
2  * loader.js : Loader for web-ui-fw
3  * Refactored from bootstrap.js
4  *
5  * By Youmin Ha <youmin.ha@samsung.com>
6  *
7  */
8 S = {
9         libFileName : "tizen-web-ui-fw(.min)?.js",
10
11         frameworkData : {
12                 rootDir: '/usr/lib/tizen-web-ui-fw',
13                 version: '0.1',
14                 theme: "default",
15                 },
16
17     cacheBust: (document.location.href.match(/debug=true/)) ?
18                '?cacheBust=' + (new Date()).getTime() :
19                '',
20
21         util : {
22                 addElementToHead : function(elem) {
23                         var head = document.getElementsByTagName('head')[0];
24                         head.appendChild(elem);
25                 },
26                 loadScriptSync : function(scriptPath, successCB, errorCB) {
27                         $.ajax({
28                                 url: scriptPath,
29                                 dataType: 'script',
30                                 async: false,
31                                 success: successCB,
32                                 error: function(jqXHR, textStatus, errorThrown) {
33                                         if(errorCB) errorCB(jqXHR, textStatus, errorThrown);
34                                         else {
35                                                 var ignoreStatusList = [
36                                                         404,    // not found
37                                                         ];
38                                                 if(-1 == $.inArray(jqXHR.status, ignoreStatusList)) {
39                                                         alert('Error while loading ' + scriptPath + '\n' + jqXHR.status + ':' + jqXHR.statusText);
40                                                 }
41                                                 else {
42                                                         console.log('Error while loading ' + scriptPath + '\n' + jqXHR.status + ':' + jqXHR.statusText);
43                                                 }
44                                         }
45                                 },
46                         });
47                 },
48                 getScaleFactor: function () {
49                         var factor = window.scale;
50
51                         if ( !factor ) {
52                                 var width = screen.width < screen.height ? screen.width : screen.height,
53                                         defaultWidth = 720;
54
55                                 factor = width / defaultWidth;
56                                 if ( factor > 1 ) {
57                                         // TODO NOTE some of targets(e.g iPad) need to set scale equal or less than 1.0
58                                         factor = 1;
59                                 }
60                         }
61                         console.log( "ScaleFactor: " + factor );
62                         return factor;
63                 },
64         },
65
66         css : {
67                 load: function (path) {
68                         S.util.addElementToHead(this.makeLink(path + S.cacheBust));
69                 },
70
71                 makeLink : function (href) {
72                         var customstylesheetLink = document.createElement('link');
73                         customstylesheetLink.setAttribute('rel', 'stylesheet');
74                         customstylesheetLink.setAttribute('href', href);
75                         return customstylesheetLink;
76                 },
77         },
78
79         getParams: function() {
80                 /* Get data-* params from <script> tag, and set S.frameworkData.* values
81                  * Returns true if proper <script> tag is found, or false if not.
82                  */
83                 // Find current <script> tag element
84                 var scriptElems = document.getElementsByTagName('script'),
85                         val = null,
86                         foundScript = false;
87                 for (var idx in scriptElems) {
88                         var elem = scriptElems[idx],
89                                 src = elem.getAttribute('src');
90                         if(src && src.match(this.libFileName)) {
91                                 // Set framework data, only when they are given.
92                                 var tokens = src.split(/[\/\\]/),
93                                         version_idx = -3;
94                                 this.frameworkData.rootDir = elem.getAttribute( 'data-framework-root' ) || tokens.slice( 0, tokens.length + version_idx ).join( '/' ) || this.frameworkData.rootDir;
95                                 this.frameworkData.version = elem.getAttribute( 'data-framework-version' ) || tokens[ tokens.length + version_idx ] || this.frameworkData.version;
96                                 this.frameworkData.theme = elem.getAttribute( 'data-framework-theme' ) || this.frameworkData.theme;
97                                 foundScript = true;
98                                 break;
99                         }
100                 }
101                 return foundScript;
102         },
103
104         loadTheme: function() {
105                 var themePath = [
106                                 this.frameworkData.rootDir, 
107                                 this.frameworkData.version,
108                                 'themes',
109                                 this.frameworkData.theme
110                                         ].join('/'),
111                         cssPath = [themePath, 'tizen-web-ui-fw-theme.css'].join('/'),
112                         jsPath = [themePath, 'theme.js'].join('/');
113
114                 this.css.load(cssPath);
115                 this.util.loadScriptSync(jsPath);
116         },
117
118         setViewport: function () {
119                 var meta;
120                 $("meta").each( function() {
121                         if ( $(this).attr("name") === "viewport" ) {
122                                 console.log("user set viewport... framework viewport will not be applied.");
123                                 meta = this;
124                         }
125                 });
126                 if ( meta )
127                         return;
128                 if ( meta = document.createElement( "meta" )) {
129                         //set meta tags for view port
130                         var scale = S.util.getScaleFactor();
131
132                         meta.name = "viewport";
133                         meta.content = "width=device-width, initial-scale=" + scale + ", maximum-scale=" + scale + ", user-scalable=0, target-densityDpi=device-dpi";
134                         console.log( meta.content );
135                         var head = document.getElementsByTagName('head').item(0);
136                         head.insertBefore(meta, head.firstChild);
137                 }
138         },
139
140         /** Load Globalize culture file, and set default culture.
141          *  @param[in]  language  Language code. ex) en-US, en, ko-KR, ko
142          *                        If language is not given, read language from html 'lang' attribute, or from system setting.
143          */
144         loadGlobalizeCulture: function(language) {
145                 function getGlobalizeCultureFile(lang) {
146                         return ['globalize.culture.', lang, '.js'].join('');
147                 };
148                 function getGlobalizeCulturePath(self, file) {
149                         return [
150                                 self.frameworkData.rootDir, 
151                                 self.frameworkData.version,
152                                 'js',
153                                 'cultures',
154                                 file,
155                         ].join('/');
156                 }
157
158                 // Get lang, and change country code to uppercase chars.
159                 var lang = language || $('html').attr('lang') || window.navigator.language,
160                         countryCodeIdx = lang.lastIndexOf('-'),
161                         ignoreCodes = ['Cyrl', 'Latn', 'Mong']; // Not country code!
162
163                 if(countryCodeIdx != -1) {      // Found country code!
164                         var countryCode = lang.substr(countryCodeIdx + 1);
165                         if(ignoreCodes.join('-').indexOf(countryCode) < 0) { // countryCode is not found from ignoreCodes
166                                 // Make countryCode to uppercase
167                                 lang = [ lang.substr(0, countryCodeIdx), countryCode.toUpperCase() ].join('-');
168                         }
169                 }
170
171                 var self = this,
172                         globalizeCultureFile = getGlobalizeCultureFile(lang),
173                         globalizeCulturePath = getGlobalizeCulturePath(self, globalizeCultureFile),
174                         neutralLangIndex = lang.lastIndexOf('-');
175
176                 // Run culture script
177                 console.log('Run globalize culture: ' + globalizeCulturePath);
178                 this.util.loadScriptSync(
179                         globalizeCulturePath, 
180                         null, 
181                         function(jqXHR, textStatus, errorThrown) {      // Failed to load!
182                                 if(jqXHR.status == 404) {
183                                         // If culture file is not found, run neutral language culture. 
184                                         // (e.g. en-US --> en)
185                                         if(neutralLangIndex != -1) {
186                                                 var neutralLang = lang.substr(0, neutralLangIndex),
187                                                         neutralCultureFile = getGlobalizeCultureFile(neutralLang),
188                                                         neutralCulturePath = getGlobalizeCulturePath(self, neutralCultureFile);
189                                                 console.log('Run globalize culture of neutral lang: ' + neutralCulturePath);
190                                                 self.util.loadScriptSync(neutralCulturePath);
191                                         }
192                                 }
193                                 else {
194                                         alert('Error while loading ' + scriptPath + '\n' + jqXHR.status + ':' + jqXHR.statusText);
195                                 }
196                         }
197                 );
198                 return lang;
199         },
200         setGlobalize: function() {
201                 var lang = this.loadGlobalizeCulture();
202
203                 // Set culture
204                 // NOTE: It is not needed to set with neutral lang. 
205                 //       Globalize automatically deals with it.
206                 Globalize.culture(lang);
207         },
208 };
209
210
211 // Loader's jobs
212 (function (S, $, undefined) {
213         S.getParams( );
214         S.loadTheme( );
215         S.setViewport( );
216         S.setGlobalize( );
217
218         // Turn off JQM's auto initialization option.
219         // NOTE: This job must be done before domready.
220         $.mobile.autoInitializePage = false;
221         domReady( function( ) {
222                 $.mobile.initializePage( );
223         });
224  })(S, jQuery);