protected internal override void ExecuteDefaultAction(EventBase evt) { base.ExecuteDefaultAction(evt); if (evt.GetEventTypeId() == MouseOverEvent.TypeId() || evt.GetEventTypeId() == MouseOutEvent.TypeId()) { UpdateCursorStyle(evt.GetEventTypeId()); } else if (evt.GetEventTypeId() == MouseEnterEvent.TypeId()) { pseudoStates |= PseudoStates.Hover; } else if (evt.GetEventTypeId() == MouseLeaveEvent.TypeId()) { pseudoStates &= ~PseudoStates.Hover; } else if (evt.GetEventTypeId() == BlurEvent.TypeId()) { pseudoStates = pseudoStates & ~PseudoStates.Focus; } else if (evt.GetEventTypeId() == FocusEvent.TypeId()) { pseudoStates = pseudoStates | PseudoStates.Focus; } }
private void DispatchMouseEnterMouseLeave(VisualElement previousTopElementUnderMouse, VisualElement currentTopElementUnderMouse, IMouseEvent triggerEvent) { if (previousTopElementUnderMouse != currentTopElementUnderMouse) { int i = 0; VisualElement visualElement; for (visualElement = previousTopElementUnderMouse; visualElement != null; visualElement = visualElement.shadow.parent) { i++; } int j = 0; VisualElement visualElement2; for (visualElement2 = currentTopElementUnderMouse; visualElement2 != null; visualElement2 = visualElement2.shadow.parent) { j++; } visualElement = previousTopElementUnderMouse; visualElement2 = currentTopElementUnderMouse; while (i > j) { MouseLeaveEvent pooled = MouseEventBase <MouseLeaveEvent> .GetPooled(triggerEvent); pooled.target = visualElement; this.DispatchEvent(pooled, visualElement.panel); EventBase <MouseLeaveEvent> .ReleasePooled(pooled); i--; visualElement = visualElement.shadow.parent; } List <VisualElement> list = new List <VisualElement>(j); while (j > i) { list.Add(visualElement2); j--; visualElement2 = visualElement2.shadow.parent; } while (visualElement != visualElement2) { MouseLeaveEvent pooled2 = MouseEventBase <MouseLeaveEvent> .GetPooled(triggerEvent); pooled2.target = visualElement; this.DispatchEvent(pooled2, visualElement.panel); EventBase <MouseLeaveEvent> .ReleasePooled(pooled2); list.Add(visualElement2); visualElement = visualElement.shadow.parent; visualElement2 = visualElement2.shadow.parent; } for (int k = list.Count - 1; k >= 0; k--) { MouseEnterEvent pooled3 = MouseEventBase <MouseEnterEvent> .GetPooled(triggerEvent); pooled3.target = list[k]; this.DispatchEvent(pooled3, list[k].panel); EventBase <MouseEnterEvent> .ReleasePooled(pooled3); } } }
void DispatchMouseEnterMouseLeave(VisualElement previousTopElementUnderMouse, VisualElement currentTopElementUnderMouse, IMouseEvent triggerEvent) { DispatchEnterLeave(previousTopElementUnderMouse, currentTopElementUnderMouse, () => MouseEnterEvent.GetPooled(triggerEvent), () => MouseLeaveEvent.GetPooled(triggerEvent)); }
void DispatchMouseEnterMouseLeave(VisualElement previousTopElementUnderMouse, VisualElement currentTopElementUnderMouse, Event triggerEvent) { if (previousTopElementUnderMouse == currentTopElementUnderMouse) { return; } // We want to find the common ancestor CA of previousTopElementUnderMouse and currentTopElementUnderMouse, // send MouseLeave events to elements between CA and previousTopElementUnderMouse // and send MouseEnter events to elements between CA and currentTopElementUnderMouse. int prevDepth = 0; var p = previousTopElementUnderMouse; while (p != null) { prevDepth++; p = p.shadow.parent; } int currDepth = 0; var c = currentTopElementUnderMouse; while (c != null) { currDepth++; c = c.shadow.parent; } p = previousTopElementUnderMouse; c = currentTopElementUnderMouse; while (prevDepth > currDepth) { using (var leaveEvent = MouseLeaveEvent.GetPooled(triggerEvent)) { leaveEvent.target = p; DispatchEvent(leaveEvent, p.panel); } prevDepth--; p = p.shadow.parent; } // We want to send enter events after all the leave events. // We will store the elements being entered in this list. List <VisualElement> enteringElements = new List <VisualElement>(currDepth); while (currDepth > prevDepth) { enteringElements.Add(c); currDepth--; c = c.shadow.parent; } // Now p and c are at the same depth. Go up the tree until p == c. while (p != c) { using (var leaveEvent = MouseLeaveEvent.GetPooled(triggerEvent)) { leaveEvent.target = p; DispatchEvent(leaveEvent, p.panel); } enteringElements.Add(c); p = p.shadow.parent; c = c.shadow.parent; } for (var i = enteringElements.Count - 1; i >= 0; i--) { using (var enterEvent = MouseEnterEvent.GetPooled(triggerEvent)) { enterEvent.target = enteringElements[i]; DispatchEvent(enterEvent, enteringElements[i].panel); } } }
public void DispatchEvent(EventBase evt, IPanel panel) { Event e = evt.imguiEvent; if (e != null && e.type == EventType.Repaint) { return; } if (panel != null && panel.panelDebug != null && panel.panelDebug.enabled && panel.panelDebug.interceptEvents != null) { if (panel.panelDebug.interceptEvents(e)) { evt.StopPropagation(); return; } } bool invokedHandleEvent = false; VisualElement captureVE = null; // Send all IMGUI events (for backward compatibility) and MouseEvents (because thats what we want to do in the new system) // to the capture, if there is one. if ((evt is IMouseEvent || e != null) && MouseCaptureController.mouseCapture != null) { captureVE = MouseCaptureController.mouseCapture as VisualElement; if (captureVE != null && captureVE.panel == null) { Debug.Log(String.Format("Capture has no panel, forcing removal (capture={0} eventType={1})", MouseCaptureController.mouseCapture, e != null ? e.type.ToString() : "null")); MouseCaptureController.ReleaseMouseCapture(); captureVE = null; } if (panel != null) { if (captureVE != null && captureVE.panel.contextType != panel.contextType) { return; } } invokedHandleEvent = true; evt.dispatch = true; if (MouseCaptureController.mouseCapture != null) { evt.target = MouseCaptureController.mouseCapture; evt.currentTarget = MouseCaptureController.mouseCapture; evt.propagationPhase = PropagationPhase.AtTarget; MouseCaptureController.mouseCapture.HandleEvent(evt); } evt.propagationPhase = PropagationPhase.None; evt.currentTarget = null; evt.dispatch = false; } if (evt.isPropagationStopped) { // Make sure to call default actions at target, but dont call it twice on mouse capture if (evt.target == null && panel != null) { evt.target = panel.visualTree; } if (evt.target != null && evt.target != MouseCaptureController.mouseCapture) { evt.dispatch = true; evt.currentTarget = evt.target; evt.propagationPhase = PropagationPhase.AtTarget; evt.target.HandleEvent(evt); evt.propagationPhase = PropagationPhase.None; evt.currentTarget = null; evt.dispatch = false; } } if (!evt.isPropagationStopped) { if (evt is IKeyboardEvent && panel != null) { if (panel.focusController.focusedElement != null) { IMGUIContainer imguiContainer = panel.focusController.focusedElement as IMGUIContainer; invokedHandleEvent = true; if (imguiContainer != null) { if (imguiContainer.HandleIMGUIEvent(evt.imguiEvent)) { evt.StopPropagation(); evt.PreventDefault(); } } else { evt.target = panel.focusController.focusedElement; PropagateEvent(evt); } } else { evt.target = panel.visualTree; PropagateEvent(evt); // Force call to PropagateToIMGUIContainer(), even if capture != null. invokedHandleEvent = false; } } else if (evt.GetEventTypeId() == MouseEnterEvent.TypeId() || evt.GetEventTypeId() == MouseLeaveEvent.TypeId()) { Debug.Assert(evt.target != null); invokedHandleEvent = true; PropagateEvent(evt); } else if (evt is IMouseEvent || ( e != null && ( e.type == EventType.ContextClick || e.type == EventType.DragUpdated || e.type == EventType.DragPerform || e.type == EventType.DragExited ) )) { // FIXME: we should not change hover state when capture is true. // However, when doing drag and drop, drop target should be highlighted. // TODO when EditorWindow is docked MouseLeaveWindow is not always sent // this is a problem in itself but it could leave some elements as "hover" VisualElement currentTopElementUnderMouse = m_TopElementUnderMouse; if (evt.GetEventTypeId() == MouseLeaveWindowEvent.TypeId()) { m_TopElementUnderMouse = null; DispatchMouseEnterMouseLeave(currentTopElementUnderMouse, m_TopElementUnderMouse, e); DispatchMouseOverMouseOut(currentTopElementUnderMouse, m_TopElementUnderMouse, e); } // update element under mouse and fire necessary events else if (evt is IMouseEvent || e != null) { if (evt.target == null && panel != null) { if (evt is IMouseEvent) { m_TopElementUnderMouse = panel.Pick((evt as IMouseEvent).localMousePosition); } else if (e != null) { m_TopElementUnderMouse = panel.Pick(e.mousePosition); } evt.target = m_TopElementUnderMouse; } if (evt.target != null) { invokedHandleEvent = true; PropagateEvent(evt); } if (evt.GetEventTypeId() == MouseMoveEvent.TypeId() || evt.GetEventTypeId() == MouseEnterWindowEvent.TypeId() || evt.GetEventTypeId() == WheelEvent.TypeId() || (e != null && e.type == EventType.DragUpdated)) { DispatchMouseEnterMouseLeave(currentTopElementUnderMouse, m_TopElementUnderMouse, e); DispatchMouseOverMouseOut(currentTopElementUnderMouse, m_TopElementUnderMouse, e); } } } else if (panel != null && e != null && (e.type == EventType.ExecuteCommand || e.type == EventType.ValidateCommand)) { IMGUIContainer imguiContainer = panel.focusController.focusedElement as IMGUIContainer; if (imguiContainer != null) { invokedHandleEvent = true; if (imguiContainer.HandleIMGUIEvent(evt.imguiEvent)) { evt.StopPropagation(); evt.PreventDefault(); } } else if (panel.focusController.focusedElement != null) { invokedHandleEvent = true; evt.target = panel.focusController.focusedElement; PropagateEvent(evt); } else { invokedHandleEvent = true; PropagateToIMGUIContainer(panel.visualTree, evt, captureVE); } } else if (evt is IPropagatableEvent || evt is IFocusEvent || evt is IChangeEvent || evt.GetEventTypeId() == InputEvent.TypeId() || evt.GetEventTypeId() == PostLayoutEvent.TypeId()) { Debug.Assert(evt.target != null); invokedHandleEvent = true; PropagateEvent(evt); } } if (!evt.isPropagationStopped && e != null && panel != null) { if (!invokedHandleEvent || e != null && ( e.type == EventType.MouseEnterWindow || e.type == EventType.MouseLeaveWindow || e.type == EventType.Used )) { PropagateToIMGUIContainer(panel.visualTree, evt, captureVE); } } if (evt.target == null && panel != null) { evt.target = panel.visualTree; } ExecuteDefaultAction(evt); }
void DispatchMouseEnterMouseLeave(VisualElement previousTopElementUnderMouse, VisualElement currentTopElementUnderMouse, IMouseEvent triggerEvent) { if (triggerEvent != null) { DispatchEnterLeave(previousTopElementUnderMouse, currentTopElementUnderMouse, () => MouseEnterEvent.GetPooled(triggerEvent), () => MouseLeaveEvent.GetPooled(triggerEvent)); } else { DispatchEnterLeave(previousTopElementUnderMouse, currentTopElementUnderMouse, () => MouseEnterEvent.GetPooled(m_LastMousePosition), () => MouseLeaveEvent.GetPooled(m_LastMousePosition)); } }