From a4b34adcb34184728be0b69b33a561f6d10f0a98 Mon Sep 17 00:00:00 2001 From: Fawn Date: Fri, 21 Jun 2019 16:27:03 -0400 Subject: can drag just a group of links on a doc --- src/client/views/nodes/LinkMenuGroup.tsx | 74 ++++++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 src/client/views/nodes/LinkMenuGroup.tsx (limited to 'src/client/views/nodes/LinkMenuGroup.tsx') diff --git a/src/client/views/nodes/LinkMenuGroup.tsx b/src/client/views/nodes/LinkMenuGroup.tsx new file mode 100644 index 000000000..229143d99 --- /dev/null +++ b/src/client/views/nodes/LinkMenuGroup.tsx @@ -0,0 +1,74 @@ +import { action, observable } from "mobx"; +import { observer } from "mobx-react"; +import { DocumentView } from "./DocumentView"; +import { LinkMenuItem } from "./LinkMenuItem"; +import { LinkEditor } from "./LinkEditor"; +import './LinkMenu.scss'; +import React = require("react"); +import { Doc, DocListCast } from "../../../new_fields/Doc"; +import { Id } from "../../../new_fields/FieldSymbols"; +import { LinkManager } from "../../util/LinkManager"; +import { DragLinksAsDocuments, DragManager } from "../../util/DragManager"; +import { emptyFunction } from "../../../Utils"; + +interface LinkMenuGroupProps { + sourceDoc: Doc; + group: Doc[]; + groupType: string; + showEditor: (linkDoc: Doc) => void; +} + +@observer +export class LinkMenuGroup extends React.Component { + + private _drag = React.createRef(); + + onLinkButtonDown = (e: React.PointerEvent): void => { + e.stopPropagation(); + document.removeEventListener("pointermove", this.onLinkButtonMoved); + document.addEventListener("pointermove", this.onLinkButtonMoved); + document.removeEventListener("pointerup", this.onLinkButtonUp); + document.addEventListener("pointerup", this.onLinkButtonUp); + } + + onLinkButtonUp = (e: PointerEvent): void => { + document.removeEventListener("pointermove", this.onLinkButtonMoved); + document.removeEventListener("pointerup", this.onLinkButtonUp); + e.stopPropagation(); + } + + onLinkButtonMoved = async (e: PointerEvent) => { + if (this._drag.current !== null && (e.movementX > 1 || e.movementY > 1)) { + document.removeEventListener("pointermove", this.onLinkButtonMoved); + document.removeEventListener("pointerup", this.onLinkButtonUp); + + let draggedDocs = this.props.group.map(linkDoc => LinkManager.Instance.findOppositeAnchor(linkDoc, this.props.sourceDoc)); + let dragData = new DragManager.DocumentDragData(draggedDocs); + + DragManager.StartLinkedDocumentDrag([this._drag.current], dragData, e.x, e.y, { + handlers: { + dragComplete: action(emptyFunction), + }, + hideSource: false + }); + } + e.stopPropagation(); + } + + render() { + let groupItems = this.props.group.map(linkDoc => { + let destination = LinkManager.Instance.findOppositeAnchor(linkDoc, this.props.sourceDoc); + return ; + }); + + return ( +
+

{this.props.groupType}:

+
+ {groupItems} +
+
+ ) + } +} \ No newline at end of file -- cgit v1.2.3-70-g09d2 From 41cf1e8536964764f18ab752140e484e36cbe464 Mon Sep 17 00:00:00 2001 From: Fawn Date: Tue, 25 Jun 2019 17:09:36 -0400 Subject: links can save --- src/client/documents/Documents.ts | 58 +--- src/client/util/DocumentManager.ts | 14 +- src/client/util/DragManager.ts | 24 +- src/client/util/LinkManager.ts | 239 +++++++++++---- src/client/views/DocumentDecorations.tsx | 2 +- src/client/views/MainView.tsx | 7 + .../views/collections/CollectionDockingView.tsx | 4 +- .../views/collections/CollectionTreeView.tsx | 18 +- .../CollectionFreeFormLinksView.tsx | 7 +- src/client/views/nodes/DocumentView.tsx | 8 +- src/client/views/nodes/LinkButtonBox.scss | 34 +-- src/client/views/nodes/LinkButtonBox.tsx | 126 ++++---- src/client/views/nodes/LinkEditor.tsx | 323 +++++++++------------ src/client/views/nodes/LinkMenu.tsx | 2 +- src/client/views/nodes/LinkMenuGroup.tsx | 8 +- src/client/views/nodes/LinkMenuItem.tsx | 6 +- src/new_fields/Doc.ts | 9 +- src/new_fields/LinkButtonField.ts | 58 ++-- 18 files changed, 503 insertions(+), 444 deletions(-) (limited to 'src/client/views/nodes/LinkMenuGroup.tsx') diff --git a/src/client/documents/Documents.ts b/src/client/documents/Documents.ts index 64032e096..fbd96fb66 100644 --- a/src/client/documents/Documents.ts +++ b/src/client/documents/Documents.ts @@ -35,8 +35,8 @@ import { DateField } from "../../new_fields/DateField"; import { UndoManager } from "../util/UndoManager"; import { RouteStore } from "../../server/RouteStore"; import { LinkManager } from "../util/LinkManager"; -import { LinkButtonBox } from "../views/nodes/LinkButtonBox"; -import { LinkButtonField, LinkButtonData } from "../../new_fields/LinkButtonField"; +// import { LinkButtonBox } from "../views/nodes/LinkButtonBox"; +// import { LinkButtonField, LinkButtonData } from "../../new_fields/LinkButtonField"; import { DocumentManager } from "../util/DocumentManager"; import { Id } from "../../new_fields/FieldSymbols"; var requestImageSize = require('request-image-size'); @@ -100,6 +100,7 @@ export namespace DocUtils { let linkDoc = Docs.TextDocument({ width: 100, height: 30, borderRounding: -1 }); let linkDocProto = Doc.GetProto(linkDoc); + linkDocProto.context = targetContext; linkDocProto.title = title; //=== "" ? source.title + " to " + target.title : title; linkDocProto.linkDescription = description; linkDocProto.linkTags = tags; @@ -111,36 +112,7 @@ export namespace DocUtils { linkDocProto.anchor2Page = target.curPage; linkDocProto.anchor2Groups = new List([]); - linkDocProto.context = targetContext; - - let sourceViews = DocumentManager.Instance.getDocumentViews(source); - let targetViews = DocumentManager.Instance.getDocumentViews(target); - sourceViews.forEach(sv => { - targetViews.forEach(tv => { - - // TODO: do only for when diff contexts - let proxy1 = Docs.LinkButtonDocument( - { sourceViewId: StrCast(sv.props.Document[Id]), targetViewId: StrCast(tv.props.Document[Id]) }, - { width: 200, height: 100, borderRounding: 0 }); - let proxy1Proto = Doc.GetProto(proxy1); - proxy1Proto.sourceViewId = StrCast(sv.props.Document[Id]); - proxy1Proto.targetViewId = StrCast(tv.props.Document[Id]); - proxy1Proto.isLinkButton = true; - - let proxy2 = Docs.LinkButtonDocument( - { sourceViewId: StrCast(tv.props.Document[Id]), targetViewId: StrCast(sv.props.Document[Id]) }, - { width: 200, height: 100, borderRounding: 0 }); - let proxy2Proto = Doc.GetProto(proxy2); - proxy2Proto.sourceViewId = StrCast(tv.props.Document[Id]); - proxy2Proto.targetViewId = StrCast(sv.props.Document[Id]); - proxy2Proto.isLinkButton = true; - - LinkManager.Instance.linkProxies.push(proxy1); - LinkManager.Instance.linkProxies.push(proxy2); - }); - }); - - LinkManager.Instance.allLinks.push(linkDoc); + LinkManager.Instance.addLink(linkDoc); return linkDoc; }, "make link"); @@ -160,7 +132,7 @@ export namespace Docs { let audioProto: Doc; let pdfProto: Doc; let iconProto: Doc; - let linkProto: Doc; + // let linkProto: Doc; const textProtoId = "textProto"; const histoProtoId = "histoProto"; const pdfProtoId = "pdfProto"; @@ -171,7 +143,7 @@ export namespace Docs { const videoProtoId = "videoProto"; const audioProtoId = "audioProto"; const iconProtoId = "iconProto"; - const linkProtoId = "linkProto"; + // const linkProtoId = "linkProto"; export function initProtos(): Promise { return DocServer.GetRefFields([textProtoId, histoProtoId, collProtoId, imageProtoId, webProtoId, kvpProtoId, videoProtoId, audioProtoId, pdfProtoId, iconProtoId]).then(fields => { @@ -185,7 +157,7 @@ export namespace Docs { audioProto = fields[audioProtoId] as Doc || CreateAudioPrototype(); pdfProto = fields[pdfProtoId] as Doc || CreatePdfPrototype(); iconProto = fields[iconProtoId] as Doc || CreateIconPrototype(); - linkProto = fields[linkProtoId] as Doc || CreateLinkPrototype(); + // linkProto = fields[linkProtoId] as Doc || CreateLinkPrototype(); }); } @@ -218,11 +190,11 @@ export namespace Docs { { x: 0, y: 0, width: Number(MINIMIZED_ICON_SIZE), height: Number(MINIMIZED_ICON_SIZE) }); return iconProto; } - function CreateLinkPrototype(): Doc { - let linkProto = setupPrototypeOptions(linkProtoId, "LINK_PROTO", LinkButtonBox.LayoutString(), - { x: 0, y: 0, width: 300 }); - return linkProto; - } + // function CreateLinkPrototype(): Doc { + // let linkProto = setupPrototypeOptions(linkProtoId, "LINK_PROTO", LinkButtonBox.LayoutString(), + // { x: 0, y: 0, width: 300 }); + // return linkProto; + // } function CreateTextPrototype(): Doc { let textProto = setupPrototypeOptions(textProtoId, "TEXT_PROTO", FormattedTextBox.LayoutString(), { x: 0, y: 0, width: 300, backgroundColor: "#f1efeb" }); @@ -309,9 +281,9 @@ export namespace Docs { export function IconDocument(icon: string, options: DocumentOptions = {}) { return CreateInstance(iconProto, new IconField(icon), options); } - export function LinkButtonDocument(data: LinkButtonData, options: DocumentOptions = {}) { - return CreateInstance(linkProto, new LinkButtonField(data), options); - } + // export function LinkButtonDocument(data: LinkButtonData, options: DocumentOptions = {}) { + // return CreateInstance(linkProto, new LinkButtonField(data), options); + // } export function PdfDocument(url: string, options: DocumentOptions = {}) { return CreateInstance(pdfProto, new PdfField(new URL(url)), options); } diff --git a/src/client/util/DocumentManager.ts b/src/client/util/DocumentManager.ts index 89e6183d6..767abe63f 100644 --- a/src/client/util/DocumentManager.ts +++ b/src/client/util/DocumentManager.ts @@ -85,12 +85,11 @@ export class DocumentManager { @computed public get LinkedDocumentViews() { - console.log("link"); - return DocumentManager.Instance.DocumentViews.filter(dv => dv.isSelected() || BoolCast(dv.props.Document.libraryBrush, false)).reduce((pairs, dv) => { - let linksList = LinkManager.Instance.findAllRelatedLinks(dv.props.Document); + let pairs = DocumentManager.Instance.DocumentViews.filter(dv => dv.isSelected() || BoolCast(dv.props.Document.libraryBrush, false)).reduce((pairs, dv) => { + let linksList = LinkManager.Instance.getAllRelatedLinks(dv.props.Document); pairs.push(...linksList.reduce((pairs, link) => { if (link) { - let linkToDoc = LinkManager.Instance.findOppositeAnchor(link, dv.props.Document); + let linkToDoc = LinkManager.Instance.getOppositeAnchor(link, dv.props.Document); DocumentManager.Instance.getDocumentViews(linkToDoc).map(docView1 => { pairs.push({ a: dv, b: docView1, l: link }); }); @@ -100,6 +99,13 @@ export class DocumentManager { // } return pairs; }, [] as { a: DocumentView, b: DocumentView, l: Doc }[]); + + // console.log("LINKED DOCUMENT VIEWS"); + // pairs.forEach(p => { + // console.log(StrCast(p.a.Document.title), p.a.props.Document[Id], StrCast(p.b.Document.title), p.b.props.Document[Id]); + // }); + + return pairs; } diff --git a/src/client/util/DragManager.ts b/src/client/util/DragManager.ts index f4c8adc8e..1aacf2c53 100644 --- a/src/client/util/DragManager.ts +++ b/src/client/util/DragManager.ts @@ -46,7 +46,7 @@ export function SetupDrag(_reference: React.RefObject, docFunc: () } export async function DragLinkAsDocument(dragEle: HTMLElement, x: number, y: number, linkDoc: Doc, sourceDoc: Doc) { - let draggeddoc = LinkManager.Instance.findOppositeAnchor(linkDoc, sourceDoc); + let draggeddoc = LinkManager.Instance.getOppositeAnchor(linkDoc, sourceDoc); let moddrag = await Cast(draggeddoc.annotationOn, Doc); let dragData = new DragManager.DocumentDragData(moddrag ? [moddrag] : [draggeddoc]); @@ -66,10 +66,10 @@ export async function DragLinksAsDocuments(dragEle: HTMLElement, x: number, y: n // TODO: if not in same context then don't drag if (srcTarg) { - let linkDocs = LinkManager.Instance.findAllRelatedLinks(srcTarg); + let linkDocs = LinkManager.Instance.getAllRelatedLinks(srcTarg); if (linkDocs) { draggedDocs = linkDocs.map(link => { - return LinkManager.Instance.findOppositeAnchor(link, sourceDoc); + return LinkManager.Instance.getOppositeAnchor(link, sourceDoc); }); } } @@ -236,10 +236,16 @@ export namespace DragManager { if (dv.props.ContainingCollectionView === SelectionManager.SelectedDocuments()[0].props.ContainingCollectionView) { return d; } else { - return Doc.MakeAlias(d); + // return d; + let r = Doc.MakeAlias(d); + // DocUtils.MakeLink(sourceDoc, r); + return r; } } else { - return Doc.MakeAlias(d); + // return d; + let r = Doc.MakeAlias(d); + // DocUtils.MakeLink(sourceDoc, r); + return r; } // return (dv && dv.props.ContainingCollectionView !== SelectionManager.SelectedDocuments()[0].props.ContainingCollectionView) || !dv ? // Doc.MakeAlias(d) : d; @@ -282,10 +288,10 @@ export namespace DragManager { StartDrag([ele], dragData, downX, downY, options); } - export function StartLinkProxyDrag(ele: HTMLElement, dragData: DocumentDragData, downX: number, downY: number, options?: DragOptions) { - runInAction(() => StartDragFunctions.map(func => func())); - StartDrag([ele], dragData, downX, downY, options); - } + // export function StartLinkProxyDrag(ele: HTMLElement, dragData: DocumentDragData, downX: number, downY: number, options?: DragOptions) { + // runInAction(() => StartDragFunctions.map(func => func())); + // StartDrag([ele], dragData, downX, downY, options); + // } export let AbortDrag: () => void = emptyFunction; diff --git a/src/client/util/LinkManager.ts b/src/client/util/LinkManager.ts index 745255f31..82c3a9acd 100644 --- a/src/client/util/LinkManager.ts +++ b/src/client/util/LinkManager.ts @@ -1,9 +1,10 @@ import { observable, action } from "mobx"; -import { StrCast, Cast } from "../../new_fields/Types"; +import { StrCast, Cast, FieldValue } from "../../new_fields/Types"; import { Doc, DocListCast } from "../../new_fields/Doc"; import { listSpec } from "../../new_fields/Schema"; import { List } from "../../new_fields/List"; import { Id } from "../../new_fields/FieldSymbols"; +import { CurrentUserUtils } from "../../server/authentication/models/current_user_utils"; /* @@ -23,6 +24,11 @@ import { Id } from "../../new_fields/FieldSymbols"; * - user defined kvps */ export class LinkManager { + // static Instance: LinkManager; + // private constructor() { + // LinkManager.Instance = this; + // } + private static _instance: LinkManager; public static get Instance(): LinkManager { return this._instance || (this._instance = new this()); @@ -30,25 +36,138 @@ export class LinkManager { private constructor() { } - @observable public allLinks: Array = []; // list of link docs - @observable public groupMetadataKeys: Map> = new Map(); - // map of group type to list of its metadata keys; serves as a dictionary of groups to what kind of metadata it hodls - @observable public linkProxies: Array = []; // list of linkbutton docs - used to visualize link when an anchors are not in the same context + public get LinkManagerDoc(): Doc | undefined { + return FieldValue(Cast(CurrentUserUtils.UserDocument.linkManagerDoc, Doc)); + } + // @observable public allLinks: Array = []; //List = new List([]); // list of link docs + // @observable public groupMetadataKeys: Map> = new Map(); + // map of group type to list of its metadata keys; serves as a dictionary of groups to what kind of metadata it holds + + public getAllLinks(): Doc[] { + return LinkManager.Instance.LinkManagerDoc ? LinkManager.Instance.LinkManagerDoc.allLinks ? DocListCast(LinkManager.Instance.LinkManagerDoc.allLinks) : [] : []; + } + + public addLink(linkDoc: Doc): boolean { + let linkList = LinkManager.Instance.getAllLinks(); + linkList.push(linkDoc); + console.log("link man doc", LinkManager.Instance.LinkManagerDoc); + if (LinkManager.Instance.LinkManagerDoc) { + LinkManager.Instance.LinkManagerDoc.allLinks = new List(linkList); + return true; + } + return false; + } + + public deleteLink(linkDoc: Doc): boolean { + let linkList = LinkManager.Instance.getAllLinks(); + let index = LinkManager.Instance.getAllLinks().indexOf(linkDoc); + if (index > -1) { + linkList.splice(index, 1); + if (LinkManager.Instance.LinkManagerDoc) { + LinkManager.Instance.LinkManagerDoc.allLinks = new List(linkList); + return true; + } + } + return false; + } // finds all links that contain the given anchor - public findAllRelatedLinks(anchor: Doc): Array { - return LinkManager.Instance.allLinks.filter(link => { + public getAllRelatedLinks(anchor: Doc): Doc[] {//List { + let related = LinkManager.Instance.getAllLinks().filter(link => { let protomatch1 = Doc.AreProtosEqual(anchor, Cast(link.anchor1, Doc, new Doc)); let protomatch2 = Doc.AreProtosEqual(anchor, Cast(link.anchor2, Doc, new Doc)); - // let idmatch1 = StrCast(anchor[Id]) === StrCast(Cast(link.anchor1, Doc, new Doc)[Id]); - // let idmatch2 = StrCast(anchor[Id]) === StrCast(Cast(link.anchor2, Doc, new Doc)[Id]); - return protomatch1 || protomatch2;// || idmatch1 || idmatch2; + return protomatch1 || protomatch2; }); + return related; + } + + public addGroupType(groupType: string): boolean { + if (LinkManager.Instance.LinkManagerDoc) { + LinkManager.Instance.LinkManagerDoc[groupType] = new List([]); + let groupTypes = LinkManager.Instance.getAllGroupTypes(); + groupTypes.push(groupType); + LinkManager.Instance.LinkManagerDoc.allGroupTypes = new List(groupTypes); + return true; + } + return false; + } + + // removes all group docs from all links with the given group type + public deleteGroupType(groupType: string): boolean { + if (LinkManager.Instance.LinkManagerDoc) { + if (LinkManager.Instance.LinkManagerDoc[groupType]) { + LinkManager.Instance.LinkManagerDoc[groupType] = undefined; + LinkManager.Instance.getAllLinks().forEach(linkDoc => { + LinkManager.Instance.removeGroupFromAnchor(linkDoc, Cast(linkDoc.anchor1, Doc, new Doc), groupType); + LinkManager.Instance.removeGroupFromAnchor(linkDoc, Cast(linkDoc.anchor2, Doc, new Doc), groupType); + }); + } + return true; + } else return false; + } + + public getAllGroupTypes(): string[] { + if (LinkManager.Instance.LinkManagerDoc) { + if (LinkManager.Instance.LinkManagerDoc.allGroupTypes) { + return Cast(LinkManager.Instance.LinkManagerDoc.allGroupTypes, listSpec("string"), []); + } else { + LinkManager.Instance.LinkManagerDoc.allGroupTypes = new List([]); + return []; + } + } + return []; + } + + // gets the groups associates with an anchor in a link + public getAnchorGroups(linkDoc: Doc, anchor: Doc): Array { + if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, new Doc))) { + return DocListCast(linkDoc.anchor1Groups); + } else { + return DocListCast(linkDoc.anchor2Groups); + } + } + + // sets the groups of the given anchor in the given link + public setAnchorGroups(linkDoc: Doc, anchor: Doc, groups: Doc[]) { + if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, new Doc))) { + linkDoc.anchor1Groups = new List(groups); + } else { + linkDoc.anchor2Groups = new List(groups); + } + } + + public addGroupToAnchor(linkDoc: Doc, anchor: Doc, groupDoc: Doc, replace: boolean = false) { + let groups = LinkManager.Instance.getAnchorGroups(linkDoc, anchor); + let index = groups.findIndex(gDoc => { + return StrCast(groupDoc.type).toUpperCase() === StrCast(gDoc.type).toUpperCase(); + }); + if (index > -1 && replace) { + groups[index] = groupDoc; + } + if (index === -1) { + groups.push(groupDoc); + } + LinkManager.Instance.setAnchorGroups(linkDoc, anchor, groups); + } + + // removes group doc of given group type only from given anchor on given link + public removeGroupFromAnchor(linkDoc: Doc, anchor: Doc, groupType: string) { + let groups = LinkManager.Instance.getAnchorGroups(linkDoc, anchor); + let newGroups = groups.filter(groupDoc => StrCast(groupDoc.type).toUpperCase() !== groupType.toUpperCase()); + LinkManager.Instance.setAnchorGroups(linkDoc, anchor, newGroups); } + // public doesAnchorHaveGroup(linkDoc: Doc, anchor: Doc, groupDoc: Doc): boolean { + // let groups = LinkManager.Instance.getAnchorGroups(linkDoc, anchor); + // let index = groups.findIndex(gDoc => { + // return StrCast(groupDoc.type).toUpperCase() === StrCast(gDoc.type).toUpperCase(); + // }); + // return index > -1; + // } + // returns map of group type to anchor's links in that group type - public findRelatedGroupedLinks(anchor: Doc): Map> { - let related = this.findAllRelatedLinks(anchor); + public getRelatedGroupedLinks(anchor: Doc): Map> { + let related = this.getAllRelatedLinks(anchor); let anchorGroups = new Map>(); related.forEach(link => { let groups = LinkManager.Instance.getAnchorGroups(link, anchor); @@ -73,10 +192,41 @@ export class LinkManager { return anchorGroups; } + // public addMetadataKeyToGroup(groupType: string, key: string): boolean { + // if (LinkManager.Instance.LinkManagerDoc) { + // if (LinkManager.Instance.LinkManagerDoc[groupType]) { + // let keyList = LinkManager.Instance.findMetadataKeysInGroup(groupType); + // keyList.push(key); + // LinkManager.Instance.LinkManagerDoc[groupType] = new List(keyList); + // return true; + // } + // return false; + // } + // return false; + // } + + public getMetadataKeysInGroup(groupType: string): string[] { + if (LinkManager.Instance.LinkManagerDoc) { + return LinkManager.Instance.LinkManagerDoc[groupType] ? Cast(LinkManager.Instance.LinkManagerDoc[groupType], listSpec("string"), []) : []; + } + return []; + } + + public setMetadataKeysForGroup(groupType: string, keys: string[]): boolean { + if (LinkManager.Instance.LinkManagerDoc) { + // if (LinkManager.Instance.LinkManagerDoc[groupType]) { + LinkManager.Instance.LinkManagerDoc[groupType] = new List(keys); + return true; + // } + // return false; + } + return false; + } + // returns a list of all metadata docs associated with the given group type - public findAllMetadataDocsInGroup(groupType: string): Array { + public getAllMetadataDocsInGroup(groupType: string): Array { let md: Doc[] = []; - let allLinks = LinkManager.Instance.allLinks; + let allLinks = LinkManager.Instance.getAllLinks(); allLinks.forEach(linkDoc => { let anchor1Groups = LinkManager.Instance.getAnchorGroups(linkDoc, Cast(linkDoc.anchor1, Doc, new Doc)); let anchor2Groups = LinkManager.Instance.getAnchorGroups(linkDoc, Cast(linkDoc.anchor2, Doc, new Doc)); @@ -86,27 +236,9 @@ export class LinkManager { return md; } - // removes all group docs from all links with the given group type - public deleteGroup(groupType: string): void { - let deleted = LinkManager.Instance.groupMetadataKeys.delete(groupType); - if (deleted) { - LinkManager.Instance.allLinks.forEach(linkDoc => { - LinkManager.Instance.removeGroupFromAnchor(linkDoc, Cast(linkDoc.anchor1, Doc, new Doc), groupType); - LinkManager.Instance.removeGroupFromAnchor(linkDoc, Cast(linkDoc.anchor2, Doc, new Doc), groupType); - }); - } - } - - // removes group doc of given group type only from given anchor on given link - public removeGroupFromAnchor(linkDoc: Doc, anchor: Doc, groupType: string) { - let groups = LinkManager.Instance.getAnchorGroups(linkDoc, anchor); - let newGroups = groups.filter(groupDoc => StrCast(groupDoc.type).toUpperCase() !== groupType.toUpperCase()); - LinkManager.Instance.setAnchorGroups(linkDoc, anchor, newGroups); - } - // checks if a link with the given anchors exists - public doesLinkExist(anchor1: Doc, anchor2: Doc) { - let allLinks = LinkManager.Instance.allLinks; + public doesLinkExist(anchor1: Doc, anchor2: Doc): boolean { + let allLinks = LinkManager.Instance.getAllLinks(); let index = allLinks.findIndex(linkDoc => { return (Doc.AreProtosEqual(Cast(linkDoc.anchor1, Doc, new Doc), anchor1) && Doc.AreProtosEqual(Cast(linkDoc.anchor2, Doc, new Doc), anchor2)) || (Doc.AreProtosEqual(Cast(linkDoc.anchor1, Doc, new Doc), anchor2) && Doc.AreProtosEqual(Cast(linkDoc.anchor2, Doc, new Doc), anchor1)); @@ -115,7 +247,7 @@ export class LinkManager { } // finds the opposite anchor of a given anchor in a link - public findOppositeAnchor(linkDoc: Doc, anchor: Doc): Doc { + public getOppositeAnchor(linkDoc: Doc, anchor: Doc): Doc { if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, new Doc))) { return Cast(linkDoc.anchor2, Doc, new Doc); } else { @@ -123,34 +255,17 @@ export class LinkManager { } } - // gets the groups associates with an anchor in a link - public getAnchorGroups(linkDoc: Doc, anchor: Doc): Array { - if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, new Doc))) { - return DocListCast(linkDoc.anchor1Groups); - } else { - return DocListCast(linkDoc.anchor2Groups); - } - } - // sets the groups of the given anchor in the given link - public setAnchorGroups(linkDoc: Doc, anchor: Doc, groups: Doc[]) { - if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, new Doc))) { - linkDoc.anchor1Groups = new List(groups); - } else { - linkDoc.anchor2Groups = new List(groups); - } - } - - @action - public addLinkProxy(proxy: Doc) { - LinkManager.Instance.linkProxies.push(proxy); - } + // @action + // public addLinkProxy(proxy: Doc) { + // LinkManager.Instance.linkProxies.push(proxy); + // } - public findLinkProxy(sourceViewId: string, targetViewId: string): Doc | undefined { - let index = LinkManager.Instance.linkProxies.findIndex(p => { - return StrCast(p.sourceViewId) === sourceViewId && StrCast(p.targetViewId) === targetViewId; - }); - return index > -1 ? LinkManager.Instance.linkProxies[index] : undefined; - } + // public findLinkProxy(sourceViewId: string, targetViewId: string): Doc | undefined { + // let index = LinkManager.Instance.linkProxies.findIndex(p => { + // return StrCast(p.sourceViewId) === sourceViewId && StrCast(p.targetViewId) === targetViewId; + // }); + // return index > -1 ? LinkManager.Instance.linkProxies[index] : undefined; + // } } \ No newline at end of file diff --git a/src/client/views/DocumentDecorations.tsx b/src/client/views/DocumentDecorations.tsx index 926273633..3a2752d7e 100644 --- a/src/client/views/DocumentDecorations.tsx +++ b/src/client/views/DocumentDecorations.tsx @@ -573,7 +573,7 @@ export class DocumentDecorations extends React.Component<{}, { value: string }> let linkButton = null; if (SelectionManager.SelectedDocuments().length > 0) { let selFirst = SelectionManager.SelectedDocuments()[0]; - let linkCount = LinkManager.Instance.findAllRelatedLinks(selFirst.props.Document).length; + let linkCount = LinkManager.Instance.getAllRelatedLinks(selFirst.props.Document).length; linkButton = (([]); + CurrentUserUtils.UserDocument.linkManagerDoc = linkManagerDoc; + } list.push(mainDoc); // bcz: strangely, we need a timeout to prevent exceptions/issues initializing GoldenLayout (the rendering engine for Main Container) setTimeout(() => { diff --git a/src/client/views/collections/CollectionDockingView.tsx b/src/client/views/collections/CollectionDockingView.tsx index c82027da5..4140f8029 100644 --- a/src/client/views/collections/CollectionDockingView.tsx +++ b/src/client/views/collections/CollectionDockingView.tsx @@ -354,9 +354,9 @@ export class CollectionDockingView extends React.Component [LinkManager.Instance.findAllRelatedLinks(doc), doc.title], + tab.reactionDisposer = reaction(() => [LinkManager.Instance.getAllRelatedLinks(doc), doc.title], () => { - counter.innerHTML = LinkManager.Instance.findAllRelatedLinks(doc).length; + counter.innerHTML = LinkManager.Instance.getAllRelatedLinks(doc).length; tab.titleElement[0].textContent = doc.title; }, { fireImmediately: true }); tab.titleElement[0].DashDocId = tab.contentItem.config.props.documentId; diff --git a/src/client/views/collections/CollectionTreeView.tsx b/src/client/views/collections/CollectionTreeView.tsx index 0b922b3c4..7bc3ad124 100644 --- a/src/client/views/collections/CollectionTreeView.tsx +++ b/src/client/views/collections/CollectionTreeView.tsx @@ -73,7 +73,7 @@ class TreeView extends React.Component { @undoBatch delete = () => this.props.deleteDoc(this.props.document); @undoBatch openRight = async () => this.props.addDocTab(this.props.document, "openRight"); - onPointerDown = (e: React.PointerEvent) => e.stopPropagation() + onPointerDown = (e: React.PointerEvent) => e.stopPropagation(); onPointerEnter = (e: React.PointerEvent): void => { this.props.active() && (this.props.document.libraryBrush = true); if (e.buttons === 1 && SelectionManager.GetIsDragging()) { @@ -115,7 +115,7 @@ class TreeView extends React.Component { return this.props.document !== target && this.props.deleteDoc(doc) && addDoc(doc); } @action - indent = () => this.props.addDocument(this.props.document) && this.delete(); + indent = () => this.props.addDocument(this.props.document) && this.delete() renderBullet() { let docList = Cast(this.props.document["data"], listSpec(Doc)); @@ -167,7 +167,7 @@ class TreeView extends React.Component { keyList.push(key); } }); - if (LinkManager.Instance.findAllRelatedLinks(this.props.document).length > 0) keyList.push("links"); + if (LinkManager.Instance.getAllRelatedLinks(this.props.document).length > 0) keyList.push("links"); if (keyList.indexOf("data") !== -1) { keyList.splice(keyList.indexOf("data"), 1); } @@ -281,9 +281,9 @@ class TreeView extends React.Component { let ele: JSX.Element[] = []; let remDoc = (doc: Doc) => this.remove(doc, this._chosenKey); let addDoc = (doc: Doc, addBefore?: Doc, before?: boolean) => TreeView.AddDocToList(this.props.document, this._chosenKey, doc, addBefore, before); - let groups = LinkManager.Instance.findRelatedGroupedLinks(this.props.document); + let groups = LinkManager.Instance.getRelatedGroupedLinks(this.props.document); groups.forEach((groupLinkDocs, groupType) => { - let destLinks = groupLinkDocs.map(d => LinkManager.Instance.findOppositeAnchor(d, this.props.document)); + let destLinks = groupLinkDocs.map(d => LinkManager.Instance.getOppositeAnchor(d, this.props.document)); ele.push(
{groupType}:
@@ -325,7 +325,7 @@ class TreeView extends React.Component { addDocTab={this.props.addDocTab} setPreviewScript={emptyFunction}> -
+ ; } } return
@@ -364,14 +364,14 @@ class TreeView extends React.Component { TreeView.AddDocToList(docList[i - 1], fieldKey, child); remove(child); } - } + }; let addDocument = (doc: Doc, relativeTo?: Doc, before?: boolean) => { return add(doc, relativeTo ? relativeTo : docList[i], before !== undefined ? before : false); - } + }; let rowHeight = () => { let aspect = NumCast(child.nativeWidth, 0) / NumCast(child.nativeHeight, 0); return aspect ? Math.min(child[WidthSym](), rowWidth()) / aspect : child[HeightSym](); - } + }; return { let srcViews = this.documentAnchors(connection.a); let targetViews = this.documentAnchors(connection.b); - console.log(srcViews.length, targetViews.length); + // console.log(srcViews.length, targetViews.length); let possiblePairs: { a: Doc, b: Doc, }[] = []; srcViews.map(sv => { targetViews.map(tv => { - console.log("PUSH", StrCast(sv.props.Document.title), StrCast(sv.props.Document.id), StrCast(tv.props.Document.title), StrCast(tv.props.Document.id)); + // console.log("PUSH", StrCast(sv.props.Document.title), StrCast(sv.props.Document.id), StrCast(tv.props.Document.title), StrCast(tv.props.Document.id)); possiblePairs.push({ a: sv.props.Document, b: tv.props.Document }); }); }); @@ -142,7 +142,6 @@ export class CollectionFreeFormLinksView extends React.Component diff --git a/src/client/views/nodes/DocumentView.tsx b/src/client/views/nodes/DocumentView.tsx index 1fc2cf770..7b185336b 100644 --- a/src/client/views/nodes/DocumentView.tsx +++ b/src/client/views/nodes/DocumentView.tsx @@ -285,7 +285,7 @@ export class DocumentView extends DocComponent(Docu let subBulletDocs = await DocListCastAsync(this.props.Document.subBulletDocs); let maximizedDocs = await DocListCastAsync(this.props.Document.maximizedDocs); let summarizedDocs = await DocListCastAsync(this.props.Document.summarizedDocs); - let linkedDocs = LinkManager.Instance.findAllRelatedLinks(this.props.Document); + let linkedDocs = LinkManager.Instance.getAllRelatedLinks(this.props.Document); let expandedDocs: Doc[] = []; expandedDocs = subBulletDocs ? [...subBulletDocs, ...expandedDocs] : expandedDocs; expandedDocs = maximizedDocs ? [...maximizedDocs, ...expandedDocs] : expandedDocs; @@ -536,11 +536,6 @@ export class DocumentView extends DocComponent(Docu onPointerEnter = (e: React.PointerEvent): void => { this.props.Document.libraryBrush = true; }; onPointerLeave = (e: React.PointerEvent): void => { this.props.Document.libraryBrush = false; }; - onDragOver = (e: React.DragEvent): void => { - this.props.Document.libraryBrush = true; - console.log("dragOver"); - }; - onDragLeave = (e: React.DragEvent): void => { this.props.Document.libraryBrush = false; }; isSelected = () => SelectionManager.IsSelected(this); @action select = (ctrlPressed: boolean) => { SelectionManager.SelectDoc(this, ctrlPressed); }; @@ -585,7 +580,6 @@ export class DocumentView extends DocComponent(Docu // display: display ? "block" : "none" }} onDrop={this.onDrop} onContextMenu={this.onContextMenu} onPointerDown={this.onPointerDown} onClick={this.onClick} - onDragOver={this.onDragOver} onDragLeave={this.onDragLeave} onPointerEnter={this.onPointerEnter} onPointerLeave={this.onPointerLeave} > {this.contents} diff --git a/src/client/views/nodes/LinkButtonBox.scss b/src/client/views/nodes/LinkButtonBox.scss index 24bfd2c9f..6be2dcf60 100644 --- a/src/client/views/nodes/LinkButtonBox.scss +++ b/src/client/views/nodes/LinkButtonBox.scss @@ -1,18 +1,18 @@ -.linkBox-cont { - width: 200px; - height: 100px; - background-color: black; - text-align: center; - color: white; - padding: 10px; - border-radius: 5px; - position: relative; +// .linkBox-cont { +// width: 200px; +// height: 100px; +// background-color: black; +// text-align: center; +// color: white; +// padding: 10px; +// border-radius: 5px; +// position: relative; - .linkBox-cont-wrapper { - width: calc(100% - 20px); - position: absolute; - left: 50%; - top: 50%; - transform: translate(-50%, -50%); - } -} \ No newline at end of file +// .linkBox-cont-wrapper { +// width: calc(100% - 20px); +// position: absolute; +// left: 50%; +// top: 50%; +// transform: translate(-50%, -50%); +// } +// } \ No newline at end of file diff --git a/src/client/views/nodes/LinkButtonBox.tsx b/src/client/views/nodes/LinkButtonBox.tsx index 8a7c1ed8b..440847ead 100644 --- a/src/client/views/nodes/LinkButtonBox.tsx +++ b/src/client/views/nodes/LinkButtonBox.tsx @@ -1,63 +1,63 @@ -import React = require("react"); -import { library } from '@fortawesome/fontawesome-svg-core'; -import { faCaretUp, faFilePdf, faFilm, faImage, faObjectGroup, faStickyNote } from '@fortawesome/free-solid-svg-icons'; -import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; -import { computed, observable, runInAction } from "mobx"; -import { observer } from "mobx-react"; -import { FieldView, FieldViewProps } from './FieldView'; -import "./LinkButtonBox.scss"; -import { DocumentView } from "./DocumentView"; -import { Doc } from "../../../new_fields/Doc"; -import { LinkButtonField } from "../../../new_fields/LinkButtonField"; -import { Cast, StrCast, BoolCast } from "../../../new_fields/Types"; -import { CollectionDockingView } from "../collections/CollectionDockingView"; -import { DocumentManager } from "../../util/DocumentManager"; -import { Id } from "../../../new_fields/FieldSymbols"; - -library.add(faCaretUp); -library.add(faObjectGroup); -library.add(faStickyNote); -library.add(faFilePdf); -library.add(faFilm); - -@observer -export class LinkButtonBox extends React.Component { - public static LayoutString() { return FieldView.LayoutString(LinkButtonBox); } - - followLink = (): void => { - console.log("follow link???"); - let field = Cast(this.props.Document[this.props.fieldKey], LinkButtonField, new LinkButtonField({ sourceViewId: "-1", targetViewId: "-1" })); - let targetView = DocumentManager.Instance.getDocumentViewById(field.data.targetViewId); - if (targetView && targetView.props.ContainingCollectionView) { - CollectionDockingView.Instance.AddRightSplit(targetView.props.ContainingCollectionView.props.Document); - } - } - - render() { - - let field = Cast(this.props.Document[this.props.fieldKey], LinkButtonField, new LinkButtonField({ sourceViewId: "-1", targetViewId: "-1" })); - let targetView = DocumentManager.Instance.getDocumentViewById(field.data.targetViewId); - - let text = "Could not find link"; - if (targetView) { - let context = targetView.props.ContainingCollectionView ? (" in the context of " + StrCast(targetView.props.ContainingCollectionView.props.Document.title)) : ""; - text = "Link to " + StrCast(targetView.props.Document.title) + context; - } - - let activeDvs = DocumentManager.Instance.DocumentViews.filter(dv => dv.isSelected() || BoolCast(dv.props.Document.libraryBrush, false)); - let display = activeDvs.reduce((found, dv) => { - let matchSv = field.data.sourceViewId === StrCast(dv.props.Document[Id]); - let matchTv = field.data.targetViewId === StrCast(dv.props.Document[Id]); - let match = matchSv || matchTv; - return match || found; - }, false); - - return ( -
-
-

{text}

-
-
- ); - } -} \ No newline at end of file +// import React = require("react"); +// import { library } from '@fortawesome/fontawesome-svg-core'; +// import { faCaretUp, faFilePdf, faFilm, faImage, faObjectGroup, faStickyNote } from '@fortawesome/free-solid-svg-icons'; +// import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; +// import { computed, observable, runInAction } from "mobx"; +// import { observer } from "mobx-react"; +// import { FieldView, FieldViewProps } from './FieldView'; +// import "./LinkButtonBox.scss"; +// import { DocumentView } from "./DocumentView"; +// import { Doc } from "../../../new_fields/Doc"; +// import { LinkButtonField } from "../../../new_fields/LinkButtonField"; +// import { Cast, StrCast, BoolCast } from "../../../new_fields/Types"; +// import { CollectionDockingView } from "../collections/CollectionDockingView"; +// import { DocumentManager } from "../../util/DocumentManager"; +// import { Id } from "../../../new_fields/FieldSymbols"; + +// library.add(faCaretUp); +// library.add(faObjectGroup); +// library.add(faStickyNote); +// library.add(faFilePdf); +// library.add(faFilm); + +// @observer +// export class LinkButtonBox extends React.Component { +// public static LayoutString() { return FieldView.LayoutString(LinkButtonBox); } + +// followLink = (): void => { +// console.log("follow link???"); +// let field = Cast(this.props.Document[this.props.fieldKey], LinkButtonField, new LinkButtonField({ sourceViewId: "-1", targetViewId: "-1" })); +// let targetView = DocumentManager.Instance.getDocumentViewById(field.data.targetViewId); +// if (targetView && targetView.props.ContainingCollectionView) { +// CollectionDockingView.Instance.AddRightSplit(targetView.props.ContainingCollectionView.props.Document); +// } +// } + +// render() { + +// let field = Cast(this.props.Document[this.props.fieldKey], LinkButtonField, new LinkButtonField({ sourceViewId: "-1", targetViewId: "-1" })); +// let targetView = DocumentManager.Instance.getDocumentViewById(field.data.targetViewId); + +// let text = "Could not find link"; +// if (targetView) { +// let context = targetView.props.ContainingCollectionView ? (" in the context of " + StrCast(targetView.props.ContainingCollectionView.props.Document.title)) : ""; +// text = "Link to " + StrCast(targetView.props.Document.title) + context; +// } + +// let activeDvs = DocumentManager.Instance.DocumentViews.filter(dv => dv.isSelected() || BoolCast(dv.props.Document.libraryBrush, false)); +// let display = activeDvs.reduce((found, dv) => { +// let matchSv = field.data.sourceViewId === StrCast(dv.props.Document[Id]); +// let matchTv = field.data.targetViewId === StrCast(dv.props.Document[Id]); +// let match = matchSv || matchTv; +// return match || found; +// }, false); + +// return ( +//
+//
+//

