鸿蒙Next-方法装饰器以及防抖方法注解实现

以下是关于 鸿蒙Next(HarmonyOS NEXT)中 MethodDecorator 的详细介绍及使用指南,结合了多个技术来源的实践总结:

以下是关于 鸿蒙Next(HarmonyOS NEXT)中 MethodDecorator 的详细介绍及使用指南,结合了多个技术来源的实践总结:


一、MethodDecorator 的概念与作用

MethodDecorator 是鸿蒙Next框架中用于装饰类方法的装饰器,属于 ArkUI 装饰器体系 的一部分。它允许开发者为类方法动态添加元数据或功能扩展,例如实现方法拦截、状态监听、日志记录等场景。通过装饰器,开发者能以声明式的方式增强代码的可维护性和复用性。

核心特点:

  1. 非侵入式增强:在不修改原方法逻辑的前提下,通过装饰器注入额外逻辑。
  2. 元数据绑定:可为方法添加配置信息(如参数校验规则、权限控制标记)。
  3. 与状态管理联动:常与 @State@Prop 等状态装饰器结合,实现数据变化响应。

二、MethodDecorator 的语法与使用示例

1. 基本语法

function MyMethodDecorator(target: any, propertyKey: string, descriptor: PropertyDescriptor{
  // 装饰器逻辑:修改或增强原方法
  const originalMethod = descriptor.value;
  descriptor.value = function (...args: any[]{
    console.log(`方法 ${propertyKey} 被调用`);
    return originalMethod.apply(this, args);
  };
  return descriptor;
}

class MyClass {
  @MyMethodDecorator
  myMethod() {
    // 原方法逻辑
  }
}

2. 常见使用场景

(1) 方法调用日志记录

function LogMethod({
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = function (...args: any[]{
      console.log(`调用方法:${methodName},参数:${JSON.stringify(args)}`);
      return original.apply(this, args);
    };
  };
}

@Component
struct MyComponent {
  @LogMethod()
  handleClick() {
    // 处理点击事件
  }
}

(2) 状态监听与联动通过 @Watch 装饰器(内置的 MethodDecorator)监听状态变量变化并触发方法:

@Component
struct MyComponent {
  @State count: number = 0;

  @Watch('count'// 监听 count 变化
  onCountChanged(newValue: number, oldValue: number) {
    console.log(`count 从 ${oldValue} 变为 ${newValue}`);
  }

  build() {
    Button('增加').onClick(() => this.count++);
  }
}

此例中,@Watch 装饰器会在 count 变化时自动调用 onCountChanged 方法。

(3) 点击事件防抖

//period间隔时间
@Debounce(2000)
clickMethod(){
}
function Debounce(period: number = 750): MethodDecorator {
  return function (
      target: object,
      propertyKey: string,
      descriptor: PropertyDescriptor
  
): PropertyDescriptor 
{
    const originalMethod = descriptor.value
    let timeId: number = 0
    descriptor.value = function (...args: object[]): void {
      if (timeId !== 0) {
        clearTimeout(timeId)
      }
      timeId = setTimeout(() => {
        originalMethod.apply(this, args)
        timeId = 0
      },
        period
      )
    }
    return descriptor
  }
}

(4) 监听某个方法的耗时

function MonitorCostTime(): MethodDecorator {
  return function (target: object,
    propertyKey: string,
    descriptor: PropertyDescriptor
{
    const originMethod = descriptor.value

    descriptor.value = function (...args: object[]{
      let startTime = systemDateTime.getTime()
      const result = originMethod.apply(this, args); // 调用原始方法
      const endTime = systemDateTime.getTime(); // 获取方法执行后的时间
      hilog.error(hilog.LogLevel.ERROR, "monitorCostTime"`方法消耗的时间为:${endTime - startTime}s`)
      return result;
    }
    return descriptor
  }
}

(5) 权限控制

function CheckPermission(permission: string{
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = function (...args: any[]{
      if (hasPermission(permission)) {
        return original.apply(this, args);
      } else {
        console.error('无权限执行此操作');
      }
    };
  };
}

class UserService {
  @CheckPermission('admin')
  deleteUser() {
    // 删除用户逻辑
  }
}

三、与 ArkUI 框架的深度集成

1. 生命周期方法装饰

鸿蒙Next的组件生命周期方法(如 aboutToAppearaboutToDisappear)本质上是内置的 MethodDecorator,开发者可通过自定义装饰器扩展生命周期行为:

function TrackLifecycle({
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = function (...args: any[]{
      console.log(`组件生命周期方法 ${methodName} 被触发`);
      return original.apply(this, args);
    };
  };
}

@Component
struct MyComponent {
  @TrackLifecycle()
  aboutToAppear() {
    // 组件初始化逻辑
  }
}

2. 动画与交互增强

结合 animateTo 方法,可通过装饰器封装动画逻辑:

function FadeAnimation(duration: number{
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = function (...args: any[]{
      animateTo({
        duration: duration,
        onFinish: () => original.apply(this, args)
      }, () => {
        this.opacity = 0;
      });
    };
  };
}

@Component
struct AnimatedButton {
  @State opacity: number = 1;

  @FadeAnimation(300)
  handleClick() {
    // 点击后的业务逻辑
  }

  build() {
    Button('点击').opacity(this.opacity).onClick(() => this.handleClick());
  }
}

四、注意事项与最佳实践

  1. 装饰器执行顺序
    多个装饰器按 从下到上 的顺序执行(装饰器工厂函数从外到内)。
  2. 避免副作用
    装饰器应保持无状态,避免修改全局变量或依赖外部环境。
  3. 性能优化
    高频调用的方法慎用复杂装饰器逻辑,必要时通过缓存优化。
  4. 兼容性
    确保装饰器与鸿蒙Next的 API 版本兼容,避免使用实验性特性。

五、扩展应用:自定义高级装饰器

1. 异步方法拦截

function Retry(maxAttempts: number{
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = async function (...args: any[]{
      let attempts = 0;
      while (attempts < maxAttempts) {
        try {
          return await original.apply(this, args);
        } catch (error) {
          attempts++;
          console.log(`重试第 ${attempts} 次`);
        }
      }
      throw new Error('操作失败');
    };
  };
}

class ApiService {
  @Retry(3)
  async fetchData() {
    // 网络请求逻辑
  }
}

2. 参数校验

function ValidateParams(...validators: Function[]{
  return function (target: any, methodName: string, descriptor: PropertyDescriptor{
    const original = descriptor.value;
    descriptor.value = function (...args: any[]{
      validators.forEach((validator, index) => {
        if (!validator(args[index])) {
          throw new Error(`参数 ${index} 校验失败`);
        }
      });
      return original.apply(this, args);
    };
  };
}

class Calculator {
  @ValidateParams(
    (x: number) => !isNaN(x),
    (y: number) => y !== 0
  )
  divide(x: number, y: number) {
    return x / y;
  }
}

总结

MethodDecorator 是鸿蒙Next开发中实现 代码复用 和 逻辑解耦 的重要工具。通过合理使用内置装饰器(如 @Watch)和自定义装饰器,开发者可以显著提升代码的可维护性,同时实现复杂的业务逻辑与交互效果。实际开发中需结合具体场景选择装饰器策略,并注意性能与兼容性问题。


来源:公众号
作者:Android技术之家
原文地址:鸿蒙Next-方法装饰器以及防抖方法注解实现

来源: 互联网
本文观点不代表码客-全球程序员交流社区立场,不承担法律责任,文章及观点也不构成任何投资意见。

赞 ()

相关推荐

  • 置顶 开发项目接单群,免费入群了

    无论你是Android、ios、java、php,或者你是产品经理、老板,都可以免费入群接单或者发布项目,全程不收取任何费用。

    2025年02月21日 15点27分
  • 鸿蒙Next-方法装饰器以及防抖方法注解实现

    以下是关于 鸿蒙Next(HarmonyOS NEXT)中 MethodDecorator 的详细介绍及使用指南,结合了多个技术来源的实践总结:

    2025年02月26日 22点58分
  • DevEco Studio常用快捷键以及如何跟AndroidStudio的保持同步

    DevEco Studio是华为推出的用于开发HarmonyOS应用的集成开发环境,它提供了丰富的快捷键以提高开发效率,以下为你详细介绍不同操作场景下的常用快捷键:

    2025年02月26日 22点56分
  • Android | 利用ItemDecoration绘制RecyclerView分割线

    RecyclerView.ItemDecoration 是 Android 提供的一种扩展机制,用于为 RecyclerView 的每个子项(Item)添加装饰(Decoration)。它通常用于绘制分割线、边距、背景等,目的是增强 RecyclerView 的显示效果。

    2025年02月26日 22点52分
  • Android 布局优化:利用 ViewStub 和 Merge 提升性能

    提升界面渲染性能是一个至关重要的任务,尤其是在应用启动时,渲染界面需要快速且流畅。为了优化 UI 渲染速度,Android 提供了许多工具,其中 ViewStub 和 Merge 标签是非常有效的布局优化手段。通过合理使用这两者,可以延迟加载不必要的视图、减少布局的嵌套层级,从而加速应用的启动和运行。

    2025年02月26日 22点47分
  • 玩转 ImageView.ScaleType:图片的缩放与裁剪技巧

    ImageView 是最常用的控件之一,它用于展示各种类型的图片。为了能够根据需求调整图片的显示效果,Android 提供了 ImageView.ScaleType 枚举,它可以灵活地控制图片如何适应 ImageView 的尺寸。本文将探讨 ImageView.ScaleType 的不同选项、使用场景及其实现技巧。

    2025年02月26日 22点45分
  • Android加快你的编译速度

    工欲善其事,必先利其器。如果每次运行项目都要花费5-10分钟,那人的心态都要崩了。

    2025年02月25日 15点40分
  • Flutter多渠道打包的解决方案(walle)

    我们的应用集成了TalkingData这个第三方工具来统计日活、事件等,需要在应用启动时初始化SDK,这个时候需要传入当前渠道,以便数据的统计。 由于最开始是用脚本一个个打包,一直想解决打包过慢的问题,但是网上大多教程是基于命令行参数或flavor,实质上并没有根本解决打包效率的问题。直到发现了文章的主角 walle。

    2025年02月25日 15点36分
  • Android-分享一个对RecyclerView二次封装的库(EasyRecyclerView)

    在日常的Android开发当中,我们肯定会有使用到RecyclerView的需求,这里分享一个对RecyclerView二次封装的开源库——EasyRecyclerView。它基本上满足基本的开发需求,希望能帮看文章的小伙伴提高开发效率。

    2025年02月25日 15点31分
  • Android原生系统真的那么好用吗?安卓原生系统吊打其他系统,因为有Google-Play,所以应用都是纯净的?

    实际方面,原生 Android 的最大优势是更新快速,对供应商特别是 Android 上游的补丁的合并速度非常快,几乎总能在第一时间更新。因为系统越原生,更新的代价就越小。反之,如果一个停止更新的原生 Android 其实是没有多大意义的,它失去了它最大的优势。

    2025年02月25日 15点30分
  • Application 作为 Dialog 的 Context?小心踩坑!

    大家好,相信大家在使用 Dialog 时,都有一个非常基本的认知:就是 Dialog 的 context 只能是 Activity,而不能是 Application,不然会导致弹窗崩溃:

    2025年02月25日 15点25分
  • Android 应用的线程世界:最少需要几个线程才能启动?

    这篇文章主要介绍了 Android App 中的多种线程,包括守护线程(如 Signal Catcher 等)、渲染线程、主线程、三方线程(如 OkHttp、Glide、ARouter 相关线程)等,还提及三方库中线程池的情况及可能存在的问题。

    2025年02月25日 15点13分
  • Android 复杂项目崩溃率收敛至0.01%实践

    在我们的项目中,每个版本发布之后,我们会创建一个opt分支,用于修复线上崩溃以及业务逻辑BUG。

    2025年02月25日 15点11分
  • Android 能悄悄知道用户截屏?这里有你想要的答案

    很多应用在当你截屏的时候能够感知到,并提示你是否要发送截屏等等。

    2025年02月25日 15点07分
  • 科大讯飞讯飞星火API能力免费开放,引领大模型商业化新篇章

    合肥本土科技巨头科大讯飞传来振奋人心的消息:讯飞星火API能力正式向公众免费开放,其中,讯飞星火Lite API更是实现了永久免费。这一举措无疑为整个行业注入了新的活力,也彰显了科大讯飞在大模型商业化进程中的坚定决心。

    2025年02月21日 15点57分
  • 一木林接入AI大模型,实现智能体功能

    一木林——全能型AI电子工具箱。这是一款集多功能于一体的工具类应用,凭借小巧的体积与全面且强大的功能,赢得了极高的口碑。应用内汇聚了上百款实用工具,诸如指南针、计算器、分贝仪等,一应俱全。如今,一木林已携手星火AI大模型,实现了AI对话与智能体的创新功能。

    2025年02月21日 15点42分

发表回复

评论列表

点击查看更多

    联系我们

    在线咨询: QQ交谈

    微信:dxmcpjl

    邮件:1529097251#qq.com

    工作时间:周一至周五,9:30-18:30,节假日休息

    微信