mirror of
https://github.com/ilyakooo0/urbit.git
synced 2024-12-14 17:41:33 +03:00
interface: fix stateless async clickables
This commit is contained in:
parent
5f3e96566d
commit
7a90f04a06
@ -64,7 +64,6 @@ export default class LaunchApp extends React.Component {
|
|||||||
<Tile
|
<Tile
|
||||||
bg={sigilColor}
|
bg={sigilColor}
|
||||||
to="/~profile"
|
to="/~profile"
|
||||||
borderRadius="3"
|
|
||||||
>
|
>
|
||||||
<Center height="100%">
|
<Center height="100%">
|
||||||
<Sigil ship={`~${window.ship}`} size={80} color={sigilColor} />
|
<Sigil ship={`~${window.ship}`} size={80} color={sigilColor} />
|
||||||
|
@ -30,6 +30,7 @@ textarea, select, input, button { outline: none; }
|
|||||||
|
|
||||||
button {
|
button {
|
||||||
background-color: transparent;
|
background-color: transparent;
|
||||||
|
cursor: pointer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,4 +1,5 @@
|
|||||||
import React, { ReactNode, useState, useEffect, useCallback } from "react";
|
import React, { ReactNode, useState, useEffect, useCallback } from "react";
|
||||||
|
import { useStatelessAsyncClickable } from '~/logic/lib/useStatelessAsyncClickable';
|
||||||
|
|
||||||
import { Button, LoadingSpinner, Action } from "@tlon/indigo-react";
|
import { Button, LoadingSpinner, Action } from "@tlon/indigo-react";
|
||||||
|
|
||||||
@ -6,35 +7,20 @@ import { useFormikContext } from "formik";
|
|||||||
|
|
||||||
interface AsyncActionProps {
|
interface AsyncActionProps {
|
||||||
children: ReactNode;
|
children: ReactNode;
|
||||||
|
name: string;
|
||||||
onClick: (e: React.MouseEvent) => Promise<void>;
|
onClick: (e: React.MouseEvent) => Promise<void>;
|
||||||
}
|
}
|
||||||
|
|
||||||
type ButtonState = "waiting" | "error" | "loading" | "success";
|
|
||||||
|
|
||||||
export function StatelessAsyncAction({
|
export function StatelessAsyncAction({
|
||||||
loadingText,
|
|
||||||
children,
|
children,
|
||||||
onClick,
|
onClick,
|
||||||
|
name = '',
|
||||||
...rest
|
...rest
|
||||||
}: AsyncActionProps & Parameters<typeof Action>[0]) {
|
}: AsyncActionProps & Parameters<typeof Action>[0]) {
|
||||||
const [state, setState] = useState<ButtonState>("waiting");
|
const {
|
||||||
const handleClick = useCallback(
|
onClick: handleClick,
|
||||||
async (e: React.MouseEvent) => {
|
buttonState: state,
|
||||||
try {
|
} = useStatelessAsyncClickable(onClick, name);
|
||||||
setState("loading");
|
|
||||||
await onClick(e);
|
|
||||||
setState("success");
|
|
||||||
} catch (e) {
|
|
||||||
console.error(e);
|
|
||||||
setState("error");
|
|
||||||
} finally {
|
|
||||||
setTimeout(() => {
|
|
||||||
setState("waiting");
|
|
||||||
}, 3000);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
[onClick, setState]
|
|
||||||
);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Action onClick={handleClick} {...rest}>
|
<Action onClick={handleClick} {...rest}>
|
||||||
@ -42,7 +28,7 @@ export function StatelessAsyncAction({
|
|||||||
"Error"
|
"Error"
|
||||||
) : state === "loading" ? (
|
) : state === "loading" ? (
|
||||||
<LoadingSpinner
|
<LoadingSpinner
|
||||||
foreground={rest.primary ? "white" : "black"}
|
foreground={rest.destructive ? "red" : "black"}
|
||||||
background="transparent"
|
background="transparent"
|
||||||
/>
|
/>
|
||||||
) : state === "success" ? (
|
) : state === "success" ? (
|
||||||
|
@ -1,40 +1,26 @@
|
|||||||
import React, { ReactNode, useState, useEffect, useCallback } from "react";
|
import React, { ReactNode, useState, useEffect, useCallback } from "react";
|
||||||
|
|
||||||
import { Button, LoadingSpinner } from "@tlon/indigo-react";
|
import { Button, LoadingSpinner } from "@tlon/indigo-react";
|
||||||
|
|
||||||
import { useFormikContext } from "formik";
|
import { useFormikContext } from "formik";
|
||||||
|
|
||||||
|
import { useStatelessAsyncClickable } from "~/logic/lib/useStatelessAsyncClickable";
|
||||||
|
|
||||||
interface AsyncButtonProps {
|
interface AsyncButtonProps {
|
||||||
children: ReactNode;
|
children: ReactNode;
|
||||||
|
name: string;
|
||||||
onClick: (e: React.MouseEvent) => Promise<void>;
|
onClick: (e: React.MouseEvent) => Promise<void>;
|
||||||
}
|
}
|
||||||
|
|
||||||
type ButtonState = "waiting" | "error" | "loading" | "success";
|
|
||||||
|
|
||||||
export function StatelessAsyncButton({
|
export function StatelessAsyncButton({
|
||||||
loadingText,
|
|
||||||
children,
|
children,
|
||||||
onClick,
|
onClick,
|
||||||
|
name = "",
|
||||||
...rest
|
...rest
|
||||||
}: AsyncButtonProps & Parameters<typeof Button>[0]) {
|
}: AsyncButtonProps & Parameters<typeof Button>[0]) {
|
||||||
const [state, setState] = useState<ButtonState>("waiting");
|
const {
|
||||||
const handleClick = useCallback(
|
onClick: handleClick,
|
||||||
async (e: React.MouseEvent) => {
|
buttonState: state,
|
||||||
try {
|
} = useStatelessAsyncClickable(onClick, name);
|
||||||
setState("loading");
|
|
||||||
await onClick(e);
|
|
||||||
setState("success");
|
|
||||||
} catch (e) {
|
|
||||||
console.error(e);
|
|
||||||
setState("error");
|
|
||||||
} finally {
|
|
||||||
setTimeout(() => {
|
|
||||||
setState("waiting");
|
|
||||||
}, 3000);
|
|
||||||
}
|
|
||||||
},
|
|
||||||
[onClick, setState]
|
|
||||||
);
|
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<Button onClick={handleClick} {...rest}>
|
<Button onClick={handleClick} {...rest}>
|
||||||
|
Loading…
Reference in New Issue
Block a user