mirror of
https://gitee.com/vant-contrib/vant.git
synced 2025-04-06 03:57:59 +08:00
fix(IndexBar): incorrect behavior inside popup (#7559)
This commit is contained in:
parent
97f2028e4e
commit
d78438a899
@ -1,6 +1,7 @@
|
|||||||
import { createNamespace } from '../utils';
|
import { createNamespace } from '../utils';
|
||||||
import { ChildrenMixin } from '../mixins/relation';
|
import { ChildrenMixin } from '../mixins/relation';
|
||||||
import { BORDER_BOTTOM } from '../utils/constant';
|
import { BORDER_BOTTOM } from '../utils/constant';
|
||||||
|
import { getScrollTop, getRootScrollTop } from '../utils/dom/scroll';
|
||||||
|
|
||||||
const [createComponent, bem] = createNamespace('index-anchor');
|
const [createComponent, bem] = createNamespace('index-anchor');
|
||||||
|
|
||||||
@ -15,6 +16,7 @@ export default createComponent({
|
|||||||
return {
|
return {
|
||||||
top: 0,
|
top: 0,
|
||||||
left: null,
|
left: null,
|
||||||
|
rect: { top: 0, height: 0 },
|
||||||
width: null,
|
width: null,
|
||||||
active: false,
|
active: false,
|
||||||
};
|
};
|
||||||
@ -39,20 +41,35 @@ export default createComponent({
|
|||||||
},
|
},
|
||||||
|
|
||||||
mounted() {
|
mounted() {
|
||||||
this.height = this.$el.offsetHeight;
|
const rect = this.$el.getBoundingClientRect();
|
||||||
|
this.rect.height = rect.height;
|
||||||
},
|
},
|
||||||
|
|
||||||
methods: {
|
methods: {
|
||||||
scrollIntoView() {
|
scrollIntoView() {
|
||||||
this.$el.scrollIntoView();
|
this.$el.scrollIntoView();
|
||||||
},
|
},
|
||||||
|
|
||||||
|
getRect(scroller, scrollerRect) {
|
||||||
|
const el = this.$el;
|
||||||
|
const elRect = el.getBoundingClientRect();
|
||||||
|
this.rect.height = elRect.height;
|
||||||
|
|
||||||
|
if (scroller === window || scroller === document.body) {
|
||||||
|
this.rect.top = elRect.top + getRootScrollTop();
|
||||||
|
} else {
|
||||||
|
this.rect.top = elRect.top + getScrollTop(scroller) - scrollerRect.top;
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.rect;
|
||||||
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
render() {
|
render() {
|
||||||
const { sticky } = this;
|
const { sticky } = this;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<div style={{ height: sticky ? `${this.height}px` : null }}>
|
<div style={{ height: sticky ? `${this.rect.height}px` : null }}>
|
||||||
<div
|
<div
|
||||||
style={this.anchorStyle}
|
style={this.anchorStyle}
|
||||||
class={[bem({ sticky }), { [BORDER_BOTTOM]: sticky }]}
|
class={[bem({ sticky }), { [BORDER_BOTTOM]: sticky }]}
|
||||||
|
@ -5,7 +5,6 @@ import { preventDefault } from '../utils/dom/event';
|
|||||||
import {
|
import {
|
||||||
getScroller,
|
getScroller,
|
||||||
getScrollTop,
|
getScrollTop,
|
||||||
getElementTop,
|
|
||||||
getRootScrollTop,
|
getRootScrollTop,
|
||||||
setRootScrollTop,
|
setRootScrollTop,
|
||||||
} from '../utils/dom/scroll';
|
} from '../utils/dom/scroll';
|
||||||
@ -103,10 +102,9 @@ export default createComponent({
|
|||||||
|
|
||||||
const scrollTop = getScrollTop(this.scroller);
|
const scrollTop = getScrollTop(this.scroller);
|
||||||
const scrollerRect = this.getScrollerRect();
|
const scrollerRect = this.getScrollerRect();
|
||||||
const rects = this.children.map((item) => ({
|
const rects = this.children.map((item) =>
|
||||||
height: item.height,
|
item.getRect(this.scroller, scrollerRect)
|
||||||
top: this.getElementTop(item.$el, scrollerRect),
|
);
|
||||||
}));
|
|
||||||
|
|
||||||
const active = this.getActiveAnchorIndex(scrollTop, rects);
|
const active = this.getActiveAnchorIndex(scrollTop, rects);
|
||||||
|
|
||||||
@ -131,7 +129,7 @@ export default createComponent({
|
|||||||
} else if (index === active - 1) {
|
} else if (index === active - 1) {
|
||||||
const activeItemTop = rects[active].top - scrollTop;
|
const activeItemTop = rects[active].top - scrollTop;
|
||||||
item.active = activeItemTop > 0;
|
item.active = activeItemTop > 0;
|
||||||
item.top = activeItemTop + scrollerRect.top - item.height;
|
item.top = activeItemTop + scrollerRect.top - rects[index].height;
|
||||||
} else {
|
} else {
|
||||||
item.active = false;
|
item.active = false;
|
||||||
}
|
}
|
||||||
@ -150,18 +148,6 @@ export default createComponent({
|
|||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
|
||||||
getElementTop(ele, scrollerRect) {
|
|
||||||
const { scroller } = this;
|
|
||||||
|
|
||||||
if (scroller === window || scroller === document.body) {
|
|
||||||
return getElementTop(ele);
|
|
||||||
}
|
|
||||||
|
|
||||||
const eleRect = ele.getBoundingClientRect();
|
|
||||||
|
|
||||||
return eleRect.top - scrollerRect.top + getScrollTop(scroller);
|
|
||||||
},
|
|
||||||
|
|
||||||
getActiveAnchorIndex(scrollTop, rects) {
|
getActiveAnchorIndex(scrollTop, rects) {
|
||||||
for (let i = this.children.length - 1; i >= 0; i--) {
|
for (let i = this.children.length - 1; i >= 0; i--) {
|
||||||
const prevHeight = i > 0 ? rects[i - 1].height : 0;
|
const prevHeight = i > 0 ? rects[i - 1].height : 0;
|
||||||
|
@ -1,13 +1,5 @@
|
|||||||
import { mount, trigger, triggerDrag, mockScrollIntoView } from '../../../test';
|
import { mount, trigger, triggerDrag, mockScrollIntoView } from '../../../test';
|
||||||
|
|
||||||
function mockOffsetHeight(offsetHeight) {
|
|
||||||
Object.defineProperty(HTMLElement.prototype, 'offsetHeight', {
|
|
||||||
get() {
|
|
||||||
return offsetHeight;
|
|
||||||
},
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
test('should allow to custom anchor text', () => {
|
test('should allow to custom anchor text', () => {
|
||||||
const wrapper = mount({
|
const wrapper = mount({
|
||||||
template: `
|
template: `
|
||||||
@ -97,11 +89,10 @@ test('should update active anchor after page scroll', () => {
|
|||||||
const { index } = this.dataset;
|
const { index } = this.dataset;
|
||||||
return {
|
return {
|
||||||
top: index ? index * 10 : 0,
|
top: index ? index * 10 : 0,
|
||||||
|
height: 10,
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
mockOffsetHeight(10);
|
|
||||||
|
|
||||||
const wrapper = mount({
|
const wrapper = mount({
|
||||||
template: `
|
template: `
|
||||||
<van-index-bar :sticky="sticky">
|
<van-index-bar :sticky="sticky">
|
||||||
@ -138,11 +129,10 @@ test('should emit change event when active index changed', () => {
|
|||||||
const { index } = this.dataset;
|
const { index } = this.dataset;
|
||||||
return {
|
return {
|
||||||
top: index ? index * 10 : 0,
|
top: index ? index * 10 : 0,
|
||||||
|
height: 10,
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
mockOffsetHeight(10);
|
|
||||||
|
|
||||||
const onChange = jest.fn();
|
const onChange = jest.fn();
|
||||||
|
|
||||||
mount({
|
mount({
|
||||||
|
Loading…
x
Reference in New Issue
Block a user