mirror of
https://github.com/GNS3/gns3-web-ui.git
synced 2025-01-31 00:23:57 +00:00
Reimplementation of adding text
This commit is contained in:
parent
78df22fae4
commit
92d6c8e411
@ -23,6 +23,7 @@ import { MapSettingsManager } from '../../managers/map-settings-manager';
|
|||||||
import { TextEditingTool } from '../../tools/text-editing-tool';
|
import { TextEditingTool } from '../../tools/text-editing-tool';
|
||||||
import { TextAddingComponent } from '../text-adding/text-adding.component';
|
import { TextAddingComponent } from '../text-adding/text-adding.component';
|
||||||
import { Server } from '../../../models/server';
|
import { Server } from '../../../models/server';
|
||||||
|
import { TextAddingTool } from '../../tools/text-adding-tool';
|
||||||
|
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
@ -66,6 +67,7 @@ export class D3MapComponent implements OnInit, OnChanges, OnDestroy {
|
|||||||
protected interfaceLabelWidget: InterfaceLabelWidget,
|
protected interfaceLabelWidget: InterfaceLabelWidget,
|
||||||
protected selectionToolWidget: SelectionTool,
|
protected selectionToolWidget: SelectionTool,
|
||||||
protected movingToolWidget: MovingTool,
|
protected movingToolWidget: MovingTool,
|
||||||
|
protected textAddingToolWidget: TextAddingTool,
|
||||||
protected textEditingToolWidget: TextEditingTool,
|
protected textEditingToolWidget: TextEditingTool,
|
||||||
public graphLayout: GraphLayout,
|
public graphLayout: GraphLayout,
|
||||||
) {
|
) {
|
||||||
@ -91,6 +93,12 @@ export class D3MapComponent implements OnInit, OnChanges, OnDestroy {
|
|||||||
this.mapChangeDetectorRef.detectChanges();
|
this.mapChangeDetectorRef.detectChanges();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Input('text-adding-tool')
|
||||||
|
set textAddingTool(value){
|
||||||
|
this.textAddingToolWidget.setEnabled(value);
|
||||||
|
this.mapChangeDetectorRef.detectChanges();
|
||||||
|
}
|
||||||
|
|
||||||
@Input('text-editing-tool')
|
@Input('text-editing-tool')
|
||||||
set textEditingTool(value){
|
set textEditingTool(value){
|
||||||
this.textEditingToolWidget.setEnabled(value);
|
this.textEditingToolWidget.setEnabled(value);
|
||||||
|
@ -1,24 +1,31 @@
|
|||||||
import { Component, OnInit } from "@angular/core";
|
import { Component, OnInit, OnDestroy } from "@angular/core";
|
||||||
import { select } from 'd3-selection';
|
import { select } from 'd3-selection';
|
||||||
import { Context } from "../../models/context";
|
import { Context } from "../../models/context";
|
||||||
|
import { TextAddingTool } from '../../tools/text-adding-tool';
|
||||||
|
import { Subscription } from 'rxjs';
|
||||||
|
import { DrawingsEventSource } from '../../events/drawings-event-source';
|
||||||
|
import { TextAddedDataEvent } from '../../events/event-source';
|
||||||
|
|
||||||
@Component({
|
@Component({
|
||||||
selector: 'app-text-adding',
|
selector: 'app-text-adding',
|
||||||
template: `<ng-content></ng-content>`,
|
template: `<ng-content></ng-content>`,
|
||||||
styleUrls: ['./text-adding.component.scss']
|
styleUrls: ['./text-adding.component.scss']
|
||||||
})
|
})
|
||||||
export class TextAddingComponent implements OnInit {
|
export class TextAddingComponent implements OnInit, OnDestroy{
|
||||||
public isEnabled: boolean = true;
|
textAddingFinished: Subscription;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
private context: Context
|
private textAddingTool: TextAddingTool,
|
||||||
|
private drawingEventSource: DrawingsEventSource
|
||||||
){}
|
){}
|
||||||
|
|
||||||
ngOnInit(){
|
ngOnInit() {
|
||||||
|
this.textAddingFinished = this.textAddingTool.addingFinished.subscribe((evt: TextAddedDataEvent) => {
|
||||||
|
this.drawingEventSource.textAdded.emit(evt);
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
addingTextSelected(){
|
ngOnDestroy() {
|
||||||
//here will be moved addText in projectMapComponent
|
this.textAddingFinished.unsubscribe();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -23,10 +23,6 @@ export class TextEditingComponent implements OnInit, OnDestroy{
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
onTextAddingChosen() {
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
ngOnDestroy() {
|
ngOnDestroy() {
|
||||||
this.textEditingFinished.unsubscribe();
|
this.textEditingFinished.unsubscribe();
|
||||||
}
|
}
|
||||||
|
@ -5,6 +5,7 @@ import { DrawingsWidget } from './widgets/drawings';
|
|||||||
import { DrawingLineWidget } from './widgets/drawing-line';
|
import { DrawingLineWidget } from './widgets/drawing-line';
|
||||||
import { SelectionTool } from './tools/selection-tool';
|
import { SelectionTool } from './tools/selection-tool';
|
||||||
import { MovingTool } from './tools/moving-tool';
|
import { MovingTool } from './tools/moving-tool';
|
||||||
|
import {TextAddingTool} from './tools/text-adding-tool';
|
||||||
import {TextEditingTool} from './tools/text-editing-tool';
|
import {TextEditingTool} from './tools/text-editing-tool';
|
||||||
import { LayersWidget } from './widgets/layers';
|
import { LayersWidget } from './widgets/layers';
|
||||||
import { LinkWidget } from './widgets/link';
|
import { LinkWidget } from './widgets/link';
|
||||||
@ -29,6 +30,7 @@ export const D3_MAP_IMPORTS = [
|
|||||||
DrawingLineWidget,
|
DrawingLineWidget,
|
||||||
SelectionTool,
|
SelectionTool,
|
||||||
MovingTool,
|
MovingTool,
|
||||||
|
TextAddingTool,
|
||||||
TextEditingTool,
|
TextEditingTool,
|
||||||
LayersWidget,
|
LayersWidget,
|
||||||
LinkWidget,
|
LinkWidget,
|
||||||
|
@ -1,5 +1,5 @@
|
|||||||
import { Injectable, EventEmitter } from "@angular/core";
|
import { Injectable, EventEmitter } from "@angular/core";
|
||||||
import { DraggedDataEvent, ResizedDataEvent } from "./event-source";
|
import { DraggedDataEvent, ResizedDataEvent, TextAddedDataEvent, TextEditedDataEvent } from "./event-source";
|
||||||
import { MapDrawing } from "../models/map/map-drawing";
|
import { MapDrawing } from "../models/map/map-drawing";
|
||||||
|
|
||||||
|
|
||||||
@ -7,5 +7,6 @@ import { MapDrawing } from "../models/map/map-drawing";
|
|||||||
export class DrawingsEventSource {
|
export class DrawingsEventSource {
|
||||||
public dragged = new EventEmitter<DraggedDataEvent<MapDrawing>>();
|
public dragged = new EventEmitter<DraggedDataEvent<MapDrawing>>();
|
||||||
public resized = new EventEmitter<ResizedDataEvent<MapDrawing>>();
|
public resized = new EventEmitter<ResizedDataEvent<MapDrawing>>();
|
||||||
public textEdited = new EventEmitter<any>();
|
public textAdded = new EventEmitter<TextAddedDataEvent>();
|
||||||
|
public textEdited = new EventEmitter<TextEditedDataEvent>();
|
||||||
}
|
}
|
||||||
|
@ -17,7 +17,7 @@ export class ResizedDataEvent<T> {
|
|||||||
public y: number,
|
public y: number,
|
||||||
public width: number,
|
public width: number,
|
||||||
public height: number
|
public height: number
|
||||||
) {}
|
) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ClickedDataEvent<T> {
|
export class ClickedDataEvent<T> {
|
||||||
@ -28,6 +28,14 @@ export class ClickedDataEvent<T> {
|
|||||||
) {}
|
) {}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export class TextAddedDataEvent {
|
||||||
|
constructor(
|
||||||
|
public savedText: string,
|
||||||
|
public x: number,
|
||||||
|
public y: number
|
||||||
|
) {}
|
||||||
|
}
|
||||||
|
|
||||||
export class TextEditedDataEvent {
|
export class TextEditedDataEvent {
|
||||||
constructor(
|
constructor(
|
||||||
public textDrawingId: string,
|
public textDrawingId: string,
|
||||||
|
0
src/app/cartography/tools/text-adding-tool.spec.ts
Normal file
0
src/app/cartography/tools/text-adding-tool.spec.ts
Normal file
62
src/app/cartography/tools/text-adding-tool.ts
Normal file
62
src/app/cartography/tools/text-adding-tool.ts
Normal file
@ -0,0 +1,62 @@
|
|||||||
|
import { Injectable, EventEmitter } from "@angular/core";
|
||||||
|
import { TextAddedDataEvent } from '../events/event-source';
|
||||||
|
|
||||||
|
|
||||||
|
@Injectable()
|
||||||
|
export class TextAddingTool {
|
||||||
|
private enabled;
|
||||||
|
private listener: Function;
|
||||||
|
public addingFinished = new EventEmitter<any>();
|
||||||
|
|
||||||
|
public setEnabled(enabled){
|
||||||
|
this.enabled = enabled;
|
||||||
|
if (enabled){
|
||||||
|
this.activate();
|
||||||
|
} else {
|
||||||
|
this.deactivate();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private deactivate(){
|
||||||
|
var map = document.getElementsByClassName('map')[0];
|
||||||
|
map.removeEventListener('click', this.listener as EventListenerOrEventListenerObject);
|
||||||
|
}
|
||||||
|
|
||||||
|
private activate(){
|
||||||
|
var map = document.getElementsByClassName('map')[0];
|
||||||
|
|
||||||
|
let addTextListener = (event: MouseEvent) => {
|
||||||
|
|
||||||
|
var div = document.createElement('div');
|
||||||
|
div.style.width = "fit-content";
|
||||||
|
div.style.left = event.clientX.toString() + 'px';
|
||||||
|
div.style.top = (event.clientY).toString() + 'px';
|
||||||
|
div.style.position = "absolute";
|
||||||
|
div.style.zIndex = "99";
|
||||||
|
|
||||||
|
div.style.fontFamily = "Noto Sans";
|
||||||
|
div.style.fontSize = "11pt";
|
||||||
|
div.style.fontWeight = "bold";
|
||||||
|
div.style.color = "#000000";
|
||||||
|
|
||||||
|
div.setAttribute("contenteditable", "true");
|
||||||
|
|
||||||
|
document.body.appendChild(div);
|
||||||
|
div.innerText = "";
|
||||||
|
div.focus();
|
||||||
|
document.body.style.cursor = "text";
|
||||||
|
|
||||||
|
div.addEventListener("focusout", () => {
|
||||||
|
let savedText = div.innerText;
|
||||||
|
this.addingFinished.emit(new TextAddedDataEvent(savedText, event.clientX, event.clientY));
|
||||||
|
|
||||||
|
document.body.style.cursor = "default";
|
||||||
|
div.remove();
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
map.removeEventListener('click', this.listener as EventListenerOrEventListenerObject);
|
||||||
|
this.listener = addTextListener;
|
||||||
|
map.addEventListener('click', this.listener as EventListenerOrEventListenerObject, {once : true});
|
||||||
|
}
|
||||||
|
}
|
@ -11,6 +11,7 @@
|
|||||||
[selection-tool]="tools.selection"
|
[selection-tool]="tools.selection"
|
||||||
[moving-tool]="tools.moving"
|
[moving-tool]="tools.moving"
|
||||||
[text-editing-tool]="tools.text_editing"
|
[text-editing-tool]="tools.text_editing"
|
||||||
|
[text-adding-tool]="drawTools.isAddingTextChosen"
|
||||||
[draw-link-tool]="tools.draw_link"
|
[draw-link-tool]="tools.draw_link"
|
||||||
[readonly]="inReadOnlyMode"
|
[readonly]="inReadOnlyMode"
|
||||||
(nodeDragged)="onNodeDragged($event)"
|
(nodeDragged)="onNodeDragged($event)"
|
||||||
|
@ -26,7 +26,7 @@ import { MapChangeDetectorRef } from '../../cartography/services/map-change-dete
|
|||||||
import { NodeContextMenu } from '../../cartography/events/nodes';
|
import { NodeContextMenu } from '../../cartography/events/nodes';
|
||||||
import { MapLinkCreated } from '../../cartography/events/links';
|
import { MapLinkCreated } from '../../cartography/events/links';
|
||||||
import { NodeWidget } from '../../cartography/widgets/node';
|
import { NodeWidget } from '../../cartography/widgets/node';
|
||||||
import { DraggedDataEvent, ResizedDataEvent, TextEditedDataEvent } from '../../cartography/events/event-source';
|
import { DraggedDataEvent, ResizedDataEvent, TextEditedDataEvent, TextAddedDataEvent } from '../../cartography/events/event-source';
|
||||||
import { DrawingService } from '../../services/drawing.service';
|
import { DrawingService } from '../../services/drawing.service';
|
||||||
import { MapNodeToNodeConverter } from '../../cartography/converters/map/map-node-to-node-converter';
|
import { MapNodeToNodeConverter } from '../../cartography/converters/map/map-node-to-node-converter';
|
||||||
import { NodesEventSource } from '../../cartography/events/nodes-event-source';
|
import { NodesEventSource } from '../../cartography/events/nodes-event-source';
|
||||||
@ -194,6 +194,10 @@ export class ProjectMapComponent implements OnInit, OnDestroy {
|
|||||||
this.drawingsEventSource.resized.subscribe((evt) => this.onDrawingResized(evt))
|
this.drawingsEventSource.resized.subscribe((evt) => this.onDrawingResized(evt))
|
||||||
);
|
);
|
||||||
|
|
||||||
|
this.subscriptions.push(
|
||||||
|
this.drawingsEventSource.textAdded.subscribe((evt) => this.onTextAdded(evt))
|
||||||
|
);
|
||||||
|
|
||||||
this.subscriptions.push(
|
this.subscriptions.push(
|
||||||
this.drawingsEventSource.textEdited.subscribe((evt) => this.onTextEdited(evt))
|
this.drawingsEventSource.textEdited.subscribe((evt) => this.onTextEdited(evt))
|
||||||
);
|
);
|
||||||
@ -352,6 +356,21 @@ export class ProjectMapComponent implements OnInit, OnDestroy {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public onTextAdded(evt: TextAddedDataEvent){
|
||||||
|
this.resetDrawToolChoice();
|
||||||
|
|
||||||
|
let drawing = this.getDrawingMock("text", evt.savedText);
|
||||||
|
(drawing.element as TextElement).text = evt.savedText;
|
||||||
|
let svgText = this.mapDrawingToSvgConverter.convert(drawing);
|
||||||
|
|
||||||
|
this.drawingService
|
||||||
|
.add(this.server, this.project.project_id, evt.x - this.mapChild.context.getZeroZeroTransformationPoint().x, evt.y - this.mapChild.context.getZeroZeroTransformationPoint().y, svgText)
|
||||||
|
.subscribe((serverDrawing: Drawing) => {
|
||||||
|
document.body.style.cursor = "default";
|
||||||
|
this.drawingsDataSource.add(serverDrawing);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
public onTextEdited(evt: TextEditedDataEvent){
|
public onTextEdited(evt: TextEditedDataEvent){
|
||||||
let mapDrawing: MapDrawing = new MapDrawing();
|
let mapDrawing: MapDrawing = new MapDrawing();
|
||||||
mapDrawing.element = evt.textElement;
|
mapDrawing.element = evt.textElement;
|
||||||
@ -510,7 +529,7 @@ export class ProjectMapComponent implements OnInit, OnDestroy {
|
|||||||
break;
|
break;
|
||||||
case "text":
|
case "text":
|
||||||
let textElement = new TextElement();
|
let textElement = new TextElement();
|
||||||
textElement.height = 100; //should be calculated
|
textElement.height = 100;
|
||||||
textElement.width = 100;
|
textElement.width = 100;
|
||||||
textElement.text = text;
|
textElement.text = text;
|
||||||
textElement.fill = "#000000";
|
textElement.fill = "#000000";
|
||||||
@ -531,55 +550,8 @@ export class ProjectMapComponent implements OnInit, OnDestroy {
|
|||||||
if (!this.drawTools.isAddingTextChosen){
|
if (!this.drawTools.isAddingTextChosen){
|
||||||
this.resetDrawToolChoice();
|
this.resetDrawToolChoice();
|
||||||
this.drawTools.isAddingTextChosen = true;
|
this.drawTools.isAddingTextChosen = true;
|
||||||
var map = document.getElementsByClassName('map')[0];
|
|
||||||
|
|
||||||
let addTextListener = (event: MouseEvent) => {
|
|
||||||
|
|
||||||
var div = document.createElement('div');
|
|
||||||
div.style.width = "fit-content";
|
|
||||||
div.style.left = event.clientX.toString() + 'px';
|
|
||||||
div.style.top = (event.clientY - 10).toString() + 'px';
|
|
||||||
div.style.position = "absolute";
|
|
||||||
div.style.zIndex = "99";
|
|
||||||
|
|
||||||
div.style.fontFamily = "Noto Sans";
|
|
||||||
div.style.fontSize = "11pt";
|
|
||||||
div.style.fontWeight = "bold";
|
|
||||||
div.style.color = "#000000";
|
|
||||||
|
|
||||||
div.setAttribute("contenteditable", "true");
|
|
||||||
|
|
||||||
document.body.appendChild(div);
|
|
||||||
div.innerText = "";
|
|
||||||
div.focus();
|
|
||||||
document.body.style.cursor = "text";
|
|
||||||
|
|
||||||
div.addEventListener("focusout", () => {
|
|
||||||
let savedText = div.innerText;
|
|
||||||
|
|
||||||
let drawing = this.getDrawingMock("text", savedText);
|
|
||||||
(drawing.element as TextElement).text = savedText;
|
|
||||||
let svgText = this.mapDrawingToSvgConverter.convert(drawing);
|
|
||||||
|
|
||||||
this.drawingService
|
|
||||||
.add(this.server, this.project.project_id, event.clientX - this.mapChild.context.getZeroZeroTransformationPoint().x, event.clientY - this.mapChild.context.getZeroZeroTransformationPoint().y, svgText)
|
|
||||||
.subscribe((serverDrawing: Drawing) => {
|
|
||||||
document.body.style.cursor = "default";
|
|
||||||
div.remove();
|
|
||||||
this.drawingsDataSource.add(serverDrawing);
|
|
||||||
});
|
|
||||||
});
|
|
||||||
|
|
||||||
this.resetDrawToolChoice();
|
|
||||||
}
|
|
||||||
|
|
||||||
map.removeEventListener('click', this.drawListener as EventListenerOrEventListenerObject);
|
|
||||||
this.drawListener = addTextListener;
|
|
||||||
map.addEventListener('click', this.drawListener as EventListenerOrEventListenerObject, {once : true});
|
|
||||||
} else {
|
} else {
|
||||||
this.resetDrawToolChoice();
|
this.resetDrawToolChoice();
|
||||||
var map = document.getElementsByClassName('map')[0];
|
|
||||||
map.removeEventListener('click', this.drawListener as EventListenerOrEventListenerObject);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user