DEV Community

HarmonyOS
HarmonyOS

Posted on

How can we add animation effects to click events to enhance the user experience

Read the original article:How can we add animation effects to click events to enhance the user experience

Requirement Description

How can we add animation effects to click events to enhance the user experience?

Background Knowledge

  • onTouch is a common event for components. It is triggered when a finger touches the screen.
  • The event has a touchType parameter:
    • Down → triggered when the finger presses down.
    • Up → triggered when the finger is lifted.
  • The keyframeAnimateTo method in the UIContext component can be used to set keyframe animations, which allows implementing animations for icon clicks.

Implementation Steps

1.Create a Stack parent component

  • Define a Text component and a Progress component inside it to achieve the basic style.

     Stack() {
           Column() {
             Text('click').fontSize(this.fontSizeInfoPerformance).fontColor(Color.White)
           }
    
           Column() {
             Progress({ value: this.valueInfo, total: 100, type: ProgressType.Ring })
               .width(this.nLength)
               .height(this.nLength)
               .color(Color.Blue)
               .style({ strokeWidth: 5 })
           }.width(60).height(60).justifyContent(FlexAlign.Center)
         }
    

2.Add onTouch method to the Progress component

3.When event.type is Down, adjust styles such as font size, button size, and progress bar length.

4.Define keyframeAnimateTo keyframe animation.

5.When event.type is Up, perform a similar process.

   .onTouch((event: TouchEvent) => {
         if (TouchType.Up === event.type) {
           this.nLength = 60
           this.fontSizeInfoClick = 10
           this.fontSizeInfoPerformance = 15
           this.fontSizeInfoProgress = 15
           this.valueInfo = 0
           if (!this.uiContext) {
             return;
           }
           this.uiContext.keyframeAnimateTo({ iterations: 3 }, [{
             duration: 100, event: () => {
               this.valueInfo = 0
             }
           }, {
             duration: 100, event: () => {
               this.valueInfo = 100;
             }
           }]);
         }
       })
Enter fullscreen mode Exit fullscreen mode

Code Snippet


@Entry
@Component
struct Index {
  @State length: number = 60
  @State fIndex: number = 0
  @State isChange: boolean = false
  @State nLength: number = 60
  @State fontSizeInfoClick: number = 10
  @State fontSizeInfoPerformance: number = 15
  @State valueInfo: number = 0
  @State count: number = 1
  @State fontSizeInfoProgress: number = 18
  uiContext: UIContext | undefined = undefined;

  aboutToAppear(): void {
    this.uiContext = this.getUIContext?.();
  }

  onPageShow(): void {
    this.length = 60
    setTimeout(() => {
      this.length = 70
    }, 50)
  }

  build() {
    Column() {
      Row() {
        Text('X').fontColor(Color.Black).fontWeight(700).fontSize(13)
        Text(this.count.toString()).fontColor(Color.Black).fontWeight(700).fontSize(this.fontSizeInfoProgress)
      }

      Stack() {
        Column() {
          Text('click').fontSize(this.fontSizeInfoPerformance).fontColor(Color.White)
        }
        .opacity(0.8)
        .width(this.nLength)
        .height(this.nLength)
        .borderRadius(this.nLength / 2)
        .backgroundColor(Color.Orange)
        .justifyContent(FlexAlign.Center)

        Column() {
          Progress({ value: this.valueInfo, total: 100, type: ProgressType.Ring })
            .width(this.nLength)
            .height(this.nLength)
            .color(Color.Blue)
            .style({ strokeWidth: 5 })
            .onTouch((event: TouchEvent) => {
              if (TouchType.Up === event.type) {
                this.nLength = 60
                this.fontSizeInfoClick = 10
                this.fontSizeInfoPerformance = 15
                this.fontSizeInfoProgress = 15
                this.valueInfo = 0
                if (!this.uiContext) {
                  return;
                }
                this.uiContext.keyframeAnimateTo({ iterations: 3 }, [{
                  duration: 100, event: () => {
                    this.valueInfo = 0
                  }
                }, {
                  duration: 100, event: () => {
                    this.valueInfo = 100;
                  }
                }]);
              }
              if (TouchType.Down === event.type) {
                this.nLength = 50
                this.fontSizeInfoClick = 7
                this.fontSizeInfoPerformance = 10
                this.fontSizeInfoProgress = 18
                this.valueInfo = 0++
                this.count
                if (!this.uiContext) {
                  return;
                }
                this.uiContext.keyframeAnimateTo({ iterations: 3 }, [{
                  duration: 100, event: () => {
                    this.valueInfo = 0
                  }
                }, {
                  duration: 100, event: () => {
                    this.valueInfo = 100;
                  }
                }]);
              }
            })
        }.width(60).height(60).justifyContent(FlexAlign.Center)
      }
    }.justifyContent(FlexAlign.Center).alignItems(HorizontalAlign.Center).width('100%').height('100%')
  }
}
Enter fullscreen mode Exit fullscreen mode

1. Code Execution Result

image.png
Code Check Result

image.png

Test Results

  • Clicking the icon triggers smooth scaling and progress animations.
  • Both Down and Up states provide visual feedback as expected.

Limitations or Considerations

  • This sample supports API Version 19 Release and above.
  • Requires HarmonyOS 5.1.1 Release SDK or later.
  • Compilation and execution must be done in DevEco Studio 5.1.1 Release or later.

Written by Arif Emre Ankara

Top comments (0)