1 /* 2 * Copyright (C) 2021 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.systemui.clipboardoverlay; 18 19 import static java.util.Objects.requireNonNull; 20 21 import android.app.Activity; 22 import android.content.ClipData; 23 import android.content.ClipDescription; 24 import android.content.ClipboardManager; 25 import android.content.pm.PackageManager; 26 import android.graphics.Insets; 27 import android.os.Bundle; 28 import android.os.PersistableBundle; 29 import android.text.Editable; 30 import android.util.Log; 31 import android.view.View; 32 import android.view.ViewGroup; 33 import android.view.WindowInsets; 34 import android.view.inputmethod.InputMethodManager; 35 import android.widget.EditText; 36 import android.widget.TextView; 37 38 import androidx.annotation.NonNull; 39 40 import com.android.systemui.res.R; 41 42 /** 43 * Lightweight activity for editing text clipboard contents 44 */ 45 public class EditTextActivity extends Activity 46 implements ClipboardManager.OnPrimaryClipChangedListener { 47 private static final String TAG = "EditTextActivity"; 48 49 private EditText mEditText; 50 private ClipboardManager mClipboardManager; 51 private TextView mAttribution; 52 private boolean mSensitive; 53 54 @Override onCreate(Bundle savedInstanceState)55 protected void onCreate(Bundle savedInstanceState) { 56 super.onCreate(savedInstanceState); 57 setContentView(R.layout.clipboard_edit_text_activity); 58 findViewById(R.id.done_button).setOnClickListener((v) -> saveToClipboard()); 59 mEditText = findViewById(R.id.edit_text); 60 mAttribution = findViewById(R.id.attribution); 61 mClipboardManager = requireNonNull(getSystemService(ClipboardManager.class)); 62 63 findViewById(R.id.editor_root).setOnApplyWindowInsetsListener( 64 new View.OnApplyWindowInsetsListener() { 65 @NonNull 66 @Override 67 public WindowInsets onApplyWindowInsets(@NonNull View view, 68 @NonNull WindowInsets windowInsets) { 69 Insets insets = windowInsets.getInsets(WindowInsets.Type.systemBars()); 70 ViewGroup.MarginLayoutParams layoutParams = 71 (ViewGroup.MarginLayoutParams) view.getLayoutParams(); 72 layoutParams.leftMargin = insets.left; 73 layoutParams.bottomMargin = insets.bottom; 74 layoutParams.rightMargin = insets.right; 75 layoutParams.topMargin = insets.top; 76 view.setLayoutParams(layoutParams); 77 return WindowInsets.CONSUMED; 78 } 79 }); 80 } 81 82 @Override onStart()83 protected void onStart() { 84 super.onStart(); 85 ClipData clip = mClipboardManager.getPrimaryClip(); 86 if (clip == null) { 87 finish(); 88 return; 89 } 90 PackageManager pm = getApplicationContext().getPackageManager(); 91 try { 92 CharSequence label = pm.getApplicationLabel( 93 pm.getApplicationInfo(mClipboardManager.getPrimaryClipSource(), 94 PackageManager.ApplicationInfoFlags.of(0))); 95 mAttribution.setText(getResources().getString(R.string.clipboard_edit_source, label)); 96 } catch (PackageManager.NameNotFoundException e) { 97 Log.w(TAG, "Package not found: " + mClipboardManager.getPrimaryClipSource(), e); 98 } 99 mEditText.setText(clip.getItemAt(0).getText().toString()); 100 mEditText.requestFocus(); 101 mEditText.setSelection(0); 102 mSensitive = clip.getDescription().getExtras() != null 103 && clip.getDescription().getExtras() 104 .getBoolean(ClipDescription.EXTRA_IS_SENSITIVE); 105 mClipboardManager.addPrimaryClipChangedListener(this); 106 } 107 108 @Override onPause()109 protected void onPause() { 110 mClipboardManager.removePrimaryClipChangedListener(this); 111 super.onPause(); 112 } 113 114 @Override // ClipboardManager.OnPrimaryClipChangedListener onPrimaryClipChanged()115 public void onPrimaryClipChanged() { 116 hideIme(); 117 finish(); 118 } 119 saveToClipboard()120 private void saveToClipboard() { 121 hideIme(); 122 Editable editedText = mEditText.getText(); 123 editedText.clearSpans(); 124 ClipData clip = ClipData.newPlainText("text", editedText); 125 PersistableBundle extras = new PersistableBundle(); 126 extras.putBoolean(ClipDescription.EXTRA_IS_SENSITIVE, mSensitive); 127 clip.getDescription().setExtras(extras); 128 mClipboardManager.setPrimaryClip(clip); 129 finish(); 130 } 131 hideIme()132 private void hideIme() { 133 InputMethodManager imm = getSystemService(InputMethodManager.class); 134 imm.hideSoftInputFromWindow(mEditText.getWindowToken(), 0); 135 } 136 } 137