mirror of
https://gitee.com/ant-design-vue/ant-design-vue.git
synced 2024-12-05 13:39:40 +08:00
66 lines
1.6 KiB
TypeScript
66 lines
1.6 KiB
TypeScript
import { shallowRef, watch } from 'vue';
|
|
import type { MaybeComputedElementRef } from './unrefElement';
|
|
import type { UseResizeObserverOptions } from './useResizeObserver';
|
|
import { useResizeObserver } from './useResizeObserver';
|
|
import { unrefElement } from './unrefElement';
|
|
|
|
export interface ElementSize {
|
|
width: number;
|
|
height: number;
|
|
}
|
|
|
|
/**
|
|
* Reactive size of an HTML element.
|
|
*
|
|
* @see https://vueuse.org/useElementSize
|
|
* @param target
|
|
* @param callback
|
|
* @param options
|
|
*/
|
|
export function useElementSize(
|
|
target: MaybeComputedElementRef,
|
|
initialSize: ElementSize = { width: 0, height: 0 },
|
|
options: UseResizeObserverOptions = {},
|
|
) {
|
|
const { box = 'content-box' } = options;
|
|
const width = shallowRef(initialSize.width);
|
|
const height = shallowRef(initialSize.height);
|
|
|
|
useResizeObserver(
|
|
target,
|
|
([entry]) => {
|
|
const boxSize =
|
|
box === 'border-box'
|
|
? entry.borderBoxSize
|
|
: box === 'content-box'
|
|
? entry.contentBoxSize
|
|
: entry.devicePixelContentBoxSize;
|
|
|
|
if (boxSize) {
|
|
width.value = boxSize.reduce((acc, { inlineSize }) => acc + inlineSize, 0);
|
|
height.value = boxSize.reduce((acc, { blockSize }) => acc + blockSize, 0);
|
|
} else {
|
|
// fallback
|
|
width.value = entry.contentRect.width;
|
|
height.value = entry.contentRect.height;
|
|
}
|
|
},
|
|
options,
|
|
);
|
|
|
|
watch(
|
|
() => unrefElement(target),
|
|
ele => {
|
|
width.value = ele ? initialSize.width : 0;
|
|
height.value = ele ? initialSize.height : 0;
|
|
},
|
|
);
|
|
|
|
return {
|
|
width,
|
|
height,
|
|
};
|
|
}
|
|
|
|
export type UseElementSizeReturn = ReturnType<typeof useElementSize>;
|