123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790 |
- <?xml version="1.0"?>
- <!-- This Source Code Form is subject to the terms of the Mozilla Public
- - License, v. 2.0. If a copy of the MPL was not distributed with this
- - file, You can obtain one at http://mozilla.org/MPL/2.0/. -->
- <bindings id="placesTreeBindings"
- xmlns="http://www.mozilla.org/xbl"
- xmlns:xbl="http://www.mozilla.org/xbl"
- xmlns:html="http://www.w3.org/1999/xhtml"
- xmlns:xul="http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul">
- <binding id="places-tree" extends="chrome://global/content/bindings/tree.xml#tree">
- <implementation>
- <constructor><![CDATA[
- // Force an initial build.
- if (this.place)
- this.place = this.place;
- ]]></constructor>
- <destructor><![CDATA[
- // Break the treeviewer->result->treeviewer cycle.
- // Note: unsetting the result's viewer also unsets
- // the viewer's reference to our treeBoxObject.
- var result = this.result;
- if (result) {
- result.root.containerOpen = false;
- }
- // Unregister the controllber before unlinking the view, otherwise it
- // may still try to update commands on a view with a null result.
- if (this._controller) {
- this._controller.terminate();
- this.controllers.removeController(this._controller);
- }
- this.view = null;
- ]]></destructor>
- <property name="controller"
- readonly="true"
- onget="return this._controller"/>
- <!-- overriding -->
- <property name="view">
- <getter><![CDATA[
- try {
- return this.treeBoxObject.view.wrappedJSObject;
- }
- catch(e) {
- return null;
- }
- ]]></getter>
- <setter><![CDATA[
- return this.treeBoxObject.view = val;
- ]]></setter>
- </property>
- <property name="associatedElement"
- readonly="true"
- onget="return this"/>
- <method name="applyFilter">
- <parameter name="filterString"/>
- <parameter name="folderRestrict"/>
- <parameter name="includeHidden"/>
- <body><![CDATA[
- // preserve grouping
- var queryNode = PlacesUtils.asQuery(this.result.root);
- var options = queryNode.queryOptions.clone();
- // Make sure we're getting uri results.
- // We do not yet support searching into grouped queries or into
- // tag containers, so we must fall to the default case.
- if (PlacesUtils.nodeIsHistoryContainer(queryNode) ||
- options.resultType == options.RESULTS_AS_TAG_QUERY ||
- options.resultType == options.RESULTS_AS_TAG_CONTENTS)
- options.resultType = options.RESULTS_AS_URI;
- var query = PlacesUtils.history.getNewQuery();
- query.searchTerms = filterString;
- if (folderRestrict) {
- query.setFolders(folderRestrict, folderRestrict.length);
- options.queryType = options.QUERY_TYPE_BOOKMARKS;
- }
- options.includeHidden = !!includeHidden;
- this.load([query], options);
- ]]></body>
- </method>
- <method name="load">
- <parameter name="queries"/>
- <parameter name="options"/>
- <body><![CDATA[
- let result = PlacesUtils.history
- .executeQueries(queries, queries.length,
- options);
- let callback;
- if (this.flatList) {
- let onOpenFlatContainer = this.onOpenFlatContainer;
- if (onOpenFlatContainer)
- callback = new Function("aContainer", onOpenFlatContainer);
- }
- if (!this._controller) {
- this._controller = new PlacesController(this);
- this.controllers.appendController(this._controller);
- }
- let treeView = new PlacesTreeView(this.flatList, callback, this._controller);
- // Observer removal is done within the view itself. When the tree
- // goes away, treeboxobject calls view.setTree(null), which then
- // calls removeObserver.
- result.addObserver(treeView, false);
- this.view = treeView;
- if (this.getAttribute("selectfirstnode") == "true" && treeView.rowCount > 0) {
- treeView.selection.select(0);
- }
- this._cachedInsertionPoint = undefined;
- ]]></body>
- </method>
- <property name="flatList">
- <getter><![CDATA[
- return this.getAttribute("flatList") == "true";
- ]]></getter>
- <setter><![CDATA[
- if (this.flatList != val) {
- this.setAttribute("flatList", val);
- // reload with the last place set
- if (this.place)
- this.place = this.place;
- }
- return val;
- ]]></setter>
- </property>
- <property name="onOpenFlatContainer">
- <getter><![CDATA[
- return this.getAttribute("onopenflatcontainer");
- ]]></getter>
- <setter><![CDATA[
- if (this.onOpenFlatContainer != val) {
- this.setAttribute("onopenflatcontainer", val);
- // reload with the last place set
- if (this.place)
- this.place = this.place;
- }
- return val;
- ]]></setter>
- </property>
- <!--
- Causes a particular node represented by the specified placeURI to be
- selected in the tree. All containers above the node in the hierarchy
- will be opened, so that the node is visible.
- -->
- <method name="selectPlaceURI">
- <parameter name="placeURI"/>
- <body><![CDATA[
- // Do nothing if a node matching the given uri is already selected
- if (this.hasSelection && this.selectedNode.uri == placeURI)
- return;
- function findNode(container, placeURI, nodesURIChecked) {
- var containerURI = container.uri;
- if (containerURI == placeURI)
- return container;
- if (nodesURIChecked.indexOf(containerURI) != -1)
- return null;
- // never check the contents of the same query
- nodesURIChecked.push(containerURI);
- var wasOpen = container.containerOpen;
- if (!wasOpen)
- container.containerOpen = true;
- for (var i = 0; i < container.childCount; ++i) {
- var child = container.getChild(i);
- var childURI = child.uri;
- if (childURI == placeURI)
- return child;
- else if (PlacesUtils.nodeIsContainer(child)) {
- var nested = findNode(PlacesUtils.asContainer(child), placeURI, nodesURIChecked);
- if (nested)
- return nested;
- }
- }
- if (!wasOpen)
- container.containerOpen = false;
- return null;
- }
- var container = this.result.root;
- NS_ASSERT(container, "No result, cannot select place URI!");
- if (!container)
- return;
- var child = findNode(container, placeURI, []);
- if (child)
- this.selectNode(child);
- else {
- // If the specified child could not be located, clear the selection
- var selection = this.view.selection;
- selection.clearSelection();
- }
- ]]></body>
- </method>
- <!--
- Causes a particular node to be selected in the tree, resulting in all
- containers above the node in the hierarchy to be opened, so that the
- node is visible.
- -->
- <method name="selectNode">
- <parameter name="node"/>
- <body><![CDATA[
- var view = this.view;
- var parent = node.parent;
- if (parent && !parent.containerOpen) {
- // Build a list of all of the nodes that are the parent of this one
- // in the result.
- var parents = [];
- var root = this.result.root;
- while (parent && parent != root) {
- parents.push(parent);
- parent = parent.parent;
- }
- // Walk the list backwards (opening from the root of the hierarchy)
- // opening each folder as we go.
- for (var i = parents.length - 1; i >= 0; --i) {
- var index = view.treeIndexForNode(parents[i]);
- if (index != Ci.nsINavHistoryResultTreeViewer.INDEX_INVISIBLE &&
- view.isContainer(index) && !view.isContainerOpen(index))
- view.toggleOpenState(index);
- }
- // Select the specified node...
- }
- var index = view.treeIndexForNode(node);
- if (index == Ci.nsINavHistoryResultTreeViewer.INDEX_INVISIBLE)
- return;
- view.selection.select(index);
- // ... and ensure it's visible, not scrolled off somewhere.
- this.treeBoxObject.ensureRowIsVisible(index);
- ]]></body>
- </method>
- <!-- nsIPlacesView -->
- <property name="result">
- <getter><![CDATA[
- try {
- return this.view.QueryInterface(Ci.nsINavHistoryResultObserver).result;
- }
- catch (e) {
- return null;
- }
- ]]></getter>
- </property>
- <!-- nsIPlacesView -->
- <property name="place">
- <getter><![CDATA[
- return this.getAttribute("place");
- ]]></getter>
- <setter><![CDATA[
- this.setAttribute("place", val);
- var queriesRef = { };
- var queryCountRef = { };
- var optionsRef = { };
- PlacesUtils.history.queryStringToQueries(val, queriesRef, queryCountRef, optionsRef);
- if (queryCountRef.value == 0)
- queriesRef.value = [PlacesUtils.history.getNewQuery()];
- if (!optionsRef.value)
- optionsRef.value = PlacesUtils.history.getNewQueryOptions();
- this.load(queriesRef.value, optionsRef.value);
- return val;
- ]]></setter>
- </property>
- <!-- nsIPlacesView -->
- <property name="hasSelection">
- <getter><![CDATA[
- return this.view && this.view.selection.count >= 1;
- ]]></getter>
- </property>
- <!-- nsIPlacesView -->
- <property name="selectedNodes">
- <getter><![CDATA[
- let nodes = [];
- if (!this.hasSelection)
- return nodes;
- let selection = this.view.selection;
- let rc = selection.getRangeCount();
- let resultview = this.view;
- for (let i = 0; i < rc; ++i) {
- let min = { }, max = { };
- selection.getRangeAt(i, min, max);
- for (let j = min.value; j <= max.value; ++j)
- nodes.push(resultview.nodeForTreeIndex(j));
- }
- return nodes;
- ]]></getter>
- </property>
- <method name="toggleCutNode">
- <parameter name="aNode"/>
- <parameter name="aValue"/>
- <body><![CDATA[
- this.view.toggleCutNode(aNode, aValue);
- ]]></body>
- </method>
- <!-- nsIPlacesView -->
- <property name="removableSelectionRanges">
- <getter><![CDATA[
- // This property exists in addition to selectedNodes because it
- // encodes selection ranges (which only occur in list views) into
- // the return value. For each removed range, the index at which items
- // will be re-inserted upon the remove transaction being performed is
- // the first index of the range, so that the view updates correctly.
- //
- // For example, if we remove rows 2,3,4 and 7,8 from a list, when we
- // undo that operation, if we insert what was at row 3 at row 3 again,
- // it will show up _after_ the item that was at row 5. So we need to
- // insert all items at row 2, and the tree view will update correctly.
- //
- // Also, this function collapses the selection to remove redundant
- // data, e.g. when deleting this selection:
- //
- // http://www.foo.com/
- // (-) Some Folder
- // http://www.bar.com/
- //
- // ... returning http://www.bar.com/ as part of the selection is
- // redundant because it is implied by removing "Some Folder". We
- // filter out all such redundancies since some partial amount of
- // the folder's children may be selected.
- //
- let nodes = [];
- if (!this.hasSelection)
- return nodes;
- var selection = this.view.selection;
- var rc = selection.getRangeCount();
- var resultview = this.view;
- // This list is kept independently of the range selected (i.e. OUTSIDE
- // the for loop) since the row index of a container is unique for the
- // entire view, and we could have some really wacky selection and we
- // don't want to blow up.
- var containers = { };
- for (var i = 0; i < rc; ++i) {
- var range = [];
- var min = { }, max = { };
- selection.getRangeAt(i, min, max);
- for (var j = min.value; j <= max.value; ++j) {
- if (this.view.isContainer(j))
- containers[j] = true;
- if (!(this.view.getParentIndex(j) in containers))
- range.push(resultview.nodeForTreeIndex(j));
- }
- nodes.push(range);
- }
- return nodes;
- ]]></getter>
- </property>
- <!-- nsIPlacesView -->
- <property name="draggableSelection"
- onget="return this.selectedNodes"/>
- <!-- nsIPlacesView -->
- <property name="selectedNode">
- <getter><![CDATA[
- var view = this.view;
- if (!view || view.selection.count != 1)
- return null;
- var selection = view.selection;
- var min = { }, max = { };
- selection.getRangeAt(0, min, max);
- return this.view.nodeForTreeIndex(min.value);
- ]]></getter>
- </property>
- <!-- nsIPlacesView -->
- <property name="insertionPoint">
- <getter><![CDATA[
- // invalidated on selection and focus changes
- if (this._cachedInsertionPoint !== undefined)
- return this._cachedInsertionPoint;
- // there is no insertion point for history queries
- // so bail out now and save a lot of work when updating commands
- var resultNode = this.result.root;
- if (PlacesUtils.nodeIsQuery(resultNode) &&
- PlacesUtils.asQuery(resultNode).queryOptions.queryType ==
- Ci.nsINavHistoryQueryOptions.QUERY_TYPE_HISTORY)
- return this._cachedInsertionPoint = null;
- var orientation = Ci.nsITreeView.DROP_BEFORE;
- // If there is no selection, insert at the end of the container.
- if (!this.hasSelection) {
- var index = this.view.rowCount - 1;
- this._cachedInsertionPoint =
- this._getInsertionPoint(index, orientation);
- return this._cachedInsertionPoint;
- }
- // This is a two-part process. The first part is determining the drop
- // orientation.
- // * The default orientation is to drop _before_ the selected item.
- // * If the selected item is a container, the default orientation
- // is to drop _into_ that container.
- //
- // Warning: It may be tempting to use tree indexes in this code, but
- // you must not, since the tree is nested and as your tree
- // index may change when folders before you are opened and
- // closed. You must convert your tree index to a node, and
- // then use getChildIndex to find your absolute index in
- // the parent container instead.
- //
- var resultView = this.view;
- var selection = resultView.selection;
- var rc = selection.getRangeCount();
- var min = { }, max = { };
- selection.getRangeAt(rc - 1, min, max);
- // If the sole selection is a container, and we are not in
- // a flatlist, insert into it.
- // Note that this only applies to _single_ selections,
- // if the last element within a multi-selection is a
- // container, insert _adjacent_ to the selection.
- //
- // If the sole selection is the bookmarks toolbar folder, we insert
- // into it even if it is not opened
- var itemId =
- PlacesUtils.getConcreteItemId(resultView.nodeForTreeIndex(max.value));
- if (selection.count == 1 && resultView.isContainer(max.value) &&
- !this.flatList)
- orientation = Ci.nsITreeView.DROP_ON;
- this._cachedInsertionPoint =
- this._getInsertionPoint(max.value, orientation);
- return this._cachedInsertionPoint;
- ]]></getter>
- </property>
- <method name="_getInsertionPoint">
- <parameter name="index"/>
- <parameter name="orientation"/>
- <body><![CDATA[
- var result = this.result;
- var resultview = this.view;
- var container = result.root;
- var dropNearItemId = -1;
- NS_ASSERT(container, "null container");
- // When there's no selection, assume the container is the container
- // the view is populated from (i.e. the result's itemId).
- if (index != -1) {
- var lastSelected = resultview.nodeForTreeIndex(index);
- if (resultview.isContainer(index) && orientation == Ci.nsITreeView.DROP_ON) {
- // If the last selected item is an open container, append _into_
- // it, rather than insert adjacent to it.
- container = lastSelected;
- index = -1;
- }
- else if (lastSelected.containerOpen &&
- orientation == Ci.nsITreeView.DROP_AFTER &&
- lastSelected.hasChildren) {
- // If the last selected item is an open container and the user is
- // trying to drag into it as a first item, really insert into it.
- container = lastSelected;
- orientation = Ci.nsITreeView.DROP_ON;
- index = 0;
- }
- else {
- // Use the last-selected node's container.
- container = lastSelected.parent;
- // See comment in the treeView.js's copy of this method
- if (!container || !container.containerOpen)
- return null;
- // Avoid the potentially expensive call to getChildIndex
- // if we know this container doesn't allow insertion
- if (PlacesControllerDragHelper.disallowInsertion(container))
- return null;
- var queryOptions = PlacesUtils.asQuery(result.root).queryOptions;
- if (queryOptions.sortingMode !=
- Ci.nsINavHistoryQueryOptions.SORT_BY_NONE) {
- // If we are within a sorted view, insert at the end
- index = -1;
- }
- else if (queryOptions.excludeItems ||
- queryOptions.excludeQueries ||
- queryOptions.excludeReadOnlyFolders) {
- // Some item may be invisible, insert near last selected one.
- // We don't replace index here to avoid requests to the db,
- // instead it will be calculated later by the controller.
- index = -1;
- dropNearItemId = lastSelected.itemId;
- }
- else {
- var lsi = container.getChildIndex(lastSelected);
- index = orientation == Ci.nsITreeView.DROP_BEFORE ? lsi : lsi + 1;
- }
- }
- }
- if (PlacesControllerDragHelper.disallowInsertion(container))
- return null;
- return new InsertionPoint(PlacesUtils.getConcreteItemId(container),
- index, orientation,
- PlacesUtils.nodeIsTagQuery(container),
- dropNearItemId);
- ]]></body>
- </method>
- <!-- nsIPlacesView -->
- <method name="selectAll">
- <body><![CDATA[
- this.view.selection.selectAll();
- ]]></body>
- </method>
- <!-- This method will select the first node in the tree that matches
- each given item id. It will open any parent nodes that it needs
- to in order to show the selected items.
- -->
- <method name="selectItems">
- <parameter name="aIDs"/>
- <parameter name="aOpenContainers"/>
- <body><![CDATA[
- // By default, we do search and select within containers which were
- // closed (note that containers in which nodes were not found are
- // closed).
- if (aOpenContainers === undefined)
- aOpenContainers = true;
- var ids = aIDs; // don't manipulate the caller's array
- // Array of nodes found by findNodes which are to be selected
- var nodes = [];
- // Array of nodes found by findNodes which should be opened
- var nodesToOpen = [];
- // A set of URIs of container-nodes that were previously searched,
- // and thus shouldn't be searched again. This is empty at the initial
- // start of the recursion and gets filled in as the recursion
- // progresses.
- var nodesURIChecked = [];
- /**
- * Recursively search through a node's children for items
- * with the given IDs. When a matching item is found, remove its ID
- * from the IDs array, and add the found node to the nodes dictionary.
- *
- * NOTE: This method will leave open any node that had matching items
- * in its subtree.
- */
- function findNodes(node) {
- var foundOne = false;
- // See if node matches an ID we wanted; add to results.
- // For simple folder queries, check both itemId and the concrete
- // item id.
- var index = ids.indexOf(node.itemId);
- if (index == -1 &&
- node.type == Ci.nsINavHistoryResultNode.RESULT_TYPE_FOLDER_SHORTCUT)
- index = ids.indexOf(PlacesUtils.asQuery(node).folderItemId);
- if (index != -1) {
- nodes.push(node);
- foundOne = true;
- ids.splice(index, 1);
- }
- if (ids.length == 0 || !PlacesUtils.nodeIsContainer(node) ||
- nodesURIChecked.indexOf(node.uri) != -1)
- return foundOne;
- PlacesUtils.asContainer(node);
- if (!aOpenContainers && !node.containerOpen)
- return foundOne;
- nodesURIChecked.push(node.uri);
- // Remember the beginning state so that we can re-close
- // this node if we don't find any additional results here.
- var previousOpenness = node.containerOpen;
- node.containerOpen = true;
- for (var child = 0; child < node.childCount && ids.length > 0;
- child++) {
- var childNode = node.getChild(child);
- var found = findNodes(childNode);
- if (!foundOne)
- foundOne = found;
- }
- // If we didn't find any additional matches in this node's
- // subtree, revert the node to its previous openness.
- if (foundOne)
- nodesToOpen.unshift(node);
- node.containerOpen = previousOpenness;
- return foundOne;
- }
- // Disable notifications while looking for nodes.
- let result = this.result;
- let didSuppressNotifications = result.suppressNotifications;
- if (!didSuppressNotifications)
- result.suppressNotifications = true
- try {
- findNodes(this.result.root);
- }
- finally {
- if (!didSuppressNotifications)
- result.suppressNotifications = false;
- }
- // For all the nodes we've found, highlight the corresponding
- // index in the tree.
- var resultview = this.view;
- var selection = this.view.selection;
- selection.selectEventsSuppressed = true;
- selection.clearSelection();
- // Open nodes containing found items
- for (var i = 0; i < nodesToOpen.length; i++) {
- nodesToOpen[i].containerOpen = true;
- }
- for (var i = 0; i < nodes.length; i++) {
- var index = resultview.treeIndexForNode(nodes[i]);
- if (index == Ci.nsINavHistoryResultTreeViewer.INDEX_INVISIBLE)
- continue;
- selection.rangedSelect(index, index, true);
- }
- selection.selectEventsSuppressed = false;
- ]]></body>
- </method>
- <field name="_contextMenuShown">false</field>
- <method name="buildContextMenu">
- <parameter name="aPopup"/>
- <body><![CDATA[
- this._contextMenuShown = true;
- return this.controller.buildContextMenu(aPopup);
- ]]></body>
- </method>
- <method name="destroyContextMenu">
- <parameter name="aPopup"/>
- this._contextMenuShown = false;
- <body/>
- </method>
- <property name="ownerWindow"
- readonly="true"
- onget="return window;"/>
- <field name="_active">true</field>
- <property name="active"
- onget="return this._active"
- onset="return this._active = val"/>
- </implementation>
- <handlers>
- <handler event="focus"><![CDATA[
- this._cachedInsertionPoint = undefined;
- // See select handler. We need the sidebar's places commandset to be
- // updated as well
- document.commandDispatcher.updateCommands("focus");
- ]]></handler>
- <handler event="select"><![CDATA[
- this._cachedInsertionPoint = undefined;
- // This additional complexity is here for the sidebars
- var win = window;
- while (true) {
- win.document.commandDispatcher.updateCommands("focus");
- if (win == window.top)
- break;
- win = win.parent;
- }
- ]]></handler>
- <handler event="dragstart"><![CDATA[
- if (event.target.localName != "treechildren")
- return;
- let nodes = this.selectedNodes;
- for (let i = 0; i < nodes.length; i++) {
- let node = nodes[i];
- // Disallow dragging the root node of a tree.
- if (!node.parent) {
- event.preventDefault();
- event.stopPropagation();
- return;
- }
- // If this node is child of a readonly container (e.g. a livemark)
- // or cannot be moved, we must force a copy.
- if (!PlacesControllerDragHelper.canMoveNode(node)) {
- event.dataTransfer.effectAllowed = "copyLink";
- break;
- }
- }
- this._controller.setDataTransfer(event);
- event.stopPropagation();
- ]]></handler>
- <handler event="dragover"><![CDATA[
- if (event.target.localName != "treechildren")
- return;
- let cell = this.treeBoxObject.getCellAt(event.clientX, event.clientY);
- let node = cell.row != -1 ?
- this.view.nodeForTreeIndex(cell.row) :
- this.result.root;
- // cache the dropTarget for the view
- PlacesControllerDragHelper.currentDropTarget = node;
- // We have to calculate the orientation since view.canDrop will use
- // it and we want to be consistent with the dropfeedback.
- let tbo = this.treeBoxObject;
- let rowHeight = tbo.rowHeight;
- let eventY = event.clientY - tbo.treeBody.boxObject.y -
- rowHeight * (cell.row - tbo.getFirstVisibleRow());
- let orientation = Ci.nsITreeView.DROP_BEFORE;
- if (cell.row == -1) {
- // If the row is not valid we try to insert inside the resultNode.
- orientation = Ci.nsITreeView.DROP_ON;
- }
- else if (PlacesUtils.nodeIsContainer(node) &&
- eventY > rowHeight * 0.75) {
- // If we are below the 75% of a container the treeview we try
- // to drop after the node.
- orientation = Ci.nsITreeView.DROP_AFTER;
- }
- else if (PlacesUtils.nodeIsContainer(node) &&
- eventY > rowHeight * 0.25) {
- // If we are below the 25% of a container the treeview we try
- // to drop inside the node.
- orientation = Ci.nsITreeView.DROP_ON;
- }
- if (!this.view.canDrop(cell.row, orientation, event.dataTransfer))
- return;
- event.preventDefault();
- event.stopPropagation();
- ]]></handler>
- <handler event="dragend"><![CDATA[
- PlacesControllerDragHelper.currentDropTarget = null;
- ]]></handler>
- </handlers>
- </binding>
- </bindings>
|