!import
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
1 /* ***** BEGIN LICENSE BLOCK *****
2 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
3 *
4 * The contents of this file are subject to the Mozilla Public License Version
5 * 1.1 (the "License"); you may not use this file except in compliance with
6 * the License. You may obtain a copy of the License at
7 * http://www.mozilla.org/MPL/
8 *
9 * Software distributed under the License is distributed on an "AS IS" basis,
10 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
11 * for the specific language governing rights and limitations under the
12 * License.
13 *
14 * The Original Code is Mozilla Communicator client code, released
15 * March 31, 1998.
16 *
17 * The Initial Developer of the Original Code is
18 * Netscape Communications Corporation.
19 * Portions created by the Initial Developer are Copyright (C) 1998-1999
20 * the Initial Developer. All Rights Reserved.
21 *
22 * Contributor(s):
23 * Ben "Count XULula" Goodger
24 * Charles Manske (cmanske@netscape.com)
25 * Neil Rashbrook (neil@parkwaycc.co.uk)
26 *
27 * Alternatively, the contents of this file may be used under the terms of
28 * either of the GNU General Public License Version 2 or later (the "GPL"),
29 * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
30 * in which case the provisions of the GPL or the LGPL are applicable instead
31 * of those above. If you wish to allow use of your version of this file only
32 * under the terms of either the GPL or the LGPL, and not to allow others to
33 * use your version of this file under the terms of the MPL, indicate your
34 * decision by deleting the provisions above and replace them with the notice
35 * and other provisions required by the GPL or the LGPL. If you do not delete
36 * the provisions above, a recipient may use your version of this file under
37 * the terms of any one of the MPL, the GPL or the LGPL.
38 *
39 * ***** END LICENSE BLOCK ***** */
40
41 /************** GLOBALS **************/
42 var gElement = null; // handle to actual element edited
43
44 var HTMLAttrs = []; // html attributes
45 var CSSAttrs = []; // css attributes
46 var JSEAttrs = []; // js events
47
48 var HTMLRAttrs = []; // removed html attributes
49 var JSERAttrs = []; // removed js events
50
51 /* Set false to allow changing selection in tree
52 without doing "onselect" handler actions
53 */
54 var gDoOnSelectTree = true;
55 var gUpdateTreeValue = true;
56
57 /************** INITIALISATION && SETUP **************/
58
59 /**
60 * function : void Startup();
61 * parameters : none
62 * returns : none
63 * desc. : startup and initialisation, prepares dialog.
64 **/
Startup
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
65 function Startup()
66 {
67 var editor = GetCurrentEditor();
68
69 // Element to edit is passed in
70 if (!editor || !window.arguments[1])
71 {
72 dump("Advanced Edit: No editor or element to edit not supplied\n");
73 window.close();
74 return;
75 }
76 // This is the return value for the parent,
77 // who only needs to know if OK was clicked
78 window.opener.AdvancedEditOK = false;
79
80 // The actual element edited (not a copy!)
81 gElement = window.arguments[1];
82
83 // place the tag name in the header
84 var tagLabel = document.getElementById("tagLabel");
85 tagLabel.setAttribute("value", ("<" + gElement.localName + ">"));
86
87 // Create dialog object to store controls for easy access
88 gDialog.AddHTMLAttributeNameInput = document.getElementById("AddHTMLAttributeNameInput");
89
90 // We use a <deck> to switch between editable menulist and textbox
91 gDialog.AddHTMLAttributeValueDeck = document.getElementById("AddHTMLAttributeValueDeck");
92 gDialog.AddHTMLAttributeValueMenulist = document.getElementById("AddHTMLAttributeValueMenulist");
93 gDialog.AddHTMLAttributeValueTextbox = document.getElementById("AddHTMLAttributeValueTextbox");
94 gDialog.AddHTMLAttributeValueInput = gDialog.AddHTMLAttributeValueTextbox;
95
96 gDialog.AddHTMLAttributeTree = document.getElementById("HTMLATree");
97 gDialog.AddCSSAttributeNameInput = document.getElementById("AddCSSAttributeNameInput");
98 gDialog.AddCSSAttributeValueInput = document.getElementById("AddCSSAttributeValueInput");
99 gDialog.AddCSSAttributeTree = document.getElementById("CSSATree");
100 gDialog.AddJSEAttributeNameList = document.getElementById("AddJSEAttributeNameList");
101 gDialog.AddJSEAttributeValueInput = document.getElementById("AddJSEAttributeValueInput");
102 gDialog.AddJSEAttributeTree = document.getElementById("JSEATree");
103 gDialog.okButton = document.documentElement.getButton("accept");
104
105 // build the attribute trees
106 BuildHTMLAttributeTable();
107 BuildCSSAttributeTable();
108 BuildJSEAttributeTable();
109
110 // Build attribute name arrays for menulists
111 BuildJSEAttributeNameList();
112 BuildHTMLAttributeNameList();
113 // No menulists for CSS panel (yet)
114
115 // Set focus to Name editable menulist in HTML panel
116 SetTextboxFocus(gDialog.AddHTMLAttributeNameInput);
117
118 // size the dialog properly
119 window.sizeToContent();
120
121 SetWindowLocation();
122 }
123
124 /**
125 * function : bool onAccept ( void );
126 * parameters : none
127 * returns : boolean true to close the window
128 * desc. : event handler for ok button
129 **/
onAccept
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
130 function onAccept()
131 {
132 var editor = GetCurrentEditor();
133 editor.beginTransaction();
134 try {
135 // Update our gElement attributes
136 UpdateHTMLAttributes();
137 UpdateCSSAttributes();
138 UpdateJSEAttributes();
139 } catch(ex) {
140 dump(ex);
141 }
142 editor.endTransaction();
143
144 window.opener.AdvancedEditOK = true;
145 SaveWindowLocation();
146
147 return true; // do close the window
148 }
149
150 // Helpers for removing and setting attributes
151 // Use editor transactions if modifying the element already in the document
152 // (Temporary element from a property dialog won't have a parent node)
doRemoveAttribute
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
153 function doRemoveAttribute(attrib)
154 {
155 try {
156 var editor = GetCurrentEditor();
157 if (gElement.parentNode)
158 editor.removeAttribute(gElement, attrib);
159 else
160 gElement.removeAttribute(attrib);
161 } catch(ex) {}
162 }
163
doSetAttribute
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
164 function doSetAttribute(attrib, value)
165 {
166 try {
167 var editor = GetCurrentEditor();
168 if (gElement.parentNode)
169 editor.setAttribute(gElement, attrib, value);
170 else
171 gElement.setAttribute(attrib, value);
172 } catch(ex) {}
173 }
174
175 /**
176 * function : bool CheckAttributeNameSimilarity ( string attName, array attArray );
177 * parameters : attribute to look for, array of current attributes
178 * returns : true if attribute already exists, false if it does not
179 * desc. : checks to see if any other attributes by the same name as the arg supplied
180 * already exist.
181 **/
CheckAttributeNameSimilarity
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
182 function CheckAttributeNameSimilarity(attName, attArray)
183 {
184 for (var i = 0; i < attArray.length; i++)
185 {
186 if (attName.toLowerCase() == attArray[i].toLowerCase())
187 return true;
188 }
189 return false;
190 }
191
192 /**
193 * function : bool UpdateExistingAttribute ( string attName, string attValue, string treeChildrenId );
194 * parameters : attribute to look for, new value, ID of <treeChildren> node in XUL tree
195 * returns : true if attribute already exists in tree, false if it does not
196 * desc. : checks to see if any other attributes by the same name as the arg supplied
197 * already exist while setting the associated value if different from current value
198 **/
UpdateExistingAttribute
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
199 function UpdateExistingAttribute( attName, attValue, treeChildrenId )
200 {
201 var treeChildren = document.getElementById(treeChildrenId);
202 if (!treeChildren)
203 return false;
204
205 var name;
206 var i;
207 attName = TrimString(attName).toLowerCase();
208 attValue = TrimString(attValue);
209
210 for (i = 0; i < treeChildren.childNodes.length; i++)
211 {
212 var item = treeChildren.childNodes[i];
213 name = GetTreeItemAttributeStr(item);
214 if (name.toLowerCase() == attName)
215 {
216 // Set the text in the "value' column treecell
217 SetTreeItemValueStr(item, attValue);
218
219 // Select item just changed,
220 // but don't trigger the tree's onSelect handler
221 gDoOnSelectTree = false;
222 try {
223 selectTreeItem(treeChildren, item);
224 } catch (e) {}
225 gDoOnSelectTree = true;
226
227 return true;
228 }
229 }
230 return false;
231 }
232
233 /**
234 * function : string GetAndSelectExistingAttributeValue ( string attName, string treeChildrenId );
235 * parameters : attribute to look for, ID of <treeChildren> node in XUL tree
236 * returns : value in from the tree or empty string if name not found
237 **/
GetAndSelectExistingAttributeValue
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
238 function GetAndSelectExistingAttributeValue( attName, treeChildrenId )
239 {
240 if (!attName)
241 return "";
242
243 var treeChildren = document.getElementById(treeChildrenId);
244 var name;
245 var i;
246
247 for (i = 0; i < treeChildren.childNodes.length; i++)
248 {
249 var item = treeChildren.childNodes[i];
250 name = GetTreeItemAttributeStr(item);
251 if (name.toLowerCase() == attName.toLowerCase())
252 {
253 // Select item in the tree
254 // but don't trigger the tree's onSelect handler
255 gDoOnSelectTree = false;
256 try {
257 selectTreeItem(treeChildren, item);
258 } catch (e) {}
259 gDoOnSelectTree = true;
260
261 // Get the text in the "value' column treecell
262 return GetTreeItemValueStr(item);
263 }
264 }
265
266 // Attribute doesn't exist in tree, so remove selection
267 gDoOnSelectTree = false;
268 try {
269 treeChildren.parentNode.view.selection.clearSelection();
270 } catch (e) {}
271 gDoOnSelectTree = true;
272
273 return "";
274 }
275
276 /* Tree structure:
277 <treeItem>
278 <treeRow>
279 <treeCell> // Name Cell
280 <treeCell // Value Cell
281 */
GetTreeItemAttributeStr
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
282 function GetTreeItemAttributeStr(treeItem)
283 {
284 if (treeItem)
285 return TrimString(treeItem.firstChild.firstChild.getAttribute("label"));
286
287 return "";
288 }
289
GetTreeItemValueStr
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
290 function GetTreeItemValueStr(treeItem)
291 {
292 if (treeItem)
293 return TrimString(treeItem.firstChild.lastChild.getAttribute("label"));
294
295 return "";
296 }
297
SetTreeItemValueStr
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
298 function SetTreeItemValueStr(treeItem, value)
299 {
300 if (treeItem && GetTreeItemValueStr(treeItem) != value)
301 treeItem.firstChild.lastChild.setAttribute("label", value);
302 }
303
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
304 function IsNotTreeHeader(treeCell)
305 {
306 if (treeCell)
307 return (treeCell.parentNode.parentNode.nodeName != "treehead");
308
309 return false;
310 }
311
RemoveNameFromAttArray
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
312 function RemoveNameFromAttArray(attName, attArray)
313 {
314 for (var i=0; i < attArray.length; i++)
315 {
316 if (attName.toLowerCase() == attArray[i].toLowerCase())
317 {
318 // Remove 1 array item
319 attArray.splice(i,1);
320 break;
321 }
322 }
323 }
324
325 // adds a generalised treeitem.
AddTreeItem
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
326 function AddTreeItem ( name, value, treeChildrenId, attArray )
327 {
328 attArray[attArray.length] = name;
329 var treeChildren = document.getElementById ( treeChildrenId );
330 var treeitem = document.createElementNS ( XUL_NS, "treeitem" );
331 var treerow = document.createElementNS ( XUL_NS, "treerow" );
332
333 var attrCell = document.createElementNS ( XUL_NS, "treecell" );
334 attrCell.setAttribute( "class", "propertylist" );
335 attrCell.setAttribute( "label", name );
336
337 var valueCell = document.createElementNS ( XUL_NS, "treecell" );
338 valueCell.setAttribute( "class", "propertylist" );
339 valueCell.setAttribute( "label", value );
340
341 treerow.appendChild ( attrCell );
342 treerow.appendChild ( valueCell );
343 treeitem.appendChild ( treerow );
344 treeChildren.appendChild ( treeitem );
345
346 // Select item just added,
347 // but suppress calling the onSelect handler
348 gDoOnSelectTree = false;
349 try {
350 selectTreeItem(treeChildren, treeitem);
351 } catch (e) {}
352 gDoOnSelectTree = true;
353
354 return treeitem;
355 }
356
selectTreeItem
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
357 function selectTreeItem(treeChildren, item)
358 {
359 var index = treeChildren.parentNode.contentView.getIndexOfItem(item);
360 treeChildren.parentNode.view.selection.select(index);
361 }
362
getSelectedItem
(0 calls, 0 incl. v-uS, 0 excl. v-uS)
363 function getSelectedItem(tree)
364 {
365 if (tree.view.selection.count == 1)
366 return tree.contentView.getItemAtIndex(tree.currentIndex);
367 else
368 return null;
369 }