{text}

+//
+//
+// ); +// } +// } \ No newline at end of file diff --git a/src/client/views/nodes/LinkEditor.tsx b/src/client/views/nodes/LinkEditor.tsx index 95199bae2..5f4f7d4f0 100644 --- a/src/client/views/nodes/LinkEditor.tsx +++ b/src/client/views/nodes/LinkEditor.tsx @@ -17,9 +17,8 @@ library.add(faArrowLeft, faEllipsisV, faTable, faTrash, faCog, faExchangeAlt, fa interface GroupTypesDropdownProps { - groupId: string; groupType: string; - setGroup: (groupId: string, group: string) => void; + setGroupType: (group: string) => void; } // this dropdown could be generalized @observer @@ -32,20 +31,20 @@ class GroupTypesDropdown extends React.Component { @action createGroup = (groupType: string): void => { - this.props.setGroup(this.props.groupId, groupType); - LinkManager.Instance.groupMetadataKeys.set(groupType, []); + this.props.setGroupType(groupType); + LinkManager.Instance.addGroupType(groupType); } renderOptions = (): JSX.Element[] | JSX.Element => { if (this._searchTerm === "") return <>; - let allGroupTypes = Array.from(LinkManager.Instance.groupMetadataKeys.keys()); + let allGroupTypes = Array.from(LinkManager.Instance.getAllGroupTypes()); let groupOptions = allGroupTypes.filter(groupType => groupType.toUpperCase().indexOf(this._searchTerm.toUpperCase()) > -1); let exactFound = groupOptions.findIndex(groupType => groupType.toUpperCase() === this._searchTerm.toUpperCase()) > -1; let options = groupOptions.map(groupType => { return
{ this.props.setGroup(this.props.groupId, groupType); this.setGroupType(groupType); this.setSearchTerm(""); }}>{groupType}
; + onClick={() => { this.props.setGroupType(groupType); this.setGroupType(groupType); this.setSearchTerm(""); }}>{groupType}
; }); // if search term does not already exist as a group type, give option to create new group type @@ -85,7 +84,7 @@ class LinkMetadataEditor extends React.Component { @action setMetadataKey = (value: string): void => { - let groupMdKeys = new Array(...LinkManager.Instance.groupMetadataKeys.get(this.props.groupType)!); + let groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType); // don't allow user to create existing key let newIndex = groupMdKeys.findIndex(key => key.toUpperCase() === value.toUpperCase()); @@ -98,12 +97,15 @@ class LinkMetadataEditor extends React.Component { } // set new value for key - let currIndex = groupMdKeys.findIndex(key => key.toUpperCase() === this._key.toUpperCase()); + let currIndex = groupMdKeys.findIndex(key => { + console.log("finding index this", key.toUpperCase(), "that", this._key.toUpperCase()); + return StrCast(key).toUpperCase() === this._key.toUpperCase(); + }); if (currIndex === -1) console.error("LinkMetadataEditor: key was not found"); groupMdKeys[currIndex] = value; this._key = value; - LinkManager.Instance.groupMetadataKeys.set(this.props.groupType, groupMdKeys); + LinkManager.Instance.setMetadataKeysForGroup(this.props.groupType, groupMdKeys); } @action @@ -116,13 +118,13 @@ class LinkMetadataEditor extends React.Component { @action removeMetadata = (): void => { - let groupMdKeys = new Array(...LinkManager.Instance.groupMetadataKeys.get(this.props.groupType)!); + let groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType); let index = groupMdKeys.findIndex(key => key.toUpperCase() === this._key.toUpperCase()); if (index === -1) console.error("LinkMetadataEditor: key was not found"); groupMdKeys.splice(index, 1); - LinkManager.Instance.groupMetadataKeys.set(this.props.groupType, groupMdKeys); + LinkManager.Instance.setMetadataKeysForGroup(this.props.groupType, groupMdKeys); this._key = ""; } @@ -137,215 +139,176 @@ class LinkMetadataEditor extends React.Component { } } - -interface LinkEditorProps { +interface LinkGroupEditorProps { sourceDoc: Doc; linkDoc: Doc; - showLinks: () => void; + groupDoc: Doc; } @observer -export class LinkEditor extends React.Component { +export class LinkGroupEditor extends React.Component { - // map of temporary group id to the corresponding group doc - @observable private _groups: Map = new Map(); - - constructor(props: LinkEditorProps) { - super(props); + @action + setGroupType = (groupType: string): void => { + console.log("SET GROUP TYPE TO", groupType); + this.props.groupDoc.type = groupType; + console.log("GROUP TYPE HAS BEEN SET TO ", StrCast(this.props.groupDoc.type)); + } - let groups = new Map(); - let groupList = LinkManager.Instance.getAnchorGroups(props.linkDoc, props.sourceDoc); - groupList.forEach(groupDoc => { - let id = Utils.GenerateGuid(); - groups.set(id, groupDoc); - }); - this._groups = groups; + removeGroupFromLink = (groupType: string): void => { + LinkManager.Instance.removeGroupFromAnchor(this.props.linkDoc, this.props.sourceDoc, groupType); } - @action - deleteLink = (): void => { - let index = LinkManager.Instance.allLinks.indexOf(this.props.linkDoc); - LinkManager.Instance.allLinks.splice(index, 1); - this.props.showLinks(); + deleteGroup = (groupType: string): void => { + LinkManager.Instance.deleteGroupType(groupType); } - @action - addGroup = (): void => { - // new group only gets added if there is not already a group with type "new group" - let index = Array.from(this._groups.values()).findIndex(groupDoc => { - return groupDoc.type === "New Group"; - }); - if (index > -1) return; + copyGroup = (groupType: string): void => { + let sourceGroupDoc = this.props.groupDoc; + let sourceMdDoc = Cast(sourceGroupDoc.metadata, Doc, new Doc); - // create new metadata document for group - let mdDoc = Docs.TextDocument(); - mdDoc.proto!.anchor1 = this.props.sourceDoc.title; - mdDoc.proto!.anchor2 = LinkManager.Instance.findOppositeAnchor(this.props.linkDoc, this.props.sourceDoc).title; + let destDoc = LinkManager.Instance.getOppositeAnchor(this.props.linkDoc, this.props.sourceDoc); + // let destGroupList = LinkManager.Instance.getAnchorGroups(this.props.linkDoc, destDoc); + let keys = LinkManager.Instance.getMetadataKeysInGroup(groupType); - // create new group document - let groupDoc = Docs.TextDocument(); - groupDoc.proto!.type = "New Group"; - groupDoc.proto!.metadata = mdDoc; + // create new metadata doc with copied kvp + let destMdDoc = new Doc(); + destMdDoc.anchor1 = StrCast(sourceMdDoc.anchor2); + destMdDoc.anchor2 = StrCast(sourceMdDoc.anchor1); + keys.forEach(key => { + let val = sourceMdDoc[key] === undefined ? "" : StrCast(sourceMdDoc[key]); + destMdDoc[key] = val; + }); - this._groups.set(Utils.GenerateGuid(), groupDoc); + // create new group doc with new metadata doc + let destGroupDoc = new Doc(); + destGroupDoc.type = groupType; + destGroupDoc.metadata = destMdDoc; - let linkDoc = this.props.linkDoc.proto ? this.props.linkDoc.proto : this.props.linkDoc; - LinkManager.Instance.setAnchorGroups(linkDoc, this.props.sourceDoc, Array.from(this._groups.values())); + LinkManager.Instance.addGroupToAnchor(this.props.linkDoc, destDoc, destGroupDoc, true); } @action - setGroupType = (groupId: string, groupType: string): void => { - let groupDoc = this._groups.get(groupId); - if (groupDoc) { - groupDoc.proto!.type = groupType; - this._groups.set(groupId, groupDoc); - LinkManager.Instance.setAnchorGroups(this.props.linkDoc, this.props.sourceDoc, Array.from(this._groups.values())); - } - } - - removeGroupFromLink = (groupId: string, groupType: string): void => { - let groupDoc = this._groups.get(groupId); - if (!groupDoc) console.error("LinkEditor: group not found"); - LinkManager.Instance.removeGroupFromAnchor(this.props.linkDoc, this.props.sourceDoc, groupType); - this._groups.delete(groupId); - } - - deleteGroup = (groupId: string, groupType: string): void => { - let groupDoc = this._groups.get(groupId); - if (!groupDoc) console.error("LinkEditor: group not found"); - LinkManager.Instance.deleteGroup(groupType); - this._groups.delete(groupId); + addMetadata = (groupType: string): void => { + let mdKeys = LinkManager.Instance.getMetadataKeysInGroup(groupType); + // only add "new key" if there is no other key with value "new key"; prevents spamming + if (mdKeys.indexOf("new key") === -1) mdKeys.push("new key"); + LinkManager.Instance.setMetadataKeysForGroup(groupType, mdKeys); } - copyGroup = (groupId: string, groupType: string): void => { - let sourceGroupDoc = this._groups.get(groupId); - let sourceMdDoc = Cast(sourceGroupDoc!.metadata, Doc, new Doc); - let destDoc = LinkManager.Instance.findOppositeAnchor(this.props.linkDoc, this.props.sourceDoc); - let destGroupList = LinkManager.Instance.getAnchorGroups(this.props.linkDoc, destDoc); - let keys = LinkManager.Instance.groupMetadataKeys.get(groupType); - - // create new metadata doc with copied kvp - let destMdDoc = Docs.TextDocument(); - destMdDoc.proto!.anchor1 = StrCast(sourceMdDoc.anchor2); - destMdDoc.proto!.anchor2 = StrCast(sourceMdDoc.anchor1); - if (keys) { - keys.forEach(key => { - let val = sourceMdDoc[key] === undefined ? "" : StrCast(sourceMdDoc[key]); - destMdDoc[key] = val; + renderMetadata = (): JSX.Element[] => { + let metadata: Array = []; + let groupDoc = this.props.groupDoc; + let mdDoc = Cast(groupDoc.metadata, Doc, new Doc); + let groupType = StrCast(groupDoc.type); + let groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(groupType); + if (groupMdKeys) { + groupMdKeys.forEach((key, index) => { + metadata.push( + + ); }); } - - // create new group doc with new metadata doc - let destGroupDoc = Docs.TextDocument(); - destGroupDoc.proto!.type = groupType; - destGroupDoc.proto!.metadata = destMdDoc; - - // if group does not already exist on opposite anchor, create group doc - let index = destGroupList.findIndex(groupDoc => { StrCast(groupDoc.type).toUpperCase() === groupType.toUpperCase(); }); - if (index > -1) { - destGroupList[index] = destGroupDoc; - } else { - destGroupList.push(destGroupDoc); - } - - LinkManager.Instance.setAnchorGroups(this.props.linkDoc, destDoc, destGroupList); + return metadata; } - viewGroupAsTable = (groupId: string, groupType: string): JSX.Element => { - let keys = LinkManager.Instance.groupMetadataKeys.get(groupType); - let groupDoc = this._groups.get(groupId); - if (keys && groupDoc) { - let docs: Doc[] = LinkManager.Instance.findAllMetadataDocsInGroup(groupType); - let createTable = action(() => Docs.SchemaDocument(["anchor1", "anchor2", ...keys!], docs, { width: 200, height: 200, title: groupType + " table" })); - let ref = React.createRef(); - return
; - } else { - return ; - } + viewGroupAsTable = (groupType: string): JSX.Element => { + let keys = LinkManager.Instance.getMetadataKeysInGroup(groupType); + let docs: Doc[] = LinkManager.Instance.getAllMetadataDocsInGroup(groupType); + let createTable = action(() => Docs.SchemaDocument(["anchor1", "anchor2", ...keys], docs, { width: 500, height: 300, title: groupType + " table" })); + let ref = React.createRef(); + return
; } - renderGroup = (groupId: string, groupDoc: Doc): JSX.Element => { - let type = StrCast(groupDoc.type); - if ((type && LinkManager.Instance.groupMetadataKeys.get(type)) || type === "New Group") { - let buttons; - if (type === "New Group") { - buttons = ( - <> - - - - - - - ); - } else { - buttons = ( - <> - - - - - {this.viewGroupAsTable(groupId, type)} - - ); - } - - return ( -
-
-

type:

- -
- {this.renderMetadata(groupId)} -
- {buttons} -
-
+ render() { + let groupType = StrCast(this.props.groupDoc.type); + // if ((groupType && LinkManager.Instance.getMetadataKeysInGroup(groupType).length > 0) || groupType === "") { + let buttons; + if (groupType === "") { + buttons = ( + <> + + + + + + ); } else { - return <>; + buttons = ( + <> + + + + + {this.viewGroupAsTable(groupType)} + + ); } + + return ( +
+
+

type:

+ +
+ {this.renderMetadata()} +
+ {buttons} +
+
+ ); } + // else { + // return <>; + // } + // } +} + +interface LinkEditorProps { + sourceDoc: Doc; + linkDoc: Doc; + showLinks: () => void; +} +@observer +export class LinkEditor extends React.Component { @action - addMetadata = (groupType: string): void => { - console.log("ADD MD"); - let mdKeys = LinkManager.Instance.groupMetadataKeys.get(groupType); - if (mdKeys) { - // only add "new key" if there is no other key with value "new key"; prevents spamming - if (mdKeys.indexOf("new key") === -1) mdKeys.push("new key"); - } else { - mdKeys = ["new key"]; - } - LinkManager.Instance.groupMetadataKeys.set(groupType, mdKeys); + deleteLink = (): void => { + LinkManager.Instance.deleteLink(this.props.linkDoc); + this.props.showLinks(); } - renderMetadata = (groupId: string): JSX.Element[] => { - let metadata: Array = []; - let groupDoc = this._groups.get(groupId); - if (groupDoc) { - let mdDoc = Cast(groupDoc.proto!.metadata, Doc, new Doc); - let groupType = StrCast(groupDoc.proto!.type); - let groupMdKeys = LinkManager.Instance.groupMetadataKeys.get(groupType); - if (groupMdKeys) { - groupMdKeys.forEach((key, index) => { - metadata.push( - - ); - }); - } - } - return metadata; + @action + addGroup = (): void => { + // create new metadata document for group + let mdDoc = new Doc(); + mdDoc.anchor1 = this.props.sourceDoc.title; + mdDoc.anchor2 = LinkManager.Instance.getOppositeAnchor(this.props.linkDoc, this.props.sourceDoc).title; + + // create new group document + let groupDoc = new Doc(); + groupDoc.type = ""; + groupDoc.metadata = mdDoc; + + LinkManager.Instance.addGroupToAnchor(this.props.linkDoc, this.props.sourceDoc, groupDoc); } render() { - let destination = LinkManager.Instance.findOppositeAnchor(this.props.linkDoc, this.props.sourceDoc); + let destination = LinkManager.Instance.getOppositeAnchor(this.props.linkDoc, this.props.sourceDoc); - let groups: Array = []; - this._groups.forEach((groupDoc, groupId) => { - groups.push(this.renderGroup(groupId, groupDoc)); + let groupList = LinkManager.Instance.getAnchorGroups(this.props.linkDoc, this.props.sourceDoc); + console.log("NUM GROUPS", groupList.length); + let groups = groupList.map(groupDoc => { + return ; }); + + // let groups: Array = []; + // this._groups.forEach((groupDoc, groupId) => { + // groups.push(this.renderGroup(groupId, groupDoc)); + // }); + return (
diff --git a/src/client/views/nodes/LinkMenu.tsx b/src/client/views/nodes/LinkMenu.tsx index f96c7d2e4..04ca47db3 100644 --- a/src/client/views/nodes/LinkMenu.tsx +++ b/src/client/views/nodes/LinkMenu.tsx @@ -38,7 +38,7 @@ export class LinkMenu extends React.Component { render() { let sourceDoc = this.props.docView.props.Document; - let groups: Map = LinkManager.Instance.findRelatedGroupedLinks(sourceDoc); + let groups: Map = LinkManager.Instance.getRelatedGroupedLinks(sourceDoc); if (this._editingLink === undefined) { return (
diff --git a/src/client/views/nodes/LinkMenuGroup.tsx b/src/client/views/nodes/LinkMenuGroup.tsx index 229143d99..71326f703 100644 --- a/src/client/views/nodes/LinkMenuGroup.tsx +++ b/src/client/views/nodes/LinkMenuGroup.tsx @@ -42,10 +42,10 @@ export class LinkMenuGroup extends React.Component { document.removeEventListener("pointermove", this.onLinkButtonMoved); document.removeEventListener("pointerup", this.onLinkButtonUp); - let draggedDocs = this.props.group.map(linkDoc => LinkManager.Instance.findOppositeAnchor(linkDoc, this.props.sourceDoc)); + let draggedDocs = this.props.group.map(linkDoc => LinkManager.Instance.getOppositeAnchor(linkDoc, this.props.sourceDoc)); let dragData = new DragManager.DocumentDragData(draggedDocs); - DragManager.StartLinkedDocumentDrag([this._drag.current], dragData, e.x, e.y, { + DragManager.StartLinkedDocumentDrag([this._drag.current], this.props.sourceDoc, dragData, e.x, e.y, { handlers: { dragComplete: action(emptyFunction), }, @@ -57,7 +57,7 @@ export class LinkMenuGroup extends React.Component { render() { let groupItems = this.props.group.map(linkDoc => { - let destination = LinkManager.Instance.findOppositeAnchor(linkDoc, this.props.sourceDoc); + let destination = LinkManager.Instance.getOppositeAnchor(linkDoc, this.props.sourceDoc); return ; }); @@ -69,6 +69,6 @@ export class LinkMenuGroup extends React.Component { {groupItems}
- ) + ); } } \ No newline at end of file diff --git a/src/client/views/nodes/LinkMenuItem.tsx b/src/client/views/nodes/LinkMenuItem.tsx index 42ef353b7..28694721d 100644 --- a/src/client/views/nodes/LinkMenuItem.tsx +++ b/src/client/views/nodes/LinkMenuItem.tsx @@ -53,8 +53,8 @@ export class LinkMenuItem extends React.Component { let mdRows: Array = []; if (groupDoc) { let mdDoc = Cast(groupDoc.metadata, Doc, new Doc); - let keys = LinkManager.Instance.groupMetadataKeys.get(this.props.groupType); - mdRows = keys!.map(key => { + let keys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);//groupMetadataKeys.get(this.props.groupType); + mdRows = keys.map(key => { return (
{key}: {StrCast(mdDoc[key])}
); }); } @@ -88,7 +88,7 @@ export class LinkMenuItem extends React.Component { render() { - let keys = LinkManager.Instance.groupMetadataKeys.get(this.props.groupType); + let keys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);//groupMetadataKeys.get(this.props.groupType); let canExpand = keys ? keys.length > 0 : false; return ( diff --git a/src/new_fields/Doc.ts b/src/new_fields/Doc.ts index fda788f2d..9b104184f 100644 --- a/src/new_fields/Doc.ts +++ b/src/new_fields/Doc.ts @@ -234,23 +234,20 @@ export namespace Doc { export function MakeCopy(doc: Doc, copyProto: boolean = false): Doc { const copy = new Doc; Object.keys(doc).forEach(key => { - console.log(key); const field = doc[key]; if (key === "proto" && copyProto) { - console.log(1); if (field instanceof Doc) { - console.log(2); copy[key] = Doc.MakeCopy(field); } } else { if (field instanceof RefField) { - console.log(3); + console.log("equals field, ref", key); copy[key] = field; } else if (field instanceof ObjectField) { - console.log(4); + console.log("copy field, object", key); copy[key] = ObjectField.MakeCopy(field); } else { - console.log(5); + console.log("equals field", key); copy[key] = field; } } diff --git a/src/new_fields/LinkButtonField.ts b/src/new_fields/LinkButtonField.ts index 92e1ed922..e6d1de749 100644 --- a/src/new_fields/LinkButtonField.ts +++ b/src/new_fields/LinkButtonField.ts @@ -1,35 +1,35 @@ -import { Deserializable } from "../client/util/SerializationHelper"; -import { serializable, primitive, createSimpleSchema, object } from "serializr"; -import { ObjectField } from "./ObjectField"; -import { Copy, ToScriptString } from "./FieldSymbols"; -import { Doc } from "./Doc"; -import { DocumentView } from "../client/views/nodes/DocumentView"; +// import { Deserializable } from "../client/util/SerializationHelper"; +// import { serializable, primitive, createSimpleSchema, object } from "serializr"; +// import { ObjectField } from "./ObjectField"; +// import { Copy, ToScriptString } from "./FieldSymbols"; +// import { Doc } from "./Doc"; +// import { DocumentView } from "../client/views/nodes/DocumentView"; -export type LinkButtonData = { - sourceViewId: string, - targetViewId: string -}; +// export type LinkButtonData = { +// sourceViewId: string, +// targetViewId: string +// }; -const LinkButtonSchema = createSimpleSchema({ - sourceViewId: true, - targetViewId: true -}); +// const LinkButtonSchema = createSimpleSchema({ +// sourceViewId: true, +// targetViewId: true +// }); -@Deserializable("linkButton") -export class LinkButtonField extends ObjectField { - @serializable(object(LinkButtonSchema)) - readonly data: LinkButtonData; +// @Deserializable("linkButton") +// export class LinkButtonField extends ObjectField { +// @serializable(object(LinkButtonSchema)) +// readonly data: LinkButtonData; - constructor(data: LinkButtonData) { - super(); - this.data = data; - } +// constructor(data: LinkButtonData) { +// super(); +// this.data = data; +// } - [Copy]() { - return new LinkButtonField(this.data); - } +// [Copy]() { +// return new LinkButtonField(this.data); +// } - [ToScriptString]() { - return "invalid"; - } -} +// [ToScriptString]() { +// return "invalid"; +// } +// } -- cgit v1.2.3-70-g09d2 From d0ff42632f8a155303e11945a1a974a15052f0db Mon Sep 17 00:00:00 2001 From: Fawn Date: Wed, 26 Jun 2019 11:40:36 -0400 Subject: link menu styling --- src/client/util/LinkManager.ts | 44 +--------------------- .../CollectionFreeFormLinksView.tsx | 21 +---------- src/client/views/nodes/DocumentView.tsx | 2 - src/client/views/nodes/LinkEditor.tsx | 1 - src/client/views/nodes/LinkMenu.scss | 25 +++++++++--- src/client/views/nodes/LinkMenuGroup.tsx | 21 ++++++++++- src/client/views/nodes/LinkMenuItem.scss | 2 + 7 files changed, 44 insertions(+), 72 deletions(-) (limited to 'src/client/views/nodes/LinkMenuGroup.tsx') diff --git a/src/client/util/LinkManager.ts b/src/client/util/LinkManager.ts index db814082f..97c816001 100644 --- a/src/client/util/LinkManager.ts +++ b/src/client/util/LinkManager.ts @@ -24,10 +24,6 @@ import { CurrentUserUtils } from "../../server/authentication/models/current_use * - user defined kvps */ export class LinkManager { - // static Instance: LinkManager; - // private constructor() { - // LinkManager.Instance = this; - // } private static _instance: LinkManager; public static get Instance(): LinkManager { @@ -36,12 +32,11 @@ export class LinkManager { private constructor() { } + // the linkmanagerdoc stores a list of docs representing all linkdocs in 'allLinks' and a list of strings representing all group types in 'allGroupTypes' + // lists of strings representing the metadata keys for each group type is stored under a key that is the same as the group type public get LinkManagerDoc(): Doc | undefined { return FieldValue(Cast(CurrentUserUtils.UserDocument.linkManagerDoc, Doc)); } - // @observable public allLinks: Array = []; //List = new List([]); // list of link docs - // @observable public groupMetadataKeys: Map> = new Map(); - // map of group type to list of its metadata keys; serves as a dictionary of groups to what kind of metadata it holds public getAllLinks(): Doc[] { return LinkManager.Instance.LinkManagerDoc ? LinkManager.Instance.LinkManagerDoc.allLinks ? DocListCast(LinkManager.Instance.LinkManagerDoc.allLinks) : [] : []; @@ -160,14 +155,6 @@ export class LinkManager { LinkManager.Instance.setAnchorGroups(linkDoc, anchor, newGroups); } - // public doesAnchorHaveGroup(linkDoc: Doc, anchor: Doc, groupDoc: Doc): boolean { - // let groups = LinkManager.Instance.getAnchorGroups(linkDoc, anchor); - // let index = groups.findIndex(gDoc => { - // return StrCast(groupDoc.type).toUpperCase() === StrCast(gDoc.type).toUpperCase(); - // }); - // return index > -1; - // } - // returns map of group type to anchor's links in that group type public getRelatedGroupedLinks(anchor: Doc): Map> { let related = this.getAllRelatedLinks(anchor); @@ -195,19 +182,6 @@ export class LinkManager { return anchorGroups; } - // public addMetadataKeyToGroup(groupType: string, key: string): boolean { - // if (LinkManager.Instance.LinkManagerDoc) { - // if (LinkManager.Instance.LinkManagerDoc[groupType]) { - // let keyList = LinkManager.Instance.findMetadataKeysInGroup(groupType); - // keyList.push(key); - // LinkManager.Instance.LinkManagerDoc[groupType] = new List(keyList); - // return true; - // } - // return false; - // } - // return false; - // } - public getMetadataKeysInGroup(groupType: string): string[] { if (LinkManager.Instance.LinkManagerDoc) { return LinkManager.Instance.LinkManagerDoc[groupType] ? Cast(LinkManager.Instance.LinkManagerDoc[groupType], listSpec("string"), []) : []; @@ -254,18 +228,4 @@ export class LinkManager { return Cast(linkDoc.anchor1, Doc, new Doc); } } - - - // @action - // public addLinkProxy(proxy: Doc) { - // LinkManager.Instance.linkProxies.push(proxy); - // } - - // public findLinkProxy(sourceViewId: string, targetViewId: string): Doc | undefined { - // let index = LinkManager.Instance.linkProxies.findIndex(p => { - // return StrCast(p.sourceViewId) === sourceViewId && StrCast(p.targetViewId) === targetViewId; - // }); - // return index > -1 ? LinkManager.Instance.linkProxies[index] : undefined; - // } - } \ No newline at end of file diff --git a/src/client/views/collections/collectionFreeForm/CollectionFreeFormLinksView.tsx b/src/client/views/collections/collectionFreeForm/CollectionFreeFormLinksView.tsx index bb8e8a5c2..ebeb1fcee 100644 --- a/src/client/views/collections/collectionFreeForm/CollectionFreeFormLinksView.tsx +++ b/src/client/views/collections/collectionFreeForm/CollectionFreeFormLinksView.tsx @@ -94,24 +94,12 @@ export class CollectionFreeFormLinksView extends React.Component { - // console.log("CONNECTION", StrCast(d.a.props.Document.title), StrCast(d.b.props.Document.title)); - // }); - - // console.log("CONNECTIONS"); - let connections = DocumentManager.Instance.LinkedDocumentViews.reduce((drawnPairs, connection) => { let srcViews = this.documentAnchors(connection.a); let targetViews = this.documentAnchors(connection.b); - // console.log(srcViews.length, targetViews.length); let possiblePairs: { a: Doc, b: Doc, }[] = []; - srcViews.map(sv => { - targetViews.map(tv => { - // console.log("PUSH", StrCast(sv.props.Document.title), StrCast(sv.props.Document.id), StrCast(tv.props.Document.title), StrCast(tv.props.Document.id)); - possiblePairs.push({ a: sv.props.Document, b: tv.props.Document }); - }); - }); + srcViews.map(sv => targetViews.map(tv => possiblePairs.push({ a: sv.props.Document, b: tv.props.Document }))); possiblePairs.map(possiblePair => { if (!drawnPairs.reduce((found, drawnPair) => { let match1 = (Doc.AreProtosEqual(possiblePair.a, drawnPair.a) && Doc.AreProtosEqual(possiblePair.b, drawnPair.b)); @@ -132,13 +120,6 @@ export class CollectionFreeFormLinksView extends React.Component; }); - - // return DocumentManager.Instance.LinkedDocumentViews.map(c => { - // // let x = c.l.reduce((p, l) => p + l[Id], ""); - // let x = c.a.Document[Id] + c.b.Document[Id]; - // return ; - // }); } render() { diff --git a/src/client/views/nodes/DocumentView.tsx b/src/client/views/nodes/DocumentView.tsx index c71d7ed68..d77e08089 100644 --- a/src/client/views/nodes/DocumentView.tsx +++ b/src/client/views/nodes/DocumentView.tsx @@ -162,9 +162,7 @@ export class DocumentView extends DocComponent(Docu this._animateToIconDisposer = reaction(() => this.props.Document.isIconAnimating, (values) => (values instanceof List) && this.animateBetweenIcon(values, values[2], values[3] ? true : false) , { fireImmediately: true }); - // console.log("CREATED NEW DOC VIEW", StrCast(this.props.Document.title), DocumentManager.Instance.DocumentViews.length); DocumentManager.Instance.DocumentViews.push(this); - // console.log("ADDED TO DOC MAN", StrCast(this.props.Document.title), DocumentManager.Instance.DocumentViews.length); } animateBetweenIcon = (iconPos: number[], startTime: number, maximizing: boolean) => { diff --git a/src/client/views/nodes/LinkEditor.tsx b/src/client/views/nodes/LinkEditor.tsx index 80eadf668..87ebeefdb 100644 --- a/src/client/views/nodes/LinkEditor.tsx +++ b/src/client/views/nodes/LinkEditor.tsx @@ -224,7 +224,6 @@ export class LinkGroupEditor extends React.Component { groupMdKeys.forEach((key) => { let val = StrCast(mdDoc[key]); - console.log(key, val); metadata.push( ); diff --git a/src/client/views/nodes/LinkMenu.scss b/src/client/views/nodes/LinkMenu.scss index ae3446e25..1dd933c32 100644 --- a/src/client/views/nodes/LinkMenu.scss +++ b/src/client/views/nodes/LinkMenu.scss @@ -20,13 +20,28 @@ } .linkMenu-group-name { - padding: 4px 6px; - line-height: 12px; - border-radius: 5px; - font-weight: bold; + display: flex; &:hover { - background-color: lightgray; + p { + background-color: lightgray; + width: calc(100% - 26px); + } + .linkEditor-tableButton { + display: block; + } + } + + p { + width: 100%; + padding: 4px 6px; + line-height: 12px; + border-radius: 5px; + font-weight: bold; + } + + .linkEditor-tableButton { + display: none; } } } diff --git a/src/client/views/nodes/LinkMenuGroup.tsx b/src/client/views/nodes/LinkMenuGroup.tsx index 71326f703..732e76997 100644 --- a/src/client/views/nodes/LinkMenuGroup.tsx +++ b/src/client/views/nodes/LinkMenuGroup.tsx @@ -8,8 +8,10 @@ import React = require("react"); import { Doc, DocListCast } from "../../../new_fields/Doc"; import { Id } from "../../../new_fields/FieldSymbols"; import { LinkManager } from "../../util/LinkManager"; -import { DragLinksAsDocuments, DragManager } from "../../util/DragManager"; +import { DragLinksAsDocuments, DragManager, SetupDrag } from "../../util/DragManager"; import { emptyFunction } from "../../../Utils"; +import { Docs } from "../../documents/Documents"; +import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; interface LinkMenuGroupProps { sourceDoc: Doc; @@ -22,6 +24,7 @@ interface LinkMenuGroupProps { export class LinkMenuGroup extends React.Component { private _drag = React.createRef(); + private _table = React.createRef(); onLinkButtonDown = (e: React.PointerEvent): void => { e.stopPropagation(); @@ -55,6 +58,17 @@ export class LinkMenuGroup extends React.Component { e.stopPropagation(); } + viewGroupAsTable = (groupType: string): JSX.Element => { + let keys = LinkManager.Instance.getMetadataKeysInGroup(groupType); + let index = keys.indexOf(""); + if (index > -1) keys.splice(index, 1); + let cols = ["anchor1", "anchor2", ...[...keys]]; + let docs: Doc[] = LinkManager.Instance.getAllMetadataDocsInGroup(groupType); + let createTable = action(() => Docs.SchemaDocument(cols, docs, { width: 500, height: 300, title: groupType + " table" })); + let ref = React.createRef(); + return
; + } + render() { let groupItems = this.props.group.map(linkDoc => { let destination = LinkManager.Instance.getOppositeAnchor(linkDoc, this.props.sourceDoc); @@ -64,7 +78,10 @@ export class LinkMenuGroup extends React.Component { return (
-

{this.props.groupType}:

+
+

{this.props.groupType}:

+ {this.viewGroupAsTable(this.props.groupType)} +
{groupItems}
diff --git a/src/client/views/nodes/LinkMenuItem.scss b/src/client/views/nodes/LinkMenuItem.scss index 25d167231..175a93cb2 100644 --- a/src/client/views/nodes/LinkMenuItem.scss +++ b/src/client/views/nodes/LinkMenuItem.scss @@ -1,4 +1,5 @@ @import "../globalCssVariables"; + .linkMenu-item { // border-top: 0.5px solid $main-accent; position: relative; @@ -13,6 +14,7 @@ padding: 4px 6px; line-height: 12px; border-radius: 5px; + overflow-wrap: break-word; } } -- cgit v1.2.3-70-g09d2 From 681ba524496d40aecb832fc79d68d7695435aed8 Mon Sep 17 00:00:00 2001 From: Fawn Date: Wed, 26 Jun 2019 16:05:24 -0400 Subject: fixed link alias dragging --- src/client/util/DocumentManager.ts | 6 +- src/client/util/DragManager.ts | 25 +- src/client/views/nodes/LinkMenu.scss | 5 +- src/client/views/nodes/LinkMenu.tsx | 2 +- src/client/views/nodes/LinkMenuGroup.tsx | 7 +- ...357\200\277 1 \357\200\272 0], targetContext);" | 792 +++++++++++++++++++++ 6 files changed, 816 insertions(+), 21 deletions(-) create mode 100644 "tance.jumpToDocument(linkedFwdDocs[altKey \357\200\277 1 \357\200\272 0], ctrlKey, false, document =\357\200\276 this.props.addDocTab(document, maxLocation), linkedFwdPage[altKey \357\200\277 1 \357\200\272 0], targetContext);" (limited to 'src/client/views/nodes/LinkMenuGroup.tsx') diff --git a/src/client/util/DocumentManager.ts b/src/client/util/DocumentManager.ts index 877475347..fed30bbdc 100644 --- a/src/client/util/DocumentManager.ts +++ b/src/client/util/DocumentManager.ts @@ -72,11 +72,7 @@ export class DocumentManager { if (doc === toFind) { toReturn.push(view); } else { - // if (Doc.AreProtosEqual(doc, toFind)) { - // toReturn.push(view); - - let docSrc = FieldValue(doc.proto); - if (docSrc && Object.is(docSrc, toFind)) { + if (Doc.AreProtosEqual(doc, toFind)) { toReturn.push(view); } } diff --git a/src/client/util/DragManager.ts b/src/client/util/DragManager.ts index 8e6abe18e..5c75c8fe5 100644 --- a/src/client/util/DragManager.ts +++ b/src/client/util/DragManager.ts @@ -9,6 +9,7 @@ import { URLField } from "../../new_fields/URLField"; import { SelectionManager } from "./SelectionManager"; import { Docs, DocUtils } from "../documents/Documents"; import { DocumentManager } from "./DocumentManager"; +import { Id } from "../../new_fields/FieldSymbols"; export type dropActionType = "alias" | "copy" | undefined; export function SetupDrag(_reference: React.RefObject, docFunc: () => Doc | Promise, moveFunc?: DragManager.MoveFunction, dropAction?: dropActionType, options?: any, dontHideOnDrop?: boolean) { @@ -213,19 +214,25 @@ export namespace DragManager { runInAction(() => StartDragFunctions.map(func => func())); StartDrag(eles, dragData, downX, downY, options, (dropData: { [id: string]: any }) => { - dropData.droppedDocuments = dragData.draggedDocuments.map(d => { - let dv = DocumentManager.Instance.getDocumentView(d); - if (dv) { - if (dv.props.ContainingCollectionView === SelectionManager.SelectedDocuments()[0].props.ContainingCollectionView) { - return d; + // dropData.droppedDocuments = + console.log(dragData.draggedDocuments.length); + let droppedDocuments: Doc[] = dragData.draggedDocuments.reduce((droppedDocs: Doc[], d) => { + let dvs = DocumentManager.Instance.getDocumentViews(d); + console.log(StrCast(d.title), dvs.length); + + if (dvs.length) { + let inContext = dvs.filter(dv => dv.props.ContainingCollectionView === SelectionManager.SelectedDocuments()[0].props.ContainingCollectionView); + if (inContext.length) { + inContext.forEach(dv => droppedDocs.push(dv.props.Document)); } else { - return Doc.MakeAlias(d); + droppedDocs.push(Doc.MakeAlias(d)); } } else { - return Doc.MakeAlias(d); + droppedDocs.push(Doc.MakeAlias(d)); } - }); - + return droppedDocs; + }, []); + dropData.droppedDocuments = droppedDocuments; }); } diff --git a/src/client/views/nodes/LinkMenu.scss b/src/client/views/nodes/LinkMenu.scss index 7cc11172b..a4018bd2d 100644 --- a/src/client/views/nodes/LinkMenu.scss +++ b/src/client/views/nodes/LinkMenu.scss @@ -25,6 +25,8 @@ &:hover { p { background-color: lightgray; + } + p.expand-one { width: calc(100% - 26px); } .linkEditor-tableButton { @@ -131,8 +133,5 @@ } } -.linkEditor-clearButton { - float: right; -} diff --git a/src/client/views/nodes/LinkMenu.tsx b/src/client/views/nodes/LinkMenu.tsx index 71384c368..68fde17a0 100644 --- a/src/client/views/nodes/LinkMenu.tsx +++ b/src/client/views/nodes/LinkMenu.tsx @@ -11,7 +11,7 @@ import { faTrash } from '@fortawesome/free-solid-svg-icons'; import { library } from "@fortawesome/fontawesome-svg-core"; import { FontAwesomeIcon } from "@fortawesome/react-fontawesome"; -library.add(faTrash) +library.add(faTrash); interface Props { docView: DocumentView; diff --git a/src/client/views/nodes/LinkMenuGroup.tsx b/src/client/views/nodes/LinkMenuGroup.tsx index 732e76997..f4e0b8931 100644 --- a/src/client/views/nodes/LinkMenuGroup.tsx +++ b/src/client/views/nodes/LinkMenuGroup.tsx @@ -79,13 +79,14 @@ export class LinkMenuGroup extends React.Component { return (
-

{this.props.groupType}:

- {this.viewGroupAsTable(this.props.groupType)} +

{this.props.groupType}:

+ {this.props.groupType === "*" || this.props.groupType === "" ? <> : this.viewGroupAsTable(this.props.groupType)}
{groupItems}
-
+
); } } \ No newline at end of file diff --git "a/tance.jumpToDocument(linkedFwdDocs[altKey \357\200\277 1 \357\200\272 0], ctrlKey, false, document =\357\200\276 this.props.addDocTab(document, maxLocation), linkedFwdPage[altKey \357\200\277 1 \357\200\272 0], targetContext);" "b/tance.jumpToDocument(linkedFwdDocs[altKey \357\200\277 1 \357\200\272 0], ctrlKey, false, document =\357\200\276 this.props.addDocTab(document, maxLocation), linkedFwdPage[altKey \357\200\277 1 \357\200\272 0], targetContext);" new file mode 100644 index 000000000..0aa3ad47b --- /dev/null +++ "b/tance.jumpToDocument(linkedFwdDocs[altKey \357\200\277 1 \357\200\272 0], ctrlKey, false, document =\357\200\276 this.props.addDocTab(document, maxLocation), linkedFwdPage[altKey \357\200\277 1 \357\200\272 0], targetContext);" @@ -0,0 +1,792 @@ +commit cc1f3b32d60786b56280a8b3c00059aa7823af89 +Merge: a81677c deb8576 +Author: Fawn +Date: Wed Jun 26 14:54:46 2019 -0400 + + merge + +commit a81677c7dffafa5134d4c5cbe893f7a886eaab63 +Author: Fawn +Date: Wed Jun 26 14:48:16 2019 -0400 + + can clear links on a doc + +commit 69e37491908b5c189b94f780994c1f142c69be2e +Author: Fawn +Date: Wed Jun 26 14:15:40 2019 -0400 + + minor changes + +commit deb85766ac5648cc8e3ab4bf9d182ac5bbbbe144 +Merge: 219cabb 5e47775 +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Wed Jun 26 12:51:18 2019 -0400 + + Merge pull request #170 from browngraphicslab/presentation-selection-mohammad + + Presentation selection mohammad + +commit 5e477755b392128ab8b39c082f16dd67708be0d2 +Merge: 444f970 6d1f161 +Author: Sam Wilkins +Date: Wed Jun 26 12:48:45 2019 -0400 + + Merge branch 'presentation-selection-mohammad' of https://github.com/browngraphicslab/Dash-Web into presentation-selection-mohammad + +commit 444f970365a4280376e929e78c16090f6ae92739 +Merge: 64ffa0a 219cabb +Author: Sam Wilkins +Date: Wed Jun 26 12:48:40 2019 -0400 + + merged with master + +commit 6d1f161de3c27ec07673b5e48a915961177b57b6 +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Wed Jun 26 12:39:54 2019 -0400 + + long line wrap + +commit f0632e4f6b608d05ef6d9f77d93da259c58c1e8d +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Wed Jun 26 12:33:16 2019 -0400 + + long line wrap + +commit 0d5e2537520ca1e6a6b52f4d0f03aa2bcfc6c5c6 +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Wed Jun 26 12:30:16 2019 -0400 + + cleanup + +commit 8954bac59b50aa3618625379a17dbefe9aceca72 +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Wed Jun 26 12:29:07 2019 -0400 + + removed console.logs + +commit d0ff42632f8a155303e11945a1a974a15052f0db +Author: Fawn +Date: Wed Jun 26 11:40:36 2019 -0400 + + link menu styling + +commit a3c4aa24a9e9074da8f2421954f610c8178e10b1 +Author: Fawn +Date: Tue Jun 25 21:28:15 2019 -0400 + + link metadata values appear on first load + +commit ca8a78de9957ad27d345ad51fdaee9dae3f096bd +Author: Fawn +Date: Tue Jun 25 20:44:34 2019 -0400 + + can't link to containing collection + +commit 2d300b0cd3d02c900865c61eacd539efed5289e6 +Author: Fawn +Date: Tue Jun 25 20:18:14 2019 -0400 + + fixed link metadata rendering bug + +commit 2a698e88da5ef0a9fee1ff4ee69746f1242798c9 +Author: Fawn +Date: Tue Jun 25 18:32:17 2019 -0400 + + fixed render links in treeview + +commit 7abe170ce5bd0c415e23456eb2bed26e8fdee7aa +Merge: 41cf1e8 219cabb +Author: Fawn +Date: Tue Jun 25 18:23:26 2019 -0400 + + merge + +commit 41cf1e8536964764f18ab752140e484e36cbe464 +Author: Fawn +Date: Tue Jun 25 17:09:36 2019 -0400 + + links can save + +commit 64ffa0accfc872c81035079527952aabaf56c6f6 +Author: Mohammad Amoush +Date: Tue Jun 25 13:16:45 2019 -0400 + + Small Css Fix On weight + +commit 219cabb3fe42ab199550efc3423b7aaed4e1ee93 +Author: Tyler Schicke +Date: Mon Jun 24 22:45:19 2019 -0400 + + Switched shift drag of tabs to normal drag and added drag target for document drag + +commit d475b19e9ba7bc8870ec7bc1e10b5cc88decea0b +Author: Tyler Schicke +Date: Mon Jun 24 15:56:42 2019 -0400 + + fixed crash + +commit 522970375fe0227f9221a7e8be02875afd74ca63 +Author: Fawn +Date: Mon Jun 24 14:01:29 2019 -0400 + + link menu styling + +commit addf0e443f64951a437701f0d5a087c1d5968faf +Merge: c9f77d5 d01039b +Author: tschicke-brown +Date: Mon Jun 24 13:57:02 2019 -0400 + + Merge pull request #167 from browngraphicslab/schema_fixes + + Schema and scripting fixes + +commit d01039b10f0ebd328224c0b1a190b0f884a7c727 +Merge: 6abf829 c9f77d5 +Author: Tyler Schicke +Date: Mon Jun 24 13:56:30 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web into schema_fixes + +commit c9f77d5aab98e6e7865cdcad957d5c937631775d +Author: Tyler Schicke +Date: Mon Jun 24 13:41:39 2019 -0400 + + Added ReadOnly mode for docs and changed computed values a bit + +commit e18662f2fa9e1d3dd1b0eb3b5531092258d05972 +Author: Mohammad Amoush +Date: Mon Jun 24 12:42:44 2019 -0400 + + Refactoring + +commit 52051829373bc4acfe9d705b64c30e3fddebf439 +Author: Tyler Schicke +Date: Mon Jun 24 10:49:05 2019 -0400 + + Fixed image size stuff + +commit ac781d2fb714ca26fb364d00d5aeb7a20b008655 +Author: Tyler Schicke +Date: Mon Jun 24 10:26:57 2019 -0400 + + Changed how zooming works + +commit 6e5cd0e991e2e6d7ae8de1d73ff273ba0737355c +Author: Tyler Schicke +Date: Sun Jun 23 17:23:33 2019 -0400 + + Fixed shift dragging with no open panes + +commit 32ef8d83d5829e2faadbebaf6f9b694df5d7ea02 +Author: Fawn +Date: Fri Jun 21 17:41:20 2019 -0400 + + link menu styling + +commit 7962aff8431b692af5229cd8e6c390bbe1110336 +Author: Fawn +Date: Fri Jun 21 16:29:31 2019 -0400 + + link menu styling + +commit a4b34adcb34184728be0b69b33a561f6d10f0a98 +Author: Fawn +Date: Fri Jun 21 16:27:03 2019 -0400 + + can drag just a group of links on a doc + +commit e1f5f341854944c533efdb7d36306edd1e1dc747 +Author: Mohammad Amoush +Date: Fri Jun 21 14:53:08 2019 -0400 + + Some More documentation + +commit 542f25d4af36cf0948696d45afba2e9e19f5bc37 +Author: Mohammad Amoush +Date: Fri Jun 21 14:47:11 2019 -0400 + + Redo Grouping Fixed + +commit 60f9122ea31d660d60d5429890c4eb0ef6d8613b +Author: Fawn +Date: Fri Jun 21 13:41:25 2019 -0400 + + following link without viewdoc opens it to right + +commit d78c651322ad228152b862eaa378946fe65cc9f9 +Author: Fawn +Date: Fri Jun 21 13:32:23 2019 -0400 + + dragged links from menu are aliases + +commit 179afa6e80631fcb8899408c3961bf1757e5b19b +Merge: ca5e29f a40e7bb +Author: Bob Zeleznik +Date: Thu Jun 20 22:23:40 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit ca5e29fdc7c238274eaf90682a8fa2ddc90e4e17 +Author: Bob Zeleznik +Date: Thu Jun 20 22:22:57 2019 -0400 + + fix to open on right, fix to image drag fro web, and layout fixes for stacking view multi-column + +commit a40e7bb5e9d1256002083d7e3f3c4db60cd8e9df +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Thu Jun 20 19:41:39 2019 -0400 + + Fixed missed pointer up event + +commit f4b75a7c921181faeeee04fbd57cd24fbd57523e +Author: Mohammad Amoush +Date: Thu Jun 20 19:16:42 2019 -0400 + + Undo/Redo First Version + +commit b1a2871fcca57ce934b8613b315a08eede188669 +Author: Fawn +Date: Thu Jun 20 19:03:16 2019 -0400 + + link menu styling + +commit f2b54dc49205f8ea8944e26e43662a0c8dd08ed0 +Merge: 0cab79a 7d0f6c1 +Author: Tyler Schicke +Date: Thu Jun 20 18:36:04 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit 0cab79a50719719e1dade40520a6967f7aa8f951 +Author: Tyler Schicke +Date: Thu Jun 20 18:35:45 2019 -0400 + + Added debug and release modes to server and client + +commit fbfe9faca199b6dedd6844f1fa20cc02060a3c5a +Author: Fawn +Date: Thu Jun 20 18:25:49 2019 -0400 + + can see what docs are linked to in treeview: + +commit 7d0f6c18489f7155818611721985d9610b08d8e7 +Merge: d2dfc0f 46a2a9e +Author: yipstanley +Date: Thu Jun 20 17:50:46 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 1f172642d12c4669960b8526324e4bd034994be4 +Author: Tyler Schicke +Date: Thu Jun 20 17:44:24 2019 -0400 + + Added arrange documents in grid command + +commit d2dfc0f9d35f0084a7c0dea73215f5d21055f2f3 +Author: yipstanley +Date: Thu Jun 20 17:17:14 2019 -0400 + + pdf page sizes loading error + +commit e6ebed17e6ddb2ccee81d65fcb451a9b54302762 +Author: Fawn +Date: Thu Jun 20 17:12:48 2019 -0400 + + links can be made from freeform view to treeview + +commit 46a2a9e1f10b63feeb21a1e186daeaef2ccbcda4 +Merge: a39b285 a5dc0e0 +Author: bob +Date: Thu Jun 20 17:11:29 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit a39b2854b848006c19460685d7bf4005a9f650ae +Author: bob +Date: Thu Jun 20 17:09:50 2019 -0400 + + moved AddDocToList to Doc utils + +commit a5dc0e04add05f2f5bf1e17f1ac0a5e0aba1ea41 +Author: Tyler Schicke +Date: Thu Jun 20 16:27:44 2019 -0400 + + Added hidden flag to documents + +commit e88538bb8af2ba648da2326d0f6edd3e0186766e +Author: Mohammad Amoush +Date: Thu Jun 20 15:45:07 2019 -0400 + + Title changing to presentations added + +commit 9b3e80def0be6c09c31b5176817a54323d217d81 +Author: Tyler Schicke +Date: Thu Jun 20 15:06:41 2019 -0400 + + Handled more events in editable view + +commit 1f24c5010a1cf6365265ea1f02327bb81a98134a +Author: Tyler Schicke +Date: Thu Jun 20 14:54:55 2019 -0400 + + Doc.GetProto change and swapped KVP syntax + +commit 4360287e6cafcb59af1ae62fc31ddc161bcf2e51 +Author: Fawn +Date: Thu Jun 20 12:56:13 2019 -0400 + + styling of link proxy + +commit 711abbeba69e4d9afc634b8edf019b12b6dff915 +Author: Mohammad Amoush +Date: Thu Jun 20 12:54:41 2019 -0400 + + Documentation and reset Presentation at removal fixed + +commit a0246ef84396545f79fc4a8b21de1a56cbf06aca +Author: Fawn +Date: Thu Jun 20 11:34:28 2019 -0400 + + merge + +commit 8dbfb3029a99eaf37a5234e9d9e33cc64f779b03 +Merge: af8e5cf e9d62f4 +Author: Tyler Schicke +Date: Thu Jun 20 11:33:01 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit af8e5cf1bfbfa2d57b4fd89c72306a71d8cabe1d +Author: Tyler Schicke +Date: Thu Jun 20 11:32:54 2019 -0400 + + Fixed context menu search + +commit cd2db5bf11fb89e3cd7016f7f798d65698c74c5e +Merge: 73f0378 e9d62f4 +Author: Fawn +Date: Thu Jun 20 11:31:15 2019 -0400 + + merge + +commit 73f03785f938542a91b28b35043f2feda2bc1432 +Author: Fawn +Date: Thu Jun 20 11:26:33 2019 -0400 + + merge + +commit e9d62f4ca0dbeb57e46239047041a8a04da7b504 +Author: bob +Date: Thu Jun 20 11:26:16 2019 -0400 + + changed color picker. fixed delting selected docs. fixed scaling items in nested panels. + +commit a5478b2d4cc3b66c6b58471cbb05c623d0109724 +Author: Tyler Schicke +Date: Thu Jun 20 10:04:51 2019 -0400 + + "Fixed" search + +commit 01aee875e626c695fe208addaaa6f58aad387dd6 +Author: Tyler Schicke +Date: Thu Jun 20 10:02:08 2019 -0400 + + Mostly keep context menu on screen + +commit 38de022621175bda7410df4444fcd2bbee0919cb +Author: Bob Zeleznik +Date: Wed Jun 19 23:43:47 2019 -0400 + + slight tweaks. + +commit 9e55bfaad39aa47ab0594c6af7f1aa68e2a8db7a +Merge: 118ecb1 827c589 +Author: Bob Zeleznik +Date: Wed Jun 19 22:40:57 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 118ecb14ce519bcbade12b3d52e11b22fcc371b3 +Author: Bob Zeleznik +Date: Wed Jun 19 22:40:54 2019 -0400 + + cleaned up and enhanced tree view + +commit c5e401cb0a7fec2279ceecbc8d1429dcdd2f04b9 +Author: Fawn +Date: Wed Jun 19 22:27:21 2019 -0400 + + buttons on cut links functional except for when dragged from link menu + +commit 6fc6054dc7aea144fd967a8cb3fe7d8fe5ec6d6d +Author: Mohammad Amoush +Date: Wed Jun 19 19:13:30 2019 -0400 + + Width of the presentations fixed, removal of presentations option added, backUP group and normal groups updated when a doc is removed from presentation by removing it from both + +commit 827c58950b649629c84211d41fdd4d041287801e +Merge: 05e50f2 96c26c5 +Author: Tyler Schicke +Date: Wed Jun 19 18:49:50 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit 96c26c57527d443784bde9752551bfa10b3ce4d2 +Author: Bob Zeleznik +Date: Wed Jun 19 18:34:45 2019 -0400 + + removed marquee summarizing icon + +commit 05e50f27a15e8a02ffb27606c51026d1b85bc677 +Author: Tyler Schicke +Date: Wed Jun 19 17:36:52 2019 -0400 + + Added basic keyboard controls to context menu + +commit fa37e023b88127cb8a6b393a848200361a396fb4 +Merge: 565b27c 5b2a498 +Author: Tyler Schicke +Date: Wed Jun 19 16:21:09 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit 565b27cca8953a60067de367cae4c0a99beb3cab +Author: Tyler Schicke +Date: Wed Jun 19 16:21:03 2019 -0400 + + started adding selection to context menu + +commit 5b2a498aca75bd53ffab61f998218bec546b8154 +Merge: 358437e 39e8a7a +Author: bob +Date: Wed Jun 19 16:17:21 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 358437eeafe42e029ffe27702bde15a3fad54a3b +Author: bob +Date: Wed Jun 19 16:17:18 2019 -0400 + + working version of embedded tree view docs. + +commit 4c1383e47f2203a00bc7f3d73c209f3149d6a772 +Author: Mohammad Amoush +Date: Wed Jun 19 15:53:05 2019 -0400 + + ... + +commit a288a2fd0a30a3a16dd01bc4e12dcf6bc117c766 +Author: Mohammad Amoush +Date: Wed Jun 19 15:25:24 2019 -0400 + + Navigation and Zoom Option For Manual Selection Added and New Presentation TItle Naming Added + + Now, You can manually click on navigate or zoom and navigate to that document if current was their index. A way to manually disregard groups, and just navigate to that doc. + +commit 39e8a7a365442cdc11024c4de8019184fd0057ac +Merge: 5b6f13d 9ab4739 +Author: Stanley Yip <33562077+yipstanley@users.noreply.github.com> +Date: Wed Jun 19 15:05:38 2019 -0400 + + Merge pull request #163 from browngraphicslab/pdf_fixes + + deleting annotations + +commit 5b6f13d64e9e38b94df0ae61ffedcb0b34290045 +Merge: 35e73f3 4ebbdd8 +Author: Tyler Schicke +Date: Wed Jun 19 15:04:46 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit 35e73f369a2145d8a042e0011a43e71763d57998 +Author: Tyler Schicke +Date: Wed Jun 19 15:02:48 2019 -0400 + + added better search to context menu + +commit 9ab47393a2ce3d174ad3238422c2c310764be9af +Author: yipstanley +Date: Wed Jun 19 14:40:28 2019 -0400 + + interaction improvements with delete button + +commit b9849810231e540a5898a56012abd32c197b23b5 +Author: yipstanley +Date: Wed Jun 19 14:39:15 2019 -0400 + + anna + +commit b960a876d6a31b3eaebb0ac6eca6f191a0d4c900 +Author: yipstanley +Date: Wed Jun 19 14:38:43 2019 -0400 + + oop + +commit 46d57bc21cda4703855b85a4603bd471975d845b +Author: yipstanley +Date: Wed Jun 19 14:25:47 2019 -0400 + + deleting annotations + +commit f362dbfc237536c6c4a8c6d088c3dc818080f7c2 +Author: Fawn +Date: Wed Jun 19 12:50:58 2019 -0400 + + both tail ends of a cut link appear on hover/focus of an anchor + +commit fb62f3b2e39bbe2dd3da5eaffedbaa8e60f06dbb +Author: Mohammad Amoush +Date: Wed Jun 19 12:35:54 2019 -0400 + + Grouping for different presentations fixed + +commit 4ebbdd803cdf83806902509dfa0432ce3a139403 +Merge: 0bb2052 c056ade +Author: Stanley Yip <33562077+yipstanley@users.noreply.github.com> +Date: Wed Jun 19 11:48:16 2019 -0400 + + Merge pull request #162 from browngraphicslab/pdf_fixes + + Pdf fixes + +commit c056adeca11f35972b5f75c6b1cc31292d5765d4 +Author: yipstanley +Date: Wed Jun 19 11:47:20 2019 -0400 + + push + +commit 37f327ab659e6fa1221f9f4ed7649402c5dedc00 +Author: yipstanley +Date: Wed Jun 19 11:24:32 2019 -0400 + + aspect ratio, dragging, and full screen scrolling fixed + +commit 0bb20528c8167b3ba1c4c88d97586d50ae183b4c +Author: bob +Date: Wed Jun 19 10:37:36 2019 -0400 + + added highlight for expanded tree view items + +commit f60398d5db9041e09c809c16a0b885936ac11a3d +Author: bob +Date: Wed Jun 19 10:21:37 2019 -0400 + + fixed multi-column stacking + +commit 0674331f3611d297028526c888c718a75b012e0a +Author: bob +Date: Wed Jun 19 09:36:21 2019 -0400 + + fixed resizing stacking views. changed defaults for new docs in treeView + +commit 1472d2b56aa64896f0a93f172322121d19cd1592 +Author: bob +Date: Wed Jun 19 09:11:35 2019 -0400 + + fixed lint errors. + +commit 8c94bb92b23dea138fa752929b6134e7214dfb60 +Merge: 3b880d7 13e301d +Author: Bob Zeleznik +Date: Tue Jun 18 22:51:48 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 3b880d7b15b7107049ae27601b9f759b17f7fde9 +Author: Bob Zeleznik +Date: Tue Jun 18 22:51:46 2019 -0400 + + added initial keyboard shortcuts for adding and moving docs in TreeView. fixed image drag bug. + +commit 13e301dea2f537b67b338cc6a98d3f3b5a8e1f36 +Author: Tyler Schicke +Date: Tue Jun 18 20:58:32 2019 -0400 + + Fixed linter errors + +commit 464fa03d6ebb2a7aaef1d7622afa3e1e7ee816a3 +Author: Tyler Schicke +Date: Tue Jun 18 20:11:31 2019 -0400 + + Context menu improvements and error fixes + +commit 4ffcff69a2fc767c6a03d46d7296b6a8c7ffd281 +Author: madelinegr +Date: Tue Jun 18 19:13:45 2019 -0400 + + Presentations Listed, Option to Change Added, and + +commit ca126adda9e4def83fb5c2e07e382917ca0b4ee0 +Author: Tyler Schicke +Date: Tue Jun 18 17:24:59 2019 -0400 + + Fixed docking view? + +commit b0ac30172019713e1c75083c1199485d902e0eed +Author: Tyler Schicke +Date: Tue Jun 18 16:37:28 2019 -0400 + + Fixed zoomBasis stuff and added deletion handling for reponse from server + +commit 8e5afb5bbb47324a381b5184254e77eba7bd8536 +Author: Fawn +Date: Tue Jun 18 16:30:24 2019 -0400 + + can click on button link to node in different context than source + +commit 6fcd0d8d6fb1471b8af460f6d80bdf0d0e681566 +Author: Fawn +Date: Tue Jun 18 15:17:27 2019 -0400 + + added button to delete a link + +commit d91e7eec9a62363b383b929166cdf600b124334c +Author: Fawn +Date: Tue Jun 18 15:09:21 2019 -0400 + + links to nodes in different contexts render as a circle + +commit d3cad099d49690810166d0342f7c371bda0f007e +Merge: 04668e2 b1af251 +Author: bob +Date: Tue Jun 18 13:30:55 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 04668e21313f6e62e5ab35ac737fc54191769a5a +Author: bob +Date: Tue Jun 18 13:30:41 2019 -0400 + + fixed cleanup of marquee keyhandler. + +commit b1af251b058743798aa3fa3895d22327c8560dfc +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Tue Jun 18 13:19:50 2019 -0400 + + Added pointer down flag for tab focus + +commit 9544576ec0167d64f564ae4c87d392eba07ff467 +Author: Sam Wilkins <35748010+samwilkins333@users.noreply.github.com> +Date: Tue Jun 18 13:18:34 2019 -0400 + + Added tab focusing on hover + +commit 2633f61d311528e62d50d4ff56f5884b3b51ac61 +Author: bob +Date: Tue Jun 18 13:12:15 2019 -0400 + + added undo/redo bindings for app. + +commit 3a25bad918c72f5d6de9a720de9e0d316c00f2fe +Author: bob +Date: Tue Jun 18 13:03:28 2019 -0400 + + fixed issues with expanding text boxes that have a dynamic title + +commit f4fcf306e2579b7479610899a01c06fb157d47de +Author: bob +Date: Tue Jun 18 12:03:14 2019 -0400 + + fixed goldenlayout nesting + +commit 4f0086f6ea948c1c5254db2acc93f6735987daa5 +Merge: 749eef1 d7ebe7b +Author: bob +Date: Tue Jun 18 11:31:49 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 749eef13af1338225b2bec4dbcd7a50a5650d285 +Author: bob +Date: Tue Jun 18 11:31:46 2019 -0400 + + fixed image drag drop when not selected. + +commit d7ebe7b7d19cf7dc797443aa485293670c3ee4e2 +Merge: 66d4cc9 08872de +Author: yipstanley +Date: Tue Jun 18 11:08:44 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 66d4cc94bcc69f590d90dd35823f93b8e2fb90d8 +Author: yipstanley +Date: Tue Jun 18 10:52:10 2019 -0400 + + selection fixes + +commit 08872def596af073c5f14336c8faf07f44561bbc +Merge: 8d00265 c50ba1c +Author: bob +Date: Tue Jun 18 10:28:31 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit 8d0026573ad9a196f864490bcf07c78f54082bad +Author: bob +Date: Tue Jun 18 10:28:29 2019 -0400 + + fixed selection within multicolumn stacking view. added drop of html image selections. + +commit c50ba1c4cc01d5cd085dee0dae6f633164efeb80 +Merge: cc032e2 64e6a94 +Author: yipstanley +Date: Tue Jun 18 10:10:58 2019 -0400 + + Merge branch 'master' of https://github.com/browngraphicslab/Dash-Web + +commit cc032e2f60015728f64f46ef009c9306e36746a0 +Author: yipstanley +Date: Tue Jun 18 10:05:49 2019 -0400 + + fixes + +commit 64e6a941639aab8d7109178aa151a50909547309 +Author: Bob Zeleznik +Date: Tue Jun 18 09:05:41 2019 -0400 + + fixed index out of range + +commit 4b8324fcf44c5d3c3a4b3f6e98a4d1dfce84811b +Author: Bob Zeleznik +Date: Tue Jun 18 08:53:01 2019 -0400 + + removed trace + +commit a3b8a57027d7c45ea19d259e1ec18fa6a8648c24 +Author: Bob Zeleznik +Date: Tue Jun 18 08:49:02 2019 -0400 + + looked like wrong code... + +commit 2f5c38c6a0a5220c2a31931c34d94e199854d703 +Author: Bob Zeleznik +Date: Tue Jun 18 08:36:37 2019 -0400 + + more streamlining + +commit 62c781c0c79ac395c5e117d208a90485ff1ba599 +Author: Bob Zeleznik +Date: Tue Jun 18 02:19:07 2019 -0400 + + faster loading of PDFs + +commit 4dc8c03562a0473becb895824740da487e16e771 +Author: Bob Zeleznik +Date: Tue Jun 18 00:17:58 2019 -0400 + + added dropping of Dash urls from gmail + +commit 9c7ff72a8ad249c05b672a46e3fbbb69ffca3a2a +Merge: 8c64ffd 71b1cfb +Author: Tyler Schicke +Date: Mon Jun 17 23:04:22 2019 -0400 + + Merge branch 'master' of github-tsch-brown:browngraphicslab/Dash-Web + +commit 8c64ffd92e382050bc8727981cf9fb830e4f02a7 +Author: Tyler Schicke +Date: Mon Jun 17 23:04:07 2019 -0400 + + Added share with user functionality -- cgit v1.2.3-70-g09d2