mirror of
https://github.com/eliasstepanik/egui_node_graph.git
synced 2026-01-11 05:48:27 +00:00
Add WidgetValueTrait::value_widget_connected
Depending on the usage of value widgets, we might wish to display an alternative UI if the input is connected. Motivating example: consider a node with an input representing some amount of time in the context of digital signal processing. Multiple valuable representations of time may be desired as inputs: * number of seconds * number of samples * wavelength corresponding to some frequency in Hz In such a case we would use value_widget to display a widget for selecting both the number and the unit, and value_widget_connected for only selecting the unit, because the numerical value would already be supplied by another node.
This commit is contained in:
parent
78fe0265dd
commit
3b5198c050
@ -537,17 +537,26 @@ where
|
|||||||
for (param_name, param_id) in inputs {
|
for (param_name, param_id) in inputs {
|
||||||
if self.graph[param_id].shown_inline {
|
if self.graph[param_id].shown_inline {
|
||||||
let height_before = ui.min_rect().bottom();
|
let height_before = ui.min_rect().bottom();
|
||||||
|
// NOTE: We want to pass the `user_data` to
|
||||||
|
// `value_widget`, but we can't since that would require
|
||||||
|
// borrowing the graph twice. Here, we make the
|
||||||
|
// assumption that the value is cheaply replaced, and
|
||||||
|
// use `std::mem::take` to temporarily replace it with a
|
||||||
|
// dummy value. This requires `ValueType` to implement
|
||||||
|
// Default, but results in a totally safe alternative.
|
||||||
|
let mut value = std::mem::take(&mut self.graph[param_id].value);
|
||||||
|
|
||||||
if self.graph.connection(param_id).is_some() {
|
if self.graph.connection(param_id).is_some() {
|
||||||
ui.label(param_name);
|
let node_responses = value.value_widget_connected(
|
||||||
|
¶m_name,
|
||||||
|
self.node_id,
|
||||||
|
ui,
|
||||||
|
user_state,
|
||||||
|
&self.graph[self.node_id].user_data,
|
||||||
|
);
|
||||||
|
|
||||||
|
responses.extend(node_responses.into_iter().map(NodeResponse::User));
|
||||||
} else {
|
} else {
|
||||||
// NOTE: We want to pass the `user_data` to
|
|
||||||
// `value_widget`, but we can't since that would require
|
|
||||||
// borrowing the graph twice. Here, we make the
|
|
||||||
// assumption that the value is cheaply replaced, and
|
|
||||||
// use `std::mem::take` to temporarily replace it with a
|
|
||||||
// dummy value. This requires `ValueType` to implement
|
|
||||||
// Default, but results in a totally safe alternative.
|
|
||||||
let mut value = std::mem::take(&mut self.graph[param_id].value);
|
|
||||||
let node_responses = value.value_widget(
|
let node_responses = value.value_widget(
|
||||||
¶m_name,
|
¶m_name,
|
||||||
self.node_id,
|
self.node_id,
|
||||||
@ -555,9 +564,12 @@ where
|
|||||||
user_state,
|
user_state,
|
||||||
&self.graph[self.node_id].user_data,
|
&self.graph[self.node_id].user_data,
|
||||||
);
|
);
|
||||||
self.graph[param_id].value = value;
|
|
||||||
responses.extend(node_responses.into_iter().map(NodeResponse::User));
|
responses.extend(node_responses.into_iter().map(NodeResponse::User));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
self.graph[param_id].value = value;
|
||||||
|
|
||||||
let height_after = ui.min_rect().bottom();
|
let height_after = ui.min_rect().bottom();
|
||||||
input_port_heights.push((height_before + height_after) / 2.0);
|
input_port_heights.push((height_before + height_after) / 2.0);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -13,10 +13,11 @@ pub trait WidgetValueTrait: Default {
|
|||||||
type Response;
|
type Response;
|
||||||
type UserState;
|
type UserState;
|
||||||
type NodeData;
|
type NodeData;
|
||||||
|
|
||||||
/// This method will be called for each input parameter with a widget. The
|
/// This method will be called for each input parameter with a widget. The
|
||||||
/// return value is a vector of custom response objects which can be used
|
/// return value is a vector of custom response objects which can be used
|
||||||
/// to implement handling of side effects. If unsure, the response Vec can
|
/// to implement handling of side effects. If unsure, the response Vec can
|
||||||
/// be empty.
|
/// be empty. It isn't called if the input is connected.
|
||||||
fn value_widget(
|
fn value_widget(
|
||||||
&mut self,
|
&mut self,
|
||||||
param_name: &str,
|
param_name: &str,
|
||||||
@ -25,6 +26,24 @@ pub trait WidgetValueTrait: Default {
|
|||||||
user_state: &mut Self::UserState,
|
user_state: &mut Self::UserState,
|
||||||
node_data: &Self::NodeData,
|
node_data: &Self::NodeData,
|
||||||
) -> Vec<Self::Response>;
|
) -> Vec<Self::Response>;
|
||||||
|
|
||||||
|
/// This method will be called for each input parameter with a widget. The
|
||||||
|
/// return value is a vector of custom response objects which can be used
|
||||||
|
/// to implement handling of side effects. If unsure, the response Vec can
|
||||||
|
/// be empty. This differs from [`WidgetValueTrait::value_widget`]
|
||||||
|
/// by being called if and only if the input has a connection.
|
||||||
|
fn value_widget_connected(
|
||||||
|
&mut self,
|
||||||
|
param_name: &str,
|
||||||
|
_node_id: NodeId,
|
||||||
|
ui: &mut egui::Ui,
|
||||||
|
_user_state: &mut Self::UserState,
|
||||||
|
_node_data: &Self::NodeData,
|
||||||
|
) -> Vec<Self::Response> {
|
||||||
|
ui.label(param_name);
|
||||||
|
|
||||||
|
Default::default()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// This trait must be implemented by the `DataType` generic parameter of the
|
/// This trait must be implemented by the `DataType` generic parameter of the
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user