首先,现在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