c5_labsci/fapp/ciyon_ap/components/ciy-aniheight/ciy-aniheight.vue

93 lines
2.0 KiB
Vue

<template>
<view class="_refani" v-if="anishow" :style="cstyle">
<slot></slot>
</view>
</template>
<style scoped>
</style>
<script>
export default {
options: {
virtualHost: true
},
props: {
show: {
type: Boolean,
default: false
},
speedms: {
type: [String, Number],
default: 500
},
ciystyle: {
type: [String, Object],
default: ''
}
},
data() {
return {
anishow: false,
height: -1
};
},
watch: {
show(newD, oldD) {
this.Showani(newD);
}
},
computed: {
cstyle() {
var sty = this.ciystyle;
var mastyle = {};
mastyle.overflow = 'hidden';
if(this.height == -1){
mastyle.height = 'auto';
if(this.op == 0)
mastyle.opacity = 0;
}else{
mastyle.height = this.height + 'px';
mastyle.opacity = 1;
}
sty = this.style2obj(sty, mastyle);
return sty;
}
},
mounted() {
this.rect = {};
if (this.show)
this.Showani(this.show);
},
methods: {
async Showani(bshow) {
if(this.height == 0)
this.op = 0;
else
this.op = 1;
this.height = -1;
this.anishow = true;
var rect = await this.getrect('._refani');
if (rect && rect.height != 0)
this.rect = rect;
clearInterval(this.anitimeout);
//cancelAnimationFrame(this.animationFrameId);
if (bshow) {
this.animateHeight(0, this.rect.height, this.toint(this.speedms));
} else {
this.animateHeight(this.rect.height, 0, this.toint(this.speedms));
}
},
animateHeight(startHeight, targetHeight, duration) {
this.height = startHeight;
const startTime = Date.now();//performance.now();
this.anitimeout = setInterval(() => {
const elapsed = Date.now() - startTime;
const progress = Math.min(elapsed / duration, 1);
this.height = startHeight + (targetHeight - startHeight) * progress;
if (progress >= 1)
clearInterval(this.anitimeout);
}, 16);
//this.animationFrameId = uni.requestAnimationFrame(step);
}
}
}
</script>