首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >"android:textIsSelectable="true“在RecyclerView中对TextView无效

"android:textIsSelectable="true“在RecyclerView中对TextView无效
EN

Stack Overflow用户
提问于 2016-04-23 03:02:28
回答 9查看 8.1K关注 0票数 36

我知道在TextView的xml中设置android:textIsSelectable="true"会显示原生文本选择弹出窗口,我一直在应用程序中使用它。但是,当我尝试在附加到RecyclerView的视图中设置相同的属性时,我发现它不再起作用。每当我尝试选择文本时,都会出现以下日志-

代码语言:javascript
复制
TextView: TextView does not support text selection. Action mode cancelled.

我不知道为什么?为什么它能在其他屏幕上工作,而不能在RecyclerView上工作。我读了很多帖子-

TextView with android:textIsSelectable="true" not working in listview

textview textIsSelectable="true" not working in Listview

android:textIsSelectable="true" for TextView inside Listview does not work

但后来我遇到了这个帖子-

Android: "TextView does not support text selection. Action mode cancelled"

@hungkk的回复对我很有效。他的解决方案建议将TextView宽度从match_parent更改为wrap_content

我知道我可以做到这一点,但我的问题是它是如何解决这个问题的,因为它对我来说看起来很奇怪。另外,如果我想保持宽度为match_parent,该如何解决呢?

欢迎任何意见。

EN

回答 9

Stack Overflow用户

发布于 2017-06-20 16:00:09

在recyclerview的main-parent布局中添加属性

android:descendantFocusability="beforeDescendants"

然后在rowitem布局的TextView中添加

代码语言:javascript
复制
android:textIsSelectable="true"
票数 14
EN

Stack Overflow用户

发布于 2019-05-21 00:24:17

我发现RecyclerView中的TextView可以第一次选择,但是当ViewHolder被回收或适配器notifyDataSetChanged时,所有的文本视图将不能被选择。我发现这个解决方案对我很有效。

代码语言:javascript
复制
yourTextView.setText("your text");
yourTextView.setTextIsSelectable(false);
yourTextView.measure(-1, -1);//you can specific other values.
yourTextView.setTextIsSelectable(true);

为什么要这样做?因为我已经调试过,在android源代码中发现了一些逻辑:

TextView.java:

代码语言:javascript
复制
public void setTextIsSelectable(boolean selectable) {
    if (!selectable && mEditor == null) return; // false is default value with no edit data

    createEditorIfNeeded();
    if (mEditor.mTextIsSelectable == selectable) return;

    mEditor.mTextIsSelectable = selectable;
    setFocusableInTouchMode(selectable);
    setFocusable(FOCUSABLE_AUTO);
    setClickable(selectable);
    setLongClickable(selectable);

    // mInputType should already be EditorInfo.TYPE_NULL and mInput should be null

    setMovementMethod(selectable ? ArrowKeyMovementMethod.getInstance() : null);
    setText(mText, selectable ? BufferType.SPANNABLE : BufferType.NORMAL);

    // Called by setText above, but safer in case of future code changes
    mEditor.prepareCursorControllers();
}

Editor.java

代码语言:javascript
复制
void prepareCursorControllers() {
    boolean windowSupportsHandles = false;

    ViewGroup.LayoutParams params = mTextView.getRootView().getLayoutParams();
    if (params instanceof WindowManager.LayoutParams) {
        WindowManager.LayoutParams windowParams = (WindowManager.LayoutParams) params;
        windowSupportsHandles = windowParams.type < WindowManager.LayoutParams.FIRST_SUB_WINDOW
                || windowParams.type > WindowManager.LayoutParams.LAST_SUB_WINDOW;
    }

    boolean enabled = windowSupportsHandles && mTextView.getLayout() != null;
    mInsertionControllerEnabled = enabled && isCursorVisible();
    **mSelectionControllerEnabled = enabled && mTextView.textCanBeSelected();**

    if (!mInsertionControllerEnabled) {
        hideInsertionPointCursorController();
        if (mInsertionPointCursorController != null) {
            mInsertionPointCursorController.onDetached();
            mInsertionPointCursorController = null;
        }
    }

    if (!mSelectionControllerEnabled) {
        stopTextActionMode();
        if (mSelectionModifierCursorController != null) {
            mSelectionModifierCursorController.onDetached();
            mSelectionModifierCursorController = null;
        }
    }
}

-> TextView.java

代码语言:javascript
复制
/**
 * Test based on the <i>intrinsic</i> charateristics of the TextView.
 * The text must be spannable and the movement method must allow for arbitary selection.
 *
 * See also {@link #canSelectText()}.
 */
boolean textCanBeSelected() {
    // prepareCursorController() relies on this method.
    // If you change this condition, make sure prepareCursorController is called anywhere
    // the value of this condition might be changed.
    if (mMovement == null || !mMovement.canSelectArbitrarily()) return false;
    return isTextEditable()
            || (isTextSelectable() && mText instanceof Spannable && isEnabled());
}

您可以在Emulator中调试并跟踪此代码。

票数 9
EN

Stack Overflow用户

发布于 2017-06-19 17:41:13

如果在recyclerviewlistview中添加android:descendantFocusability="blocksDescendants"​,则将其删除。检查完这个之后

票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/36801486

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档