@@ -497,17 +497,18 @@ void AnimationNodeStateMachineEditor::_state_machine_gui_input(const Ref<InputEv
497497 box_selecting_from = box_selecting_to = state_machine_draw->get_local_mouse_position ();
498498 box_selecting_rect = Rect2 (box_selecting_from.min (box_selecting_to), (box_selecting_from - box_selecting_to).abs ());
499499
500- if (mb->is_command_or_control_pressed () || mb->is_shift_pressed ()) {
500+ if (mb->is_shift_pressed () || mb->is_command_or_control_pressed ()) {
501501 previous_selected = selected_nodes;
502- } else {
503- selected_nodes.clear ();
504- previous_selected.clear ();
505502 }
506503 }
507504
508505 // End box selecting
509506 if (mb.is_valid () && mb->get_button_index () == MouseButton::LEFT && !mb->is_pressed () && box_selecting) {
510507 box_selecting = false ;
508+ if (!any_inside_selection) {
509+ selected_nodes.clear ();
510+ }
511+ any_inside_selection = false ;
511512 state_machine_draw->queue_redraw ();
512513 _update_mode ();
513514 }
@@ -525,15 +526,21 @@ void AnimationNodeStateMachineEditor::_state_machine_gui_input(const Ref<InputEv
525526 if (selected_nodes.has (clicked_node) && mb->is_shift_pressed ()) {
526527 selected_nodes.erase (clicked_node);
527528 } else {
528- if (!mb->is_shift_pressed ()) {
529+ if (!mb->is_command_or_control_pressed ()) {
529530 selected_nodes.clear ();
530531 }
531532 selected_nodes.insert (clicked_node);
532533 }
533534 selected_node = clicked_node;
535+ box_selecting = false ;
534536 } else {
535537 // Clicked on empty space.
536- selected_nodes.clear ();
538+ // If the user is starting a shift/ctrl drag, let's not clear the past selection.
539+ if (!mb->is_shift_pressed () && !mb->is_command_or_control_pressed ()) {
540+ previous_selected.clear ();
541+ } else {
542+ previous_selected = selected_nodes;
543+ }
537544 selected_node = StringName ();
538545 }
539546
@@ -639,16 +646,28 @@ void AnimationNodeStateMachineEditor::_state_machine_gui_input(const Ref<InputEv
639646
640647 box_selecting_rect = Rect2 (box_selecting_from.min (box_selecting_to), (box_selecting_from - box_selecting_to).abs ());
641648
649+ if (!selected_node.is_empty ()) {
650+ box_selecting = false ;
651+ }
652+
642653 for (int i = 0 ; i < node_rects.size (); i++) {
643654 bool in_box = node_rects[i].node .intersects (box_selecting_rect);
644-
655+ // If ctrl/cmd is pressed, only add to our current selection
656+ // If shift is pressed, only remove from our current selection
657+ bool shift_pressed =
658+ Input::get_singleton ()->is_key_pressed (Key::SHIFT);
659+ bool ctrl_or_cmd_pressed =
660+ Input::get_singleton ()->is_key_pressed (Key::CTRL) ||
661+ Input::get_singleton ()->is_key_pressed (Key::META);
645662 if (in_box) {
646- if (previous_selected.has (node_rects[i].node_name )) {
663+ any_inside_selection = true ;
664+ if (previous_selected.has (node_rects[i].node_name ) && !ctrl_or_cmd_pressed) {
647665 selected_nodes.erase (node_rects[i].node_name );
648- } else {
666+ } else if (!shift_pressed) {
649667 selected_nodes.insert (node_rects[i].node_name );
650668 }
651669 } else {
670+ any_inside_selection = true ;
652671 if (previous_selected.has (node_rects[i].node_name )) {
653672 selected_nodes.insert (node_rects[i].node_name );
654673 } else {
@@ -672,10 +691,15 @@ void AnimationNodeStateMachineEditor::_state_machine_gui_input(const Ref<InputEv
672691
673692 if (node_rects[i].node .has_point (mm->get_position ())) {
674693 new_hovered_node_name = node_rects[i].node_name ;
675- if (node_rects[i].play .has_point (mm->get_position ())) {
676- new_hovered_node_area = HOVER_NODE_PLAY;
677- } else if (node_rects[i].edit .has_point (mm->get_position ())) {
678- new_hovered_node_area = HOVER_NODE_EDIT;
694+ bool ctrl_or_cmd_pressed =
695+ Input::get_singleton ()->is_key_pressed (Key::CTRL) ||
696+ Input::get_singleton ()->is_key_pressed (Key::META);
697+ if (!ctrl_or_cmd_pressed) {
698+ if (node_rects[i].play .has_point (mm->get_position ())) {
699+ new_hovered_node_area = HOVER_NODE_PLAY;
700+ } else if (node_rects[i].edit .has_point (mm->get_position ())) {
701+ new_hovered_node_area = HOVER_NODE_EDIT;
702+ }
679703 }
680704 break ;
681705 }
@@ -779,11 +803,14 @@ Control::CursorShape AnimationNodeStateMachineEditor::get_cursor_shape(const Poi
779803 // Put ibeam (text cursor) over names to make it clearer that they are editable.
780804 Transform2D xform = panel->get_transform () * state_machine_draw->get_transform ();
781805 Point2 pos = xform.xform_inv (p_pos);
806+ bool ctrl_or_cmd_pressed =
807+ Input::get_singleton ()->is_key_pressed (Key::CTRL) ||
808+ Input::get_singleton ()->is_key_pressed (Key::META);
782809
783810 for (int i = node_rects.size () - 1 ; i >= 0 ; i--) { // Inverse to draw order.
784811 if (node_rects[i].node .has_point (pos)) {
785812 if (node_rects[i].name .has_point (pos)) {
786- if (state_machine->can_edit_node (node_rects[i].node_name )) {
813+ if (state_machine->can_edit_node (node_rects[i].node_name ) && !ctrl_or_cmd_pressed ) {
787814 cursor_shape = Control::CURSOR_IBEAM;
788815 }
789816 }
0 commit comments