Read the original article:Ripple animation effect
Context
Animation can make the application interface transition naturally smooth and enhance the user's feedback and sense of interaction from the interface. How to achieve the water ripple effect of the component?
Description
Implementing property animation: Creating continuous visual effects on the UI by changing animatable properties is called property animation. Property animation is the most basic and easy-to-understand type of animation. ArkUI provides two property animation interfaces, animateTo and animation, to drive component properties to continuously change according to animation parameters such as animation curves, generating property animation.
Transition within a component : Transition within a component mainly configures transition parameters through the transition attribute, and displays transition effects when components are inserted and deleted. It is mainly used to improve the user experience when subcomponents in container components are inserted and deleted.
Solution / Approach
Solution 1: Implement ripple effects after clicking.
The onClick callback is used to obtain the finger click position and assign a value to the position of the circular component. Then, the transition within the component is used to achieve the effect of the circle appearing and gradually becoming transparent. The core code is as follows:
@Entry
@Component
struct WaterPage {
@State message: string = 'Hello World';
@State flag: boolean = false
@State ballX: number = 0
@State ballY: number = 0
build() {
Column() {
Column() {
}.layoutWeight(1).backgroundColor(Color.Pink).width("100%")
Stack() {
if (this.flag) {
Row()
.width(5)
.height(5)
.position({
x: this.ballX,
y: this.ballY
})
.backgroundColor("rgba(0,0,0,0.7)")
.transition(TransitionEffect.asymmetric(
TransitionEffect.IDENTITY,
TransitionEffect.OPACITY.animation({ duration: 1000, curve: Curve.EaseInOut }).combine(
TransitionEffect.scale({ x: 100, y: 100 })
)
))
.borderRadius(15)
}
}.width("100%").height('100%').clip(true)
.onClick((e) => {
this.ballX = e.x - 3
this.ballY = e.y - 3
this.flag = !this.flag;
setTimeout(() => {
this.flag = !this.flag;
}, 100)
})
}
.width('100%')
.height('100%')
}
}
The results are as follows:
Solution 2: The control generates dynamic effects autonomously
- Autonomous Implementation:
The core code is as follows:
@Entry
@Component
struct WaterPage2 {
private settings: RenderingContextSettings = new RenderingContextSettings(true)
private context: CanvasRenderingContext2D = new CanvasRenderingContext2D(this.settings)
waveSpeed: number = 0.03
phase: number = 0
drawWave() {
this.context?.clearRect(0, 0, this.context.width, this.context.height)
this.context?.beginPath()
for (let x = 0; x <= this.context.width; x += 10) {
const y = this.context.height / 2 + Math.sin(x * 0.01 + this.phase) * 20
this.context?.lineTo(x, y)
}
this.context?.lineTo(this.context.width, this.context.height)
this.context?.lineTo(0, this.context.height)
this.context?.closePath()
this.context.fillStyle = '#30007bff'
this.context?.fill()
this.context?.beginPath()
for (let x = 0; x <= this.context.width; x += 10) {
const y = this.context.height / 2 + Math.sin(x * 0.02 + this.phase) * 10
this.context?.lineTo(x, y)
}
this.context?.lineTo(this.context.width, this.context.height)
this.context?.lineTo(0, this.context.height)
this.context?.closePath()
this.context.fillStyle = '#50007bff'
this.context?.fill()
this.context?.beginPath()
for (let x = 0; x <= this.context.width; x += 10) {
const y = this.context.height / 2 + Math.sin(x * 0.015 + this.phase) * 30
this.context?.lineTo(x, y)
}
this.context?.lineTo(this.context.width, this.context.height)
this.context?.lineTo(0, this.context.height)
this.context?.closePath()
this.context.fillStyle = '#20007bff'
this.context?.fill()
this.phase += this.waveSpeed
}
build() {
Column() {
Canvas(this.context)
.width(200)
.height(100)
.backgroundColor(Color.Pink)
.onReady(() => {
setInterval(this.drawWave.bind(this), 20)
})
}.width("100%").height("100%").justifyContent(FlexAlign.Center)
}
}
- Third-party library implementation:
Please refer to the third-party library shimmer : shimmer is a simple and flexible library for adding flashing effects to application views, mainly including flashing effects such as tilting from left to right, vertically from left to right, circularly from left to right, and horizontally from top to bottom.
Key Takeaways
- Use property animation (animateTo or animation modifier) to drive scale/opacity changes.
- Combine scaling and fading to mimic a ripple’s expansion and dissipation.
- Optimize performance by limiting simultaneous animations or using lightweight components.


Top comments (0)