imgui: synchronize platform code with upstream allegro5 example

This commit is contained in:
Sebastian Krzyszkowiak 2019-05-31 02:52:29 +02:00
parent 7ade9ee1aa
commit b0ec8ef683
No known key found for this signature in database
GPG key ID: E8F235CF3BDBC3FF

View file

@ -16,6 +16,9 @@
// CHANGELOG
// (minor and older changes stripped away, please see git history for details)
// 2019-05-11: Inputs: Don't filter character value from ALLEGRO_EVENT_KEY_CHAR before calling AddInputCharacter().
// 2019-04-30: Renderer: Added support for special ImDrawCallback_ResetRenderState callback to reset render state.
// 2018-11-30: Misc: Setting up io.BackendPlatformName/io.BackendRendererName so they can be displayed in the About Window.
// 2018-06-13: Platform: Added clipboard support (from Allegro 5.1.12).
// 2018-06-13: Renderer: Use draw_data->DisplayPos and draw_data->DisplaySize to setup projection matrix and clipping rectangle.
// 2018-06-13: Renderer: Backup/restore transform and clipping rectangle.
@ -31,6 +34,8 @@
#include <stdint.h> // uint64_t
#include <string.h> // memcpy
#define ImDrawCallback_ResetRenderState (ImDrawCallback)(-1)
#define ALLEGRO_HAS_CLIPBOARD (ALLEGRO_VERSION_INT >= ((5 << 24) | (1 << 16) | (12 << 8))) // Clipboard only supported from Allegro 5.1.12
// Visual Studio warnings
@ -52,18 +57,8 @@ struct ImDrawVertAllegro {
};
typedef struct ImDrawVertAllegro ImDrawVertAllegro;
// Render function.
// (this used to be set in io->RenderDrawListsFn and called by ImGui::Render(), but you can now call this directly from your main loop)
SYMBOL_INTERNAL void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data) {
// Backup Allegro state that will be modified
ALLEGRO_TRANSFORM last_transform = *al_get_current_transform();
ALLEGRO_TRANSFORM last_projection_transform = *al_get_current_projection_transform();
int last_clip_x, last_clip_y, last_clip_w, last_clip_h;
al_get_clipping_rectangle(&last_clip_x, &last_clip_y, &last_clip_w, &last_clip_h);
int last_blender_op, last_blender_src, last_blender_dst;
al_get_blender(&last_blender_op, &last_blender_src, &last_blender_dst);
// Setup render state
static void ImGui_ImplAllegro5_SetupRenderState(ImDrawData* draw_data) {
// Setup blending
al_set_blender(ALLEGRO_ADD, ALLEGRO_ALPHA, ALLEGRO_INVERSE_ALPHA);
// Setup orthographic projection matrix
@ -79,7 +74,28 @@ SYMBOL_INTERNAL void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data) {
al_orthographic_transform(&transform, L, T, 1.0F, R, B, -1.0F);
al_use_projection_transform(&transform);
}
}
// Render function.
// (this used to be set in io->RenderDrawListsFn and called by ImGui::Render(), but you can now call this directly from your main loop)
SYMBOL_INTERNAL void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data) {
// Avoid rendering when minimized
if (draw_data->DisplaySize.x <= 0.0f || draw_data->DisplaySize.y <= 0.0f) {
return;
}
// Backup Allegro state that will be modified
ALLEGRO_TRANSFORM last_transform = *al_get_current_transform();
ALLEGRO_TRANSFORM last_projection_transform = *al_get_current_projection_transform();
int last_clip_x, last_clip_y, last_clip_w, last_clip_h;
al_get_clipping_rectangle(&last_clip_x, &last_clip_y, &last_clip_w, &last_clip_h);
int last_blender_op, last_blender_src, last_blender_dst;
al_get_blender(&last_blender_op, &last_blender_src, &last_blender_dst);
// Setup desired render state
ImGui_ImplAllegro5_SetupRenderState(draw_data);
// Render command lists
for (int n = 0; n < draw_data->CmdListsCount; n++) {
const ImDrawList* cmd_list = draw_data->CmdLists[n];
@ -111,15 +127,23 @@ SYMBOL_INTERNAL void ImGui_ImplAllegro5_RenderDrawData(ImDrawData* draw_data) {
indices = (void*)cmd_list->IdxBuffer.Data;
}
// Render command lists
int idx_offset = 0;
ImVec2 pos = draw_data->DisplayPos;
ImVec2 clip_off = draw_data->DisplayPos;
for (int cmd_i = 0; cmd_i < cmd_list->CmdBuffer.Size; cmd_i++) {
const ImDrawCmd* pcmd = &cmd_list->CmdBuffer.Data[cmd_i];
if (pcmd->UserCallback) {
pcmd->UserCallback(cmd_list, pcmd);
// User callback, registered via ImDrawList::AddCallback()
// (ImDrawCallback_ResetRenderState is a special callback value used by the user to request the renderer to reset render state.)
if (pcmd->UserCallback == ImDrawCallback_ResetRenderState) {
ImGui_ImplAllegro5_SetupRenderState(draw_data);
} else {
pcmd->UserCallback(cmd_list, pcmd);
}
} else {
// Draw
ALLEGRO_BITMAP* texture = (ALLEGRO_BITMAP*)pcmd->TextureId;
al_set_clipping_rectangle((int)(pcmd->ClipRect.x - pos.x), (int)(pcmd->ClipRect.y - pos.y), (int)(pcmd->ClipRect.z - pcmd->ClipRect.x), (int)(pcmd->ClipRect.w - pcmd->ClipRect.y));
al_set_clipping_rectangle((int)(pcmd->ClipRect.x - clip_off.x), (int)(pcmd->ClipRect.y - clip_off.y), (int)(pcmd->ClipRect.z - pcmd->ClipRect.x), (int)(pcmd->ClipRect.w - pcmd->ClipRect.y));
al_draw_prim(&vertices[0], g_VertexDecl, texture, idx_offset, idx_offset + pcmd->ElemCount, ALLEGRO_PRIM_TRIANGLE_LIST);
}
idx_offset += pcmd->ElemCount;
@ -207,6 +231,7 @@ SYMBOL_INTERNAL bool ImGui_ImplAllegro5_Init(ALLEGRO_DISPLAY* display) {
// Setup back-end capabilities flags
ImGuiIO* io = igGetIO();
io->BackendFlags |= ImGuiBackendFlags_HasMouseCursors; // We can honor GetMouseCursor() values (optional)
io->BackendPlatformName = io->BackendRendererName = "imgui_impl_allegro5";
// Create custom vertex declaration.
// Unfortunately Allegro doesn't support 32-bits packed colors so we have to convert them to 4 floats.
@ -254,7 +279,13 @@ SYMBOL_INTERNAL void ImGui_ImplAllegro5_Shutdown() {
ImGui_ImplAllegro5_InvalidateDeviceObjects();
g_Display = NULL;
// Destroy last known clipboard data
g_Time = 0.0;
if (g_VertexDecl) {
al_destroy_vertex_decl(g_VertexDecl);
}
g_VertexDecl = NULL;
if (g_ClipboardTextData) {
al_free(g_ClipboardTextData);
}
@ -301,9 +332,7 @@ SYMBOL_INTERNAL bool ImGui_ImplAllegro5_ProcessEvent(ALLEGRO_EVENT* ev) {
return true;
case ALLEGRO_EVENT_KEY_CHAR:
if (ev->keyboard.display == g_Display) {
if (ev->keyboard.unichar > 0 && ev->keyboard.unichar < 0x10000) {
ImGuiIO_AddInputCharacter(io, (unsigned short)ev->keyboard.unichar);
}
ImGuiIO_AddInputCharacter(io, (unsigned int)ev->keyboard.unichar);
}
return true;
case ALLEGRO_EVENT_KEY_DOWN: