dojo/dnd/Source.js

  • Provides:

    • dojo.dnd.Source
  • dojo.dnd.Source

    • type
      Function
    • chains:
      • dojo.dnd.Selector: (prototype)
      • dojo.dnd.Selector: (call)
    • summary
      a constructor of the Source
    • parameters:
      • node: (typeof DOMNode|String)
        node or node's id to build the source on
      • params: (typeof dojo.dnd.__SourceArgs)
        any property of this class may be configured via the params
        object which is mixed-in to the `dojo.dnd.Source` instance
    • source: [view]
        dojo.mixin(this, dojo.mixin({}, params));
        var type = this.accept;
        if(type.length){
         this.accept = {};
         for(var i = 0; i < type.length; ++i){
          this.accept[type[i]] = 1;
         }
        }
        // class-specific variables
        this.isDragging = false;
        this.mouseDown = false;
        this.targetAnchor = null;
        this.targetBox = null;
        this.before = true;
        this._lastX = 0;
        this._lastY = 0;
        // states
        this.sourceState = "";
        if(this.isSource){
         dojo.addClass(this.node, "dojoDndSource");
        }
        this.targetState = "";
        if(this.accept){
         dojo.addClass(this.node, "dojoDndTarget");
        }
        if(this.horizontal){
         dojo.addClass(this.node, "dojoDndHorizontal");
        }
        // set up events
        this.topics = [
         dojo.subscribe("/dnd/source/over", this, "onDndSourceOver"),
         dojo.subscribe("/dnd/start", this, "onDndStart"),
         dojo.subscribe("/dnd/drop", this, "onDndDrop"),
         dojo.subscribe("/dnd/cancel", this, "onDndCancel")
        ];
  • dojo.dnd.Source.isSource

    • summary
  • dojo.dnd.Source.horizontal

    • summary
  • dojo.dnd.Source.copyOnly

    • summary
  • dojo.dnd.Source.selfCopy

    • summary
  • dojo.dnd.Source.selfAccept

    • summary
  • dojo.dnd.Source.skipForm

    • summary
  • dojo.dnd.Source.withHandles

    • summary
  • dojo.dnd.Source.autoSync

    • summary
  • dojo.dnd.Source.delay

    • summary
  • dojo.dnd.Source.accept

    • summary
  • dojo.dnd.Source.generateText

    • summary
  • dojo.dnd.Source.checkAcceptance

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which provides items
      • nodes: (typeof Array)
        the list of transferred items
    • source: [view]
        if(this == source){
         return !this.copyOnly || this.selfAccept;
        }
        for(var i = 0; i < nodes.length; ++i){
         var type = source.getItem(nodes[i].id).type;
         // type instanceof Array
         var flag = false;
         for(var j = 0; j < type.length; ++j){
          if(type[j] in this.accept){
           flag = true;
           break;
          }
         }
         if(!flag){
          return false; // Boolean
         }
        }
        return true; // Boolean
    • summary
      checks if the target can accept nodes from this source
    • returns
      Boolean
  • dojo.dnd.Source.copyState

    • type
      Function
    • parameters:
      • keyPressed: (typeof Boolean)
        the &quot;copy&quot; key was pressed
      • self: (typeof Boolean)
        optional flag that means that we are about to drop on itself
    • source: [view]
        if(keyPressed){ return true; }
        if(arguments.length < 2){
         self = this == dojo.dnd.manager().target;
        }
        if(self){
         if(this.copyOnly){
          return this.selfCopy;
         }
        }else{
         return this.copyOnly;
        }
        return false; // Boolean
    • summary
      Returns true if we need to copy items, false to move.
      It is separated to be overwritten dynamically, if needed.
    • returns
      Boolean
  • dojo.dnd.Source.destroy

    • type
      Function
    • source: [view]
        dojo.dnd.Source.superclass.destroy.call(this);
        dojo.forEach(this.topics, dojo.unsubscribe);
        this.targetAnchor = null;
    • summary
      prepares the object to be garbage-collected
    • chains:
      • dojo.dnd.Source.superclass.destroy: (call)
  • dojo.dnd.Source.markupFactory

    • type
      Function
    • parameters:
      • params: (typeof )
      • node: (typeof )
    • source: [view]
        params._skipStartup = true;
        return new dojo.dnd.Source(node, params);
    • summary
  • dojo.dnd.Source.onMouseMove

    • type
      Function
    • parameters:
      • e: (typeof Event)
        mouse event
    • source: [view]
        if(this.isDragging && this.targetState == "Disabled"){ return; }
        dojo.dnd.Source.superclass.onMouseMove.call(this, e);
        var m = dojo.dnd.manager();
        if(!this.isDragging){
         if(this.mouseDown && this.isSource &&
           (Math.abs(e.pageX - this._lastX) > this.delay || Math.abs(e.pageY - this._lastY) > this.delay)){
          var nodes = this.getSelectedNodes();
          if(nodes.length){
           m.startDrag(this, nodes, this.copyState(dojo.isCopyKey(e), true));
          }
         }
        }
        if(this.isDragging){
         // calculate before/after
         var before = false;
         if(this.current){
          if(!this.targetBox || this.targetAnchor != this.current){
           this.targetBox = dojo.position(this.current, true);
          }
          if(this.horizontal){
           before = (e.pageX - this.targetBox.x) < (this.targetBox.w / 2);
          }else{
           before = (e.pageY - this.targetBox.y) < (this.targetBox.h / 2);
          }
         }
         if(this.current != this.targetAnchor || before != this.before){
          this._markTargetAnchor(before);
          m.canDrop(!this.current || m.source != this || !(this.current.id in this.selection));
         }
        }
    • summary
      event processor for onmousemove
    • chains:
      • dojo.dnd.Source.superclass.onMouseMove: (call)
  • dojo.dnd.Source.onMouseDown

    • type
      Function
    • parameters:
      • e: (typeof Event)
        mouse event
    • source: [view]
        if(!this.mouseDown && this._legalMouseDown(e) && (!this.skipForm || !dojo.dnd.isFormElement(e))){
         this.mouseDown = true;
         this._lastX = e.pageX;
         this._lastY = e.pageY;
         dojo.dnd.Source.superclass.onMouseDown.call(this, e);
        }
    • summary
      event processor for onmousedown
    • chains:
      • dojo.dnd.Source.superclass.onMouseDown: (call)
  • dojo.dnd.Source.onMouseUp

    • type
      Function
    • parameters:
      • e: (typeof Event)
        mouse event
    • source: [view]
        if(this.mouseDown){
         this.mouseDown = false;
         dojo.dnd.Source.superclass.onMouseUp.call(this, e);
        }
    • summary
      event processor for onmouseup
    • chains:
      • dojo.dnd.Source.superclass.onMouseUp: (call)
  • dojo.dnd.Source.onDndSourceOver

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which has the mouse over it
    • source: [view]
        if(this != source){
         this.mouseDown = false;
         if(this.targetAnchor){
          this._unmarkTargetAnchor();
         }
        }else if(this.isDragging){
         var m = dojo.dnd.manager();
         m.canDrop(this.targetState != "Disabled" && (!this.current || m.source != this || !(this.current.id in this.selection)));
        }
    • summary
      topic event processor for /dnd/source/over, called when detected a current source
  • dojo.dnd.Source.onDndStart

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which provides items
      • nodes: (typeof Array)
        the list of transferred items
      • copy: (typeof Boolean)
        copy items, if true, move items otherwise
    • source: [view]
        if(this.autoSync){ this.sync(); }
        if(this.isSource){
         this._changeState("Source", this == source ? (copy ? "Copied" : "Moved") : "");
        }
        var accepted = this.accept && this.checkAcceptance(source, nodes);
        this._changeState("Target", accepted ? "" : "Disabled");
        if(this == source){
         dojo.dnd.manager().overSource(this);
        }
        this.isDragging = true;
    • summary
      topic event processor for /dnd/start, called to initiate the DnD operation
  • dojo.dnd.Source.onDndDrop

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which provides items
      • nodes: (typeof Array)
        the list of transferred items
      • copy: (typeof Boolean)
        copy items, if true, move items otherwise
      • target: (typeof Object)
        the target which accepts items
    • source: [view]
        if(this == target){
         // this one is for us => move nodes!
         this.onDrop(source, nodes, copy);
        }
        this.onDndCancel();
    • summary
      topic event processor for /dnd/drop, called to finish the DnD operation
  • dojo.dnd.Source.onDndCancel

    • type
      Function
    • source: [view]
        if(this.targetAnchor){
         this._unmarkTargetAnchor();
         this.targetAnchor = null;
        }
        this.before = true;
        this.isDragging = false;
        this.mouseDown = false;
        this._changeState("Source", "");
        this._changeState("Target", "");
    • summary
      topic event processor for /dnd/cancel, called to cancel the DnD operation
  • dojo.dnd.Source.onDrop

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which provides items
      • nodes: (typeof Array)
        the list of transferred items
      • copy: (typeof Boolean)
        copy items, if true, move items otherwise
    • source: [view]
        if(this != source){
         this.onDropExternal(source, nodes, copy);
        }else{
         this.onDropInternal(nodes, copy);
        }
    • summary
      called only on the current target, when drop is performed
  • dojo.dnd.Source.onDropExternal

    • type
      Function
    • parameters:
      • source: (typeof Object)
        the source which provides items
      • nodes: (typeof Array)
        the list of transferred items
      • copy: (typeof Boolean)
        copy items, if true, move items otherwise
    • source: [view]
        var oldCreator = this._normalizedCreator;
        // transferring nodes from the source to the target
        if(this.creator){
         // use defined creator
         this._normalizedCreator = function(node, hint){
          return oldCreator.call(this, source.getItem(node.id).data, hint);
         };
        }else{
         // we have no creator defined => move/clone nodes
         if(copy){
          // clone nodes
          this._normalizedCreator = function(node, hint){
           var t = source.getItem(node.id);
           var n = node.cloneNode(true);
           n.id = dojo.dnd.getUniqueId();
           return {node: n, data: t.data, type: t.type};
          };
         }else{
          // move nodes
          this._normalizedCreator = function(node, hint){
           var t = source.getItem(node.id);
           source.delItem(node.id);
           return {node: node, data: t.data, type: t.type};
          };
         }
        }
        this.selectNone();
        if(!copy && !this.creator){
         source.selectNone();
        }
        this.insertNodes(true, nodes, this.before, this.current);
        if(!copy && this.creator){
         source.deleteSelectedNodes();
        }
        this._normalizedCreator = oldCreator;
    • summary
      called only on the current target, when drop is performed
      from an external source
  • dojo.dnd.Source.onDropInternal

    • type
      Function
    • parameters:
      • nodes: (typeof Array)
        the list of transferred items
      • copy: (typeof Boolean)
        copy items, if true, move items otherwise
    • source: [view]
        var oldCreator = this._normalizedCreator;
        // transferring nodes within the single source
        if(this.current && this.current.id in this.selection){
         // do nothing
         return;
        }
        if(copy){
         if(this.creator){
          // create new copies of data items
          this._normalizedCreator = function(node, hint){
           return oldCreator.call(this, this.getItem(node.id).data, hint);
          };
         }else{
          // clone nodes
          this._normalizedCreator = function(node, hint){
           var t = this.getItem(node.id);
           var n = node.cloneNode(true);
           n.id = dojo.dnd.getUniqueId();
           return {node: n, data: t.data, type: t.type};
          };
         }
        }else{
         // move nodes
         if(!this.current){
          // do nothing
          return;
         }
         this._normalizedCreator = function(node, hint){
          var t = this.getItem(node.id);
          return {node: node, data: t.data, type: t.type};
         };
        }
        this._removeSelection();
        this.insertNodes(true, nodes, this.before, this.current);
        this._normalizedCreator = oldCreator;
    • summary
      called only on the current target, when drop is performed
      from the same target/source
  • dojo.dnd.Source.onDraggingOver

    • type
      Function
    • source: [view]
        // summary:
        //  called during the active DnD operation, when items
        //  are dragged over this target, and it is not disabled
    • summary
      called during the active DnD operation, when items
      are dragged over this target, and it is not disabled
  • dojo.dnd.Source.onDraggingOut

    • type
      Function
    • source: [view]
        // summary:
        //  called during the active DnD operation, when items
        //  are dragged away from this target, and it is not disabled
    • summary
      called during the active DnD operation, when items
      are dragged away from this target, and it is not disabled
  • dojo.dnd.Source.onOverEvent

    • type
      Function
    • source: [view]
        dojo.dnd.Source.superclass.onOverEvent.call(this);
        dojo.dnd.manager().overSource(this);
        if(this.isDragging && this.targetState != "Disabled"){
         this.onDraggingOver();
        }
    • summary
      this function is called once, when mouse is over our container
    • chains:
      • dojo.dnd.Source.superclass.onOverEvent: (call)
  • dojo.dnd.Source.onOutEvent

    • type
      Function
    • source: [view]
        dojo.dnd.Source.superclass.onOutEvent.call(this);
        dojo.dnd.manager().outSource(this);
        if(this.isDragging && this.targetState != "Disabled"){
         this.onDraggingOut();
        }
    • summary
      this function is called once, when mouse is out of our container
    • chains:
      • dojo.dnd.Source.superclass.onOutEvent: (call)
  • dojo.dnd.Source._markTargetAnchor

    • type
      Function
    • parameters:
      • before: (typeof Boolean)
        insert before, if true, after otherwise
    • source: [view]
        if(this.current == this.targetAnchor && this.before == before){ return; }
        if(this.targetAnchor){
         this._removeItemClass(this.targetAnchor, this.before ? "Before" : "After");
        }
        this.targetAnchor = this.current;
        this.targetBox = null;
        this.before = before;
        if(this.targetAnchor){
         this._addItemClass(this.targetAnchor, this.before ? "Before" : "After");
        }
    • summary
      assigns a class to the current target anchor based on &quot;before&quot; status
  • dojo.dnd.Source._unmarkTargetAnchor

    • type
      Function
    • source: [view]
        if(!this.targetAnchor){ return; }
        this._removeItemClass(this.targetAnchor, this.before ? "Before" : "After");
        this.targetAnchor = null;
        this.targetBox = null;
        this.before = true;
    • summary
      removes a class of the current target anchor based on &quot;before&quot; status
  • dojo.dnd.Source._markDndStatus

    • type
      Function
    • parameters:
      • copy: (typeof )
    • source: [view]
        this._changeState("Source", copy ? "Copied" : "Moved");
    • summary
      changes source's state based on &quot;copy&quot; status
  • dojo.dnd.Source._legalMouseDown

    • type
      Function
    • parameters:
      • e: (typeof Event)
        mouse event
        
        accept only the left mouse button
    • source: [view]
        if(!dojo.mouseButtons.isLeft(e)){ return false; }

        
        if(!this.withHandles){ return true; }

        
        // check for handles
        for(var node = e.target; node && node !== this.node; node = node.parentNode){
         if(dojo.hasClass(node, "dojoDndHandle")){ return true; }
         if(dojo.hasClass(node, "dojoDndItem") || dojo.hasClass(node, "dojoDndIgnore")){ break; }
        }
        return false; // Boolean
    • summary
      checks if user clicked on &quot;approved&quot; items
    • returns
      Boolean
  • dojo.dnd.Source.targetAnchor

    • summary
  • dojo.dnd.Source.targetState

    • summary
  • dojo.dnd.Source.targetBox

    • summary
  • dojo.dnd.Source.mouseDown

    • summary
  • dojo.dnd.Source._lastX

    • summary
  • dojo.dnd.Source._lastY

    • summary
  • dojo.dnd.Source.isDragging

    • summary
  • dojo.dnd.Source.before

    • summary
  • dojo.dnd.Source._normalizedCreator

    • summary
  • dojo.dnd.Source.onDropExternal._normalizedCreator

    • type
      Function
    • parameters:
      • node: (typeof )
      • hint: (typeof )
    • source: [view]
           var t = source.getItem(node.id);
           source.delItem(node.id);
           return {node: node, data: t.data, type: t.type};
    • chains:
      • oldCreator: (call)
    • summary
  • dojo.dnd.Source.onDropInternal._normalizedCreator

    • type
      Function
    • parameters:
      • node: (typeof )
      • hint: (typeof )
    • source: [view]
          var t = this.getItem(node.id);
          return {node: node, data: t.data, type: t.type};
    • chains:
      • oldCreator: (call)
    • summary
  • dojo.dnd.Source.current

    • summary
  • dojo.dnd.Source._markTargetAnchor.before

    • type
      Boolean
    • summary
      insert before, if true, after otherwise
  • dojo.dnd.Source.sourceState

    • summary
  • dojo.dnd.Source.topics

    • summary
  • dojo.dnd.Target

    • type
      Function
    • chains:
      • dojo.dnd.Source: (prototype)
      • dojo.dnd.Source: (call)
    • summary
      a constructor of the Target --- see the `dojo.dnd.Source.constructor` for details
    • parameters:
      • node: (typeof )
      • params: (typeof )
    • source: [view]
        this.isSource = false;
        dojo.removeClass(this.node, "dojoDndSource");
  • dojo.dnd.Target.markupFactory

    • type
      Function
    • parameters:
      • params: (typeof )
      • node: (typeof )
    • source: [view]
        params._skipStartup = true;
        return new dojo.dnd.Target(node, params);
    • summary
  • dojo.dnd.Target.isSource

    • summary
  • dojo.dnd.AutoSource

    • type
      Function
    • chains:
      • dojo.dnd.Source: (prototype)
      • dojo.dnd.Source: (call)
    • summary
      constructor of the AutoSource --- see the Source constructor for details
    • parameters:
      • node: (typeof )
      • params: (typeof )
    • source: [view]
        this.autoSync = true;
  • dojo.dnd.AutoSource.markupFactory

    • type
      Function
    • parameters:
      • params: (typeof )
      • node: (typeof )
    • source: [view]
        params._skipStartup = true;
        return new dojo.dnd.AutoSource(node, params);
    • summary
  • dojo.dnd.AutoSource.autoSync

    • summary
  • dojo.dnd.__SourceArgs

    • type
      Function
    • source: [view]
       this.isSource = isSource;
       this.accept = accept;
       this.autoSync = autoSync;
       this.copyOnly = copyOnly;
       this.delay = delay;
       this.horizontal = horizontal;
       this.selfCopy = selfCopy;
       this.selfAccept = selfAccept;
       this.withHandles = withHandles;
       this.generateText = true;
    • summary
      a dict of parameters for DnD Source configuration. Note that any
      property on Source elements may be configured, but this is the
      short-list
  • dojo.dnd.__SourceArgs.isSource

    • type
      Boolean?
    • summary
      can be used as a DnD source. Defaults to true.
  • dojo.dnd.__SourceArgs.accept

    • type
      Array?
    • summary
      list of accepted types (text strings) for a target; defaults to
      [&quot;text&quot;]
  • dojo.dnd.__SourceArgs.autoSync

    • type
      Boolean
    • summary
      if true refreshes the node list on every operation; false by default
  • dojo.dnd.__SourceArgs.copyOnly

    • type
      Boolean?
    • summary
      copy items, if true, use a state of Ctrl key otherwise,
      see selfCopy and selfAccept for more details
  • dojo.dnd.__SourceArgs.delay

    • type
      Number
    • summary
      the move delay in pixels before detecting a drag; 0 by default
  • dojo.dnd.__SourceArgs.horizontal

    • type
      Boolean?
    • summary
      a horizontal container, if true, vertical otherwise or when omitted
  • dojo.dnd.__SourceArgs.selfCopy

    • type
      Boolean?
    • summary
      copy items by default when dropping on itself,
      false by default, works only if copyOnly is true
  • dojo.dnd.__SourceArgs.selfAccept

    • type
      Boolean?
    • summary
      accept its own items when copyOnly is true,
      true by default, works only if copyOnly is true
  • dojo.dnd.__SourceArgs.withHandles

    • type
      Boolean?
    • summary
      allows dragging only by handles, false by default
  • dojo.dnd.__SourceArgs.generateText

    • type
      Boolean?
    • summary
      generate text node for drag and drop, true by default
  • this

    • mixins:
      • dojo.mixin({}, params): (normal)
    • summary
  • dojo.dnd

    • type
      Object
    • summary
  • dojo

    • type
      Object
    • summary