-
Notifications
You must be signed in to change notification settings - Fork 39
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
feat(editors/ied): add read only data model structure (#423)
* Added IED Container * Added tests * Added Access Point container * Added Server container * Added LDevice container * Added LN Container * Added DO container * Fixing unit tests IED container * Fixing Unit tests AccessPoint container * Fixing Unit tests Server container * Fix unit tests LDevice container * Added padding * fix broken test * Fixing LN container unit tests * Added IED drop down * Small addition * Added integration test for IED filter * Small refactoring * IED list is now ordered alphabetically * Refactoring * Added check for available IEDs * First batch of review adjustments * Second batch of review stuff * Some more refactoring * Batch review comments * Batch review comments * refactor(editors/IED): add german translation * feat(editors/ied): add DO elements to IED editor (#454) * Added DO/SDO elements * Added DO/SDO/DOI/SDI * Added unit tests ln-container * Made methods private in ln-container * Added do-container snapshot tests * Added batch of do-container unit tests * Review comments Co-authored-by: Rob Tjalma <rob@tjalma.com> * Added basic DA container for DA/DAI show * Added BDA container * Added value css * Added Enum container * Refactoring * Refactoring + Adding Unit Tests * Added Enum Tests * Small refactoring * First review comments + Added toggle action * Bugfix when showing DA data * Small refactoring * Added toggle test for ln-container * refactor(ied/da-container,do-container): code improvements * Added consistent toggle functionality * Added da container unit tests * Added da container unit tests * Small typo * Revert browserLogs to false Co-authored-by: Jakob Vogelsang <jakob.vogelsang@omicronenergy.com> Co-authored-by: Jakob Vogelsang <jakob-vogelsang@posteo.de>
- Loading branch information
1 parent
dfae9b0
commit fa15c7a
Showing
38 changed files
with
2,268 additions
and
91 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,98 @@ | ||
import { css, html, LitElement, property, query, state, TemplateResult } from 'lit-element'; | ||
|
||
import '@material/mwc-fab'; | ||
import '@material/mwc-select'; | ||
import '@material/mwc-list/mwc-list-item'; | ||
|
||
import '../zeroline-pane.js'; | ||
import './ied/ied-container.js' | ||
|
||
import { translate } from 'lit-translate'; | ||
import { Select } from '@material/mwc-select'; | ||
import { SingleSelectedEvent } from '@material/mwc-list/mwc-list-foundation'; | ||
import { compareNames, getDescriptionAttribute, getNameAttribute } from '../foundation.js'; | ||
|
||
/** An editor [[`plugin`]] for editing the `IED` section. */ | ||
export default class IedPlugin extends LitElement { | ||
/** The document being edited as provided to plugins by [[`OpenSCD`]]. */ | ||
@property() | ||
doc!: XMLDocument; | ||
|
||
/** Query holding the current selected IEDs. */ | ||
@state() | ||
currentSelectedIEDs = ':root > IED'; | ||
|
||
@query('#iedSelect') iedSelector?: Select; | ||
|
||
private get alphabeticOrderedIeds() : Element[] { | ||
return Array.from(this.doc?.querySelectorAll(':root > IED')) | ||
.sort((a,b) => compareNames(a,b)); | ||
} | ||
|
||
/** | ||
* When selecting drop down, update the search query. | ||
* Because an event only returns an index, we need to retrieve the | ||
* actual IED before getting the actual value (in this case the name). | ||
*/ | ||
private onSelect(event: SingleSelectedEvent): void { | ||
const ied = this.alphabeticOrderedIeds[event.detail.index]; | ||
this.currentSelectedIEDs = `:root > IED[name="${getNameAttribute(ied)}"]`; | ||
} | ||
|
||
render(): TemplateResult { | ||
return this.doc?.querySelector(':root > IED') | ||
? html`<section> | ||
<mwc-select | ||
id="iedSelect" | ||
label="${translate("iededitor.searchHelper")}" | ||
@selected=${this.onSelect}> | ||
${this.alphabeticOrderedIeds.map( | ||
ied => | ||
html`<mwc-list-item | ||
?selected=${ied == this.alphabeticOrderedIeds[0]} | ||
value="${getNameAttribute(ied)}" | ||
>${getNameAttribute(ied)} ${ied.hasAttribute('desc') ? translate('iededitor.searchHelperDesc', { | ||
description: getDescriptionAttribute(ied)!, | ||
}) : ''} | ||
</mwc-list-item>` | ||
)} | ||
</mwc-select> | ||
${Array.from(this.doc?.querySelectorAll(this.currentSelectedIEDs)).map( | ||
ied => html`<ied-container | ||
.element=${ied} | ||
></ied-container>` | ||
)}</section>` | ||
: html`<h1> | ||
<span style="color: var(--base1)" | ||
>${translate('iededitor.missing')}</span | ||
> | ||
</h1>`; | ||
} | ||
|
||
static styles = css` | ||
:host { | ||
width: 100vw; | ||
} | ||
section { | ||
padding: 8px 12px 16px; | ||
} | ||
#iedSelect { | ||
width: 35vw; | ||
padding-bottom: 20px; | ||
} | ||
h1 { | ||
color: var(--mdc-theme-on-surface); | ||
font-family: 'Roboto', sans-serif; | ||
font-weight: 300; | ||
overflow: hidden; | ||
white-space: nowrap; | ||
text-overflow: ellipsis; | ||
margin: 0px; | ||
line-height: 48px; | ||
padding-left: 0.3em; | ||
} | ||
`; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,38 @@ | ||
import { | ||
css, | ||
customElement, | ||
html, | ||
LitElement, | ||
property, | ||
TemplateResult, | ||
} from 'lit-element'; | ||
|
||
import '../../action-pane.js'; | ||
import './server-container.js' | ||
import { nothing } from 'lit-html'; | ||
import { getDescriptionAttribute, getNameAttribute } from '../../foundation.js'; | ||
|
||
/** [[`IED`]] plugin subeditor for editing `AccessPoint` element. */ | ||
@customElement('access-point-container') | ||
export class AccessPointContainer extends LitElement { | ||
@property({ attribute: false }) | ||
element!: Element; | ||
|
||
private header(): TemplateResult { | ||
const name = getNameAttribute(this.element); | ||
const desc = getDescriptionAttribute(this.element); | ||
|
||
return html`${name}${desc ? html` — ${desc}` : nothing}`; | ||
} | ||
|
||
render(): TemplateResult { | ||
return html`<action-pane .label="${this.header()}"> | ||
${Array.from(this.element.querySelectorAll(':scope > Server')).map( | ||
server => html`<server-container | ||
.element=${server} | ||
></server-container>`)} | ||
</action-pane>`; | ||
} | ||
|
||
static styles = css``; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,116 @@ | ||
import { | ||
css, | ||
customElement, | ||
html, | ||
LitElement, | ||
property, | ||
query, | ||
TemplateResult, | ||
} from 'lit-element'; | ||
import { nothing } from 'lit-html'; | ||
import { translate } from 'lit-translate'; | ||
|
||
import '@material/mwc-icon-button-toggle'; | ||
import { IconButtonToggle } from '@material/mwc-icon-button-toggle'; | ||
|
||
import '../../action-pane.js'; | ||
import { getNameAttribute } from '../../foundation.js'; | ||
|
||
/** [[`IED`]] plugin subeditor for editing `(B)DA` element. */ | ||
@customElement('da-container') | ||
export class DAContainer extends LitElement { | ||
/** | ||
* The DA itself. | ||
*/ | ||
@property({ attribute: false }) | ||
element!: Element; | ||
|
||
/** | ||
* The optional DAI of this (B)DA. | ||
*/ | ||
@property({ attribute: false }) | ||
instanceElement!: Element; | ||
|
||
@query('#toggleButton') toggleButton: IconButtonToggle | undefined; | ||
|
||
private header(): TemplateResult { | ||
const name = getNameAttribute(this.element); | ||
const bType = this.element!.getAttribute('bType') ?? nothing; | ||
|
||
if (this.instanceElement) { | ||
return html`<b>${name}</b> — ${bType}`; | ||
} else { | ||
return html`${name} — ${bType}`; | ||
} | ||
} | ||
|
||
/** | ||
* Rendering an optional value of this (B)DA container. | ||
* If there is a DAI, it get's priority on top of (B)DA values. | ||
* @returns TemplateResult containing the value of the instance, element or nothing. | ||
*/ | ||
private renderValue(): TemplateResult { | ||
if (this.instanceElement) { | ||
return html`${this.getValueElement(this.instanceElement)?.textContent}` | ||
} | ||
|
||
return html`${this.getValueElement(this.element)?.textContent}`; | ||
} | ||
|
||
/** | ||
* Get the 'Val' element of another element. | ||
* @param element - The element to search for an 'Val' element. | ||
* @returns the 'Val' element, or null if not found. | ||
*/ | ||
private getValueElement(element: Element): Element | null { | ||
return element.querySelector('Val') ?? null; | ||
} | ||
|
||
/** | ||
* Get the nested (B)DA element(s) if available. | ||
* @returns The nested (B)DA element(s) of this (B)DA container. | ||
*/ | ||
private getBDAElements(): Element[] { | ||
const type = this.element!.getAttribute('type') ?? undefined; | ||
const doType = this.element!.closest('SCL')!.querySelector(`:root > DataTypeTemplates > DAType[id="${type}"]`); | ||
if (doType != null) { | ||
return Array.from(doType!.querySelectorAll(':scope > BDA')) | ||
} | ||
return []; | ||
} | ||
|
||
render(): TemplateResult { | ||
const bType = this.element!.getAttribute('bType'); | ||
|
||
return html`<action-pane .label="${this.header()}" icon="${this.instanceElement != null ? 'done' : ''}"> | ||
${bType == 'Struct' ? html`<abbr slot="action" title="${translate('iededitor.toggleChildElements')}"> | ||
<mwc-icon-button-toggle | ||
id="toggleButton" | ||
onIcon="keyboard_arrow_up" | ||
offIcon="keyboard_arrow_down" | ||
@click=${() => this.requestUpdate()} | ||
></mwc-icon-button-toggle> | ||
</abbr>` : nothing} | ||
<h6>${this.renderValue()}</h6> | ||
${this.toggleButton?.on && bType == 'Struct' ? this.getBDAElements().map(element => | ||
html`<da-container | ||
.element=${element}> | ||
</da-container>`) : nothing} | ||
</action-pane> | ||
`; | ||
} | ||
|
||
static styles = css` | ||
h6 { | ||
color: var(--mdc-theme-on-surface); | ||
font-family: 'Roboto', sans-serif; | ||
font-weight: 500; | ||
font-size: 0.8em; | ||
overflow: hidden; | ||
white-space: nowrap; | ||
text-overflow: ellipsis; | ||
margin: 0px; | ||
padding-left: 0.3em; | ||
} | ||
`; | ||
} |
Oops, something went wrong.