aboutsummaryrefslogtreecommitdiff
path: root/src/client/views/search
diff options
context:
space:
mode:
Diffstat (limited to 'src/client/views/search')
-rw-r--r--src/client/views/search/FilterBox.tsx13
-rw-r--r--src/client/views/search/Pager.tsx8
-rw-r--r--src/client/views/search/SearchBox.tsx3
-rw-r--r--src/client/views/search/SearchItem.scss58
-rw-r--r--src/client/views/search/SearchItem.tsx154
-rw-r--r--src/client/views/search/ToggleBar.tsx2
6 files changed, 176 insertions, 62 deletions
diff --git a/src/client/views/search/FilterBox.tsx b/src/client/views/search/FilterBox.tsx
index 8faf0a991..5d36e650b 100644
--- a/src/client/views/search/FilterBox.tsx
+++ b/src/client/views/search/FilterBox.tsx
@@ -64,7 +64,7 @@ export class FilterBox extends React.Component {
componentDidMount = () => {
document.addEventListener("pointerdown", (e) => {
- if (e.timeStamp !== this._pointerTime) {
+ if (!e.defaultPrevented && e.timeStamp !== this._pointerTime) {
SearchBox.Instance.closeSearch();
}
});
@@ -72,9 +72,9 @@ export class FilterBox extends React.Component {
setupAccordion() {
$('document').ready(function () {
- var acc = document.getElementsByClassName('filter-header');
-
- for (var i = 0; i < acc.length; i++) {
+ const acc = document.getElementsByClassName('filter-header');
+ // tslint:disable-next-line: prefer-for-of
+ for (let i = 0; i < acc.length; i++) {
acc[i].addEventListener("click", function (this: HTMLElement) {
this.classList.toggle("active");
@@ -103,6 +103,7 @@ export class FilterBox extends React.Component {
$('document').ready(function () {
var acc = document.getElementsByClassName('filter-header');
+ // tslint:disable-next-line: prefer-for-of
for (var i = 0; i < acc.length; i++) {
let classList = acc[i].classList;
if (classList.contains("active")) {
@@ -247,8 +248,8 @@ export class FilterBox extends React.Component {
filterDocsByType(docs: Doc[]) {
let finalDocs: Doc[] = [];
docs.forEach(doc => {
- let layoutresult = Cast(doc.type, "string", "");
- if (this._icons.includes(layoutresult)) {
+ let layoutresult = Cast(doc.type, "string");
+ if (!layoutresult || this._icons.includes(layoutresult)) {
finalDocs.push(doc);
}
});
diff --git a/src/client/views/search/Pager.tsx b/src/client/views/search/Pager.tsx
index e7d3b810f..9bcfb1676 100644
--- a/src/client/views/search/Pager.tsx
+++ b/src/client/views/search/Pager.tsx
@@ -3,7 +3,7 @@ import { observer } from 'mobx-react';
import { faArrowCircleRight, faArrowCircleLeft } from '@fortawesome/free-solid-svg-icons';
import { FontAwesomeIcon } from '@fortawesome/react-fontawesome';
import { library } from '@fortawesome/fontawesome-svg-core';
-import "./Pager.scss"
+import "./Pager.scss";
import { SearchBox } from './SearchBox';
import { observable, action } from 'mobx';
import { FilterBox } from './FilterBox';
@@ -20,7 +20,7 @@ export class Pager extends React.Component {
@action
onLeftClick(e: React.PointerEvent) {
FilterBox.Instance._pointerTime = e.timeStamp;
- if(SearchBox.Instance._pageNum > 0){
+ if (SearchBox.Instance._pageNum > 0) {
SearchBox.Instance._pageNum -= 1;
}
}
@@ -28,7 +28,7 @@ export class Pager extends React.Component {
@action
onRightClick(e: React.PointerEvent) {
FilterBox.Instance._pointerTime = e.timeStamp;
- if(SearchBox.Instance._pageNum+1 < SearchBox.Instance._maxNum){
+ if (SearchBox.Instance._pageNum + 1 < SearchBox.Instance._maxNum) {
SearchBox.Instance._pageNum += 1;
}
}
@@ -72,7 +72,7 @@ export class Pager extends React.Component {
</div>
</div>
</div>
- )
+ );
}
} \ No newline at end of file
diff --git a/src/client/views/search/SearchBox.tsx b/src/client/views/search/SearchBox.tsx
index dbaa6eba2..af0c541f1 100644
--- a/src/client/views/search/SearchBox.tsx
+++ b/src/client/views/search/SearchBox.tsx
@@ -15,7 +15,6 @@ import { Id } from '../../../new_fields/FieldSymbols';
import { SearchUtil } from '../../util/SearchUtil';
import { RouteStore } from '../../../server/RouteStore';
import { FilterBox } from './FilterBox';
-import { Pager } from './Pager';
@observer
export class SearchBox extends React.Component {
@@ -169,7 +168,7 @@ export class SearchBox extends React.Component {
@action.bound
closeSearch = () => {
- console.log("closing search")
+ console.log("closing search");
FilterBox.Instance.closeFilter();
this.closeResults();
}
diff --git a/src/client/views/search/SearchItem.scss b/src/client/views/search/SearchItem.scss
index 946680f0e..fa4c9cb38 100644
--- a/src/client/views/search/SearchItem.scss
+++ b/src/client/views/search/SearchItem.scss
@@ -5,6 +5,7 @@
flex-direction: row-reverse;
justify-content: flex-end;
height: 70px;
+ z-index: 0;
.search-item {
width: 500px;
@@ -13,6 +14,7 @@
border-bottom-style: solid;
padding: 10px;
height: 70px;
+ z-index: 0;
display: inline-block;
.main-search-info {
@@ -23,16 +25,17 @@
.search-title {
text-transform: uppercase;
text-align: left;
- width: 80%;
+ width: 100%;
font-weight: bold;
}
.search-info {
display: flex;
justify-content: flex-end;
- width: 40%;
.link-container.item {
+ margin-left: auto;
+ margin-right: auto;
height: 26px;
width: 26px;
border-radius: 13px;
@@ -41,7 +44,6 @@
display: flex;
justify-content: center;
align-items: center;
- right: 15px;
-webkit-transition: all 0.2s ease-in-out;
-moz-transition: all 0.2s ease-in-out;
-o-transition: all 0.2s ease-in-out;
@@ -84,26 +86,42 @@
.link-container.item:hover .link-extended {
opacity: 1;
}
+
+ .icon-icons {
+ width:50px
+ }
+ .icon-live {
+ width:175px;
+ }
- .icon {
-
+ .icon-icons, .icon-live {
+ height:50px;
+ margin:auto;
+ overflow: hidden;
.search-type {
- width: 25PX;
- height: 25PX;
- display: flex;
+ display: inline-block;
+ width:100%;
+ position: absolute;
justify-content: center;
align-items: center;
position: relative;
margin-right: 5px;
}
+ .pdfBox-cont {
+ overflow: hidden;
+
+ img {
+ width:100% !important;
+ height:auto !important;
+ }
+ }
.search-type:hover+.search-label {
opacity: 1;
}
.search-label {
font-size: 10;
- padding: 5px;
position: relative;
right: 0px;
text-transform: capitalize;
@@ -114,6 +132,18 @@
transition: opacity 0.2s ease-in-out;
}
}
+
+ .icon-live:hover {
+ height:175px;
+ .pdfBox-cont {
+ img {
+ width:100% !important;
+ }
+ }
+ }
+ }
+ .search-info:hover {
+ width:60%;
}
}
}
@@ -143,7 +173,15 @@
-webkit-transform: scale(0);
-ms-transform: scale(0);
transform: scale(0);
- // height: 100%
}
+}
+.search-overview:hover {
+ z-index: 1;
+}
+.collection {
+ display:flex;
+}
+.collection-item {
+ width:35px;
} \ No newline at end of file
diff --git a/src/client/views/search/SearchItem.tsx b/src/client/views/search/SearchItem.tsx
index 50bf1f6b8..f8a0c7b16 100644
--- a/src/client/views/search/SearchItem.tsx
+++ b/src/client/views/search/SearchItem.tsx
@@ -1,24 +1,26 @@
import React = require("react");
import { library } from '@fortawesome/fontawesome-svg-core';
-import { faCaretUp, faFilePdf, faFilm, faImage, faObjectGroup, faStickyNote, faMusic, faLink, faChartBar, faGlobeAsia } from '@fortawesome/free-solid-svg-icons';
+import { faCaretUp, faChartBar, faFilePdf, faFilm, faGlobeAsia, faImage, faLink, faMusic, faObjectGroup, faStickyNote } from '@fortawesome/free-solid-svg-icons';
import { FontAwesomeIcon } from "@fortawesome/react-fontawesome";
-import { Cast, NumCast } from "../../../new_fields/Types";
-import { observable, runInAction, computed, action } from "mobx";
-import { listSpec } from "../../../new_fields/Schema";
-import { Doc } from "../../../new_fields/Doc";
+import { action, computed, observable, runInAction } from "mobx";
+import { observer } from "mobx-react";
+import { Doc, DocListCast, HeightSym, WidthSym } from "../../../new_fields/Doc";
+import { Id } from "../../../new_fields/FieldSymbols";
+import { Cast, NumCast, StrCast } from "../../../new_fields/Types";
+import { emptyFunction, returnFalse, returnOne } from "../../../Utils";
+import { DocTypes } from "../../documents/Documents";
import { DocumentManager } from "../../util/DocumentManager";
import { SetupDrag } from "../../util/DragManager";
+import { LinkManager } from "../../util/LinkManager";
import { SearchUtil } from "../../util/SearchUtil";
-import { Id } from "../../../new_fields/FieldSymbols";
-import { CollectionDockingView } from "../collections/CollectionDockingView";
-import { observer } from "mobx-react";
-import "./SearchItem.scss";
+import { Transform } from "../../util/Transform";
+import { SEARCH_THUMBNAIL_SIZE } from "../../views/globalCssVariables.scss";
import { CollectionViewType } from "../collections/CollectionBaseView";
-import { DocTypes } from "../../documents/Documents";
-import { FilterBox } from "./FilterBox";
+import { CollectionDockingView } from "../collections/CollectionDockingView";
import { DocumentView } from "../nodes/DocumentView";
-import "./SelectorContextMenu.scss";
import { SearchBox } from "./SearchBox";
+import "./SearchItem.scss";
+import "./SelectorContextMenu.scss";
export interface SearchItemProps {
doc: Doc;
@@ -66,16 +68,23 @@ export class SelectorContextMenu extends React.Component<SearchItemProps> {
col.panX = newPanX;
col.panY = newPanY;
}
- CollectionDockingView.Instance.AddRightSplit(col);
+ CollectionDockingView.Instance.AddRightSplit(col, undefined);
};
}
-
render() {
return (
- < div className="parents">
+ <div className="parents">
<p className="contexts">Contexts:</p>
- {this._docs.map(doc => <div className="collection"><a className="title" onClick={this.getOnClick(doc)}>{doc.col.title}</a></div>)}
- {this._otherDocs.map(doc => <div className="collection"><a className="title" onClick={this.getOnClick(doc)}>{doc.col.title}</a></div>)}
+ {[...this._docs, ...this._otherDocs].map(doc => {
+ let item = React.createRef<HTMLDivElement>();
+ return <div className="collection" key={doc.col[Id] + doc.target[Id]} ref={item}>
+ <div className="collection-item" onPointerDown={
+ SetupDrag(item, () => doc.col, undefined, undefined, undefined, undefined, () => SearchBox.Instance.closeSearch())}>
+ <FontAwesomeIcon icon={faStickyNote} />
+ </div>
+ <a className="title" onClick={this.getOnClick(doc)}>{doc.col.title}</a>
+ </div>;
+ })}
</div>
);
}
@@ -87,12 +96,58 @@ export class SearchItem extends React.Component<SearchItemProps> {
@observable _selected: boolean = false;
onClick = () => {
- CollectionDockingView.Instance.AddRightSplit(this.props.doc);
+ DocumentManager.Instance.jumpToDocument(this.props.doc, false);
}
+ @observable _useIcons = true;
+ @observable _displayDim = 50;
@computed
public get DocumentIcon() {
- let layoutresult = Cast(this.props.doc.type, "string", "");
+ let layoutresult = StrCast(this.props.doc.type);
+ if (!this._useIcons) {
+ let renderDoc = this.props.doc;
+ let box: number[] = [];
+ if (layoutresult.indexOf(DocTypes.COL) !== -1) {
+ renderDoc = Doc.MakeDelegate(renderDoc);
+ let bounds = DocListCast(renderDoc.data).reduce((bounds, doc) => {
+ var [sptX, sptY] = [NumCast(doc.x), NumCast(doc.y)];
+ let [bptX, bptY] = [sptX + doc[WidthSym](), sptY + doc[HeightSym]()];
+ return {
+ x: Math.min(sptX, bounds.x), y: Math.min(sptY, bounds.y),
+ r: Math.max(bptX, bounds.r), b: Math.max(bptY, bounds.b)
+ };
+ }, { x: Number.MAX_VALUE, y: Number.MAX_VALUE, r: Number.MIN_VALUE, b: Number.MIN_VALUE });
+ box = [(bounds.x + bounds.r) / 2, (bounds.y + bounds.b) / 2, Number(SEARCH_THUMBNAIL_SIZE) / (bounds.r - bounds.x), this._displayDim];
+ }
+ let returnXDimension = () => this._useIcons ? 50 : Number(SEARCH_THUMBNAIL_SIZE);
+ let returnYDimension = () => this._displayDim;
+ let scale = () => returnXDimension() / NumCast(renderDoc.nativeWidth, returnXDimension());
+ return <div
+ onPointerDown={action(() => { this._useIcons = !this._useIcons; this._displayDim = this._useIcons ? 50 : Number(SEARCH_THUMBNAIL_SIZE); })}
+ onPointerEnter={action(() => this._displayDim = this._useIcons ? 50 : Number(SEARCH_THUMBNAIL_SIZE))}
+ onPointerLeave={action(() => this._displayDim = 50)} >
+ <DocumentView
+ fitToBox={box}
+ Document={renderDoc}
+ addDocument={returnFalse}
+ removeDocument={returnFalse}
+ ScreenToLocalTransform={Transform.Identity}
+ addDocTab={returnFalse}
+ renderDepth={1}
+ PanelWidth={returnXDimension}
+ PanelHeight={returnYDimension}
+ focus={emptyFunction}
+ selectOnLoad={false}
+ parentActive={returnFalse}
+ whenActiveChanged={returnFalse}
+ bringToFront={emptyFunction}
+ zoomToScale={emptyFunction}
+ getScale={returnOne}
+ ContainingCollectionView={undefined}
+ ContentScaling={scale}
+ />
+ </div>;
+ }
let button = layoutresult.indexOf(DocTypes.PDF) !== -1 ? faFilePdf :
layoutresult.indexOf(DocTypes.IMG) !== -1 ? faImage :
@@ -104,7 +159,9 @@ export class SearchItem extends React.Component<SearchItemProps> {
layoutresult.indexOf(DocTypes.HIST) !== -1 ? faChartBar :
layoutresult.indexOf(DocTypes.WEB) !== -1 ? faGlobeAsia :
faCaretUp;
- return <FontAwesomeIcon icon={button} size="2x" />;
+ return <div onPointerDown={action(() => { this._useIcons = false; this._displayDim = Number(SEARCH_THUMBNAIL_SIZE); })} >
+ <FontAwesomeIcon icon={button} size="2x" />
+ </div>;
}
collectionRef = React.createRef<HTMLDivElement>();
@@ -119,7 +176,7 @@ export class SearchItem extends React.Component<SearchItemProps> {
}
@computed
- get linkCount() { return Cast(this.props.doc.linkedToDocs, listSpec(Doc), []).length + Cast(this.props.doc.linkedFromDocs, listSpec(Doc), []).length; }
+ get linkCount() { return LinkManager.Instance.getAllRelatedLinks(this.props.doc).length; }
@computed
get linkString(): string {
@@ -130,40 +187,59 @@ export class SearchItem extends React.Component<SearchItemProps> {
return num.toString() + " links";
}
- pointerDown = (e: React.PointerEvent) => { SearchBox.Instance.openSearch(e); };
+ @action
+ pointerDown = (e: React.PointerEvent) => SearchBox.Instance.openSearch(e)
highlightDoc = (e: React.PointerEvent) => {
- let docViews: DocumentView[] = DocumentManager.Instance.getAllDocumentViews(this.props.doc);
- docViews.forEach(element => {
- element.props.Document.libraryBrush = true;
- });
+ if (this.props.doc.type === DocTypes.LINK) {
+ if (this.props.doc.anchor1 && this.props.doc.anchor2) {
+
+ let doc1 = Cast(this.props.doc.anchor1, Doc, new Doc());
+ let doc2 = Cast(this.props.doc.anchor2, Doc, new Doc());
+ doc1.libraryBrush = true;
+ doc2.libraryBrush = true;
+ }
+ } else {
+ let docViews: DocumentView[] = DocumentManager.Instance.getAllDocumentViews(this.props.doc);
+ docViews.forEach(element => {
+ element.props.Document.libraryBrush = true;
+ });
+ }
}
unHighlightDoc = (e: React.PointerEvent) => {
- let docViews: DocumentView[] = DocumentManager.Instance.getAllDocumentViews(this.props.doc);
- docViews.forEach(element => {
- element.props.Document.libraryBrush = false;
- });
+ if (this.props.doc.type === DocTypes.LINK) {
+ if (this.props.doc.anchor1 && this.props.doc.anchor2) {
+
+ let doc1 = Cast(this.props.doc.anchor1, Doc, new Doc());
+ let doc2 = Cast(this.props.doc.anchor2, Doc, new Doc());
+ doc1.libraryBrush = false;
+ doc2.libraryBrush = false;
+ }
+ } else {
+ let docViews: DocumentView[] = DocumentManager.Instance.getAllDocumentViews(this.props.doc);
+ docViews.forEach(element => {
+ element.props.Document.libraryBrush = false;
+ });
+ }
}
render() {
return (
<div className="search-overview" onPointerDown={this.pointerDown}>
- <div className="search-item" onPointerEnter={this.highlightDoc} onPointerLeave={this.unHighlightDoc} ref={this.collectionRef} id="result" onClick={this.onClick} onPointerDown={() => {
- this.pointerDown;
- SetupDrag(this.collectionRef, this.startDocDrag);
- }} >
+ <div className="search-item" onPointerEnter={this.highlightDoc} onPointerLeave={this.unHighlightDoc} ref={this.collectionRef} id="result"
+ onClick={this.onClick} onPointerDown={this.pointerDown} >
<div className="main-search-info">
<div className="search-title" id="result" >{this.props.doc.title}</div>
- <div className="search-info">
+ <div className="search-info" style={{ width: this._useIcons ? "15%" : "400px" }}>
+ <div className={`icon-${this._useIcons ? "icons" : "live"}`}>
+ <div className="search-type" >{this.DocumentIcon}</div>
+ <div className="search-label">{this.props.doc.type}</div>
+ </div>
<div className="link-container item">
<div className="link-count">{this.linkCount}</div>
<div className="link-extended">{this.linkString}</div>
</div>
- <div className="icon">
- <div className="search-type" >{this.DocumentIcon}</div>
- <div className="search-label">{this.props.doc.type}</div>
- </div>
</div>
</div>
</div>
diff --git a/src/client/views/search/ToggleBar.tsx b/src/client/views/search/ToggleBar.tsx
index 8a3aacf96..178578c5c 100644
--- a/src/client/views/search/ToggleBar.tsx
+++ b/src/client/views/search/ToggleBar.tsx
@@ -78,7 +78,7 @@ export class ToggleBar extends React.Component<ToggleBarProps>{
<div className="toggle-option" style={{ opacity: (this.props.getStatus() ? .4 : 1) }}>{this.props.optionTwo}</div>
</div>
<div className="toggle-bar" id="toggle-bar" onClick={this.onclick} style={{ flexDirection: (this._originalStatus ? "row" : "row-reverse") }}>
- <div className="toggle-button" id="toggle-button" ref={this._toggleButton} />
+ <div className="toggle-button" id="toggle-button" ref={this._toggleButton} />
</div>
</div>
);