gui: display VMUs on pause

This commit is contained in:
Flyinghead 2019-03-29 17:35:00 +01:00
parent 80626b1f4e
commit 8fb1d80751
6 changed files with 120 additions and 39 deletions

View File

@ -408,7 +408,6 @@ int main(int argc, wchar* argv[])
#endif
int get_mic_data(u8* buffer) { return 0; }
int push_vmu_screen(u8* buffer) { return 0; }
void os_DebugBreak()
{

View File

@ -585,3 +585,20 @@ void ImGui_ImplOpenGL3_DrawBackground()
glClear(GL_COLOR_BUFFER_BIT);
}
}
ImTextureID ImGui_ImplOpenGL3_CreateVmuTexture(const unsigned int *data)
{
GLuint tex_id;
glGenTextures(1, &tex_id);
glBindTexture(GL_TEXTURE_2D, tex_id);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA, 48, 32, 0, GL_RGBA, GL_UNSIGNED_BYTE, data);
return reinterpret_cast<ImTextureID>(tex_id);
}
void ImGui_ImplOpenGL3_DeleteVmuTexture(ImTextureID tex_id)
{
glDeleteTextures(1, &(GLuint &)tex_id);
}

View File

@ -34,6 +34,8 @@ IMGUI_IMPL_API void ImGui_ImplOpenGL3_Shutdown();
IMGUI_IMPL_API void ImGui_ImplOpenGL3_NewFrame();
IMGUI_IMPL_API void ImGui_ImplOpenGL3_RenderDrawData(ImDrawData* draw_data, bool save_background = false);
IMGUI_IMPL_API void ImGui_ImplOpenGL3_DrawBackground();
IMGUI_IMPL_API ImTextureID ImGui_ImplOpenGL3_CreateVmuTexture(const unsigned int *);
IMGUI_IMPL_API void ImGui_ImplOpenGL3_DeleteVmuTexture(ImTextureID);
// Called by Init/NewFrame/Shutdown
IMGUI_IMPL_API bool ImGui_ImplOpenGL3_CreateFontsTexture();

View File

@ -64,6 +64,10 @@ GuiState gui_state = Main;
static bool settings_opening;
static bool touch_up;
static void display_vmus();
static void reset_vmus();
static void term_vmus();
void gui_init()
{
if (inited)
@ -290,6 +294,8 @@ static void gui_display_commands()
if (!settings_opening)
ImGui_ImplOpenGL3_DrawBackground();
display_vmus();
ImGui::SetNextWindowPos(ImVec2(screen_width / 2.f, screen_height / 2.f), ImGuiCond_Always, ImVec2(0.5f, 0.5f));
ImGui::SetNextWindowSize(ImVec2(330 * scaling, 0));
@ -635,6 +641,7 @@ static void gui_display_settings()
gui_state = Main;
#if DC_PLATFORM == DC_PLATFORM_DREAMCAST
maple_ReconnectDevices();
reset_vmus();
#endif
SaveSettings();
}
@ -1470,6 +1477,7 @@ void gui_open_onboarding()
void gui_term()
{
inited = false;
term_vmus();
ImGui_ImplOpenGL3_Shutdown();
ImGui::DestroyContext();
}
@ -1495,3 +1503,93 @@ void gui_refresh_files()
game_list_done = false;
subfolders_read = false;
}
#define VMU_WIDTH (70 * 48 * scaling / 32)
#define VMU_HEIGHT (70 * scaling)
#define VMU_PADDING (8 * scaling)
static u32 vmu_lcd_data[8][48 * 32];
static bool vmu_lcd_status[8];
static ImTextureID vmu_lcd_tex_ids[8];
int push_vmu_screen(int vmu_id, u8* buffer)
{
u32 *p = &vmu_lcd_data[vmu_id][0];
for (int i = 0; i < ARRAY_SIZE(vmu_lcd_data[vmu_id]); i++, buffer++)
*p++ = *buffer != 0 ? 0xFFFFFFFFu : 0xFF000000u;
vmu_lcd_status[vmu_id] = true;
return 0;
}
static const int vmu_coords[8][2] = {
{ 0 , 0 },
{ 0 , 0 },
{ 1 , 0 },
{ 1 , 0 },
{ 0 , 1 },
{ 0 , 1 },
{ 1 , 1 },
{ 1 , 1 },
};
static void display_vmus()
{
if (!game_started)
return;
ImGui::SetNextWindowBgAlpha(0);
ImGui::SetNextWindowPos(ImVec2(0, 0));
ImGui::SetNextWindowSize(ImVec2(screen_width, screen_height));
ImGui::Begin("vmu-window", NULL, ImGuiWindowFlags_NoDecoration | ImGuiWindowFlags_NoNav | ImGuiWindowFlags_NoInputs
| ImGuiWindowFlags_NoBackground | ImGuiWindowFlags_NoFocusOnAppearing);
for (int i = 0; i < 8; i++)
{
if (!vmu_lcd_status[i])
continue;
if (vmu_lcd_tex_ids[i] != (ImTextureID)0)
ImGui_ImplOpenGL3_DeleteVmuTexture(vmu_lcd_tex_ids[i]);
vmu_lcd_tex_ids[i] = ImGui_ImplOpenGL3_CreateVmuTexture(vmu_lcd_data[i]);
int x = vmu_coords[i][0];
int y = vmu_coords[i][1];
ImVec2 pos;
if (x == 0)
pos.x = VMU_PADDING;
else
pos.x = screen_width - VMU_WIDTH - VMU_PADDING;
if (y == 0)
{
pos.y = VMU_PADDING;
if (i & 1)
pos.y += VMU_HEIGHT + VMU_PADDING;
}
else
{
pos.y = screen_height - VMU_HEIGHT - VMU_PADDING;
if (i & 1)
pos.y -= VMU_HEIGHT + VMU_PADDING;
}
ImVec2 pos_b(pos.x + VMU_WIDTH, pos.y + VMU_HEIGHT);
ImGui::GetWindowDrawList()->AddImage(vmu_lcd_tex_ids[i], pos, pos_b, ImVec2(0, 1), ImVec2(1, 0), 0xC0ffffff);
}
ImGui::End();
}
static void reset_vmus()
{
for (int i = 0; i < ARRAY_SIZE(vmu_lcd_status); i++)
vmu_lcd_status[i] = false;
}
static void term_vmus()
{
for (int i = 0; i < ARRAY_SIZE(vmu_lcd_status); i++)
{
if (vmu_lcd_tex_ids[i] != (ImTextureID)0)
{
ImGui_ImplOpenGL3_DeleteVmuTexture(vmu_lcd_tex_ids[i]);
vmu_lcd_tex_ids[i] = (ImTextureID)0;
}
}
}

