mirror of
https://bitbucket.org/wisemapping/wisemapping-frontend.git
synced 2024-11-25 23:54:55 +01:00
Merged in feature/model_to_typescript (pull request #22)
Feature/model to typescript Approved-by: Matias Arriola
This commit is contained in:
commit
b1809816b0
@ -59,7 +59,7 @@ class CommandContext {
|
|||||||
/** */
|
/** */
|
||||||
createModel() {
|
createModel() {
|
||||||
const mindmap = this._designer.getMindmap();
|
const mindmap = this._designer.getMindmap();
|
||||||
return mindmap.createNode(NodeModel.MAIN_TOPIC_TYPE);
|
return mindmap.createNode('MainTopic');
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
|
@ -34,7 +34,7 @@ class ConnectionLine {
|
|||||||
|
|
||||||
let line;
|
let line;
|
||||||
const ctrlPoints = this._getCtrlPoints(sourceNode, targetNode);
|
const ctrlPoints = this._getCtrlPoints(sourceNode, targetNode);
|
||||||
if (targetNode.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (targetNode.getType() === 'CentralTopic') {
|
||||||
line = this._createLine(lineType, ConnectionLine.CURVED);
|
line = this._createLine(lineType, ConnectionLine.CURVED);
|
||||||
line.setSrcControlPoint(ctrlPoints[0]);
|
line.setSrcControlPoint(ctrlPoints[0]);
|
||||||
line.setDestControlPoint(ctrlPoints[1]);
|
line.setDestControlPoint(ctrlPoints[1]);
|
||||||
|
@ -243,7 +243,7 @@ class Designer extends Events {
|
|||||||
});
|
});
|
||||||
|
|
||||||
// Register node listeners ...
|
// Register node listeners ...
|
||||||
if (topic.getType() !== INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (topic.getType() !== 'CentralTopic') {
|
||||||
// Central Topic doesn't support to be dragged
|
// Central Topic doesn't support to be dragged
|
||||||
this._dragManager.add(topic);
|
this._dragManager.add(topic);
|
||||||
}
|
}
|
||||||
@ -443,7 +443,7 @@ class Designer extends Events {
|
|||||||
}
|
}
|
||||||
// Execute event ...
|
// Execute event ...
|
||||||
const topic = nodes[0];
|
const topic = nodes[0];
|
||||||
if (topic.getType() !== INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (topic.getType() !== 'CentralTopic') {
|
||||||
this._actionDispatcher.shrinkBranch([topic.getId()], !topic.areChildrenShrunken());
|
this._actionDispatcher.shrinkBranch([topic.getId()], !topic.areChildrenShrunken());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -476,7 +476,7 @@ class Designer extends Events {
|
|||||||
*/
|
*/
|
||||||
_copyNodeProps(sourceModel, targetModel) {
|
_copyNodeProps(sourceModel, targetModel) {
|
||||||
// I don't copy the font size if the target is the source is the central topic.
|
// I don't copy the font size if the target is the source is the central topic.
|
||||||
if (sourceModel.getType() !== INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (sourceModel.getType() !== 'CentralTopic') {
|
||||||
const fontSize = sourceModel.getFontSize();
|
const fontSize = sourceModel.getFontSize();
|
||||||
if (fontSize) {
|
if (fontSize) {
|
||||||
targetModel.setFontSize(fontSize);
|
targetModel.setFontSize(fontSize);
|
||||||
@ -586,7 +586,7 @@ class Designer extends Events {
|
|||||||
|
|
||||||
// Hack: if parent is central topic, add node below not on opposite side.
|
// Hack: if parent is central topic, add node below not on opposite side.
|
||||||
// This should be done in the layout
|
// This should be done in the layout
|
||||||
if (parentTopic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (parentTopic.getType() === 'CentralTopic') {
|
||||||
siblingModel.setOrder(topic.getOrder() + 2);
|
siblingModel.setOrder(topic.getOrder() + 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -954,7 +954,7 @@ class Designer extends Events {
|
|||||||
/** */
|
/** */
|
||||||
changeTopicShape(shape) {
|
changeTopicShape(shape) {
|
||||||
const validateFunc = (topic) => !(
|
const validateFunc = (topic) => !(
|
||||||
topic.getType() === INodeModel.CENTRAL_TOPIC_TYPE && shape === TopicShape.LINE
|
topic.getType() === 'CentralTopic' && shape === TopicShape.LINE
|
||||||
);
|
);
|
||||||
|
|
||||||
const validateError = 'Central Topic shape can not be changed to line figure.';
|
const validateError = 'Central Topic shape can not be changed to line figure.';
|
||||||
|
@ -145,7 +145,7 @@ class DragPivot {
|
|||||||
let result = null;
|
let result = null;
|
||||||
const parentTopic = this._targetTopic;
|
const parentTopic = this._targetTopic;
|
||||||
if (parentTopic) {
|
if (parentTopic) {
|
||||||
if (parentTopic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (parentTopic.getType() === 'CentralTopic') {
|
||||||
result = this._straightLine;
|
result = this._straightLine;
|
||||||
} else {
|
} else {
|
||||||
result = this._curvedLine;
|
result = this._curvedLine;
|
||||||
|
@ -25,15 +25,12 @@ import {
|
|||||||
} from '@wisemapping/web2d';
|
} from '@wisemapping/web2d';
|
||||||
import IconGroupRemoveTip from './IconGroupRemoveTip';
|
import IconGroupRemoveTip from './IconGroupRemoveTip';
|
||||||
|
|
||||||
import NoteModel from './model/NoteModel';
|
|
||||||
import LinkModel from './model/LinkModel';
|
|
||||||
import IconModel from './model/IconModel';
|
|
||||||
import Icon from './Icon';
|
import Icon from './Icon';
|
||||||
|
|
||||||
const ORDER_BY_TYPE = new Map();
|
const ORDER_BY_TYPE = new Map();
|
||||||
ORDER_BY_TYPE.set(IconModel.FEATURE_TYPE, 0);
|
ORDER_BY_TYPE.set('icon', 0);
|
||||||
ORDER_BY_TYPE.set(NoteModel.FEATURE_TYPE, 1);
|
ORDER_BY_TYPE.set('note', 1);
|
||||||
ORDER_BY_TYPE.set(LinkModel.FEATURE_TYPE, 2);
|
ORDER_BY_TYPE.set('link', 2);
|
||||||
|
|
||||||
class IconGroup {
|
class IconGroup {
|
||||||
constructor(topicId, iconSize) {
|
constructor(topicId, iconSize) {
|
||||||
|
@ -22,9 +22,9 @@ export const create = (nodeModel, options) => {
|
|||||||
$assert(type, 'Node model type can not be null');
|
$assert(type, 'Node model type can not be null');
|
||||||
|
|
||||||
let result;
|
let result;
|
||||||
if (type === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (type === 'CentralTopic') {
|
||||||
result = new CentralTopic(nodeModel, options);
|
result = new CentralTopic(nodeModel, options);
|
||||||
} else if (type === INodeModel.MAIN_TOPIC_TYPE) {
|
} else if (type === 'MainTopic') {
|
||||||
result = new MainTopic(nodeModel, options);
|
result = new MainTopic(nodeModel, options);
|
||||||
} else {
|
} else {
|
||||||
$assert(false, `unsupported node type:${type}`);
|
$assert(false, `unsupported node type:${type}`);
|
||||||
|
@ -86,7 +86,7 @@ class Relationship extends ConnectionLine {
|
|||||||
|
|
||||||
const targetTopic = this._targetTopic;
|
const targetTopic = this._targetTopic;
|
||||||
let targetPosition = targetTopic.getPosition();
|
let targetPosition = targetTopic.getPosition();
|
||||||
if (targetTopic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (targetTopic.getType() === 'CentralTopic') {
|
||||||
targetPosition = Shape.workoutIncomingConnectionPoint(targetTopic, sourcePosition);
|
targetPosition = Shape.workoutIncomingConnectionPoint(targetTopic, sourcePosition);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -131,7 +131,7 @@ class RelationshipPivot {
|
|||||||
_calculateFromPosition(toPosition) {
|
_calculateFromPosition(toPosition) {
|
||||||
// Calculate origin position ...
|
// Calculate origin position ...
|
||||||
let sourcePosition = this._sourceTopic.getPosition();
|
let sourcePosition = this._sourceTopic.getPosition();
|
||||||
if (this._sourceTopic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (this._sourceTopic.getType() === 'CentralTopic') {
|
||||||
sourcePosition = Shape.workoutIncomingConnectionPoint(this._sourceTopic, toPosition);
|
sourcePosition = Shape.workoutIncomingConnectionPoint(this._sourceTopic, toPosition);
|
||||||
}
|
}
|
||||||
const controlPoint = Shape.calculateDefaultControlPoints(sourcePosition, toPosition);
|
const controlPoint = Shape.calculateDefaultControlPoints(sourcePosition, toPosition);
|
||||||
|
@ -1337,7 +1337,7 @@ class Topic extends NodeGraph {
|
|||||||
|
|
||||||
/** @return {Boolean} true if the topic is the central topic of the map */
|
/** @return {Boolean} true if the topic is the central topic of the map */
|
||||||
isCentralTopic() {
|
isCentralTopic() {
|
||||||
return this.getModel().getType() === INodeModel.CENTRAL_TOPIC_TYPE;
|
return this.getModel().getType() === 'CentralTopic';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17,29 +17,26 @@
|
|||||||
*/
|
*/
|
||||||
|
|
||||||
import { $assert } from '@wisemapping/core-js';
|
import { $assert } from '@wisemapping/core-js';
|
||||||
import IconModel from './model/IconModel';
|
|
||||||
import ImageIcon from './ImageIcon';
|
import ImageIcon from './ImageIcon';
|
||||||
import LinkModel from './model/LinkModel';
|
|
||||||
import LinkIcon from './LinkIcon';
|
import LinkIcon from './LinkIcon';
|
||||||
import NoteModel from './model/NoteModel';
|
|
||||||
import NoteIcon from './NoteIcon';
|
import NoteIcon from './NoteIcon';
|
||||||
|
|
||||||
const TopicFeatureFactory = {
|
const TopicFeatureFactory = {
|
||||||
/** the icon object */
|
/** the icon object */
|
||||||
Icon: {
|
Icon: {
|
||||||
id: IconModel.FEATURE_TYPE,
|
id: 'icon',
|
||||||
icon: ImageIcon,
|
icon: ImageIcon,
|
||||||
},
|
},
|
||||||
|
|
||||||
/** the link object */
|
/** the link object */
|
||||||
Link: {
|
Link: {
|
||||||
id: LinkModel.FEATURE_TYPE,
|
id: 'link',
|
||||||
icon: LinkIcon,
|
icon: LinkIcon,
|
||||||
},
|
},
|
||||||
|
|
||||||
/** the note object */
|
/** the note object */
|
||||||
Note: {
|
Note: {
|
||||||
id: NoteModel.FEATURE_TYPE,
|
id: 'note',
|
||||||
icon: NoteIcon,
|
icon: NoteIcon,
|
||||||
},
|
},
|
||||||
|
|
||||||
|
@ -16,6 +16,8 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { Mindmap } from "../..";
|
import { Mindmap } from "../..";
|
||||||
|
import INodeModel from "../model/INodeModel";
|
||||||
|
import LinkModel from "../model/LinkModel";
|
||||||
import NodeModel from "../model/NodeModel";
|
import NodeModel from "../model/NodeModel";
|
||||||
import Exporter from "./Exporter";
|
import Exporter from "./Exporter";
|
||||||
|
|
||||||
@ -37,17 +39,20 @@ class TxtExporter implements Exporter {
|
|||||||
return Promise.resolve(retult);
|
return Promise.resolve(retult);
|
||||||
}
|
}
|
||||||
|
|
||||||
private traverseBranch(prefix: string, branches: Array<NodeModel>) {
|
private traverseBranch(prefix: string, branches: Array<INodeModel>) {
|
||||||
let result = '';
|
let result = '';
|
||||||
branches.forEach((node, index) => {
|
branches.forEach((node, index) => {
|
||||||
result = result + `${prefix}${index+1} ${node.getText()}`;
|
result = result + `${prefix}${index+1} ${node.getText()}`;
|
||||||
node.getFeatures().forEach((f)=>{
|
node.getFeatures().forEach((f)=>{
|
||||||
|
const type = f.getType();
|
||||||
|
if(type === 'link'){
|
||||||
|
result = result + ` [link: ${(f as LinkModel).getUrl()}]`
|
||||||
|
}
|
||||||
});
|
});
|
||||||
result = result + '\n';
|
result = result + '\n';
|
||||||
|
|
||||||
if (node.getChildren().length > 0) {
|
if (node.getChildren().length > 0) {
|
||||||
result = result + this.traverseBranch(`${prefix}${index+1}.`, node.getChildren());
|
result = result + this.traverseBranch(`\t${prefix}${index+1}.`, node.getChildren());
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
return result;
|
return result;
|
||||||
|
@ -15,16 +15,23 @@
|
|||||||
* See the License for the specific language governing permissions and
|
* See the License for the specific language governing permissions and
|
||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { $assert, $defined } from '@wisemapping/core-js';
|
import { $assert } from '@wisemapping/core-js';
|
||||||
|
|
||||||
|
export type FeatureType = 'note' | 'link' | 'icon';
|
||||||
|
|
||||||
class FeatureModel {
|
class FeatureModel {
|
||||||
|
static _next_id = 0;
|
||||||
|
private _id: number;
|
||||||
|
private _type: FeatureType;
|
||||||
|
private _attributes: {};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @constructs
|
* @constructs
|
||||||
* @param type
|
* @param type
|
||||||
* @throws will throw an exception if type is null or undefined
|
* @throws will throw an exception if type is null or undefined
|
||||||
* assigns a unique id and the given type to the new model
|
* assigns a unique id and the given type to the new model
|
||||||
*/
|
*/
|
||||||
constructor(type) {
|
constructor(type: FeatureType) {
|
||||||
$assert(type, 'type can not be null');
|
$assert(type, 'type can not be null');
|
||||||
this._id = FeatureModel._nextUUID();
|
this._id = FeatureModel._nextUUID();
|
||||||
|
|
||||||
@ -77,19 +84,15 @@ class FeatureModel {
|
|||||||
this._id = id;
|
this._id = id;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
getType(): FeatureType {
|
||||||
getType() {
|
|
||||||
return this._type;
|
return this._type;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
FeatureModel._nextUUID = function _nextUUID() {
|
static _nextUUID(): number {
|
||||||
if (!$defined(FeatureModel._uuid)) {
|
const result = FeatureModel._next_id + 1;
|
||||||
FeatureModel._uuid = 0;
|
FeatureModel._next_id = result;
|
||||||
|
return result;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
FeatureModel._uuid += 1;
|
|
||||||
return FeatureModel._uuid;
|
|
||||||
};
|
|
||||||
|
|
||||||
export default FeatureModel;
|
export default FeatureModel;
|
@ -2,20 +2,25 @@ import { $assert } from '@wisemapping/core-js';
|
|||||||
import IconModel from './IconModel';
|
import IconModel from './IconModel';
|
||||||
import LinkModel from './LinkModel';
|
import LinkModel from './LinkModel';
|
||||||
import NoteModel from './NoteModel';
|
import NoteModel from './NoteModel';
|
||||||
import FeatureModel from './FeatureModel';
|
import FeatureModel, { FeatureType } from './FeatureModel';
|
||||||
|
|
||||||
|
|
||||||
|
interface NodeById {
|
||||||
|
id: FeatureType,
|
||||||
|
model: typeof FeatureModel;
|
||||||
|
}
|
||||||
|
|
||||||
class FeatureModelFactory {
|
class FeatureModelFactory {
|
||||||
|
static modelById: Array<NodeById> = [{
|
||||||
private static modelById = [{
|
id: 'icon',
|
||||||
id: IconModel.FEATURE_TYPE,
|
|
||||||
model: IconModel,
|
model: IconModel,
|
||||||
}, {
|
}, {
|
||||||
id: LinkModel.FEATURE_TYPE,
|
id: 'link',
|
||||||
model: LinkModel,
|
model: LinkModel,
|
||||||
}, {
|
}, {
|
||||||
id: NoteModel.FEATURE_TYPE,
|
id: 'note',
|
||||||
model: NoteModel,
|
model: NoteModel,
|
||||||
}] as const;
|
}];
|
||||||
|
|
||||||
static createModel(type: string, attributes): FeatureModel {
|
static createModel(type: string, attributes): FeatureModel {
|
||||||
$assert(type, 'type can not be null');
|
$assert(type, 'type can not be null');
|
||||||
|
@ -18,35 +18,36 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { $assert } from '@wisemapping/core-js';
|
import { $assert } from '@wisemapping/core-js';
|
||||||
|
import INodeModel, { NodeModelType as NodeType } from './INodeModel';
|
||||||
import NodeModel from './NodeModel';
|
import NodeModel from './NodeModel';
|
||||||
import RelationshipModel from './RelationshipModel';
|
import RelationshipModel from './RelationshipModel';
|
||||||
|
|
||||||
abstract class IMindmap {
|
abstract class IMindmap {
|
||||||
getCentralTopic(): NodeModel {
|
getCentralTopic(): INodeModel {
|
||||||
return this.getBranches()[0];
|
return this.getBranches()[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
abstract getDescription(): string;
|
abstract getDescription(): string;
|
||||||
|
|
||||||
abstract setDescription(value: string);
|
abstract setDescription(value: string): void;
|
||||||
|
|
||||||
abstract getId(): string
|
abstract getId(): string
|
||||||
|
|
||||||
abstract setId(id: string);
|
abstract setId(id: string): void;
|
||||||
|
|
||||||
abstract getVersion(): string;
|
abstract getVersion(): string;
|
||||||
|
|
||||||
abstract setVersion(version: string): void;
|
abstract setVersion(version: string): void;
|
||||||
|
|
||||||
abstract addBranch(nodeModel: NodeModel): void;
|
abstract addBranch(nodeModel: INodeModel): void;
|
||||||
|
|
||||||
abstract getBranches(): Array<NodeModel>;
|
abstract getBranches(): Array<INodeModel>;
|
||||||
|
|
||||||
abstract removeBranch(node: NodeModel): void;
|
abstract removeBranch(node: INodeModel): void;
|
||||||
|
|
||||||
abstract getRelationships(): Array<RelationshipModel>;
|
abstract getRelationships(): Array<RelationshipModel>;
|
||||||
|
|
||||||
connect(parent: NodeModel, child: NodeModel): void {
|
connect(parent: INodeModel, child: INodeModel): void {
|
||||||
// Child already has a parent ?
|
// Child already has a parent ?
|
||||||
$assert(!child.getParent(), 'Child model seems to be already connected');
|
$assert(!child.getParent(), 'Child model seems to be already connected');
|
||||||
|
|
||||||
@ -62,7 +63,7 @@ abstract class IMindmap {
|
|||||||
* @throws will throw an error if child is null or undefined
|
* @throws will throw an error if child is null or undefined
|
||||||
* @throws will throw an error if child's parent cannot be found
|
* @throws will throw an error if child's parent cannot be found
|
||||||
*/
|
*/
|
||||||
disconnect(child: NodeModel): void {
|
disconnect(child: INodeModel): void {
|
||||||
const parent = child.getParent();
|
const parent = child.getParent();
|
||||||
$assert(child, 'Child can not be null.');
|
$assert(child, 'Child can not be null.');
|
||||||
$assert(parent, 'Child model seems to be already connected');
|
$assert(parent, 'Child model seems to be already connected');
|
||||||
@ -71,23 +72,15 @@ abstract class IMindmap {
|
|||||||
this.addBranch(child);
|
this.addBranch(child);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @abstract */
|
abstract hasAlreadyAdded(node: INodeModel): boolean;
|
||||||
hasAlreadyAdded(node) {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @abstract */
|
abstract createNode(type: NodeType, id: number):void;
|
||||||
createNode(type, id) {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
abstract createRelationship(fromNode: NodeModel, toNode: NodeModel): void;
|
abstract createRelationship(fromNode: NodeModel, toNode: NodeModel): void;
|
||||||
|
|
||||||
abstract addRelationship(rel: RelationshipModel): void;
|
abstract addRelationship(rel: RelationshipModel): void;
|
||||||
|
|
||||||
deleteRelationship(relationship: RelationshipModel): void {
|
abstract deleteRelationship(relationship: RelationshipModel): void;
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
inspect() {
|
inspect() {
|
||||||
|
@ -17,47 +17,53 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { $assert, $defined } from '@wisemapping/core-js';
|
import { $assert, $defined } from '@wisemapping/core-js';
|
||||||
|
import FeatureModel from './FeatureModel';
|
||||||
|
import Mindmap from './Mindmap';
|
||||||
|
|
||||||
// regex taken from https://stackoverflow.com/a/34763398/58128
|
// regex taken from https://stackoverflow.com/a/34763398/58128
|
||||||
const parseJsObject = (str) => JSON.parse(str.replace(/(['"])?([a-z0-9A-Z_]+)(['"])?:/g, '"$2": '));
|
const parseJsObject = (str: string) => JSON.parse(str.replace(/(['"])?([a-z0-9A-Z_]+)(['"])?:/g, '"$2": '));
|
||||||
|
|
||||||
class INodeModel {
|
abstract class INodeModel {
|
||||||
constructor(mindmap) {
|
static MAIN_TOPIC_TO_MAIN_TOPIC_DISTANCE: number = 220;
|
||||||
|
static _next_uuid: number = 0;
|
||||||
|
|
||||||
|
protected _mindmap: Mindmap;
|
||||||
|
|
||||||
|
constructor(mindmap: Mindmap) {
|
||||||
$assert(mindmap && mindmap.getBranches, 'mindmap can not be null');
|
$assert(mindmap && mindmap.getBranches, 'mindmap can not be null');
|
||||||
this._mindmap = mindmap;
|
this._mindmap = mindmap;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
getId(): number {
|
||||||
getId() {
|
|
||||||
return this.getProperty('id');
|
return this.getProperty('id');
|
||||||
}
|
}
|
||||||
|
abstract getFeatures(): Array<FeatureModel>;
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setId(id) {
|
setId(id: number): void {
|
||||||
if (!$defined(id)) {
|
if (!$defined(id)) {
|
||||||
const newId = INodeModel._nextUUID();
|
const newId = INodeModel._nextUUID();
|
||||||
this.putProperty('id', newId);
|
this.putProperty('id', newId);
|
||||||
} else {
|
} else {
|
||||||
if (id > INodeModel._uuid) {
|
if (id > INodeModel._next_uuid) {
|
||||||
$assert(Number.isFinite(id));
|
$assert(Number.isFinite(id));
|
||||||
INodeModel._uuid = id;
|
INodeModel._next_uuid = id;
|
||||||
}
|
}
|
||||||
this.putProperty('id', id);
|
this.putProperty('id', id);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
getType(): NodeModelType {
|
||||||
getType() {
|
|
||||||
return this.getProperty('type');
|
return this.getProperty('type');
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setType(type) {
|
setType(type: NodeModelType): void {
|
||||||
this.putProperty('type', type);
|
this.putProperty('type', type);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setText(text) {
|
setText(text: string): void {
|
||||||
this.putProperty('text', text);
|
this.putProperty('text', text);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -315,39 +321,55 @@ class INodeModel {
|
|||||||
// console.log("After:" + mindmap.inspect());
|
// console.log("After:" + mindmap.inspect());
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @abstract */
|
abstract getPropertiesKeys(): string[];
|
||||||
getPropertiesKeys() {
|
|
||||||
throw new Error('Unsupported operation');
|
abstract getProperty(key: string);
|
||||||
|
|
||||||
|
abstract putProperty(key: string, value: any): void;
|
||||||
|
|
||||||
|
abstract setParent(parent: INodeModel): void;
|
||||||
|
|
||||||
|
abstract getChildren(): INodeModel[];
|
||||||
|
|
||||||
|
abstract getParent(): INodeModel;
|
||||||
|
|
||||||
|
abstract clone(): INodeModel;
|
||||||
|
|
||||||
|
isChildNode(node: INodeModel): boolean {
|
||||||
|
let result = false;
|
||||||
|
if (node === this) {
|
||||||
|
result = true;
|
||||||
|
} else {
|
||||||
|
const children = this.getChildren();
|
||||||
|
for (let i = 0; i < children.length; i++) {
|
||||||
|
const child = children[i];
|
||||||
|
result = child.isChildNode(node);
|
||||||
|
if (result) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @abstract */
|
findNodeById(id: number): INodeModel {
|
||||||
// eslint-disable-next-line no-unused-vars
|
$assert(Number.isFinite(id));
|
||||||
putProperty(key, value) {
|
let result = null;
|
||||||
throw new Error('Unsupported operation');
|
if (this.getId() === id) {
|
||||||
|
result = this;
|
||||||
|
} else {
|
||||||
|
const children = this.getChildren();
|
||||||
|
for (let i = 0; i < children.length; i++) {
|
||||||
|
const child = children[i];
|
||||||
|
result = child.findNodeById(id);
|
||||||
|
if (result) {
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @abstract */
|
|
||||||
// eslint-disable-next-line no-unused-vars
|
|
||||||
setParent(parent) {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @abstract */
|
|
||||||
getChildren() {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @abstract */
|
|
||||||
getParent() {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** @abstract */
|
|
||||||
clone() {
|
|
||||||
throw new Error('Unsupported operation');
|
|
||||||
}
|
|
||||||
|
|
||||||
/** */
|
|
||||||
inspect() {
|
inspect() {
|
||||||
let result = `{ type: ${this.getType()} , id: ${this.getId()} , text: ${this.getText()}`;
|
let result = `{ type: ${this.getType()} , id: ${this.getId()} , text: ${this.getText()}`;
|
||||||
|
|
||||||
@ -369,16 +391,14 @@ class INodeModel {
|
|||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @abstract */
|
abstract removeChild(child: INodeModel);
|
||||||
// eslint-disable-next-line no-unused-vars
|
|
||||||
removeChild(child) {
|
static _nextUUID(): number {
|
||||||
throw new Error('Unsupported operation');
|
INodeModel._next_uuid += 1;
|
||||||
}
|
return INodeModel._next_uuid;
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @enum {String}
|
|
||||||
*/
|
|
||||||
const TopicShape = {
|
const TopicShape = {
|
||||||
RECTANGLE: 'rectagle',
|
RECTANGLE: 'rectagle',
|
||||||
ROUNDED_RECT: 'rounded rectagle',
|
ROUNDED_RECT: 'rounded rectagle',
|
||||||
@ -387,38 +407,10 @@ const TopicShape = {
|
|||||||
IMAGE: 'image',
|
IMAGE: 'image',
|
||||||
};
|
};
|
||||||
|
|
||||||
/**
|
export type NodeModelType = 'CentralTopic' | 'MainTopic';
|
||||||
* @constant
|
|
||||||
* @type {String}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
INodeModel.CENTRAL_TOPIC_TYPE = 'CentralTopic';
|
|
||||||
/**
|
|
||||||
* @constant
|
|
||||||
* @type {String}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
INodeModel.MAIN_TOPIC_TYPE = 'MainTopic';
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @constant
|
|
||||||
* @type {Number}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
INodeModel.MAIN_TOPIC_TO_MAIN_TOPIC_DISTANCE = 220;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @todo: This method must be implemented. (unascribed)
|
* @todo: This method must be implemented. (unascribed)
|
||||||
*/
|
*/
|
||||||
INodeModel._nextUUID = () => {
|
|
||||||
if (!$defined(INodeModel._uuid)) {
|
|
||||||
INodeModel._uuid = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
INodeModel._uuid += 1;
|
|
||||||
return INodeModel._uuid;
|
|
||||||
};
|
|
||||||
INodeModel._uuid = 0;
|
|
||||||
|
|
||||||
export { TopicShape };
|
export { TopicShape };
|
||||||
export default INodeModel;
|
export default INodeModel;
|
@ -20,27 +20,17 @@ import FeatureModel from './FeatureModel';
|
|||||||
|
|
||||||
class IconModel extends FeatureModel {
|
class IconModel extends FeatureModel {
|
||||||
constructor(attributes) {
|
constructor(attributes) {
|
||||||
super(IconModel.FEATURE_TYPE);
|
super('icon');
|
||||||
this.setIconType(attributes.id);
|
this.setIconType(attributes.id);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @return the icon type id */
|
getIconType(): string {
|
||||||
getIconType() {
|
|
||||||
return this.getAttribute('id');
|
return this.getAttribute('id');
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @param {String} iconType the icon type id */
|
setIconType(iconType: string) {
|
||||||
setIconType(iconType) {
|
|
||||||
$assert(iconType, 'iconType id can not be null');
|
$assert(iconType, 'iconType id can not be null');
|
||||||
this.setAttribute('id', iconType);
|
this.setAttribute('id', iconType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @constant
|
|
||||||
* @type {String}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
IconModel.FEATURE_TYPE = 'icon';
|
|
||||||
|
|
||||||
export default IconModel;
|
export default IconModel;
|
@ -20,12 +20,12 @@ import FeatureModel from './FeatureModel';
|
|||||||
|
|
||||||
class LinkModel extends FeatureModel {
|
class LinkModel extends FeatureModel {
|
||||||
constructor(attributes) {
|
constructor(attributes) {
|
||||||
super(LinkModel.FEATURE_TYPE);
|
super('link');
|
||||||
this.setUrl(attributes.url);
|
this.setUrl(attributes.url);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** @return {String} the url attribute value */
|
/** @return {String} the url attribute value */
|
||||||
getUrl() {
|
getUrl():string {
|
||||||
return this.getAttribute('url');
|
return this.getAttribute('url');
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -33,7 +33,7 @@ class LinkModel extends FeatureModel {
|
|||||||
* @param {String} url a URL provided by the user to set the link to
|
* @param {String} url a URL provided by the user to set the link to
|
||||||
* @throws will throw an error if url is null or undefined
|
* @throws will throw an error if url is null or undefined
|
||||||
*/
|
*/
|
||||||
setUrl(url) {
|
setUrl(url: string): void {
|
||||||
$assert(url, 'url can not be null');
|
$assert(url, 'url can not be null');
|
||||||
|
|
||||||
const fixedUrl = LinkModel._fixUrl(url);
|
const fixedUrl = LinkModel._fixUrl(url);
|
||||||
@ -44,7 +44,7 @@ class LinkModel extends FeatureModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// url format is already checked in LinkEditor.checkUrl
|
// url format is already checked in LinkEditor.checkUrl
|
||||||
static _fixUrl(url) {
|
static _fixUrl(url: string): string {
|
||||||
let result = url;
|
let result = url;
|
||||||
if (!result.includes('http://') && !result.includes('https://') && !result.includes('mailto://')) {
|
if (!result.includes('http://') && !result.includes('https://') && !result.includes('mailto://')) {
|
||||||
result = `http://${result}`;
|
result = `http://${result}`;
|
||||||
@ -61,12 +61,4 @@ class LinkModel extends FeatureModel {
|
|||||||
this.setAttribute('urlType', urlType);
|
this.setAttribute('urlType', urlType);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @constant
|
|
||||||
* @type {String}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
LinkModel.FEATURE_TYPE = 'link';
|
|
||||||
|
|
||||||
export default LinkModel;
|
export default LinkModel;
|
@ -17,17 +17,17 @@
|
|||||||
*/
|
*/
|
||||||
import { $assert, $defined } from '@wisemapping/core-js';
|
import { $assert, $defined } from '@wisemapping/core-js';
|
||||||
import IMindmap from './IMindmap';
|
import IMindmap from './IMindmap';
|
||||||
import INodeModel from './INodeModel';
|
import INodeModel, { NodeModelType } from './INodeModel';
|
||||||
import NodeModel from './NodeModel';
|
import NodeModel from './NodeModel';
|
||||||
import RelationshipModel from './RelationshipModel';
|
import RelationshipModel from './RelationshipModel';
|
||||||
import ModelCodeName from '../persistence/ModelCodeName';
|
import ModelCodeName from '../persistence/ModelCodeName';
|
||||||
|
|
||||||
class Mindmap extends IMindmap {
|
class Mindmap extends IMindmap {
|
||||||
_description: string;
|
private _description: string;
|
||||||
_version: string;
|
private _version: string;
|
||||||
_id: string;
|
private _id: string;
|
||||||
_branches: Array<NodeModel>;
|
private _branches: Array<NodeModel>;
|
||||||
_relationships: Array<RelationshipModel>;
|
private _relationships: Array<RelationshipModel>;
|
||||||
|
|
||||||
constructor(id: string, version: string = ModelCodeName.TANGO) {
|
constructor(id: string, version: string = ModelCodeName.TANGO) {
|
||||||
super();
|
super();
|
||||||
@ -79,10 +79,10 @@ class Mindmap extends IMindmap {
|
|||||||
$assert(nodeModel && nodeModel.isNodeModel(), 'Add node must be invoked with model objects');
|
$assert(nodeModel && nodeModel.isNodeModel(), 'Add node must be invoked with model objects');
|
||||||
const branches = this.getBranches();
|
const branches = this.getBranches();
|
||||||
if (branches.length === 0) {
|
if (branches.length === 0) {
|
||||||
$assert(nodeModel.getType() === INodeModel.CENTRAL_TOPIC_TYPE, 'First element must be the central topic');
|
$assert(nodeModel.getType() === 'CentralTopic', 'First element must be the central topic');
|
||||||
nodeModel.setPosition(0, 0);
|
nodeModel.setPosition(0, 0);
|
||||||
} else {
|
} else {
|
||||||
$assert(nodeModel.getType() !== INodeModel.CENTRAL_TOPIC_TYPE, 'Mindmaps only have one cental topic');
|
$assert(nodeModel.getType() !== 'CentralTopic', 'Mindmaps only have one cental topic');
|
||||||
}
|
}
|
||||||
|
|
||||||
this._branches.push(nodeModel);
|
this._branches.push(nodeModel);
|
||||||
@ -91,7 +91,7 @@ class Mindmap extends IMindmap {
|
|||||||
/**
|
/**
|
||||||
* @param nodeModel
|
* @param nodeModel
|
||||||
*/
|
*/
|
||||||
removeBranch(nodeModel: NodeModel): void {
|
removeBranch(nodeModel: INodeModel): void {
|
||||||
$assert(nodeModel && nodeModel.isNodeModel(), 'Remove node must be invoked with model objects');
|
$assert(nodeModel && nodeModel.isNodeModel(), 'Remove node must be invoked with model objects');
|
||||||
this._branches = this._branches.filter((b) => b !== nodeModel);
|
this._branches = this._branches.filter((b) => b !== nodeModel);
|
||||||
}
|
}
|
||||||
@ -104,29 +104,22 @@ class Mindmap extends IMindmap {
|
|||||||
return this._relationships;
|
return this._relationships;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @param node
|
hasAlreadyAdded(node: NodeModel): boolean {
|
||||||
* @return {Boolean} true if node already exists
|
|
||||||
*/
|
|
||||||
hasAlreadyAdded(node: any) {
|
|
||||||
let result = false;
|
let result = false;
|
||||||
|
|
||||||
// Check in not connected nodes.
|
// Check in not connected nodes.
|
||||||
const branches = this._branches;
|
const branches = this._branches;
|
||||||
for (let i = 0; i < branches.length; i++) {
|
for (let i = 0; i < branches.length; i++) {
|
||||||
result = branches[i]._isChildNode(node);
|
result = branches[i].isChildNode(node);
|
||||||
if (result) {
|
if (result) {
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
createNode(type: NodeModelType = 'MainTopic', id: number) {
|
||||||
* @param type
|
|
||||||
* @param id
|
|
||||||
* @return the node model created
|
|
||||||
*/
|
|
||||||
createNode(type = INodeModel.MAIN_TOPIC_TYPE, id: number) {
|
|
||||||
return new NodeModel(type, this, id);
|
return new NodeModel(type, this, id);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -172,7 +165,7 @@ class Mindmap extends IMindmap {
|
|||||||
|
|
||||||
static buildEmpty = (mapId: string) => {
|
static buildEmpty = (mapId: string) => {
|
||||||
const result = new Mindmap(mapId);
|
const result = new Mindmap(mapId);
|
||||||
const node = result.createNode(INodeModel.CENTRAL_TOPIC_TYPE, 0);
|
const node = result.createNode('CentralTopic', 0);
|
||||||
result.addBranch(node);
|
result.addBranch(node);
|
||||||
return result;
|
return result;
|
||||||
};
|
};
|
||||||
|
@ -17,21 +17,28 @@
|
|||||||
*/
|
*/
|
||||||
import { $assert, $defined } from '@wisemapping/core-js';
|
import { $assert, $defined } from '@wisemapping/core-js';
|
||||||
import cloneDeep from 'lodash/cloneDeep';
|
import cloneDeep from 'lodash/cloneDeep';
|
||||||
import INodeModel from './INodeModel';
|
import INodeModel, { NodeModelType } from './INodeModel';
|
||||||
import FeatureModelFactory from './FeatureModelFactory';
|
import FeatureModelFactory from './FeatureModelFactory';
|
||||||
|
import FeatureModel from './FeatureModel';
|
||||||
|
import Mindmap from './Mindmap';
|
||||||
|
|
||||||
class NodeModel extends INodeModel {
|
class NodeModel extends INodeModel {
|
||||||
constructor(type, mindmap, id) {
|
private _properties: {};
|
||||||
|
private _children: INodeModel[];
|
||||||
|
private _features: FeatureModel[];
|
||||||
|
private _parent: INodeModel;
|
||||||
|
|
||||||
|
constructor(type: NodeModelType, mindmap: Mindmap, id: number) {
|
||||||
$assert(type, 'Node type can not be null');
|
$assert(type, 'Node type can not be null');
|
||||||
$assert(mindmap, 'mindmap can not be null');
|
$assert(mindmap, 'mindmap can not be null');
|
||||||
super(mindmap);
|
super(mindmap);
|
||||||
this._properties = {};
|
this._properties = {};
|
||||||
this.setId(id);
|
this.setId(id);
|
||||||
this.setType(type);
|
this.setType(type);
|
||||||
this.areChildrenShrunken(false);
|
this.areChildrenShrunken();
|
||||||
|
|
||||||
this._children = [];
|
this._children = [];
|
||||||
this._feature = [];
|
this._features = [];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -49,12 +56,12 @@ class NodeModel extends INodeModel {
|
|||||||
*/
|
*/
|
||||||
addFeature(feature) {
|
addFeature(feature) {
|
||||||
$assert(feature, 'feature can not be null');
|
$assert(feature, 'feature can not be null');
|
||||||
this._feature.push(feature);
|
this._features.push(feature);
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
getFeatures() {
|
getFeatures() {
|
||||||
return this._feature;
|
return this._features;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -64,9 +71,9 @@ class NodeModel extends INodeModel {
|
|||||||
*/
|
*/
|
||||||
removeFeature(feature) {
|
removeFeature(feature) {
|
||||||
$assert(feature, 'feature can not be null');
|
$assert(feature, 'feature can not be null');
|
||||||
const size = this._feature.length;
|
const size = this._features.length;
|
||||||
this._feature = this._feature.filter((f) => feature.getId() !== f.getId());
|
this._features = this._features.filter((f) => feature.getId() !== f.getId());
|
||||||
$assert(size - 1 === this._feature.length, 'Could not be removed ...');
|
$assert(size - 1 === this._features.length, 'Could not be removed ...');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -75,7 +82,7 @@ class NodeModel extends INodeModel {
|
|||||||
*/
|
*/
|
||||||
findFeatureByType(type) {
|
findFeatureByType(type) {
|
||||||
$assert(type, 'type can not be null');
|
$assert(type, 'type can not be null');
|
||||||
return this._feature.filter((feature) => feature.getType() === type);
|
return this._features.filter((feature) => feature.getType() === type);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -86,7 +93,7 @@ class NodeModel extends INodeModel {
|
|||||||
*/
|
*/
|
||||||
findFeatureById(id) {
|
findFeatureById(id) {
|
||||||
$assert($defined(id), 'id can not be null');
|
$assert($defined(id), 'id can not be null');
|
||||||
const result = this._feature.filter((feature) => feature.getId() === id);
|
const result = this._features.filter((feature) => feature.getId() === id);
|
||||||
$assert(result.length === 1, `Feature could not be found:${id}`);
|
$assert(result.length === 1, `Feature could not be found:${id}`);
|
||||||
return result[0];
|
return result[0];
|
||||||
}
|
}
|
||||||
@ -112,7 +119,7 @@ class NodeModel extends INodeModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
getProperty(key) {
|
getProperty(key: string) {
|
||||||
$defined(key, 'key can not be null');
|
$defined(key, 'key can not be null');
|
||||||
const result = this._properties[key];
|
const result = this._properties[key];
|
||||||
return !$defined(result) ? null : result;
|
return !$defined(result) ? null : result;
|
||||||
@ -122,15 +129,15 @@ class NodeModel extends INodeModel {
|
|||||||
* @return {mindplot.model.NodeModel} an identical clone of the NodeModel
|
* @return {mindplot.model.NodeModel} an identical clone of the NodeModel
|
||||||
*/
|
*/
|
||||||
clone() {
|
clone() {
|
||||||
const result = new NodeModel(this.getType(), this._mindmap);
|
const result = new NodeModel(this.getType(), this._mindmap, -1);
|
||||||
result._children = this._children.map((node) => {
|
result._children = this._children.map((node) => {
|
||||||
const cnode = node.clone();
|
const cnode = node.clone() as NodeModel;
|
||||||
cnode._parent = result;
|
cnode._parent = result;
|
||||||
return cnode;
|
return cnode;
|
||||||
});
|
});
|
||||||
|
|
||||||
result._properties = cloneDeep(this._properties);
|
result._properties = cloneDeep(this._properties);
|
||||||
result._feature = cloneDeep(this._feature);
|
result._features = cloneDeep(this._features);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -138,19 +145,19 @@ class NodeModel extends INodeModel {
|
|||||||
* Similar to clone, assign new id to the elements ...
|
* Similar to clone, assign new id to the elements ...
|
||||||
* @return {mindplot.model.NodeModel}
|
* @return {mindplot.model.NodeModel}
|
||||||
*/
|
*/
|
||||||
deepCopy() {
|
deepCopy(): NodeModel {
|
||||||
const result = new NodeModel(this.getType(), this._mindmap);
|
const result = new NodeModel(this.getType(), this._mindmap, -1);
|
||||||
result._children = this._children.map((node) => {
|
result._children = this._children.map((node) => {
|
||||||
const cnode = node.deepCopy();
|
const cnode = (node as NodeModel).deepCopy();
|
||||||
cnode._parent = result;
|
cnode._parent = result;
|
||||||
return cnode;
|
return cnode;
|
||||||
});
|
});
|
||||||
|
|
||||||
const id = result.getId();
|
const id = result.getId();
|
||||||
result._properties = Object.clone(this._properties);
|
result._properties = Object.assign({}, this._properties);
|
||||||
result.setId(id);
|
result.setId(id);
|
||||||
|
|
||||||
result._feature = this._feature.clone();
|
result._features = cloneDeep(this._features);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -158,7 +165,7 @@ class NodeModel extends INodeModel {
|
|||||||
* @param {mindplot.model.NodeModel} child
|
* @param {mindplot.model.NodeModel} child
|
||||||
* @throws will throw an error if child is null, undefined or not a NodeModel object
|
* @throws will throw an error if child is null, undefined or not a NodeModel object
|
||||||
*/
|
*/
|
||||||
append(child) {
|
append(child: NodeModel) {
|
||||||
$assert(child && child.isNodeModel(), 'Only NodeModel can be appended to Mindmap object');
|
$assert(child && child.isNodeModel(), 'Only NodeModel can be appended to Mindmap object');
|
||||||
this._children.push(child);
|
this._children.push(child);
|
||||||
// eslint-disable-next-line no-param-reassign
|
// eslint-disable-next-line no-param-reassign
|
||||||
@ -169,7 +176,7 @@ class NodeModel extends INodeModel {
|
|||||||
* @param {mindplot.model.NodeModel} child
|
* @param {mindplot.model.NodeModel} child
|
||||||
* @throws will throw an error if child is null, undefined or not a NodeModel object
|
* @throws will throw an error if child is null, undefined or not a NodeModel object
|
||||||
*/
|
*/
|
||||||
removeChild(child) {
|
removeChild(child): void {
|
||||||
$assert(child && child.isNodeModel(), 'Only NodeModel can be appended to Mindmap object.');
|
$assert(child && child.isNodeModel(), 'Only NodeModel can be appended to Mindmap object.');
|
||||||
this._children = this._children.filter((c) => c !== child);
|
this._children = this._children.filter((c) => c !== child);
|
||||||
// eslint-disable-next-line no-param-reassign
|
// eslint-disable-next-line no-param-reassign
|
||||||
@ -192,44 +199,6 @@ class NodeModel extends INodeModel {
|
|||||||
this._parent = parent;
|
this._parent = parent;
|
||||||
}
|
}
|
||||||
|
|
||||||
_isChildNode(node) {
|
|
||||||
let result = false;
|
|
||||||
if (node === this) {
|
|
||||||
result = true;
|
|
||||||
} else {
|
|
||||||
const children = this.getChildren();
|
|
||||||
for (let i = 0; i < children.length; i++) {
|
|
||||||
const child = children[i];
|
|
||||||
result = child._isChildNode(node);
|
|
||||||
if (result) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @id
|
|
||||||
* @return {mindplot.model.NodeModel} the node with the respective id
|
|
||||||
*/
|
|
||||||
findNodeById(id) {
|
|
||||||
$assert(Number.isFinite(id));
|
|
||||||
let result = null;
|
|
||||||
if (this.getId() === id) {
|
|
||||||
result = this;
|
|
||||||
} else {
|
|
||||||
const children = this.getChildren();
|
|
||||||
for (let i = 0; i < children.length; i++) {
|
|
||||||
const child = children[i];
|
|
||||||
result = child.findNodeById(id);
|
|
||||||
if (result) {
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export default NodeModel;
|
export default NodeModel;
|
@ -20,7 +20,7 @@ import FeatureModel from './FeatureModel';
|
|||||||
|
|
||||||
class NoteModel extends FeatureModel {
|
class NoteModel extends FeatureModel {
|
||||||
constructor(attributes) {
|
constructor(attributes) {
|
||||||
super(NoteModel.FEATURE_TYPE);
|
super('note');
|
||||||
const noteText = attributes.text ? attributes.text : ' ';
|
const noteText = attributes.text ? attributes.text : ' ';
|
||||||
this.setText(noteText);
|
this.setText(noteText);
|
||||||
}
|
}
|
||||||
@ -37,11 +37,4 @@ class NoteModel extends FeatureModel {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @constant
|
|
||||||
* @type {String}
|
|
||||||
* @default
|
|
||||||
*/
|
|
||||||
NoteModel.FEATURE_TYPE = 'note';
|
|
||||||
|
|
||||||
export default NoteModel;
|
export default NoteModel;
|
@ -16,10 +16,21 @@
|
|||||||
* limitations under the License.
|
* limitations under the License.
|
||||||
*/
|
*/
|
||||||
import { $assert, $defined } from '@wisemapping/core-js';
|
import { $assert, $defined } from '@wisemapping/core-js';
|
||||||
|
import Point from '@wisemapping/web2d';
|
||||||
import ConnectionLine from '../ConnectionLine';
|
import ConnectionLine from '../ConnectionLine';
|
||||||
|
|
||||||
class RelationshipModel {
|
class RelationshipModel {
|
||||||
constructor(sourceTopicId, targetTopicId) {
|
static _next_uuid: number = 0;
|
||||||
|
private _id: number;
|
||||||
|
private _sourceTargetId: number;
|
||||||
|
private _targetTopicId: number;
|
||||||
|
private _lineType: number;
|
||||||
|
private _srcCtrlPoint: Point;
|
||||||
|
private _destCtrlPoint: Point;
|
||||||
|
private _endArrow: boolean;
|
||||||
|
private _startArrow: boolean;
|
||||||
|
|
||||||
|
constructor(sourceTopicId: number, targetTopicId: number) {
|
||||||
$assert($defined(sourceTopicId), 'from node type can not be null');
|
$assert($defined(sourceTopicId), 'from node type can not be null');
|
||||||
$assert($defined(targetTopicId), 'to node type can not be null');
|
$assert($defined(targetTopicId), 'to node type can not be null');
|
||||||
$assert(Number.isFinite(sourceTopicId), 'sourceTopicId is not a number');
|
$assert(Number.isFinite(sourceTopicId), 'sourceTopicId is not a number');
|
||||||
@ -46,7 +57,7 @@ class RelationshipModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
getId() {
|
getId():number {
|
||||||
$assert(this._id, 'id is null');
|
$assert(this._id, 'id is null');
|
||||||
return this._id;
|
return this._id;
|
||||||
}
|
}
|
||||||
@ -57,27 +68,27 @@ class RelationshipModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setLineType(lineType) {
|
setLineType(lineType: number) {
|
||||||
this._lineType = lineType;
|
this._lineType = lineType;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
getSrcCtrlPoint() {
|
getSrcCtrlPoint(): Point {
|
||||||
return this._srcCtrlPoint;
|
return this._srcCtrlPoint;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setSrcCtrlPoint(srcCtrlPoint) {
|
setSrcCtrlPoint(srcCtrlPoint: Point) {
|
||||||
this._srcCtrlPoint = srcCtrlPoint;
|
this._srcCtrlPoint = srcCtrlPoint;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
getDestCtrlPoint() {
|
getDestCtrlPoint(): Point {
|
||||||
return this._destCtrlPoint;
|
return this._destCtrlPoint;
|
||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setDestCtrlPoint(destCtrlPoint) {
|
setDestCtrlPoint(destCtrlPoint: Point) {
|
||||||
this._destCtrlPoint = destCtrlPoint;
|
this._destCtrlPoint = destCtrlPoint;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -87,7 +98,7 @@ class RelationshipModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setEndArrow(endArrow) {
|
setEndArrow(endArrow: boolean) {
|
||||||
this._endArrow = endArrow;
|
this._endArrow = endArrow;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -97,7 +108,7 @@ class RelationshipModel {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/** */
|
/** */
|
||||||
setStartArrow(startArrow) {
|
setStartArrow(startArrow: boolean) {
|
||||||
this._startArrow = startArrow;
|
this._startArrow = startArrow;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -118,23 +129,19 @@ class RelationshipModel {
|
|||||||
/**
|
/**
|
||||||
* @return {String} textual information about the relationship's source and target node
|
* @return {String} textual information about the relationship's source and target node
|
||||||
*/
|
*/
|
||||||
inspect() {
|
inspect(): string {
|
||||||
return (
|
return (
|
||||||
`(fromNode:${this.getFromNode().getId()
|
`(fromNode:${this.getFromNode()
|
||||||
} , toNode: ${this.getToNode().getId()
|
} , toNode: ${this.getToNode()
|
||||||
})`
|
})`
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static _nextUUID() {
|
||||||
|
RelationshipModel._next_uuid += 1;
|
||||||
|
return RelationshipModel._next_uuid;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function _nextUUID() {
|
|
||||||
if (!$defined(RelationshipModel._uuid)) {
|
|
||||||
RelationshipModel._uuid = 0;
|
|
||||||
}
|
|
||||||
RelationshipModel._uuid += 1;
|
|
||||||
return RelationshipModel._uuid;
|
|
||||||
}
|
|
||||||
|
|
||||||
RelationshipModel._nextUUID = _nextUUID;
|
|
||||||
|
|
||||||
export default RelationshipModel;
|
export default RelationshipModel;
|
@ -51,11 +51,11 @@ class XMLSerializerBeta {
|
|||||||
const parentTopic = document.createElement('topic');
|
const parentTopic = document.createElement('topic');
|
||||||
|
|
||||||
// Set topic attributes...
|
// Set topic attributes...
|
||||||
if (topic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (topic.getType() === 'CentralTopic') {
|
||||||
parentTopic.setAttribute('central', true);
|
parentTopic.setAttribute('central', true);
|
||||||
} else {
|
} else {
|
||||||
const parent = topic.getParent();
|
const parent = topic.getParent();
|
||||||
if (parent == null || parent.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (parent == null || parent.getType() === 'CentralTopic') {
|
||||||
const pos = topic.getPosition();
|
const pos = topic.getPosition();
|
||||||
parentTopic.setAttribute('position', `${pos.x},${pos.y}`);
|
parentTopic.setAttribute('position', `${pos.x},${pos.y}`);
|
||||||
} else {
|
} else {
|
||||||
@ -206,8 +206,8 @@ class XMLSerializerBeta {
|
|||||||
|
|
||||||
_deserializeNode(domElem, mindmap) {
|
_deserializeNode(domElem, mindmap) {
|
||||||
const type = domElem.getAttribute('central') != null
|
const type = domElem.getAttribute('central') != null
|
||||||
? INodeModel.CENTRAL_TOPIC_TYPE
|
? 'CentralTopic'
|
||||||
: INodeModel.MAIN_TOPIC_TYPE;
|
: 'MainTopic';
|
||||||
const topic = mindmap.createNode(type);
|
const topic = mindmap.createNode(type);
|
||||||
|
|
||||||
// Load attributes...
|
// Load attributes...
|
||||||
|
@ -68,7 +68,7 @@ class XMLSerializerPela {
|
|||||||
const parentTopic = document.createElement('topic');
|
const parentTopic = document.createElement('topic');
|
||||||
|
|
||||||
// Set topic attributes...
|
// Set topic attributes...
|
||||||
if (topic.getType() === INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (topic.getType() === 'CentralTopic') {
|
||||||
parentTopic.setAttribute('central', 'true');
|
parentTopic.setAttribute('central', 'true');
|
||||||
} else {
|
} else {
|
||||||
const pos = topic.getPosition();
|
const pos = topic.getPosition();
|
||||||
@ -96,7 +96,7 @@ class XMLSerializerPela {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (topic.areChildrenShrunken() && topic.getType() !== INodeModel.CENTRAL_TOPIC_TYPE) {
|
if (topic.areChildrenShrunken() && topic.getType() !== 'CentralTopic') {
|
||||||
parentTopic.setAttribute('shrink', 'true');
|
parentTopic.setAttribute('shrink', 'true');
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -268,8 +268,8 @@ class XMLSerializerPela {
|
|||||||
|
|
||||||
_deserializeNode(domElem, mindmap) {
|
_deserializeNode(domElem, mindmap) {
|
||||||
const type = domElem.getAttribute('central') != null
|
const type = domElem.getAttribute('central') != null
|
||||||
? INodeModel.CENTRAL_TOPIC_TYPE
|
? 'CentralTopic'
|
||||||
: INodeModel.MAIN_TOPIC_TYPE;
|
: 'MainTopic';
|
||||||
|
|
||||||
// Load attributes...
|
// Load attributes...
|
||||||
let id = domElem.getAttribute('id');
|
let id = domElem.getAttribute('id');
|
||||||
@ -349,7 +349,7 @@ class XMLSerializerPela {
|
|||||||
|
|
||||||
const isShrink = domElem.getAttribute('shrink');
|
const isShrink = domElem.getAttribute('shrink');
|
||||||
// Hack: Some production maps has been stored with the central topic collapsed. This is a bug.
|
// Hack: Some production maps has been stored with the central topic collapsed. This is a bug.
|
||||||
if ($defined(isShrink) && type !== INodeModel.CENTRAL_TOPIC_TYPE) {
|
if ($defined(isShrink) && type !== 'CentralTopic') {
|
||||||
topic.setChildrenShrunken(isShrink);
|
topic.setChildrenShrunken(isShrink);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -22,7 +22,7 @@ import fs from 'fs';
|
|||||||
import { diff } from 'jest-diff';
|
import { diff } from 'jest-diff';
|
||||||
import { expect } from '@jest/globals';
|
import { expect } from '@jest/globals';
|
||||||
|
|
||||||
const saveOutputRecord = false;
|
const saveOutputRecord = true;
|
||||||
|
|
||||||
export const setupBlob = () => {
|
export const setupBlob = () => {
|
||||||
// Workaround for partial implementations on Jest:
|
// Workaround for partial implementations on Jest:
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
1 PPM Plan
|
1 PPM Plan
|
||||||
1.1 Business Development
|
1.1 Business Development
|
||||||
1.2 Backlog Management
|
1.2 Backlog Management [link: https://docs.google.com/a/freeform.ca/drawings/d/1mrtkVAN3_XefJJCgfxw4Va6xk9TVDBKXDt_uzyIF4Us/edit]
|
||||||
1.3 Freeform IT
|
1.3 Freeform IT
|
||||||
1.4 Client Project Management
|
1.4 Client Project Management
|
||||||
1.5 Governance & Executive
|
1.5 Governance & Executive
|
||||||
@ -81,7 +81,7 @@
|
|||||||
11.1.1 null
|
11.1.1 null
|
||||||
11.2 Strategic Priority 3b: Health Promotion
|
11.2 Strategic Priority 3b: Health Promotion
|
||||||
11.2.1 Health and Wellness Committee
|
11.2.1 Health and Wellness Committee
|
||||||
11.2.2 Work-life Balance Initiative
|
11.2.2 Work-life Balance Initiative [link: http://hrcouncil.ca/hr-toolkit/workplaces-health-safety.cfm]
|
||||||
11.3 So that...
|
11.3 So that...
|
||||||
12 Benefits
|
12 Benefits
|
||||||
12.1 As Freeform Staff
|
12.1 As Freeform Staff
|
||||||
@ -98,8 +98,8 @@
|
|||||||
13.3 Drupal Community
|
13.3 Drupal Community
|
||||||
13.4 CiviCRM
|
13.4 CiviCRM
|
||||||
13.5 Other
|
13.5 Other
|
||||||
14 Backlog Plan
|
14 Backlog Plan [link: https://docs.google.com/a/freeform.ca/drawings/d/1mrtkVAN3_XefJJCgfxw4Va6xk9TVDBKXDt_uzyIF4Us/edit]
|
||||||
14.1 Go To Backlog Plan
|
14.1 Go To Backlog Plan [link: https://docs.google.com/a/freeform.ca/drawings/d/1mrtkVAN3_XefJJCgfxw4Va6xk9TVDBKXDt_uzyIF4Us/edit]
|
||||||
15 Strategy Prospecting
|
15 Strategy Prospecting
|
||||||
15.1 null
|
15.1 null
|
||||||
15.2 null
|
15.2 null
|
||||||
|
@ -3,11 +3,11 @@
|
|||||||
2.1 Normas aplicables a problemas de determinación de resultados
|
2.1 Normas aplicables a problemas de determinación de resultados
|
||||||
3 CIRCULANTES
|
3 CIRCULANTES
|
||||||
3.1 Adquisición temporal de acciones propias
|
3.1 Adquisición temporal de acciones propias
|
||||||
4 NIF A
|
4 NIF A [link: http://www.youtube.com/watch?v=7YN-sOlkQp0]
|
||||||
4.1 Marco conceptual
|
4.1 Marco conceptual
|
||||||
5 NIF C
|
5 NIF C [link: https://sites.google.com/site/contabilidadimcpnif/estructura-de-las-nif]
|
||||||
5.1 Normas aplicables a conceptos específicos de los estados financieros
|
5.1 Normas aplicables a conceptos específicos de los estados financieros
|
||||||
6 NIF E
|
6 NIF E
|
||||||
6.1 Normas aplicables alas actividades especializadas de distintos sectores
|
6.1 Normas aplicables alas actividades especializadas de distintos sectores
|
||||||
7 NIF B
|
7 NIF B [link: http://www.contaduria.uady.mx/files/cuerpo-acad/caef/aief/resumen_NIF_marco_conceptual.pdf]
|
||||||
7.1 Normas aplicables a los estados financieros en su conjunto
|
7.1 Normas aplicables a los estados financieros en su conjunto
|
||||||
|
@ -29,7 +29,7 @@
|
|||||||
1.5.1.1 Orange County Eye and Transplant Bank
|
1.5.1.1 Orange County Eye and Transplant Bank
|
||||||
1.5.1.2 Northern California Transplant Bank
|
1.5.1.2 Northern California Transplant Bank
|
||||||
1.5.1.2.1 In 2010, 2,500 referrals forwarded to OneLegacy
|
1.5.1.2.1 In 2010, 2,500 referrals forwarded to OneLegacy
|
||||||
1.5.1.3 Doheny Eye and Tissue Transplant Bank
|
1.5.1.3 Doheny Eye and Tissue Transplant Bank [link: http://www.dohenyeyebank.org/]
|
||||||
1.5.2 OneLegacy
|
1.5.2 OneLegacy
|
||||||
1.5.2.1 In 2010, 11,828 referrals
|
1.5.2.1 In 2010, 11,828 referrals
|
||||||
1.5.3 San Diego Eye Bank
|
1.5.3 San Diego Eye Bank
|
||||||
|
@ -1,13 +1,13 @@
|
|||||||
1 Welcome To WiseMapping
|
1 Welcome To WiseMapping
|
||||||
1.1 5 min tutorial video ?
|
1.1 5 min tutorial video ?
|
||||||
Follow the link !
|
Follow the link ! [link: https://www.youtube.com/tv?vq=medium#/watch?v=rKxZwNKs9cE]
|
||||||
1.2 Try it Now!
|
1.2 Try it Now!
|
||||||
1.2.1 Double Click
|
1.2.1 Double Click
|
||||||
1.2.2 Press "enter" to add a
|
1.2.2 Press "enter" to add a
|
||||||
Sibling
|
Sibling
|
||||||
1.2.3 Drag map to move
|
1.2.3 Drag map to move
|
||||||
1.3 Features
|
1.3 Features
|
||||||
1.3.1 Links to Sites
|
1.3.1 Links to Sites [link: http://www.digg.com]
|
||||||
1.3.2 Styles
|
1.3.2 Styles
|
||||||
1.3.2.1 Fonts
|
1.3.2.1 Fonts
|
||||||
1.3.2.2 Topic Shapes
|
1.3.2.2 Topic Shapes
|
||||||
@ -24,8 +24,8 @@ Sibling
|
|||||||
1.5.2 Brainstorming
|
1.5.2 Brainstorming
|
||||||
1.5.3 Visual
|
1.5.3 Visual
|
||||||
1.6 Install In Your Server
|
1.6 Install In Your Server
|
||||||
1.6.1 Open Source
|
1.6.1 Open Source [link: http://www.wisemapping.org/]
|
||||||
1.6.2 Download
|
1.6.2 Download [link: http://www.wisemapping.com/inyourserver.html]
|
||||||
1.7 Collaborate
|
1.7 Collaborate
|
||||||
1.7.1 Embed
|
1.7.1 Embed
|
||||||
1.7.2 Publish
|
1.7.2 Publish
|
||||||
|
Loading…
Reference in New Issue
Block a user