「=10=」SetSpan与Editxt
android setSpan to editText
很长一段时间我都对 setSpan
感到困惑,因为它看起来很简单但并不总是按预期工作
在我最后一次尝试中,我试图 setSpan
识别模式。
当用户开始输入“5 kilo toma”时,“5 kilo”将突出显示。
我使用下一个代码作为 TextWatcher
侦听器的一部分来执行此操作
@Override
public void afterTextChanged(Editable s) {
String quantity = mAutoCompleteAdapter.getQuantity();
if (!quantity.isEmpty()) {
int index = mAutoCompleteAdapter.getQuantityIndex();
final StyleSpan styleSpan = new StyleSpan( Typeface.BOLD_ITALIC );
s.setSpan( styleSpan, index, index + quantity.length(), Spanned.SPAN_MARK_MARK );
}
}
这工作正常(基本测试)
但是,如果我开始删除文本以读取“5 kil”,则当不再检测到模式时,setSpan
不会刷新为正常
所以我在想,也许 setSpan
保存在内存中或其他东西中,我每次都需要设置整个字符串跨度。所以我尝试了下一个代码:
@Override
public void afterTextChanged(Editable s) {
if (s.length() > 0) {
String quantity = mAutoCompleteAdapter.getQuantity();
int index = 0;
if (!quantity.isEmpty()) {
index = mAutoCompleteAdapter.getQuantityIndex();
StyleSpan styleSpan = new StyleSpan( Typeface.BOLD_ITALIC );
s.setSpan( styleSpan, index, index + quantity.length(), Spanned.SPAN_MARK_MARK );
}
StyleSpan styleSpanNormal = new StyleSpan( Typeface.NORMAL );
s.setSpan( styleSpanNormal, index + quantity.length(), s.length(), Spanned.SPAN_MARK_MARK );
}
}
但仍然无法正常工作
我认为你应该尝试 textChangedListener
因为它的方法 onTextChanged
将帮助你在用户输入新文本时检查文本,删除文本视图中的一些文本
textview.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after{
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
//place your code here
//the code here will work when user is changing the text
}
我想我现在更明白了。
如有错误请指正,不要着急降级
我很困惑地认为 EditText.getText()
正在返回 String
,甚至当我看到 afterTextChanged(Editable s)
使用 Editable
时,我仍然认为它是一个相似的对象。
直到现在我注意到我可以使用 getText()
,然后是 setSpan
而无需使用 setText
,我才意识到我实际上是在获取实际对象并因此直接操作它。
意思是每一个 getText()
或使用 TextWatcher
监听器,旧的 setSpan
仍然存在,我需要清除它。
起初我以为 clearSpans()
可以解决问题,但它似乎也清除了其他所有内容。因此,我首先设置默认跨度,然后才设置正确的跨度
例如:
//Clear old span
s.setSpan( new BackgroundColorSpan( Color.TRANSPARENT),
0,
s.length(),
Spanned.SPAN_MARK_MARK );
//set new span
s.setSpan( new BackgroundColorSpan( Color.RED),
indexStart,
indexStart + mQuantity.length(),
Spanned.SPAN_MARK_MARK );
此外,我注意到自动完成适配器和 TextWatcher 的顺序并不总是相同。使用日志时,我注意到大多数情况下 TextWatcher 在自动完成之前触发,但并非总是如此。要么那个,要么一个可以开火,另一个可以开火?!我不知道。
无论如何,由于适配器检查文本时顺序很重要,所以我使用 MutableLiveData<String>
来跟踪 mQuantity
值并相应地修改跨度
//In AutoComplete adapter
public MutableLiveData<String> getQuantity() {
if (mQuantity == null) {
mQuantity = new MutableLiveData<>();
}
return mQuantity;
}
//In handler constructor
mAutoCompleteAdapter.getQuantity().observe( (LifecycleOwner) activity, new
Observer<String>() {
@Override
public void onChanged(String s) {
mQuantity = s;
refreshSpans();
}
} );
private void refreshSpans() {
Editable s = mTextView.getText();
clearEditTextSpan(s);
if (!mQuantity.isEmpty()) {
//Set span
int indexStart = mAutoCompleteAdapter.getQuantityIndex();
s.setSpan( new BackgroundColorSpan( Color.RED),
indexStart,
indexStart + mQuantity.length(),
Spanned.SPAN_MARK_MARK );
}
}
private void clearEditTextSpan(Editable s) {
s.setSpan( new BackgroundColorSpan( Color.TRANSPARENT),
0,
s.length(),
Spanned.SPAN_MARK_MARK );
}
希望对大家有所帮助。
很长一段时间我都对 setSpan
感到困惑,因为它看起来很简单但并不总是按预期工作
在我最后一次尝试中,我试图 setSpan
识别模式。
当用户开始输入“5 kilo toma”时,“5 kilo”将突出显示。
我使用下一个代码作为 TextWatcher
侦听器的一部分来执行此操作
@Override
public void afterTextChanged(Editable s) {
String quantity = mAutoCompleteAdapter.getQuantity();
if (!quantity.isEmpty()) {
int index = mAutoCompleteAdapter.getQuantityIndex();
final StyleSpan styleSpan = new StyleSpan( Typeface.BOLD_ITALIC );
s.setSpan( styleSpan, index, index + quantity.length(), Spanned.SPAN_MARK_MARK );
}
}
这工作正常(基本测试)
但是,如果我开始删除文本以读取“5 kil”,则当不再检测到模式时,setSpan
不会刷新为正常
所以我在想,也许 setSpan
保存在内存中或其他东西中,我每次都需要设置整个字符串跨度。所以我尝试了下一个代码:
@Override
public void afterTextChanged(Editable s) {
if (s.length() > 0) {
String quantity = mAutoCompleteAdapter.getQuantity();
int index = 0;
if (!quantity.isEmpty()) {
index = mAutoCompleteAdapter.getQuantityIndex();
StyleSpan styleSpan = new StyleSpan( Typeface.BOLD_ITALIC );
s.setSpan( styleSpan, index, index + quantity.length(), Spanned.SPAN_MARK_MARK );
}
StyleSpan styleSpanNormal = new StyleSpan( Typeface.NORMAL );
s.setSpan( styleSpanNormal, index + quantity.length(), s.length(), Spanned.SPAN_MARK_MARK );
}
}
但仍然无法正常工作
我认为你应该尝试 textChangedListener
因为它的方法 onTextChanged
将帮助你在用户输入新文本时检查文本,删除文本视图中的一些文本
textview.addTextChangedListener(new TextWatcher() {
@Override
public void beforeTextChanged(CharSequence s, int start, int count, int after{
}
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
//place your code here
//the code here will work when user is changing the text
}
我想我现在更明白了。
如有错误请指正,不要着急降级
我很困惑地认为 EditText.getText()
正在返回 String
,甚至当我看到 afterTextChanged(Editable s)
使用 Editable
时,我仍然认为它是一个相似的对象。
直到现在我注意到我可以使用 getText()
,然后是 setSpan
而无需使用 setText
,我才意识到我实际上是在获取实际对象并因此直接操作它。
意思是每一个 getText()
或使用 TextWatcher
监听器,旧的 setSpan
仍然存在,我需要清除它。
起初我以为 clearSpans()
可以解决问题,但它似乎也清除了其他所有内容。因此,我首先设置默认跨度,然后才设置正确的跨度
例如:
//Clear old span
s.setSpan( new BackgroundColorSpan( Color.TRANSPARENT),
0,
s.length(),
Spanned.SPAN_MARK_MARK );
//set new span
s.setSpan( new BackgroundColorSpan( Color.RED),
indexStart,
indexStart + mQuantity.length(),
Spanned.SPAN_MARK_MARK );
此外,我注意到自动完成适配器和 TextWatcher 的顺序并不总是相同。使用日志时,我注意到大多数情况下 TextWatcher 在自动完成之前触发,但并非总是如此。要么那个,要么一个可以开火,另一个可以开火?!我不知道。
无论如何,由于适配器检查文本时顺序很重要,所以我使用 MutableLiveData<String>
来跟踪 mQuantity
值并相应地修改跨度
//In AutoComplete adapter
public MutableLiveData<String> getQuantity() {
if (mQuantity == null) {
mQuantity = new MutableLiveData<>();
}
return mQuantity;
}
//In handler constructor
mAutoCompleteAdapter.getQuantity().observe( (LifecycleOwner) activity, new
Observer<String>() {
@Override
public void onChanged(String s) {
mQuantity = s;
refreshSpans();
}
} );
private void refreshSpans() {
Editable s = mTextView.getText();
clearEditTextSpan(s);
if (!mQuantity.isEmpty()) {
//Set span
int indexStart = mAutoCompleteAdapter.getQuantityIndex();
s.setSpan( new BackgroundColorSpan( Color.RED),
indexStart,
indexStart + mQuantity.length(),
Spanned.SPAN_MARK_MARK );
}
}
private void clearEditTextSpan(Editable s) {
s.setSpan( new BackgroundColorSpan( Color.TRANSPARENT),
0,
s.length(),
Spanned.SPAN_MARK_MARK );
}
希望对大家有所帮助。