aboutsummaryrefslogtreecommitdiff
path: root/src/client/views/nodes/LinkBox.tsx
diff options
context:
space:
mode:
Diffstat (limited to 'src/client/views/nodes/LinkBox.tsx')
-rw-r--r--src/client/views/nodes/LinkBox.tsx69
1 files changed, 45 insertions, 24 deletions
diff --git a/src/client/views/nodes/LinkBox.tsx b/src/client/views/nodes/LinkBox.tsx
index 8b6293806..7ade846e7 100644
--- a/src/client/views/nodes/LinkBox.tsx
+++ b/src/client/views/nodes/LinkBox.tsx
@@ -4,7 +4,7 @@ import { observer } from 'mobx-react';
import * as React from 'react';
import { Id } from '../../../fields/FieldSymbols';
import { DocCast, NumCast, StrCast } from '../../../fields/Types';
-import { aggregateBounds, emptyFunction, returnAlways, returnFalse, Utils } from '../../../Utils';
+import { aggregateBounds, emptyFunction, returnAlways, returnFalse, setupMoveUpEvents, Utils } from '../../../Utils';
import { DocumentManager } from '../../util/DocumentManager';
import { Transform } from '../../util/Transform';
import { CollectionFreeFormView } from '../collections/collectionFreeForm';
@@ -13,6 +13,8 @@ import { StyleProp } from '../StyleProvider';
import { ComparisonBox } from './ComparisonBox';
import { FieldView, FieldViewProps } from './FieldView';
import './LinkBox.scss';
+import { LinkDescriptionPopup } from './LinkDescriptionPopup';
+import { LinkManager } from '../../util/LinkManager';
@observer
export class LinkBox extends ViewBoxBaseComponent<FieldViewProps>() {
@@ -97,8 +99,8 @@ export class LinkBox extends ViewBoxBaseComponent<FieldViewProps>() {
) {
this.layoutDoc.x = params?.lx;
this.layoutDoc.y = params?.ty;
- this.layoutDoc._width = params.rx - params?.lx;
- this.layoutDoc._height = params?.by - params?.ty;
+ this.layoutDoc._width = Math.max(1, params.rx - params?.lx);
+ this.layoutDoc._height = Math.max(1, params?.by - params?.ty);
}
} else {
this.layoutDoc._width = Math.max(50, NumCast(this.layoutDoc._width));
@@ -108,6 +110,22 @@ export class LinkBox extends ViewBoxBaseComponent<FieldViewProps>() {
{ fireImmediately: true }
);
}
+ descriptionDown = (e: React.PointerEvent) => {
+ setupMoveUpEvents(this, e, returnFalse, returnFalse, () => {
+ LinkManager.Instance.currentLink = this.Document;
+ LinkDescriptionPopup.Instance.popupX = e.clientX;
+ LinkDescriptionPopup.Instance.popupY = e.clientY;
+ LinkDescriptionPopup.Instance.display = true;
+
+ const rect = document.body.getBoundingClientRect();
+ if (LinkDescriptionPopup.Instance.popupX + 200 > rect.width) {
+ LinkDescriptionPopup.Instance.popupX -= 190;
+ }
+ if (LinkDescriptionPopup.Instance.popupY + 100 > rect.height) {
+ LinkDescriptionPopup.Instance.popupY -= 40;
+ }
+ });
+ };
componentWillUnmount(): void {
this.disposer?.();
}
@@ -117,19 +135,21 @@ export class LinkBox extends ViewBoxBaseComponent<FieldViewProps>() {
const highlight = this._props.styleProvider?.(this.layoutDoc, this._props, StyleProp.Highlighting);
const highlightColor = highlight?.highlightIndex ? highlight?.highlightColor : undefined;
- const bez = new Bezier(this.renderProps.pts.map(p => ({ x: p[0], y: p[1] })));
- const text = bez.get(0.5);
- const linkDesc = StrCast(this.dataDoc.link_description) || 'description';
+ const { pts, lx, ty, rx, by } = this.renderProps;
+ const bez = new Bezier(pts.map(p => ({ x: p[0] - lx, y: p[1] - ty })));
+ const { x, y } = bez.get(0.5);
+ const linkDesc = StrCast(this.dataDoc.link_description) || ' ';
const strokeWidth = NumCast(this.dataDoc.stroke_width, 4);
const dash = StrCast(this.Document.stroke_dash);
const strokeDasharray = dash && Number(dash) ? String(strokeWidth * Number(dash)) : undefined;
- const { pts, lx, ty, rx, by } = this.renderProps;
+ const pointerEvents = this._props.pointerEvents?.() === 'none' ? 'none' : 'all';
+ const stroke = highlightColor ?? 'lightblue';
return (
- <div style={{ transition: 'inherit', pointerEvents: 'none', position: 'absolute', width: '100%', height: '100%' }}>
- <svg width={Math.max(100, rx - lx)} height={Math.max(100, by - ty)} style={{ transition: 'inherit', overflow: 'visible' }}>
+ <div className="linkBox">
+ <svg width={Math.max(100, rx - lx)} height={Math.max(100, by - ty)}>
<defs>
<filter x="0" y="0" width="1" height="1" id={`${this.Document[Id] + 'background'}`}>
- <feFlood floodColor={`${StrCast(this.layoutDoc._backgroundColor, 'lightblue')}`} result="bg" />
+ <feFlood floodColor={`${highlightColor ?? StrCast(this.layoutDoc._backgroundColor, 'lightblue')}`} result="bg" />
<feMerge>
<feMergeNode in="bg" />
<feMergeNode in="SourceGraphic" />
@@ -137,26 +157,27 @@ export class LinkBox extends ViewBoxBaseComponent<FieldViewProps>() {
</filter>
</defs>
<path
- className="collectionfreeformlinkview-linkLine"
style={{
pointerEvents: this._props.pointerEvents?.() === 'none' ? 'none' : 'visibleStroke', //
- stroke: highlightColor ?? 'lightblue',
+ stroke,
strokeDasharray,
strokeWidth,
- transition: 'inherit',
}}
- d={`M ${pts[1][0] - lx} ${pts[1][1] - ty} C ${pts[1][0] + pts[1][0] - pts[0][0] - lx} ${pts[1][1] + pts[1][1] - pts[0][1] - ty},
- ${pts[2][0] + pts[2][0] - pts[3][0] - lx} ${pts[2][1] + pts[2][1] - pts[3][1] - ty}, ${pts[2][0] - lx} ${pts[2][1] - ty}`}
+ d={`M ${bez.points[0].x} ${bez.points[0].y} C ${bez.points[1].x} ${bez.points[1].y},
+ ${bez.points[2].x} ${bez.points[2].y}, ${bez.points[3].x} ${bez.points[3].y}`}
/>
- <text
- filter={`url(#${this.Document[Id] + 'background'})`}
- style={{ pointerEvents: this._props.pointerEvents?.() === 'none' ? 'none' : 'all', textAnchor: 'middle', fontSize: '12', stroke: 'black' }}
- x={text.x - lx}
- y={text.y - ty}>
- <tspan>&nbsp;</tspan>
- <tspan dy="2">{linkDesc.substring(0, 50) + (linkDesc.length > 50 ? '...' : '')}</tspan>
- <tspan dy="2">&nbsp;</tspan>
- </text>
+ {!linkDesc.trim().length ? (
+ <circle r={5} onPointerDown={this.descriptionDown} style={{ fill: stroke, pointerEvents }} cx={x} cy={y} />
+ ) : (
+ <text
+ onPointerDown={this.descriptionDown} //
+ filter={`url(#${this.Document[Id] + 'background'})`}
+ style={{ pointerEvents, background: stroke }}
+ x={x}
+ y={y}>
+ <tspan style={{ background: stroke }}>&nbsp;{linkDesc.substring(0, 50) + (linkDesc.length > 50 ? '...' : '')}&nbsp;</tspan>
+ </text>
+ )}
</svg>
</div>
);