browser_995164_registerArea_during_customize_mode.js (8127B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 4 5 "use strict"; 6 7 const TOOLBARID = "test-toolbar-added-during-customize-mode"; 8 9 // The ID of a button that is not placed (ie, is in the palette) by default 10 const kNonPlacedWidgetId = "open-file-button"; 11 12 add_task(async function () { 13 await startCustomizing(); 14 let toolbar = createToolbarWithPlacements(TOOLBARID, []); 15 CustomizableUI.addWidgetToArea(kNonPlacedWidgetId, TOOLBARID); 16 let button = document.getElementById(kNonPlacedWidgetId); 17 ok(button, "Button should exist."); 18 is( 19 button.parentNode.localName, 20 "toolbarpaletteitem", 21 "Button's parent node should be a wrapper." 22 ); 23 24 simulateItemDrag(button, gNavToolbox.palette); 25 ok( 26 !CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 27 "Button moved to the palette" 28 ); 29 ok( 30 gNavToolbox.palette.querySelector(`#${kNonPlacedWidgetId}`), 31 "Button really is in palette." 32 ); 33 34 button.scrollIntoView(); 35 simulateItemDrag(button, toolbar); 36 ok( 37 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 38 "Button moved out of palette" 39 ); 40 is( 41 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId).area, 42 TOOLBARID, 43 "Button's back on toolbar" 44 ); 45 ok( 46 toolbar.querySelector(`#${kNonPlacedWidgetId}`), 47 "Button really is on toolbar." 48 ); 49 50 await endCustomizing(); 51 isnot( 52 button.parentNode.localName, 53 "toolbarpaletteitem", 54 "Button's parent node should not be a wrapper outside customize mode." 55 ); 56 await startCustomizing(); 57 58 is( 59 button.parentNode.localName, 60 "toolbarpaletteitem", 61 "Button's parent node should be a wrapper back in customize mode." 62 ); 63 64 simulateItemDrag(button, gNavToolbox.palette); 65 ok( 66 !CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 67 "Button moved to the palette" 68 ); 69 ok( 70 gNavToolbox.palette.querySelector(`#${kNonPlacedWidgetId}`), 71 "Button really is in palette." 72 ); 73 74 ok( 75 !CustomizableUI.inDefaultState, 76 "Not in default state while toolbar is not collapsed yet." 77 ); 78 setToolbarVisibility(toolbar, false); 79 ok( 80 CustomizableUI.inDefaultState, 81 "In default state while toolbar is collapsed." 82 ); 83 84 setToolbarVisibility(toolbar, true); 85 86 info( 87 "Check that removing the area registration from within customize mode works" 88 ); 89 CustomizableUI.unregisterArea(TOOLBARID); 90 ok( 91 CustomizableUI.inDefaultState, 92 "Now that the toolbar is no longer registered, should be in default state." 93 ); 94 ok( 95 !gCustomizeMode.areas.has(toolbar), 96 "Toolbar shouldn't be known to customize mode." 97 ); 98 99 CustomizableUI.registerArea(TOOLBARID, { defaultPlacements: [] }); 100 CustomizableUI.registerToolbarNode(toolbar, []); 101 ok( 102 !CustomizableUI.inDefaultState, 103 "Now that the toolbar is registered again, should no longer be in default state." 104 ); 105 ok( 106 gCustomizeMode.areas.has(toolbar), 107 "Toolbar should be known to customize mode again." 108 ); 109 110 button.scrollIntoView(); 111 simulateItemDrag(button, toolbar); 112 ok( 113 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 114 "Button moved out of palette" 115 ); 116 is( 117 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId).area, 118 TOOLBARID, 119 "Button's back on toolbar" 120 ); 121 ok( 122 toolbar.querySelector(`#${kNonPlacedWidgetId}`), 123 "Button really is on toolbar." 124 ); 125 126 let otherWin = await openAndLoadWindow({}, true); 127 let otherTB = otherWin.document.createXULElement("toolbar"); 128 otherTB.id = TOOLBARID; 129 otherTB.setAttribute("customizable", "true"); 130 let wasInformedCorrectlyOfAreaAppearing = false; 131 let listener = { 132 onAreaNodeRegistered(aArea, aNode) { 133 if (aNode == otherTB) { 134 wasInformedCorrectlyOfAreaAppearing = true; 135 } 136 }, 137 }; 138 CustomizableUI.addListener(listener); 139 otherWin.gNavToolbox.appendChild(otherTB); 140 CustomizableUI.registerToolbarNode(otherTB); 141 ok( 142 wasInformedCorrectlyOfAreaAppearing, 143 "Should have been told area was registered." 144 ); 145 CustomizableUI.removeListener(listener); 146 147 ok( 148 otherTB.querySelector(`#${kNonPlacedWidgetId}`), 149 "Button is on other toolbar, too." 150 ); 151 152 simulateItemDrag(button, gNavToolbox.palette); 153 ok( 154 !CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 155 "Button moved to the palette" 156 ); 157 ok( 158 gNavToolbox.palette.querySelector(`#${kNonPlacedWidgetId}`), 159 "Button really is in palette." 160 ); 161 ok( 162 !otherTB.querySelector(`#${kNonPlacedWidgetId}`), 163 "Button is in palette in other window, too." 164 ); 165 166 button.scrollIntoView(); 167 simulateItemDrag(button, toolbar); 168 ok( 169 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId), 170 "Button moved out of palette" 171 ); 172 is( 173 CustomizableUI.getPlacementOfWidget(kNonPlacedWidgetId).area, 174 TOOLBARID, 175 "Button's back on toolbar" 176 ); 177 ok( 178 toolbar.querySelector(`#${kNonPlacedWidgetId}`), 179 "Button really is on toolbar." 180 ); 181 ok( 182 otherTB.querySelector(`#${kNonPlacedWidgetId}`), 183 "Button is on other toolbar, too." 184 ); 185 186 let wasInformedCorrectlyOfAreaDisappearing = false; 187 // XXXgijs So we could be using promiseWindowClosed here. However, after 188 // repeated random oranges, I'm instead relying on onWindowClosed below to 189 // fire appropriately - it is linked to an unload event as well, and so 190 // reusing it prevents a potential race between unload handlers where the 191 // one from promiseWindowClosed could fire before the onWindowClosed 192 // (and therefore onAreaNodeRegistered) one, causing the test to fail. 193 let windowClosed = await new Promise(resolve => { 194 listener = { 195 onAreaNodeUnregistered(aArea, aNode, aReason) { 196 if (aArea == TOOLBARID) { 197 is(aNode, otherTB, "Should be informed about other toolbar"); 198 is( 199 aReason, 200 CustomizableUI.REASON_WINDOW_CLOSED, 201 "Reason should be correct." 202 ); 203 wasInformedCorrectlyOfAreaDisappearing = 204 aReason === CustomizableUI.REASON_WINDOW_CLOSED; 205 } 206 }, 207 onWindowClosed(aWindow) { 208 if (aWindow == otherWin) { 209 resolve(aWindow); 210 } else { 211 info("Other window was closed!"); 212 info( 213 "Other window title: " + 214 (aWindow.document && aWindow.document.title) 215 ); 216 info( 217 "Our window title: " + 218 (otherWin.document && otherWin.document.title) 219 ); 220 } 221 }, 222 }; 223 CustomizableUI.addListener(listener); 224 otherWin.close(); 225 }); 226 227 is( 228 windowClosed, 229 otherWin, 230 "Window should have sent onWindowClosed notification." 231 ); 232 ok( 233 wasInformedCorrectlyOfAreaDisappearing, 234 "Should be told about window closing." 235 ); 236 // Closing the other window should not be counted against this window's customize mode: 237 is( 238 button.parentNode.localName, 239 "toolbarpaletteitem", 240 "Button's parent node should still be a wrapper." 241 ); 242 ok( 243 gCustomizeMode.areas.has(toolbar), 244 "Toolbar should still be a customizable area for this customize mode instance." 245 ); 246 247 await gCustomizeMode.reset(); 248 249 await endCustomizing(); 250 251 CustomizableUI.removeListener(listener); 252 wasInformedCorrectlyOfAreaDisappearing = false; 253 listener = { 254 onAreaNodeUnregistered(aArea, aNode, aReason) { 255 if (aArea == TOOLBARID) { 256 is(aNode, toolbar, "Should be informed about this window's toolbar"); 257 is( 258 aReason, 259 CustomizableUI.REASON_AREA_UNREGISTERED, 260 "Reason for final removal should be correct." 261 ); 262 wasInformedCorrectlyOfAreaDisappearing = 263 aReason === CustomizableUI.REASON_AREA_UNREGISTERED; 264 } 265 }, 266 }; 267 CustomizableUI.addListener(listener); 268 removeCustomToolbars(); 269 ok( 270 wasInformedCorrectlyOfAreaDisappearing, 271 "Should be told about area being unregistered." 272 ); 273 CustomizableUI.removeListener(listener); 274 ok( 275 CustomizableUI.inDefaultState, 276 "Should be fine after exiting customize mode." 277 ); 278 });