diff --git a/package-lock.json b/package-lock.json index ba001446..64b070a1 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1526,18 +1526,18 @@ } }, "@types/react-router": { - "version": "5.0.3", - "resolved": "https://registry.npmjs.org/@types/react-router/-/react-router-5.0.3.tgz", - "integrity": "sha512-j2Gge5cvxca+5lK9wxovmGPgpVJMwjyu5lTA/Cd6fLGoPq7FXcUE1jFkEdxeyqGGz8VfHYSHCn5Lcn24BzaNKA==", + "version": "5.1.3", + "resolved": "https://registry.npmjs.org/@types/react-router/-/react-router-5.1.3.tgz", + "integrity": "sha512-0gGhmerBqN8CzlnDmSgGNun3tuZFXerUclWkqEhozdLaJtfcJRUTGkKaEKk+/MpHd1KDS1+o2zb/3PkBUiv2qQ==", "requires": { "@types/history": "*", "@types/react": "*" } }, "@types/react-router-dom": { - "version": "4.3.5", - "resolved": "https://registry.npmjs.org/@types/react-router-dom/-/react-router-dom-4.3.5.tgz", - "integrity": "sha512-eFajSUASYbPHg2BDM1G8Btx+YqGgvROPIg6sBhl3O4kbDdYXdFdfrgQFf/pcBuQVObjfT9AL/dd15jilR5DIEA==", + "version": "5.1.2", + "resolved": "https://registry.npmjs.org/@types/react-router-dom/-/react-router-dom-5.1.2.tgz", + "integrity": "sha512-kRx8hoBflE4Dp7uus+j/0uMHR5uGTAvQtc4A3vOTWKS+epe0leCuxEx7HNT7XGUd1lH53/moWM51MV2YUyhzAg==", "requires": { "@types/history": "*", "@types/react": "*", @@ -6838,9 +6838,9 @@ "integrity": "sha512-d4sze1JNC454Wdo2fkuyzCr6aHcbL6PGGuFAz0Li/NcOm1tCHGnWDRmJP85dh9IhQErTc2svWFEX5xHIOo//kQ==" }, "handlebars": { - "version": "4.4.0", - "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.4.0.tgz", - "integrity": "sha512-xkRtOt3/3DzTKMOt3xahj2M/EqNhY988T+imYSlMgs5fVhLN2fmKVVj0LtEGmb+3UUYV5Qmm1052Mm3dIQxOvw==", + "version": "4.5.2", + "resolved": "https://registry.npmjs.org/handlebars/-/handlebars-4.5.2.tgz", + "integrity": "sha512-29Zxv/cynYB7mkT1rVWQnV7mGX6v7H/miQ6dbEpYTKq5eJBN7PsRB+ViYJlcT6JINTSu4dVB9kOqEun78h6Exg==", "requires": { "neo-async": "^2.6.0", "optimist": "^0.6.1", @@ -12026,9 +12026,9 @@ "integrity": "sha512-GSmOT2EbHrINBf9SR7CDELwlJ8AENk3Qn7OikK4nFYAu3Ote2+JYNVvkpAEQm3/TLNEJFD/xZJjzyxg3KBWOzw==" }, "path-to-regexp": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-1.7.0.tgz", - "integrity": "sha1-Wf3g9DW62suhA6hOnTvGTpa5k30=", + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/path-to-regexp/-/path-to-regexp-1.8.0.tgz", + "integrity": "sha512-n43JRhlUKUAlibEJhPeir1ncUID16QnEjNpwzNdO3Lm4ywrBpBZ5oLD0I6br9evr1Y9JTqwRtAh7JLoOzAQdVA==", "requires": { "isarray": "0.0.1" } diff --git a/package.json b/package.json index 1d4637b8..ebe48c97 100644 --- a/package.json +++ b/package.json @@ -10,7 +10,7 @@ "@types/node": "12.6.2", "@types/prop-types": "^15.7.3", "@types/react-dom": "16.8.4", - "@types/react-router-dom": "^4.3.5", + "@types/react-router-dom": "^5.1.2", "apollo-cache-inmemory": "^1.6.3", "apollo-client": "^2.6.4", "apollo-link": "^1.2.13", diff --git a/public/beamline.json b/public/beamline.json new file mode 100644 index 00000000..31d1ada3 --- /dev/null +++ b/public/beamline.json @@ -0,0 +1,94 @@ +{ + "type": "display", + "position": "relative", + "overflow": "auto", + "border": "solid 3px red", + "children": [ + { + "type": "flexcontainer", + "position": "relative", + "overflow": "auto", + "border": "solid 3px green", + "children": [ + { + "type": "display", + "position": "relative", + "width": "100%", + "border": "solid 3px blue", + "backgroundColor": "#cccccc", + "overflow": "auto", + "children": [ + { + "type": "label", + "position": "relative", + "width": "90%", + "height": "20px", + "textAlign": "center", + "fontWeight": "bold", + "backgroundColor": "#eeeeee", + "text": "Synoptic" + }, + { + "type": "widgetFromJSON", + "position": "relative", + "file": "http://localhost:3000/synoptic.json" + } + ] + }, + { + "type": "display", + "position": "relative", + "width": "75%", + "border": "solid 3px pink", + "backgroundColor": "#cccccc", + "overflow": "auto", + "macroMap": { + "motor": "1" + }, + "children": [ + { + "type": "label", + "position": "relative", + "width": "100%", + "height": "20px", + "textAlign": "center", + "fontWeight": "bold", + "backgroundColor": "#eeeeee", + "text": "Embed" + }, + { + "type": "dynamicpage", + "position": "relative", + "routePath": "embed" + } + ] + }, + { + "type": "display", + "position": "relative", + "width": "25%", + "border": "solid 3px orange", + "backgroundColor": "#cccccc", + "overflow": "auto", + "children": [ + { + "type": "label", + "position": "relative", + "width": "100%", + "height": "20px", + "textAlign": "center", + "fontWeight": "bold", + "backgroundColor": "#eeeeee", + "text": "Detail" + }, + { + "type": "dynamicpage", + "position": "relative", + "routePath": "detail" + } + ] + } + ] + } + ] +} diff --git a/public/coniqlPage.json b/public/coniqlPage.json deleted file mode 100644 index d772758a..00000000 --- a/public/coniqlPage.json +++ /dev/null @@ -1,64 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "relative", - "width": "90%", - "margin": "auto" - }, - "children": [ - { - "type": "label", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "widgetStyling": { - "fontWeight": "bold", - "backgroundColor": "transparent" - }, - "text": "This page works only if the Coniql plugin is configured." - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "pvName": "sim://sine" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "pvName": "sim://sine(-10, 10, 5, 1, 50, 80)" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "pvName": "pva://TMC43-TS-IOC-01:CURRENT", - "showUnits": true - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "pvName": "pva://TMC43-TS-IOC-01:AI", - "showUnits": true - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "pvName": "sim://sinewave" - } - ] -} diff --git a/public/digitelMpc.opi b/public/digitelMpc.opi new file mode 100644 index 00000000..e27d177a --- /dev/null +++ b/public/digitelMpc.opi @@ -0,0 +1,588 @@ + + + + + false + -1 + -1 + + true + + + + 5.1.0 + + + + 8 + 246 + + true + + Digitel MPC - $(device) + + + true + true + true + true + true + Display + 240 + 64ead72b:16b223eef45:-6c18 + 521 + 135 + + + false + + + + + + + 0 + 1 + true + + + + + + + 32 + 1 + EDM Label + + + true + true + false + + + $(device) + + false + 1 + true + Label + 240 + false + 64ead72b:16b223eef45:-6c17 + 0 + 0 + + + + + + + true + + + + false + false + + + + false + + + + 0 + 1 + true + + + + false + + + + 25 + + EDM Exit Button + 0 + + + + + true + true + false + + + + Exit + false + $(pv_name) +$(pv_value) + true + Action Button + 109 + 64ead72b:16b223eef45:-6c16 + 124 + 214 + + + + false + 255 + true + false + + + + + + + false + + + + 0 + 1 + true + + + + 0.0 + + Default + + false + + + + false + 159 + true + + + + 0 + 1 + EDM Rectangle + + + + + true + true + false + + + $(pv_name) +$(pv_value) + false + true + Rectangle + 225 + 64ead72b:16b223eef45:-6c15 + 8 + 48 + + + + false + + + + + + + 0 + 1 + true + + + + + + + 16 + 0 + EDM Label + + + true + true + false + + + Model + + true + 1 + true + Label + 40 + false + 64ead72b:16b223eef45:-6c13 + 16 + 64 + + + + false + false + false + + + + false + + + + 1 + 0 + true + + + + true + + + + 0 + 23 + 2 + EDM Text Update + 0 + true + $(device):VERSION + + 0.0 + + + true + true + false + + + true + ###### + $(pv_name) +$(pv_value) + false + 1 + true + Text Update + 209 + false + 64ead72b:16b223eef45:-6c12 + 16 + 92 + + + + false + false + false + + + + false + + + + 1 + 0 + true + + + + true + + + + 0 + 23 + 2 + EDM Text Update + 0 + true + $(device):MODEL + + 0.0 + + + true + true + false + + + true + ###### + $(pv_name) +$(pv_value) + false + 1 + true + Text Update + 153 + false + 64ead72b:16b223eef45:-6c0e + 72 + 64 + + + + false + + + + + + + 0 + 1 + true + + + + + + + 16 + 0 + EDM Label + + + true + true + false + + + Auto Re-start + + true + 1 + true + Label + 86 + false + 64ead72b:16b223eef45:-6c0d + 16 + 152 + + + + false + false + false + + + + false + + + + 1 + 0 + true + + + + true + + + + 0 + 23 + 2 + EDM Text Update + 0 + true + $(device):AUTOST + + 0.0 + + + true + true + false + + + true + ###### + $(pv_name) +$(pv_value) + false + 1 + true + Text Update + 113 + false + 64ead72b:16b223eef45:-6c0c + 112 + 148 + + + + false + + + + + + + 0 + 1 + true + + + + + + + 16 + 1 + EDM Label + + + true + true + false + + + Details + + false + 1 + true + Label + 48 + false + 64ead72b:16b223eef45:-6c0a + 8 + 40 + + + + false + 255 + true + false + + + + + + + false + + + + 0 + 1 + true + + + + 0.0 + + Default + + false + + + + false + 17 + true + + + + 0 + 1 + EDM Rectangle + + + + + true + true + false + + + $(pv_name) +$(pv_value) + true + true + Rectangle + 49 + 64ead72b:16b223eef45:-6c09 + 8 + 40 + + + + + $(pv_name) + Reset + 10 + + + + + false + false + + + + false + + + + 0 + 1 + true + + + + false + + + + 25 + + EDM Message Button + 0 + $(device):RESET + + + + + + + + + + + + + + $(device):RESET + + + + true + true + false + + + + Reset + false + $(pv_name) +$(pv_value) + true + Action Button + 109 + 64ead72b:16b223eef45:-6c08 + 8 + 214 + + \ No newline at end of file diff --git a/public/digitelMpcIonp.opi b/public/digitelMpcIonp.opi new file mode 100644 index 00000000..856f13f8 --- /dev/null +++ b/public/digitelMpcIonp.opi @@ -0,0 +1,712 @@ + + + 86 + 217 + 232 + 310 + + + + 4.0.0 + + + + + + + Digitel MPC Ion Pump Controller - $(device) + true + 8 + true + + false + + + + false + + + + 0 + + + + + + + 32 + 1 + EDM Label + $(device) + false + 232 + 0 + 0 + + + + + + false + 159 + + + + 0 + 1 + EDM Rectangle + false + true + 217 + 8 + 48 + + + true + + + + false + + + + 0 + + + + + + + 16 + 0 + EDM Label + Pressure + true + 60 + 16 + 68 + + + true + + + + false + + + + 0 + + + + + + + 16 + 0 + EDM Label + Status + true + 42 + 16 + 96 + + + true + + + + false + + + + 0 + + + + + + + 16 + 0 + EDM Label + Voltage + true + 50 + 16 + 124 + + + true + + + + false + + + + 0 + + + + + + + 16 + 0 + EDM Label + Current + true + 48 + 16 + 152 + + + true + + + + false + + + + 0 + + + + + + + 16 + 0 + EDM Label + Pump Size + true + 69 + 16 + 180 + + + false + + + + false + + + + 0 + + + + + + + 16 + 1 + EDM Label + Details + false + 48 + 8 + 40 + + + + + + false + 17 + + + + 0 + 1 + EDM Rectangle + true + true + 49 + 8 + 40 + + + + + + true + + + + 0 + 2 + + + + true + + + + 2 + 24 + 1 + 2 + EDM Text Update + 1 + false + $(device):P + false + false + 122 + 95 + 63 + + + + + + true + + + + 0 + 2 + + + + true + + + + 0 + 24 + 1 + 2 + EDM Text Update + 0 + true + $(device):V + true + false + 122 + 95 + 119 + + + + + + true + + + + 0 + 2 + + + + true + + + + 7 + 24 + 1 + 2 + EDM Text Update + 1 + false + $(device):I + false + false + 122 + 95 + 147 + + + + + + true + + + + 0 + 2 + + + + true + + + + 0 + 24 + 1 + 2 + EDM Text Update + 0 + true + $(device):SIZE + true + false + 122 + 95 + 175 + + + + + + false + + + + 1 + 0 + + + + true + + + + 0 + 23 + 2 + 1 + EDM Text Update + 0 + true + $(device):STA + true + true + 121 + 96 + 92 + + + false + + + + false + + + + 0 + + + + + + + 16 + 1 + EDM Label + Details + false + 48 + 8 + 40 + + + + + + false + 17 + + + + 0 + 1 + EDM Rectangle + true + true + 49 + 8 + 40 + + + + + true + importPackage(Packages.org.csstudio.opibuilder.scriptUtil);ScriptUtil.closeAssociatedOPI(widget); + + + + + + false + + + + + + + 25 + EDM Exit Button + Exit + 65 + 160 + 278 + + + + + ./digitelMpcIonpControl.opi + + true + $(device) + + 8 + Control + + + + + + false + + + + + + + 25 + EDM related display + Control + 65 + 160 + 214 + + + + + + + true + + + + + + + false + + + + + + + 25 + EDM shell command + Graph + 65 + 160 + 246 + + + false + 0 + 57 + true + 0 + false + true + + + + + false + 49 + + + + 0 + 1 + EDM Rectangle + false + true + 137 + 0 + 8 + + + + + $(pv_name) + Stop + + + false + + + + + + + 25 + EDM Message Button + $(device):START + + + + + + + + + + + + + $(device):START + + + Stop + 57 + 72 + 24 + + + + + + false + + + + 1 + 0 + + + + true + + + + 0 + 25 + 1 + 1 + EDM Text Update + 0 + true + $(device):STARTING + true + true + 57 + 8 + 24 + + + + + $(device):START + Start + + + false + + + + + + + 25 + EDM Message Button + + + + Start + + + + Start + 1 + 0 + + + + true + + + false + + $(device):STARTING + + + + + + + + + + + + + $(device):START + + + true + 0 + false + true + false + 57 + 8 + 24 + + + false + + + + false + + + + 0 + + + + + + + 16 + 1 + EDM Label + Control + false + 48 + 0 + 0 + + + + + + false + 17 + + + + 0 + 1 + EDM Rectangle + true + true + 49 + 0 + 0 + + 137 + 8 + 214 + + diff --git a/public/digitelmpc.json b/public/digitelmpc.json new file mode 100644 index 00000000..0a37e212 --- /dev/null +++ b/public/digitelmpc.json @@ -0,0 +1,17 @@ +{ + "type": "flexcontainer", + "position": "relative", + "children": [ + { + "type": "widgetFromBob", + "position": "relative", + "margin": "10px", + "file": "http://localhost:3000/digitelMpc.opi", + "macroMap": { + "device": "pva://TEST", + "pv_name": "${pvName}", + "pv_value": "${pvValue}" + } + } + ] +} diff --git a/public/digitelmpcionp.json b/public/digitelmpcionp.json new file mode 100644 index 00000000..6462ef5c --- /dev/null +++ b/public/digitelmpcionp.json @@ -0,0 +1,17 @@ +{ + "type": "flexcontainer", + "position": "relative", + "children": [ + { + "type": "widgetFromBob", + "position": "relative", + "margin": "10px", + "file": "http://localhost:3000/digitelMpcIonp.opi", + "macroMap": { + "device": "pva://TEST", + "pv_name": "${pvName}", + "pv_value": "${pvValue}" + } + } + ] +} diff --git a/public/embeddedScreens/flexiEmbedded.json b/public/embeddedScreens/flexiEmbedded.json deleted file mode 100644 index c1f3a426..00000000 --- a/public/embeddedScreens/flexiEmbedded.json +++ /dev/null @@ -1,101 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "100%", - "height": "100%" - }, - "macroMap": { - "EMBEDSUFFIX": "embed0" - }, - "children": [ - { - "type": "flexcontainer", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "100%", - "height": "100%" - }, - "children": [ - { - "type": "label", - "containerStyling": { - "position": "relative", - "height": "200px", - "width": "110px", - "margin": "5px" - }, - "text": "Parent: ${EMBEDSUFFIX}" - }, - { - "type": "widgetFromJSON", - "file": "http://localhost:3000/embeddedScreens/simpleEmbed.json", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "macroMap": { - "EMBEDSUFFIX": "embed1" - } - }, - { - "type": "widgetFromJSON", - "file": "http://localhost:3000/embeddedScreens/simpleEmbed.json", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "macroMap": { - "EMBEDSUFFIX": "embed2" - } - }, - { - "type": "widgetFromJSON", - "file": "http://localhost:3000/embeddedScreens/simpleEmbed.json", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "macroMap": { - "EMBEDSUFFIX": "embed3" - } - }, - { - "type": "widgetFromJSON", - "file": "http://localhost:3000/embeddedScreens/simpleEmbed.json", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "macroMap": { - "EMBEDSUFFIX": "embed4" - } - }, - { - "type": "widgetFromJSON", - "file": "http://localhost:3000/embeddedScreens/simpleEmbed.json", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "macroMap": { - "EMBEDSUFFIX": "embed5" - } - }, - { - "type": "widgetFromBob", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "widgetStyling": { "backgroundColor": "#999999" }, - "file": "http://localhost:3000/basic.bob" - } - ] - } - ] -} diff --git a/public/embeddedScreens/simpleEmbed.json b/public/embeddedScreens/simpleEmbed.json deleted file mode 100644 index 35d82f0f..00000000 --- a/public/embeddedScreens/simpleEmbed.json +++ /dev/null @@ -1,37 +0,0 @@ -{ - "type": "flexcontainer", - "containerStyling": { - "position": "relative", - "height": "150px", - "width": "110px", - "margin": "5px" - }, - "flexFlow": "column", - "children": [ - { - "type": "label", - "containerStyling": { - "position": "relative", - "height": "100%" - }, - "text": "Screen: ${EMBEDSUFFIX}" - }, - { - "type": "input", - "containerStyling": { - "position": "relative", - "height": "100%" - }, - "pvName": "sim://limit#pv${EMBEDSUFFIX}" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "height": "100%" - }, - "pvName": "sim://limit#pv${EMBEDSUFFIX}", - "precision": 3 - } - ] -} diff --git a/public/examplePage.json b/public/examplePage.json deleted file mode 100644 index 93166487..00000000 --- a/public/examplePage.json +++ /dev/null @@ -1,291 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "relative", - "width": "80%", - "margin": "auto", - "height": "", - "padding": "" - }, - "macroMap": { - "pv1": "sim://limit#1", - "pv2": "sim://limit#2", - "pv3": "sim://limit#3", - "pv4": "sim://limit#4" - }, - "children": [ - { - "type": "flexcontainer", - "containerStyling": { - "position": "relative", - "width": "", - "margin": "", - "height": "", - "padding": "" - }, - "children": [ - { - "type": "label", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "text": "${pv1}", - "actions": { - "executeAsOne": false, - "actions": [ - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 10, - "description": "set limit #1 to 10" - }, - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 20, - "description": "set limit #1 to 20" - }, - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 100, - "description": "set limit #1 to 100" - } - ] - } - }, - { - "type": "input", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv1}" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv1}" - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "text": "${pv2}" - }, - { - "type": "input", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv2}" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv2}" - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "text": "${pv3}" - }, - { - "type": "input", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv3}" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv3}" - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "text": "${pv4}" - }, - { - "type": "input", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv4}" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "30%", - "margin": "", - "height": "", - "padding": "" - }, - "pvName": "${pv4}" - } - ] - }, - { - "type": "actionbutton", - "pvName": "sim://limit#1", - "text": "more ...", - "image": "DCM-base.png", - "containerStyling": { - "position": "relative", - "width": "20%", - "margin": "", - "height": "", - "padding": "" - }, - "macroMap": { - "prefix": "sim://" - }, - "actions": { - "executeAsOne": false, - "actions": [ - { - "type": "WRITE_PV", - "pvName": "${prefix}limit#1", - "value": 10, - "description": "set limit #1 to 10" - }, - { - "type": "WRITE_PV", - "pvName": "${prefix}limit#1", - "value": 20, - "description": "set limit #1 to 20" - }, - { - "type": "WRITE_PV", - "pvName": "${prefix}limit#1", - "value": 100, - "description": "set limit #1 to 100" - } - ] - }, - "alarmBorder": true - }, - { - "type": "actionbutton", - "containerStyling": { - "position": "relative", - "width": "80%", - "margin": "auto", - "height": "", - "padding": "" - }, - "pvName": "${pv2}", - "text": "set ${pv2} to 10", - "actions": { - "actions": [ - { - "type": "WRITE_PV", - "pvName": "sim://limit#2", - "value": 10 - } - ] - }, - "executeAsOne": false - }, - { - "type": "actionbutton", - "containerStyling": { - "position": "relative", - "width": "80%", - "margin": "auto", - "height": "", - "padding": "" - }, - "pvName": "${pv3}", - "text": "set ${pv3} to 10", - "actions": { - "actions": [ - { - "type": "WRITE_PV", - "pvName": "sim://limit#3", - "value": 10 - } - ] - }, - "executeAsOne": false - }, - { - "type": "actionbutton", - "containerStyling": { - "position": "relative", - "width": "80%", - "margin": "auto", - "height": "", - "padding": "" - }, - "pvName": "${pv4}", - "text": "set ${pv4} to 10", - "actions": { - "actions": [ - { - "type": "WRITE_PV", - "pvName": "sim://limit#4", - "value": 10 - } - ] - }, - "executeAsOne": false - } - ] -} diff --git a/public/flexiblePage.json b/public/flexiblePage.json deleted file mode 100644 index 97a6f631..00000000 --- a/public/flexiblePage.json +++ /dev/null @@ -1,102 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "100%", - "height": "10)0%" - }, - "children": [ - { - "type": "flexcontainer", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "100%", - "height": "100%" - }, - "children": [ - { - "type": "input", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1" - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - }, - { - "type": "readback", - "containerStyling": { - "position": "relative", - "width": "200px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "500px", - "y": "500px", - "width": "400px", - "height": "100px", - "margin": "5px" - }, - "pvName": "sim://limit#metapv1", - "precision": 3 - } - ] - } - ] -} diff --git a/public/frontPage.json b/public/frontPage.json index 4506a999..571e18a5 100644 --- a/public/frontPage.json +++ b/public/frontPage.json @@ -1,7 +1,8 @@ { "type": "display", "position": "relative", - "width": "80%", + "width": "90%", + "maxWidth": "600px", "margin": "auto", "children": [ { @@ -211,10 +212,31 @@ { "type": "readback", "position": "relative", - "margin": "5px 0 0 0", + "margin": "5px 0 30px 0", "pvName": "loc://test(1.1)" } ] + }, + { + "type": "grouping", + "position": "relative", + "margin": "20px 0 0 0", + "name": "Slide Control", + "children": [ + { + "type": "label", + "position": "relative", + "text": "In a grouping container...", + "textAlign": "left", + "backgroundColor": "transparent" + }, + { + "type": "slidecontrol", + "position": "relative", + "pvName": "sim://limit#progressPV", + "alarmBorder": true + } + ] } ] } diff --git a/public/graphics.json b/public/graphics.json deleted file mode 100644 index 85572316..00000000 --- a/public/graphics.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "1000px", - "height": "168px" - }, - "children": [ - { - "type": "actionbutton", - "pvName": "sim://limit#1", - "text": "more ...", - "image": "DCM-base.png", - "containerStyling": { - "position": "absolute", - "x": "100px", - "y": "50px", - "width": "", - "height": "" - }, - "actions": { - "executeAsOne": false, - "actions": [ - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 10, - "description": "set limit #1 to 10" - }, - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 20, - "description": "set limit #1 to 20" - }, - { - "type": "WRITE_PV", - "pvName": "sim://limit#1", - "value": 100, - "description": "set limit #1 to 100" - } - ] - }, - "alarmBorder": true - } - ] -} diff --git a/public/ionp.svg b/public/ionp.svg new file mode 100644 index 00000000..5c1a9c51 --- /dev/null +++ b/public/ionp.svg @@ -0,0 +1,107 @@ + + + + + + + + image/svg+xml + + + + + + + + + + + + + + + + + + + + diff --git a/public/ionpExample.json b/public/ionpExample.json deleted file mode 100644 index e314ef96..00000000 --- a/public/ionpExample.json +++ /dev/null @@ -1,187 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "absolute", - "x": "136px", - "y": "100px", - "width": "328px", - "height": "468px" - }, - "widgetStyling": { - "backgroundColor": "#999999" - }, - "children": [ - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": 0, - "y": 0, - "width": "328px", - "height": "32px" - }, - "widgetStyling": { - "fontWeight": "bold", - "fontSize": "1.8em", - "backgroundColor": "#bdf57d" - }, - "text": "${device}" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "68px", - "width": "60px", - "height": "16px" - }, - "widgetStyling": { - "fontSize": "0.8em" - }, - "text": "Pressure" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "64px", - "width": "72px", - "height": "22px" - }, - "pvName": "loc://ionp:pressure" - }, - { - "type": "progressbar", - "containerStyling": { - "position": "absolute", - "x": "172px", - "y": "64px", - "width": "140px", - "height": "22px" - }, - "widgetStyling": { "fontSize": "1em" }, - "min": -12, - "max": 3, - "pvName": "loc://${device}:pressure" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "96px", - "width": "42px", - "height": "16px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "text": "Status" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "92px", - "width": "216px", - "height": "22px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "pvName": "loc://${device}:status" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "124px", - "width": "72px", - "height": "16px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "text": "Error Code" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "120px", - "width": "216px", - "height": "22px" - }, - "pvName": "loc://${device}:error" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "152px", - "width": "50px", - "height": "16px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "text": "Voltage" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "148px", - "width": "72px", - "height": "22px" - }, - "pvName": "loc://${device}:error" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "179px", - "width": "50px", - "height": "16px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "text": "Current" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "176px", - "width": "72px", - "height": "22px" - }, - "pvName": "loc://${device}:current" - }, - { - "type": "label", - "containerStyling": { - "position": "absolute", - "x": "16px", - "y": "208px", - "width": "62px", - "height": "16px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "text": "Strapping" - }, - { - "type": "readback", - "containerStyling": { - "position": "absolute", - "x": "96px", - "y": "204px", - "width": "72px", - "height": "22px" - }, - "widgetStyling": { "fontSize": "0.8em" }, - "pvName": "loc://${device}:strapping" - } - ] -} diff --git a/public/menu.json b/public/menu.json new file mode 100644 index 00000000..ccd986b7 --- /dev/null +++ b/public/menu.json @@ -0,0 +1,71 @@ +{ + "type": "flexcontainer", + "position": "relative", + "height": "100%", + "width": "100%", + "children": [ + { + "type": "actionbutton", + "text": "Beamline Synoptic", + "position": "relative", + "width": "300px", + "height": "200px", + "margin": "10px", + "backgroundColor": "#4da6ff", + "fontSize": "3rem", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "app", + "page": "beamline", + "macros": "{}" + } + ] + } + }, + { + "type": "actionbutton", + "text": "Mobile Layout", + "position": "relative", + "width": "300px", + "height": "200px", + "margin": "10px", + "backgroundColor": "#ffa64d", + "fontSize": "3rem", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "app", + "page": "frontPage", + "macros": "{}" + } + ] + } + }, + { + "type": "actionbutton", + "text": "Performance Testing", + "position": "relative", + "width": "300px", + "height": "200px", + "margin": "10px", + "backgroundColor": "#4dffa6", + "fontSize": "3rem", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "app", + "page": "performance", + "macros": "{}" + } + ] + } + } + ] +} diff --git a/public/motor.json b/public/motor.json new file mode 100644 index 00000000..c9227fd3 --- /dev/null +++ b/public/motor.json @@ -0,0 +1,172 @@ +{ + "type": "grouping", + "position": "relative", + "height": "300px", + "width": "350px", + "margin": "10px", + "fontSize": "1.5em", + "backgroundColor": "#dddddd", + "name": "Motor Screen ${motor}", + "children": [ + { + "type": "flexcontainer", + "position": "relative", + "children": [ + { + "type": "label", + "position": "relative", + "width": "50%", + "text": "Position", + "backgroundColor": "transparent" + }, + { + "type": "progressbar", + "position": "relative", + "width": "50%", + "pvName": "sim://sine#m${motor}", + "precision": 2, + "min": -1, + "max": 1, + "border": "1px solid #aaaaaa", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "50%", + "text": "Motor Speed", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "input", + "position": "relative", + "width": "25%", + "pvName": "sim://limit#m${motor}", + "border": "1px solid #aaaaaa", + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "readback", + "position": "relative", + "width": "25%", + "pvName": "sim://limit#m${motor}", + "alarmBorder": true, + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "50%", + "text": "Motor Mode", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "menubutton", + "position": "relative", + "width": "25%", + "pvName": "loc://enum#m${motor}(2, \"slow\", \"med\", \"fast\")", + "border": "1px solid #aaaaaa", + "margin": "5px 0px 0px 0px", + "fontSize": "0.75em" + }, + { + "type": "readback", + "position": "relative", + "width": "25%", + "pvName": "loc://enum#m${motor}", + "color": "#22ee22", + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "actionbutton", + "position": "relative", + "width": "100%", + "margin": "5px 0px 0px 0px", + "text": "SLOW", + "actions": { + "executeAsOne": true, + "actions": [ + { + "type": "WRITE_PV", + "pvName": "sim://limit#m${motor}", + "value": 15 + }, + { + "type": "WRITE_PV", + "pvName": "loc://enum#m${motor}", + "value": "slow" + } + ] + } + }, + { + "type": "actionbutton", + "position": "relative", + "width": "100%", + "margin": "5px 0px 0px 0px", + "text": "MEDIUM", + "actions": { + "executeAsOne": true, + "actions": [ + { + "type": "WRITE_PV", + "pvName": "sim://limit#m${motor}", + "value": 50 + }, + { + "type": "WRITE_PV", + "pvName": "loc://enum#m${motor}", + "value": "med" + } + ] + } + }, + { + "type": "actionbutton", + "position": "relative", + "width": "100%", + "margin": "5px 0px 0px 0px", + "text": "FAST", + "actions": { + "executeAsOne": true, + "actions": [ + { + "type": "WRITE_PV", + "pvName": "sim://limit#m${motor}", + "value": 99 + }, + { + "type": "WRITE_PV", + "pvName": "loc://enum#m${motor}", + "value": "fast" + } + ] + } + }, + { + "type": "actionbutton", + "position": "relative", + "width": "100%", + "margin": "5px 0px 0px 0px", + "text": "More...", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "detail", + "page": "motorDetail", + "macros": "{\"motor\":\"${motor}\"}" + } + ] + } + } + ] + } + ] +} diff --git a/public/motorDetail.json b/public/motorDetail.json new file mode 100644 index 00000000..8e7056f6 --- /dev/null +++ b/public/motorDetail.json @@ -0,0 +1,139 @@ +{ + "type": "flexcontainer", + "position": "relative", + "margin": "auto", + "children": [ + { + "type": "label", + "position": "relative", + "width": "100%", + "text": "Motor ${motor} Detail Panel", + "fontSize": "2em", + "fontWeight": "bold", + "margin": "0px 0px 10px 0px", + "backgroundColor": "transparent" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Position", + "textAlign": "left", + "backgroundColor": "transparent" + }, + { + "type": "progressbar", + "position": "relative", + "width": "50%", + "pvName": "sim://sine#m${motor}", + "precision": 2, + "min": -1, + "max": 1, + "border": "1px solid #aaaaaa", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Motor Speed", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "input", + "position": "relative", + "width": "25%", + "pvName": "sim://limit#m${motor}", + "border": "1px solid #aaaaaa", + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "readback", + "position": "relative", + "width": "25%", + "pvName": "sim://limit#m${motor}", + "alarmBorder": true, + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Motor Mode", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "menubutton", + "position": "relative", + "width": "25%", + "pvName": "loc://enum#m${motor}(2, \"slow\", \"med\", \"fast\")", + "border": "1px solid #aaaaaa", + "margin": "5px 0px 0px 0px", + "fontSize": "0.75em" + }, + { + "type": "readback", + "position": "relative", + "width": "25%", + "pvName": "loc://enum#m${motor}", + "color": "#22ee22", + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Motor Name", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "readback", + "position": "relative", + "width": "55%", + "pvName": "loc://name#m${motor}", + "alarmBorder": true, + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Current Status", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "readback", + "position": "relative", + "width": "55%", + "pvName": "loc://status#m${motor}", + "alarmBorder": true, + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + }, + { + "type": "label", + "position": "relative", + "width": "30%", + "text": "Another Detail", + "margin": "5px 0px 0px 0px", + "backgroundColor": "transparent" + }, + { + "type": "readback", + "position": "relative", + "width": "55%", + "pvName": "loc://detail#m${motor}", + "alarmBorder": true, + "margin": "5px 0px 0px 0px", + "fontSize": "1em" + } + ] +} diff --git a/public/motorSummary.json b/public/motorSummary.json new file mode 100644 index 00000000..30a61039 --- /dev/null +++ b/public/motorSummary.json @@ -0,0 +1,33 @@ +{ + "type": "flexcontainer", + "position": "relative", + "children": [ + { + "type": "widgetFromJSON", + "position": "relative", + "margin": "10px", + "file": "http://localhost:3000/motor.json", + "macroMap": { + "motor": "1" + } + }, + { + "type": "widgetFromJSON", + "position": "relative", + "margin": "10px", + "file": "http://localhost:3000/motor.json", + "macroMap": { + "motor": "2" + } + }, + { + "type": "widgetFromJSON", + "position": "relative", + "margin": "10px", + "file": "http://localhost:3000/motor.json", + "macroMap": { + "motor": "3" + } + } + ] +} diff --git a/public/performance.json b/public/performance.json new file mode 100644 index 00000000..9f349df6 --- /dev/null +++ b/public/performance.json @@ -0,0 +1,1214 @@ +{ + "type": "display", + "containerStyling": { + "position": "relative", + "margin": "auto", + "width": "500px", + "height": "500px" + }, + "widgetStyling": { + "backgroundColor": "#999999" + }, + "children": [ + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "2px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#000", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "2px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#001", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "2px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#002", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "2px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#003", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "2px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#004", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "24px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#005", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "24px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#006", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "24px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#007", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "24px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#008", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "24px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#009", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "46px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#010", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "46px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#011", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "46px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#012", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "46px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#013", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "46px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#014", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "68px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#015", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "68px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#016", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "68px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#017", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "68px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#018", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "68px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#019", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "90px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#020", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "90px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#021", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "90px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#022", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "90px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#023", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "90px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#024", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "112px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#025", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "112px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#026", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "112px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#027", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "112px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#028", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "112px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#029", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "134px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#030", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "134px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#031", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "134px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#032", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "134px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#033", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "134px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#034", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "156px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#035", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "156px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#036", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "156px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#037", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "156px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#038", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "156px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#039", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "178px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#040", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "178px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#041", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "178px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#042", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "178px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#043", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "178px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#044", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "200px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#045", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "200px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#046", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "200px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#047", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "200px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#048", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "200px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#049", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "222px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#050", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "222px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#051", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "222px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#052", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "222px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#053", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "222px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#054", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "244px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#055", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "244px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#056", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "244px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#057", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "244px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#058", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "244px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#059", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "266px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#060", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "266px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#061", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "266px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#062", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "266px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#063", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "266px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#064", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "288px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#065", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "288px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#066", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "288px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#067", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "288px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#068", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "288px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#069", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "310px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#070", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "310px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#071", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "310px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#072", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "310px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#073", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "310px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#074", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "332px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#075", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "332px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#076", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "332px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#077", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "332px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#078", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "332px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#079", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "354px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#080", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "354px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#081", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "354px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#082", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "354px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#083", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "354px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#084", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "376px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#085", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "376px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#086", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "376px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#087", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "376px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#088", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "376px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#089", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "398px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#090", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "398px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#091", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "398px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#092", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "398px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#093", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "398px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#094", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "2px", + "y": "420px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#095", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "84px", + "y": "420px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#096", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "166px", + "y": "420px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#097", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "248px", + "y": "420px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#098", + "precision": 0 + }, + { + "type": "readback", + "containerStyling": { + "position": "absolute", + "x": "330px", + "y": "420px", + "width": "80px", + "height": "20px" + }, + "pvName": "sim://ramp#099", + "precision": 0 + } + ] +} diff --git a/public/progressPage.json b/public/progressPage.json deleted file mode 100644 index c6b95616..00000000 --- a/public/progressPage.json +++ /dev/null @@ -1,87 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "relative", - "width": "80%", - "margin": "auto" - }, - "macroMap": { - "PROG": "sim://limit#progresspv" - }, - "children": [ - { - "type": "label", - "containerStyling": { - "position": "relative", - "margin": "20px 5px 5px 5px" - }, - "text": "Input: ${PROG}" - }, - { - "type": "input", - "pvName": "${PROG}", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "alarmBorder": true, - "precision": 3 - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "margin": "20px 5px 5px 5px" - }, - "text": "Readback: ${PROG}" - }, - { - "type": "readback", - "pvName": "${PROG}", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "alarmBorder": true, - "precision": 3 - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "margin": "20px 5px 5px 5px" - }, - "text": "Progress Bar: ${PROG}" - }, - { - "type": "progressbar", - "pvName": "${PROG}", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "alarmBorder": true, - "min": 0, - "max": 100 - }, - { - "type": "label", - "containerStyling": { - "position": "relative", - "margin": "20px 5px 5px 5px" - }, - "text": "Slide Control: ${PROG}" - }, - { - "type": "slidecontrol", - "pvName": "${PROG}", - "containerStyling": { - "position": "relative", - "margin": "5px" - }, - "alarmBorder": true, - "min": -25, - "max": 125 - } - ] -} diff --git a/public/shapesPage.json b/public/shapesPage.json deleted file mode 100644 index b53c1bab..00000000 --- a/public/shapesPage.json +++ /dev/null @@ -1,26 +0,0 @@ -{ - "type": "display", - "containerStyling": { - "position": "absolute", - "x": "0px", - "y": "0px", - "width": "1000px", - "height": "168px" - }, - "children": [ - { - "type": "shape", - "containerStyling": { - "position": "absolute", - "x": "70px", - "y": "0px", - "width": "100px", - "height": "100px" - }, - "shapeWidth": "100px", - "shapeHeight": "70px", - "shapeRadius": "50%", - "shapeColour": "red" - } - ] -} diff --git a/public/simple.json b/public/simple.json deleted file mode 100644 index beb2c52f..00000000 --- a/public/simple.json +++ /dev/null @@ -1,49 +0,0 @@ -{ - "type": "display", - "position": "relative", - "macroMap": { - "metapv": "metapv1" - }, - "children": [ - { - "type": "flexcontainer", - "position": "relative", - "width": "100%", - "height": "100%", - "children": [ - { - "type": "actionbutton", - "pvName": "sim://limit#1", - "image": "basicBob.png", - "position": "relative", - "margin": "20px" - }, - { - "type": "widgetFromBob", - "position": "relative", - "margin": "20px", - "backgroundColor": "#ffffff", - "file": "http://localhost:3000/basic.bob" - }, - { - "type": "actionbutton", - "pvName": "sim://limit#1", - "image": "basicOpi.png", - "position": "relative", - "margin": "20px" - }, - { - "type": "widgetFromBob", - "position": "relative", - "margin": "20px", - "backgroundColor": "#ffffff", - "file": "http://localhost:3000/basic.opi", - "macroMap": { - "pv_name": "${pvName}", - "pv_value": "${pvValue}" - } - } - ] - } - ] -} diff --git a/public/synoptic.json b/public/synoptic.json new file mode 100644 index 00000000..d2a5f514 --- /dev/null +++ b/public/synoptic.json @@ -0,0 +1,171 @@ +{ + "type": "display", + "position": "relative", + "width": "600px", + "height": "200px", + "margin": "10px", + "border": "dashed 3px red", + "children": [ + { + "type": "actionbutton", + "pvName": "sim://limit#1", + "text": "Motor 1", + "image": "http://localhost:3000/DCM-base.png", + "position": "absolute", + "x": "0px", + "y": "0px", + "width": "100px", + "height": "100px", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "motor", + "description": "Motor 1 Info", + "macros": "{\"motor\":\"1\"}" + } + ] + } + }, + { + "type": "actionbutton", + "pvName": "sim://limit#1", + "text": "Motor 2", + "image": "http://localhost:3000/DCM-base.png", + "position": "absolute", + "x": "150px", + "y": "0px", + "width": "100px", + "height": "100px", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "motor", + "description": "Motor 2 Info", + "macros": "{\"motor\":\"2\"}" + } + ] + } + }, + { + "type": "shape", + "position": "absolute", + "x": "250px", + "y": "50px", + "width": "100px", + "height": "100px", + "shapeWidth": "100px", + "shapeHeight": "5px", + "shapeRadius": "0", + "backgroundColor": "red" + }, + { + "type": "shape", + "position": "absolute", + "x": "100px", + "y": "0px", + "width": "50px", + "height": "100px", + "shapeWidth": "50px", + "shapeHeight": "100px", + "shapeRadius": "50%", + "backgroundColor": "green" + }, + { + "type": "actionbutton", + "pvName": "sim://limit#1", + "text": "Motor 3", + "image": "http://localhost:3000/DCM-base.png", + "position": "absolute", + "x": "350px", + "y": "0px", + "width": "100px", + "height": "100px", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "motor", + "description": "Motor 3 Info", + "macros": "{\"motor\":\"3\"}" + } + ] + } + }, + { + "type": "actionbutton", + "pvName": "sim://limit#1", + "text": "Digitel MPC", + "image": "http://localhost:3000/ionp.svg", + "position": "absolute", + "x": "450px", + "y": "0px", + "width": "100px", + "height": "80px", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "digitelmpc", + "description": "Digitel MPC Sim", + "macros": "{}" + } + ] + } + }, + { + "type": "actionbutton", + "pvName": "sim://limit#1", + "text": "Digitel MPC Ionp", + "image": "http://localhost:3000/ionp.svg", + "position": "absolute", + "x": "450px", + "y": "80px", + "width": "100px", + "height": "80px", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "digitelmpcionp", + "description": "Digitel MPC Ionp Sim", + "macros": "{}" + } + ] + } + }, + { + "type": "actionbutton", + "text": "Motor Summary Screen", + "position": "absolute", + "x": "20px", + "y": "125px", + "width": "200px", + "height": "40px", + "backgroundColor": "#aaaaaa", + "actions": { + "executeAsOne": false, + "actions": [ + { + "type": "OPEN_PAGE", + "location": "embed", + "page": "motorSummary", + "macros": "{}", + "description": "Motor Summary Screen" + } + ] + } + } + ] +} diff --git a/src/App.css b/src/App.css index 35a197d7..9e677dd5 100644 --- a/src/App.css +++ b/src/App.css @@ -1,3 +1,7 @@ +* { + box-sizing: border-box; +} + html, body, #root { @@ -5,9 +9,14 @@ body, width: 100%; background-color: var(--colour-background); } - -.hidden { - display: none; +html, +body { + margin: 0; + padding: 0; + background: var(--colour-background); + color: var(--color-text); + font-family: "Open sans"; + font-size: 16px; } .App { @@ -52,12 +61,9 @@ body, .Slider { cursor: grab; } - -@keyframes App-logo-spin { - from { - transform: rotate(0deg); - } - to { - transform: rotate(360deg); - } +.top { + width: 100%; + background: var(--colour-background); + text-align: right; + height: 200px; } diff --git a/src/App.tsx b/src/App.tsx index 33fb1396..5462d08d 100644 --- a/src/App.tsx +++ b/src/App.tsx @@ -4,27 +4,17 @@ import React from "react"; import "./App.css"; import { Provider } from "react-redux"; -import { BrowserRouter, Link, Route } from "react-router-dom"; +import { BrowserRouter } from "react-router-dom"; import { getStore, initialiseStore } from "./redux/store"; import log from "loglevel"; -import { FrontPage } from "./pages/frontpage"; -import { GraphicalPage } from "./pages/graphics"; -import { ExamplePage } from "./pages/examplePage"; -import { ProgressPage } from "./pages/progressPage"; -import { PositioningExamplePage } from "./pages/positioningExamplePage"; -import { JsonPage } from "./pages/fromJson"; -import { ConiqlPage } from "./pages/coniqlPage"; -import { MacrosPage } from "./pages/macrosPage"; import { lightTheme, darkTheme, ThemeContext } from "./themeContext"; -import { FlexExamplePage } from "./pages/flexExamplePage"; -import { EmbeddedPage } from "./pages/embeddedPage"; -import { ShapesPage } from "./pages/shapesPage"; - import { SimulatorPlugin } from "./connection/sim"; -import { DynamicPage } from "./pages/dynamicPage"; import { ConiqlPlugin } from "./connection/coniql"; import { ConnectionForwarder } from "./connection/forwarder"; +import { DynamicPageWidget } from "./components/DynamicPage/dynamicPage"; import { Connection } from "./connection/plugin"; +import { ActionButton } from "./components/ActionButton/actionButton"; +import { OPEN_PAGE } from "./widgetActions"; var settings: any; try { @@ -34,7 +24,7 @@ try { settings = {}; } -log.setLevel("debug"); +log.setLevel("warn"); function applyTheme(theme: any): void { Object.keys(theme).forEach(function(key): void { @@ -44,7 +34,7 @@ function applyTheme(theme: any): void { } const App: React.FC = (): JSX.Element => { - const simulator = new SimulatorPlugin(); + const simulator = new SimulatorPlugin(100); const fallbackPlugin = simulator; const plugins: [string, Connection][] = [ ["sim://", simulator], @@ -61,94 +51,48 @@ const App: React.FC = (): JSX.Element => { const { toggle, dark } = React.useContext(ThemeContext); applyTheme(dark ? darkTheme : lightTheme); - const styleLinkButton = { - backgroundColor: "#eeeeee", - margin: "10px 10px" - }; - return ( - - + +
-

