要在Objective-C中创建一个高度可复用的工具类,以防止按钮的暴力点击,并且使用切面编程(AOP)的方式,我们可以考虑使用Aspects这个库来实现方法的拦截。以下是具体的实现步骤:

第一步:引入Aspects库

首先,需要将Aspects集成到项目中。Aspects是一个轻量级的AOP框架,允许你在运行时拦截类的实例方法和类方法。你可以通过CocoaPods来添加此库:

pod 'Aspects'

第二步:创建UIButton的Category

接下来,创建一个UIButton的Category,用于添加防暴力点击的逻辑。

UIButton+PreventSpam.h:

#import <UIKit/UIKit.h>

@interface UIButton (PreventSpam)

// 设置间隔时间,进行防暴力点击设置
- (void)setPreventSpamInterval:(NSTimeInterval)interval; @end

UIButton+PreventSpam.m:

#import "UIButton+PreventSpam.h"
#import <objc/runtime.h>
#import <Aspects/Aspects.h> static const char *UIButton_preventSpamIntervalKey = "UIButton_preventSpamIntervalKey"; @implementation UIButton (PreventSpam) - (void)setPreventSpamInterval:(NSTimeInterval)interval {
objc_setAssociatedObject(self, UIButton_preventSpamIntervalKey, @(interval), OBJC_ASSOCIATION_RETAIN_NONATOMIC);
// 使用Aspects进行方法拦截
[self aspect_hookSelector:@selector(sendAction:to:forEvent:) withOptions:AspectPositionInstead usingBlock:^(id<AspectInfo> aspectInfo, SEL action, id target, UIEvent *event) {
UIButton *button = aspectInfo.instance;
if (button.isIgnoring) {
return;
}
button.isIgnoring = YES; // 执行原始的 sendAction:to:forEvent: 方法
// 这里直接调用原始方法是不合适的,因为这是一个拦截后的block,我们要重新invoke original invocation
[[aspectInfo originalInvocation] invoke]; // 延迟间隔时间后,重置为可以点击
dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(interval * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
button.isIgnoring = NO;
});
} error:NULL];
} // 判断当前是否应该忽略点击,通过关联对象添加属性
- (void)setIsIgnoring:(BOOL)isIgnoring {
objc_setAssociatedObject(self, @selector(isIgnoring), @(isIgnoring), OBJC_ASSOCIATION_ASSIGN);
} - (BOOL)isIgnoring {
return [objc_getAssociatedObject(self, @selector(isIgnoring)) boolValue];
} @end

使用

在适当的位置设置按钮的点击间隔:

#import "UIButton+PreventSpam.h"

[myButton setPreventSpamInterval:1.0]; // 点击间隔设置为1秒

注意

  1. 本示例使用了Aspects库进行方法的拦截,这是一种运行时AOP的技巧。这里利用了Objective-C的动态特性。AOP可以帮助增加代码的可维护性和可复用性,但它也会增加代码的复杂性,使用时需要权衡。

  2. 使用关联对象(objc_setAssociatedObjectobjc_getAssociatedObject)来给UIButton动态添加属性,用于存储是否应该忽略点击和间隔时间,这是Objective-C扩展现有类功能的常用技巧。

  3. 在实际项目中,可能需要考虑多种情况和细节,如处理快速切换界面时按钮点击事件的响应等。

