|
1 /* |
|
2 * Copyright (c) 2006 Nokia Corporation and/or its subsidiary(-ies). |
|
3 * All rights reserved. |
|
4 * This component and the accompanying materials are made available |
|
5 * under the terms of the License "Eclipse Public License v1.0" |
|
6 * which accompanies this distribution, and is available |
|
7 * at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 * |
|
9 * Initial Contributors: |
|
10 * Nokia Corporation - initial contribution. |
|
11 * |
|
12 * Contributors: |
|
13 * |
|
14 * Description: |
|
15 * |
|
16 */ |
|
17 |
|
18 |
|
19 include("containerLibrary.js") |
|
20 include("embeddedControlImplLibrary.js")// for isSettingItemList |
|
21 |
|
22 editorLibraryStrings = getLocalizedStrings("editorLibrary"); |
|
23 |
|
24 /** |
|
25 * Set up rendering support for editor components. This clears out |
|
26 * a rectangle of the component's size and draws text inside it |
|
27 * according to a component-specific formatter and MFNE layout. |
|
28 * This sets up a component to appear in a form. |
|
29 * |
|
30 * @param prototype the prototype to add IVisualAppearance to. |
|
31 * The prototype must implement these functions: |
|
32 * <p> |
|
33 * <li> |
|
34 * getDisplayText(instance): return the text formatted for display |
|
35 * (may be empty or null). Return the entire |
|
36 * string, even if longer than getMaxLength() |
|
37 * <li> |
|
38 * getMaxLength(instance): return the character limit on the text |
|
39 * <li> |
|
40 * getFlags(instance, laf): return an IFont#xxx mask desribing |
|
41 * parameters to font.drawFormattedString() |
|
42 * |
|
43 */ |
|
44 function setupEditorRendering(prototype) { |
|
45 prototype.drawContent = function(instance, laf, graphics, rect) { |
|
46 var properties = instance.properties; |
|
47 |
|
48 if( properties.isVisible != null && properties.isVisible == false) |
|
49 return; |
|
50 |
|
51 var flags = this.getFlags(instance, laf); |
|
52 if (isSettingItemList(instance.parent)) { |
|
53 flags = (flags & ~Font.ALIGN_MASK) | Font.ALIGN_CENTER; |
|
54 |
|
55 // white on blue doesn't look good antialiased |
|
56 flags = (flags & ~Font.ANTIALIAS_MASK) | Font.ANTIALIAS_OFF; |
|
57 } |
|
58 |
|
59 var font = this.getFont(instance, laf); |
|
60 if (font == null) |
|
61 font = laf.getFont("NormalFont"); |
|
62 |
|
63 graphics.setFont(font); |
|
64 |
|
65 //graphics.setBackground(laf.getColor("CAknSettingItemList.ContentBackground")); |
|
66 graphics.setBackground(getBackgroundColor(instance, laf)); |
|
67 graphics.fillRectangle(rect); |
|
68 |
|
69 var color = null; |
|
70 if (prototype.getDisplayColor) { |
|
71 color = prototype.getDisplayColor(instance, laf); |
|
72 } |
|
73 if (color == null && isSettingItemList(instance.parent)) |
|
74 color = laf.getColor("CAknSettingItemList.ContentForeground"); |
|
75 |
|
76 if (color == null) |
|
77 color = laf.getColor("EEikColorControlText"); |
|
78 graphics.setForeground(color); |
|
79 |
|
80 var text = "" + this.getDisplayText(instance); |
|
81 if (instance.isInstanceOf("com.nokia.carbide.uiq.CEikEdwinBase")) |
|
82 text = text.replace(/\n/,""); |
|
83 else |
|
84 text = chooseScalableText(text, font, rect.width); |
|
85 var maxLength = this.getMaxLength(instance); |
|
86 if (maxLength == 0 || text.length <= maxLength) { |
|
87 // in settings list, blank text is replaced |
|
88 if ((!text || text == "") && isSettingItemList(instance.parent)) { |
|
89 text = instance.properties.itemEmptyText; |
|
90 if (!text || text == "") |
|
91 text = editorLibraryStrings.getString("EmptyText"); |
|
92 } |
|
93 |
|
94 graphics.drawFormattedString(text, rect, flags, 0); |
|
95 } else { |
|
96 var visibleText = text.substring(0, maxLength); |
|
97 var truncatedText = text.substring(maxLength); |
|
98 |
|
99 var visibleSize = font.formattedStringExtent(visibleText, new Point(rect.width, rect.height), flags, 0); |
|
100 var truncatedSize = font.formattedStringExtent(truncatedText, new Point(rect.width, rect.height), flags, 0); |
|
101 |
|
102 // indicate truncated text |
|
103 if (false) { |
|
104 // dim background of truncated part |
|
105 graphics.setBackground(laf.getColor("EEikColorControlHighlightBackground")); |
|
106 graphics.fillRectangle(rect.x + visibleSize.x, rect.y, truncatedSize.x, rect.height); |
|
107 graphics.drawFormattedString(text, rect, flags, 0); |
|
108 } else { |
|
109 // dim letters of truncated part |
|
110 graphics.drawFormattedString(visibleText, rect, flags, 0); |
|
111 graphics.setForeground(Colors.getColor(200, 200, 200)); |
|
112 rect.x += visibleSize.x; |
|
113 graphics.drawFormattedString(truncatedText, rect, flags, 0); |
|
114 } |
|
115 } |
|
116 |
|
117 } |
|
118 |
|
119 prototype.getContentSize = function(instance, laf, size) { |
|
120 var properties = instance.properties; |
|
121 var isInForm = isForm(instance.parent); |
|
122 |
|
123 var font = this.getFont(instance, laf); |
|
124 if (font == null) |
|
125 font = laf.getFont("NormalFont"); |
|
126 |
|
127 var flags = this.getFlags(instance, laf); |
|
128 var text = this.getDisplayText(instance); |
|
129 if (text == null || text == "") |
|
130 text = "Temporary"; // provide enough space so click-added |
|
131 // editor has some perceivable width |
|
132 |
|
133 // use wrapping width to get adjusted height |
|
134 var size = font.formattedStringExtent(text, size, flags, 0); |
|
135 |
|
136 // this property is not necessarily present, in which case only one line is used |
|
137 var lines = properties.lines; |
|
138 if (isNaN(lines) || lines < 1) |
|
139 lines = 1; |
|
140 |
|
141 var linesHeight = getFontHeight(font) * lines; |
|
142 var textHeight = size.y; |
|
143 |
|
144 // this property flag is not necessarily present, in which case this code falls through |
|
145 var isResizable = 'flags' in properties |
|
146 && 'EEikEdwinResizable' in properties.flags |
|
147 && properties.flags.EEikEdwinResizable; |
|
148 |
|
149 //println("lines("+lines+"), linesHeight(" + linesHeight + "), textHeight(" + textHeight + "), resizable(" + isResizable + ")"); |
|
150 |
|
151 if (isResizable && (textHeight > linesHeight)) |
|
152 size.y = textHeight; |
|
153 else if (!isInForm) |
|
154 size.y = linesHeight; // don't resize if in container |
|
155 |
|
156 return size; |
|
157 } |
|
158 |
|
159 // now make this form-able |
|
160 setupEmbeddedRendering(prototype); |
|
161 |
|
162 } |
|
163 |
|
164 |
|
165 |
|
166 /** |
|
167 * Format the number to have zeroes on the left. |
|
168 */ |
|
169 function padWithZeroes(number, count) { |
|
170 var str = "" + number; |
|
171 if (str.length >= count) |
|
172 return str; |
|
173 var zeroes = "0000000000000000000".substring(0, count); |
|
174 return zeroes.substring(0, count - str.length) + str; |
|
175 } |
|
176 |
|
177 /** |
|
178 * Format the number to have spaces on the left. |
|
179 */ |
|
180 function padWithSpaces(number, count) { |
|
181 var str = "" + number; |
|
182 if (str.length >= count) |
|
183 return str; |
|
184 var zeroes = " ".substring(0, count); |
|
185 return zeroes.substring(0, count - str.length) + str; |
|
186 } |
|
187 |
|
188 /** |
|
189 * Format a time the way S60 would. This is piggishly restricted |
|
190 * to the American format, since S60 has some weirdness with formatting |
|
191 * (hiding hours -- but not AM/PM!, and hiding seconds) which would make |
|
192 * our task of mirroring these in a locale-dependent way too difficult. |
|
193 * |
|
194 * Likely it would be better to use a format string in the future. |
|
195 */ |
|
196 |
|
197 function formatTime(h, m, s, showHours, showMinutes, showSeconds, showAmPm) { |
|
198 var str = ""; |
|
199 var suffix = ""; |
|
200 |
|
201 if (showAmPm) { |
|
202 if (h >= 12) { |
|
203 h -= 12; |
|
204 suffix = " PM"; |
|
205 } else { |
|
206 suffix = " AM"; |
|
207 } |
|
208 if (h == 0) |
|
209 h = 12; |
|
210 } |
|
211 |
|
212 if (showHours) { |
|
213 str += padWithZeroes(h, 2) + ":"; |
|
214 } |
|
215 |
|
216 if (showMinutes) { |
|
217 str += padWithZeroes(m, 2); |
|
218 } |
|
219 |
|
220 if (showSeconds) { |
|
221 str += ":" + padWithZeroes(s, 2); |
|
222 } |
|
223 |
|
224 str += suffix; |
|
225 |
|
226 return str; |
|
227 |
|
228 } |
|
229 |
|
230 /** |
|
231 * Format a date the way S60 would. |
|
232 */ |
|
233 |
|
234 function formatDate(d) { |
|
235 return formatDateDMY(d.day, d.month, d.year); |
|
236 } |
|
237 |
|
238 function formatDateDMY(day, month, year) { |
|
239 var str = ""; |
|
240 str = padWithZeroes(day - 0 + 1, 2) + "/" + |
|
241 padWithZeroes(month - 0 + 1, 2) + "/" + |
|
242 padWithZeroes(year, 4); |
|
243 return str; |
|
244 |
|
245 } |
|
246 |
|
247 function commonEditorGetFlags(instance, laf) { |
|
248 var properties = instance.properties; |
|
249 var flags = 0; |
|
250 |
|
251 if (properties.alignment == undefined) |
|
252 return flags; |
|
253 |
|
254 switch (properties.alignment) { |
|
255 case "EAknEditorAlignCenter": |
|
256 flags = Font.ALIGN_CENTER; break; |
|
257 case "EAknEditorAlignLeft": |
|
258 flags = Font.ALIGN_LEFT; break; |
|
259 case "EAknEditorAlignRight": |
|
260 flags = Font.ALIGN_RIGHT; break; |
|
261 } |
|
262 |
|
263 return flags; |
|
264 } |
|
265 |
|
266 var CONTROL_ID = "com.nokia.sdt.series60.CCoeControl"; |
|
267 |
|
268 function isControl(instance) { |
|
269 return instance.componentId == CONTROL_ID; |
|
270 } |
|
271 |