aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorbobzel <zzzman@gmail.com>2025-03-05 14:54:18 -0500
committerbobzel <zzzman@gmail.com>2025-03-05 14:54:18 -0500
commitdb3bdb19ff7bc1c69c544797c05a6db3b72b1464 (patch)
treefe01be9276ffcbaf9e27bb17e8f1fe7a25b22505 /src
parent9688e3bb1e67336fe57e11b186936830d5483b06 (diff)
added:hover mode for images to make primary image fade in instead of alternate.
Diffstat (limited to 'src')
-rw-r--r--src/client/documents/Documents.ts3
-rw-r--r--src/client/views/MainView.tsx2
-rw-r--r--src/client/views/TagsView.tsx3
-rw-r--r--src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx2
-rw-r--r--src/client/views/nodes/DocumentView.scss1
-rw-r--r--src/client/views/nodes/DocumentView.tsx16
-rw-r--r--src/client/views/nodes/ImageBox.scss6
-rw-r--r--src/client/views/nodes/ImageBox.tsx40
-rw-r--r--src/client/views/nodes/chatbot/tools/ImageCreationTool.ts3
-rw-r--r--src/client/views/pdf/GPTPopup/GPTPopup.tsx3
-rw-r--r--src/client/views/smartdraw/DrawingFillHandler.tsx4
-rw-r--r--src/client/views/smartdraw/SmartDrawHandler.tsx8
12 files changed, 65 insertions, 26 deletions
diff --git a/src/client/documents/Documents.ts b/src/client/documents/Documents.ts
index 1ce25165c..21d3c978b 100644
--- a/src/client/documents/Documents.ts
+++ b/src/client/documents/Documents.ts
@@ -384,6 +384,9 @@ export class DocumentOptions {
presentation_duration?: NUMt = new NumInfo('the duration of the slide in presentation view', false);
presentation_zoomText?: BOOLt = new BoolInfo('whether text anchors should shown in a larger box when following links to make them stand out', false);
+ data_annotations?: List<Doc>;
+ _data_usePath?: STRt = new StrInfo("description of field key to display in image box ('alternate','alternate:hover', 'data:hover'). defaults to primary", false);
+ data_alternates?: List<Doc>;
data?: FieldType;
data_useCors?: BOOLt = new BoolInfo('whether CORS protocol should be used for web page');
_face_showImages?: BOOLt = new BoolInfo('whether to show images in uniqe face Doc');
diff --git a/src/client/views/MainView.tsx b/src/client/views/MainView.tsx
index afefe3f03..cc7c1a42b 100644
--- a/src/client/views/MainView.tsx
+++ b/src/client/views/MainView.tsx
@@ -686,7 +686,7 @@ export class MainView extends ObservableReactComponent<object> {
);
}
@computed get mainDocView() {
- const headerBar = null; // this._hideUI || !this.headerBarDocHeight?.() ? null : this.headerBarDocView;
+ const headerBar = this._hideUI || !this.headerBarDocHeight?.() ? null : this.headerBarDocView;
return (
<>
{headerBar}
diff --git a/src/client/views/TagsView.tsx b/src/client/views/TagsView.tsx
index b70e21918..93d6fb684 100644
--- a/src/client/views/TagsView.tsx
+++ b/src/client/views/TagsView.tsx
@@ -398,8 +398,7 @@ export class TagsView extends ObservableReactComponent<TagViewProps> {
e.stopPropagation();
}}
type="text"
- placeholder="Input tags for document..."
- aria-label="tagsView-input"
+ placeholder="Enter #tags or @metadata"
className="tagsView-input"
style={{ width: '100%', borderRadius: '5px' }}
/>
diff --git a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
index b3d908da4..43addfc29 100644
--- a/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
+++ b/src/client/views/collections/collectionFreeForm/CollectionFreeFormView.tsx
@@ -344,7 +344,7 @@ export class CollectionFreeFormView extends CollectionSubView<Partial<collection
focusOnPoint = (options: FocusViewOptions) => {
const { pointFocus, zoomTime, didMove } = options;
if (!this.Document.isGroup && pointFocus && !didMove) {
- const dfltScale = this.isAnnotationOverlay ? 1 : 0.5;
+ const dfltScale = this.isAnnotationOverlay ? 1 : 0.25;
if (this.layoutDoc[this.scaleFieldKey] !== dfltScale) {
this.zoomSmoothlyAboutPt(this.screenToFreeformContentsXf.transformPoint(pointFocus.X, pointFocus.Y), dfltScale, zoomTime);
options.didMove = true;
diff --git a/src/client/views/nodes/DocumentView.scss b/src/client/views/nodes/DocumentView.scss
index 294af4d96..dd5fd0d0c 100644
--- a/src/client/views/nodes/DocumentView.scss
+++ b/src/client/views/nodes/DocumentView.scss
@@ -291,6 +291,7 @@
justify-items: center;
background-color: rgb(223, 223, 223);
transform-origin: top left;
+ background: transparent;
.documentView-editorView-resizer {
height: 5px;
diff --git a/src/client/views/nodes/DocumentView.tsx b/src/client/views/nodes/DocumentView.tsx
index 5f5dd1210..595abc7f8 100644
--- a/src/client/views/nodes/DocumentView.tsx
+++ b/src/client/views/nodes/DocumentView.tsx
@@ -279,16 +279,17 @@ export class DocumentViewInternal extends DocComponent<FieldViewProps & Document
setTimeout(() => this._titleRef.current?.setIsFocused(true)); // use timeout in case title wasn't shown to allow re-render so that titleref will be defined
};
onBrowseClick = (e: React.MouseEvent) => {
- const browseTransitionTime = 500;
+ //const browseTransitionTime = 500;
DocumentView.DeselectAll();
DocumentView.showDocument(this.Document, { zoomScale: 0.8, willZoomCentered: true }, (focused: boolean) => {
- const options: FocusViewOptions = { pointFocus: { X: e.clientX, Y: e.clientY }, zoomTime: browseTransitionTime };
+ // const options: FocusViewOptions = { pointFocus: { X: e.clientX, Y: e.clientY }, zoomTime: browseTransitionTime };
if (!focused && this._docView) {
- this._docView
- .docViewPath()
- .reverse()
- .forEach(cont => cont.ComponentView?.focus?.(cont.Document, options));
- Doc.linkFollowHighlight(this.Document, false);
+ DocumentView.showDocument(this.Document, { zoomScale: 0.3, willZoomCentered: true });
+ // this._docView
+ // .docViewPath()
+ // .reverse()
+ // .forEach(cont => cont.ComponentView?.focus?.(cont.Document, options));
+ // Doc.linkFollowHighlight(this.Document, false);
}
});
e.stopPropagation();
@@ -797,6 +798,7 @@ export class DocumentViewInternal extends DocComponent<FieldViewProps & Document
<div
className="documentView-editorView"
style={{
+ background: SnappingManager.userVariantColor,
width: `${100 / this.uiBtnScaling}%`, //
transform: `scale(${this.uiBtnScaling})`,
}}
diff --git a/src/client/views/nodes/ImageBox.scss b/src/client/views/nodes/ImageBox.scss
index 15581a9e8..3d6942e6f 100644
--- a/src/client/views/nodes/ImageBox.scss
+++ b/src/client/views/nodes/ImageBox.scss
@@ -40,6 +40,7 @@
max-height: 100%;
pointer-events: inherit;
background: transparent;
+ z-index: 0;
// z-index: -10000; // bcz: not sure why this was here. it broke dropping images on the image box alternate bullseye icon.
img {
@@ -103,6 +104,10 @@
margin: 0 auto;
display: flex;
height: 100%;
+ img {
+ object-fit: contain;
+ height: 100%;
+ }
.imageBox-fadeBlocker,
.imageBox-fadeBlocker-hover {
@@ -237,5 +242,6 @@
text-overflow: ellipsis;
max-width: 65%;
width: 100%;
+ color: black;
}
}
diff --git a/src/client/views/nodes/ImageBox.tsx b/src/client/views/nodes/ImageBox.tsx
index 4979a4d4d..017ef7191 100644
--- a/src/client/views/nodes/ImageBox.tsx
+++ b/src/client/views/nodes/ImageBox.tsx
@@ -436,6 +436,11 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
};
getScrollHeight = () => (this._props.fitWidth?.(this.Document) !== false && NumCast(this.layoutDoc._freeform_scale, 1) === NumCast(this.dataDoc._freeform_scaleMin, 1) ? this.nativeSize.nativeHeight : undefined);
+ @computed get usingAlternate() {
+ const usePath = StrCast(this.Document[this.fieldKey + '_usePath']);
+ return 'alternate' === usePath || ('alternate:hover' === usePath && this._isHovering) || (':hover' === usePath && !this._isHovering);
+ }
+
@computed get nativeSize() {
TraceMobx();
if (this.paths.length && this.paths[0].includes('icon-hi')) return { nativeWidth: NumCast(this.layoutDoc._width), nativeHeight: NumCast(this.layoutDoc._height), nativeOrientation: 0 };
@@ -471,10 +476,13 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
<span style={{ color: usePath === 'alternate' ? 'black' : undefined }}>
<em>alternate, </em>
</span>
- and show
<span style={{ color: usePath === 'alternate:hover' ? 'black' : undefined }}>
<em> alternate on hover</em>
</span>
+ and show
+ <span style={{ color: usePath === ':hover' ? 'black' : undefined }}>
+ <em> primary on hover</em>
+ </span>
</div>
}>
<div
@@ -482,7 +490,7 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
ref={this._overlayIconRef}
onPointerDown={e =>
setupMoveUpEvents(e.target, e, returnFalse, emptyFunction, () => {
- this.layoutDoc[`_${this.fieldKey}_usePath`] = usePath === undefined ? 'alternate' : usePath === 'alternate' ? 'alternate:hover' : undefined;
+ this.layoutDoc[`_${this.fieldKey}_usePath`] = usePath === undefined ? 'alternate' : usePath === 'alternate' ? 'alternate:hover' : usePath === 'alternate:hover' ? ':hover' : undefined;
})
}
style={{
@@ -527,7 +535,7 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
.filter(url => url)
.map(url => this.choosePath(url)) ?? []; // acc ess the primary layout data of the alternate documents
const paths = field ? [this.choosePath(field.url), ...altpaths] : altpaths;
- return paths.length ? paths : [defaultUrl.href];
+ return paths.length ? paths.reverse() : [defaultUrl.href];
}
@computed get content() {
@@ -552,7 +560,6 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
transformOrigin = 'right top';
transform = `translate(-100%, 0%) rotate(${rotation}deg) scale(${aspect})`;
}
- const usePath = this.layoutDoc[`_${this.fieldKey}_usePath`];
return (
<div
@@ -571,7 +578,7 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
ref={action((r: HTMLImageElement | null) => (this.imageRef = r))}
key="paths"
src={srcpath}
- style={{ transform, transformOrigin, objectFit: 'fill', height: '100%' }}
+ style={{ transform, transformOrigin }}
onError={action(e => {
this._error = e.toString();
})}
@@ -579,7 +586,7 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
width={nativeWidth}
/>
{fadepath === srcpath ? null : (
- <div className={`imageBox-fadeBlocker${(this._isHovering && usePath === 'alternate:hover') || usePath === 'alternate' ? '-hover' : ''}`} style={{ transition: StrCast(this.layoutDoc.viewTransition, 'opacity 1000ms') }}>
+ <div className={`imageBox-fadeBlocker${this.usingAlternate ? '-hover' : ''}`} style={{ transition: StrCast(this.layoutDoc.viewTransition, 'opacity 1000ms') }}>
<img alt="" className="imageBox-fadeaway" key="fadeaway" src={fadepath} style={{ transform, transformOrigin }} draggable={false} width={nativeWidth} />
</div>
)}
@@ -619,8 +626,11 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
return (
<div className="imageBox-aiView">
<div className="imageBox-aiView-regenerate">
- <span className="imageBox-aiView-firefly">Firefly:</span>
+ <span className="imageBox-aiView-firefly" style={{ color: SnappingManager.userColor }}>
+ Firefly:
+ </span>
<input
+ style={{ color: SnappingManager.userColor, background: SnappingManager.userBackgroundColor }}
className="imageBox-aiView-input"
aria-label="Edit instructions input"
type="text"
@@ -631,7 +641,9 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
<div className="imageBox-aiView-regenerate-createBtn">
<Button
text="Create"
- type={Type.SEC}
+ type={Type.TERT}
+ color={SnappingManager.userColor}
+ background={SnappingManager.userBackgroundColor}
// style={{ alignSelf: 'flex-end' }}
icon={this._regenerateLoading ? <ReactLoading type="spin" color={SettingsManager.userVariantColor} width={16} height={20} /> : <AiOutlineSend />}
iconPlacement="right"
@@ -663,13 +675,15 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
</div>
</div>
<div className="imageBox-aiView-strength">
- <span className="imageBox-aiView-similarity">Similarity</span>
+ <span className="imageBox-aiView-similarity" style={{ color: SnappingManager.userColor }}>
+ Similarity
+ </span>
<Slider
className="imageBox-aiView-slider"
sx={{
- '& .MuiSlider-track': { color: SettingsManager.userVariantColor },
+ '& .MuiSlider-track': { color: SettingsManager.userColor },
'& .MuiSlider-rail': { color: SettingsManager.userBackgroundColor },
- '& .MuiSlider-thumb': { color: SettingsManager.userVariantColor, '&.Mui-focusVisible, &:hover, &.Mui-active': { boxShadow: `0px 0px 0px 8px${SettingsManager.userColor.slice(0, 7)}10` } },
+ '& .MuiSlider-thumb': { color: SettingsManager.userColor, '&.Mui-focusVisible, &:hover, &.Mui-active': { boxShadow: `0px 0px 0px 8px${SettingsManager.userColor.slice(0, 7)}10` } },
}}
min={0}
max={100}
@@ -725,11 +739,12 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
return { width, height };
};
savedAnnotations = () => this._savedAnnotations;
-
render() {
TraceMobx();
const borderRad = this._props.styleProvider?.(this.layoutDoc, this._props, StyleProp.BorderRounding) as string;
const borderRadius = borderRad?.includes('px') ? `${Number(borderRad.split('px')[0]) / (this._props.NativeDimScaling?.() || 1)}px` : borderRad;
+ const alts = DocListCast(this.dataDoc[this.fieldKey + '_alternates']);
+ const doc = this.usingAlternate ? (alts.lastElement() ?? this.Document) : this.Document;
return (
<div
className="imageBox"
@@ -754,6 +769,7 @@ export class ImageBox extends ViewBoxAnnotatableComponent<FieldViewProps>() {
<CollectionFreeFormView
ref={this._ffref}
{...this._props}
+ Document={doc}
setContentViewBox={emptyFunction}
NativeWidth={returnZero}
NativeHeight={returnZero}
diff --git a/src/client/views/nodes/chatbot/tools/ImageCreationTool.ts b/src/client/views/nodes/chatbot/tools/ImageCreationTool.ts
index e92d87dfd..37907fd4f 100644
--- a/src/client/views/nodes/chatbot/tools/ImageCreationTool.ts
+++ b/src/client/views/nodes/chatbot/tools/ImageCreationTool.ts
@@ -5,6 +5,7 @@ import { ParametersType, ToolInfo } from '../types/tool_types';
import { Observation } from '../types/types';
import { BaseTool } from './BaseTool';
import { Upload } from '../../../../../server/SharedMediaTypes';
+import { List } from '../../../../../fields/List';
const imageCreationToolParams = [
{
@@ -41,7 +42,7 @@ export class ImageCreationTool extends BaseTool<ImageCreationToolParamsType> {
image_prompt,
})) as { result: Upload.FileInformation & Upload.InspectionResults; url: string };
console.log('Image generation result:', result);
- this._createImage(result, { text: RTFCast(image_prompt) });
+ this._createImage(result, { text: RTFCast(image_prompt), ai: 'dall-e-3', tags: new List<string>(['@ai']) });
return url
? [
{
diff --git a/src/client/views/pdf/GPTPopup/GPTPopup.tsx b/src/client/views/pdf/GPTPopup/GPTPopup.tsx
index 79f5121ed..4dc45e6a0 100644
--- a/src/client/views/pdf/GPTPopup/GPTPopup.tsx
+++ b/src/client/views/pdf/GPTPopup/GPTPopup.tsx
@@ -30,6 +30,7 @@ import { Upload } from '../../../../server/SharedMediaTypes';
import { OpenWhere } from '../../nodes/OpenWhere';
import { DrawingFillHandler } from '../../smartdraw/DrawingFillHandler';
import { ImageField } from '../../../../fields/URLField';
+import { List } from '../../../../fields/List';
export enum GPTPopupMode {
SUMMARY, // summary of seleted document text
@@ -352,6 +353,8 @@ export class GPTPopup extends ObservableReactComponent<object> {
y: NumCast(textAnchor.y),
_height: 200,
_width: 200,
+ ai: 'dall-e',
+ tags: new List<string>(['@ai']),
data_nativeWidth: 1024,
data_nativeHeight: 1024,
});
diff --git a/src/client/views/smartdraw/DrawingFillHandler.tsx b/src/client/views/smartdraw/DrawingFillHandler.tsx
index 0a30b14b8..c672bc718 100644
--- a/src/client/views/smartdraw/DrawingFillHandler.tsx
+++ b/src/client/views/smartdraw/DrawingFillHandler.tsx
@@ -1,6 +1,7 @@
import { imageUrlToBase64 } from '../../../ClientUtils';
import { Doc, StrListCast } from '../../../fields/Doc';
import { DocData } from '../../../fields/DocSymbols';
+import { List } from '../../../fields/List';
import { DocCast, ImageCast } from '../../../fields/Types';
import { ImageField } from '../../../fields/URLField';
import { Upload } from '../../../server/SharedMediaTypes';
@@ -53,7 +54,10 @@ export class DrawingFillHandler {
undefined,
Docs.Create.ImageDocument(info.accessPaths.agnostic.client, {
ai: 'firefly',
+ tags: new List<string>(['@ai']),
title: newPrompt,
+ _data_usePath: 'alternate:hover',
+ data_alternates: new List<Doc>([drawing]),
ai_firefly_prompt: newPrompt,
_width: 500,
data_nativeWidth: info.nativeWidth,
diff --git a/src/client/views/smartdraw/SmartDrawHandler.tsx b/src/client/views/smartdraw/SmartDrawHandler.tsx
index ca308015d..1cceabed3 100644
--- a/src/client/views/smartdraw/SmartDrawHandler.tsx
+++ b/src/client/views/smartdraw/SmartDrawHandler.tsx
@@ -28,6 +28,7 @@ import { FireflyDimensionsMap, FireflyImageData, FireflyImageDimensions } from '
import './SmartDrawHandler.scss';
import { Upload } from '../../../server/SharedMediaTypes';
import { PointData } from '../../../pen-gestures/GestureTypes';
+import { List } from '../../../fields/List';
export interface DrawingOptions {
text?: string;
@@ -293,15 +294,17 @@ export class SmartDrawHandler extends ObservableReactComponent<object> {
return undefined;
}
const newseed = img.accessPaths.agnostic.client.match(/\/(\d+)upload/)?.[1];
- const imgDoc: Doc = Docs.Create.ImageDocument(img.accessPaths.agnostic.client, {
+ return Docs.Create.ImageDocument(img.accessPaths.agnostic.client, {
title: input,
nativeWidth: dims.width,
nativeHeight: dims.height,
+ tags: new List<string>(['@ai']),
+ _width: Math.min(400, dims.width),
+ _height: (Math.min(400, dims.width) * dims.height) / dims.width,
ai: 'firefly',
ai_firefly_seed: +(newseed ?? 0),
ai_firefly_prompt: input,
});
- return imgDoc;
})
.catch(e => {
alert('create image failed: ' + e.toString());
@@ -568,6 +571,7 @@ export class SmartDrawHandler extends ObservableReactComponent<object> {
color={SettingsManager.userColor}
/>
<input
+ style={{ color: SettingsManager.userColor, background: SettingsManager.userBackgroundColor }}
aria-label="Smart Draw Input"
className="smartdraw-input"
type="text"