|
5 | 5 | #include "Components/CTypeEditor.h" |
6 | 6 | #include "DockSpaceLayout.h" |
7 | 7 | #include "Utils/EditorStyle.h" |
| 8 | +#include "Utils/FunctionGraphContextMenu.h" |
8 | 9 | #include "Utils/FunctionUtils.h" |
9 | | -#include "Utils/TypeUtils.h" |
10 | 10 |
|
11 | 11 | #include <AST/Components/CDeclFunction.h> |
12 | 12 | #include <AST/Components/CDeclVariable.h> |
|
26 | 26 | #include <AST/Components/CStmtInput.h> |
27 | 27 | #include <AST/Components/CStmtOutputs.h> |
28 | 28 | #include <AST/Components/CStmtReturn.h> |
| 29 | +#include <AST/Components/CType.h> |
29 | 30 | #include <AST/Components/Views/CGraphTransform.h> |
30 | 31 | #include <AST/Filtering.h> |
31 | | -#include <AST/Statics/STypes.h> |
32 | 32 | #include <AST/Utils/Expressions.h> |
33 | 33 | #include <AST/Utils/Hierarchy.h> |
34 | 34 | #include <AST/Utils/Statements.h> |
@@ -71,6 +71,11 @@ namespace Rift::Graph |
71 | 71 | return {0.f, settings.verticalMargin + settings.verticalPadding}; |
72 | 72 | } |
73 | 73 |
|
| 74 | + v2 Settings::GetGridPosition(v2 screenPosition) const |
| 75 | + { |
| 76 | + return Nodes::ScreenToGridPosition(screenPosition) * GetInvGridSize(); |
| 77 | + } |
| 78 | + |
74 | 79 | void BeginNode(TAccessRef<TWrite<CGraphTransform>> access, AST::Id id) |
75 | 80 | { |
76 | 81 | currentNodeTransform = &access.GetOrAdd<CGraphTransform>(id); |
@@ -465,223 +470,6 @@ namespace Rift::Graph |
465 | 470 | { |
466 | 471 | ImGui::PopStyleVar(2); |
467 | 472 | } |
468 | | - void DrawNodeContextMenu(AST::Tree& ast, AST::Id typeId, TSpan<AST::Id> nodeIds) |
469 | | - { |
470 | | - Check(!nodeIds.IsEmpty()); |
471 | | - |
472 | | - AST::Id firstNodeId = nodeIds[0]; |
473 | | - |
474 | | - if (nodeIds.Size() == 1 && ast.Has<CDeclFunction>(firstNodeId)) |
475 | | - { |
476 | | - if (UI::MenuItem("Add return node")) |
477 | | - { |
478 | | - AST::Id newId = Functions::AddReturn({ast, typeId}); |
479 | | - if (!IsNone(newId)) |
480 | | - { |
481 | | - v2 position = ast.Get<CGraphTransform>(firstNodeId).position; |
482 | | - ast.Add<CGraphTransform>(newId, position + v2{10.f, 0.f}); |
483 | | - |
484 | | - AST::Statements::TryConnect(ast, firstNodeId, newId); |
485 | | - } |
486 | | - } |
487 | | - UI::Separator(); |
488 | | - } |
489 | | - if (UI::MenuItem("Delete")) |
490 | | - { |
491 | | - Functions::RemoveNodes(ast, nodeIds); |
492 | | - } |
493 | | - } |
494 | | - |
495 | | - void DrawGraphContextMenu(AST::Tree& ast, AST::Id typeId) |
496 | | - { |
497 | | - static ImGuiTextFilter filter; |
498 | | - if (UI::IsWindowAppearing()) |
499 | | - { |
500 | | - UI::SetKeyboardFocusHere(); |
501 | | - } |
502 | | - filter.Draw("##Filter"); |
503 | | - const v2 clickPos = UI::GetMousePosOnOpeningCurrentPopup(); |
504 | | - const v2 gridPos = GetGridPosition(clickPos).Floor(); |
505 | | - |
506 | | - if (filter.IsActive() || UI::TreeNode("Flow")) |
507 | | - { |
508 | | - if (filter.PassFilter("Return") && UI::MenuItem("Return")) |
509 | | - { |
510 | | - AST::Id newId = Functions::AddReturn({ast, typeId}); |
511 | | - if (!IsNone(newId)) |
512 | | - { |
513 | | - ast.Add<CGraphTransform>(newId, gridPos); |
514 | | - } |
515 | | - } |
516 | | - if (filter.PassFilter("If") && UI::MenuItem("If")) |
517 | | - { |
518 | | - AST::Id newId = Functions::AddIf({ast, typeId}); |
519 | | - if (!IsNone(newId)) |
520 | | - { |
521 | | - ast.Add<CGraphTransform>(newId, gridPos); |
522 | | - } |
523 | | - } |
524 | | - |
525 | | - if (!filter.IsActive()) |
526 | | - { |
527 | | - UI::TreePop(); |
528 | | - } |
529 | | - } |
530 | | - |
531 | | - if (filter.IsActive() || UI::TreeNode("Operators")) |
532 | | - { |
533 | | - static String name; |
534 | | - // Unary operators |
535 | | - for (auto type : Refl::GetEnumValues<UnaryOperatorType>()) |
536 | | - { |
537 | | - StringView shortName = Functions::GetUnaryOperatorName(type); |
538 | | - StringView longName = Functions::GetUnaryOperatorLongName(type); |
539 | | - name.clear(); |
540 | | - Strings::FormatTo(name, "{} ({})", shortName, longName); |
541 | | - if (filter.PassFilter(name.data(), name.data() + name.size()) |
542 | | - && UI::MenuItem(name.data())) |
543 | | - { |
544 | | - AST::Id newId = Functions::AddUnaryOperator({ast, typeId}, type); |
545 | | - if (!IsNone(newId)) |
546 | | - { |
547 | | - ast.Add<CGraphTransform>(newId, gridPos); |
548 | | - } |
549 | | - } |
550 | | - } |
551 | | - // Binary operators |
552 | | - for (auto type : Refl::GetEnumValues<BinaryOperatorType>()) |
553 | | - { |
554 | | - StringView shortName = Functions::GetBinaryOperatorName(type); |
555 | | - StringView longName = Functions::GetBinaryOperatorLongName(type); |
556 | | - name.clear(); |
557 | | - Strings::FormatTo(name, "{} ({})", shortName, longName); |
558 | | - if (filter.PassFilter(name.data(), name.data() + name.size()) |
559 | | - && UI::MenuItem(name.data())) |
560 | | - { |
561 | | - AST::Id newId = Functions::AddBinaryOperator({ast, typeId}, type); |
562 | | - if (!IsNone(newId)) |
563 | | - { |
564 | | - ast.Add<CGraphTransform>(newId, gridPos); |
565 | | - } |
566 | | - } |
567 | | - } |
568 | | - |
569 | | - if (!filter.IsActive()) |
570 | | - { |
571 | | - UI::TreePop(); |
572 | | - } |
573 | | - } |
574 | | - |
575 | | - if (filter.IsActive() || UI::TreeNode("Constructors")) |
576 | | - { |
577 | | - String makeStr{}; |
578 | | - auto& typeList = ast.GetStatic<STypes>(); |
579 | | - auto types = ast.Filter<CType>(); |
580 | | - for (const auto& it : typeList.typesByName) |
581 | | - { |
582 | | - if (auto* type = types.TryGet<CType>(it.second)) |
583 | | - { |
584 | | - makeStr.clear(); |
585 | | - Strings::FormatTo(makeStr, "Make {}", type->name); |
586 | | - if (filter.PassFilter(makeStr.c_str(), makeStr.c_str() + makeStr.size())) |
587 | | - { |
588 | | - if (UI::MenuItem(makeStr.c_str())) |
589 | | - { |
590 | | - AST::Id newId = Functions::AddLiteral({ast, typeId}, it.second); |
591 | | - if (!IsNone(newId)) |
592 | | - { |
593 | | - ast.Add<CGraphTransform>(newId, gridPos); |
594 | | - } |
595 | | - } |
596 | | - } |
597 | | - } |
598 | | - } |
599 | | - |
600 | | - if (!filter.IsActive()) |
601 | | - { |
602 | | - UI::TreePop(); |
603 | | - } |
604 | | - } |
605 | | - |
606 | | - if (filter.IsActive() || UI::TreeNode("Variables")) |
607 | | - { |
608 | | - auto variables = ast.Filter<CDeclVariable>(); |
609 | | - auto identifiers = ast.Filter<CIdentifier>(); |
610 | | - for (AST::Id variableId : variables) |
611 | | - { |
612 | | - if (auto* iden = identifiers.TryGet<CIdentifier>(variableId)) |
613 | | - { |
614 | | - const String& name = iden->name.ToString(); |
615 | | - if (filter.PassFilter(name.c_str(), name.c_str() + name.size())) |
616 | | - { |
617 | | - if (UI::MenuItem(name.c_str())) |
618 | | - { |
619 | | - AST::Id newId = |
620 | | - Functions::AddDeclarationReference({ast, typeId}, variableId); |
621 | | - if (!IsNone(newId)) |
622 | | - { |
623 | | - ast.Add<CGraphTransform>(newId, gridPos); |
624 | | - } |
625 | | - } |
626 | | - } |
627 | | - } |
628 | | - } |
629 | | - |
630 | | - if (!filter.IsActive()) |
631 | | - { |
632 | | - UI::TreePop(); |
633 | | - } |
634 | | - } |
635 | | - |
636 | | - if (filter.IsActive() || UI::TreeNode("Functions")) |
637 | | - { |
638 | | - auto functions = ast.Filter<CDeclFunction>(); |
639 | | - auto identifiers = ast.Filter<CIdentifier>(); |
640 | | - for (AST::Id functionId : functions) |
641 | | - { |
642 | | - if (auto* iden = identifiers.TryGet<CIdentifier>(functionId)) |
643 | | - { |
644 | | - const String& name = iden->name.ToString(); |
645 | | - if (filter.PassFilter(name.c_str(), name.c_str() + name.size())) |
646 | | - { |
647 | | - if (UI::MenuItem(name.c_str())) |
648 | | - { |
649 | | - AST::Id newId = Functions::AddCall({ast, typeId}, functionId); |
650 | | - if (!IsNone(newId)) |
651 | | - { |
652 | | - ast.Add<CGraphTransform>(newId, gridPos); |
653 | | - } |
654 | | - } |
655 | | - } |
656 | | - } |
657 | | - } |
658 | | - |
659 | | - if (!filter.IsActive()) |
660 | | - { |
661 | | - ImGui::TreePop(); |
662 | | - } |
663 | | - } |
664 | | - } |
665 | | - |
666 | | - void DrawContextMenu(AST::Tree& ast, AST::Id typeId, AST::Id hoveredNodeId) |
667 | | - { |
668 | | - if (ImGui::BeginPopup("GraphContextMenu")) |
669 | | - { |
670 | | - if (IsNone(hoveredNodeId)) |
671 | | - { |
672 | | - DrawGraphContextMenu(ast, typeId); |
673 | | - } |
674 | | - else if (Nodes::IsNodeSelected(hoveredNodeId)) |
675 | | - { |
676 | | - DrawNodeContextMenu(ast, typeId, Nodes::GetSelectedNodes()); |
677 | | - } |
678 | | - else |
679 | | - { |
680 | | - DrawNodeContextMenu(ast, typeId, hoveredNodeId); |
681 | | - } |
682 | | - ImGui::EndPopup(); |
683 | | - } |
684 | | - } |
685 | 473 |
|
686 | 474 | void DrawFunctionDecls(AST::Tree& ast, const TArray<AST::Id>& functionDecls) |
687 | 475 | { |
@@ -1065,15 +853,15 @@ namespace Rift::Graph |
1065 | 853 | // Links |
1066 | 854 | DrawStatementLinks(ast, *children); |
1067 | 855 | DrawExpressionLinks(ast, *children); |
1068 | | - |
1069 | | - if (UI::IsKeyReleased(GLFW_KEY_DELETE)) |
1070 | | - { |
1071 | | - Functions::RemoveNodes(ast, Nodes::GetSelectedNodes()); |
1072 | | - } |
1073 | 856 | } |
1074 | 857 |
|
1075 | 858 | Nodes::DrawMiniMap(0.2f, Nodes::MiniMapCorner::TopRight); |
1076 | 859 | PopNodeStyle(); |
| 860 | + |
| 861 | + if (UI::IsKeyReleased(GLFW_KEY_DELETE)) |
| 862 | + { |
| 863 | + Functions::RemoveNodes(ast, Nodes::GetSelectedNodes()); |
| 864 | + } |
1077 | 865 | Nodes::EndNodeEditor(); |
1078 | 866 |
|
1079 | 867 | Nodes::Id outputPin; |
@@ -1102,12 +890,6 @@ namespace Rift::Graph |
1102 | 890 | } |
1103 | 891 | } |
1104 | 892 |
|
1105 | | - |
1106 | | - v2 GetGridPosition(v2 screenPosition) |
1107 | | - { |
1108 | | - return Nodes::ScreenToGridPosition(screenPosition) * settings.GetInvGridSize(); |
1109 | | - } |
1110 | | - |
1111 | 893 | void SetNodePosition(AST::Id id, v2 position) |
1112 | 894 | { |
1113 | 895 | position *= settings.GetGridSize(); |
|
0 commit comments