Z ordering, prep for command window
This commit is contained in:
@@ -18,8 +18,9 @@ Vec2 GetSizeF(Rect2I r) {
|
||||
return result;
|
||||
}
|
||||
|
||||
Vec2 ToVec2(Vec2I v) { return {(float)v.x, (float)v.y}; }
|
||||
Vec2I ToVec2I(Vec2 v) { return {(Int)v.x, (Int)v.y}; }
|
||||
Vec2 ToVec2(Vec2I v) { return {(float)v.x, (float)v.y}; }
|
||||
Vec2I ToVec2I(Vec2 v) { return {(Int)v.x, (Int)v.y}; }
|
||||
Rect2I ToRect2I(Rect2 r) { return {ToVec2I(r.min), ToVec2I(r.max)}; }
|
||||
|
||||
// clang-format off
|
||||
Rect2 operator-(Rect2 r, Rect2 value) { return { r.min.x - value.min.x, r.min.y - value.min.y, r.max.x - value.max.x, r.max.y - value.max.y }; }
|
||||
|
||||
@@ -13,6 +13,11 @@ Rect2I GetScreenRect() {
|
||||
return result;
|
||||
}
|
||||
|
||||
Rect2 GetScreenRectF() {
|
||||
Rect2 result = {0, 0, (float)GetRenderWidth(), (float)GetRenderHeight()};
|
||||
return result;
|
||||
}
|
||||
|
||||
Int GetCharSpacing(Font font, Int font_size, Int spacing) {
|
||||
int index = GetGlyphIndex(font, '_');
|
||||
Int textOffsetX = 0;
|
||||
|
||||
@@ -96,9 +96,22 @@ int main(void) {
|
||||
LoadLine(b);
|
||||
AddView(w->id, v->id);
|
||||
}
|
||||
{
|
||||
Window *w = CreateWindow();
|
||||
w->draw_scrollbar = false;
|
||||
w->draw_line_numbers = false;
|
||||
w->draw_infobar = false;
|
||||
Buffer *b = CreateBuffer(sys_allocator);
|
||||
View *v = CreateView(b->id);
|
||||
LoadLine(b);
|
||||
AddView(w->id, v->id);
|
||||
}
|
||||
|
||||
Int LastFrameIDWhenSwitchedActiveWindow = 0;
|
||||
|
||||
while (!WindowShouldClose()) {
|
||||
ProfileScope(game_loop);
|
||||
FrameID += 1;
|
||||
|
||||
Rect2I screen_rect = GetScreenRect();
|
||||
float line_numbers_size = MeasureTextEx(MainFont, "12345", (float)FontSize, (float)FontSpacing).x;
|
||||
@@ -126,13 +139,56 @@ int main(void) {
|
||||
if (Windows[i].draw_infobar) Windows[i].infobar_rect = CutBottom(&Windows[i].document_rect, (Int)MenuFontSize);
|
||||
if (Windows[i].draw_line_numbers) Windows[i].line_numbers_rect = CutLeft(&Windows[i].document_rect, (Int)line_numbers_size);
|
||||
}
|
||||
{
|
||||
int i = 4;
|
||||
Rect2 screen_rect = GetScreenRectF();
|
||||
Vec2 size = GetSize(screen_rect);
|
||||
CutTop(&screen_rect, size.y * 0.05f);
|
||||
CutBottom(&screen_rect, size.y * 0.8f);
|
||||
CutLeft(&screen_rect, size.x * 0.2f);
|
||||
CutRight(&screen_rect, size.x * 0.2f);
|
||||
|
||||
Windows[i].z = 1;
|
||||
Windows[i].total_rect = ToRect2I(screen_rect);
|
||||
Windows[i].document_rect = Windows[i].total_rect;
|
||||
}
|
||||
|
||||
BeginDrawing();
|
||||
ClearBackground(ColorBackground);
|
||||
For(Windows) {
|
||||
if (!it.visible) continue;
|
||||
HandleKeybindings(&it);
|
||||
DrawWindow(it);
|
||||
|
||||
Scratch scratch;
|
||||
Array<Int> order = GetWindowZOrder(scratch);
|
||||
|
||||
For(order) {
|
||||
Window *window = &Windows[it];
|
||||
if (window->visible == false) continue;
|
||||
View *view = GetActiveView(window);
|
||||
|
||||
Vec2 _mouse = GetMousePosition();
|
||||
bool mouse_in_view = CheckCollisionPointRec(_mouse, ToRectangle(window->document_rect));
|
||||
bool mouse_in_scrollbar = CheckCollisionPointRec(_mouse, ToRectangle(window->scrollbar_rect));
|
||||
|
||||
if (mouse_in_view || mouse_in_scrollbar) {
|
||||
if (IsKeyDown(KEY_F1)) {
|
||||
view->scroll.x -= (Int)(GetMouseWheelMove() * 48);
|
||||
} else {
|
||||
view->scroll.y -= (Int)(GetMouseWheelMove() * 48);
|
||||
}
|
||||
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
if (LastFrameIDWhenSwitchedActiveWindow != FrameID) {
|
||||
ActiveWindow = window->id;
|
||||
LastFrameIDWhenSwitchedActiveWindow = FrameID;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
For(IterateInReverse(&order)) {
|
||||
Window &window = Windows[it];
|
||||
if (window.visible == false) continue;
|
||||
HandleKeybindings(&window);
|
||||
DrawWindow(window);
|
||||
}
|
||||
SetMouseCursor();
|
||||
EndDrawing();
|
||||
|
||||
@@ -55,6 +55,7 @@ struct Window {
|
||||
Rect2I document_rect;
|
||||
|
||||
double mouse_scroller_offset;
|
||||
int z;
|
||||
|
||||
struct {
|
||||
bool mouse_selecting_scrollbar : 1;
|
||||
@@ -99,6 +100,8 @@ Int FontSpacing;
|
||||
Int FontLineSpacing;
|
||||
Int FontCharSpacing;
|
||||
|
||||
Int FrameID;
|
||||
|
||||
inline Window *GetWindow(WindowID id) {
|
||||
For(Windows) if (it.id.id == id.id) return ⁢
|
||||
return &Windows[0];
|
||||
|
||||
@@ -118,319 +118,298 @@ void HandleKeybindings(Window *window) {
|
||||
Buffer *buffer = GetBuffer(view.buffer_id);
|
||||
Caret main_caret_on_begin_frame = view.carets[0];
|
||||
|
||||
{
|
||||
Vec2 _mouse = GetMousePosition();
|
||||
bool mouse_in_view = CheckCollisionPointRec(_mouse, ToRectangle(window->document_rect));
|
||||
bool mouse_in_scrollbar = CheckCollisionPointRec(_mouse, ToRectangle(window->scrollbar_rect));
|
||||
if (IsActive(window)) {
|
||||
|
||||
if (mouse_in_view || mouse_in_scrollbar) {
|
||||
if (IsKeyDown(KEY_F1)) {
|
||||
view.scroll.x -= (Int)(GetMouseWheelMove() * 48);
|
||||
} else {
|
||||
view.scroll.y -= (Int)(GetMouseWheelMove() * 48);
|
||||
}
|
||||
if (CtrlPress(KEY_F2)) {
|
||||
LoadBigLine(buffer);
|
||||
} else if (Press(KEY_F2)) {
|
||||
LoadBigText(buffer);
|
||||
}
|
||||
|
||||
if (!IsActive(window)) {
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
ActiveWindow = window->id;
|
||||
if (Press(KEY_ESCAPE)) {
|
||||
view.carets.len = 1;
|
||||
}
|
||||
|
||||
if (CtrlAltPress(KEY_DOWN)) {
|
||||
Command_DuplicateLine(&view, DIR_DOWN);
|
||||
} else if (AltShiftPress(KEY_DOWN)) {
|
||||
Command_CreateCursorVertical(&view, DIR_DOWN);
|
||||
} else if (CtrlShiftPress(KEY_DOWN)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_DOWN, true));
|
||||
} else if (CtrlPress(KEY_DOWN)) {
|
||||
For(view.carets) it = MakeCaret(MovePos(*buffer, it.range.max, DIR_DOWN, true));
|
||||
} else if (ShiftPress(KEY_DOWN)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_DOWN, false));
|
||||
} else if (Press(KEY_DOWN)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_DOWN, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.max);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!IsActive(window)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (CtrlPress(KEY_F2)) {
|
||||
LoadBigLine(buffer);
|
||||
} else if (Press(KEY_F2)) {
|
||||
LoadBigText(buffer);
|
||||
}
|
||||
|
||||
if (Press(KEY_ESCAPE)) {
|
||||
view.carets.len = 1;
|
||||
}
|
||||
|
||||
if (CtrlAltPress(KEY_DOWN)) {
|
||||
Command_DuplicateLine(&view, DIR_DOWN);
|
||||
} else if (AltShiftPress(KEY_DOWN)) {
|
||||
Command_CreateCursorVertical(&view, DIR_DOWN);
|
||||
} else if (CtrlShiftPress(KEY_DOWN)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_DOWN, true));
|
||||
} else if (CtrlPress(KEY_DOWN)) {
|
||||
For(view.carets) it = MakeCaret(MovePos(*buffer, it.range.max, DIR_DOWN, true));
|
||||
} else if (ShiftPress(KEY_DOWN)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_DOWN, false));
|
||||
} else if (Press(KEY_DOWN)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_DOWN, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.max);
|
||||
if (CtrlAltPress(KEY_UP)) {
|
||||
Command_DuplicateLine(&view, DIR_UP);
|
||||
} else if (AltShiftPress(KEY_UP)) {
|
||||
Command_CreateCursorVertical(&view, DIR_UP);
|
||||
} else if (CtrlShiftPress(KEY_UP)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_UP, CTRL_PRESSED));
|
||||
} else if (CtrlPress(KEY_UP)) {
|
||||
For(view.carets) it = MakeCaret(MovePos(*buffer, it.range.min, DIR_UP, CTRL_PRESSED));
|
||||
} else if (ShiftPress(KEY_UP)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_UP));
|
||||
} else if (Press(KEY_UP)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_UP));
|
||||
} else {
|
||||
it = MakeCaret(it.range.min);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CtrlAltPress(KEY_UP)) {
|
||||
Command_DuplicateLine(&view, DIR_UP);
|
||||
} else if (AltShiftPress(KEY_UP)) {
|
||||
Command_CreateCursorVertical(&view, DIR_UP);
|
||||
} else if (CtrlShiftPress(KEY_UP)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_UP, CTRL_PRESSED));
|
||||
} else if (CtrlPress(KEY_UP)) {
|
||||
For(view.carets) it = MakeCaret(MovePos(*buffer, it.range.min, DIR_UP, CTRL_PRESSED));
|
||||
} else if (ShiftPress(KEY_UP)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_UP));
|
||||
} else if (Press(KEY_UP)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_UP));
|
||||
} else {
|
||||
it = MakeCaret(it.range.min);
|
||||
if (CtrlShiftPress(KEY_LEFT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_LEFT, true));
|
||||
} else if (CtrlPress(KEY_LEFT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) != 0 && GetFront(it) != it.range.min) {
|
||||
it = MakeCaret(it.range.min);
|
||||
} else {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_LEFT, true));
|
||||
}
|
||||
}
|
||||
} else if (ShiftPress(KEY_LEFT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_LEFT, false));
|
||||
} else if (Press(KEY_LEFT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_LEFT, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.min);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CtrlShiftPress(KEY_LEFT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_LEFT, true));
|
||||
} else if (CtrlPress(KEY_LEFT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) != 0 && GetFront(it) != it.range.min) {
|
||||
it = MakeCaret(it.range.min);
|
||||
} else {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_LEFT, true));
|
||||
if (CtrlShiftPress(KEY_RIGHT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_RIGHT, true));
|
||||
} else if (CtrlPress(KEY_RIGHT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) != 0 && GetFront(it) != it.range.max) {
|
||||
it = MakeCaret(it.range.max);
|
||||
} else {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_RIGHT, true));
|
||||
}
|
||||
}
|
||||
} else if (ShiftPress(KEY_RIGHT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_RIGHT, false));
|
||||
} else if (Press(KEY_RIGHT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_RIGHT, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.max);
|
||||
}
|
||||
}
|
||||
}
|
||||
} else if (ShiftPress(KEY_LEFT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_LEFT, false));
|
||||
} else if (Press(KEY_LEFT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.min, DIR_LEFT, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.min);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CtrlShiftPress(KEY_RIGHT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_RIGHT, true));
|
||||
} else if (CtrlPress(KEY_RIGHT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) != 0 && GetFront(it) != it.range.max) {
|
||||
it = MakeCaret(it.range.max);
|
||||
} else {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_RIGHT, true));
|
||||
}
|
||||
}
|
||||
} else if (ShiftPress(KEY_RIGHT)) {
|
||||
For(view.carets) it = ChangeFront(it, MovePos(*buffer, GetFront(it), DIR_RIGHT, false));
|
||||
} else if (Press(KEY_RIGHT)) {
|
||||
For(view.carets) {
|
||||
if (GetSize(it.range) == 0) {
|
||||
it = MakeCaret(MovePos(*buffer, it.range.max, DIR_RIGHT, false));
|
||||
} else {
|
||||
it = MakeCaret(it.range.max);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CtrlPress(KEY_D)) {
|
||||
Range range = view.carets[0].range;
|
||||
String16 string = GetString(*buffer, range);
|
||||
String16 string_buffer = GetString(*buffer, {range.max, INT64_MAX});
|
||||
Int index = 0;
|
||||
if (Seek(string_buffer, string, &index)) {
|
||||
Insert(&view.carets, MakeCaret(range.max + index, range.max + index + string.len), 0);
|
||||
} else {
|
||||
String16 string_buffer = GetString(*buffer);
|
||||
if (CtrlPress(KEY_D)) {
|
||||
Range range = view.carets[0].range;
|
||||
String16 string = GetString(*buffer, range);
|
||||
String16 string_buffer = GetString(*buffer, {range.max, INT64_MAX});
|
||||
Int index = 0;
|
||||
if (Seek(string_buffer, string, &index)) {
|
||||
Insert(&view.carets, MakeCaret(index, index + string.len), 0);
|
||||
Insert(&view.carets, MakeCaret(range.max + index, range.max + index + string.len), 0);
|
||||
} else {
|
||||
String16 string_buffer = GetString(*buffer);
|
||||
if (Seek(string_buffer, string, &index)) {
|
||||
Insert(&view.carets, MakeCaret(index, index + string.len), 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (CtrlShiftPress(KEY_Z)) {
|
||||
RedoEdit(buffer, &view.carets);
|
||||
} else if (CtrlPress(KEY_Z)) {
|
||||
UndoEdit(buffer, &view.carets);
|
||||
}
|
||||
if (CtrlShiftPress(KEY_Z)) {
|
||||
RedoEdit(buffer, &view.carets);
|
||||
} else if (CtrlPress(KEY_Z)) {
|
||||
UndoEdit(buffer, &view.carets);
|
||||
}
|
||||
|
||||
if (CtrlPress(KEY_C)) {
|
||||
Command_Copy(&view);
|
||||
} else if (CtrlPress(KEY_V)) {
|
||||
Command_Paste(&view);
|
||||
} else if (CtrlPress(KEY_X)) {
|
||||
Command_Copy(&view);
|
||||
Command_Replace(&view, L"");
|
||||
}
|
||||
if (CtrlPress(KEY_C)) {
|
||||
Command_Copy(&view);
|
||||
} else if (CtrlPress(KEY_V)) {
|
||||
Command_Paste(&view);
|
||||
} else if (CtrlPress(KEY_X)) {
|
||||
Command_Copy(&view);
|
||||
Command_Replace(&view, L"");
|
||||
}
|
||||
|
||||
bool dont_update_scroll = false;
|
||||
if (CtrlPress(KEY_A)) {
|
||||
view.carets.len = 1;
|
||||
view.carets[0] = MakeCaret(0, buffer->len);
|
||||
dont_update_scroll = true;
|
||||
}
|
||||
bool dont_update_scroll = false;
|
||||
if (CtrlPress(KEY_A)) {
|
||||
view.carets.len = 1;
|
||||
view.carets[0] = MakeCaret(0, buffer->len);
|
||||
dont_update_scroll = true;
|
||||
}
|
||||
|
||||
if (ShiftPress(KEY_PAGE_UP)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_UP, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_PAGE_UP)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_UP);
|
||||
}
|
||||
if (ShiftPress(KEY_PAGE_UP)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_UP, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_PAGE_UP)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_UP);
|
||||
}
|
||||
|
||||
if (ShiftPress(KEY_PAGE_DOWN)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_DOWN, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_PAGE_DOWN)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_DOWN);
|
||||
}
|
||||
if (ShiftPress(KEY_PAGE_DOWN)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_DOWN, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_PAGE_DOWN)) {
|
||||
Command_MoveCursorsByPageSize(window, DIR_DOWN);
|
||||
}
|
||||
|
||||
if (ShiftPress(KEY_HOME)) {
|
||||
Command_MoveCursorsToSide(window, DIR_LEFT, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_HOME)) {
|
||||
Command_MoveCursorsToSide(window, DIR_LEFT);
|
||||
}
|
||||
if (ShiftPress(KEY_HOME)) {
|
||||
Command_MoveCursorsToSide(window, DIR_LEFT, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_HOME)) {
|
||||
Command_MoveCursorsToSide(window, DIR_LEFT);
|
||||
}
|
||||
|
||||
if (ShiftPress(KEY_END)) {
|
||||
Command_MoveCursorsToSide(window, DIR_RIGHT, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_END)) {
|
||||
Command_MoveCursorsToSide(window, DIR_RIGHT);
|
||||
}
|
||||
if (ShiftPress(KEY_END)) {
|
||||
Command_MoveCursorsToSide(window, DIR_RIGHT, SHIFT_PRESSED);
|
||||
} else if (Press(KEY_END)) {
|
||||
Command_MoveCursorsToSide(window, DIR_RIGHT);
|
||||
}
|
||||
|
||||
if (Press(KEY_ENTER)) {
|
||||
Command_Replace(&view, L"\n");
|
||||
}
|
||||
if (Press(KEY_ENTER)) {
|
||||
Command_Replace(&view, L"\n");
|
||||
}
|
||||
|
||||
if (Press(KEY_TAB)) {
|
||||
Command_Replace(&view, L" ");
|
||||
}
|
||||
if (Press(KEY_TAB)) {
|
||||
Command_Replace(&view, L" ");
|
||||
}
|
||||
|
||||
if (CtrlPress(KEY_BACKSPACE)) {
|
||||
Command_Delete(&view, DIR_LEFT, CTRL_PRESSED);
|
||||
} else if (Press(KEY_BACKSPACE)) {
|
||||
Command_Delete(&view, DIR_LEFT);
|
||||
}
|
||||
if (CtrlPress(KEY_BACKSPACE)) {
|
||||
Command_Delete(&view, DIR_LEFT, CTRL_PRESSED);
|
||||
} else if (Press(KEY_BACKSPACE)) {
|
||||
Command_Delete(&view, DIR_LEFT);
|
||||
}
|
||||
|
||||
if (CtrlPress(KEY_DELETE)) {
|
||||
Command_Delete(&view, DIR_RIGHT, CTRL_PRESSED);
|
||||
} else if (Press(KEY_DELETE)) {
|
||||
Command_Delete(&view, DIR_RIGHT);
|
||||
}
|
||||
if (CtrlPress(KEY_DELETE)) {
|
||||
Command_Delete(&view, DIR_RIGHT, CTRL_PRESSED);
|
||||
} else if (Press(KEY_DELETE)) {
|
||||
Command_Delete(&view, DIR_RIGHT);
|
||||
}
|
||||
|
||||
for (int c = GetCharPressed(); c; c = GetCharPressed()) {
|
||||
// we interpret 2 byte sequences as 1 byte when rendering but we still
|
||||
// want to read them properly.
|
||||
String16 string = L"?";
|
||||
UTF16Result result = UTF32ToUTF16((uint32_t)c);
|
||||
if (!result.error) string = {(wchar_t *)result.out_str, result.len};
|
||||
Command_Replace(&view, string);
|
||||
}
|
||||
for (int c = GetCharPressed(); c; c = GetCharPressed()) {
|
||||
// we interpret 2 byte sequences as 1 byte when rendering but we still
|
||||
// want to read them properly.
|
||||
String16 string = L"?";
|
||||
UTF16Result result = UTF32ToUTF16((uint32_t)c);
|
||||
if (!result.error) string = {(wchar_t *)result.out_str, result.len};
|
||||
Command_Replace(&view, string);
|
||||
}
|
||||
|
||||
{
|
||||
ProfileScope(mouse);
|
||||
{
|
||||
ProfileScope(mouse);
|
||||
|
||||
Vec2 _mouse = GetMousePosition();
|
||||
bool mouse_in_view = CheckCollisionPointRec(_mouse, ToRectangle(window->document_rect));
|
||||
bool mouse_in_scrollbar = CheckCollisionPointRec(_mouse, ToRectangle(window->scrollbar_rect));
|
||||
Vec2I mouse = ToVec2I(_mouse);
|
||||
Vec2 _mouse = GetMousePosition();
|
||||
bool mouse_in_view = CheckCollisionPointRec(_mouse, ToRectangle(window->document_rect));
|
||||
bool mouse_in_scrollbar = CheckCollisionPointRec(_mouse, ToRectangle(window->scrollbar_rect));
|
||||
Vec2I mouse = ToVec2I(_mouse);
|
||||
|
||||
if (!(mouse_in_scrollbar || window->mouse_selecting_scrollbar) && (mouse_in_view || window->mouse_selecting)) {
|
||||
Vec2I mworld = mouse - window->document_rect.min + view.scroll;
|
||||
Vec2I pos = mworld / Vec2I{FontCharSpacing, FontLineSpacing};
|
||||
XY xy = {(Int)(pos.x), (Int)(pos.y)};
|
||||
Int p = XYToPosWithoutNL(*buffer, xy);
|
||||
if (!(mouse_in_scrollbar || window->mouse_selecting_scrollbar) && (mouse_in_view || window->mouse_selecting)) {
|
||||
Vec2I mworld = mouse - window->document_rect.min + view.scroll;
|
||||
Vec2I pos = mworld / Vec2I{FontCharSpacing, FontLineSpacing};
|
||||
XY xy = {(Int)(pos.x), (Int)(pos.y)};
|
||||
Int p = XYToPosWithoutNL(*buffer, xy);
|
||||
|
||||
if (mouse_in_view && IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
if (IsDoubleClick()) {
|
||||
Caret *c = GetLast(view.carets);
|
||||
if (InBounds({c->range.min - 1, c->range.max + 1}, p)) {
|
||||
c->range = EncloseWord(*buffer, p);
|
||||
view.selection_anchor = c->range;
|
||||
if (mouse_in_view && IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
if (IsDoubleClick()) {
|
||||
Caret *c = GetLast(view.carets);
|
||||
if (InBounds({c->range.min - 1, c->range.max + 1}, p)) {
|
||||
c->range = EncloseWord(*buffer, p);
|
||||
view.selection_anchor = c->range;
|
||||
}
|
||||
} else {
|
||||
if (!IsKeyDown(KEY_LEFT_CONTROL)) {
|
||||
view.carets.len = 0;
|
||||
}
|
||||
Add(&view.carets, MakeCaret(p, p));
|
||||
view.selection_anchor = GetLast(view.carets)->range;
|
||||
}
|
||||
} else {
|
||||
if (!IsKeyDown(KEY_LEFT_CONTROL)) {
|
||||
view.carets.len = 0;
|
||||
}
|
||||
Add(&view.carets, MakeCaret(p, p));
|
||||
view.selection_anchor = GetLast(view.carets)->range;
|
||||
|
||||
MergeCarets(&view.carets);
|
||||
} else if (IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting = true;
|
||||
}
|
||||
}
|
||||
|
||||
MergeCarets(&view.carets);
|
||||
} else if (IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting = true;
|
||||
if (window->mouse_selecting) {
|
||||
if (!IsMouseButtonDown(MOUSE_BUTTON_LEFT)) window->mouse_selecting = false;
|
||||
Caret &caret = *GetLast(view.carets);
|
||||
if (view.selection_anchor.min > p) {
|
||||
caret = MakeCaret(p, view.selection_anchor.max);
|
||||
} else if (view.selection_anchor.max < p) {
|
||||
caret = MakeCaret(p, view.selection_anchor.min);
|
||||
} else {
|
||||
caret = MakeCaret(view.selection_anchor.max, view.selection_anchor.min);
|
||||
}
|
||||
MergeCarets(&view.carets, &view.selection_anchor);
|
||||
}
|
||||
} else if (!(mouse_in_view || window->mouse_selecting) && mouse_in_scrollbar || window->mouse_selecting_scrollbar) {
|
||||
Scroller s = ComputeScrollerRect(*window);
|
||||
double size_y = (double)GetSize(window->scrollbar_rect).y;
|
||||
double p = _mouse.y - window->scrollbar_rect.min.y;
|
||||
|
||||
if (IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting_scrollbar = true;
|
||||
} else if (!IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting_scrollbar = false;
|
||||
}
|
||||
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
if (_mouse.y < s.rect.min.y || _mouse.y > s.rect.max.y) {
|
||||
view.scroll.y = (Int)(p / size_y * (double)s.line_count * (double)FontLineSpacing);
|
||||
window->mouse_scroller_offset = -(double)GetSize(s.rect).y / 2.0 / size_y;
|
||||
} else {
|
||||
window->mouse_scroller_offset = (s.rect.min.y - p) / size_y;
|
||||
}
|
||||
}
|
||||
|
||||
if (window->mouse_selecting_scrollbar) {
|
||||
double v = p / size_y;
|
||||
v = v + (window->mouse_scroller_offset);
|
||||
view.scroll.y = (Int)(v * (double)s.line_count * (double)FontLineSpacing);
|
||||
}
|
||||
}
|
||||
|
||||
if (window->mouse_selecting) {
|
||||
if (!IsMouseButtonDown(MOUSE_BUTTON_LEFT)) window->mouse_selecting = false;
|
||||
Caret &caret = *GetLast(view.carets);
|
||||
if (view.selection_anchor.min > p) {
|
||||
caret = MakeCaret(p, view.selection_anchor.max);
|
||||
} else if (view.selection_anchor.max < p) {
|
||||
caret = MakeCaret(p, view.selection_anchor.min);
|
||||
} else {
|
||||
caret = MakeCaret(view.selection_anchor.max, view.selection_anchor.min);
|
||||
}
|
||||
MergeCarets(&view.carets, &view.selection_anchor);
|
||||
}
|
||||
} else if (!(mouse_in_view || window->mouse_selecting) && mouse_in_scrollbar || window->mouse_selecting_scrollbar) {
|
||||
Scroller s = ComputeScrollerRect(*window);
|
||||
double size_y = (double)GetSize(window->scrollbar_rect).y;
|
||||
double p = _mouse.y - window->scrollbar_rect.min.y;
|
||||
|
||||
if (IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting_scrollbar = true;
|
||||
} else if (!IsMouseButtonDown(MOUSE_BUTTON_LEFT)) {
|
||||
window->mouse_selecting_scrollbar = false;
|
||||
}
|
||||
|
||||
if (IsMouseButtonPressed(MOUSE_BUTTON_LEFT)) {
|
||||
if (_mouse.y < s.rect.min.y || _mouse.y > s.rect.max.y) {
|
||||
view.scroll.y = (Int)(p / size_y * (double)s.line_count * (double)FontLineSpacing);
|
||||
window->mouse_scroller_offset = -(double)GetSize(s.rect).y / 2.0 / size_y;
|
||||
} else {
|
||||
window->mouse_scroller_offset = (s.rect.min.y - p) / size_y;
|
||||
}
|
||||
}
|
||||
|
||||
if (window->mouse_selecting_scrollbar) {
|
||||
double v = p / size_y;
|
||||
v = v + (window->mouse_scroller_offset);
|
||||
view.scroll.y = (Int)(v * (double)s.line_count * (double)FontLineSpacing);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Scrolling with caret
|
||||
if (!AreEqual(main_caret_on_begin_frame, view.carets[0]) && !dont_update_scroll) {
|
||||
Caret c = view.carets[0];
|
||||
Int front = GetFront(c);
|
||||
XY xy = PosToXY(*buffer, front);
|
||||
|
||||
Rect2I visible = GetVisibleCells(*window);
|
||||
Vec2I visible_cells = GetSize(visible);
|
||||
Vec2I visible_size = visible_cells * Vec2I{FontCharSpacing, FontLineSpacing};
|
||||
Vec2I rect_size = GetSize(window->document_rect);
|
||||
|
||||
if (xy.line > visible.max.y - 2) {
|
||||
Int set_view_at_line = xy.line - (visible_cells.y - 1);
|
||||
Int cut_off_y = Max((Int)0, visible_size.y - rect_size.y);
|
||||
view.scroll.y = (set_view_at_line * FontLineSpacing) + cut_off_y;
|
||||
}
|
||||
|
||||
if (xy.line < visible.min.y + 1) {
|
||||
view.scroll.y = xy.line * FontLineSpacing;
|
||||
}
|
||||
// Scrolling with caret
|
||||
if (!AreEqual(main_caret_on_begin_frame, view.carets[0]) && !dont_update_scroll) {
|
||||
Caret c = view.carets[0];
|
||||
Int front = GetFront(c);
|
||||
XY xy = PosToXY(*buffer, front);
|
||||
|
||||
if (xy.col >= visible.max.x - 1) {
|
||||
Int set_view_at_line = xy.col - (visible_cells.x - 1);
|
||||
Int cut_off_x = Max((Int)0, visible_size.x - rect_size.x);
|
||||
view.scroll.x = (set_view_at_line * FontCharSpacing) + cut_off_x;
|
||||
}
|
||||
Rect2I visible = GetVisibleCells(*window);
|
||||
Vec2I visible_cells = GetSize(visible);
|
||||
Vec2I visible_size = visible_cells * Vec2I{FontCharSpacing, FontLineSpacing};
|
||||
Vec2I rect_size = GetSize(window->document_rect);
|
||||
|
||||
if (xy.col <= visible.min.x) {
|
||||
view.scroll.x = xy.col * FontCharSpacing;
|
||||
if (xy.line > visible.max.y - 2) {
|
||||
Int set_view_at_line = xy.line - (visible_cells.y - 1);
|
||||
Int cut_off_y = Max((Int)0, visible_size.y - rect_size.y);
|
||||
view.scroll.y = (set_view_at_line * FontLineSpacing) + cut_off_y;
|
||||
}
|
||||
|
||||
if (xy.line < visible.min.y + 1) {
|
||||
view.scroll.y = xy.line * FontLineSpacing;
|
||||
}
|
||||
|
||||
if (xy.col >= visible.max.x - 1) {
|
||||
Int set_view_at_line = xy.col - (visible_cells.x - 1);
|
||||
Int cut_off_x = Max((Int)0, visible_size.x - rect_size.x);
|
||||
view.scroll.x = (set_view_at_line * FontCharSpacing) + cut_off_x;
|
||||
}
|
||||
|
||||
if (xy.col <= visible.min.x) {
|
||||
view.scroll.x = xy.col * FontCharSpacing;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -150,6 +150,7 @@ void DrawSelection(Window &window, Caret &it) {
|
||||
void DrawWindow(Window &window) {
|
||||
View &view = *GetActiveView(&window);
|
||||
Buffer *buffer = GetBuffer(view.buffer_id);
|
||||
DrawRectangleRec(ToRectangle(window.total_rect), ColorBackground);
|
||||
|
||||
BeginScissorMode((int)window.document_rect.min.x, (int)window.document_rect.min.y, (int)window.document_rect.max.x - (int)window.document_rect.min.x, (int)window.document_rect.max.y - (int)window.document_rect.min.y);
|
||||
For(view.carets) {
|
||||
|
||||
@@ -39,3 +39,11 @@ void SetMouseCursor() {
|
||||
SetMouseCursor(MOUSE_CURSOR_POINTING_HAND);
|
||||
}
|
||||
}
|
||||
|
||||
Array<Int> GetWindowZOrder(Allocator allocator) {
|
||||
Array<Int> order = {allocator};
|
||||
For(Windows) if (it.z == 2) Add(&order, GetIndex(Windows, it));
|
||||
For(Windows) if (it.z == 1) Add(&order, GetIndex(Windows, it));
|
||||
For(Windows) if (it.z == 0) Add(&order, GetIndex(Windows, it));
|
||||
return order;
|
||||
}
|
||||
Reference in New Issue
Block a user