1 #include <imgui_imhex_extensions.h>
2 
3 #include <imgui.h>
4 #include <imgui_freetype.h>
5 #define IMGUI_DEFINE_MATH_OPERATORS
6 #include <imgui_internal.h>
7 #undef IMGUI_DEFINE_MATH_OPERATORS
8 
9 #include <string>
10 
11 namespace ImGui {
12 
Hyperlink(const char * label,const ImVec2 & size_arg,ImGuiButtonFlags flags)13     bool Hyperlink(const char* label, const ImVec2& size_arg, ImGuiButtonFlags flags) {
14         ImGuiWindow* window = GetCurrentWindow();
15         if (window->SkipItems)
16             return false;
17 
18         ImGuiContext& g = *GImGui;
19         const ImGuiStyle& style = g.Style;
20         const ImGuiID id = window->GetID(label);
21         const ImVec2 label_size = CalcTextSize(label, NULL, true);
22 
23         ImVec2 pos = window->DC.CursorPos;
24         ImVec2 size = CalcItemSize(size_arg, label_size.x, label_size.y);
25 
26         const ImRect bb(pos, pos + size);
27         if (!ItemAdd(bb, id))
28             return false;
29 
30         if (window->DC.ItemFlags & ImGuiItemFlags_ButtonRepeat)
31             flags |= ImGuiButtonFlags_Repeat;
32         bool hovered, held;
33         bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags);
34 
35         // Render
36         const ImU32 col = hovered ? GetColorU32(ImGuiCol_ButtonHovered) : GetColorU32(ImGuiCol_ButtonActive);
37         PushStyleColor(ImGuiCol_Text, ImU32(col));
38         TextEx(label, NULL, ImGuiTextFlags_NoWidthForLargeClippedText); // Skip formatting
39         GetWindowDrawList()->AddLine(ImVec2(pos.x, pos.y + size.y), pos + size, ImU32(col));
40         PopStyleColor();
41 
42         IMGUI_TEST_ENGINE_ITEM_INFO(id, label, window->DC.LastItemStatusFlags);
43         return pressed;
44     }
45 
BulletHyperlink(const char * label,const ImVec2 & size_arg,ImGuiButtonFlags flags)46     bool BulletHyperlink(const char* label, const ImVec2& size_arg, ImGuiButtonFlags flags) {
47         ImGuiWindow* window = GetCurrentWindow();
48         if (window->SkipItems)
49             return false;
50 
51         ImGuiContext& g = *GImGui;
52         const ImGuiStyle& style = g.Style;
53         const ImGuiID id = window->GetID(label);
54         const ImVec2 label_size = CalcTextSize(label, NULL, true);
55 
56         ImVec2 pos = window->DC.CursorPos;
57         ImVec2 size = CalcItemSize(size_arg, label_size.x, label_size.y) + ImVec2(g.FontSize + style.FramePadding.x * 2, 0.0f);
58 
59         const ImRect bb(pos, pos + size);
60         if (!ItemAdd(bb, id))
61             return false;
62 
63         if (window->DC.ItemFlags & ImGuiItemFlags_ButtonRepeat)
64             flags |= ImGuiButtonFlags_Repeat;
65         bool hovered, held;
66         bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags);
67 
68         // Render
69         const ImU32 col = hovered ? GetColorU32(ImGuiCol_ButtonHovered) : GetColorU32(ImGuiCol_ButtonActive);
70         PushStyleColor(ImGuiCol_Text, ImU32(col));
71         RenderBullet(window->DrawList, bb.Min + ImVec2(style.FramePadding.x + g.FontSize * 0.5f, g.FontSize * 0.5f), col);
72         RenderText(bb.Min + ImVec2(g.FontSize + style.FramePadding.x * 2, 0.0f), label, nullptr, false);
73         GetWindowDrawList()->AddLine(bb.Min + ImVec2(style.FramePadding.x, size.y), pos + size, ImU32(col));
74         ImGui::NewLine();
75         PopStyleColor();
76 
77         IMGUI_TEST_ENGINE_ITEM_INFO(id, label, window->DC.LastItemStatusFlags);
78         return pressed;
79     }
80 
DescriptionButton(const char * label,const char * description,const ImVec2 & size_arg,ImGuiButtonFlags flags)81     bool DescriptionButton(const char* label, const char* description, const ImVec2& size_arg, ImGuiButtonFlags flags) {
82         ImGuiWindow* window = GetCurrentWindow();
83         if (window->SkipItems)
84             return false;
85 
86         ImGuiContext& g = *GImGui;
87         const ImGuiStyle& style = g.Style;
88         const ImGuiID id = window->GetID(label);
89         const ImVec2 text_size = CalcTextSize((std::string(label) + "\n  " + std::string(description)).c_str(), NULL, true);
90         const ImVec2 label_size = CalcTextSize(label, NULL, true);
91 
92         ImVec2 pos = window->DC.CursorPos;
93         if ((flags & ImGuiButtonFlags_AlignTextBaseLine) && style.FramePadding.y < window->DC.CurrLineTextBaseOffset) // Try to vertically align buttons that are smaller/have no padding so that text baseline matches (bit hacky, since it shouldn't be a flag)
94             pos.y += window->DC.CurrLineTextBaseOffset - style.FramePadding.y;
95         ImVec2 size = CalcItemSize(size_arg, text_size.x + style.FramePadding.x * 4.0f, text_size.y + style.FramePadding.y * 4.0f);
96 
97         const ImRect bb(pos, pos + size);
98         ItemSize(size, style.FramePadding.y);
99         if (!ItemAdd(bb, id))
100             return false;
101 
102         if (window->DC.ItemFlags & ImGuiItemFlags_ButtonRepeat)
103             flags |= ImGuiButtonFlags_Repeat;
104         bool hovered, held;
105         bool pressed = ButtonBehavior(bb, id, &hovered, &held, flags);
106 
107         ImGui::PushStyleVar(ImGuiStyleVar_ButtonTextAlign, ImVec2(0.0, 0.5));
108 
109         // Render
110         const ImU32 col = GetColorU32((held && hovered) ? ImGuiCol_TableHeaderBg : hovered ? ImGuiCol_TableBorderLight : ImGuiCol_TableBorderStrong);
111         RenderNavHighlight(bb, id);
112         RenderFrame(bb.Min, bb.Max, col, true, style.FrameRounding);
113         PushStyleColor(ImGuiCol_Text, GetColorU32(ImGuiCol_ButtonActive));
114         RenderTextClipped(bb.Min + style.FramePadding * 2, bb.Max - style.FramePadding * 2, label, NULL, &text_size, style.ButtonTextAlign, &bb);
115         PopStyleColor();
116         PushStyleColor(ImGuiCol_Text, GetColorU32(ImGuiCol_Text));
117         RenderTextClipped(bb.Min + style.FramePadding * 2 + ImVec2(style.FramePadding.x * 2, label_size.y), bb.Max - style.FramePadding, description, NULL, &text_size, style.ButtonTextAlign, &bb);
118         PopStyleColor();
119 
120         ImGui::PopStyleVar();
121 
122         // Automatically close popups
123         //if (pressed && !(flags & ImGuiButtonFlags_DontClosePopups) && (window->Flags & ImGuiWindowFlags_Popup))
124         //    CloseCurrentPopup();
125 
126         IMGUI_TEST_ENGINE_ITEM_INFO(id, label, window->DC.LastItemStatusFlags);
127         return pressed;
128     }
129 
UnderlinedText(const char * label,ImColor color,const ImVec2 & size_arg)130     void UnderlinedText(const char* label, ImColor color, const ImVec2& size_arg) {
131         ImGuiWindow* window = GetCurrentWindow();
132 
133         const ImVec2 label_size = CalcTextSize(label, NULL, true);
134 
135         ImVec2 pos = window->DC.CursorPos;
136         ImVec2 size = CalcItemSize(size_arg, label_size.x, label_size.y);
137 
138         PushStyleColor(ImGuiCol_Text, ImU32(color));
139         TextEx(label, NULL, ImGuiTextFlags_NoWidthForLargeClippedText); // Skip formatting
140         GetWindowDrawList()->AddLine(ImVec2(pos.x, pos.y + size.y), pos + size, ImU32(color));
141         PopStyleColor();
142     }
143 
144 }