5

我正在尝试在 中进行长按EditText,但是当我长按时,我收到以下错误。我希望能够长按以获取复制/粘贴/全选上下文弹出窗口,以便用户可以将文本粘贴到框中。

Fatal Exception: android.view.WindowManager$BadTokenException: Unable to add window -- token android.view.ViewRootImpl$W@799bfc6 is not valid; is your activity running?

EditText 在 PopupWindow 的 ScrollView 中。因此,当错误发生时,我当前在 PopupWindow 打开的 Activity 上处于活动状态,并且我在 PopupWindow 中包含的 EditText 内进行了长按。

摇篮设置

compileSdkVersion 25
buildToolsVersion '25.0.0'
defaultConfig {
    applicationId 'com.accoservice.cico'
    minSdkVersion 17
    targetSdkVersion 25
    versionCode 37
    versionName '4.2.6'
    multiDexEnabled true
}

包含 EditText 的布局:

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/outer_layout"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:background="#73000000">

    <LinearLayout
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_gravity="top"
        android:layout_marginLeft="20dp"
        android:layout_marginRight="20dp"
        android:layout_marginTop="100dp"
        android:layout_marginBottom="5dp"
        android:background="#ffffff"
        android:orientation="vertical">

        <TextView
            android:id="@+id/title"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginBottom="5dp"
            android:layout_marginLeft="5dp"
            android:layout_marginTop="15dp"
            android:singleLine="true"
            android:text="@string/note_msg"
            android:textColor="#62CCFE"
            android:textSize="18sp" />

        <View
            android:layout_width="fill_parent"
            android:layout_height="2dp"
            android:layout_marginBottom="5dp"
            android:layout_marginTop="10dp"
            android:background="#62CCFE" />

        <ScrollView
            android:id="@+id/sv_resolution_note"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:layout_marginLeft="5dp"
            android:layout_marginRight="5dp"
            android:layout_marginTop="5dp">

            <EditText
                android:id="@+id/et_note_msz"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:layout_above="@+id/view"
                android:layout_alignParentTop="true"
                android:scrollbars="vertical"
                android:focusable="true"
                android:gravity="left"
                android:maxLines="20"
                android:hint="@string/write_note"
                android:inputType="textFilter|textMultiLine|textCapSentences"
                android:singleLine="false"
                android:textIsSelectable="true"
                android:enabled="true"
                android:longClickable="true" />
        </ScrollView>

        <View
            android:id="@+id/view"
            android:layout_width="fill_parent"
            android:layout_height="1dp"
            android:layout_above="@+id/send_note"
            android:layout_alignParentLeft="true"
            android:layout_alignParentStart="true"
            android:background="@android:color/darker_gray" />

        <Button
            android:id="@+id/send_note"
            android:layout_width="fill_parent"
            android:layout_height="wrap_content"
            android:layout_above="@+id/viewss"
            android:layout_gravity="center"
            android:background="@color/white"
            android:text="@string/add_note" />

        <View
            android:id="@+id/viewss"
            android:layout_width="fill_parent"
            android:layout_height="1dp"
            android:layout_alignParentBottom="true"
            android:layout_alignParentLeft="true"
            android:layout_alignParentStart="true"

            android:background="@android:color/darker_gray" />

    </LinearLayout>

</LinearLayout>

弹出窗口:

@Override
public void onClick(View v) {
     noteDialog(getResources().getString(R.string.laborentryresolutionstart), tv_labor_entry_resolution_start);
}

