aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/client/util/CurrentUserUtils.ts2
-rw-r--r--src/client/util/LinkManager.ts83
-rw-r--r--src/client/views/MainView.scss1
-rw-r--r--src/client/views/PropertiesView.tsx4
-rw-r--r--src/client/views/linking/LinkEditor.tsx264
-rw-r--r--src/client/views/linking/LinkMenuGroup.tsx11
-rw-r--r--src/client/views/linking/LinkMenuItem.tsx19
7 files changed, 10 insertions, 374 deletions
diff --git a/src/client/util/CurrentUserUtils.ts b/src/client/util/CurrentUserUtils.ts
index ec550c15a..f6ac363da 100644
--- a/src/client/util/CurrentUserUtils.ts
+++ b/src/client/util/CurrentUserUtils.ts
@@ -986,9 +986,9 @@ export class CurrentUserUtils {
this.setupDockedButtons(doc); // the bottom bar of font icons
await this.setupSidebarButtons(doc); // the pop-out left sidebar of tools/panels
await this.setupMenuPanel(doc, sharingDocumentId);
- doc.globalLinkDatabase = Docs.Prototypes.MainLinkDocument();
doc.globalScriptDatabase = Docs.Prototypes.MainScriptDocument();
doc.globalGroupDatabase = Docs.Prototypes.MainGroupDocument();
+ if (!doc.myLinkDatabase) doc.myLinkDatabase = new List([]);
setTimeout(() => this.setupDefaultPresentation(doc), 0); // presentation that's initially triggered
diff --git a/src/client/util/LinkManager.ts b/src/client/util/LinkManager.ts
index 269de08a1..0371dc4d9 100644
--- a/src/client/util/LinkManager.ts
+++ b/src/client/util/LinkManager.ts
@@ -2,7 +2,7 @@ import { Doc, DocListCast, Opt } from "../../fields/Doc";
import { List } from "../../fields/List";
import { listSpec } from "../../fields/Schema";
import { Cast, StrCast } from "../../fields/Types";
-import { CurrentUserUtils } from "./CurrentUserUtils";
+import { SharingManager } from "./SharingManager";
/*
* link doc:
@@ -33,31 +33,19 @@ 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 Doc.UserDoc().globalLinkDatabase as Doc;
- }
public getAllLinks(): Doc[] {
- const ldoc = LinkManager.Instance.LinkManagerDoc;
- return ldoc ? DocListCast(ldoc.data) : [];
+ const lset = new Set<Doc>(DocListCast(Doc.UserDoc().myLinkDatabase));
+ SharingManager.Instance.users.forEach(user => DocListCast(user.sharingDoc.myLinkDatabase).map(lset.add));
+ return Array.from(lset);
}
public addLink(linkDoc: Doc): boolean {
- if (LinkManager.Instance.LinkManagerDoc) {
- Doc.AddDocToList(LinkManager.Instance.LinkManagerDoc, "data", linkDoc);
- return true;
- }
- return false;
+ return Doc.AddDocToList(Doc.UserDoc(), "myLinkDatabase", linkDoc);
}
public deleteLink(linkDoc: Doc): boolean {
- if (LinkManager.Instance.LinkManagerDoc && linkDoc instanceof Doc) {
- Doc.RemoveDocFromList(LinkManager.Instance.LinkManagerDoc, "data", linkDoc);
- return true;
- }
- return false;
+ return Doc.RemoveDocFromList(Doc.UserDoc(), "myLinkDatabase", linkDoc);
}
// finds all links that contain the given anchor
@@ -85,49 +73,6 @@ export class LinkManager {
related.forEach(linkDoc => LinkManager.Instance.deleteLink(linkDoc));
}
- public addGroupType(groupType: string): boolean {
- if (LinkManager.Instance.LinkManagerDoc) {
- LinkManager.Instance.LinkManagerDoc[groupType] = new List<string>([]);
- const groupTypes = LinkManager.Instance.getAllGroupTypes();
- groupTypes.push(groupType);
- LinkManager.Instance.LinkManagerDoc.allGroupTypes = new List<string>(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]) {
- const groupTypes = LinkManager.Instance.getAllGroupTypes();
- const index = groupTypes.findIndex(type => type.toUpperCase() === groupType.toUpperCase());
- if (index > -1) groupTypes.splice(index, 1);
- LinkManager.Instance.LinkManagerDoc.allGroupTypes = new List<string>(groupTypes);
- LinkManager.Instance.LinkManagerDoc[groupType] = undefined;
- LinkManager.Instance.getAllLinks().forEach(async linkDoc => {
- const anchor1 = await Cast(linkDoc.anchor1, Doc);
- const anchor2 = await Cast(linkDoc.anchor2, Doc);
- anchor1 && LinkManager.Instance.removeGroupFromAnchor(linkDoc, anchor1, groupType);
- anchor2 && LinkManager.Instance.removeGroupFromAnchor(linkDoc, anchor2, 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<string>([]);
- return [];
- }
- }
- return [];
- }
-
// gets the groups associates with an anchor in a link
public getAnchorGroups(linkDoc: Doc, anchor?: Doc): Array<Doc> {
if (Doc.AreProtosEqual(anchor, Cast(linkDoc.anchor1, Doc, null))) {
@@ -164,22 +109,6 @@ export class LinkManager {
return anchorGroups;
}
- // gets a list of strings representing the keys of the metadata associated with the given group type
- 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) {
- LinkManager.Instance.LinkManagerDoc[groupType] = new List<string>(keys);
- return true;
- }
- return false;
- }
-
// returns a list of all metadata docs associated with the given group type
public getAllMetadataDocsInGroup(groupType: string): Array<Doc> {
const md: Doc[] = [];
diff --git a/src/client/views/MainView.scss b/src/client/views/MainView.scss
index 5efe9adad..b608eceb1 100644
--- a/src/client/views/MainView.scss
+++ b/src/client/views/MainView.scss
@@ -293,7 +293,6 @@
.mainView-libraryFlyout-out,
.mainView-libraryFlyout {
height: 100%;
- width: 100%;
position: relative;
display: flex;
flex-direction: column;
diff --git a/src/client/views/PropertiesView.tsx b/src/client/views/PropertiesView.tsx
index f3241e8d9..a64004c5c 100644
--- a/src/client/views/PropertiesView.tsx
+++ b/src/client/views/PropertiesView.tsx
@@ -972,7 +972,7 @@ export class PropertiesView extends React.Component<PropertiesViewProps> {
</div>
{this.openContexts ? <div className="propertiesView-contexts-content" >{this.contexts}</div> : null}
</div>
- <div className="propertiesView-layout">
+ {/* <div className="propertiesView-layout">
<div className="propertiesView-layout-title"
onPointerDown={action(() => this.openLayout = !this.openLayout)}
style={{ backgroundColor: this.openLayout ? "black" : "" }}>
@@ -982,7 +982,7 @@ export class PropertiesView extends React.Component<PropertiesViewProps> {
</div>
</div>
{this.openLayout ? <div className="propertiesView-layout-content" >{this.layoutPreview}</div> : null}
- </div>
+ </div> */}
</div>;
}
if (this.isPres) {
diff --git a/src/client/views/linking/LinkEditor.tsx b/src/client/views/linking/LinkEditor.tsx
index 3713a1026..435b9d904 100644
--- a/src/client/views/linking/LinkEditor.tsx
+++ b/src/client/views/linking/LinkEditor.tsx
@@ -10,264 +10,6 @@ import { undoBatch } from "../../util/UndoManager";
import './LinkEditor.scss';
import React = require("react");
-interface GroupTypesDropdownProps {
- groupType: string;
- setGroupType: (group: string) => void;
-}
-// this dropdown could be generalized
-@observer
-class GroupTypesDropdown extends React.Component<GroupTypesDropdownProps> {
- @observable private _searchTerm: string = this.props.groupType;
- @observable private _groupType: string = this.props.groupType;
- @observable private _isEditing: boolean = false;
-
- @action
- createGroup = (groupType: string): void => {
- this.props.setGroupType(groupType);
- LinkManager.Instance.addGroupType(groupType);
- }
-
- @action
- onChange = (val: string): void => {
- this._searchTerm = val;
- this._groupType = val;
- this._isEditing = true;
- }
-
- @action
- onKeyDown = (e: React.KeyboardEvent): void => {
- if (e.key === "Enter") {
- const allGroupTypes = Array.from(LinkManager.Instance.getAllGroupTypes());
- const groupOptions = allGroupTypes.filter(groupType => groupType.toUpperCase().indexOf(this._searchTerm.toUpperCase()) > -1);
- const exactFound = groupOptions.findIndex(groupType => groupType.toUpperCase() === this._searchTerm.toUpperCase());
-
- if (exactFound > -1) {
- const groupType = groupOptions[exactFound];
- this.props.setGroupType(groupType);
- this._groupType = groupType;
- } else {
- this.createGroup(this._searchTerm);
- this._groupType = this._searchTerm;
- }
-
- this._searchTerm = this._groupType;
- this._isEditing = false;
- }
- }
-
- @action
- onOptionClick = (value: string, createNew: boolean): void => {
- if (createNew) {
- this.createGroup(this._searchTerm);
- this._groupType = this._searchTerm;
-
- } else {
- this.props.setGroupType(value);
- this._groupType = value;
-
- }
- this._searchTerm = this._groupType;
- this._isEditing = false;
- }
-
- @action
- onButtonPointerDown = (): void => {
- this._isEditing = true;
- }
-
- renderOptions = (): JSX.Element[] | JSX.Element => {
- if (this._searchTerm === "") return <></>;
-
- const allGroupTypes = Array.from(LinkManager.Instance.getAllGroupTypes());
- const groupOptions = allGroupTypes.filter(groupType => groupType.toUpperCase().indexOf(this._searchTerm.toUpperCase()) > -1);
- const exactFound = groupOptions.findIndex(groupType => groupType.toUpperCase() === this._searchTerm.toUpperCase()) > -1;
-
- const options = groupOptions.map(groupType => {
- const ref = React.createRef<HTMLDivElement>();
- return <div key={groupType} ref={ref} className="linkEditor-option"
- onClick={() => this.onOptionClick(groupType, false)}>{groupType}</div>;
- });
-
- // if search term does not already exist as a group type, give option to create new group type
- if (!exactFound && this._searchTerm !== "") {
- const ref = React.createRef<HTMLDivElement>();
- options.push(<div key={""} ref={ref} className="linkEditor-option"
- onClick={() => this.onOptionClick(this._searchTerm, true)}>Define new "{this._searchTerm}" relationship</div>);
- }
-
- return options;
- }
-
- render() {
- if (this._isEditing || this._groupType === "") {
- return (
- <div className="linkEditor-dropdown">
- <input type="text" value={this._groupType === "-ungrouped-" ? "" : this._groupType} placeholder="Search for or create a new group"
- onChange={e => this.onChange(e.target.value)} onKeyDown={this.onKeyDown} autoFocus></input>
- <div className="linkEditor-options-wrapper">
- {this.renderOptions()}
- </div>
- </div >
- );
- } else {
- return <button className="linkEditor-typeButton" onClick={() => this.onButtonPointerDown()}>{this._groupType}</button>;
- }
- }
-}
-
-
-interface LinkMetadataEditorProps {
- id: string;
- groupType: string;
- mdDoc: Doc;
- mdKey: string;
- mdValue: string;
- changeMdIdKey: (id: string, newKey: string) => void;
-}
-@observer
-class LinkMetadataEditor extends React.Component<LinkMetadataEditorProps> {
- @observable private _key: string = this.props.mdKey;
- @observable private _value: string = this.props.mdValue;
- @observable private _keyError: boolean = false;
-
- @action
- setMetadataKey = (value: string): void => {
- const groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);
-
- // don't allow user to create existing key
- const newIndex = groupMdKeys.findIndex(key => key.toUpperCase() === value.toUpperCase());
- if (newIndex > -1) {
- this._keyError = true;
- this._key = value;
- return;
- } else {
- this._keyError = false;
- }
-
- // set new value for key
- const currIndex = groupMdKeys.findIndex(key => {
- return StrCast(key).toUpperCase() === this._key.toUpperCase();
- });
- if (currIndex === -1) console.error("LinkMetadataEditor: key was not found");
- groupMdKeys[currIndex] = value;
-
- this.props.changeMdIdKey(this.props.id, value);
- this._key = value;
- LinkManager.Instance.setMetadataKeysForGroup(this.props.groupType, [...groupMdKeys]);
- }
-
- @action
- setMetadataValue = (value: string): void => {
- if (!this._keyError) {
- this._value = value;
- Doc.GetProto(this.props.mdDoc)[this._key] = value;
- }
- }
-
- @action
- removeMetadata = (): void => {
- const groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);
-
- const 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.setMetadataKeysForGroup(this.props.groupType, groupMdKeys);
- this._key = "";
- }
-
- render() {
- return (
- <div className="linkEditor-metadata-row">
- <input className={this._keyError ? "linkEditor-error" : ""} type="text" value={this._key === "new key" ? "" : this._key} placeholder="key" onChange={e => this.setMetadataKey(e.target.value)}></input>:
- <input type="text" value={this._value} placeholder="value" onChange={e => this.setMetadataValue(e.target.value)}></input>
- <button title="remove metadata from relationship" onClick={() => this.removeMetadata()}><FontAwesomeIcon icon="times" size="sm" /></button>
- </div>
- );
- }
-}
-
-interface LinkGroupEditorProps {
- sourceDoc: Doc;
- linkDoc: Doc;
- groupDoc: Doc;
-}
-@observer
-export class LinkGroupEditor extends React.Component<LinkGroupEditorProps> {
-
- private _metadataIds: Map<string, string> = new Map();
-
- constructor(props: LinkGroupEditorProps) {
- super(props);
-
- const groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(StrCast(props.groupDoc.linkRelationship));
- groupMdKeys.forEach(key => this._metadataIds.set(key, Utils.GenerateGuid()));
- }
-
- @action
- setGroupType = (groupType: string): void => {
- Doc.GetProto(this.props.groupDoc).linkRelationship = groupType;
- }
-
- removeGroupFromLink = (groupType: string): void => {
- LinkManager.Instance.removeGroupFromAnchor(this.props.linkDoc, this.props.sourceDoc, groupType);
- }
-
- deleteGroup = (groupType: string): void => {
- LinkManager.Instance.deleteGroupType(groupType);
- }
-
-
- @action
- addMetadata = (groupType: string): void => {
- this._metadataIds.set("new key", Utils.GenerateGuid());
- const 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);
- }
-
- // for key rendering purposes
- changeMdIdKey = (id: string, newKey: string) => {
- this._metadataIds.set(newKey, id);
- }
-
- renderMetadata = (): JSX.Element[] => {
- const metadata: Array<JSX.Element> = [];
- const groupDoc = this.props.groupDoc;
- const groupType = StrCast(groupDoc.linkRelationship);
- const groupMdKeys = LinkManager.Instance.getMetadataKeysInGroup(groupType);
-
- groupMdKeys.forEach((key) => {
- const val = StrCast(groupDoc[key]);
- metadata.push(
- <LinkMetadataEditor key={"mded-" + this._metadataIds.get(key)} id={this._metadataIds.get(key)!} groupType={groupType} mdDoc={groupDoc} mdKey={key} mdValue={val} changeMdIdKey={this.changeMdIdKey} />
- );
- });
- return metadata;
- }
-
- render() {
- const groupType = StrCast(this.props.groupDoc.linkRelationship);
- // if ((groupType && LinkManager.Instance.getMetadataKeysInGroup(groupType).length > 0) || groupType === "") {
- const buttons = <button className="linkEditor-button" disabled={groupType === ""} onClick={() => this.deleteGroup(groupType)} title="Delete Relationship from all links"><FontAwesomeIcon icon="trash" size="sm" /></button>;
- const addButton = <button className="linkEditor-addbutton" onClick={() => this.addMetadata(groupType)} disabled={groupType === ""} title="Add metadata to relationship"><FontAwesomeIcon icon="plus" size="sm" /></button>;
-
- return (
- <div className="linkEditor-group">
- <div className="linkEditor-group-row ">
- {buttons}
- <GroupTypesDropdown groupType={groupType} setGroupType={this.setGroupType} />
- <button className="linkEditor-button" onClick={() => this.removeGroupFromLink(groupType)} title="Remove relationship from link"><FontAwesomeIcon icon="times" size="sm" /></button>
- </div>
- {this.renderMetadata().length > 0 ? <p className="linkEditor-group-row-label">metadata:</p> : <></>}
- {addButton}
- {this.renderMetadata()}
- </div>
- );
- }
-}
-
interface LinkEditorProps {
sourceDoc: Doc;
@@ -422,10 +164,6 @@ export class LinkEditor extends React.Component<LinkEditorProps> {
render() {
const destination = LinkManager.getOppositeAnchor(this.props.linkDoc, this.props.sourceDoc);
- const groups = [this.props.linkDoc].map(groupDoc => {
- return <LinkGroupEditor key={"gred-" + StrCast(groupDoc.linkRelationship)} linkDoc={this.props.linkDoc}
- sourceDoc={this.props.sourceDoc} groupDoc={groupDoc} />;
- });
return !destination ? (null) : (
<div className="linkEditor">
@@ -450,8 +188,6 @@ export class LinkEditor extends React.Component<LinkEditorProps> {
<div>{this.editDescription}</div>
<div>{this.followingDropdown}</div>
-
- {/* {groups.length > 0 ? groups : <div className="linkEditor-group">There are currently no relationships associated with this link.</div>} */}
</div>
);
diff --git a/src/client/views/linking/LinkMenuGroup.tsx b/src/client/views/linking/LinkMenuGroup.tsx
index 29e1d921c..e76227ccf 100644
--- a/src/client/views/linking/LinkMenuGroup.tsx
+++ b/src/client/views/linking/LinkMenuGroup.tsx
@@ -54,17 +54,6 @@ export class LinkMenuGroup extends React.Component<LinkMenuGroupProps> {
e.stopPropagation();
}
- viewGroupAsTable = (groupType: string): JSX.Element => {
- const keys = LinkManager.Instance.getMetadataKeysInGroup(groupType);
- const index = keys.indexOf("");
- if (index > -1) keys.splice(index, 1);
- const cols = ["anchor1", "anchor2", ...[...keys]].map(c => new SchemaHeaderField(c, "#f1efeb"));
- const docs: Doc[] = LinkManager.Instance.getAllMetadataDocsInGroup(groupType);
- const createTable = action(() => Docs.Create.SchemaDocument(cols, docs, { _width: 500, _height: 300, title: groupType + " table", childDropAction: "alias" }));
- const ref = React.createRef<HTMLDivElement>();
- return <div ref={ref}><button className="linkEditor-button linkEditor-tableButton" onPointerDown={SetupDrag(ref, createTable)} title="Drag to view relationship table"><FontAwesomeIcon icon="table" size="sm" /></button></div>;
- }
-
render() {
const set = new Set<Doc>(this.props.group);
const groupItems = Array.from(set.keys()).map(linkDoc => {
diff --git a/src/client/views/linking/LinkMenuItem.tsx b/src/client/views/linking/LinkMenuItem.tsx
index 3a8d41fef..00e667db7 100644
--- a/src/client/views/linking/LinkMenuItem.tsx
+++ b/src/client/views/linking/LinkMenuItem.tsx
@@ -90,19 +90,6 @@ export class LinkMenuItem extends React.Component<LinkMenuItemProps> {
return true;
}
- renderMetadata = (): JSX.Element => {
- const index = StrCast(this.props.linkDoc.title).toUpperCase() === this.props.groupType.toUpperCase() ? 0 : -1;
- const mdDoc = index > -1 ? this.props.linkDoc : undefined;
-
- let mdRows: Array<JSX.Element> = [];
- if (mdDoc) {
- const keys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);//groupMetadataKeys.get(this.props.groupType);
- mdRows = keys.map(key => <div key={key} className="link-metadata-row"><b>{key}</b>: {StrCast(mdDoc[key])}</div>);
- }
-
- return (<div className="link-metadata">{mdRows}</div>);
- }
-
@action
onLinkButtonDown = (e: React.PointerEvent): void => {
this._downX = e.clientX;
@@ -191,8 +178,6 @@ export class LinkMenuItem extends React.Component<LinkMenuItemProps> {
}
render() {
- const keys = LinkManager.Instance.getMetadataKeysInGroup(this.props.groupType);//groupMetadataKeys.get(this.props.groupType);
- const canExpand = keys ? keys.length > 0 : false;
const eyeIcon = this.props.linkDoc.hidden ? "eye-slash" : "eye";
@@ -230,7 +215,7 @@ export class LinkMenuItem extends React.Component<LinkMenuItemProps> {
return (
<div className="linkMenu-item">
- <div className={canExpand ? "linkMenu-item-content expand-three" : "linkMenu-item-content expand-two"}>
+ <div className={"linkMenu-item-content expand-two"}>
<div ref={this._drag} className="linkMenu-name" //title="drag to view target. click to customize."
onPointerLeave={action(() => LinkDocPreview.LinkInfo = undefined)}
@@ -257,8 +242,6 @@ export class LinkMenuItem extends React.Component<LinkMenuItemProps> {
{StrCast(this.props.linkDoc.description)}</p> : null} </div>
<div className="linkMenu-item-buttons" ref={this._buttonRef} >
- {canExpand ? <div title="Show more" className="button" onPointerDown={e => this.toggleShowMore(e)}>
- <FontAwesomeIcon className="fa-icon" icon={this._showMore ? "chevron-up" : "chevron-down"} size="sm" /></div> : <></>}
<Tooltip title={<><div className="dash-tooltip">{this.props.linkDoc.hidden ? "Show link" : "Hide link"}</div></>}>
<div className="button" ref={this._editRef} onPointerDown={this.showLink}>