gojs Diagram Events(图表事件)

事件(Events)

GoJS涵盖了三种基本事件:DiagramEvents(图表事件)、InputEvents(输入事件)以及ChangedEvents(变更事件)。这一页我们讨论前两种事件;至于最后一种事件请见 Changed Events

1、图表事件(Diagram Events)

DiagramEvent(图表事件)表示一般用户发起的对图表的改变。你可以通过调用Diagram.addDiagramListener注册图表事件处理程序。各个图表事件以名字区分。

目前定义了的图表事件名称包括:

更多详细内容,请见文档DiagramEvent

图表事件并不一定与鼠标/键盘或者触摸事件相对应。它们也不一定与图表模型的变化相对应——要跟踪这些变化,使用Model.addChangedListener或者Diagram.addModelChangedListener。当用户做了什么或者间接做了什么时,图表事件才会产生。

除了图表事件监听器之外,还有一些情况是,当发现一些变动足以表明一些属性是事件处理程序。由于这些事件并不一定需要与任何特殊的输入或者图表事件对应,座椅这些事件处理程序就会有特定于情况的自定义参数。

一个非常常见的事件属性是GraphObject.click,它指的是无论何时用户点击一个对象时调用的一个非空的函数。它最常用于为按钮指定行为,但是它与其他的点击事件属性,双击和右键点击,对于任何GraphObject都是有用的。

另外一个常见的事件属性是Part.selectionChanged,它指的是当Part.isSelected改变时调用的一个非空函数。在下面的示例中,事件处理函数有一个参数,该Part。由于函数能够检查Part.isSelected的当前值从而决定要做什么,所以不需要其余的参数。

模型的ChangedEvent事件比基于DiagramEvent更完成可靠。例如,当在代码里为图表增加一条连接线时,"LinkDrawn" 图表事件不会被调用。图表事件只有在用户用 LinkingTool 添加一条新的连接线时才被调用。另外,连接线没有被改变路线,因此Link.points不会被计算。事实上,创建一条新的连接线可能会使一个Layout失效,因此,所有的节点都可能会在不久后被移动。

有时候用户对图标做了一些改动,你需要更新数据库。 通常,你会想要执行一个Model ChangedEvent监听器, 通过调用Model.addChangedListener或者Diagram.addModelChangedListener, 然后把这些改变通知给模型层,再决定把哪些记录到数据库里。请查看关于Changed EventsUpdate Demo的讨论.

这个示例展示了几个图表事件:"ObjectSingleClicked"(单机对象),"BackgroundDoubleClicked"(双击背景), 和"ClipboardPasted"(剪贴板复制)。

例子:

function showMessage(s) {
    document.getElementById("diagramEventsMsg").textContent = s;
}

// 为diagram添加一个“对象单机”事件
diagram.addDiagramListener("ObjectSingleClicked",      
    function(e) {
        var part = e.subject.part;
        //如果鼠标单机的不是连接线,则显示信息:"Clicked on" +  鼠标点击的目标的key值      
        if (!(part instanceof go.Link)) showMessage("Clicked on " + part.data.key);
    }
);

//为diagram添加“背景双击”事件
diagram.addDiagramListener("BackgroundDoubleClicked",      
    function(e) { 
        //显示信息: “Double-clicked at” + 点击的点的坐标值
        showMessage("Double-clicked at " + e.diagram.lastInput.documentPoint); 
    }
);

//为diagram添加“剪贴板复制粘贴”事件
diagram.addDiagramListener("ClipboardPasted",      
    function(e) {
        //复制某个节点Part后,粘贴时,显示信息:“Pasted” + 复制粘贴的节点数量
        showMessage("Pasted " + e.diagram.selection.count + " parts"); 
    }
);  

var nodeDataArray = [
    { key: "Alpha" },
    { key: "Beta", group: "Omega" },
    { key: "Gamma", group: "Omega" },
    { key: "Omega", isGroup: true },
    { key: "Delta" }
];  
var linkDataArray = [
    { from: "Alpha", to: "Beta" },  // 从Group外指向Group内
    { from: "Beta", to: "Gamma" },  // 这条连接线是Group内部的
    { from: "Omega", to: "Delta" }  // 从Group指向一个节点
];
  diagram.model = new go.GraphLinksModel(nodeDataArray, linkDataArray);

2、输入事件

当发生低级HTML DOM事件时,GoJS会将键盘/鼠标/触摸事件信息规范化转换为一个能够被传递给各种事件处理方法且为后面的检查而保存的新的 InputEvent(输入事件)。

一个输入事件,用InputEvent.key存放键盘事件, 用InputEvent.button存放鼠标事件, 用InputEvent.viewPoint存放鼠标和触摸事件, 用InputEvent.modifiers存放键盘和鼠标事件。

图表的事件处理程序同时也记录InputEvent.documentPoint,也就是鼠标事件发生时的文档坐标 InputEvent.viewPoint ,以及事件发生时的以毫秒为单位的时间戳 InputEvent.timestamp

输入事件类还未特定类型的事件提供了很多很便利的属性。比如,InputEvent.control (如果按下控制键)和InputEvent.left (如果按下左/主鼠标按钮)。

一些工具在鼠标点击的点可以找到当前的GraphObject(图形对象)。这些图形对象就被记为InputEvent.targetObject

