mirror of
https://github.com/khairul169/code-share.git
synced 2026-10-24 11:53:58 +07:00
fix: responsive fix
This commit is contained in:
@@ -0,0 +1,57 @@
|
||||
import { useCallback, useEffect, useRef, useState } from "react";
|
||||
|
||||
export const breakpoints = {
|
||||
sm: 640,
|
||||
md: 768,
|
||||
lg: 1024,
|
||||
xl: 1280,
|
||||
"2xl": 1536,
|
||||
};
|
||||
|
||||
export type Breakpoint = keyof typeof breakpoints;
|
||||
|
||||
export const breakpointKeys = Object.keys(breakpoints);
|
||||
export const breakpointValues = Object.values(breakpoints);
|
||||
|
||||
export const useBreakpoint = (onChange?: (breakpoint: number) => void) => {
|
||||
const prevRef = useRef<number>(0);
|
||||
const [curBreakpoint, setBreakpoint] = useState<number>(
|
||||
getScreenBreakpoint()
|
||||
);
|
||||
|
||||
const onResize = useCallback(() => {
|
||||
const breakpointIdx = getScreenBreakpoint();
|
||||
|
||||
if (breakpointIdx >= 0 && prevRef.current !== breakpointIdx) {
|
||||
if (onChange) {
|
||||
onChange(breakpointIdx);
|
||||
} else {
|
||||
setBreakpoint(breakpointIdx);
|
||||
}
|
||||
prevRef.current = breakpointIdx;
|
||||
}
|
||||
}, [onChange]);
|
||||
|
||||
useEffect(() => {
|
||||
window.addEventListener("resize", onResize);
|
||||
onResize();
|
||||
|
||||
return () => {
|
||||
window.removeEventListener("resize", onResize);
|
||||
};
|
||||
}, [onResize]);
|
||||
|
||||
const breakpoint = breakpointKeys[curBreakpoint];
|
||||
|
||||
return [curBreakpoint, breakpoint] as [number, Breakpoint];
|
||||
};
|
||||
|
||||
export function getScreenBreakpoint() {
|
||||
const width = typeof window !== "undefined" ? window.innerWidth : 0;
|
||||
let breakpointIdx = breakpointValues.findIndex((i) => width <= i);
|
||||
if (breakpointIdx < 0) {
|
||||
breakpointIdx = breakpointKeys.length - 1;
|
||||
}
|
||||
|
||||
return breakpointIdx;
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
import { useState } from "react";
|
||||
import {
|
||||
Breakpoint,
|
||||
breakpointKeys,
|
||||
getScreenBreakpoint,
|
||||
useBreakpoint,
|
||||
} from "./useBreakpoint";
|
||||
|
||||
export type BreakpointValues<T> = Partial<Record<Breakpoint, T | null>>;
|
||||
|
||||
export const useBreakpointValue = <T>(values: T | BreakpointValues<T>) => {
|
||||
const [value, setValue] = useState(
|
||||
typeof values === "object"
|
||||
? getValueByBreakpoint(
|
||||
values as BreakpointValues<T>,
|
||||
getScreenBreakpoint()
|
||||
)
|
||||
: values
|
||||
);
|
||||
|
||||
useBreakpoint((breakpoint) => {
|
||||
if (typeof values !== "object") {
|
||||
return;
|
||||
}
|
||||
|
||||
const newValue = getValueByBreakpoint(
|
||||
values as BreakpointValues<T>,
|
||||
breakpoint
|
||||
);
|
||||
|
||||
if (newValue !== value) {
|
||||
setValue(newValue);
|
||||
}
|
||||
});
|
||||
|
||||
return value as T;
|
||||
};
|
||||
|
||||
export function getValueByBreakpoint<T>(
|
||||
values: BreakpointValues<T>,
|
||||
breakpoint: number
|
||||
) {
|
||||
const valueEntries = Object.entries(values as never);
|
||||
|
||||
let resIdx = valueEntries.findIndex(([key]) => {
|
||||
const bpIdx = breakpointKeys.indexOf(key);
|
||||
return breakpoint <= bpIdx;
|
||||
});
|
||||
if (resIdx < 0) {
|
||||
resIdx = valueEntries.length - 1;
|
||||
}
|
||||
|
||||
const value = valueEntries[resIdx]?.[1] as T;
|
||||
return value;
|
||||
}
|
||||
Reference in New Issue
Block a user