Android自由选择复制功能实现

简介

在Android应用中,我们经常会遇到需要复制文本的情况。通常情况下,用户只能通过长按文本,然后选择“复制”来复制文本内容。但是有时候我们希望用户可以自由选择复制文本的内容,而不是整个文本块。本文将介绍如何在Android应用中实现自由选择复制功能。

实现步骤

1. 创建可选择文本的TextView

首先,我们需要自定义一个TextView,让用户可以自由选择文本。下面是一个示例代码:

public class SelectableTextView extends AppCompatTextView {
    
    private int startSelection;
    private int endSelection;

    public SelectableTextView(Context context) {
        super(context);
        init();
    }

    public SelectableTextView(Context context, AttributeSet attrs) {
        super(context, attrs);
        init();
    }

    public SelectableTextView(Context context, AttributeSet attrs, int defStyleAttr) {
        super(context, attrs, defStyleAttr);
        init();
    }

    private void init() {
        setMovementMethod(LinkMovementMethod.getInstance());
        setHighlightColor(Color.TRANSPARENT);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        Paint paint = new Paint();
        paint.setColor(ContextCompat.getColor(getContext(), R.color.colorAccent));
        paint.setStyle(Paint.Style.STROKE);
        paint.setStrokeWidth(3);
        if (startSelection >= 0 && endSelection >= 0) {
            Layout layout = getLayout();
            int startLine = layout.getLineForOffset(startSelection);
            int endLine = layout.getLineForOffset(endSelection);
            for (int i = startLine; i <= endLine; i++) {
                int lineStart = layout.getLineStart(i);
                int lineEnd = layout.getLineEnd(i);
                float startX = layout.getPrimaryHorizontal(lineStart);
                float endX = layout.getPrimaryHorizontal(lineEnd);
                float top = layout.getLineTop(i);
                float bottom = layout.getLineBottom(i);
                canvas.drawRect(startX, top, endX, bottom, paint);
            }
        }
    }

    public void setSelection(int start, int end) {
        startSelection = start;
        endSelection = end;
        invalidate();
    }
}
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.
  • 35.
  • 36.
  • 37.
  • 38.
  • 39.
  • 40.
  • 41.
  • 42.
  • 43.
  • 44.
  • 45.
  • 46.
  • 47.
  • 48.
  • 49.
  • 50.
  • 51.
  • 52.
  • 53.
  • 54.
2. 在布局文件中使用SelectableTextView
<com.example.app.SelectableTextView
    android:id="@+id/selectableTextView"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="This is a selectable text view. You can select text freely."
    android:textColor="@android:color/black"
    android:textSize="16sp"
    android:padding="16dp"/>
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
3. 处理文本选择事件

在Activity或Fragment中处理文本选择事件,并实现复制功能。

SelectableTextView selectableTextView = findViewById(R.id.selectableTextView);

selectableTextView.setOnLongClickListener(new View.OnLongClickListener() {
    @Override
    public boolean onLongClick(View v) {
        int start = selectableTextView.getSelectionStart();
        int end = selectableTextView.getSelectionEnd();
        selectableTextView.setSelection(start, end); // 绘制选择区域
        return false;
    }
});

registerForContextMenu(selectableTextView);

@Override
public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) {
    super.onCreateContextMenu(menu, v, menuInfo);
    menu.add(0, v.getId(), 0, "Copy");
}

@Override
public boolean onContextItemSelected(MenuItem item) {
    if (item.getTitle() == "Copy") {
        ClipboardManager clipboard = (ClipboardManager) getSystemService(Context.CLIPBOARD_SERVICE);
        int start = selectableTextView.getSelectionStart();
        int end = selectableTextView.getSelectionEnd();
        CharSequence selectedText = selectableTextView.getText().subSequence(start, end);
        ClipData clip = ClipData.newPlainText("SelectedText", selectedText);
        clipboard.setPrimaryClip(clip);
        Toast.makeText(this, "Text copied to clipboard", Toast.LENGTH_SHORT).show();
        return true;
    }
    return super.onContextItemSelected(item);
}
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.
  • 30.
  • 31.
  • 32.
  • 33.
  • 34.

类图

下面是SelectableTextView类的类图:

SelectableTextView AppCompatTextView

总结

通过自定义TextView,并实现文本选择事件和复制功能,我们实现了Android应用中的自由选择复制功能。用户可以自由选择文本内容,并复制到剪贴板中。这种功能在一些需要用户输入文本的应用中非常有用,例如笔记应用、聊天应用等。希最本文的内容能够帮助你实现类似的功能。