Html 未知高度折叠菜单使用transition过渡动画
2019-05-04
4,774 views
4 min read
这是此前项目要实现的效果,一个简单的折叠框,但为了让其使用更加的顺滑,想通过加入transition
过渡动画让其展开更加的舒服。
但是有一个致命的问题,transition
过渡动画是必须得提前知道元素的起止属性,即展开前高度和展开后高度,因为里面内容是动态的,所以无法直接给出最终高度。使用max-height
属性能实现过渡动画,但是效果太差,所以采用了js计算高度的方式。
首先给父容器即折叠栏赋予overflow: hidden;
和固定的高度的classflod
,以及过渡动画transition: height .75s;
,子元素即内容赋予visibility: hidden;
,如果所示。
.collapse {
background-color: white;
border-radius: 40rpx;
box-sizing: border-box;
overflow: hidden;
transition: all .75s;
}
.fold {
height: 80rpx !important;
}
折叠栏在折叠的情况下:
触发点击事件=>
移除classflod
=>
动态加载元素=>
计算出内容元素高度=>
赋予折叠栏新高度(折叠下高度+元素内容高度) && 显示内容元素(visibility: visible;
)
折叠栏在展开的情况下:
触发点击事件=>
计算当前总高度并赋予折叠栏=>
移除内容元素=>
添加classflod
以下是在微信小程序内的实现方式
wxml
<view class='collapse {{fold || hide ? "fold" : ""}}' style='height: {{height}};'>
<view class='top-container' bindtap='fold'>
<view class='title'>{{title}}</view>
<view class='angle'>
<view wx:if='{{fold}}' class='fa fa-angle-down'></view>
<view wx:else class='fa fa-angle-up'></view>
</view>
</view>
<view class='content-container {{hide ? "hidden" : ""}}' wx:if='{{!fold}}'>
<slot></slot>
</view>
</view>
wxss
.collapse {
background-color: white;
border-radius: 40rpx;
box-sizing: border-box;
overflow: hidden;
transition: all .75s;
}
.fold {
height: 80rpx !important;
}
.collapse .top-container {
width: 100%;
height: 80rpx;
display: flex;
justify-content: space-between;
align-items: center;
box-sizing: border-box;
padding: 0 40rpx;
}
.collapse .top-container .title {
color: #353535;
font-size: 32rpx;
}
.collapse .top-container .angle {
font-size: 40rpx;
}
.collapse .content-container {
border-top: 1px solid rgb(240, 240, 240);
}
.hidden {
visibility: hidden;
}
js
fold() {
if (this.data.fold) {
this.setData({
fold: false,
hide: true
})
let query = wx.createSelectorQuery().in(this) //in!
query.select(`.top-container`).boundingClientRect()
query.select(`.content-container`).boundingClientRect()
query.exec(res => {
let height = res[0].height + res[1].height
height += 'px'
this.setData({
height: height,
hide: false
})
})
} else {
let query = wx.createSelectorQuery().in(this)
query.select(`.top-container`).boundingClientRect()
query.select(`.content-container`).boundingClientRect()
query.exec(res => {
let height = res[0].height + res[1].height
height += 'px'
this.setData({
height: height,
})
setTimeout(() => {
this.setData({
fold: true
})
}, 50)
})
}
}
最终效果
Previous Post
微信小程序components无法使用createSelectorQuery
Next Post
Flutter redux 模块化管理
Or you can contact me by Email