new web init

This commit is contained in:
Qing
2023-11-22 08:53:20 +08:00
parent a5c241ac02
commit 04c5dfece8
51 changed files with 11603 additions and 0 deletions

View File

@@ -0,0 +1,33 @@
import { DependencyList, useEffect, useState } from 'react'
export function useAsyncMemo<T>(
factory: () => Promise<T> | undefined | null,
deps: DependencyList
): T | undefined
export function useAsyncMemo<T>(
factory: () => Promise<T> | undefined | null,
deps: DependencyList,
initial: T
): T
export function useAsyncMemo<T>(
factory: () => Promise<T> | undefined | null,
deps: DependencyList,
initial?: T
) {
const [val, setVal] = useState<T | undefined>(initial)
useEffect(() => {
let cancel = false
const promise = factory()
if (promise === undefined || promise === null) return
promise.then(v => {
if (!cancel) {
setVal(v)
}
})
return () => {
cancel = true
}
}, deps)
return val
}

View File

@@ -0,0 +1,22 @@
import { Options, useHotkeys } from "react-hotkeys-hook"
import { useRecoilValue } from "recoil"
import { appState } from "@/lib/store"
const useHotKey = (
keys: string,
callback: any,
options?: Options,
deps?: any[]
) => {
const app = useRecoilValue(appState)
const ref = useHotkeys(
keys,
callback,
{ ...options, enabled: !app.disableShortCuts },
deps
)
return ref
}
export default useHotKey

View File

@@ -0,0 +1,24 @@
import { useEffect, useState } from "react"
function useImage(file?: File): [HTMLImageElement, boolean] {
const [image] = useState(new Image())
const [isLoaded, setIsLoaded] = useState(false)
useEffect(() => {
if (file === undefined) {
return
}
image.onload = () => {
setIsLoaded(true)
}
setIsLoaded(false)
image.src = URL.createObjectURL(file)
return () => {
image.onload = null
}
}, [file, image])
return [image, isLoaded]
}
export { useImage }

View File

@@ -0,0 +1,34 @@
import { API_ENDPOINT } from "@/lib/api"
import { useCallback, useEffect, useState } from "react"
export default function useInputImage() {
const [inputImage, setInputImage] = useState<File>()
const fetchInputImage = useCallback(() => {
const headers = new Headers()
headers.append("pragma", "no-cache")
headers.append("cache-control", "no-cache")
fetch(`${API_ENDPOINT}/inputimage`, { headers }).then(async (res) => {
const filename = res.headers
.get("content-disposition")
?.split("filename=")[1]
.split(";")[0]
const data = await res.blob()
if (data && data.type.startsWith("image")) {
const userInput = new File(
[data],
filename !== undefined ? filename : "inputImage"
)
setInputImage(userInput)
}
})
}, [setInputImage])
useEffect(() => {
fetchInputImage()
}, [fetchInputImage])
return inputImage
}

View File

@@ -0,0 +1,31 @@
import { useCallback, useEffect, useState } from 'react'
const useResolution = () => {
const [width, setWidth] = useState(window.innerWidth)
const windowSizeHandler = useCallback(() => {
setWidth(window.innerWidth)
}, [])
useEffect(() => {
window.addEventListener('resize', windowSizeHandler)
return () => {
window.removeEventListener('resize', windowSizeHandler)
}
})
if (width < 768) {
return 'mobile'
}
if (width >= 768 && width < 1224) {
return 'tablet'
}
if (width >= 1224) {
return 'desktop'
}
}
export default useResolution