You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

273 lines
6.0KB

  1. #include "widget/event.hpp"
  2. #include "widget/Widget.hpp"
  3. namespace rack {
  4. namespace widget {
  5. void EventState::setHovered(Widget *w) {
  6. if (w == hoveredWidget)
  7. return;
  8. if (hoveredWidget) {
  9. // LeaveEvent
  10. LeaveEvent eLeave;
  11. hoveredWidget->onLeave(eLeave);
  12. hoveredWidget = NULL;
  13. }
  14. if (w) {
  15. // EnterEvent
  16. EventContext cEnter;
  17. EnterEvent eEnter;
  18. eEnter.context = &cEnter;
  19. w->onEnter(eEnter);
  20. hoveredWidget = cEnter.consumed;
  21. }
  22. }
  23. void EventState::setDragged(Widget *w) {
  24. if (w == draggedWidget)
  25. return;
  26. if (draggedWidget) {
  27. // DragEndEvent
  28. DragEndEvent eDragEnd;
  29. draggedWidget->onDragEnd(eDragEnd);
  30. draggedWidget = NULL;
  31. }
  32. if (w) {
  33. // DragStartEvent
  34. EventContext cDragStart;
  35. DragStartEvent eDragStart;
  36. eDragStart.context = &cDragStart;
  37. w->onDragStart(eDragStart);
  38. draggedWidget = cDragStart.consumed;
  39. }
  40. }
  41. void EventState::setDragHovered(Widget *w) {
  42. if (w == dragHoveredWidget)
  43. return;
  44. if (dragHoveredWidget) {
  45. // DragLeaveEvent
  46. DragLeaveEvent eDragLeave;
  47. eDragLeave.origin = draggedWidget;
  48. dragHoveredWidget->onDragLeave(eDragLeave);
  49. dragHoveredWidget = NULL;
  50. }
  51. if (w) {
  52. // DragEnterEvent
  53. EventContext cDragEnter;
  54. DragEnterEvent eDragEnter;
  55. eDragEnter.context = &cDragEnter;
  56. eDragEnter.origin = draggedWidget;
  57. w->onDragEnter(eDragEnter);
  58. dragHoveredWidget = cDragEnter.consumed;
  59. }
  60. }
  61. void EventState::setSelected(Widget *w) {
  62. if (w == selectedWidget)
  63. return;
  64. if (selectedWidget) {
  65. // DeselectEvent
  66. DeselectEvent eDeselect;
  67. selectedWidget->onDeselect(eDeselect);
  68. selectedWidget = NULL;
  69. }
  70. if (w) {
  71. // SelectEvent
  72. EventContext cSelect;
  73. SelectEvent eSelect;
  74. eSelect.context = &cSelect;
  75. w->onSelect(eSelect);
  76. selectedWidget = cSelect.consumed;
  77. }
  78. }
  79. void EventState::finalizeWidget(Widget *w) {
  80. if (hoveredWidget == w) setHovered(NULL);
  81. if (draggedWidget == w) setDragged(NULL);
  82. if (dragHoveredWidget == w) setDragHovered(NULL);
  83. if (selectedWidget == w) setSelected(NULL);
  84. if (lastClickedWidget == w) lastClickedWidget = NULL;
  85. }
  86. void EventState::handleButton(math::Vec pos, int button, int action, int mods) {
  87. // ButtonEvent
  88. EventContext cButton;
  89. ButtonEvent eButton;
  90. eButton.context = &cButton;
  91. eButton.pos = pos;
  92. eButton.button = button;
  93. eButton.action = action;
  94. eButton.mods = mods;
  95. rootWidget->onButton(eButton);
  96. Widget *clickedWidget = cButton.consumed;
  97. if (button == GLFW_MOUSE_BUTTON_LEFT) {
  98. if (action == GLFW_PRESS) {
  99. setDragged(clickedWidget);
  100. }
  101. if (action == GLFW_RELEASE) {
  102. setDragHovered(NULL);
  103. if (clickedWidget && draggedWidget) {
  104. // DragDropEvent
  105. DragDropEvent eDragDrop;
  106. eDragDrop.origin = draggedWidget;
  107. clickedWidget->onDragDrop(eDragDrop);
  108. }
  109. setDragged(NULL);
  110. }
  111. if (action == GLFW_PRESS) {
  112. setSelected(clickedWidget);
  113. }
  114. if (action == GLFW_PRESS) {
  115. const double doubleClickDuration = 0.3;
  116. double clickTime = glfwGetTime();
  117. if (clickedWidget
  118. && clickTime - lastClickTime <= doubleClickDuration
  119. && lastClickedWidget == clickedWidget) {
  120. // DoubleClickEvent
  121. DoubleClickEvent eDoubleClick;
  122. clickedWidget->onDoubleClick(eDoubleClick);
  123. // Reset double click
  124. lastClickTime = -INFINITY;
  125. lastClickedWidget = NULL;
  126. }
  127. else {
  128. lastClickTime = clickTime;
  129. lastClickedWidget = clickedWidget;
  130. }
  131. }
  132. }
  133. }
  134. void EventState::handleHover(math::Vec pos, math::Vec mouseDelta) {
  135. if (draggedWidget) {
  136. // DragMoveEvent
  137. DragMoveEvent eDragMove;
  138. eDragMove.mouseDelta = mouseDelta;
  139. draggedWidget->onDragMove(eDragMove);
  140. // DragHoverEvent
  141. EventContext cDragHover;
  142. DragHoverEvent eDragHover;
  143. eDragHover.context = &cDragHover;
  144. eDragHover.pos = pos;
  145. eDragHover.mouseDelta = mouseDelta;
  146. eDragHover.origin = draggedWidget;
  147. rootWidget->onDragHover(eDragHover);
  148. setDragHovered(cDragHover.consumed);
  149. return;
  150. }
  151. // HoverEvent
  152. EventContext cHover;
  153. HoverEvent eHover;
  154. eHover.context = &cHover;
  155. eHover.pos = pos;
  156. eHover.mouseDelta = mouseDelta;
  157. rootWidget->onHover(eHover);
  158. setHovered(cHover.consumed);
  159. }
  160. void EventState::handleLeave() {
  161. setDragHovered(NULL);
  162. setHovered(NULL);
  163. }
  164. void EventState::handleScroll(math::Vec pos, math::Vec scrollDelta) {
  165. // HoverScrollEvent
  166. EventContext cHoverScroll;
  167. HoverScrollEvent eHoverScroll;
  168. eHoverScroll.context = &cHoverScroll;
  169. eHoverScroll.pos = pos;
  170. eHoverScroll.scrollDelta = scrollDelta;
  171. rootWidget->onHoverScroll(eHoverScroll);
  172. }
  173. void EventState::handleDrop(math::Vec pos, const std::vector<std::string> &paths) {
  174. // PathDropEvent
  175. EventContext cPathDrop;
  176. PathDropEvent ePathDrop(paths);
  177. ePathDrop.context = &cPathDrop;
  178. ePathDrop.pos = pos;
  179. rootWidget->onPathDrop(ePathDrop);
  180. }
  181. void EventState::handleText(math::Vec pos, int codepoint) {
  182. if (selectedWidget) {
  183. // SelectTextEvent
  184. EventContext cSelectText;
  185. SelectTextEvent eSelectText;
  186. eSelectText.context = &cSelectText;
  187. eSelectText.codepoint = codepoint;
  188. selectedWidget->onSelectText(eSelectText);
  189. if (cSelectText.consumed)
  190. return;
  191. }
  192. // HoverTextEvent
  193. EventContext cHoverText;
  194. HoverTextEvent eHoverText;
  195. eHoverText.context = &cHoverText;
  196. eHoverText.pos = pos;
  197. eHoverText.codepoint = codepoint;
  198. rootWidget->onHoverText(eHoverText);
  199. }
  200. void EventState::handleKey(math::Vec pos, int key, int scancode, int action, int mods) {
  201. if (selectedWidget) {
  202. // SelectKeyEvent
  203. EventContext cSelectKey;
  204. SelectKeyEvent eSelectKey;
  205. eSelectKey.context = &cSelectKey;
  206. eSelectKey.key = key;
  207. eSelectKey.scancode = scancode;
  208. eSelectKey.action = action;
  209. eSelectKey.mods = mods;
  210. selectedWidget->onSelectKey(eSelectKey);
  211. if (cSelectKey.consumed)
  212. return;
  213. }
  214. // HoverKeyEvent
  215. EventContext cHoverKey;
  216. HoverKeyEvent eHoverKey;
  217. eHoverKey.context = &cHoverKey;
  218. eHoverKey.pos = pos;
  219. eHoverKey.key = key;
  220. eHoverKey.scancode = scancode;
  221. eHoverKey.action = action;
  222. eHoverKey.mods = mods;
  223. rootWidget->onHoverKey(eHoverKey);
  224. }
  225. void EventState::handleZoom() {
  226. // ZoomEvent
  227. EventContext cZoom;
  228. ZoomEvent eZoom;
  229. eZoom.context = &cZoom;
  230. rootWidget->onZoom(eZoom);
  231. }
  232. } // namespace widget
  233. } // namespace rack