miracle_plugin/
workspace.rs1use super::bindings;
2use super::container::*;
3use super::core::Rectangle;
4use super::host::*;
5use super::output::*;
6
7#[derive(Debug, Clone)]
8pub struct Workspace {
9 pub number: Option<u32>,
11 pub name: Option<String>,
13 pub num_trees: u32,
15 pub rectangle: Rectangle,
17 internal: u64,
18}
19
20impl Workspace {
21 pub fn id(&self) -> u64 {
22 self.internal
23 }
24
25 pub unsafe fn from_c_with_name(value: &bindings::miracle_workspace_t, name: String) -> Self {
27 Self {
28 number: if value.has_number != 0 {
29 Some(value.number)
30 } else {
31 None
32 },
33 name: if value.has_name != 0 {
34 Some(name)
35 } else {
36 None
37 },
38 num_trees: value.num_trees,
39 internal: value.internal,
40 rectangle: Rectangle {
41 x: value.position.x,
42 y: value.position.y,
43 width: value.size.w,
44 height: value.size.h,
45 },
46 }
47 }
48
49 pub fn output(&self) -> Option<Output> {
51 const NAME_BUF_LEN: usize = 256;
52 let mut output = std::mem::MaybeUninit::<crate::bindings::miracle_output_t>::uninit();
53 let mut name_buf: [u8; NAME_BUF_LEN] = [0; NAME_BUF_LEN];
54
55 unsafe {
56 let result = miracle_workspace_get_output(
57 self.internal as i64,
58 output.as_mut_ptr() as i32,
59 name_buf.as_mut_ptr() as i32,
60 NAME_BUF_LEN as i32,
61 );
62
63 if result != 0 {
64 return None;
65 }
66
67 let output = output.assume_init();
68
69 let name_len = name_buf
71 .iter()
72 .position(|&c| c == 0)
73 .unwrap_or(NAME_BUF_LEN);
74 let name = String::from_utf8_lossy(&name_buf[..name_len]).into_owned();
75
76 Some(Output::from_c_with_name(&output, name))
77 }
78 }
79
80 pub fn tree_at(&self, index: u32) -> Option<Container> {
84 if index >= self.num_trees {
85 return None;
86 }
87
88 let mut container = std::mem::MaybeUninit::<crate::bindings::miracle_container_t>::uninit();
89 unsafe {
90 let result = miracle_workspace_get_tree(
91 self.internal as i64,
92 index,
93 container.as_mut_ptr() as i32,
94 );
95
96 if result != 0 {
97 return None;
98 }
99
100 let container = container.assume_init();
101 Some(Container::from(container))
102 }
103 }
104
105 pub fn trees(&self) -> Vec<Container> {
107 (0..self.num_trees)
108 .filter_map(|i| self.tree_at(i))
109 .collect()
110 }
111}