Skip to content

Commit fb5a083

Browse files
committed
Merge branch 'refs/heads/main' into forman-add_callback_function_details
2 parents 323711e + 36a9fe7 commit fb5a083

File tree

15 files changed

+147
-78
lines changed

15 files changed

+147
-78
lines changed

dashi/package-lock.json

Lines changed: 7 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

dashi/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
"dependencies": {
1515
"@emotion/react": "^11.13.3",
1616
"@emotion/styled": "^11.13.0",
17+
"@fontsource/roboto": "^5.1.0",
1718
"@mui/material": "^6.1.1",
1819
"immer": "^10.1.1",
1920
"plotly.js": "^2.35.2",

dashi/src/actions/handleComponentPropertyChange.ts

Lines changed: 46 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -5,13 +5,9 @@ import {
55
isContainerModel,
66
PropertyChangeEvent,
77
} from "../model/component";
8-
import {
9-
CallbackCallRequest,
10-
CallbackCallResult,
11-
ComputedOutput,
12-
} from "../model/callback";
8+
import { CallbackCallRequest, ChangeRequest, Change } from "../model/callback";
139
import fetchApiResult from "../utils/fetchApiResult";
14-
import { fetchCallbackCallResults } from "../api";
10+
import { fetchChangeRequests } from "../api";
1511
import { updateArray } from "../utils/updateArray";
1612

1713
export default function handleComponentPropertyChange(
@@ -27,6 +23,8 @@ export default function handleComponentPropertyChange(
2723
const componentPropertyValue = contribEvent.propertyValue;
2824
const contributionModel = contributionModels[contribIndex];
2925
const callRequests: CallbackCallRequest[] = [];
26+
// Prepare calling all callbacks of the contribution
27+
// that are triggered by the property change
3028
(contributionModel.callbacks || []).forEach((callback, callbackIndex) => {
3129
if (callback.inputs && callback.inputs.length > 0) {
3230
let triggerIndex: number = -1;
@@ -38,11 +36,12 @@ export default function handleComponentPropertyChange(
3836
input.id === componentId &&
3937
input.property === componentPropertyName
4038
) {
39+
// Ok - the current callback is triggered by the property change
4140
triggerIndex = inputIndex;
4241
return componentPropertyValue;
4342
} else {
4443
// TODO: get inputValue from other component with given id/property.
45-
// For time being we use null as it is JSON-serializable
44+
// For time being we use null as it is JSON-serializable
4645
}
4746
} else {
4847
// TODO: get inputValue from other kinds.
@@ -62,44 +61,64 @@ export default function handleComponentPropertyChange(
6261
}
6362
}
6463
});
64+
const originalChangeRequest: ChangeRequest = {
65+
contribPoint,
66+
contribIndex,
67+
changes: [
68+
{
69+
kind: "Component",
70+
id: componentId,
71+
property: componentPropertyName,
72+
value: componentPropertyValue,
73+
},
74+
],
75+
};
6576
console.debug("callRequests", callRequests);
66-
if (callRequests.length) {
67-
fetchApiResult(fetchCallbackCallResults, callRequests).then(
68-
(callResultResult) => {
69-
if (callResultResult.data) {
70-
applyCallbackCallResults(callResultResult.data);
77+
if (callRequests.length == 0) {
78+
applyChangeRequests([originalChangeRequest]);
79+
} else {
80+
fetchApiResult(fetchChangeRequests, callRequests).then(
81+
(changeRequestsResult) => {
82+
if (changeRequestsResult.data) {
83+
applyChangeRequests(
84+
[originalChangeRequest].concat(changeRequestsResult.data),
85+
);
7186
} else {
72-
console.error("callback failed:", callResultResult.error);
73-
console.error(" for requests:", callRequests);
87+
console.error(
88+
"callback failed:",
89+
changeRequestsResult.error,
90+
"for call requests:",
91+
callRequests,
92+
);
7493
}
7594
},
7695
);
7796
}
7897
}
7998

80-
function applyCallbackCallResults(callResults: CallbackCallResult[]) {
81-
console.log("processing call results", callResults);
82-
callResults.forEach(({ contribPoint, contribIndex, computedOutputs }) => {
99+
function applyChangeRequests(changeRequests: ChangeRequest[]) {
100+
console.log("applying change requests", changeRequests);
101+
changeRequests.forEach(({ contribPoint, contribIndex, changes }) => {
83102
console.log(
84-
"processing output of",
103+
"processing change request",
85104
contribPoint,
86105
contribIndex,
87-
computedOutputs,
106+
changes,
88107
);
89108
const contributionStatesRecord =
90109
appStore.getState().contributionStatesRecord;
91110
const contributionStates = contributionStatesRecord[contribPoint];
92111
const contributionState = contributionStates[contribIndex];
93112
const componentModelOld = contributionState.componentModelResult.data;
94113
let componentModel = componentModelOld;
95-
computedOutputs.forEach((output) => {
96-
if (componentModel && (!output.kind || output.kind === "Component")) {
97-
componentModel = updateComponentState(componentModel, output);
114+
changes.forEach((change) => {
115+
if (componentModel && (!change.kind || change.kind === "Component")) {
116+
componentModel = updateComponentState(componentModel, change);
98117
} else {
99118
// TODO: process other output kinds which may not require componentModel.
100119
console.warn(
101120
"processing of this kind of output not supported yet:",
102-
output,
121+
change,
103122
);
104123
}
105124
});
@@ -126,16 +145,16 @@ function applyCallbackCallResults(callResults: CallbackCallResult[]) {
126145

127146
function updateComponentState(
128147
componentModel: ComponentModel,
129-
output: ComputedOutput,
148+
change: Change,
130149
): ComponentModel {
131-
if (componentModel.id === output.id) {
132-
return { ...componentModel, [output.property]: output.value };
150+
if (componentModel.id === change.id) {
151+
return { ...componentModel, [change.property]: change.value };
133152
} else if (isContainerModel(componentModel)) {
134153
const containerModelOld: ContainerModel = componentModel;
135154
let containerModelNew: ContainerModel = containerModelOld;
136155
for (let i = 0; i < containerModelOld.components.length; i++) {
137156
const itemOld = containerModelOld.components[i];
138-
const itemNew = updateComponentState(itemOld, output);
157+
const itemNew = updateComponentState(itemOld, change);
139158
if (itemNew !== itemOld) {
140159
if (containerModelNew === containerModelOld) {
141160
containerModelNew = {

dashi/src/api.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import { ComponentModel } from "./model/component";
22
import { Extension } from "./model/extension";
33
import { Contribution } from "./model/contribution";
4-
import { CallbackCallRequest, CallbackCallResult } from "./model/callback";
4+
import { CallbackCallRequest, ChangeRequest } from "./model/callback";
55
import { callApi } from "./utils/fetchApiResult";
66
import { ContribPoint } from "./store/appStore";
77

@@ -28,9 +28,9 @@ export async function fetchComponentModel(
2828
});
2929
}
3030

31-
export async function fetchCallbackCallResults(
31+
export async function fetchChangeRequests(
3232
callRequests: CallbackCallRequest[],
33-
): Promise<CallbackCallResult[]> {
33+
): Promise<ChangeRequest[]> {
3434
return callApi(`${serverUrl}/dashi/callback`, {
3535
body: JSON.stringify({ callRequests }),
3636
method: "post",

dashi/src/app/App.tsx

Lines changed: 27 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,42 @@
1+
import {
2+
CssBaseline,
3+
ThemeProvider,
4+
createTheme,
5+
Typography,
6+
} from "@mui/material";
7+
18
import ExtensionsInfo from "./ExtensionInfo";
29
import PanelsControl from "./PanelsControl";
310
import PanelsRow from "./PanelsRow";
411
import { initAppStore } from "../actions/initAppStore";
512

613
initAppStore();
714

15+
// MUI's default font family
16+
const fontFamily = "Roboto, Arial, sans-serif";
17+
18+
const theme = createTheme({
19+
typography: { fontFamily },
20+
components: {
21+
MuiCssBaseline: {
22+
styleOverrides: {
23+
"*": { fontFamily },
24+
},
25+
},
26+
},
27+
});
28+
829
function App() {
930
return (
10-
<>
11-
<div style={{ fontSize: 48, paddingBottom: 10 }}>Dashi Demo</div>
31+
<ThemeProvider theme={theme}>
32+
<CssBaseline />
33+
<Typography fontSize="3em" fontWeight="bold">
34+
Dashi Demo
35+
</Typography>
1236
<ExtensionsInfo />
1337
<PanelsControl />
1438
<PanelsRow />
15-
</>
39+
</ThemeProvider>
1640
);
1741
}
1842

dashi/src/app/ExtensionInfo.tsx

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import useAppStore from "../store/appStore";
2+
import { Typography } from "@mui/material";
23

34
function ExtensionsInfo() {
45
const appState = useAppStore();
@@ -9,10 +10,11 @@ function ExtensionsInfo() {
910
{extensionsResult.data.map((extension, extIndex) => {
1011
const id = `extensions.${extIndex}`;
1112
return (
12-
<span
13+
<Typography
1314
key={id}
14-
style={{ padding: 5 }}
15-
>{`${extension.name}/${extension.version}`}</span>
15+
style={{ padding: 4 }}
16+
fontSize="small"
17+
>{`${extension.name}/${extension.version}`}</Typography>
1618
);
1719
})}
1820
</div>

dashi/src/app/Panel.tsx

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,16 @@
1-
import {CSSProperties, ReactElement} from "react";
1+
import { CSSProperties, ReactElement } from "react";
22

33
import { Contribution } from "../model/contribution";
44
import { PropertyChangeHandler } from "../model/component";
55
import DashiComponent from "../components/DashiComponent";
66
import { ContributionState } from "../store/appStore";
7-
import {CircularProgress} from "@mui/material";
7+
import { CircularProgress } from "@mui/material";
88

99
const panelContainerStyle: CSSProperties = {
1010
display: "flex",
1111
flexDirection: "column",
1212
width: 400,
13-
height: 300,
13+
height: 400,
1414
padding: 5,
1515
border: "1px gray solid",
1616
};
@@ -41,7 +41,12 @@ function Panel({ panelModel, panelState, onPropertyChange }: PanelProps) {
4141
</span>
4242
);
4343
} else if (componentModelResult.status === "pending") {
44-
panelElement = <span><CircularProgress size={30} color="secondary" /> Loading {panelModel.name}...</span>;
44+
panelElement = (
45+
<span>
46+
<CircularProgress size={30} color="secondary" /> Loading{" "}
47+
{panelModel.name}...
48+
</span>
49+
);
4550
}
4651
return <div style={panelContainerStyle}>{panelElement}</div>;
4752
}

dashi/src/app/PanelsControl.tsx

Lines changed: 22 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
import useAppStore, { ContribPoint } from "../store/appStore";
22
import { hidePanel } from "../actions/hidePanel";
33
import { showPanel } from "../actions/showPanel";
4-
import {Checkbox} from "@mui/material";
4+
import { Checkbox, FormControlLabel, FormGroup } from "@mui/material";
55

66
const contribPoint: ContribPoint = "panels";
77

@@ -23,29 +23,32 @@ function PanelsControl() {
2323
throw Error("internal state error");
2424
}
2525
return (
26-
<div style={{ padding: 5 }}>
26+
<FormGroup>
2727
{panelStates.map((panelState, panelIndex) => {
2828
const id = `panels.${panelIndex}`;
2929
return (
30-
<div key={id}>
31-
<Checkbox
32-
color="secondary"
33-
id={id}
34-
checked={panelState.visible || false}
35-
value={panelIndex}
36-
onChange={(e) => {
37-
if (e.currentTarget.checked) {
38-
showPanel(panelIndex);
39-
} else {
40-
hidePanel(panelIndex);
41-
}
42-
}}
43-
/>
44-
<label htmlFor={id}>{panelModels[panelIndex].name}</label>
45-
</div>
30+
<FormControlLabel
31+
key={panelIndex}
32+
label={panelModels[panelIndex].name}
33+
control={
34+
<Checkbox
35+
color="secondary"
36+
id={id}
37+
checked={panelState.visible || false}
38+
value={panelIndex}
39+
onChange={(e) => {
40+
if (e.currentTarget.checked) {
41+
showPanel(panelIndex);
42+
} else {
43+
hidePanel(panelIndex);
44+
}
45+
}}
46+
/>
47+
}
48+
/>
4649
);
4750
})}
48-
</div>
51+
</FormGroup>
4952
);
5053
}
5154

dashi/src/components/DashiDropdown.tsx

Lines changed: 4 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
11
import "react";
22
import { DropdownModel, PropertyChangeHandler } from "../model/component";
3-
import React from "react";
43
import {
54
// Box,
65
FormControl,
@@ -24,7 +23,6 @@ function DashiDropdown({
2423
label,
2524
onPropertyChange,
2625
}: DashiDropdownProps) {
27-
const [dropdownValue, setDropdownValue] = React.useState(value);
2826
const handleChange = (event: SelectChangeEvent) => {
2927
if (!id) {
3028
return;
@@ -34,7 +32,6 @@ function DashiDropdown({
3432
newValue = Number.parseInt(newValue);
3533
}
3634

37-
setDropdownValue(newValue);
3835
return onPropertyChange({
3936
componentType: "Dropdown",
4037
componentId: id,
@@ -43,16 +40,15 @@ function DashiDropdown({
4340
});
4441
};
4542
return (
46-
<FormControl>
47-
{label && <InputLabel>{label}</InputLabel>}
43+
<FormControl variant="filled" size="small" style={style}>
44+
{label && <InputLabel id={`${id}-label`}>{label}</InputLabel>}
4845
<Select
46+
labelId={`${id}-label`}
4947
id={id}
5048
name={name}
51-
style={style}
52-
value={`${dropdownValue}`}
49+
value={`${value}`}
5350
disabled={disabled}
5451
onChange={handleChange}
55-
variant={"filled"}
5652
>
5753
{options.map(([text, value], index) => (
5854
<MenuItem key={index} value={value}>

0 commit comments

Comments
 (0)