mcai_workflow/worker_definition_panel/
panel.rs

1use super::WorkerInformation;
2use by_address::ByAddress;
3use css_in_rust_next::Style;
4use mcai_models::WorkerDefinition;
5use std::sync::{Arc, Mutex};
6use yew::{html, Callback, Component, Context, Html, Properties};
7
8pub type SharedWorkerDefinition = ByAddress<Arc<Mutex<WorkerDefinition>>>;
9
10#[derive(PartialEq, Properties)]
11pub struct WorkerDefinitionPanelProperties {
12  pub height: String,
13  pub width: String,
14  pub worker_definitions: Vec<SharedWorkerDefinition>,
15  pub selected_worker_definition: Option<SharedWorkerDefinition>,
16  pub events: Option<Callback<WorkerDefinitionEvent>>,
17}
18
19pub enum WorkerDefinitionEvent {
20  WorkerDeselected,
21  WorkerSelected(SharedWorkerDefinition),
22}
23
24pub enum WorkerDefinitionMessage {
25  WorkerSelected(SharedWorkerDefinition),
26}
27
28pub struct WorkerDefinitionPanel {
29  style: Style,
30}
31
32impl Component for WorkerDefinitionPanel {
33  type Message = WorkerDefinitionMessage;
34  type Properties = WorkerDefinitionPanelProperties;
35
36  fn create(_ctx: &Context<Self>) -> Self {
37    let style = Style::create("Component", include_str!("panel.css")).unwrap();
38    Self { style }
39  }
40
41  fn update(&mut self, ctx: &Context<Self>, msg: Self::Message) -> bool {
42    match msg {
43      WorkerDefinitionMessage::WorkerSelected(worker_definition) => {
44        let event = if ctx.props().selected_worker_definition == Some(worker_definition.clone()) {
45          WorkerDefinitionEvent::WorkerDeselected
46        } else {
47          WorkerDefinitionEvent::WorkerSelected(worker_definition)
48        };
49
50        if let Some(callback) = ctx.props().events.as_ref() {
51          callback.emit(event)
52        }
53      }
54    }
55    false
56  }
57
58  fn view(&self, ctx: &Context<Self>) -> Html {
59    let style = format!(
60      "height: {}; width: {};",
61      ctx.props().height,
62      ctx.props().width,
63    );
64
65    let list = ctx.props().worker_definitions.clone();
66
67    let worker_list: Html = list
68      .iter()
69      .map(|worker| {
70        let worker_definition = worker.clone();
71
72        let selected = ctx
73          .props()
74          .selected_worker_definition
75          .as_ref()
76          .map(|worker| worker_definition == *worker)
77          .unwrap_or_default();
78
79        html!(
80          <WorkerInformation
81            worker={worker.clone()}
82            events={ctx.link().callback(move |_| WorkerDefinitionMessage::WorkerSelected(worker_definition.clone()))}
83            selected={selected}
84            />
85        )
86      })
87      .collect();
88
89    html!(
90      <span class={self.style.clone()} style={style}>
91        <div class="title">
92          <label>{"Workers"}</label>
93        </div>
94
95        <div class="content">
96          {worker_list}
97        </div>
98      </span>
99    )
100  }
101}