@kieler/klighd-core
Version:
Core KLighD diagram visualization with Sprotty
94 lines (89 loc) • 3.4 kB
text/typescript
/*
* KIELER - Kiel Integrated Environment for Layout Eclipse RichClient
*
* http://rtsys.informatik.uni-kiel.de/kieler
*
* Copyright 2021-2023 by
* + Kiel University
* + Department of Computer Science
* + Real-Time and Embedded Systems Group
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* SPDX-License-Identifier: EPL-2.0
*/
import { SKGraphElement } from '@kieler/klighd-interactive/lib/constraint-classes'
import { injectable } from 'inversify'
import { IPopupModelProvider } from 'sprotty'
import {
HtmlRoot as HtmlRootSchema,
PreRenderedElement as PreRenderedElementSchema,
RequestPopupModelAction,
SModelElement as SModelElementSchema,
SModelRoot as SModelRootSchema,
} from 'sprotty-protocol'
import { isSKGraphElement } from '../skgraph-models'
import { findRendering } from '../skgraph-utils'
import { RequestKlighdPopupModelAction } from './hover'
/* global SVGElement */
/** Provide PopupModels created from SKGraphElements. */
()
export class PopupModelProvider implements IPopupModelProvider {
getPopupModel(request: RequestPopupModelAction, elementSchema?: SModelElementSchema): SModelRootSchema | undefined {
if (
elementSchema &&
RequestKlighdPopupModelAction.isThisAction(request) &&
isSKGraphElement(request.parent) &&
request.element !== undefined
) {
const tooltip = this.findTooltip(request.parent, request.element)
if (tooltip) {
const escapedTooltip = this.escapeHtml(tooltip)
return <HtmlRootSchema>{
type: 'html',
id: 'popup',
children: [
<PreRenderedElementSchema>{
type: 'pre-rendered',
id: 'popup-body',
code: `<div class="klighd-popup">${escapedTooltip}</div>`,
},
],
canvasBounds: request.bounds,
}
}
}
return undefined
}
/**
* Finds the tooltip defined in the SKGraphElement in its rendering with the given ID.
* @param element The SKGraphElement to look in.
* @param svgElement The SVG element representing the KRendering.
*/
protected findTooltip(element: SKGraphElement, svgElement: SVGElement): string | undefined {
if (element.properties['klighd.tooltip'] as string) {
return element.properties['klighd.tooltip'] as string
}
const rendering = findRendering(element, svgElement)
if (rendering) {
return rendering.properties['klighd.tooltip'] as string
}
return undefined
}
/**
* Escapes the given string to prevent XSS attacks and to let it appear correctly in HTML.
* @param unsafe The string to escape.
* @returns The escaped string.
*/
private escapeHtml(unsafe: string): string {
return unsafe
.replace(/&/g, '&')
.replace(/</g, '<')
.replace(/>/g, '>')
.replace(/"/g, '"')
.replace(/'/g, ''')
.replace(/\n/g, '<br/>')
}
}