我有一个简单TextView的本地电话号码852112222或(8 5)211 2222.
我需要它可以点击,所以我很自然地使用它android:autoLink="all".
但由于某种原因,我不明白同一电话号码在所有设备上都没有"链接".
在普通的Genymotion设备上它没有用.在我个人的OnePlus2设备上它工作.在不同的设备上测试一堆 - 没有运气.
可能是什么问题?
用户帐户首选项?Android版本?ORM?别的什么?
小智 19
这是我的调查.
我创建了一个新项目,并添加android:autoLink="all"到文本视图中activity_main.xml.感谢Android Studio的开发人员,我可以看到预览,我发现了一些有趣的东西:
12345 没有联系123456 没有联系1234567 关联12345678 关联123456789 没有联系1234567890 不喜欢12345678901 关联123456789012 没有联系我的手机上的结果是一样的.所以我查看了源代码,搜索了关键字autolink,然后我发现了这个:
private void setText(CharSequence text, BufferType type,
boolean notifyBefore, int oldlen) {
...
// unconcerned code above
if (mAutoLinkMask != 0) {
Spannable s2;
if (type == BufferType.EDITABLE || text instanceof Spannable) {
s2 = (Spannable) text;
} else {
s2 = mSpannableFactory.newSpannable(text);
}
if (Linkify.addLinks(s2, mAutoLinkMask)) {
text = s2;
type = (type == BufferType.EDITABLE) ? BufferType.EDITABLE : BufferType.SPANNABLE;
/*
* We must go ahead and set the text before changing the
* movement method, because setMovementMethod() may call
* setText() again to try to upgrade the buffer type.
*/
mText = text;
// Do not change the movement method for text that support text selection as it
// would prevent an arbitrary cursor displacement.
if (mLinksClickable && !textCanBeSelected()) {
setMovementMethod(LinkMovementMethod.getInstance());
}
}
}
...
// unconcerned code above
}
Run Code Online (Sandbox Code Playgroud)
所以关键字Linkify现在是.用于addLinks:
public static final boolean addLinks(@NonNull Spannable text, @LinkifyMask int mask) {
...
if ((mask & PHONE_NUMBERS) != 0) {
gatherTelLinks(links, text);
}
...
}
private static final void gatherTelLinks(ArrayList<LinkSpec> links, Spannable s) {
PhoneNumberUtil phoneUtil = PhoneNumberUtil.getInstance();
Iterable<PhoneNumberMatch> matches = phoneUtil.findNumbers(s.toString(),
Locale.getDefault().getCountry(), Leniency.POSSIBLE, Long.MAX_VALUE);
for (PhoneNumberMatch match : matches) {
LinkSpec spec = new LinkSpec();
spec.url = "tel:" + PhoneNumberUtils.normalizeNumber(match.rawString());
spec.start = match.start();
spec.end = match.end();
links.add(spec);
}
}
Run Code Online (Sandbox Code Playgroud)
然后,发生了一些不好的事情,SDK没有PhoneNumberUtil,特别是以下3个类:
import com.android.i18n.phonenumbers.PhoneNumberMatch;
import com.android.i18n.phonenumbers.PhoneNumberUtil;
import com.android.i18n.phonenumbers.PhoneNumberUtil.Leniency;
Run Code Online (Sandbox Code Playgroud)
目前,第一个原因浮出水面:Locale.getDefault().getCountry().
所以我去设置,找到语言,选中文.结果如下:
12345 关联123456 关联1234567 关联12345678 关联123456789 关联1234567890 关联12345678901 关联123456789012 关联其次,对于包com.android.i18n.phonenumbers,我发现了这个:
https://android.googlesource.com/platform/external/libphonenumber/+/ics-factoryrom-2-release/java/src/com/android/i18n/phonenumbers
如果你有兴趣,请查看上面的链接.请注意URL : ics-factoryrom-2-release. 所以我高度怀疑这是依赖于平台的.
对于解决方案,CleverAndroid是对的,完全控制LinkMovementMethod是一个不错的选择.
Ili*_*hin 12
我为电话号码制作了一个通用模式并添加了一个 Linkify 掩码。Kotlin,扩展功能:
fun TextView.makeLinkedable(){
val pattern = Pattern.compile("""([\d|\(][\h|\(\d{3}\)|\.|\-|\d]{4,}\d)""",
Pattern.CASE_INSENSITIVE)
LinkifyCompat.addLinks(this, Linkify.ALL)
LinkifyCompat.addLinks(this, pattern, "tel://", null, null, null)
setLinkTextColor(ContextCompat.getColor(context, R.color.blue))
}
Run Code Online (Sandbox Code Playgroud)
应该适用于所有设备
重点在于此:
val pattern = Pattern.compile("""([\d|\(][\h|\(\d{3}\)|\.|\-|\d]{4,}\d)""",
Pattern.CASE_INSENSITIVE)
LinkifyCompat.addLinks(this, pattern, "tel://", null, null, null)
Run Code Online (Sandbox Code Playgroud)
在 Java 中:
Pattern pattern = Pattern.compile("([\\d|(][\\h|(\\d{3})|.|\\-|\\d]{4,}\\d{4,})", Pattern.CASE_INSENSITIVE);
LinkifyCompat.addLinks(textView, pattern, "tel://", null, null, null);
Run Code Online (Sandbox Code Playgroud)
请执行以下操作
TextView userInput= (TextView) view.findViewById(R.id.textView);
if(userInput != null){
Linkify.addLinks(userInput, Patterns.PHONE,"tel:",Linkify.sPhoneNumberMatchFilter,Linkify.sPhoneNumberTransformFilter);
userInput.setMovementMethod(LinkMovementMethod.getInstance());
}
Run Code Online (Sandbox Code Playgroud)
并删除
android:autoLink
Run Code Online (Sandbox Code Playgroud)
来自您的xml文件
你可以试试下面的代码.以编程方式设置属性.
活动
package custom.com.android_lab;
import android.app.Activity;
import android.os.Bundle;
import android.text.util.Linkify;
import android.widget.TextView;
/**
* You can use Activity or AppCompatActivity
*/
public class MainActivity extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// local phone number 852112222 or (8 5) 211 2222.
// Tested OK!
TextView textView1 = (TextView) findViewById(R.id.textv1);
textView1.setAutoLinkMask(Linkify.PHONE_NUMBERS);
textView1.setText("852112222");
// Tested OK!
TextView textView2 = (TextView) findViewById(R.id.textv2);
textView2.setAutoLinkMask(Linkify.PHONE_NUMBERS);
textView2.setText("(85) 211-2222");
// Tested Failed!
// Reason : Need to apply setAutoLinkMask prior to apply setText
TextView textView3 = (TextView) findViewById(R.id.textv3);
textView3.setText("852112222");
textView2.setAutoLinkMask(Linkify.PHONE_NUMBERS);
}
}
Run Code Online (Sandbox Code Playgroud)
视图
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/activity_main"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<TextView
android:id="@+id/textv1"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/textv2"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<TextView
android:id="@+id/textv3"
android:layout_width="match_parent"
android:layout_height="55dp" />
</LinearLayout>
Run Code Online (Sandbox Code Playgroud)
测试设备
小智 5
我在使用自动链接时发现了很多不一致的情况。如果您正在使用产品版本。始终使用 SpannableStringBuilder 和 LinkMovementMethod。您可以很好地控制文本的显示方式。
下面的代码片段可能会有所帮助。
String phone = "your phone number";
String message = "Phone number is: ";
Spannable span = new SpannableString(String.format("%s\n%s",message, phone));
ForegroundColorSpan color = new ForegroundColorSpan(Res.color(R.color.blue));
ClickableSpan click = new ClickableSpan() {
@Override
public void onClick(View widget) {
Navigator.dialer("your phone number");
}
public void updateDrawState(TextPaint ds) {// override updateDrawState
ds.setUnderlineText(false); // set to false to remove underline
}
};
span.setSpan(color, message.length(), message.length() + phone.length() + 1, Spanned.SPAN_INCLUSIVE_INCLUSIVE);
span.setSpan(click, message.length(), message.length() + phone.length() + 1, Spanned.SPAN_INCLUSIVE_INCLUSIVE);
changesMessageLabel.setText(span);
changesMessageLabel.setMovementMethod(LinkMovementMethod.getInstance());
Run Code Online (Sandbox Code Playgroud)
我建议您仅添加国家代码,所有问题都将得到解决,
android:autoLink="phone"
android:text="+91-8000000000"
Run Code Online (Sandbox Code Playgroud)
如果我们在号码前添加国家/地区代码,则无需其他临时解决方案。
小智 5
在电话号码为 11 位或更多且包含 3 个块的情况下,Harsh Agrawal 的回答对我有用。例如 123 456 78910
TextView textView = findViewById(R.id.text_view);
textView.setText("123 456 78910");
Linkify.addLinks(textView, Patterns.PHONE, "tel:", Linkify.sPhoneNumberMatchFilter,
Linkify.sPhoneNumberTransformFilter);
Run Code Online (Sandbox Code Playgroud)
我必须Linkify.addLinks在设置文本后调用它才能工作。
请注意,Linkify.addLinks已经调用setMovementMethod了文本视图。
| 归档时间: |
|
| 查看次数: |
8234 次 |
| 最近记录: |