public void noteDialog(String noteTitle, final TextView tv_resolution_note)
{
    LayoutInflater layoutInflater = (LayoutInflater) getBaseContext().getSystemService(LAYOUT_INFLATER_SERVICE);
            final View popupView;
            popupView = layoutInflater.inflate(R.layout.resolution_note, null);

            TextView title = (TextView) popupView.findViewById(R.id.title);
            title.setText(noteTitle);

            final EditText editText = (EditText) popupView.findViewById(R.id.et_note_msz);
            final PopupWindow popupWindow = new PopupWindow(popupView, ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT, true);
            popupWindow.update();
            popupWindow.setFocusable(true);
            popupWindow.setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_ALWAYS_VISIBLE);
            editText.setEnabled(false);
            editText.setEnabled(true);
            editText.setFocusable(true);
            editText.setOnLongClickListener(new View.OnLongClickListener() {
                @Override
                public boolean onLongClick(View v) {

                    //ADD HERE ABOUT CUT COPY PASTE
                    // TODO Auto-generated method stub
                    return false;
                }
            });

            if (!tv_resolution_note.getText().toString().isEmpty()) {
                editText.setText(tv_resolution_note.getText().toString());
            }

            Button btnDone = (Button) popupView.findViewById(R.id.send_note);
            LinearLayout outer_layout = (LinearLayout) popupView.findViewById(R.id.outer_layout);
            outer_layout.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    popupWindow.dismiss();

                    InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
                    imm.toggleSoftInput(InputMethodManager.RESULT_HIDDEN, 0);
                }
            });

            System.gc();
            try {
                btnDone.setOnClickListener(new Button.OnClickListener() {
                    @Override
                    public void onClick(View v) {
                        EditText noteMsz = (EditText) popupView.findViewById(R.id.et_note_msz);
                        tv_resolution_note.setText(noteMsz.getText().toString());

                        popupWindow.dismiss();

                        InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
                        imm.toggleSoftInput(InputMethodManager.RESULT_HIDDEN, 0);

                        invalidateOptionsMenu();
                    }
                });
            } catch (Exception e) {
            }

            popupWindow.setFocusable(true);
            popupWindow.setBackgroundDrawable(new BitmapDrawable(null, ""));
            popupWindow.showAsDropDown(tv_labor_sym_entry, 0, -60);
            popupWindow.update();     
}
4

4 回答 4

4

据我说,您收到此错误的原因是outer_layout'onClickListeneronLongClickListener您的editText. 而且,由于popupWindow.dismiss在您的点击侦听器中调用outer_layout,弹出窗口在您的长点击侦听器代码可以运行之前被关闭editText,从而导致错误。

最简单的解决方案是返回true您的onLongClick方法:-

editText.setOnLongClickListener(new View.OnLongClickListener() {
                @Override
                public boolean onLongClick(View v) {

                    //ADD HERE ABOUT CUT COPY PASTE
                    // TODO Auto-generated method stub
                    return true;
                }
            });

通过这样做,您将消耗给定的长单击,并且不会触发任何其他不需要的侦听器。

onLongClick() - 这将返回一个布尔值,以指示您是否已消费该事件并且不应进一步携带它。也就是说,返回 true 表示您已经处理了该事件,它应该在这里停止;如果您还没有处理它,则返回 false 和/或事件应该继续到任何其他点击监听器。

于 2017-09-14T18:33:23.303 回答
0

您可能过早地调用您的弹出窗口。在我的示例(此处的要点)中,我正在通过按下按钮执行弹出代码。这是在onCreate()其他关键生命周期方法运行之后。有了这个例子,一切正常。

但是,如果我尝试在 中实例化弹出onCreate()窗口,则会收到一个 logcat 错误,指出:“android.view.WindowManager$BadTokenException: Unable to add window”,这就是您所看到的。

我相信您正试图过早地实例化您的弹出窗口。在活动的生命周期后期启动它,并且绝对是在onCreate()执行之后。如果您需要立即实例化它,您可以通过调用将代码附加到 UI 消息队列post(Runnable)。(见这里)。

我相当肯定这是你的问题。如果这没有帮助,请使用有关如何以及何时实例化弹出窗口的更多信息来更新您的问题。

于 2017-09-12T12:03:12.417 回答
0

我们进行了重新设计以消除弹出窗口并消除存在的错误。

于 2017-09-19T00:59:53.447 回答
0

在您的主要活动中

私有内容 mContext;

public void onCreate(){
 mContext = this;
}

用 mContext 替换 getBaseContext()

LayoutInflater layoutInflater = (LayoutInflater) mContext.getSystemService(LAYOUT_INFLATER_SERVICE);

或者

  LayoutInflater layoutInflater = (LayoutInflater) getSystemService(LAYOUT_INFLATER_SERVICE);
于 2017-09-18T13:55:42.553 回答