CS Web Proto

- -
+ - - - - - - - - - - - - -
+ />
-
-
+ + ); }; diff --git a/src/components/ActionButton/actionButton.module.css b/src/components/ActionButton/actionButton.module.css index 65091632..983a7362 100644 --- a/src/components/ActionButton/actionButton.module.css +++ b/src/components/ActionButton/actionButton.module.css @@ -8,7 +8,6 @@ .image { background-color: transparent; border: none; - color: white; cursor: pointer; } diff --git a/src/components/ActionButton/actionButton.tsx b/src/components/ActionButton/actionButton.tsx index fab6e5e6..aa17a410 100644 --- a/src/components/ActionButton/actionButton.tsx +++ b/src/components/ActionButton/actionButton.tsx @@ -1,7 +1,14 @@ import React from "react"; +import PropTypes from "prop-types"; import { WidgetActions, executeActions } from "../../widgetActions"; -import { InferWidgetProps, PVWidget, PVWidgetPropType } from "../Widget/widget"; +import { + InferWidgetProps, + PVComponent, + PVWidget, + PVWidgetPropType +} from "../Widget/widget"; import classes from "./actionButton.module.css"; +import { useHistory } from "react-router-dom"; export interface ActionButtonProps { text: string; @@ -38,22 +45,31 @@ export const ActionButtonComponent = ( } }; -export interface ActionButtonWidgetProps { - text: string; - actions: WidgetActions; - style?: {}; - image?: string; -} +const ActionButtonPropType = { + text: PropTypes.string.isRequired, + actions: PropTypes.shape({ + executeAsOne: PropTypes.bool, + actions: PropTypes.arrayOf(PropTypes.object) + }).isRequired, + style: PropTypes.object, + image: PropTypes.string +}; + +const ActionButtonProps = { + ...ActionButtonPropType, + ...PVWidgetPropType +}; // Menu button which also knows how to write to a PV export const ActionButtonWidget = ( - props: ActionButtonWidgetProps + props: InferWidgetProps & PVComponent ): JSX.Element => { // Function to send the value on to the PV + const history = useHistory(); function onClick(event: React.MouseEvent): void { - if (props.actions !== undefined) executeActions(props.actions); + if (props.actions !== undefined) + executeActions(props.actions as WidgetActions, history); } - return ( + props: InferWidgetProps ): JSX.Element => ; -ActionButton.propTypes = PVWidgetPropType; +ActionButton.propTypes = ActionButtonProps; diff --git a/src/components/DynamicPage/dynamicPage.tsx b/src/components/DynamicPage/dynamicPage.tsx new file mode 100644 index 00000000..f1b03924 --- /dev/null +++ b/src/components/DynamicPage/dynamicPage.tsx @@ -0,0 +1,127 @@ +import React from "react"; +import log from "loglevel"; +import PropTypes from "prop-types"; +import { Route, RouteComponentProps } from "react-router-dom"; + +import { + Component, + Widget, + WidgetPropType, + InferWidgetProps +} from "../Widget/widget"; +import { WidgetFromJson } from "../FromJson/fromJson"; // eslint-disable-line import/no-cycle +import { ActionButton } from "../ActionButton/actionButton"; +import { CLOSE_PAGE } from "../../widgetActions"; + +export interface DynamicParams { + json: string; + macros?: string; +} + +export function DynamicPageFetch({ + match +}: RouteComponentProps): JSX.Element { + const file = "http://localhost:3000/" + match.params.json + ".json"; + let map = {}; + try { + map = match.params.macros && JSON.parse(match.params.macros); + } catch (error) { + log.warn(match.params.json); + log.warn(error); + } + return ( + + ); +} + +const DynamicPageProps = { + routePath: PropTypes.string.isRequired +}; + +// Generic display widget to put other things inside +const DynamicPageComponent = ( + props: InferWidgetProps & Component +): JSX.Element => ( +
+ ( +
+
+
+ +
+
+ +
+ )} + /> +
+); + +const DynamicPageWidgetProps = { + ...DynamicPageProps, + ...WidgetPropType +}; + +export const DynamicPageWidget = ( + props: InferWidgetProps +): JSX.Element => ; + +DynamicPageWidget.propTypes = DynamicPageWidgetProps; diff --git a/src/components/FromBob/bobConversionUtils.ts b/src/components/FromBob/bobConversionUtils.ts index ec9a73de..15417a5e 100644 --- a/src/components/FromBob/bobConversionUtils.ts +++ b/src/components/FromBob/bobConversionUtils.ts @@ -47,8 +47,6 @@ export const bobParseColor = ( jsonProp: convert.ElementCompact ): string => { const color = jsonProp.color as BobColor; - console.log("bobparsecolor"); - console.log(color); try { return `rgb(${color._attributes.red}, ${color._attributes.green}, ${color._attributes.blue})`; } catch (e) { @@ -114,11 +112,13 @@ export const bobParseActions = ( try { let type: string = availableActions[action._attributes.type]; if (type === WRITE_PV) { + // Not all actions have descriptions so ret processedActions.actions.push({ type: WRITE_PV, pvName: action.pv_name._text, value: action.value._text, - description: action.description._text + description: + (action.description && action.description._text) || undefined }); } } catch (e) { diff --git a/src/components/FromBob/fromBob.test.tsx b/src/components/FromBob/fromBob.test.tsx index 602fd31a..671c9220 100644 --- a/src/components/FromBob/fromBob.test.tsx +++ b/src/components/FromBob/fromBob.test.tsx @@ -5,6 +5,15 @@ import { shallow } from "enzyme"; import { Display } from "../Display/display"; import { Label } from "../Label/label"; +const useEffect = jest.spyOn(React, "useEffect"); +const mockUseEffect = (): void => { + useEffect.mockImplementationOnce((f): any => f()); +}; + +beforeEach((): void => { + mockUseEffect(); +}); + describe("", (): void => { it("fetches a file from the server", (done): void => { const mockSuccessResponse = {}; @@ -30,7 +39,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> @@ -78,7 +90,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> @@ -100,7 +115,8 @@ describe("", (): void => { const mockSuccessResponse = ` - Display200 + Display + 200 350 Label @@ -132,7 +148,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> diff --git a/src/components/FromBob/fromBob.ts b/src/components/FromBob/fromBob.ts index f3bae5b1..bfb590ff 100644 --- a/src/components/FromBob/fromBob.ts +++ b/src/components/FromBob/fromBob.ts @@ -1,7 +1,7 @@ /* Provide the same component as fromJson but converting bob files and providing a useful widget dictionary */ -import { useState } from "react"; +import React, { useState } from "react"; import PropTypes from "prop-types"; import log from "loglevel"; @@ -9,6 +9,7 @@ import { WidgetDescription, widgetDescriptionToComponent } from "../Positioning/positioning"; +import { MacroMap } from "../../redux/csState"; import { Label } from "../Label/label"; import { Readback } from "../Readback/readback"; import { Input } from "../Input/input"; @@ -52,21 +53,43 @@ export const WidgetFromBob = ( props: InferWidgetProps ): JSX.Element => { const [bob, setBob] = useState(""); + const [renderedFile, setFile] = useState(""); + const [currentMacros, setMacros] = useState({}); // Extract props let { file, macroMap } = props; - if (bob === "") { - fetch(file) - .then( - (response): Promise => { - return response.text(); - } - ) - .then((bob): void => { - setBob(bob); - }); + // Using directly from React for testing purposes + React.useEffect((): (() => void) => { + // Will be set on the first render + let mounted = true; + if (file !== renderedFile) { + fetch(file) + .then( + (response): Promise => { + return response.text(); + } + ) + .then((bob): void => { + // Check component is still mounted when result comes back + if (mounted) { + setBob(bob); + setFile(file); + setMacros(macroMap as MacroMap); + } + }); + } + + // Clean up function + return (): void => { + mounted = false; + }; + }); + + if (macroMap !== currentMacros) { + setMacros(macroMap as MacroMap); } + const widgetDict = { textupdate: Readback, "org.csstudio.opibuilder.widgets.TextUpdate": Readback, @@ -81,6 +104,7 @@ export const WidgetFromBob = ( "org.csstudio.opibuilder.widgets.Rectangle": Shape, action_button: ActionButton, // eslint-disable-line @typescript-eslint/camelcase "org.csstudio.opibuilder.widgets.ActionButton": ActionButton, + "org.csstudio.opibuilder.widgets.BoolButton": Shape, empty: Display, widgetFromBob: WidgetFromBob }; diff --git a/src/components/FromJson/fromJson.test.tsx b/src/components/FromJson/fromJson.test.tsx index 83e85d9e..1b70d804 100644 --- a/src/components/FromJson/fromJson.test.tsx +++ b/src/components/FromJson/fromJson.test.tsx @@ -5,6 +5,15 @@ import { shallow } from "enzyme"; import { Display } from "../Display/display"; import { Label } from "../Label/label"; +beforeEach((): void => { + const useEffect = jest.spyOn(React, "useEffect"); + const mockUseEffect = (): void => { + useEffect.mockImplementationOnce((f): any => f()); + }; + + mockUseEffect(); +}); + describe("", (): void => { it("fetches a file from the server", (done): void => { const mockSuccessResponse = {}; @@ -31,7 +40,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> @@ -70,7 +82,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> @@ -116,7 +131,10 @@ describe("", (): void => { height: "", width: "", margin: "", - padding: "" + padding: "", + border: "", + minWidth: "", + maxWidth: "" }} file="TestFile" /> diff --git a/src/components/FromJson/fromJson.ts b/src/components/FromJson/fromJson.ts index 5f8a51c1..0a4c732f 100644 --- a/src/components/FromJson/fromJson.ts +++ b/src/components/FromJson/fromJson.ts @@ -1,4 +1,4 @@ -import { useState } from "react"; +import React, { useState } from "react"; import PropTypes from "prop-types"; import log from "loglevel"; @@ -6,6 +6,7 @@ import { widgetDescriptionToComponent, WidgetDescription } from "../Positioning/positioning"; +import { MacroMap } from "../../redux/csState"; import { Label } from "../Label/label"; import { Readback } from "../Readback/readback"; import { Input } from "../Input/input"; @@ -16,7 +17,9 @@ import { SlideControl } from "../SlideControl/slideControl"; import { MenuButton } from "../MenuButton/menuButton"; import { Display } from "../Display/display"; import { ActionButton } from "../ActionButton/actionButton"; +import { DynamicPageWidget } from "../DynamicPage/dynamicPage"; // eslint-disable-line import/no-cycle import { WidgetFromBob } from "../FromBob/fromBob"; +import { GroupingContainer } from "../GroupingContainer/groupingContainer"; import { WidgetPropType, InferWidgetProps } from "../Widget/widget"; const EMPTY_WIDGET: WidgetDescription = { @@ -43,21 +46,43 @@ export const WidgetFromJson = ( props: InferWidgetProps ): JSX.Element | null => { const [json, setJson] = useState(EMPTY_WIDGET); + const [renderedFile, setFile] = useState(""); + const [currentMacros, setMacros] = useState({}); // Extract props let { file, macroMap } = props; - if (json["type"] === "empty") { - fetch(file) - .then( - (response): Promise => { - return response.json(); - } - ) - .then((json): void => { - setJson(json); - }); + // Using directly from React for testing purposes + React.useEffect((): (() => void) => { + // Will be set on the first render + let mounted = true; + if (file !== renderedFile) { + fetch(file) + .then( + (response): Promise => { + return response.json(); + } + ) + .then((json): void => { + // Check component is still mounted when result comes back + if (mounted) { + setJson(json); + setFile(file); + setMacros(macroMap as MacroMap); + } + }); + } + + // Clean up function + return (): void => { + mounted = false; + }; + }); + + if (macroMap !== currentMacros) { + setMacros(macroMap as MacroMap); } + const widgetDict = { readback: Readback, shape: Shape, @@ -71,12 +96,14 @@ export const WidgetFromJson = ( display: Display, empty: Display, widgetFromJSON: WidgetFromJson, - widgetFromBob: WidgetFromBob + dynamicpage: DynamicPageWidget, + widgetFromBob: WidgetFromBob, + grouping: GroupingContainer }; let component: JSX.Element | null; try { - component = widgetDescriptionToComponent(json, widgetDict, macroMap); + component = widgetDescriptionToComponent(json, widgetDict, currentMacros); } catch (e) { log.error(`Error converting JSON into components in ${file}`); log.error(e.msg); @@ -84,7 +111,7 @@ export const WidgetFromJson = ( component = widgetDescriptionToComponent( ERROR_WIDGET, widgetDict, - macroMap + currentMacros ); } diff --git a/src/components/MenuWrapper/menuWrapper.test.tsx b/src/components/MenuWrapper/menuWrapper.test.tsx index 5a2cd304..4fa3fab5 100644 --- a/src/components/MenuWrapper/menuWrapper.test.tsx +++ b/src/components/MenuWrapper/menuWrapper.test.tsx @@ -5,6 +5,13 @@ import { MenuWrapper } from "./menuWrapper"; let wrapper: ShallowWrapper; +// Mock the useHistory hook +jest.mock("react-router-dom", (): object => ({ + useHistory: (): object => ({ + push: jest.fn() + }) +})); + beforeEach((): void => { const actions = { executeAsOne: false, actions: [] }; const menuWrapper = ( diff --git a/src/components/MenuWrapper/menuWrapper.tsx b/src/components/MenuWrapper/menuWrapper.tsx index b10ded52..c21e4cad 100644 --- a/src/components/MenuWrapper/menuWrapper.tsx +++ b/src/components/MenuWrapper/menuWrapper.tsx @@ -6,6 +6,7 @@ import { getActionDescription } from "../../widgetActions"; import classes from "./menuWrapper.module.css"; +import { useHistory } from "react-router-dom"; export const MenuWrapper = (props: { pvName: string; @@ -16,6 +17,9 @@ export const MenuWrapper = (props: { const [contextOpen, setContextOpen] = useState(false); const [x, setX] = useState(0); const [y, setY] = useState(0); + + const history = useHistory(); + const handleClick = (e: React.MouseEvent): void => { e.preventDefault(); if (e.button === 2) { @@ -30,7 +34,7 @@ export const MenuWrapper = (props: { }; function triggerCallback(action: WidgetAction): void { - executeAction(action); + executeAction(action, history); setContextOpen(false); } diff --git a/src/components/Positioning/positioning.tsx b/src/components/Positioning/positioning.tsx index af65bc74..f2398d37 100644 --- a/src/components/Positioning/positioning.tsx +++ b/src/components/Positioning/positioning.tsx @@ -36,6 +36,9 @@ export function widgetDescriptionToComponent( width = undefined, margin = undefined, padding = undefined, + border = undefined, + minWidth = undefined, + maxWidth = undefined, color = undefined, font = undefined, fontSize = undefined, @@ -77,7 +80,10 @@ export function widgetDescriptionToComponent( height: height, width: width, margin: margin, - padding: padding + padding: padding, + border: border, + minWidth: minWidth, + maxWidth: maxWidth }); const widgetStyling = filterUndefinedOut({ color: color, diff --git a/src/components/Widget/widget.tsx b/src/components/Widget/widget.tsx index 479601bf..a633c9de 100644 --- a/src/components/Widget/widget.tsx +++ b/src/components/Widget/widget.tsx @@ -34,7 +34,10 @@ export type PVInputComponent = PVComponent & { pvName: string }; // complex units const ContainerFeaturesPropType = { margin: PropTypes.string, - padding: PropTypes.string + padding: PropTypes.string, + border: PropTypes.string, + minWidth: PropTypes.string, + maxWidth: PropTypes.string }; const OpenWebpagePropType = PropTypes.shape({ @@ -43,6 +46,20 @@ const OpenWebpagePropType = PropTypes.shape({ description: PropTypes.string }); +const OpenPagePropType = PropTypes.shape({ + type: PropTypes.string.isRequired, + page: PropTypes.string.isRequired, + location: PropTypes.string.isRequired, + macros: PropTypes.string.isRequired, + description: PropTypes.string.isRequired +}); + +const ClosePagePropType = PropTypes.shape({ + type: PropTypes.string.isRequired, + location: PropTypes.string.isRequired, + description: PropTypes.string +}); + const WritePvPropType = PropTypes.shape({ type: PropTypes.string.isRequired, pvName: PropTypes.string.isRequired, @@ -51,8 +68,10 @@ const WritePvPropType = PropTypes.shape({ }); const ActionPropType = PropTypes.oneOfType([ - OpenWebpagePropType, - WritePvPropType + OpenPagePropType, + ClosePagePropType, + WritePvPropType, + OpenWebpagePropType ]); const ActionsPropType = PropTypes.shape({ @@ -90,7 +109,8 @@ const WidgetStylingPropType = { fontSize: PropTypes.oneOfType([PropTypes.string, PropTypes.number]), fontWeight: PropTypes.oneOfType([PropTypes.string, PropTypes.number]), textAlign: PropTypes.oneOf(["center", "left", "right", "justify"]), - backgroundColor: PropTypes.string + backgroundColor: PropTypes.string, + color: PropTypes.string }; type WidgetStyling = InferWidgetProps; diff --git a/src/connection/sim.ts b/src/connection/sim.ts index b693b73d..4f31ad2d 100644 --- a/src/connection/sim.ts +++ b/src/connection/sim.ts @@ -106,6 +106,21 @@ class SinePv extends SimPv { } } +class RampPv extends SimPv { + // Goes from 0-99 on a loop + public constructor(...args: SimArgs) { + super(...args); + setInterval(this.publish.bind(this), this.updateRate); + } + + public getValue(): VType | undefined { + let d = new Date(); + return vdouble( + (d.getSeconds() % 10) * 10 + Math.floor(d.getMilliseconds() / 100) + ); + } +} + class RandomPv extends SimPv { public constructor(...args: SimArgs) { super(...args); @@ -421,6 +436,9 @@ export class SimulatorPlugin implements Connection { } else if (nameInfo.protocol === "sim://limit") { initial = undefined; cls = LimitData; + } else if (nameInfo.protocol === "sim://ramp") { + initial = undefined; + cls = RampPv; } else { return { simulator: undefined, initialValue: undefined }; } diff --git a/src/pages/coniqlPage.tsx b/src/pages/coniqlPage.tsx deleted file mode 100644 index a2ecfc6a..00000000 --- a/src/pages/coniqlPage.tsx +++ /dev/null @@ -1,18 +0,0 @@ -// Demos from the coniql server, if running. - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const ConiqlPage = (): JSX.Element => ( - -); diff --git a/src/pages/dynamicPage.tsx b/src/pages/dynamicPage.tsx deleted file mode 100644 index c7cceb64..00000000 --- a/src/pages/dynamicPage.tsx +++ /dev/null @@ -1,31 +0,0 @@ -// Demos from the coniql server, if running. - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; -import { RouteComponentProps } from "react-router-dom"; - -export interface DynamicParams { - json: string; - macros: string; -} - -export function DynamicPage({ - match -}: RouteComponentProps): JSX.Element { - var file = "http://localhost:3000/" + match.params.json + ".json"; - var map = JSON.parse(match.params.macros); - return ( - - ); -} diff --git a/src/pages/embeddedPage.tsx b/src/pages/embeddedPage.tsx deleted file mode 100644 index d910ffa2..00000000 --- a/src/pages/embeddedPage.tsx +++ /dev/null @@ -1,30 +0,0 @@ -// Simple page that loads from a JSON file directly. - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const EmbeddedPage = (): JSX.Element => ( -
-
- -
-
-); diff --git a/src/pages/examplePage.tsx b/src/pages/examplePage.tsx deleted file mode 100644 index 9af315cd..00000000 --- a/src/pages/examplePage.tsx +++ /dev/null @@ -1,19 +0,0 @@ -// Page with many readbacks - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const ExamplePage = (): JSX.Element => ( - -); diff --git a/src/pages/flexExamplePage.tsx b/src/pages/flexExamplePage.tsx deleted file mode 100644 index 8a0d0c90..00000000 --- a/src/pages/flexExamplePage.tsx +++ /dev/null @@ -1,17 +0,0 @@ -// Page to show off the absolute positiong example -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const FlexExamplePage = (): JSX.Element => ( - -); diff --git a/src/pages/fromJson.tsx b/src/pages/fromJson.tsx deleted file mode 100644 index f341a35b..00000000 --- a/src/pages/fromJson.tsx +++ /dev/null @@ -1,31 +0,0 @@ -// Simple page that loads from a JSON file directly. - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const JsonPage = (): JSX.Element => ( -
-

Loading from JSON and Bob

-
- -
-
-); diff --git a/src/pages/frontpage.tsx b/src/pages/frontpage.tsx deleted file mode 100644 index 52abbcc2..00000000 --- a/src/pages/frontpage.tsx +++ /dev/null @@ -1,18 +0,0 @@ -// Front page of application - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const FrontPage = (): JSX.Element => ( - -); diff --git a/src/pages/graphics.tsx b/src/pages/graphics.tsx deleted file mode 100644 index 6633b9fd..00000000 --- a/src/pages/graphics.tsx +++ /dev/null @@ -1,17 +0,0 @@ -// Page to show off graphical layouts -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const GraphicalPage = (): JSX.Element => ( - -); diff --git a/src/pages/macrosPage.tsx b/src/pages/macrosPage.tsx deleted file mode 100644 index 14b39135..00000000 --- a/src/pages/macrosPage.tsx +++ /dev/null @@ -1,85 +0,0 @@ -/* eslint no-template-curly-in-string: 0 */ - -import React from "react"; - -import { Label } from "../components/Label/label"; -import { Readback } from "../components/Readback/readback"; -import { MacroUpdater } from "../components/MacroUpdater/macroUpdater"; -import { MacroDisplayer } from "../components/MacroDisplayer/macroDisplayer"; -import { Input } from "../components/Input/input"; - -export const MacrosPage = (): JSX.Element => ( -
-
- - -
-
-
-
-); diff --git a/src/pages/positioningExamplePage.tsx b/src/pages/positioningExamplePage.tsx deleted file mode 100644 index 9a6c07d9..00000000 --- a/src/pages/positioningExamplePage.tsx +++ /dev/null @@ -1,18 +0,0 @@ -// Page to show off the absolute positiong example -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const PositioningExamplePage = (): JSX.Element => ( - -); diff --git a/src/pages/progressPage.tsx b/src/pages/progressPage.tsx deleted file mode 100644 index 2ee87bda..00000000 --- a/src/pages/progressPage.tsx +++ /dev/null @@ -1,18 +0,0 @@ -// Page to show off the progress bar and slide control -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const ProgressPage = (): JSX.Element => ( - -); diff --git a/src/pages/shapesPage.tsx b/src/pages/shapesPage.tsx deleted file mode 100644 index ac3853c0..00000000 --- a/src/pages/shapesPage.tsx +++ /dev/null @@ -1,18 +0,0 @@ -// Page with many inputs - -import React from "react"; - -import { WidgetFromJson } from "../components/FromJson/fromJson"; - -export const ShapesPage = (): JSX.Element => ( - -); diff --git a/src/themeContext.tsx b/src/themeContext.tsx index f4394797..b92ea2c3 100644 --- a/src/themeContext.tsx +++ b/src/themeContext.tsx @@ -3,13 +3,15 @@ import React, { useState, useEffect } from "react"; export const lightTheme = { "--colour-text": "#000000", "--colour-secondary-text": "#000000", - "--colour-background": "#DDDDDD" + "--colour-background": "#F7F9FB", + "--colour-secondary-background": "#8FC1E3" }; export const darkTheme = { "--colour-text": "#FFFFFF", - "--colour-secondary-text": "#FFFF00", - "--colour-background": "#535353" + "--colour-secondary-text": "#FFFFFF", + "--colour-background": "#282828", + "--colour-secondary-background": "#0C0032" }; const initialState = { diff --git a/src/widgetActions.ts b/src/widgetActions.ts index b6397bca..e50dca13 100644 --- a/src/widgetActions.ts +++ b/src/widgetActions.ts @@ -1,10 +1,27 @@ import { writePv } from "./hooks/useSubscription"; import { valueToVtype } from "./vtypes/utils"; +import { History } from "history"; import log from "loglevel"; +export const OPEN_PAGE = "OPEN_PAGE"; +export const CLOSE_PAGE = "CLOSE_PAGE"; export const OPEN_WEBPAGE = "OPEN_WEBPAGE"; export const WRITE_PV = "WRITE_PV"; +export interface OpenPage { + type: typeof OPEN_PAGE; + page: string; + location: string; + macros: string; + description: string; +} + +export interface ClosePage { + type: typeof CLOSE_PAGE; + location: string; + description: string; +} + export interface OpenWebpage { type: typeof OPEN_WEBPAGE; url: string; @@ -18,7 +35,7 @@ export interface WritePv { description?: string; } -export type WidgetAction = OpenWebpage | WritePv; +export type WidgetAction = OpenWebpage | WritePv | OpenPage | ClosePage; export interface WidgetActions { actions: WidgetAction[]; @@ -41,14 +58,74 @@ export const getActionDescription = (action: WidgetAction): string => { return `Write ${action.value} to ${action.pvName}`; case OPEN_WEBPAGE: return `Open ${action.url}`; + case OPEN_PAGE: + return `Open ${action.page}`; + case CLOSE_PAGE: + return `Close ${action.location}`; default: throw new InvalidAction(action); } } }; -export const executeAction = (action: WidgetAction): void => { +export const openPage = (action: OpenPage, history: History): void => { + //Find current browser path: currentPath + let currentPath = ""; + if (history.location.pathname !== undefined) + currentPath = history.location.pathname; + + //New page component in action.location + let newPathComponent = + action.location + "/" + action.page + "/" + action.macros + "/"; + + //Find existing component in same location + let matcher = new RegExp(action.location + "/[^/]*/[^/]*/"); + let groups = matcher.exec(currentPath); + if (groups !== null && groups[0] !== undefined) { + //Swap component in location + currentPath = currentPath.replace(groups[0], newPathComponent); + } else { + //Append component in location + currentPath = currentPath + newPathComponent; + } + history.push(currentPath); +}; + +export const closePage = (action: ClosePage, history: History): void => { + //Find current browser path: currentPath + let currentPath = ""; + if (history.location.pathname !== undefined) + currentPath = history.location.pathname; + + //Find any existing component in action location + let matcher = new RegExp(action.location + "/[^/]*/[^/]*/"); + let groups = matcher.exec(currentPath); + if (groups !== null && groups[0] !== undefined) { + //Remove component in location + currentPath = currentPath.replace(groups[0], ""); + } + history.push(currentPath); +}; + +export const executeAction = ( + action: WidgetAction, + history?: History +): void => { switch (action.type) { + case OPEN_PAGE: + if (history) { + openPage(action, history); + } else { + log.error("Tried to open a page but no history object passed"); + } + break; + case CLOSE_PAGE: + if (history) { + closePage(action, history); + } else { + log.error("Tried to open a page but no history object passed"); + } + break; case OPEN_WEBPAGE: window.open(action.url); break; @@ -60,7 +137,10 @@ export const executeAction = (action: WidgetAction): void => { } }; -export const executeActions = (actions: WidgetActions): void => { +export const executeActions = ( + actions: WidgetActions, + history?: History +): void => { if (actions.actions.length > 0) { let toExecute: WidgetAction[] = []; if (actions.executeAsOne) { @@ -70,7 +150,7 @@ export const executeActions = (actions: WidgetActions): void => { } for (const action of toExecute) { log.debug(`executing an action: ${getActionDescription(action)}`); - executeAction(action); + executeAction(action, history); } } };