/* SPDX-License-Identifier: GPL-3.0-or-later */ /* Copyright (C) 2021 KikooDX */ #include "conf.h" #include "editing_area/draw.h" #include "editing_area/level.h" #include "info.h" #include "mouse.h" #include "options.h" #include "scale.h" #include "shared_data.h" #include #include #include #include #include static void init_mouse(struct Options options); static void update_mouse(int *mouse_x, int *mouse_y, struct Level level, struct SharedData *shared_data); int editing_area_main(struct Options options, struct SharedData *shared_data) { int mouse_x; int mouse_y; int error; struct Level level; level.data = NULL; Texture2D tileset; /* initialize raylib */ InitWindow(options.editor_width * options.editor_scale, options.editor_height * options.editor_scale, "SLE main window"); SetWindowState(FLAG_WINDOW_RESIZABLE); SetTargetFPS(options.editor_target_fps); /* load textures */ tileset = LoadTexture(options.tileset_path); /* render targets used for upscaling */ const RenderTexture2D rend_target = LoadRenderTexture( options.editor_width, options.editor_height); const RenderTexture2D flip_target = LoadRenderTexture( options.editor_width, options.editor_height); /* only proceed if tileset is large enough */ if (tileset.width < options.tile_width || tileset.height < options.tile_height) { fprintf(stderr, "ERROR: tileset size is invalid, expected at " "least [%d ; %d], got [%d ; %d]\n", options.tile_width, options.tile_height, tileset.width, tileset.height); goto panic; } /* load level or create empty one */ if (options.level_create) { if (level_create(&level, options)) goto panic; } else if (level_read(&level, options.level_path)) goto panic; while (!WindowShouldClose()) { /* update */ init_mouse(options); update_mouse(&mouse_x, &mouse_y, level, shared_data); /* draw */ BeginDrawing(); BeginTextureMode(rend_target); ClearBackground(options.editor_bg_color); level_draw(level, options, tileset); editor_mouse_draw(options, mouse_x, mouse_y); EndTextureMode(); /* flip texture */ BeginTextureMode(flip_target); DrawTexture(rend_target.texture, 0, 0, WHITE); EndTextureMode(); /* draw upscaled render */ ClearBackground(BLACK); DrawTextureEx(flip_target.texture, offset_editor(options), 0, scale_editor(options), WHITE); EndDrawing(); } /* save level */ level_write(level, options.level_path); panic: /* deinit */ level_free(&level); /* unload raylib stuff */ UnloadTexture(tileset); UnloadRenderTexture(rend_target); UnloadRenderTexture(flip_target); CloseWindow(); /* tell to the child process it can end */ shared_data->end_child = true; /* wait for child process to exit */ wait(NULL); return EXIT_SUCCESS; } static void init_mouse(struct Options options) { const float scaling = scale_editor(options); const Vector2 off = offset_editor(options); SetMouseOffset(-options.editor_draw_offset_x - off.x, -options.editor_draw_offset_y - off.y); SetMouseScale(1.0 / scaling / options.tile_width, 1.0 / scaling / options.tile_height); } static void update_mouse(int *mouse_x, int *mouse_y, struct Level level, struct SharedData *shared_data) { const bool left_click = IsMouseButtonDown(0); const bool right_click = IsMouseButtonDown(1); const bool middle_click = IsMouseButtonPressed(2); update_mouse_position(mouse_x, mouse_y, level.width - 1, level.height - 1); /* set tile */ if (left_click) level.data[*mouse_x + *mouse_y * level.width] = shared_data->selected_tile; /* remove tile */ if (right_click) level.data[*mouse_x + *mouse_y * level.width] = 0; /* set tile to pointed cell (pick tile) */ if (middle_click) { INFO_VAR("%d", level.data[*mouse_x + *mouse_y * level.width]); shared_data->selected_tile = level.data[*mouse_x + *mouse_y * level.width]; } }