Feat: 添加半模态转场

This commit is contained in:
cheliangzhao 2023-10-30 11:37:34 +08:00
parent 914c1ca917
commit ae149eef94
2 changed files with 178 additions and 67 deletions

View File

@ -2,9 +2,10 @@
import { CustomPanel } from '../components/CustomPanel';
import curves from '@ohos.curves';
import { InnerView } from '../views/InnerView'
import { SideBar } from '../views/SideBar';
// 方案1panel
// 方案2模态转场
// 1custom panel
// 2模态转场
@Preview
@Entry
@Component
@ -15,12 +16,16 @@ struct Index {
@State showPanel: boolean = false;
// 模态转场控制变量
@State isPresent: boolean = false;
@State contentWidth: number | string = this.defaultWidth;
@State marginLeft: number = 0;
@State sheetIsPresent: boolean = false;
// @State contentWidth: number | string = this.defaultWidth;
// @State marginLeft: number = 0;
@Builder
innerView() {
InnerView();
InnerView()
.height('100%')
.width('100%')
}
handleClose() {
@ -28,75 +33,99 @@ struct Index {
}
// sidebar控制变量
controlValue = {
beginX: 0,
endX: 0,
maxMoveRate: 0.12,
swipeDirection: 0, // 0 is left, 1 is right
leftMoveDistance: 0,
}
// controlValue = {
// beginX: 0,
// endX: 0,
// maxMoveRate: 0.12,
// swipeDirection: 0, // 0 is left, 1 is right
// leftMoveDistance: 0,
// }
// @Builder
// sideBar_origin() {
// Column() {
// InnerView()
// }
// .margin({ left: -this.marginLeft })
// .width(this.contentWidth)
// .height('100%')
// .transition( // 通过转场动画实现出现消失转场动画效果transition需要加在builder下的第一个组件
// TransitionEffect.translate({ x: '-' + this.contentWidth, y: 0, z: 0 })
// .animation({ curve: curves.springMotion(0.6, 0.8) })
// )
// .onTouch(event => {
// // 按下赋初始值
// if (event.type === TouchType.Down) {
// this.controlValue.beginX = event.touches[0].displayX;
// this.controlValue.leftMoveDistance = 0;
// }
// // 移动改变移动宽度
// if (event.type === TouchType.Move) {
// this.controlValue.endX = event.touches[0].displayX; // 手指停止的位置
// const moveDistance = this.controlValue.beginX - this.controlValue.endX; // 滑动的水平距离
//
// // 判断水平滑动方向
// if (this.controlValue.leftMoveDistance > 0) {
// this.controlValue.swipeDirection = 0;
// } else {
// this.controlValue.swipeDirection = 1;
// }
//
// // 更新
// this.marginLeft = (this.marginLeft + moveDistance) > 0 ? (this.marginLeft + moveDistance) : 0;
//
// this.controlValue.beginX = this.controlValue.endX;
//
// this.controlValue.leftMoveDistance += moveDistance
// }
//
// if (event.type === TouchType.Up) {
// console.log(this.TAG, 'TouchType up' + this.controlValue.leftMoveDistance);
// if (this.controlValue.leftMoveDistance > this.controlValue.maxMoveRate * +this.defaultWidth) {
// this.isPresent = false;
// }
// this.marginLeft = 0;
// }
// })
// .gesture(
// SwipeGesture({ direction: SwipeDirection.Horizontal })
// .onAction((event?: GestureEvent) => {
// if (event && this.controlValue.swipeDirection == 0) {
// this.isPresent = false;
// this.marginLeft = 0;
// }
// })
// ) // 快速滑动关闭
// }
@Builder
SideBar() {
InnerView()
.margin({ left: -this.marginLeft })
.width(this.contentWidth)
.height('100%')
sideBarComponent() {
SideBar({
contentView: () => this.innerView(),
contentWidth: this.defaultWidth,
onClose: () => this.isPresent = false,
})
.transition(// 通过转场动画实现出现消失转场动画效果transition需要加在builder下的第一个组件
TransitionEffect.translate({ x: '-' + this.contentWidth, y: 0, z: 0 })
TransitionEffect.translate({ x: '-' + this.defaultWidth, y: 0, z: 0 })
.animation({ curve: curves.springMotion(0.6, 0.8) })
)
.onTouch(event => {
// 按下赋初始值
if (event.type === TouchType.Down) {
this.controlValue.beginX = event.touches[0].displayX;
this.controlValue.leftMoveDistance = 0;
}
// 移动改变移动宽度
if (event.type === TouchType.Move) {
this.controlValue.endX = event.touches[0].displayX; // 手指停止的位置
const moveDistance = this.controlValue.beginX - this.controlValue.endX; // 滑动的水平距离
// 判断水平滑动方向
if (this.controlValue.leftMoveDistance > 0) {
this.controlValue.swipeDirection = 0;
} else {
this.controlValue.swipeDirection = 1;
}
// 更新
this.marginLeft = (this.marginLeft + moveDistance) > 0 ? (this.marginLeft + moveDistance) : 0;
this.controlValue.beginX = this.controlValue.endX;
this.controlValue.leftMoveDistance += moveDistance
}
if (event.type === TouchType.Up) {
console.log(this.TAG, 'TouchType up' + this.controlValue.leftMoveDistance);
if (this.controlValue.leftMoveDistance > this.controlValue.maxMoveRate * +this.defaultWidth) {
this.isPresent = false;
}
this.marginLeft = 0;
}
})
.gesture(
SwipeGesture({ direction: SwipeDirection.Horizontal })
.onAction((event?: GestureEvent) => {
if (event && this.controlValue.swipeDirection == 0) {
this.isPresent = false;
this.marginLeft = 0;
}
})
) // 快速滑动关闭
}
build() {
Row() {
Button('open panel')
.onClick(() => this.showPanel = true);
Button('模态转场')// 通过选定的模态接口绑定模态展示界面ModalTransition是内置的ContentCover转场动画类型这里选择None代表系统不加默认动画
.bindContentCover(this.isPresent, this.SideBar, ModalTransition.NONE)
// mask
// if (this.isPresent) {
// Row()
// .width('100%')
// .height('100%')
// .position({ x: 0, y: 0 })
// .backgroundColor('#80111317')
// }
Button('open panel').onClick(() => this.showPanel = true);
Button('全屏模态转场')// 通过选定的模态接口绑定模态展示界面ModalTransition是内置的ContentCover转场动画类型这里选择None代表系统不加默认动画
.bindContentCover(this.isPresent, this.sideBarComponent, ModalTransition.NONE)
.onClick(() => {
if (this.isPresent) {
this.isPresent = false;
@ -104,9 +133,19 @@ struct Index {
} else {
this.isPresent = true;
}
this.contentWidth = this.defaultWidth;
})
Button('半模态转场')
.onClick(() => {
if (this.sheetIsPresent) {
this.sheetIsPresent = false;
this.sheetIsPresent = true;
} else {
this.sheetIsPresent = true;
}
})
.bindSheet(this.sheetIsPresent, this.innerView(), { height: 300, dragBar: true })
CustomPanel({
contentView: () => this.innerView(),
show: this.showPanel,
@ -117,6 +156,5 @@ struct Index {
.width('100%')
.height('100%')
.justifyContent(FlexAlign.SpaceEvenly)
}
}

View File

@ -0,0 +1,73 @@
@Component
export struct SideBar {
private TAG: string = 'Sidebar';
private defaultWidth: number = 350
@BuilderParam contentView: () => void
// 模态转场控制变量
onClose?: () => void
@Prop contentWidth: number | string = this.defaultWidth;
@State marginLeft: number = 0;
// sidebar控制变量
controlValue = {
beginX: 0,
endX: 0,
maxMoveRate: 0.12,
swipeDirection: 0, // 0 is left, 1 is right
leftMoveDistance: 0,
}
aboutToDisappear() {
this.onClose()
}
build() {
Column() {
this.contentView()
}
.margin({ left: -this.marginLeft })
.width(this.contentWidth)
.height('100%')
.onTouch(event => {
// 按下赋初始值
if (event.type === TouchType.Down) {
this.controlValue.beginX = event.touches[0].displayX;
this.controlValue.leftMoveDistance = 0;
}
// 移动改变宽度
if (event.type === TouchType.Move) {
this.controlValue.endX = event.touches[0].displayX; // 手指停止的位置
const moveDistance = this.controlValue.beginX - this.controlValue.endX; // 滑动的水平距离
// 判断水平滑动方向
if (this.controlValue.leftMoveDistance > 0) {
this.controlValue.swipeDirection = 0;
} else {
this.controlValue.swipeDirection = 1;
}
// 更新
this.marginLeft = (this.marginLeft + moveDistance) > 0 ? (this.marginLeft + moveDistance) : 0;
this.controlValue.beginX = this.controlValue.endX;
this.controlValue.leftMoveDistance += moveDistance
}
// 手指抬起判断是否关闭
if (event.type === TouchType.Up) {
console.log(this.TAG, 'TouchType up' + this.controlValue.leftMoveDistance);
if (this.controlValue.leftMoveDistance > this.controlValue.maxMoveRate * +this.defaultWidth) {
this.onClose()
}
this.marginLeft = 0;
}
})
.gesture(
SwipeGesture({ direction: SwipeDirection.Horizontal })
.onAction((event?: GestureEvent) => {
if (event && this.controlValue.swipeDirection == 0) {
this.onClose()
this.marginLeft = 0;
}
})
) // 快速滑动关闭
}
}