Skip to main content

agpu/ontology/
gpu.rs

1//! GPU-specific ontology implementations.
2//!
3//! Provides [`Discoverable`] wrappers for GPU subsystems: the shape
4//! renderer, text engine, surface, pipeline, and the agpu application
5//! itself.
6
7use super::*;
8
9/// Ontology for the [`ShapeRenderer`](crate::renderer::ShapeRenderer).
10pub struct ShapeRendererOntology;
11
12impl Discoverable for ShapeRendererOntology {
13    fn schema(&self) -> WidgetSchema {
14        let mut s = WidgetSchema::new(
15            "ShapeRenderer",
16            "Batched 2D shape renderer — fills, strokes, circles, and lines",
17            SemanticRole::System,
18        );
19        s.tags = vec![
20            "gpu".into(),
21            "renderer".into(),
22            "2d".into(),
23            "shapes".into(),
24        ];
25        s
26    }
27
28    fn capabilities(&self) -> Vec<AgentCapability> {
29        vec![AgentCapability::Custom("gpu_renderer".into())]
30    }
31
32    fn actions(&self) -> Vec<AgentAction> {
33        vec![
34            AgentAction::simple("fill_rect", "Draw a filled rectangle", false),
35            AgentAction::simple("stroke_rect", "Draw a stroked rectangle", false),
36            AgentAction::simple("fill_circle", "Draw a filled circle", false),
37            AgentAction::simple("stroke_circle", "Draw a stroked circle outline", false),
38            AgentAction::simple("line", "Draw a line segment", false),
39        ]
40    }
41
42    fn semantic_role(&self) -> SemanticRole {
43        SemanticRole::System
44    }
45
46    fn agent_state(&self) -> serde_json::Value {
47        serde_json::json!({ "kind": "ShapeRenderer" })
48    }
49
50    fn execute_action(
51        &mut self,
52        action: &str,
53        _params: &serde_json::Value,
54    ) -> Result<serde_json::Value, String> {
55        Err(format!("ShapeRenderer actions are internal: {action}"))
56    }
57}
58
59/// Ontology for the [`TextEngine`](crate::text::TextEngine).
60pub struct TextEngineOntology;
61
62impl Discoverable for TextEngineOntology {
63    fn schema(&self) -> WidgetSchema {
64        let mut s = WidgetSchema::new(
65            "TextEngine",
66            "GPU text renderer (glyphon) — font shaping, glyph rasterisation",
67            SemanticRole::System,
68        );
69        s.tags = vec!["gpu".into(), "text".into(), "font".into(), "glyphon".into()];
70        s
71    }
72
73    fn capabilities(&self) -> Vec<AgentCapability> {
74        vec![AgentCapability::Custom("gpu_text".into())]
75    }
76
77    fn actions(&self) -> Vec<AgentAction> {
78        vec![
79            AgentAction::simple("measure_text", "Measure text size without drawing", false),
80            AgentAction::simple("draw_text", "Draw text at a position", false),
81        ]
82    }
83
84    fn semantic_role(&self) -> SemanticRole {
85        SemanticRole::System
86    }
87
88    fn agent_state(&self) -> serde_json::Value {
89        serde_json::json!({ "kind": "TextEngine" })
90    }
91
92    fn execute_action(
93        &mut self,
94        action: &str,
95        _params: &serde_json::Value,
96    ) -> Result<serde_json::Value, String> {
97        Err(format!("TextEngine actions are internal: {action}"))
98    }
99}
100
101/// Ontology for the GPU surface (swap chain).
102pub struct SurfaceOntology;
103
104impl Discoverable for SurfaceOntology {
105    fn schema(&self) -> WidgetSchema {
106        let mut s = WidgetSchema::new(
107            "GpuSurface",
108            "GPU presentation surface — swap chain and frame management",
109            SemanticRole::System,
110        );
111        s.tags = vec!["gpu".into(), "surface".into(), "swap-chain".into()];
112        s
113    }
114
115    fn capabilities(&self) -> Vec<AgentCapability> {
116        vec![AgentCapability::Custom("gpu_surface".into())]
117    }
118
119    fn actions(&self) -> Vec<AgentAction> {
120        vec![AgentAction::simple(
121            "get_format",
122            "Query the surface texture format",
123            false,
124        )]
125    }
126
127    fn semantic_role(&self) -> SemanticRole {
128        SemanticRole::System
129    }
130
131    fn agent_state(&self) -> serde_json::Value {
132        serde_json::json!({ "kind": "Surface" })
133    }
134
135    fn execute_action(
136        &mut self,
137        action: &str,
138        _params: &serde_json::Value,
139    ) -> Result<serde_json::Value, String> {
140        Err(format!("Surface actions are internal: {action}"))
141    }
142}
143
144/// Ontology for a render/compute pipeline.
145pub struct PipelineOntology;
146
147impl Discoverable for PipelineOntology {
148    fn schema(&self) -> WidgetSchema {
149        let mut s = WidgetSchema::new(
150            "GpuPipeline",
151            "GPU pipeline — compiled shader program and fixed-function state",
152            SemanticRole::System,
153        );
154        s.tags = vec!["gpu".into(), "pipeline".into(), "shader".into()];
155        s
156    }
157
158    fn capabilities(&self) -> Vec<AgentCapability> {
159        vec![AgentCapability::Custom("gpu_pipeline".into())]
160    }
161
162    fn actions(&self) -> Vec<AgentAction> {
163        vec![AgentAction::simple(
164            "get_info",
165            "Query pipeline metadata",
166            false,
167        )]
168    }
169
170    fn semantic_role(&self) -> SemanticRole {
171        SemanticRole::System
172    }
173
174    fn agent_state(&self) -> serde_json::Value {
175        serde_json::json!({ "kind": "Pipeline" })
176    }
177
178    fn execute_action(
179        &mut self,
180        action: &str,
181        _params: &serde_json::Value,
182    ) -> Result<serde_json::Value, String> {
183        Err(format!("Pipeline actions are internal: {action}"))
184    }
185}
186
187/// Ontology for the whole agpu application.
188pub struct AgpuAppOntology;
189
190impl Discoverable for AgpuAppOntology {
191    fn schema(&self) -> WidgetSchema {
192        let mut s = WidgetSchema::new(
193            "AgpuApp",
194            "agpu application runner — winit window + wgpu rendering loop",
195            SemanticRole::Container,
196        );
197        s.tags = vec!["app".into(), "window".into(), "gpu".into()];
198        s
199    }
200
201    fn capabilities(&self) -> Vec<AgentCapability> {
202        vec![
203            AgentCapability::Focusable,
204            AgentCapability::Resizable {
205                min_width: None,
206                min_height: None,
207                max_width: None,
208                max_height: None,
209            },
210            AgentCapability::Closable,
211        ]
212    }
213
214    fn actions(&self) -> Vec<AgentAction> {
215        vec![
216            AgentAction::simple("quit", "Close the application", false),
217            AgentAction::simple("export_ontology", "Export ontology registry as JSON", false),
218        ]
219    }
220
221    fn semantic_role(&self) -> SemanticRole {
222        SemanticRole::Container
223    }
224
225    fn agent_state(&self) -> serde_json::Value {
226        serde_json::json!({ "kind": "AgpuApp", "running": true })
227    }
228
229    fn execute_action(
230        &mut self,
231        action: &str,
232        _params: &serde_json::Value,
233    ) -> Result<serde_json::Value, String> {
234        match action {
235            "quit" => Ok(serde_json::json!({"status": "quit_requested"})),
236            "export_ontology" => Ok(serde_json::json!({"status": "export_requested"})),
237            _ => Err(format!("Unknown action: {action}")),
238        }
239    }
240}