3、高级输入事件

一些工具能检测一系列的输入事件以组成一些更抽象的用户事件。比如说,“点击”(鼠标迅速的按下并放开)和“悬停”(鼠标静止不动一段时间)。这些工具会为当前鼠标所在的点对应的GrapgObject调用一个事件处理程序(如果有的话)。这个事件处理程序被当做对象的一个属性值。它还会沿着 GraphObject.panel的链向上冒泡知道这个Part结束。这允许了一个“点击”事件在一个Panel上被申明并应用,即使实际的点击是发生在Panel内部的元素上的。如果鼠标所在的点没有对象,那时间就会发生在最外层的图表上。

类似的点击事件属性包括 GraphObject.clickGraphObject.doubleClick, 和 GraphObject.contextClick。即便没有GraphObject时,这些事件也会发生——事件会发生在图表的背景上发生:Diagram.clickDiagram.doubleClick, 和 Diagram.contextClick。这些都是你可以设置为事件处理程序的函数。这些事件是由鼠标事件和触摸事件引起的。

类似的鼠标移入事件属性包括GraphObject.mouseEnterGraphObject.mouseOverGraphObject.mouseLeave。但是只有Diagram.mouseOver会被应用到图表上。

类似的鼠标悬停事件属性包括 GraphObject.mouseHoverGraphObject.mouseHold。等价的图表属性是Diagram.mouseHoverDiagram.mouseHold.

拖拽操作也有对应的事件属性:GraphObject.mouseDragEnterGraphObject.mouseDragLeave, 和GraphObject.mouseDrop. 他们适用于静止的对象,而不是被拖动中的对象。同时,他们也适用于触摸事件的拖拽,而不仅仅是鼠标事件的拖拽。

下面的示例展示了三个高级输入事件:点击节点、进入/离开group(组)。

function showMessage(s) {
    document.getElementById("inputEventsMsg").textContent = s;
  }

  diagram.nodeTemplate =
    $(go.Node, "Auto",
      $(go.Shape, "Ellipse", { fill: "white" }),
      $(go.TextBlock,        
        new go.Binding("text", "key")),
      { click: function(e, obj) { showMessage("Clicked on " + obj.part.data.key); } }
    );

  diagram.groupTemplate =
    $(go.Group, "Vertical",
      $(go.TextBlock,
        { alignment: go.Spot.Left, font: "Bold 12pt Sans-Serif" },        
        new go.Binding("text", "key")),
      $(go.Panel, "Auto",
        $(go.Shape, "RoundedRectangle",
          { name: "SHAPE",
            parameter1: 14,
            fill: "rgba(128,128,128,0.33)" }),
        $(go.Placeholder, { padding: 5 })
      ),
      { mouseEnter: function(e, obj, prev) {  // 改变group的背景画笔
            var shape = obj.part.findObject("SHAPE");            
            if (shape) shape.fill = "red";
          },
        mouseLeave: function(e, obj, next) {  // 回复原始的画笔
            var shape = obj.part.findObject("SHAPE");            
            if (shape) shape.fill = "rgba(128,128,128,0.33)";
          } });  
          
  var nodeDataArray = [
    { key: "Alpha" },
    { key: "Beta", group: "Omega" },
    { key: "Gamma", group: "Omega" },
    { key: "Omega", isGroup: true },
    { key: "Delta" }
  ];  
  
  var linkDataArray = [
    { from: "Alpha", to: "Beta" },  // 从Group外指向Group内
    { from: "Beta", to: "Gamma" },  // 这条连接线是Group内部的
    { from: "Omega", to: "Delta" }  // 从Group指向一个节点
  ];
  diagram.model = new go.GraphLinksModel(nodeDataArray, linkDataArray);

3、点击与选中

这个示例同时展示了“点击”和“selectionChanged”事件:

function showMessage(s) {
    document.getElementById("changeMethodsMsg").textContent = s;
  }

  diagram.nodeTemplate =
    $(go.Node, "Auto",
      { selectionAdorned: false },
      $(go.Shape, "Ellipse", { fill: "white" }),
      $(go.TextBlock,        
      new go.Binding("text", "key")),
      {
        click: function(e, obj) { showMessage("Clicked on " + obj.part.data.key); },
        selectionChanged: function(part) {
            var shape = part.elt(0);
            shape.fill = part.isSelected ? "red" : "white";
          }
      }
    );  
  var nodeDataArray = [
    { key: "Alpha" }, { key: "Beta" }, { key: "Gamma" }
  ];  
  
  var linkDataArray = [
    { from: "Alpha", to: "Beta" },
    { from: "Beta", to: "Gamma" }
  ];
  diagram.model = new go.GraphLinksModel(nodeDataArray, linkDataArray);

试着按下“Ctrl-A”可以全选所有的对象。注意 GraphObject.click事件属性与Part.selectionChanged事件属性的区别。当节点上发生什么事情时,两个方法都能被调用。GraphObject.click事件会在用户点击节点时发生,选中了节点。但是Part.selectionChanged事件在没有点击事件(或者任何鼠标事件)时就会发生——这是由于节点的一个属性值变了

猜你喜欢

转载自blog.csdn.net/pdw2009/article/details/82993971
今日推荐