HarmonyOS 如何实现跑道进度条?

如题:HarmonyOS 如何实现跑道进度条?

阅读 585
1 个回答

可以通过手动绘制canvas的方式去实现跑道效果,参考代码如下:

@Entry
@Component
export struct Index {
  private settings: RenderingContextSettings = new RenderingContextSettings(true)
  private context: CanvasRenderingContext2D = new CanvasRenderingContext2D(this.settings)
  private offCanvas: OffscreenCanvas = new OffscreenCanvas(600, 600)
  @State @Watch('onCountUpdated') radianTest: number = 0
  @State color: string = '#ff8c909b'

  onCountUpdated(): void {
    this.canvasTest()
  }

  canvasTest = (): void => {
    let offContext = this.offCanvas.getContext('2d', this.settings)
    offContext.lineCap = 'round'
    offContext.lineWidth = 8
    // 左半圆
    offContext.beginPath()
    offContext.arc(
      100,
      75,
      50,
      (180 - 90) * Math.PI / 180,
      (360 - 90) * Math.PI / 180
    )
    offContext.strokeStyle = '#ff8c909b'
    offContext.stroke()

    // 上方直线
    offContext.beginPath()
    offContext.moveTo(((180 - 90) * Math.PI / 180) + 100, 25)
    offContext.lineTo((180 - 90) * Math.PI / 180 + 180, 25)
    offContext.strokeStyle = '#ff8c909b'
    offContext.stroke()

    // 右半圆
    offContext.beginPath()
    offContext.arc(
      180,
      75,
      50,
      (360 - 90) * Math.PI / 180,
      (180 - 90) * Math.PI / 180
    )
    offContext.strokeStyle = '#ff8c909b'
    offContext.stroke()

    // 下方直线
    offContext.beginPath()
    offContext.moveTo(((180 - 90) * Math.PI / 180) + 100, 125)
    offContext.lineTo((180 - 90) * Math.PI / 180 + 180, 125)
    offContext.strokeStyle = '#ff8c909b'
    offContext.stroke()


    // 改变颜色 就是将上面画图部分重新以不同颜色重画一遍
    // 左半圆重画填充颜色
    offContext.beginPath()
    offContext.arc(
      100,
      75,
      50,
      (180 - 90) * Math.PI / 180,
      // (360 - 90) * Math.PI / 180
      this.radianTest === 0 ? (180 - 90) * (Math.PI / 180) : ( this.radianTest <=0.66 ? - 270 * (1 - this.radianTest) * (Math.PI / 180): - 270 * (1 - 0.66) * (Math.PI / 180) ) ,
    )
    offContext.strokeStyle = this.color
    offContext.stroke()

    let image = this.offCanvas.transferToImageBitmap()
    this.context.transferFromImageBitmap(image)
    // 自行完成剩下部分 TODO

  }

  build() {
    NavDestination() {
      Column() {
        Canvas(this.context)
          .width('100%')
          .height('100%')
          .backgroundColor('#ffff00')
          .onReady(
            this.canvasTest
          )

        Button('test')
          .onClick(() => {
            this.color = '#ff144cd2'
            this.radianTest = Number(this.radianTest + 0.01)
            if (this.radianTest > 1) {
              this.radianTest = 0
            }
          })
      }
      .width('100%')
      .height(500)
    }
  }
}
撰写回答
你尚未登录,登录后可以
  • 和开发者交流问题的细节
  • 关注并接收问题和回答的更新提醒
  • 参与内容的编辑和改进,让解决方法与时俱进