Skip to content

Commit 4c663d0

Browse files
feat(editors/publisher): filter for control blocks and DataSets (openscd#844)
* feat(editors/publisher): filter for control blocks and DataSets Initial publisher plugin allowing to filter for ReportControl, GSEControl, SampledValueControl and DataSets without showing and editing their details * test(open-scd): update snapshots
1 parent 15c2d3b commit 4c663d0

17 files changed

+1095
-0
lines changed

public/js/plugins.js

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,13 @@ export const officialPlugins = [
5555
default: true,
5656
kind: 'editor',
5757
},
58+
{
59+
name: 'Publisher',
60+
src: '/src/editors/Publisher.js',
61+
icon: 'publish',
62+
default: false,
63+
kind: 'editor',
64+
},
5865
{
5966
name: 'Open project',
6067
src: '/src/menu/OpenProject.js',

src/editors/Publisher.ts

Lines changed: 94 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,94 @@
1+
import {
2+
css,
3+
html,
4+
LitElement,
5+
property,
6+
state,
7+
TemplateResult,
8+
} from 'lit-element';
9+
import { classMap } from 'lit-html/directives/class-map';
10+
11+
import '@material/mwc-formfield';
12+
import '@material/mwc-radio';
13+
14+
import './publisher/report-control-editor.js';
15+
import './publisher/gse-control-editor.js';
16+
import './publisher/sampled-value-control-editor.js';
17+
import './publisher/data-set-editor.js';
18+
19+
/** An editor [[`plugin`]] to configure `Report`, `GOOSE`, `SampledValue` control blocks and its `DataSet` */
20+
export default class PublisherPlugin extends LitElement {
21+
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */
22+
@property({ attribute: false })
23+
doc!: XMLDocument;
24+
@state()
25+
private publisherType: 'Report' | 'GOOSE' | 'SampledValue' | 'DataSet' =
26+
'GOOSE';
27+
28+
render(): TemplateResult {
29+
return html`<div class="publishertypeselector">
30+
<mwc-formfield label="Report"
31+
><mwc-radio
32+
value="Report"
33+
?checked=${this.publisherType === 'Report'}
34+
@checked=${() => (this.publisherType = 'Report')}
35+
></mwc-radio></mwc-formfield
36+
><mwc-formfield label="GOOSE"
37+
><mwc-radio
38+
value="GOOSE"
39+
?checked=${this.publisherType === 'GOOSE'}
40+
@checked=${() => (this.publisherType = 'GOOSE')}
41+
></mwc-radio></mwc-formfield
42+
><mwc-formfield label="SampledValue"
43+
><mwc-radio
44+
value="SampledValue"
45+
?checked=${this.publisherType === 'SampledValue'}
46+
@checked=${() => (this.publisherType = 'SampledValue')}
47+
></mwc-radio></mwc-formfield
48+
><mwc-formfield label="DataSet"
49+
><mwc-radio
50+
value="DataSet"
51+
?checked=${this.publisherType === 'DataSet'}
52+
@checked=${() => (this.publisherType = 'DataSet')}
53+
></mwc-radio
54+
></mwc-formfield>
55+
</div>
56+
<report-control-editor
57+
.doc=${this.doc}
58+
class="${classMap({
59+
hidden: this.publisherType !== 'Report',
60+
})}"
61+
></report-control-editor
62+
><gse-control-editor
63+
.doc=${this.doc}
64+
class="${classMap({
65+
hidden: this.publisherType !== 'GOOSE',
66+
})}"
67+
></gse-control-editor
68+
><sampled-value-control-editor
69+
.doc=${this.doc}
70+
class="${classMap({
71+
hidden: this.publisherType !== 'SampledValue',
72+
})}"
73+
></sampled-value-control-editor
74+
><data-set-editor
75+
.doc=${this.doc}
76+
class="${classMap({
77+
hidden: this.publisherType !== 'DataSet',
78+
})}"
79+
></data-set-editor>`;
80+
}
81+
82+
static styles = css`
83+
.hidden {
84+
display: none;
85+
}
86+
87+
.publishertypeselector {
88+
margin: 4px 8px 16px;
89+
background-color: var(--mdc-theme-surface);
90+
width: calc(100% - 16px);
91+
justify-content: space-around;
92+
}
93+
`;
94+
}
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
import {
2+
css,
3+
customElement,
4+
html,
5+
LitElement,
6+
property,
7+
TemplateResult,
8+
} from 'lit-element';
9+
import { compareNames, identity } from '../../foundation.js';
10+
11+
@customElement('data-set-editor')
12+
export class DataSetEditor extends LitElement {
13+
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */
14+
@property({ attribute: false })
15+
doc!: XMLDocument;
16+
17+
renderList(): TemplateResult {
18+
return html`<filtered-list
19+
>${Array.from(this.doc.querySelectorAll('IED'))
20+
.sort(compareNames)
21+
.flatMap(ied => {
22+
const ieditem = html`<mwc-list-item
23+
class="listitem header"
24+
noninteractive
25+
graphic="icon"
26+
>
27+
<span>${ied.getAttribute('name')}</span>
28+
<mwc-icon slot="graphic">developer_board</mwc-icon>
29+
</mwc-list-item>
30+
<li divider role="separator"></li>`;
31+
32+
const dataSets = Array.from(ied.querySelectorAll('DataSet')).map(
33+
reportCb =>
34+
html`<mwc-list-item twoline value="${identity(reportCb)}"
35+
><span>${reportCb.getAttribute('name')}</span
36+
><span slot="secondary">${identity(reportCb)}</span>
37+
</mwc-list-item>`
38+
);
39+
40+
return [ieditem, ...dataSets];
41+
})}</filtered-list
42+
>`;
43+
}
44+
45+
render(): TemplateResult {
46+
return html`${this.renderList()}`;
47+
}
48+
49+
static styles = css`
50+
filtered-list {
51+
margin: 4px 8px 16px;
52+
background-color: var(--mdc-theme-surface);
53+
}
54+
55+
.listitem.header {
56+
font-weight: 500;
57+
}
58+
`;
59+
}
Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
import {
2+
css,
3+
customElement,
4+
html,
5+
LitElement,
6+
property,
7+
TemplateResult,
8+
} from 'lit-element';
9+
10+
import '@material/mwc-list/mwc-list-item';
11+
import '@material/mwc-icon';
12+
13+
import '../../filtered-list.js';
14+
import { compareNames, identity } from '../../foundation.js';
15+
import { gooseIcon } from '../../icons/icons.js';
16+
17+
@customElement('gse-control-editor')
18+
export class GseControlEditor extends LitElement {
19+
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */
20+
@property({ attribute: false })
21+
doc!: XMLDocument;
22+
23+
renderList(): TemplateResult {
24+
return html`<filtered-list
25+
>${Array.from(this.doc.querySelectorAll('IED'))
26+
.sort(compareNames)
27+
.flatMap(ied => {
28+
const ieditem = html`<mwc-list-item
29+
class="listitem header"
30+
noninteractive
31+
graphic="icon"
32+
>
33+
<span>${ied.getAttribute('name')}</span>
34+
<mwc-icon slot="graphic">developer_board</mwc-icon>
35+
</mwc-list-item>
36+
<li divider role="separator"></li>`;
37+
38+
const gseControls = Array.from(
39+
ied.querySelectorAll('GSEControl')
40+
).map(
41+
reportCb =>
42+
html`<mwc-list-item
43+
twoline
44+
value="${identity(reportCb)}"
45+
graphic="icon"
46+
><span>${reportCb.getAttribute('name')}</span
47+
><span slot="secondary">${identity(reportCb)}</span>
48+
<mwc-icon slot="graphic">${gooseIcon}</mwc-icon>
49+
</mwc-list-item>`
50+
);
51+
52+
return [ieditem, ...gseControls];
53+
})}</filtered-list
54+
>`;
55+
}
56+
57+
render(): TemplateResult {
58+
return html`${this.renderList()}`;
59+
}
60+
61+
static styles = css`
62+
filtered-list {
63+
margin: 4px 8px 16px;
64+
background-color: var(--mdc-theme-surface);
65+
}
66+
67+
.listitem.header {
68+
font-weight: 500;
69+
}
70+
`;
71+
}
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
import {
2+
css,
3+
customElement,
4+
html,
5+
LitElement,
6+
property,
7+
TemplateResult,
8+
} from 'lit-element';
9+
10+
import '@material/mwc-list/mwc-list-item';
11+
import '@material/mwc-icon';
12+
13+
import '../../filtered-list.js';
14+
import { compareNames, identity } from '../../foundation.js';
15+
import { reportIcon } from '../../icons/icons.js';
16+
17+
@customElement('report-control-editor')
18+
export class ReportControlEditor extends LitElement {
19+
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */
20+
@property({ attribute: false })
21+
doc!: XMLDocument;
22+
23+
renderList(): TemplateResult {
24+
return html`<filtered-list
25+
>${Array.from(this.doc.querySelectorAll('IED'))
26+
.sort(compareNames)
27+
.flatMap(ied => {
28+
const ieditem = html`<mwc-list-item
29+
class="listitem header"
30+
noninteractive
31+
graphic="icon"
32+
>
33+
<span>${ied.getAttribute('name')}</span>
34+
<mwc-icon slot="graphic">developer_board</mwc-icon>
35+
</mwc-list-item>
36+
<li divider role="separator"></li>`;
37+
38+
const reports = Array.from(ied.querySelectorAll('ReportControl')).map(
39+
reportCb =>
40+
html`<mwc-list-item
41+
twoline
42+
value="${identity(reportCb)}"
43+
graphic="icon"
44+
><span>${reportCb.getAttribute('name')}</span
45+
><span slot="secondary">${identity(reportCb)}</span>
46+
<mwc-icon slot="graphic">${reportIcon}</mwc-icon>
47+
</mwc-list-item>`
48+
);
49+
50+
return [ieditem, ...reports];
51+
})}</filtered-list
52+
>`;
53+
}
54+
55+
render(): TemplateResult {
56+
return html`${this.renderList()}`;
57+
}
58+
59+
static styles = css`
60+
filtered-list {
61+
margin: 4px 8px 16px;
62+
background-color: var(--mdc-theme-surface);
63+
}
64+
65+
.listitem.header {
66+
font-weight: 500;
67+
}
68+
`;
69+
}
Lines changed: 71 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,71 @@
1+
import {
2+
css,
3+
customElement,
4+
html,
5+
LitElement,
6+
property,
7+
TemplateResult,
8+
} from 'lit-element';
9+
10+
import '@material/mwc-list/mwc-list-item';
11+
import '@material/mwc-icon';
12+
13+
import '../../filtered-list.js';
14+
import { compareNames, identity } from '../../foundation.js';
15+
import { smvIcon } from '../../icons/icons.js';
16+
17+
@customElement('sampled-value-control-editor')
18+
export class SampledValueControlEditor extends LitElement {
19+
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */
20+
@property({ attribute: false })
21+
doc!: XMLDocument;
22+
23+
renderList(): TemplateResult {
24+
return html`<filtered-list
25+
>${Array.from(this.doc.querySelectorAll('IED'))
26+
.sort(compareNames)
27+
.flatMap(ied => {
28+
const ieditem = html`<mwc-list-item
29+
class="listitem header"
30+
noninteractive
31+
graphic="icon"
32+
>
33+
<span>${ied.getAttribute('name')}</span>
34+
<mwc-icon slot="graphic">developer_board</mwc-icon>
35+
</mwc-list-item>
36+
<li divider role="separator"></li>`;
37+
38+
const sampledValueControls = Array.from(
39+
ied.querySelectorAll('SampledValueControl')
40+
).map(
41+
reportCb =>
42+
html`<mwc-list-item
43+
twoline
44+
value="${identity(reportCb)}"
45+
graphic="icon"
46+
><span>${reportCb.getAttribute('name')}</span
47+
><span slot="secondary">${identity(reportCb)}</span>
48+
<mwc-icon slot="graphic">${smvIcon}</mwc-icon>
49+
</mwc-list-item>`
50+
);
51+
52+
return [ieditem, ...sampledValueControls];
53+
})}</filtered-list
54+
>`;
55+
}
56+
57+
render(): TemplateResult {
58+
return html`${this.renderList()}`;
59+
}
60+
61+
static styles = css`
62+
filtered-list {
63+
margin: 4px 8px 16px;
64+
background-color: var(--mdc-theme-surface);
65+
}
66+
67+
.listitem.header {
68+
font-weight: 500;
69+
}
70+
`;
71+
}

0 commit comments

Comments
 (0)