Change text copy to use fallback (#811)

This commit is contained in:
Salih Altun
2024-09-11 20:01:45 +03:00
committed by GitHub
parent dddfaf98e2
commit 267c859d3b
5 changed files with 51 additions and 18 deletions

View File

@@ -2,6 +2,7 @@ import { useState } from "react";
import { Button } from "./button"; import { Button } from "./button";
import { Input } from "./input"; import { Input } from "./input";
import { CheckIcon, CopyIcon } from "@radix-ui/react-icons"; import { CheckIcon, CopyIcon } from "@radix-ui/react-icons";
import { copyText } from "@/util/copyText";
type Props = { type Props = {
value: string; value: string;
@@ -22,14 +23,15 @@ function HiddenCopyableInput({ value }: Props) {
size="sm" size="sm"
variant="secondary" variant="secondary"
className="cursor-pointer" className="cursor-pointer"
onClick={async () => { onClick={() => {
if (hidden) { if (hidden) {
setHidden(false); setHidden(false);
return; return;
} }
await navigator.clipboard.writeText(value); copyText(value).then(() => {
setCopied(true); setCopied(true);
setTimeout(() => setCopied(false), 3000); setTimeout(() => setCopied(false), 3000);
});
}} }}
> >
{!hidden && !copied && <CopyIcon className="mr-2 h-4 w-4" />} {!hidden && !copied && <CopyIcon className="mr-2 h-4 w-4" />}

View File

@@ -47,6 +47,7 @@ import {
import { OrganizationApiResponse } from "@/api/types"; import { OrganizationApiResponse } from "@/api/types";
import { Skeleton } from "@/components/ui/skeleton"; import { Skeleton } from "@/components/ui/skeleton";
import { MAX_STEPS_DEFAULT } from "../constants"; import { MAX_STEPS_DEFAULT } from "../constants";
import { copyText } from "@/util/copyText";
const createNewTaskFormSchema = z const createNewTaskFormSchema = z
.object({ .object({
@@ -487,10 +488,11 @@ function CreateNewTaskForm({ initialValues }: Props) {
"x-api-key": apiCredential ?? "<your-api-key>", "x-api-key": apiCredential ?? "<your-api-key>",
}, },
}); });
await navigator.clipboard.writeText(curl); copyText(curl).then(() => {
toast({ toast({
title: "Copied cURL", title: "Copied cURL",
description: "cURL copied to clipboard", description: "cURL copied to clipboard",
});
}); });
}} }}
> >

View File

@@ -49,6 +49,7 @@ import {
import { OrganizationApiResponse } from "@/api/types"; import { OrganizationApiResponse } from "@/api/types";
import { MAX_STEPS_DEFAULT } from "../constants"; import { MAX_STEPS_DEFAULT } from "../constants";
import { Skeleton } from "@/components/ui/skeleton"; import { Skeleton } from "@/components/ui/skeleton";
import { copyText } from "@/util/copyText";
const savedTaskFormSchema = z const savedTaskFormSchema = z
.object({ .object({
@@ -629,10 +630,11 @@ function SavedTaskForm({ initialValues }: Props) {
"x-api-key": apiCredential ?? "<your-api-key>", "x-api-key": apiCredential ?? "<your-api-key>",
}, },
}); });
await navigator.clipboard.writeText(curl); copyText(curl).then(() => {
toast({ toast({
title: "Copied cURL", title: "Copied cURL",
description: "cURL copied to clipboard", description: "cURL copied to clipboard",
});
}); });
}} }}
> >

View File

@@ -26,6 +26,7 @@ import { taskIsFinalized } from "@/api/utils";
import fetchToCurl from "fetch-to-curl"; import fetchToCurl from "fetch-to-curl";
import { apiBaseUrl } from "@/util/env"; import { apiBaseUrl } from "@/util/env";
import { useApiCredential } from "@/hooks/useApiCredential"; import { useApiCredential } from "@/hooks/useApiCredential";
import { copyText } from "@/util/copyText";
function createTaskRequestObject(values: TaskApiResponse) { function createTaskRequestObject(values: TaskApiResponse) {
return { return {
@@ -142,12 +143,13 @@ function TaskDetails() {
"x-api-key": apiCredential ?? "<your-api-key>", "x-api-key": apiCredential ?? "<your-api-key>",
}, },
}); });
navigator.clipboard.writeText(curl); copyText(curl).then(() => {
toast({ toast({
variant: "success", variant: "success",
title: "Copied to Clipboard", title: "Copied to Clipboard",
description: description:
"The cURL command has been copied to your clipboard.", "The cURL command has been copied to your clipboard.",
});
}); });
}} }}
> >

View File

@@ -0,0 +1,25 @@
/**
* Progressively enhanced text copying
* https://web.dev/patterns/clipboard/copy-text
*/
async function copyText(text: string): Promise<void> {
if ("clipboard" in navigator) {
return navigator.clipboard.writeText(text);
} else {
const textArea = document.createElement("textarea");
textArea.value = text;
textArea.style.opacity = "0";
document.body.appendChild(textArea);
textArea.focus();
textArea.select();
const success = document.execCommand("copy");
document.body.removeChild(textArea);
if (success) {
return Promise.resolve();
} else {
return Promise.reject();
}
}
}
export { copyText };