fix drop target
This commit is contained in:
parent
3849d6b447
commit
b2b849695b
@ -15,7 +15,7 @@
|
||||
// TODO: make this nicer
|
||||
color: theme.$text-normal;
|
||||
background-color: theme.$background-primary;
|
||||
padding: 16px;
|
||||
padding: 32px;
|
||||
border-radius: 8px;
|
||||
|
||||
display: flex;
|
||||
@ -28,9 +28,15 @@
|
||||
margin-right: 16px;
|
||||
}
|
||||
|
||||
.drop-message {
|
||||
font-size: 2em;
|
||||
.drop-description {
|
||||
color: theme.$header-primary;
|
||||
.drop-title {
|
||||
font-size: 2em;
|
||||
font-weight: 600;
|
||||
}
|
||||
.drop-message {
|
||||
font-size: 1.5em;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -26,7 +26,7 @@ $borderRadius: 8px;
|
||||
.attachment-preview {
|
||||
position: relative;
|
||||
margin: 16px 16px 0 16px;
|
||||
padding: 8px;
|
||||
padding: 12px;
|
||||
border-radius: 8px;
|
||||
box-sizing: border-box;
|
||||
max-width: calc(100% - 32px);
|
||||
@ -40,6 +40,8 @@ $borderRadius: 8px;
|
||||
}
|
||||
|
||||
.name {
|
||||
color: theme.$interactive-hover;
|
||||
/* font-weight: 600; */
|
||||
line-height: 1;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
|
@ -6,6 +6,7 @@ const LOG = Logger.create(__filename, electronConsole);
|
||||
import React, { Dispatch, DragEvent, FC, SetStateAction, useCallback, useRef } from 'react';
|
||||
|
||||
export interface FileDropTargetProps {
|
||||
title: string;
|
||||
message: string;
|
||||
setBuff: Dispatch<SetStateAction<Buffer | null>>;
|
||||
setName: Dispatch<SetStateAction<string | null>>;
|
||||
@ -13,7 +14,7 @@ export interface FileDropTargetProps {
|
||||
}
|
||||
|
||||
const FileDropTarget: FC<FileDropTargetProps> = (props: FileDropTargetProps) => {
|
||||
const { setBuff, setName, close, message } = props;
|
||||
const { setBuff, setName, close, title, message } = props;
|
||||
|
||||
const rootRef = useRef<HTMLDivElement>(null);
|
||||
|
||||
@ -64,7 +65,10 @@ const FileDropTarget: FC<FileDropTargetProps> = (props: FileDropTargetProps) =>
|
||||
<div className="file-drop" ref={rootRef} onDrop={onDrop} onDragOver={onDragOver} onDragLeave={onDragLeave}>
|
||||
<div className="panel">
|
||||
<img className="drop-icon" src="./img/file-improved.svg" alt="file" />
|
||||
<div className="drop-message">{message}</div>
|
||||
<div className="drop-description">
|
||||
<div className="drop-title">{title}</div>
|
||||
<div className="drop-message">{message}</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
@ -21,7 +21,7 @@ export interface ImageContextMenuProps {
|
||||
const ImageContextMenu: FC<ImageContextMenuProps> = (props: ImageContextMenuProps) => {
|
||||
const { relativeToPos, close, resourceName, resourceBuff, isPreview } = props;
|
||||
|
||||
const previewText = isPreview ? ' Preview' : '';
|
||||
const previewText = isPreview ? ' Preview' : ' Image';
|
||||
|
||||
// TODO: Integrate shaking
|
||||
|
||||
@ -44,23 +44,33 @@ const ImageContextMenu: FC<ImageContextMenuProps> = (props: ImageContextMenuProp
|
||||
},
|
||||
[resourceBuff],
|
||||
{
|
||||
start: 'Copy Image' + previewText,
|
||||
start: 'Copy ' + previewText,
|
||||
pending: 'Copying' + previewText,
|
||||
error: 'Copy Failed. Click to Try Again',
|
||||
done: 'Copied to Clipboard',
|
||||
},
|
||||
);
|
||||
|
||||
const [saveCallable, saveText, _saveShaking] = useDownloadButton(resourceName + (isPreview ? '-preview.jpg' : ''), async () => resourceBuff, [resourceBuff], {
|
||||
start: 'Save Image' + previewText,
|
||||
pendingSave: 'Saving' + previewText + '...',
|
||||
errorSave: 'Save Failed. Click to Try Again',
|
||||
});
|
||||
const [saveCallable, saveText, _saveShaking] = useDownloadButton(
|
||||
resourceName + (isPreview ? '-preview.jpg' : ''),
|
||||
async () => resourceBuff,
|
||||
[resourceBuff],
|
||||
{
|
||||
start: 'Save ' + previewText,
|
||||
pendingSave: 'Saving' + previewText + '...',
|
||||
errorSave: 'Save Failed. Click to Try Again',
|
||||
},
|
||||
);
|
||||
|
||||
const alignment = useMemo(() => ({ top: 'centerY', left: 'centerX' }), []);
|
||||
|
||||
return (
|
||||
<ContextMenu alignment={alignment} relativeToPos={relativeToPos} realignDeps={[copyText, saveText]} close={close}>
|
||||
<ContextMenu
|
||||
alignment={alignment}
|
||||
relativeToPos={relativeToPos}
|
||||
realignDeps={[copyText, saveText]}
|
||||
close={close}
|
||||
>
|
||||
<div className="image">
|
||||
<div className="item copy-image" onClick={copyCallable}>
|
||||
{copyText}
|
||||
|
@ -573,6 +573,7 @@ export function useContextHover(
|
||||
|
||||
/** creates a drop target element that will appear when you drag a file over the document */
|
||||
export function useDocumentDropTarget(
|
||||
title: string,
|
||||
message: string,
|
||||
setBuff: Dispatch<SetStateAction<Buffer | null>>,
|
||||
setName: Dispatch<SetStateAction<string | null>>,
|
||||
@ -599,8 +600,16 @@ export function useDocumentDropTarget(
|
||||
|
||||
const dropTarget = useMemo(() => {
|
||||
if (!dragEnabled) return null;
|
||||
return <FileDropTarget close={closeDragOverlay} message={message} setBuff={setBuff} setName={setName} />;
|
||||
}, [closeDragOverlay, dragEnabled, message, setBuff, setName]);
|
||||
return (
|
||||
<FileDropTarget
|
||||
close={closeDragOverlay}
|
||||
title={title}
|
||||
message={message}
|
||||
setBuff={setBuff}
|
||||
setName={setName}
|
||||
/>
|
||||
);
|
||||
}, [closeDragOverlay, dragEnabled, title, message, setBuff, setName]);
|
||||
|
||||
return [dropTarget];
|
||||
}
|
||||
|
@ -1,8 +1,23 @@
|
||||
import React, { ClipboardEvent, FC, FormEvent, KeyboardEvent, RefObject, useCallback, useMemo, useRef, useState } from 'react';
|
||||
import React, {
|
||||
ClipboardEvent,
|
||||
FC,
|
||||
FormEvent,
|
||||
KeyboardEvent,
|
||||
RefObject,
|
||||
useCallback,
|
||||
useMemo,
|
||||
useRef,
|
||||
useState,
|
||||
} from 'react';
|
||||
import { Channel } from '../../data-types';
|
||||
import CombinedGuild from '../../guild-combined';
|
||||
import BaseElements from '../require/base-elements';
|
||||
import { useAsyncVoidCallback, useDocumentDropTarget, useIsMountedRef, useOneTimeAsyncAction } from '../require/react-helper';
|
||||
import {
|
||||
useAsyncVoidCallback,
|
||||
useDocumentDropTarget,
|
||||
useIsMountedRef,
|
||||
useOneTimeAsyncAction,
|
||||
} from '../require/react-helper';
|
||||
import * as FileType from 'file-type';
|
||||
import ElementsUtil from '../require/elements-util';
|
||||
import FileInput from '../components/input-file';
|
||||
@ -66,7 +81,12 @@ const SendMessage: FC<SendMessageProps> = (props: SendMessageProps) => {
|
||||
|
||||
// TODO: Deal with errors (toasts are probably the best way)
|
||||
if (attachmentBuff && attachmentName) {
|
||||
await guild.requestSendMessageWithResource(channel.id, text === '' ? null : text, attachmentBuff, attachmentName);
|
||||
await guild.requestSendMessageWithResource(
|
||||
channel.id,
|
||||
text === '' ? null : text,
|
||||
attachmentBuff,
|
||||
attachmentName,
|
||||
);
|
||||
if (!isMounted.current) return;
|
||||
setAttachmentBuff(null);
|
||||
setAttachmentName(null);
|
||||
@ -122,11 +142,22 @@ const SendMessage: FC<SendMessageProps> = (props: SendMessageProps) => {
|
||||
setAttachmentName(null);
|
||||
}, []);
|
||||
|
||||
const [attachmentDropTarget] = useDocumentDropTarget('Upload to #' + channel.name, setAttachmentBuff, setAttachmentName);
|
||||
const [attachmentDropTarget] = useDocumentDropTarget(
|
||||
'Drop to Attach',
|
||||
'#' + channel.name,
|
||||
setAttachmentBuff,
|
||||
setAttachmentName,
|
||||
);
|
||||
|
||||
const attachmentPreview = useMemo(() => {
|
||||
if (!attachmentBuff || !attachmentName) return null;
|
||||
return <AttachmentPreview attachmentBuff={attachmentBuff} attachmentName={attachmentName} remove={removeAttachment} />;
|
||||
return (
|
||||
<AttachmentPreview
|
||||
attachmentBuff={attachmentBuff}
|
||||
attachmentName={attachmentName}
|
||||
remove={removeAttachment}
|
||||
/>
|
||||
);
|
||||
}, [attachmentBuff, attachmentName, removeAttachment]);
|
||||
|
||||
// WARNING: The types on this are funky because of react's lack of explicit support for 'plaintext-only'
|
||||
@ -149,7 +180,15 @@ const SendMessage: FC<SendMessageProps> = (props: SendMessageProps) => {
|
||||
{BaseElements.SEND_MESSAGE_ATTACH}
|
||||
</FileInput>
|
||||
</div>
|
||||
<div ref={contentEditableRef} className={textInputClassName} contentEditable={contentEditableType} data-placeholder={`Message #${channel.name}`} onInput={onTextInput} onKeyDown={onTextKeyDown} onPaste={onPaste} />
|
||||
<div
|
||||
ref={contentEditableRef}
|
||||
className={textInputClassName}
|
||||
contentEditable={contentEditableType}
|
||||
data-placeholder={`Message #${channel.name}`}
|
||||
onInput={onTextInput}
|
||||
onKeyDown={onTextKeyDown}
|
||||
onPaste={onPaste}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
{attachmentDropTarget}
|
||||
|
@ -9,7 +9,5 @@
|
||||
</head>
|
||||
<body class="preload">
|
||||
<div id="react-root"></div>
|
||||
<!-- it's important that this comes at the end so that these take prescedence over the other absolutely positioned objects-->
|
||||
<div id="react-overlays"></div>
|
||||
</body>
|
||||
</html>
|
||||
|
Loading…
Reference in New Issue
Block a user