I would like to find the top and bottom edge of a div when i move my cursor over it. The div is generated dynamically. However, it produced error message
getBoundingClientRect is not a function
<template>
<div>
<div v-for="(i, index) in divs" :key="index">
<div :ref="'ref_' + index" @mouseover="divDragOver($event, index)">
This is div {{ index }}
</div>
</div>
</div>
</template>
<script>
export default{
methods: {
divDragOver(e, i){
var divTop = this.$refs["ref_" + i].getBoundingClientRect().top;
console.log(divTop);
}
}
}
</script>
I would like to find the top and bottom edge of a div when i move my cursor over it. The div is generated dynamically. However, it produced error message
getBoundingClientRect is not a function
<template>
<div>
<div v-for="(i, index) in divs" :key="index">
<div :ref="'ref_' + index" @mouseover="divDragOver($event, index)">
This is div {{ index }}
</div>
</div>
</div>
</template>
<script>
export default{
methods: {
divDragOver(e, i){
var divTop = this.$refs["ref_" + i].getBoundingClientRect().top;
console.log(divTop);
}
}
}
</script>
Share
Improve this question
asked Jun 2, 2020 at 19:05
davidleedavidlee
6,18718 gold badges58 silver badges87 bronze badges
1
-
There's no need for dynamic refs. Here's an easy way of getting the
top
. – tao Commented Jun 2, 2020 at 20:15
4 Answers
Reset to default 2You can use event.target
as another user suggested which is, I think, the cleanest way
<template>
<div>
<div v-for="(i, index) in divs" :key="index">
<div ref="myDiv" @mouseover="divDragOver">This is div {{ index }}</div>
</div>
</div>
</template>
<script>
export default {
data: function() {
return { divs: [1, 2, 3, 4] };
},
methods: {
divDragOver(event) {
console.log(event.target); // this will be your mouseover div
}
}
};
</script>
For your issue though, based on Vue.js documentation:
When
ref
is used together withv-for
, theref
you get will be an array containing the child ponents mirroring the data source.
So you don't have to use the index on your ref
creation, while you will end up with divs.length
arrays which their first element will be your reference.
If you had to use refs
:
<template>
<div>
<div v-for="(i, index) in divs" :key="index">
<div ref="myDiv" @mouseover="divDragOver($event, index)">This is div {{ index }}</div>
</div>
</div>
</template>
<script>
export default {
data: function() {
return { divs: [1, 2, 3, 4] };
},
methods: {
divDragOver(e, i) {
console.log(this.$refs.myDiv); // this will be an array with all your refs, use i to access
}
}
};
</script>
So you were getting an error because your element's ref
was on this.$refs["ref_" + i][0]
Try something like that:
<template>
<div>
<div v-for="index in divs" :key="index">
<div :ref="'ref_' + index" @mouseover="divDragOver($event, index)">
This is div {{ index }}
</div>
</div>
</div>
</template>
<script>
export default {
name: 'App',
data: () => ({
divs: [1, 2, 3, 4, 5, 6, 7, 8, 9, 10],
}),
methods: {
divDragOver(e, i) {
let [div] = this.$refs['ref_' + i];
let top = div.getBoundingClientRect().top;
console.log(top);
},
},
};
</script>
Your code doesn't work, because the this.refs
return an Array.
this works for me, just add $el
like this
var divTop = this.$refs["ref_" + i].$el.getBoundingClientRect().top;
You can handle this problem by accessing the target element in the event:
<script>
export default{
methods: {
divDragOver(e){
var divTop = e.target.getBoundingClientRect();
console.log(divTop);
}
}
}
</script>