diff options
Diffstat (limited to 'src/client/views/collections/CollectionSubView.tsx')
-rw-r--r-- | src/client/views/collections/CollectionSubView.tsx | 51 |
1 files changed, 48 insertions, 3 deletions
diff --git a/src/client/views/collections/CollectionSubView.tsx b/src/client/views/collections/CollectionSubView.tsx index 581201a20..c057d2402 100644 --- a/src/client/views/collections/CollectionSubView.tsx +++ b/src/client/views/collections/CollectionSubView.tsx @@ -9,7 +9,7 @@ import { Id } from '../../../fields/FieldSymbols'; import { List } from '../../../fields/List'; import { listSpec } from '../../../fields/Schema'; import { ScriptField } from '../../../fields/ScriptField'; -import { BoolCast, Cast, ScriptCast, StrCast } from '../../../fields/Types'; +import { BoolCast, Cast, NumCast, ScriptCast, StrCast } from '../../../fields/Types'; import { WebField } from '../../../fields/URLField'; import { GetEffectiveAcl, TraceMobx } from '../../../fields/util'; import { GestureUtils } from '../../../pen-gestures/GestureUtils'; @@ -25,7 +25,8 @@ import { SnappingManager } from '../../util/SnappingManager'; import { UndoManager } from '../../util/UndoManager'; import { ViewBoxBaseComponent } from '../DocComponent'; import { FieldViewProps } from '../nodes/FieldView'; -import { DocumentView } from '../nodes/DocumentView'; +import { DocumentView, DocumentViewProps } from '../nodes/DocumentView'; +import { FlashcardPracticeUI } from './FlashcardPracticeUI'; export interface CollectionViewProps extends React.PropsWithChildren<FieldViewProps> { isAnnotationOverlay?: boolean; // is the collection an annotation overlay (eg an overlay on an image/video/etc) @@ -119,7 +120,8 @@ export function CollectionSubView<X>() { pair => // filter out any documents that have a proto that we don't have permissions to !pair.layout?.hidden && pair.layout && (!pair.layout.proto || (pair.layout.proto instanceof Doc && GetEffectiveAcl(pair.layout.proto) !== AclPrivate)) - ); + ) + .filter(pair => !this._filterFunc?.(pair.layout!)); return validPairs.map(({ data, layout }) => ({ data: data as Doc, layout: layout! })); // this mapping is a bit of a hack to coerce types } /** @@ -515,6 +517,49 @@ export function CollectionSubView<X>() { alert('Document upload failed - possibly an unsupported file type.'); } }; + + protected _sideBtnWidth = 35; + @observable _filterFunc: ((doc: Doc) => boolean) | undefined = undefined; + /** + * How much the content of the collection is being scaled based on its nesting and its fit-to-width settings + */ + @computed get contentScaling() { return this.ScreenToLocalBoxXf().Scale * (this._props.NativeDimScaling?.() ?? 1); } // prettier-ignore + /** + * The maximum size a UI widget can be in collection coordinates based on not wanting the widget to visually obscure too much of the collection + * This takes the desired screen space size and converts into collection coordinates. It then returns the smaller of the converted + * size or a fraction of the collection view. + */ + @computed get maxWidgetSize() { return Math.min(this._sideBtnWidth * this.contentScaling, 0.25 * NumCast(this.layoutDoc.width, 1)); } // prettier-ignore + /** + * This computes a scale factor for UI elements so that they shrink and grow as the collection does in screen space. + * Note, the scale factor does not allow for elements to grow larger than their native screen space size. + */ + @computed get uiBtnScaling() { return this.maxWidgetSize / this._sideBtnWidth; } // prettier-ignore + + screenXPadding = () => (this.uiBtnScaling * this._sideBtnWidth - NumCast(this.layoutDoc.xMargin)) / this._props.ScreenToLocalTransform().Scale; + filteredChildDocs = () => this.childLayoutPairs.map(pair => pair.layout); + childDocsFunc = () => this.childDocs; + @action setFilterFunc = (func?: (doc: Doc) => boolean) => { this._filterFunc = func; }; // prettier-ignore + + public flashCardUI = (curDoc: () => Doc | undefined, docViewProps: () => DocumentViewProps, answered?: (correct: boolean) => void) => { + return ( + <FlashcardPracticeUI + setFilterFunc={this.setFilterFunc} + fieldKey={this.fieldKey} + sideBtnWidth={this._sideBtnWidth} + allChildDocs={this.childDocsFunc} + filteredChildDocs={this.filteredChildDocs} + advance={answered} + curDoc={curDoc} + practiceBtnOffset={this._sideBtnWidth * 4} + layoutDoc={this.layoutDoc} + uiBtnScaling={this.uiBtnScaling} + ScreenToLocalBoxXf={this.ScreenToLocalBoxXf} + renderDepth={this._props.renderDepth} + docViewProps={docViewProps} + /> + ); + }; } return CollectionSubViewInternal; |