通过防止按钮快速重复点击简单了解AOP和注解

首先,现在build.gradle中添加配置:
替换为Aspectj的编译方法

buildscript {
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath 'org.aspectj:aspectjtools:1.8.8'
        classpath 'org.aspectj:aspectjweaver:1.8.8'
    }
}
import org.aspectj.bridge.IMessage
import org.aspectj.bridge.MessageHandler
import org.aspectj.tools.ajc.Main

final def log = project.logger
final def variants = project.android.applicationVariants

variants.all { variant ->
    if (!variant.buildType.isDebuggable()) {
        log.debug("Skipping non-debuggable build type '${variant.buildType.name}'.")
        return;
    }

    JavaCompile javaCompile = variant.javaCompile
    javaCompile.doLast {
        String[] args = ["-showWeaveInfo",
                         "-1.8",
                         "-inpath", javaCompile.destinationDir.toString(),
                         "-aspectpath", javaCompile.classpath.asPath,
                         "-d", javaCompile.destinationDir.toString(),
                         "-classpath", javaCompile.classpath.asPath,
                         "-bootclasspath", project.android.bootClasspath.join(File.pathSeparator)]
        log.debug "ajc args: " + Arrays.toString(args)

        MessageHandler handler = new MessageHandler(true);
        new Main().run(args, handler);
        for (IMessage message : handler.getMessages(null, true)) {
            switch (message.getKind()) {
                case IMessage.ABORT:
                case IMessage.ERROR:
                case IMessage.FAIL:
                    log.error message.message, message.thrown
                    break;
                case IMessage.WARNING:
                    log.warn message.message, message.thrown
                    break;
                case IMessage.INFO:
                    log.info message.message, message.thrown
                    break;
                case IMessage.DEBUG:
                    log.debug message.message, message.thrown
                    break;
            }
        }
    }
}

然后定义AOP处理的类:

@Aspect
public class ClickListenerAspect {

    @Around("execution(* android.view.View.OnClickListener.onClick(..))")
    public void onClickLitener(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        if (!ClickUtils.isFastClick()){
            proceedingJoinPoint.proceed();
        }
    }

判断是否是快速点击的工具类:

public class ClickUtils {
    private static long lastClickTime = 0;
    private final static int SPACE_TIME = 300;

    public synchronized static boolean isFastClick() {
        long currentTime = System.currentTimeMillis();
        boolean isClick2;
        if (currentTime - lastClickTime >
                SPACE_TIME) {
            isClick2 = false;
        } else {
            isClick2 = true;
        }
        lastClickTime = currentTime;
        return isClick2;
    }
}

以上实现了全局监听点击,和防止重复点击,当然可能有的按钮允许重复点击,这就可以定义一个注解类:

@Target(ElementType.METHOD)
@Retention(RetentionPolicy.CLASS)
public @interface CanFastClick {
}

onclick一般在方法中所以直接设置target 为Method,然后修改Aspect类为:

@Aspect
public class ClickListenerAspect {
    private  boolean canFastClick;

    //Pointcut 表示执行切入点
    //execution(注释名   注释用的地方)
    //com.zqb.baselibrary.util.aspectj注解类所在包名,CanFastClick注解类名,* *(..) 方法名和可执行参数名
    @Pointcut("execution(@ com.zqb.baselibrary.util.aspectj.CanFastClick * *(..))")
    public void canFastClick(){ }

    //@Before()  在切入点之前运行
    //@After()   在切入点之后运行
    //@Around()  在切入点前后都运行
    @Before("canFastClick()")
    public void beforeClick(ProceedingJoinPoint joinPoint) throws Throwable {
        canFastClick=true;
    }

    @Around("execution(* android.view.View.OnClickListener.onClick(..))")
    public void onClickLitener(ProceedingJoinPoint proceedingJoinPoint) throws Throwable {
        //可以通过proceedingJoinPoint获取到方法名注解参数,反射获取方法参数等
        if (!ClickUtils.isFastClick()
            || !canFastClick) {
            //可在此处理执行之前想要做的操作
            proceedingJoinPoint.proceed();//执行方法
            //可在此处理执行之后想要做的操作
            canFastClick=false;
        }
    }
}

附:如果在library中使用aspectj,需要把applicationVariants替换成libraryVariants

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值