Merge pull request #168 from danny-avila/feat-export-convo

fix: remove use-screenshot
This commit is contained in:
Danny Avila 2023-04-07 10:15:43 -04:00 committed by GitHub
commit 7ec90a3585
4 changed files with 81 additions and 58 deletions

View file

@ -68,7 +68,6 @@
"tailwindcss-animate": "^1.0.5",
"tailwindcss-radix": "^2.8.0",
"url": "^0.11.0",
"use-react-screenshot": "github:danny-avila/use-react-screenshot#master",
"uuidv4": "^6.2.13"
},
"devDependencies": {

View file

@ -23,7 +23,6 @@ export default function ExportModel({ open, onOpenChange }) {
const [includeOptions, setIncludeOptions] = useState(true);
const [exportBranches, setExportBranches] = useState(false);
const [exportBranchesSupport, setExportBranchesSupport] = useState(false);
const [recursive, setRecursive] = useState(true);
const conversation = useRecoilValue(store.conversation) || {};
@ -37,30 +36,34 @@ export default function ExportModel({ open, onOpenChange }) {
[]
);
const typeOptions = ['text', 'markdown', 'csv', 'json', 'screenshot']; //,, 'webpage'];
const typeOptions = [
{ value: 'text', display: 'text (.txt)' },
{ value: 'markdown', display: 'markdown (.md)' },
{ value: 'csv', display: 'csv (.csv)' },
{ value: 'json', display: 'json (.json)' },
{ value: 'screenshot', display: 'screenshot (.png)' }
]; //,, 'webpage'];
useEffect(() => {
setFileName(
filenamify(String(conversation?.title || 'file'))
);
setFileName(filenamify(String(conversation?.title || 'file')));
setType('text');
setIncludeOptions(true);
setExportBranches(false);
setExportBranchesSupport(false);
setRecursive(true);
}, [open]);
const _setType = newType => {
if (newType === 'json' || newType === 'csv' || newType === 'webpage') {
setExportBranches(true);
setExportBranchesSupport(true);
} else {
setExportBranches(false);
setExportBranchesSupport(false);
}
const exportBranchesSupport = newType === 'json' || newType === 'csv' || newType === 'webpage';
const exportOptionsSupport = newType !== 'csv' && newType !== 'screenshot';
setExportBranches(exportBranchesSupport);
setIncludeOptions(exportOptionsSupport);
setType(newType);
};
const exportBranchesSupport = type === 'json' || type === 'csv' || type === 'webpage';
const exportOptionsSupport = type !== 'csv' && type !== 'screenshot';
// return an object or an array based on branches and recursive option
// messageId is used to get siblindIdx from recoil snapshot
const buildMessageTree = async ({ messageId, message, messages, branches = false, recursive = false }) => {
@ -320,7 +323,6 @@ export default function ExportModel({ open, onOpenChange }) {
</div>
</div>
<div className="grid w-full gap-6 sm:grid-cols-2">
{type !== 'csv' && type !== 'screenshot' ? (
<div className="col-span-1 flex flex-col items-start justify-start gap-2">
<div className="grid w-full items-center gap-2">
<Label
@ -332,6 +334,7 @@ export default function ExportModel({ open, onOpenChange }) {
<div className="flex h-[40px] w-full items-center space-x-3">
<Checkbox
id="includeOptions"
disabled={!exportOptionsSupport}
checked={includeOptions}
className="focus:ring-opacity-20 dark:border-gray-500 dark:bg-gray-700 dark:text-gray-50 dark:focus:ring-gray-600 dark:focus:ring-opacity-50 dark:focus:ring-offset-0"
onCheckedChange={setIncludeOptions}
@ -340,13 +343,11 @@ export default function ExportModel({ open, onOpenChange }) {
htmlFor="includeOptions"
className="text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70 dark:text-gray-50"
>
Enabled
{exportOptionsSupport ? 'Enabled' : 'Not Supported'}
</label>
</div>
</div>
</div>
) : null}
{type !== 'screenshot' ? (
<div className="grid w-full items-center gap-2">
<Label
htmlFor="exportBranches"
@ -370,7 +371,6 @@ export default function ExportModel({ open, onOpenChange }) {
</label>
</div>
</div>
) : null}
{type === 'json' ? (
<div className="grid w-full items-center gap-2">
<Label

View file

@ -4,6 +4,7 @@ import { Listbox } from '@headlessui/react';
import { cn } from '~/utils/';
function Dropdown({ value, onChange, options, className, containerClassName }) {
const currentOption = options.find(element => element === value || element?.value === value) ?? value;
return (
<div className={cn('flex items-center justify-center gap-2', containerClassName)}>
<div className="relative w-full">
@ -19,7 +20,7 @@ function Dropdown({ value, onChange, options, className, containerClassName }) {
>
<span className="inline-flex w-full truncate">
<span className="flex h-6 items-center gap-1 truncate text-sm text-black dark:text-white">
{value}
{currentOption?.display ?? value}
</span>
</span>
<span className="pointer-events-none absolute inset-y-0 right-0 flex items-center pr-2">
@ -43,19 +44,19 @@ function Dropdown({ value, onChange, options, className, containerClassName }) {
{options.map((item, i) => (
<Listbox.Option
key={i}
value={item}
value={item?.value ?? item}
className="group relative flex h-[42px] cursor-pointer select-none items-center overflow-hidden border-b border-black/10 pl-3 pr-9 text-gray-900 last:border-0 hover:bg-[#ECECF1] dark:border-white/20 dark:text-white dark:hover:bg-gray-700"
>
<span className="flex items-center gap-1.5 truncate">
<span
className={cn(
'flex h-6 items-center gap-1 text-gray-800 dark:text-gray-100',
value === item ? 'font-semibold' : ''
value === (item?.value ?? item) ? 'font-semibold' : ''
)}
>
{item}
{item?.display ?? item}
</span>
{value === item && (
{value === (item?.value ?? item) && (
<span className="absolute inset-y-0 right-0 flex items-center pr-3 text-gray-800 dark:text-gray-100">
<CheckMark />
</span>

View file

@ -1,14 +1,37 @@
import React, { createContext, useRef, useContext, useCallback } from 'react';
import { useScreenshot as useScreenshot_ } from 'use-react-screenshot';
import html2canvas from 'html2canvas';
const ScreenshotContext = createContext({});
export const useScreenshot = () => {
const { ref } = useContext(ScreenshotContext);
const [image, takeScreenshot] = useScreenshot_();
const takeScreenShot = node => {
if (!node) {
throw new Error('You should provide correct html node.');
}
return html2canvas(node).then(canvas => {
const croppedCanvas = document.createElement('canvas');
const croppedCanvasContext = croppedCanvas.getContext('2d');
// init data
const cropPositionTop = 0;
const cropPositionLeft = 0;
const cropWidth = canvas.width;
const cropHeight = canvas.height;
croppedCanvas.width = cropWidth;
croppedCanvas.height = cropHeight;
croppedCanvasContext.drawImage(canvas, cropPositionLeft, cropPositionTop);
const base64Image = croppedCanvas.toDataURL('image/png', 1);
return base64Image;
});
};
const captureScreenshot = () => {
return takeScreenshot(ref.current);
return takeScreenShot(ref.current);
};
return { screenshotTargetRef: ref, captureScreenshot };