lhasa-ligand-builder 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.eslintrc.cjs +18 -0
- package/LICENSE +674 -0
- package/README.md +41 -0
- package/index.html +49 -0
- package/package.json +37 -0
- package/public/.gitkeep +0 -0
- package/public/Components-inchikey.ich +48167 -0
- package/public/icons/README +7 -0
- package/public/icons/dark/layla_3c.svg +82 -0
- package/public/icons/dark/layla_4c.svg +82 -0
- package/public/icons/dark/layla_5c.svg +82 -0
- package/public/icons/dark/layla_6arom.svg +89 -0
- package/public/icons/dark/layla_6c.svg +82 -0
- package/public/icons/dark/layla_7c.svg +82 -0
- package/public/icons/dark/layla_8c.svg +82 -0
- package/public/icons/dark/layla_charge_tool.svg +78 -0
- package/public/icons/dark/layla_delete_hydrogens_tool.svg +384 -0
- package/public/icons/dark/layla_double_bond.svg +78 -0
- package/public/icons/dark/layla_format_tool.svg +283 -0
- package/public/icons/dark/layla_geometry_tool.svg +105 -0
- package/public/icons/dark/layla_key.svg +76 -0
- package/public/icons/dark/layla_move_tool.svg +110 -0
- package/public/icons/dark/layla_single_bond.svg +73 -0
- package/public/icons/dark/layla_triple_bond.svg +87 -0
- package/public/icons/dark/lhasa_delete_tool.svg +401 -0
- package/public/icons/dark/lhasa_flip_x_tool.svg +106 -0
- package/public/icons/dark/lhasa_flip_y_tool.svg +106 -0
- package/public/icons/dark/lhasa_rotate_tool.svg +112 -0
- package/public/icons/icons/hicolor_apps_scalable_coot-layla.svg +105 -0
- package/public/icons/layla_3c.svg +82 -0
- package/public/icons/layla_4c.svg +82 -0
- package/public/icons/layla_5c.svg +82 -0
- package/public/icons/layla_6arom.svg +89 -0
- package/public/icons/layla_6c.svg +82 -0
- package/public/icons/layla_7c.svg +82 -0
- package/public/icons/layla_8c.svg +82 -0
- package/public/icons/layla_charge_tool.svg +78 -0
- package/public/icons/layla_delete_hydrogens_tool.svg +384 -0
- package/public/icons/layla_double_bond.svg +78 -0
- package/public/icons/layla_format_tool.svg +283 -0
- package/public/icons/layla_geometry_tool-dark.svg +105 -0
- package/public/icons/layla_geometry_tool.svg +105 -0
- package/public/icons/layla_key.svg +76 -0
- package/public/icons/layla_move_tool.svg +110 -0
- package/public/icons/layla_single_bond.svg +73 -0
- package/public/icons/layla_triple_bond.svg +87 -0
- package/public/icons/lhasa_delete_tool.svg +401 -0
- package/public/icons/lhasa_flip_x_tool.svg +106 -0
- package/public/icons/lhasa_flip_y_tool.svg +106 -0
- package/public/icons/lhasa_rotate_tool.svg +112 -0
- package/public/lhasa.js +2 -0
- package/public/lhasa.wasm +0 -0
- package/public/react.svg +1 -0
- package/src/Lhasa.tsx +1452 -0
- package/src/assets/.gitkeep +0 -0
- package/src/bansu_integration.tsx +315 -0
- package/src/customize_mui.scss +97 -0
- package/src/inchikey_database_parse.tsx +20 -0
- package/src/index.d.ts +11 -0
- package/src/index.scss +352 -0
- package/src/main.tsx +79 -0
- package/src/qed_property_infobox.tsx +14 -0
- package/src/types.d.ts +375 -0
- package/src/vite-env.d.ts +1 -0
- package/tsconfig.json +25 -0
- package/tsconfig.node.json +10 -0
- package/vite.config.ts +55 -0
package/src/index.scss
ADDED
|
@@ -0,0 +1,352 @@
|
|
|
1
|
+
@use 'sass:color';
|
|
2
|
+
|
|
3
|
+
$lhasa_background_color: rgba(119, 119, 119, 0.076);
|
|
4
|
+
$lhasa_background_color_dark: rgb(53, 53, 53);
|
|
5
|
+
$lhasa_text_color: black;
|
|
6
|
+
$lhasa_text_color_dark: white;
|
|
7
|
+
$lhasa_qed_value_color: color.adjust($lhasa_text_color, $saturation: +50%, $lightness: +50%, $hue: 196);
|
|
8
|
+
$lhasa_qed_value_color_dark: color.adjust($lhasa_text_color, $saturation: +75%, $lightness: +65%, $hue: 310);
|
|
9
|
+
$lhasa_border_color: rgba(0, 0, 0, 0.24);
|
|
10
|
+
$lhasa_border_color_dark: rgba(255, 255, 255, 0.24);
|
|
11
|
+
$lhasa_toolbar_border_color: rgba(184, 0, 0, 0.181);
|
|
12
|
+
$lhasa_toolbar_border_color_dark: rgba(250, 85, 85, 0.281);
|
|
13
|
+
$lhasa_base_padding: 3px;
|
|
14
|
+
$lhasa_padding_minor: 2px;
|
|
15
|
+
$lhasa_font_size: 0.65rem;
|
|
16
|
+
|
|
17
|
+
.editor_canvas_container {
|
|
18
|
+
border: $lhasa_border_color 1px solid;
|
|
19
|
+
/* Padding here breaks relative coords */
|
|
20
|
+
/* padding: 5px; */
|
|
21
|
+
cursor: default;
|
|
22
|
+
user-select: none;
|
|
23
|
+
overflow: auto;
|
|
24
|
+
width: 480px;
|
|
25
|
+
height: 270px;
|
|
26
|
+
// max-width: 700px;
|
|
27
|
+
// min-width: 300px;
|
|
28
|
+
// max-height: 500px;
|
|
29
|
+
// min-height: 320px;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
.editor_canvas_container.lhasa_dark_mode {
|
|
33
|
+
border-color: $lhasa_border_color_dark;
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
.lhasa_drawing {
|
|
37
|
+
background-color: white;
|
|
38
|
+
/* Removes weird, empty margin-like area */
|
|
39
|
+
margin-bottom: -$lhasa_base_padding;
|
|
40
|
+
// Disable default scroll on touch behaviour
|
|
41
|
+
touch-action: none;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
.lhasa_editor {
|
|
45
|
+
font-family: sans-serif;
|
|
46
|
+
background-color: $lhasa_background_color;
|
|
47
|
+
color: $lhasa_text_color;
|
|
48
|
+
font-size: $lhasa_font_size;
|
|
49
|
+
padding: 2 * $lhasa_base_padding;
|
|
50
|
+
width: fit-content;
|
|
51
|
+
text-align: left;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
.lhasa_editor.lhasa_dark_mode {
|
|
55
|
+
background-color: $lhasa_background_color_dark;
|
|
56
|
+
color: $lhasa_text_color_dark;
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
// For the menus
|
|
60
|
+
.keybind_hint {
|
|
61
|
+
color: color.adjust($lhasa_text_color, $saturation: -50%, $lightness: +40%);
|
|
62
|
+
background-color: $lhasa_background_color;
|
|
63
|
+
margin-left: $lhasa_base_padding;
|
|
64
|
+
border-radius: $lhasa_padding_minor;
|
|
65
|
+
padding: $lhasa_padding_minor;
|
|
66
|
+
// font-family: monospace;
|
|
67
|
+
}
|
|
68
|
+
|
|
69
|
+
.lhasa_dark_mode .keybind_hint {
|
|
70
|
+
background-color: $lhasa_background_color_dark;
|
|
71
|
+
color: color.adjust($lhasa_text_color_dark, $saturation: -20%, $lightness: -40%);
|
|
72
|
+
// color: pink;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
.lhasa_tooltip_keybind_infoblock {
|
|
76
|
+
padding: $lhasa_base_padding * 2;
|
|
77
|
+
margin-top: $lhasa_base_padding;
|
|
78
|
+
border-radius: 3px;
|
|
79
|
+
// This border color works well in both modes
|
|
80
|
+
border: rgba(255, 255, 255, 0.405) 1px solid;
|
|
81
|
+
}
|
|
82
|
+
|
|
83
|
+
.lhasa_tooltip_keybind_info {
|
|
84
|
+
margin: $lhasa_base_padding;
|
|
85
|
+
// font-size: medium;
|
|
86
|
+
// margin-top: $lhasa_base_padding * 8;
|
|
87
|
+
border-radius: 3px;
|
|
88
|
+
color: lightblue;
|
|
89
|
+
background-color: color.adjust(lightblue, $alpha: -0.8);
|
|
90
|
+
padding: $lhasa_base_padding;
|
|
91
|
+
}
|
|
92
|
+
|
|
93
|
+
.lhasa_tooltip {
|
|
94
|
+
font-size: small;
|
|
95
|
+
font-family: sans-serif;
|
|
96
|
+
margin: $lhasa_base_padding * 2;
|
|
97
|
+
// color: red !important;
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
@mixin toolbar {
|
|
101
|
+
border: $lhasa_toolbar_border_color 1px solid;
|
|
102
|
+
border-radius: 3px;
|
|
103
|
+
padding: $lhasa_base_padding;
|
|
104
|
+
/* align-items: center; */
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
@mixin toolbar_dark {
|
|
108
|
+
border-color: $lhasa_toolbar_border_color_dark;
|
|
109
|
+
}
|
|
110
|
+
|
|
111
|
+
@mixin panel {
|
|
112
|
+
border: $lhasa_border_color 1px solid;
|
|
113
|
+
border-radius: 3px;
|
|
114
|
+
padding: $lhasa_base_padding;
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
@mixin panel_dark {
|
|
118
|
+
border-color: $lhasa_border_color_dark;
|
|
119
|
+
}
|
|
120
|
+
|
|
121
|
+
.scale_panel {
|
|
122
|
+
flex-grow: 1;
|
|
123
|
+
}
|
|
124
|
+
|
|
125
|
+
.invalid_molecules_panel,
|
|
126
|
+
.display_mode_panel,
|
|
127
|
+
.status_display_panel {
|
|
128
|
+
margin-bottom: $lhasa_base_padding;
|
|
129
|
+
}
|
|
130
|
+
|
|
131
|
+
.x_element_panel {
|
|
132
|
+
margin-bottom: $lhasa_base_padding;
|
|
133
|
+
/* display: none; */
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
|
|
137
|
+
@mixin horizontal_flex {
|
|
138
|
+
display: flex;
|
|
139
|
+
flex-direction: row;
|
|
140
|
+
}
|
|
141
|
+
|
|
142
|
+
@mixin vertical_flex {
|
|
143
|
+
display: flex;
|
|
144
|
+
flex-direction: column;
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
@mixin lhasa_disable_MUI_swelling {
|
|
148
|
+
font-size: $lhasa_font_size;
|
|
149
|
+
line-height: normal;
|
|
150
|
+
letter-spacing: 0em;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
@mixin center_flex {
|
|
154
|
+
text-align: center;
|
|
155
|
+
justify-content: center;
|
|
156
|
+
/* CSS is weird */
|
|
157
|
+
align-items: center;
|
|
158
|
+
}
|
|
159
|
+
|
|
160
|
+
@mixin horizontal_container {
|
|
161
|
+
@include horizontal_flex;
|
|
162
|
+
gap: $lhasa_base_padding;
|
|
163
|
+
}
|
|
164
|
+
|
|
165
|
+
.horizontal_container {
|
|
166
|
+
@include horizontal_container;
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
.horizontal_container_centered {
|
|
170
|
+
@include horizontal_container;
|
|
171
|
+
@include center_flex;
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
.children_expanded > * {
|
|
175
|
+
flex-grow: 1;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
@mixin vertical_container {
|
|
179
|
+
@include vertical_flex;
|
|
180
|
+
gap: $lhasa_base_padding;
|
|
181
|
+
}
|
|
182
|
+
|
|
183
|
+
.horizontal_toolbar {
|
|
184
|
+
@include toolbar;
|
|
185
|
+
@include horizontal_container;
|
|
186
|
+
margin-bottom: $lhasa_padding_minor;
|
|
187
|
+
margin-top: $lhasa_padding_minor;
|
|
188
|
+
}
|
|
189
|
+
|
|
190
|
+
.lhasa_dark_mode .horizontal_toolbar {
|
|
191
|
+
@include toolbar_dark;
|
|
192
|
+
}
|
|
193
|
+
|
|
194
|
+
.vertical_toolbar {
|
|
195
|
+
@include toolbar;
|
|
196
|
+
@include vertical_container;
|
|
197
|
+
/* margin-right: 2px;
|
|
198
|
+
margin-left: 2px; */
|
|
199
|
+
align-items: normal;
|
|
200
|
+
}
|
|
201
|
+
|
|
202
|
+
.lhasa_dark_mode .vertical_toolbar {
|
|
203
|
+
@include toolbar_dark;
|
|
204
|
+
}
|
|
205
|
+
|
|
206
|
+
.vertical_panel {
|
|
207
|
+
@include vertical_container;
|
|
208
|
+
@include panel;
|
|
209
|
+
}
|
|
210
|
+
|
|
211
|
+
.lhasa_dark_mode .vertical_panel {
|
|
212
|
+
@include panel_dark;
|
|
213
|
+
}
|
|
214
|
+
|
|
215
|
+
.horizontal_panel {
|
|
216
|
+
@include horizontal_container;
|
|
217
|
+
@include panel;
|
|
218
|
+
}
|
|
219
|
+
|
|
220
|
+
.lhasa_dark_mode .horizontal_panel {
|
|
221
|
+
@include panel_dark;
|
|
222
|
+
}
|
|
223
|
+
|
|
224
|
+
.lhasa_icon {
|
|
225
|
+
width: 18px;
|
|
226
|
+
}
|
|
227
|
+
|
|
228
|
+
.tool_button {
|
|
229
|
+
@include vertical_container;
|
|
230
|
+
@include center_flex;
|
|
231
|
+
@include lhasa_disable_MUI_swelling;
|
|
232
|
+
gap: $lhasa_padding_minor;
|
|
233
|
+
padding: $lhasa_base_padding;
|
|
234
|
+
}
|
|
235
|
+
|
|
236
|
+
.vertical_popup {
|
|
237
|
+
@include vertical_container;
|
|
238
|
+
@include center_flex;
|
|
239
|
+
gap: $lhasa_padding_minor * 4;
|
|
240
|
+
padding: $lhasa_base_padding * 4;
|
|
241
|
+
}
|
|
242
|
+
|
|
243
|
+
.vertical_popup_title {
|
|
244
|
+
@include horizontal_container;
|
|
245
|
+
font-size: larger;
|
|
246
|
+
font-weight: bold;
|
|
247
|
+
// todo: dark_theme
|
|
248
|
+
border-bottom: color.adjust($lhasa_toolbar_border_color, $saturation: +90%, $lightness: -0%, $alpha: +0.7) 2px solid;
|
|
249
|
+
margin-bottom: $lhasa_base_padding;
|
|
250
|
+
// border-radius: 4px;
|
|
251
|
+
// padding: $lhasa_base_padding;
|
|
252
|
+
flex-grow: 1;
|
|
253
|
+
justify-content: center;
|
|
254
|
+
align-self: normal;
|
|
255
|
+
}
|
|
256
|
+
|
|
257
|
+
.lhasa_dark_mode .vertical_popup_title {
|
|
258
|
+
border-color: color.adjust($lhasa_toolbar_border_color_dark, $saturation: +90%, $lightness: -0%, $alpha: +0.7);
|
|
259
|
+
}
|
|
260
|
+
|
|
261
|
+
.smiles_display {
|
|
262
|
+
padding: $lhasa_base_padding;
|
|
263
|
+
font-family: monospace;
|
|
264
|
+
margin-bottom: $lhasa_base_padding * 2;
|
|
265
|
+
}
|
|
266
|
+
|
|
267
|
+
.scale_display {
|
|
268
|
+
flex-grow: 1;
|
|
269
|
+
margin-left: $lhasa_base_padding * 4;
|
|
270
|
+
}
|
|
271
|
+
|
|
272
|
+
.status_display_panel,
|
|
273
|
+
.qed_panel {
|
|
274
|
+
padding: 2 * $lhasa_base_padding;
|
|
275
|
+
margin-top: $lhasa_base_padding;
|
|
276
|
+
}
|
|
277
|
+
|
|
278
|
+
.qed_property_value {
|
|
279
|
+
color: $lhasa_qed_value_color;
|
|
280
|
+
margin-left: $lhasa_padding_minor;
|
|
281
|
+
font-weight: bold;
|
|
282
|
+
}
|
|
283
|
+
|
|
284
|
+
.lhasa_dark_mode .qed_property_value {
|
|
285
|
+
color: $lhasa_qed_value_color_dark;
|
|
286
|
+
}
|
|
287
|
+
|
|
288
|
+
.qed_property_label {
|
|
289
|
+
font-weight: bolder;
|
|
290
|
+
}
|
|
291
|
+
|
|
292
|
+
.lhasa_editor input {
|
|
293
|
+
font-family: sans-serif;
|
|
294
|
+
background-color: $lhasa_background_color;
|
|
295
|
+
color: $lhasa_text_color;
|
|
296
|
+
font-size: $lhasa_font_size;
|
|
297
|
+
border-style: ridge;
|
|
298
|
+
}
|
|
299
|
+
|
|
300
|
+
.lhasa_editor.lhasa_dark_mode input {
|
|
301
|
+
background-color: $lhasa_background_color_dark;
|
|
302
|
+
// border-color: $lhasa_toolbar_border_color_dark;
|
|
303
|
+
color: $lhasa_text_color_dark;
|
|
304
|
+
// this is broken
|
|
305
|
+
// /* Apply infinite transition to block autofill styles */
|
|
306
|
+
// // transition: background-color 9999s, color 9999s;
|
|
307
|
+
}
|
|
308
|
+
|
|
309
|
+
//Fix 'internal-autofill-selected' whitish background in Chrome
|
|
310
|
+
.lhasa_editor.lhasa_dark_mode input:-webkit-autofill {
|
|
311
|
+
-webkit-box-shadow: 0 0 0px 1000px $lhasa_background_color inset !important;
|
|
312
|
+
box-shadow: 0 0 0px 1000px $lhasa_background_color_dark inset !important;
|
|
313
|
+
-webkit-text-fill-color: $lhasa_text_color_dark !important;
|
|
314
|
+
}
|
|
315
|
+
|
|
316
|
+
.smiles_input {
|
|
317
|
+
flex-grow: 1;
|
|
318
|
+
}
|
|
319
|
+
|
|
320
|
+
.lhasa_footer {
|
|
321
|
+
margin-top: 4 * $lhasa_base_padding;
|
|
322
|
+
}
|
|
323
|
+
|
|
324
|
+
.pre_render_message {
|
|
325
|
+
color: $lhasa_text_color;
|
|
326
|
+
font-weight: bold;
|
|
327
|
+
font-size: 200%;
|
|
328
|
+
background-color: $lhasa_background_color;
|
|
329
|
+
}
|
|
330
|
+
|
|
331
|
+
.lhasa_dark_mode .pre_render_message{
|
|
332
|
+
color: $lhasa_text_color_dark;
|
|
333
|
+
}
|
|
334
|
+
|
|
335
|
+
.warning_box {
|
|
336
|
+
color: darkred;
|
|
337
|
+
background-color: color.adjust(darkorange, $alpha: -0.90);
|
|
338
|
+
border: red 1px solid;
|
|
339
|
+
border-radius: 3px;
|
|
340
|
+
padding: $lhasa_base_padding;
|
|
341
|
+
}
|
|
342
|
+
|
|
343
|
+
.lhasa_dark_mode .warning_box {
|
|
344
|
+
color: red;
|
|
345
|
+
// background-color: ;
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
.text_measurement_worker_div {
|
|
349
|
+
/* Cancels out the gap in the owning container
|
|
350
|
+
so that we get nice alignment */
|
|
351
|
+
margin-left: -$lhasa_base_padding;
|
|
352
|
+
}
|
package/src/main.tsx
ADDED
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
import React from 'react'
|
|
2
|
+
import { useState, useCallback, useEffect } from 'react'
|
|
3
|
+
|
|
4
|
+
import ReactDOM from 'react-dom/client'
|
|
5
|
+
import { LhasaComponent } from './Lhasa.tsx'
|
|
6
|
+
import './index.scss'
|
|
7
|
+
// Type definitions for TS linter, auto-generated by Embind
|
|
8
|
+
import { MainModule } from './types'
|
|
9
|
+
// import { Window } from './index';
|
|
10
|
+
import { FormControl, FormControlLabel, Switch } from '@mui/material'
|
|
11
|
+
|
|
12
|
+
// const lhasa_module : MainModule = await Module();
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
|
|
18
|
+
export function App() {
|
|
19
|
+
const [showLhasa, setShowLhasa] = useState(true);
|
|
20
|
+
const [darkMode, setDarkMode] = useState(false);
|
|
21
|
+
const [isLhasaAttached, setLhasaAttached] = useState(window.LhasaModule !== undefined);
|
|
22
|
+
|
|
23
|
+
const handleLhasaAttached = useCallback(() => {
|
|
24
|
+
if (window.LhasaModule !== undefined) {
|
|
25
|
+
setLhasaAttached(true);
|
|
26
|
+
} else {
|
|
27
|
+
console.warn("Lhasa module not available... Cannot start Lhasa.")
|
|
28
|
+
}
|
|
29
|
+
}, []);
|
|
30
|
+
|
|
31
|
+
useEffect(() => {
|
|
32
|
+
document.addEventListener('lhasaModuleAttached', handleLhasaAttached);
|
|
33
|
+
return () => {
|
|
34
|
+
document.removeEventListener('lhasaModuleAttached', handleLhasaAttached)
|
|
35
|
+
};
|
|
36
|
+
}, [handleLhasaAttached]);
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
let MaybeLhasaComponent = isLhasaAttached ?
|
|
40
|
+
<LhasaComponent
|
|
41
|
+
Lhasa={window.LhasaModule}
|
|
42
|
+
show_top_panel={true}
|
|
43
|
+
// show_footer={true}
|
|
44
|
+
icons_path_prefix='icons'
|
|
45
|
+
smiles_callback={(internal_id, id_from_prop, smiles) => console.log("ID=", internal_id," SMILES=", smiles, "Id-From-Prop", id_from_prop)}
|
|
46
|
+
// Works when using `npx vite server --port 5174`
|
|
47
|
+
// Inside `vite.config.js` there is a proxy setup to redirect this to an actual bansu instance.
|
|
48
|
+
// CORS stuff is broken for localhost connections, it seems.
|
|
49
|
+
// bansu_endpoint='http://localhost:5174'
|
|
50
|
+
|
|
51
|
+
bansu_endpoint='https://www.ccp4.ac.uk/bansu'
|
|
52
|
+
data_path_prefix=''
|
|
53
|
+
dark_mode={darkMode}
|
|
54
|
+
/> : <div>
|
|
55
|
+
Lhasa module not loaded yet
|
|
56
|
+
</div>;
|
|
57
|
+
|
|
58
|
+
return (
|
|
59
|
+
<>
|
|
60
|
+
<FormControl>
|
|
61
|
+
<FormControlLabel
|
|
62
|
+
control={<Switch checked={showLhasa} onChange={(event) => setShowLhasa(event.target.checked)} />}
|
|
63
|
+
label={"Show Lhasa"}
|
|
64
|
+
/>
|
|
65
|
+
<FormControlLabel
|
|
66
|
+
control={<Switch checked={darkMode} onChange={(event) => setDarkMode(event.target.checked)} />}
|
|
67
|
+
label={"Dark Mode"}
|
|
68
|
+
/>
|
|
69
|
+
</FormControl>
|
|
70
|
+
{showLhasa ? MaybeLhasaComponent : null}
|
|
71
|
+
</>
|
|
72
|
+
)
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
ReactDOM.createRoot(document.getElementById('root')!).render(
|
|
76
|
+
<React.StrictMode>
|
|
77
|
+
<App />
|
|
78
|
+
</React.StrictMode>,
|
|
79
|
+
)
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { LinearProgress } from '@mui/material';
|
|
2
|
+
class QedPropertyInfoboxProps {
|
|
3
|
+
property_name!: string;
|
|
4
|
+
display_value: string | number | undefined;
|
|
5
|
+
progressbar_value: number | undefined;
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
export function QedPropertyInfobox(props: QedPropertyInfoboxProps) {
|
|
9
|
+
return <span className="qed_property_field">
|
|
10
|
+
<span className="qed_property_label">{props.property_name}</span>
|
|
11
|
+
<span className="qed_property_value">{props.display_value}</span>
|
|
12
|
+
{props.progressbar_value && <LinearProgress variant="determinate" value={props.progressbar_value * 100} />}
|
|
13
|
+
</span>;
|
|
14
|
+
}
|