25 if (typeof(
Ci) ==
"undefined")
26 var
Ci = Components.interfaces;
27 if (typeof(
Cc) ==
"undefined")
28 var
Cc = Components.classes;
29 if (typeof(
Cr) ==
"undefined")
30 var
Cr = Components.results;
31 if (typeof(
Cu) ==
"undefined")
32 var
Cu = Components.utils;
34 Cu.import(
"resource://app/jsmodules/ArrayConverter.jsm");
35 Cu.import(
"resource://app/jsmodules/sbCoverHelper.jsm");
36 Cu.import(
"resource://app/jsmodules/SBJobUtils.jsm");
37 Cu.import(
"resource://app/jsmodules/sbLibraryUtils.jsm");
38 Cu.import(
"resource://app/jsmodules/sbMetadataUtils.jsm");
39 Cu.import(
"resource://app/jsmodules/sbProperties.jsm");
40 Cu.import(
"resource://app/jsmodules/StringUtils.jsm");
41 Cu.import(
"resource://gre/modules/XPCOMUtils.jsm");
54 _propertyManager: Cc[
"@songbirdnest.com/Songbird/Properties/PropertyManager;1"]
55 .getService(Ci.sbIPropertyManager),
70 onLoadTrackEditor:
function TrackEditor_onLoadTrackEditor() {
73 var windowMediator = Cc[
"@mozilla.org/appshell/window-mediator;1"]
74 .getService(Ci.nsIWindowMediator);
76 var songbirdWindow = windowMediator.getMostRecentWindow(
"Songbird:Main");
77 this.
_browser = songbirdWindow.gBrowser;
82 this._setUpDefaultWidgets();
88 this.onTabContentChange();
90 var initialTab =
window.arguments[0];
92 var tabBox = document.getElementById(
"trackeditor-tabbox");
93 var
tabs = tabBox.parentNode.getElementsByTagName(
"tab");
95 if (tab.id == initialTab) {
96 tabBox.selectedTab =
tab;
105 _setUpDefaultWidgets:
function TrackEditor__setUpDefaultWidgets() {
108 var tabBox = document.getElementById(
"trackeditor-tabbox");
109 var
tabs = tabBox.tabs;
115 this._elements[
"anonymous"] = [];
118 var elements = document.getElementsByAttribute(
"property",
"*");
119 for each (var
element in elements) {
120 var wrappedElement =
null;
121 if (element.tagName ==
"label" ||
122 (element.tagName ==
"textbox" && /\bplain\b/(element.className)))
124 var
property = element.getAttribute(
"property");
125 var propertyInfo = this._propertyManager.getPropertyInfo(property);
127 if (element.getAttribute(
"property-type") !=
"label" &&
128 propertyInfo.type ==
"uri") {
129 wrappedElement =
new TrackEditorURILabel(element);
131 else if (element.getAttribute(
"property-type") !=
"label" &&
132 property == SBProperties.originPage) {
137 wrappedElement =
new TrackEditorLabel(element);
139 }
else if (element.tagName ==
"textbox") {
140 wrappedElement =
new TrackEditorTextbox(element);
141 }
else if (element.tagName ==
"sb-rating") {
142 wrappedElement =
new TrackEditorRating(element);
143 }
else if (element.localName ==
"svg") {
148 if (wrappedElement) {
150 this._elements[element.id] = wrappedElement;
152 this._elements[
"anonymous"].push(wrappedElement);
159 var propMan = Cc[
"@songbirdnest.com/Songbird/Properties/PropertyManager;1"]
160 .getService(Ci.sbIPropertyManager);
162 var advancedRowItemsToLoad = document.getElementsByAttribute(
"class",
"advTabRowElements");
165 var advancedMenupopup = document.getElementById(
"menupopup");
168 for (var
i = 0;
i < advancedRowItemsToLoad.length;
i++){
169 var singleRowItem = advancedRowItemsToLoad[
i];
170 var
property = singleRowItem.getAttribute(
"property");
171 var propInfo = propMan.getPropertyInfo(property);
173 var menuitem = document.createElement(
"menuitem");
174 menuitem.setAttribute(
"type",
"checkbox");
175 menuitem.setAttribute(
"class",
"advTabMenuItems");
176 menuitem.setAttribute(
"property", property);
177 menuitem.setAttribute(
"label", propInfo.displayName);
179 menuitem.setAttribute(
"closemenu",
"none");
180 advancedMenupopup.appendChild(menuitem);
184 advancedMenupopup.addEventListener(
"popuphidden",
function(){TrackEditor.onpopupclose()},
false);
187 elements = [
"notification_box",
"notification_text",
188 "prev_button",
"next_button",
"infotab_trackname_label",
189 "ok_button",
"cancel_button"];
192 for each (var elementName
in elements) {
193 var element = document.getElementById(elementName);
195 this._elements[elementName] =
element;
199 this._elements[
"notification_box"].hidden =
true;
201 var trackeditorTabs = document.getElementById(
"trackeditor-tabs");
203 for (var
tab = trackeditorTabs.firstChild;
tab;
tab =
tab.nextSibling) {
204 if ((
"hidden" in
tab) && (!tab.hidden)) {
209 trackeditorTabs.hidden =
false;
213 this.state.addPropertyListener(
"all",
this);
219 updateNotificationBox:
function TrackEditor__updateNotificationBox() {
221 var itemCount = this.state.selectedItems.length;
222 var writableCount = this.state.writableItemCount;
225 var notificationClass =
"dialog-notification notification-warning";
228 if (writableCount == itemCount) {
229 message =
SBFormattedString(
"trackeditor.notification.editingmultiple", [itemCount]);
230 notificationClass =
"dialog-notification notification-info";
231 }
else if (writableCount >= 1) {
233 [(itemCount - writableCount), itemCount]);
235 message =
SBString(
"trackeditor.notification.multiplereadonly");
237 }
else if (writableCount == 0) {
238 message =
SBString(
"trackeditor.notification.singlereadonly");
242 this._elements[
"notification_box"].className = notificationClass;
243 this._elements[
"notification_text"].textContent =
message;
244 this._elements[
"notification_box"].hidden =
false;
246 this._elements[
"notification_box"].hidden =
true;
253 updateControls:
function TrackEditor__updateControls() {
257 var hasErrors = this.state.isKnownInvalid();
259 this._elements[
"ok_button"].disabled = hasErrors;
263 var idx = this.mediaListView.selection.currentIndex;
264 var atStart = (idx == 0)
265 var atEnd = (idx == this.mediaListView.length - 1);
266 var hasMultiple = this.mediaListView.selection.count > 1;
267 this._elements[
"prev_button"].setAttribute(
"disabled",
268 (atStart || hasErrors || hasMultiple ?
"true" :
"false"));
269 this._elements[
"next_button"].setAttribute(
"disabled",
270 (atEnd || hasErrors || hasMultiple ?
"true" :
"false"));
277 onTabContentChange:
function TrackEditor_onTabContentChange() {
283 this.mediaListView = this.
_browser.currentMediaListView;
288 this.onSelectionChanged();
319 onSelectionChanged:
function TrackEditor_onSelectionChanged() {
322 var itemContentType = this.mediaListView.selection.currentMediaItem.contentType;
324 if (itemContentType ==
"audio"){
327 "songbird.trackeditor.audioAdvancedTags",
""));
330 TrackEditor.updateAdvancedTab(userPreferenceProperty);
332 else if (itemContentType ==
"video"){
335 "songbird.trackeditor.videoAdvancedTags",
""));
338 TrackEditor.updateAdvancedTab(userPreferenceProperty);
341 this.state.setSelection(this.mediaListView.selection);
358 this.updateNotificationBox();
359 this.updateControls();
363 var
hidden = this.state.selectedItems.length > 1;
364 this._elements[
"infotab_trackname_textbox"].hidden =
hidden;
365 this._elements[
"infotab_trackname_label"].hidden =
hidden;
371 onTrackEditorPropertyChange:
function TrackEditor_onTrackEditorPropertyChange(property) {
374 this.updateControls();
381 onUnloadTrackEditor:
function() {
384 this.mediaListView.selection.removeListener(
this);
389 this.mediaListView =
null;
401 var idx = this.mediaListView.selection.currentIndex;
403 if (idx ==
null || idx == undefined) {
return; }
406 if (idx >= this.mediaListView.length) {
408 idx = this.mediaListView.length - 1
411 this.mediaListView.selection.selectOnly(idx);
413 this.onSelectionChanged();
425 var idx = this.mediaListView.selection.currentIndex;
427 if (idx ==
null || idx == undefined) {
return; }
435 this.mediaListView.selection.selectOnly(idx);
437 this.onSelectionChanged();
447 onSelectionChanged();
453 closeAndApply:
function() {
465 if (this.state.isKnownInvalid()) {
466 Components.utils.reportError(
"TrackEditor: attempt to call apply() with known invalid state");
470 var properties = this.state.getEnabledProperties();
471 var items = this.state.selectedItems;
472 if (items.length == 0 || properties.length == 0) {
476 var enableRatingWrite =
Application.prefs.getValue(
"songbird.metadata.ratings.enableWriting",
false);
479 var writeProperties = [];
483 var needsWriting =
new Array(items.length);
486 runBatched:
function(aUserData) {
487 for each (property
in properties) {
488 if (!TrackEditor.state.isPropertyEdited(property)) {
492 writeProperties.push(property);
494 for (var
i = 0;
i < items.length;
i++) {
495 var
value = TrackEditor.state.getPropertyValue(property);
499 &&
property != SBProperties.rating) {
503 if (value != item.getProperty(property)) {
508 if (value ==
"" && property != SBProperties.primaryImageURL) {
512 item.setProperty(property, value);
517 if (property != SBProperties.rating || enableRatingWrite) {
518 needsWriting[
i] =
true;
526 this.mediaListView.mediaList.runInBatchMode(batchSetter,
null);
555 var mediaItemArray = [];
556 for (var
i = 0;
i < items.length;
i++) {
558 mediaItemArray.push(items[i]);
561 if (mediaItemArray.length > 0 && writeProperties.length > 0) {
565 this.mediaListView.mediaList);
579 onpopupclose:
function() {
581 var advancedMenuItems = document.getElementsByAttribute(
"class",
"advTabMenuItems");
582 var checkedPropertyStrings = [];
583 for (var
i = 0;
i < advancedMenuItems.length;
i++){
585 var propertyString = advancedMenuItems[
i].getAttribute(
"property");
586 checkedPropertyStrings.push(propertyString);
591 TrackEditor.updateAdvancedTab(checkedPropertyStrings);
594 var itemContentType = this.
_browser.currentMediaListView.selection.currentMediaItem.contentType;
597 if (itemContentType ==
"audio"){
598 Application.prefs.setValue(
"songbird.trackeditor.audioAdvancedTags",
599 JSON.stringify(checkedPropertyStrings));
601 else if (itemContentType ==
"video"){
602 Application.prefs.setValue(
"songbird.trackeditor.videoAdvancedTags",
603 JSON.stringify(checkedPropertyStrings));
614 updateAdvancedTab:
function(anArrayOfPropertyStrings){
616 var advancedMenuItems = document.getElementsByAttribute(
"class",
"advTabMenuItems");
618 var rowElementsAdvancedTab = document.getElementsByAttribute(
"class",
"advTabRowElements");
626 for (var
i = 0;
i < rowElementsAdvancedTab.length;
i++){
627 var
property = rowElementsAdvancedTab[
i].getAttribute(
"property");
628 var matchStringProperty = anArrayOfPropertyStrings.indexOf(property,0);
629 if(matchStringProperty > -1){
630 rowElementsAdvancedTab[
i].removeAttribute(
"hidden");
632 rowElementsAdvancedTab[
i].setAttribute(
"hidden",
true);
642 for (var
i = 0;
i < advancedMenuItems.length;
i++){
643 var
property = advancedMenuItems[
i].getAttribute(
"property");
644 var matchStringProperty = anArrayOfPropertyStrings.indexOf(property,0);
645 if(matchStringProperty > -1){
646 advancedMenuItems[
i].setAttribute(
"checked",
"true");
648 advancedMenuItems[
i].removeAttribute(
"checked");
function SBFormattedString(aKey, aParams, aDefault, aStringBundle)
function SBString(aKey, aDefault, aStringBundle)
function TrackEditorState()
return ret concat apply([], ret)
return aWindow document documentElement getAttribute(aAttribute)||dimension
Javascript wrappers for common library tasks.
_getSelectedPageStyle s i