iOS开发基础136-防暴力点击的更多相关文章

  1. IOS开发基础知识碎片-导航

    1:IOS开发基础知识--碎片1 a:NSString与NSInteger的互换 b:Objective-c中集合里面不能存放基础类型,比如int string float等,只能把它们转化成对象才可 ...

  2. IOS开发基础环境搭建

    一.目的 本文的目的是windows下IOS开发基础环境搭建做了对应的介绍,大家可根据文档步骤进行mac环境部署: 二.安装虚拟机 下载虚拟机安装文件绿色版,点击如下文件安装 获取安装包:       ...

  3. 【1】windows下IOS开发基础环境搭建

    一.目的 本文的目的是windows下IOS开发基础环境搭建做了对应的介绍,大家可根据文档步骤进行mac环境部署: 二.安装虚拟机 下载虚拟机安装文件绿色版,点击如下文件安装 获取安装包:       ...

  4. iOS开发——总结篇&IOS开发基础知识

    IOS开发基础知识 1:Objective-C语法之动态类型(isKindOfClass, isMemberOfClass,id) 对象在运行时获取其类型的能力称为内省.内省可以有多种方法实现. 判断 ...

  5. iOS开发基础-九宫格坐标(6)

    继续对iOS开发基础-九宫格坐标(5)中的代码进行优化. 优化思路:把字典转模型部分的数据处理操作也拿到模型类中去实现,即将 ViewController 类实现中 apps 方法搬到 WJQAppI ...

  6. iOS开发基础-九宫格坐标(5)

    继续在iOS开发基础-九宫格坐标(4)的基础上进行优化. 一.改进思路 1)iOS开发基础-九宫格坐标(4)中 viewDidLoad 方法中的第21.22行对控件属性的设置能否拿到视图类 WJQAp ...

  7. iOS开发基础-九宫格坐标(4)

    对iOS开发基础-九宫格坐标(3)的代码进行进一步优化. 新建一个 UIView 的子类,并命名为 WJQAppView ,将 appxib.xib 中的 UIView 对象与新建的视图类进行关联. ...

  8. iOS开发基础-九宫格坐标(3)之Xib

    延续iOS开发基础-九宫格坐标(2)的内容,对其进行部分修改. 本部分采用 Xib 文件来创建用于显示图片的 UIView 对象. 一.简单介绍  Xib 和 storyboard 的比较: 1) X ...

  9. iOS开发基础-九宫格坐标(2)之模型

    在iOS开发基础-九宫格(1)中,属性变量 apps 是从plist文件中加载数据的,在 viewDidLoad 方法中的第20行.26行中,直接通过字典的键名来获取相应的信息,使得 ViewCont ...

  10. iOS开发基础-图片切换(4)之懒加载

    延续:iOS开发基础-图片切换(3),对(3)里面的代码用懒加载进行改善. 一.懒加载基本内容 懒加载(延迟加载):即在需要的时候才加载,修改属性的 getter 方法. 注意:懒加载时一定要先判断该 ...

随机推荐

  1. Leetcode-916. Word Subsets-(Medium)

    一.问题描述 We are given two arrays A and B of words.  Each word is a string of lowercase letters. Now, s ...

  2. 小程序转发 搜索wxml

    新闻转发 在小程序中要不通过菜单项来完成分享功能,只能通过表单组件中的按钮来完成. 它是通过按钮中的开放能力完成 按钮自定义处理 新闻搜索 搜索wxml 搜索业务的js

  3. linux系统下,搭建kafka环境(单机版)

    安装前准备: 安装JDK 安装zookeeper(如果使用kafka内置的zookeeper,可以忽略) 第一步.安装JDK kafka依赖JAVA环境,所以首先要安装jdk 第二步.安装zookee ...

  4. 容器docker技术

    我们先看看很久很久以前,服务器是怎么部署应用的! 由于物理机的诸多问题,后来出现了虚拟机. 但是虚拟化也是有局限性的,每一个虚拟机都是一个完整的操作系统,要分配系统资源,虚拟机多道一定程度时,操作系统 ...

  5. Selenium模块的使用(一)

    简介 selenium最初是一个自动化测试工具,而爬虫中使用它主要是为了解决requests无法直接执行JavaScript代码的问题 selenium本质是通过驱动浏览器, 完全模拟浏览器的操作,比 ...

  6. 《Android开发卷——程序自动登录》

    Android程序的自动登录功能 因为是公司的项目,所以这里不方便说出项目名称,这里就说我在做这个项目中用到的一些功能或者叫技术问题吧. 咱们经常用的Android程序中有一个情况,就是当你第一次注册 ...

  7. Postman 的 Basic Auth 如何通过 Feign 实现

    Postman 的 Basic Auth: 分析 根据以上图片分析: Postman 的 Authorization 实际为: header 中添加 Authorization: ******* ** ...

  8. springboot支持http2

    现在http/3都出来了,但是很多项目还是没有采用https,这个是说不过去的. http3在2022/06/06 正式发布,具体见https://www.163.com/dy/article/H9B ...

  9. 攻防世界——CRYPTO新手练习区解题总结<3>(9-12题)

    第九题easychallenge: 下载附件,得到一个后缀为pyc的文件,上网百度一下pyc文件,得知 pyc是一种二进制文件,是由py文件经过编译后,生成的文件,是一种byte code,py文件变 ...

  10. 2.SpringBoot快速上手

    2.SpringBoot快速上手 SpringBoot介绍 javaEE的开发经常会涉及到3个框架Spring ,SpringMVC,MyBatis.但是这三个框架配置极其繁琐,有大量的xml文件,s ...