kitgit

tirbofish/dropbear · diff

519e08b · Thribhu K

wip: still doing testing on the buttons, doesn't look like its working Unverified

diff --git a/crates/eucalyptus-core/src/ui.rs b/crates/eucalyptus-core/src/ui.rs
index 8764363..a6426a1 100644
--- a/crates/eucalyptus-core/src/ui.rs
+++ b/crates/eucalyptus-core/src/ui.rs
@@ -2,6 +2,7 @@ mod button;
 mod utils;
 
 use std::cell::RefCell;
+use std::collections::HashMap;
 use ::jni::JNIEnv;
 use ::jni::objects::JObject;
 use parking_lot::Mutex;
@@ -31,13 +32,29 @@ pub struct UIComponent {
 
 // note for tomorrow: use UIInstruction like that of asm
 
+#[derive(Clone, Copy, Debug, Default)]
+pub struct WidgetState {
+    pub clicked: bool,
+    pub hovering: bool,
+}
+
 pub trait NativeWidget: Send + std::fmt::Debug {
-    fn build(self: Box<Self>);
+    fn build(self: Box<Self>, states: &mut HashMap<i64, WidgetState>);
+}
+
+#[derive(Debug)]
+pub struct WrapperWidget<T> {
+    pub id: i64,
+    pub widget: T,
 }
 
-impl NativeWidget for yakui::widgets::Button {
-    fn build(mut self: Box<Self>) {
-        let _ = self.show();
+impl NativeWidget for WrapperWidget<yakui::widgets::Button> {
+    fn build(self: Box<Self>, states: &mut HashMap<i64, WidgetState>) {
+        let res = self.widget.show();
+        states.insert(self.id, WidgetState {
+            clicked: res.clicked,
+            hovering: res.hovering,
+        });
     }
 }
 
@@ -71,7 +88,14 @@ impl WidgetParser for ButtonParser {
         if name_string.contains("ButtonInstruction$Button") {
             let button_obj = env.get_field(obj, "button", "Lcom/dropbear/ui/widgets/Button;")?.l()?;
             let btn = yakui::widgets::Button::from_jobject(env, &button_obj)?;
-            return Ok(Some(Box::new(btn)));
+            
+            let id_obj = env.get_field(obj, "id", "Lcom/dropbear/ui/WidgetId;")?.l()?;
+            let id = env.get_field(id_obj, "id", "J")?.j()?;
+            
+            return Ok(Some(Box::new(WrapperWidget {
+                id,
+                widget: btn,
+            })));
         }
 
         Ok(None)
@@ -82,15 +106,24 @@ impl WidgetParser for ButtonParser {
 pub struct UiContext {
     pub yakui_state: Mutex<Yakui>,
     pub instruction_set: Mutex<Vec<Box<dyn NativeWidget>>>,
+    pub widget_states: Mutex<HashMap<i64, WidgetState>>,
 }
 
 pub fn poll() {
     UI_CONTEXT.with(|v| {
         let ctx = v.borrow();
         let mut instructions = ctx.instruction_set.lock();
+        let mut widget_states = ctx.widget_states.lock();
+        // Clear previous states before rebuild? 
+        // Or yakui persistent state implies we should keep? 
+        // If we clear, and script runs before poll, it might see empty.
+        // But script reads states from PREVIOUS frame usually.
+        // Let's clear to avoid stale data from removed widgets.
+        widget_states.clear();
+        
         let current_instructions = instructions.drain(..).collect::<Vec<Box<dyn NativeWidget>>>();
         for i in current_instructions {
-            i.build();
+            i.build(&mut widget_states);
         }
     });
 }
@@ -100,6 +133,7 @@ impl UiContext {
         Self {
             yakui_state: Mutex::new(Yakui::new()),
             instruction_set: Default::default(),
+            widget_states: Default::default(),
         }
     }
 }
@@ -112,12 +146,13 @@ pub trait UiWidgetType: FromJObject {
 }
 
 pub mod jni {
+    #![allow(non_snake_case)]
+
     use jni::sys::jlong;
     use jni::objects::{JClass, JObjectArray};
     use jni::JNIEnv;
     use crate::convert_ptr;
     use crate::ui::{UiContext, get_parsers};
-    use crate::scripting::jni::utils::FromJObject;
 
     #[unsafe(no_mangle)]
     pub extern "system" fn Java_com_dropbear_ui_UINative_renderUI(
@@ -126,6 +161,7 @@ pub mod jni {
         ui_buf_ptr: jlong,
         instructions: JObjectArray,
     ) {
+        println!("[Java_com_dropbear_ui_UINative_renderUI] received new renderUI request");
         let ui = convert_ptr!(ui_buf_ptr => UiContext);
         let mut rust_instructions = Vec::new();
 
@@ -137,15 +173,16 @@ pub mod jni {
                 Ok(o) => o,
                 Err(_) => continue,
             };
-            if obj.is_null() { continue; }
+            if obj.is_null() { println!("[Java_com_dropbear_ui_UINative_renderUI] obj is null at index {}", i); continue; }
 
             for parser in parsers_guard.iter() {
                 match parser.parse(&mut env, &obj) {
                     Ok(Some(widget)) => {
+                        println!("[Java_com_dropbear_ui_UINative_renderUI] successfully located widget: {:?}", widget);
                         rust_instructions.push(widget);
                         break;
                     },
-                    Ok(None) => continue,
+                    Ok(None) => {println!("[Java_com_dropbear_ui_UINative_renderUI] Ok but None"); continue},
                     Err(e) => {
                         eprintln!("Error converting UI instruction: {:?}", e);
                     }
@@ -155,4 +192,28 @@ pub mod jni {
 
         ui.instruction_set.lock().extend(rust_instructions);
     }
+    
+    #[unsafe(no_mangle)]
+    pub extern "system" fn Java_com_dropbear_ui_widgets_ButtonNative_getClicked(
+        _env: JNIEnv,
+        _class: JClass,
+        ui_buf_ptr: jlong,
+        id: jlong,
+    ) -> bool {
+         let ui = convert_ptr!(ui_buf_ptr => UiContext);
+         let states = ui.widget_states.lock();
+         states.get(&id).map(|s| s.clicked).unwrap_or(false)
+    }
+
+    #[unsafe(no_mangle)]
+    pub extern "system" fn Java_com_dropbear_ui_widgets_ButtonNative_getHovering(
+        _env: JNIEnv,
+        _class: JClass,
+        ui_buf_ptr: jlong,
+        id: jlong,
+    ) -> bool {
+         let ui = convert_ptr!(ui_buf_ptr => UiContext);
+         let states = ui.widget_states.lock();
+         states.get(&id).map(|s| s.hovering).unwrap_or(false)
+    }
 }
\ No newline at end of file
diff --git a/scripting/commonMain/kotlin/com/dropbear/DropbearEngine.kt b/scripting/commonMain/kotlin/com/dropbear/DropbearEngine.kt
index d3c3fd4..295a6ac 100644
--- a/scripting/commonMain/kotlin/com/dropbear/DropbearEngine.kt
+++ b/scripting/commonMain/kotlin/com/dropbear/DropbearEngine.kt
@@ -3,6 +3,7 @@ package com.dropbear
 import com.dropbear.asset.AssetHandle
 import com.dropbear.ffi.NativeEngine
 import com.dropbear.input.InputState
+import com.dropbear.logging.Logger
 import com.dropbear.scene.SceneManager
 import com.dropbear.ui.UIInstruction
 
@@ -75,7 +76,8 @@ class DropbearEngine(val native: NativeEngine) {
     }
 
     fun renderUI(uiInstructionSet: List<UIInstruction>) {
-        com.dropbear.renderUI(uiInstructionSet)
+        Logger.trace("instructions: $uiInstructionSet")
+        renderUI(instructions = uiInstructionSet)
     }
 
     /**
@@ -95,4 +97,4 @@ class DropbearEngine(val native: NativeEngine) {
 internal expect fun getEntity(label: String): Long?
 internal expect fun getAsset(eucaURI: String): Long?
 internal expect fun quit()
-internal expect fun renderUI(uiInstructionSet: List<UIInstruction>)
\ No newline at end of file
+internal expect fun renderUI(instructions: List<UIInstruction>)
\ No newline at end of file
diff --git a/scripting/jvmMain/kotlin/com/dropbear/DropbearEngine.jvm.kt b/scripting/jvmMain/kotlin/com/dropbear/DropbearEngine.jvm.kt
index 124beaa..808543e 100644
--- a/scripting/jvmMain/kotlin/com/dropbear/DropbearEngine.jvm.kt
+++ b/scripting/jvmMain/kotlin/com/dropbear/DropbearEngine.jvm.kt
@@ -15,6 +15,6 @@ internal actual fun quit() {
     DropbearEngineNative.quit(DropbearEngine.native.commandBufferHandle)
 }
 
-internal actual fun renderUI(uiInstructionSet: List<UIInstruction>) {
-    UINative.renderUI(DropbearEngine.native.uiBufferHandle, uiInstructionSet.toTypedArray())
+internal actual fun renderUI(instructions: List<UIInstruction>) {
+    UINative.renderUI(DropbearEngine.native.uiBufferHandle, instructions.toTypedArray())
 }
\ No newline at end of file
diff --git a/scripting/nativeMain/kotlin/com/dropbear/DropbearEngine.native.kt b/scripting/nativeMain/kotlin/com/dropbear/DropbearEngine.native.kt
index cc722cf..6b2a1ca 100644
--- a/scripting/nativeMain/kotlin/com/dropbear/DropbearEngine.native.kt
+++ b/scripting/nativeMain/kotlin/com/dropbear/DropbearEngine.native.kt
@@ -14,5 +14,5 @@ internal actual fun getAsset(eucaURI: String): Long? {
 internal actual fun quit() {
 }
 
-internal actual fun renderUI(uiInstructionSet: List<UIInstruction>) {
+internal actual fun renderUI(instructions: List<UIInstruction>) {
 }
\ No newline at end of file