View File

@ -183,7 +183,7 @@ void select_directory_popup(const char *prompt, float scaling, StringCallback ca
}
ImGui::Text("%s", error_message.empty() ? select_current_directory.c_str() : error_message.c_str());
ImGui::BeginChild(ImGui::GetID("dir_list"), ImVec2(0, -ImGui::CalcTextSize("Cancel").y - ImGui::GetStyle().FramePadding. y * 2 - ImGui::GetStyle().ItemSpacing.y), true);
ImGui::BeginChild(ImGui::GetID("dir_list"), ImVec2(0, - 30 * scaling - ImGui::GetStyle().ItemSpacing.y), true);
ImGui::PushStyleVar(ImGuiStyleVar_ItemSpacing, ImVec2(8 * scaling, 20 * scaling)); // from 8, 4
@ -245,14 +245,14 @@ void select_directory_popup(const char *prompt, float scaling, StringCallback ca
}
ImGui::PopStyleVar();
ImGui::EndChild();
if (ImGui::Button("Select Current Directory"))
if (ImGui::Button("Select Current Directory", ImVec2(0, 30 * scaling)))
{
subfolders_read = false;
callback(false, select_current_directory);
ImGui::CloseCurrentPopup();
}
ImGui::SameLine();
if (ImGui::Button("Cancel"))
if (ImGui::Button("Cancel", ImVec2(0, 30 * scaling)))
{
subfolders_read = false;
callback(true, "");

View File

@ -315,10 +315,6 @@ JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_diskSwap(JNIEnv *env,
//stuff for microphone
jobject sipemu;
jmethodID getmicdata;
//stuff for vmu lcd
jobject vmulcd = NULL;
jbyteArray jpix = NULL;
jmethodID updatevmuscreen;
extern bool game_started;
//stuff for audio
@ -333,12 +329,6 @@ JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_setupMic(JNIEnv *env,
getmicdata = env->GetMethodID(env->GetObjectClass(sipemu),"getData","()[B");
}
JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_setupVmu(JNIEnv *env,jobject obj,jobject vmu)
{
vmulcd = env->NewGlobalRef(vmu);
updatevmuscreen = env->GetMethodID(env->GetObjectClass(vmu),"updateBytes","([B)V");
}
JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_pause(JNIEnv *env,jobject obj)
{
if (game_started)
@ -362,18 +352,6 @@ JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_destroy(JNIEnv *env,j
dc_term();
}
JNIEXPORT void JNICALL Java_com_reicast_emulator_emu_JNIdc_vmuSwap(JNIEnv *env,jobject obj)
{
maple_device* olda = MapleDevices[0][0];
maple_device* oldb = MapleDevices[0][1];
MapleDevices[0][0] = NULL;
MapleDevices[0][1] = NULL;
usleep(50000);//50 ms, wait for host to detect disconnect
MapleDevices[0][0] = oldb;
MapleDevices[0][1] = olda;
}
JNIEXPORT jint JNICALL Java_com_reicast_emulator_emu_JNIdc_send(JNIEnv *env,jobject obj,jint cmd, jint param)
{
if (cmd==0)
@ -584,19 +562,6 @@ int get_mic_data(u8* buffer)
return 1;
}
int push_vmu_screen(u8* buffer)
{
if(vmulcd==NULL){
return 0;
}
if(jpix==NULL){
jpix = jvm_attacher.getEnv()->NewByteArray(1536);
}
jvm_attacher.getEnv()->SetByteArrayRegion(jpix, 0, 1536, (jbyte*)buffer);
jvm_attacher.getEnv()->CallVoidMethod(vmulcd, updatevmuscreen, jpix);
return 1;
}
void os_DebugBreak()
{
// TODO: notify the parent thread about it ...