从4.4.2和Lollypop开始,这些链接已停止工作.文本仍显示带下划线且带有超链接颜色,但点击它们不会产生任何结果.
必须要说的是,这些字段被标记为可复制粘贴,已知这些字段与这些字段相互作用.
有没有人能够解决这个问题?
解决方法 问题是,当在TextVIEw中启用复制和粘贴时,AndroID将使用ArrowKeyMovementMethod,它支持选择文本但不支持单击链接.当您使用@R_404_6862@MovementMethod时,您可以单击链接但不能选择文本(无论您使用的是Lollipop,KitKat还是较低的AndroID版本).为了解决这个问题,我扩展了ArrayKeyMovementMethod类并使用@R_404_6862@MovementMethod ontouchEvent覆盖了ontouchEvent.为了允许文本选择,我必须删除三行代码.由于我在具有大量文本格式的富文本编辑器中使用该类,因此我还添加了逻辑来查找所单击的字符,而不管文本大小,缩进或文本对齐.如果您希望使用纯文本的简单解决方案,请在自定义ArrowKeyMovementMethod类中使用它:
@OverrIDepublic boolean ontouchEvent(TextVIEw Widget,Spannable buffer,MotionEvent event) { int action = event.getAction(); if (action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_DOWN) { int x = (int) event.getX(); int y = (int) event.getY(); x -= Widget.getTotalpaddingleft(); y -= Widget.getTotalpaddingtop(); x += Widget.getScrollX(); y += Widget.getScrollY(); Layout layout = Widget.getLayout(); int line = layout.getlineForVertical(y); int off = layout.getoffsetForHorizontal(line,x); ClickableSpan[] @R_404_6862@ = buffer.getSpans(off,off,ClickableSpan.class); if (@R_404_6862@.length != 0) { if (action == MotionEvent.ACTION_UP) { @R_404_6862@[0].onClick(Widget); } else if (action == MotionEvent.ACTION_DOWN) { Selection.setSelection(buffer,buffer.getSpanStart(@R_404_6862@[0]),buffer.getSpanEnd(@R_404_6862@[0])); } return true; } /* These are the lines of code you want to remove else { Selection.removeSelection(buffer); }*/ } return super.ontouchEvent(Widget,buffer,event);}
别忘了打电话:
myTv.setMovementMethod(new ClickAndSelectMovementMethod());
如果您希望支持各种文本格式的版本使用此代码:
import androID.graphics.Rect;import androID.text.Layout;import androID.text.Selection;import androID.text.Spannable;import androID.text.Spanned;import androID.text.TextPaint;import androID.text.method.ArrowKeyMovementMethod;import androID.text.method.MovementMethod;import androID.text.style.absoluteSizeSpan;import androID.text.style.ClickableSpan;import androID.text.style.LeadingmarginSpan;import androID.vIEw.MotionEvent;import androID.Widget.TextVIEw;/** * ArrowKeyMovementMethod does support selection of text but not the clicking of * @R_404_6862@s. @R_404_6862@MovementMethod does support clicking of @R_404_6862@s but not the * selection of text. This class adds the @R_404_6862@ clicking to the * ArrowKeyMovementMethod. We basically take the @R_404_6862@MovementMethod ontouchEvent * code and remove the line Selection.removeSelection(buffer); which de-selects * all text when no @R_404_6862@ was found. */public class ClickAndSelectMovementMethod extends ArrowKeyMovementMethod { private static Rect slineBounds = new Rect(); @OverrIDe public boolean ontouchEvent(TextVIEw Widget,MotionEvent event) { int action = event.getAction(); if (action == MotionEvent.ACTION_UP || action == MotionEvent.ACTION_DOWN) { int index = getCharIndexAt(Widget,event); if (index != -1) { ClickableSpan[] @R_404_6862@ = buffer.getSpans(index,index,ClickableSpan.class); if (@R_404_6862@.length != 0) { if (action == MotionEvent.ACTION_UP) { @R_404_6862@[0].onClick(Widget); } else if (action == MotionEvent.ACTION_DOWN) { Selection.setSelection(buffer,buffer.getSpanEnd(@R_404_6862@[0])); } return true; } } /* * else { Selection.removeSelection(buffer); } */ } return super.ontouchEvent(Widget,event); } private int getCharIndexAt(TextVIEw textVIEw,MotionEvent event) { // get coordinates int x = (int) event.getX(); int y = (int) event.getY(); x -= textVIEw.getTotalpaddingleft(); y -= textVIEw.getTotalpaddingtop(); x += textVIEw.getScrollX(); y += textVIEw.getScrollY(); /* * fail-fast check of the line bound. If we're not within the line bound * no character was touched */ Layout layout = textVIEw.getLayout(); int line = layout.getlineForVertical(y); synchronized (slineBounds) { layout.getlineBounds(line,slineBounds); if (!slineBounds.contains(x,y)) { return -1; } } // retrIEve line text Spanned text = (Spanned) textVIEw.getText(); int linestart = layout.getlinestart(line); int lineEnd = layout.getlineEnd(line); int lineLength = lineEnd - linestart; if (lineLength == 0) { return -1; } Spanned lineText = (Spanned) text.subSequence(linestart,lineEnd); // compute leading margin and subtract it from the x coordinate int margin = 0; LeadingmarginSpan[] marginSpans = lineText.getSpans(0,lineLength,LeadingmarginSpan.class); if (marginSpans != null) { for (LeadingmarginSpan span : marginSpans) { margin += span.getLeadingmargin(true); } } x -= margin; // retrIEve text wIDths float[] wIDths = new float[lineLength]; TextPaint paint = textVIEw.getPaint(); paint.getTextWIDths(lineText,wIDths); // scale text wIDths by relative Font size (absolute size / default size) final float defaultSize = textVIEw.getTextSize(); float scaleFactor = 1f; absoluteSizeSpan[] absspans = lineText.getSpans(0,absoluteSizeSpan.class); if (absspans != null) { for (absoluteSizeSpan span : absspans) { int spanStart = lineText.getSpanStart(span); int spanEnd = lineText.getSpanEnd(span); scaleFactor = span.getSize() / defaultSize; int start = Math.max(linestart,spanStart); int end = Math.min(lineEnd,spanEnd); for (int i = start; i < end; i++) { wIDths[i] *= scaleFactor; } } } // find index of touched character float startChar = 0; float endChar = 0; for (int i = 0; i < lineLength; i++) { startChar = endChar; endChar += wIDths[i]; if (endChar >= x) { // which "end" is closer to x,the start or the end of the character? int index = linestart + (x - startChar < endChar - x ? i : i + 1); return index; } } return -1; }}总结
以上是内存溢出为你收集整理的android – 在Lollipop上打破的TextView fromHtml链接全部内容,希望文章能够帮你解决android – 在Lollipop上打破的TextView fromHtml链接所遇到的程序开发问题。
如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。
欢迎分享,转载请注明来源:内存溢出
评论列表(0条)