需求描述

1. 发布信息时,通过键盘键入@符号,或者点选相关功能键,唤醒@列表,进行选择

2.选择结束后,输入栏改色显示相关内容

3.删除时,整体删除@区块,且不能让光标落在@区块之间

实现步骤

1. 键入@符号,触发相关功能

 - (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text{
//判断键入的字符
if ([text isEqualToString:@"@"]) {
//触发相关功能
//[self pickRemaidBtnClick];
return NO;
} return YES;
}

2. @区块颜色修改

(1)使用到的正则表达式

#define kATRegular @"@[\\u4e00-\\u9fa5\\w\\-\\_]+ "

(2)获取匹配到的区块下标数组

+ (NSArray *) getMatchsWithStr : (NSString *) text {
// 找到文本中所有的@
NSRegularExpression *regex = [NSRegularExpression regularExpressionWithPattern:kATRegular options:NSRegularExpressionCaseInsensitive error:nil];
NSArray *matches = [regex matchesInString:text options:NSMatchingReportProgress range:NSMakeRange(, [text length])];
return matches;
}

(3)修改文本颜色

-(void)textViewDidChange:(UITextView *)textView {
NSArray *matchs = [RemaidUserUtils getMatchsWithStr:textView.text];
//改色
[textView.textStorage addAttribute:NSForegroundColorAttributeName value:[UIColor colorWithHexString:@"#333333"] range:NSMakeRange(, textView.text.length)];
for (NSTextCheckingResult *match in matchs)
{
[textView.textStorage addAttribute:NSForegroundColorAttributeName value:BLUECOLOR range:NSMakeRange(match.range.location, match.range.length - )];
}
}

3.删除时整体删除@区块

- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text{

    if ([text isEqualToString:@""])
{
NSRange selectRange = textView.selectedRange;
if (selectRange.length > )
{
//用户长按选择文本时不处理
return YES;
} // 判断删除的是一个@中间的字符就整体删除
NSMutableString *string = [NSMutableString stringWithString:textView.text];
NSArray *matches = [RemaidUserUtils getMatchsWithStr:string]; BOOL inAt = NO;
NSInteger index = range.location;
for (NSTextCheckingResult *match in matches)
{
NSRange newRange = NSMakeRange(match.range.location + , match.range.length - );
if (NSLocationInRange(range.location, newRange))
{
inAt = YES;
index = match.range.location;
[textView.textStorage replaceCharactersInRange:match.range withString:@""];
textView.selectedRange = NSMakeRange(index, );
[self textViewDidChange:textView];
return NO;
break;
}
}
} return YES;
}

4.不允许光标落在@区块之间

- (void)textViewDidChangeSelection:(UITextView *)textView {
// 光标不能点落在@词中间
NSRange range = textView.selectedRange;
if (range.length > )
{
// 选择文本时可以
return;
} NSArray *matches = [RemaidUserUtils getMatchsWithStr:textView.text]; for (NSTextCheckingResult *match in matches)
{
NSRange newRange = NSMakeRange(match.range.location + , match.range.length - );
if (NSLocationInRange(range.location, newRange))
{
if (range.location == match.range.location + ) {
textView.selectedRange = NSMakeRange(match.range.location + match.range.length, );
} else {
textView.selectedRange = NSMakeRange(match.range.location , );
}
break;
}
}
}

BY: chu

iOS @功能的部分实现思路的更多相关文章

  1. Unity iOS混合开发界面切换思路

    Unity iOS混合开发界面切换思路 最近有很多博友QQ 私信 或则 留言联系我,请教iOS和Unity界面之前相互切换的问题,源代码就不私下发你们了,界面跳转功能的代码我直接贴到下面好了,顺带说i ...

  2. 多文件上传 iOS功能

    多文件上传 iOS功能,原文来自ios教程网整理的,大家可以看看演示:ios.662p.com ,喜欢的朋友可以看看我的博客吧. NSURL* url = [NSURL URLWithString:@ ...

  3. 李洪强iOS开发-网络新闻获取数据思路回顾

    李洪强iOS开发-网络新闻获取数据思路回顾 01 创建一个继承自AFHTTPSessionManager的工具类:LHQNetworkTool 用来发送网络请求获取数据  1.1 定义类方法返回单例对 ...

  4. iOS 组件化 —— 路由设计思路分析

    原文 前言 随着用户的需求越来越多,对App的用户体验也变的要求越来越高.为了更好的应对各种需求,开发人员从软件工程的角度,将App架构由原来简单的MVC变成MVVM,VIPER等复杂架构.更换适合业 ...

  5. 怎么样才是设计功能函数的好思路(javascript)?

    在js里面,对于函数的调用,实际上也是也是面向对象的思路,于是写好js函数,也是考核面向对象设计的能力,同时也必须考虑到如何实现高内聚和低耦合,拿一个例子来说,现在的需求是这样的,实现个投资进度框,就 ...

  6. iOS逆向系列-逆向APP思路

    界面分析 通过Cycript.Reveal. 对于Reveal安装配置可参考配置iOS逆向系列-Reveal 通过Reveal找到内存中的UI对象 静态分析 开发者编写的所有代码最终编译链接到Mach ...

  7. 【iOS功能实现】之利用UIDocumentInteractionController打开和预览文档

    iOS提供了使用其他app预览文件的支持,这就是Document Interaction Controller.此外,iOS也支持文件关联,允许其他程序调用你的app打开某种文件.而且,从4.2开始, ...

  8. 关于 iOS 刷新效果实现的思路 和 mac软件网址推荐

    有一次面试,突然有个人问了我一个问题:MJRefresh的原理是什么? 我说这种效果可以有两种方法实现: 1.  UIRefreshControl 2.  通过监听scrollview的偏移量,自定义 ...

  9. 实现ios常见菜单效果的思路

    眼下见过的实现边側菜单的效果.比較流行的有下面三种:(效果图) 1.菜单条覆盖在部分主视图上 附上实现该效果的一个不错的源代码地址: http://code4app.com/ios/RNFrosted ...

随机推荐

  1. STLNormalFunc

    #include <iostream> #include <vector> using namespace std; void main_1() { vector<int ...

  2. Python的可变类型和不可变类型?

    Python的每个对象都分为可变和不可变可变:列表.字典   不可变:数字.字符串.元组

  3. LeetCode 787. Cheapest Flights Within K Stops

    原题链接在这里:https://leetcode.com/problems/cheapest-flights-within-k-stops/ 题目: There are n cities connec ...

  4. solidworks 学习 (三)

    汽车轮毂三维建模

  5. LOJ P10016 灯泡 题解

    每日一题 day50 打卡 Analysis 用初中学的相似推一波式子,再用三分一搞就好了. #include<iostream> #include<cstdio> #incl ...

  6. WinDbg 图形界面功能(三)

    1.4.调试菜单 调试相关操作的功能菜单在这个下面,比如单步执行等. Go 单击Go调试菜单恢复 (或开始) 在目标上的执行. 此执行将继续,直到抵达某个断点. 异常或事件发生时,该过程结束或调试器将 ...

  7. [codewars] - int32 to IPv4 二进制十进制 ip地址转换

    原题 https://www.codewars.com/kata/int32-to-ipv4/train/java Take the following IPv4 address: 128.32.10 ...

  8. luoguP1576 最小花费

    LOL新英雄皮肤弹丸天使点击就送 两种做法: 1.边的权值为手续费z,从b向a跑最短路,边跑边处理答案 2.边的权值为汇率,从a向b跑最短路,边跑边处理答案 #include<cstdio> ...

  9. powershell.exe WannaCrypt(永恒之蓝) down.bddp.net

    今天win机器进程出现大量 powershell.exe,把cpu占满100%,打开任务管理器看到如下信息: powershell -nop -w hidden -ep bypass -c " ...

  10. mysql sqrt() 函数

    mysql> ); +----------+ | sqrt() | +----------+ | | +----------+ row in set (0.00 sec)