我正在Image
使用 flexbox设计一个组件,使其位于屏幕中央,效果很好。现在我希望第二个Image
组件直接显示在第一个组件的顶部。第二张图片使用绝对定位。目前,我只是在猜测像素以使其适合,但这当然不准确,并且在可维护性方面付出了太多努力。
我几乎在寻找 jQuery 的 React Native 等价物.offset()
。有没有这样的事情,如果没有什么是实现这一目标的最佳方法?
我正在Image
使用 flexbox设计一个组件,使其位于屏幕中央,效果很好。现在我希望第二个Image
组件直接显示在第一个组件的顶部。第二张图片使用绝对定位。目前,我只是在猜测像素以使其适合,但这当然不准确,并且在可维护性方面付出了太多努力。
我几乎在寻找 jQuery 的 React Native 等价物.offset()
。有没有这样的事情,如果没有什么是实现这一目标的最佳方法?
React Native 提供了一种.measure(...)
方法,该方法接受回调并使用组件的偏移量和宽度/高度调用它:
myComponent.measure( (fx, fy, width, height, px, py) => {
console.log('Component width is: ' + width)
console.log('Component height is: ' + height)
console.log('X offset to frame: ' + fx)
console.log('Y offset to frame: ' + fy)
console.log('X offset to page: ' + px)
console.log('Y offset to page: ' + py)
})
以下计算渲染后的自定义组件的布局:
class MyComponent extends React.Component {
render() {
return <View ref={view => { this.myComponent = view; }} />
}
componentDidMount() {
// Print component dimensions to console
this.myComponent.measure( (fx, fy, width, height, px, py) => {
console.log('Component width is: ' + width)
console.log('Component height is: ' + height)
console.log('X offset to frame: ' + fx)
console.log('Y offset to frame: ' + fy)
console.log('X offset to page: ' + px)
console.log('Y offset to page: ' + py)
})
}
}
请注意,有时组件在componentDidMount()
调用之前未完成渲染。如果您从 中得到零measure(...)
,那么将它包装在 a 中setTimeout
应该可以解决问题,即:
setTimeout( myComponent.measure(...), 0 )
您可以使用它们在可用的最早时刻onLayout
获取组件的宽度、高度和相对于父级的位置:
<View
onLayout={event => {
const layout = event.nativeEvent.layout;
console.log('height:', layout.height);
console.log('width:', layout.width);
console.log('x:', layout.x);
console.log('y:', layout.y);
}}
>
与接受的答案中所示的使用.measure()
相比,这样做的优点是您永远不必摆弄推迟.measure()
呼叫setTimeout
以确保测量可用,但缺点是它不会为您提供相对于整个页面,只有与元素的父元素相关的页面。
我有一个类似的问题并通过结合上面的答案解决了它
class FeedPost extends React.Component {
constructor(props) {
...
this.handleLayoutChange = this.handleLayoutChange.bind(this);
}
handleLayoutChange() {
this.feedPost.measure( (fx, fy, width, height, px, py) => {
console.log('Component width is: ' + width)
console.log('Component height is: ' + height)
console.log('X offset to page: ' + px)
console.log('Y offset to page: ' + py)
})
}
render {
return(
<View onLayout={(event) => {this.handleLayoutChange(event) }}
ref={view => { this.feedPost = view; }} >
...
现在我可以在日志中看到我的 feedPost 元素的位置:
08-24 11:15:36.838 3727 27838 I ReactNativeJS: Component width is: 156
08-24 11:15:36.838 3727 27838 I ReactNativeJS: Component height is: 206
08-24 11:15:36.838 3727 27838 I ReactNativeJS: X offset to page: 188
08-24 11:15:36.838 3727 27838 I ReactNativeJS: Y offset to page: 870
我需要在 ListView 中找到元素的位置并使用这个片段,它的工作原理类似于.offset
:
const UIManager = require('NativeModules').UIManager;
const handle = React.findNodeHandle(this.refs.myElement);
UIManager.measureLayoutRelativeToParent(
handle,
(e) => {console.error(e)},
(x, y, w, h) => {
console.log('offset', x, y, w, h);
});
这假设ref='myElement'
我的组件上有一个。
如果您使用的功能部件,并且不希望使用forwardRef
来衡量你的组件的绝对布局,你可以从它的一个引用LayoutChangeEvent
的onLayout
回调。
这样,您就可以获取元素的绝对位置:
<MyFunctionComp
onLayout={(event) => {
event.target.measure(
(x, y, width, height, pageX, pageY) => {
doSomethingWithAbsolutePosition({
x: x + pageX,
y: y + pageY,
});
},
);
}}
/>
使用 React Native 0.63.3 测试。