java.lang.IllegalArgumentException: 从给定的视图中找不到合适的父级。请提供有效视图

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/47666685/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-03 09:44:09  来源:igfitidea点击:

java.lang.IllegalArgumentException: No suitable parent found from the given view. Please provide a valid view

javaandroidwebserver

提问by Mani

my app crashes when trying to display server message and I think the problem could be with my getView(). below is the registerActivitywere the crash occurs and my activity_register.xml

我的应用程序在尝试显示服务器消息时崩溃,我认为问题可能出在我的getView(). 下面是registerActivity崩溃发生的地方和我的activity_register.xml

import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.os.Bundle;
import android.support.design.widget.Snackbar;
import android.util.Log;
import android.view.View;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ProgressBar;
import android.widget.Toast;

import com.fastchat.helper.SQLiteHandler;
import com.fastchat.helper.SessionManager;
import com.google.gson.Gson;
import com.google.gson.GsonBuilder;

import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Retrofit;
import retrofit2.converter.gson.GsonConverterFactory;


public class RegisterActivity extends Activity {

private static final String TAG = RegisterActivity.class.getSimpleName();
private Button btnRegister;
private Button btnLinkToLogin;
private EditText inputFullName;
private EditText inputEmail;
private EditText inputPassword;
private ProgressDialog pDialog;
private SessionManager session;
private SQLiteHandler db;
private ProgressBar progress;


@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_register);


    inputFullName = (EditText) findViewById(R.id.name);
    inputEmail = (EditText) findViewById(R.id.email);
    inputPassword = (EditText) findViewById(R.id.password);
    btnRegister = (Button) findViewById(R.id.btnRegister);
    btnLinkToLogin = (Button) findViewById(R.id.btnLinkToLoginScreen);

    // Progress dialog
    pDialog = new ProgressDialog(this);
    pDialog.setCancelable(true);

    /*
    // Session manager
    session = new SessionManager(getApplicationContext());

    // SQLite database handler
    db = new SQLiteHandler(getApplicationContext());

    // Check if user is already logged in or not
   if (session.isLoggedIn()) {
        // User is already logged in. Take him to main activity
        Intent intent = new Intent(RegisterActivity.this,
                SearchableActivity.class);
        startActivity(intent);
        finish();

    }
*/
    // Register Button Click event
    btnRegister.setOnClickListener(new View.OnClickListener() {
        public void onClick(View view) {
            String name = inputFullName.getText().toString();
            String email = inputEmail.getText().toString();
            String password = inputPassword.getText().toString();

            if (!name.isEmpty() && !email.isEmpty() && !password.isEmpty()) {
                registerProcess(name, email, password);
            } else {
                Toast.makeText(getApplicationContext(),
                        "Please enter your details!", Toast.LENGTH_LONG)
                        .show();
            }
        }
    });

    // Link to Login Screen
    btnLinkToLogin.setOnClickListener(new View.OnClickListener() {

        public void onClick(View view) {
            Intent i = new Intent(getApplicationContext(),
                    LoginActivity.class);
            startActivity(i);
            finish();
        }
    });

}   

 private void registerProcess(String name,String email,String password){

    String tag_string_req = "req_register";
    //pDialog = new AlertDialog.Builder(getActivity());
    pDialog.setMessage("please wait");
    pDialog.show();


    Retrofit retrofit = new Retrofit.Builder()
            .baseUrl(Constants.BASE_URL)
            .addConverterFactory(GsonConverterFactory.create())
            .build();

    RequestInterface requestInterface = retrofit.create(RequestInterface.class);

    User user = new User();
    user.setName(name);
    user.setEmail(email);
    user.setPassword(password);
    ServerRequest request = new ServerRequest();
    request.setOperation(Constants.REGISTER_OPERATION);
    request.setUser(user);
    Call<ServerResponse> response = requestInterface.operation(request);

    response.enqueue(new Callback<ServerResponse>() {
        private View view;

        public View getView() {
            return view;

        }

        @Override
        public void onResponse(Call<ServerResponse> call, retrofit2.Response<ServerResponse> response) {

            ServerResponse resp = response.body();

           if(resp !=null)//tried to check if resp is null but its not

//crash occurs here
            Snackbar.make(getView(),resp.getMessage(), Snackbar.LENGTH_LONG).show();
            pDialog.dismiss();
        }


        @Override
        public void onFailure(Call<ServerResponse> call, Throwable t) {

           // progress.setVisibility(View.INVISIBLE);
            Log.d(Constants.TAG, "failed");
            Toast.makeText(getApplicationContext(), t.getLocalizedMessage(), Toast.LENGTH_LONG).show();
            pDialog.dismiss();


        }
    });
}

activity_register.xml

activity_register.xml

  <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
xmlns:tools="http://schemas.android.com/tools"
android:background="@color/bg_register"
android:gravity="center"
android:orientation="vertical"
android:padding="10dp"
android:id="@+id/chat">

<LinearLayout
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
    android:layout_gravity="center"
    android:orientation="vertical"
    android:paddingLeft="20dp"
    android:paddingRight="20dp" >

    <ImageView
        android:layout_width="389dp"
        android:layout_height="72dp"
        android:layout_gravity="center_horizontal"
        android:layout_marginBottom="24dp"
        android:src="@drawable/logo"
        tools:ignore="ContentDescription" />


    <EditText
        android:id="@+id/name"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_marginBottom="10dp"
        android:background="@color/input_register_bg"
        android:hint="@string/hint_name"
        android:padding="10dp"
        android:singleLine="true"
        android:inputType="textCapWords"
        android:textColor="@color/input_register"
        android:textColorHint="@color/input_register_hint" />

    <EditText
        android:id="@+id/email"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_marginBottom="10dp"
        android:background="@color/input_register_bg"
        android:hint="@string/hint_email"
        android:inputType="textEmailAddress"
        android:padding="10dp"
        android:singleLine="true"
        android:textColor="@color/input_register"
        android:textColorHint="@color/input_register_hint" />

    <EditText
        android:id="@+id/password"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_marginBottom="10dp"
        android:background="@color/input_register_bg"
        android:hint="@string/hint_password"
        android:inputType="textPassword"
        android:padding="10dp"
        android:singleLine="true"
        android:textColor="@color/input_register"
        android:textColorHint="@color/input_register_hint" />

    <!-- Login Button -->

    <Button
        android:id="@+id/btnRegister"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="20dip"
        android:background="#ea4c88"
        android:text="register"
        android:textColor="@color/white" />

    <!-- Link to Login Screen -->

    <Button
        android:id="@+id/btnLinkToLoginScreen"
        android:layout_width="fill_parent"
        android:layout_height="wrap_content"
        android:layout_marginTop="40dip"
        android:background="@null"
        android:text="already a member? login"
        android:textAllCaps="false"
        android:textColor="@color/white"
        android:textSize="15dp" />
</LinearLayout>

below is logcat message

下面是 logcat 消息

 java.lang.IllegalArgumentException: No suitable parent found from the given view. Please provide a valid view.
                                                              at android.support.design.widget.Snackbar.make(Snackbar.java:137)
                                                              at com.chat.RegisterActivity.onResponse(RegisterActivity.java:143)
                                                              at retrofit2.ExecutorCallAdapterFactory$ExecutorCallbackCall.run(ExecutorCallAdapterFactory.java:68)
                                                              at android.os.Handler.handleCallback(Handler.java:739)
                                                              at android.os.Handler.dispatchMessage(Handler.java:95)

回答by Normando

I suggest that you to try with findViewById(android.R.id.content).

我建议您尝试使用findViewById(android.R.id.content).

This is what did the trick for me:

这就是对我有用的技巧:

Snackbar.make(findViewById(android.R.id.content), resp.getMessage(), Snackbar.LENGTH_LONG).show();

android.R.id.contentwill give you the root element of the view (for more information on that, please check Android: What is android.R.id.content used for?).

android.R.id.content将为您提供视图的根元素(有关更多信息,请查看Android: What is android.R.id.content used for?)。

回答by Pratik Butani

I found one solution that may help others who are looking for common solution.

我找到了一种解决方案,可以帮助其他正在寻找通用解决方案的人。

I got this error when I have tried to show message with Snackbarbefore loading our whole XML file.

当我在加载整个 XML 文件之前尝试使用Snackbar显示消息时出现此错误。

In fragment I have tried to call API in onCreateView();and showing Snackbarmessage of Internet connection is offas below:

在片段中,我尝试调用 APIonCreateView();并显示如下Snackbar消息Internet connection is off

@Override
public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {

    mBindingObject = DataBindingUtil.inflate(inflater, getLayoutResId(), container, false);

    getData();

    return mBindingObject.getRoot();
}

I just put that method in onViewCreated()

我只是把那个方法放进去 onViewCreated()

@Override
public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
    super.onViewCreated(view, savedInstanceState);

    getData();
}

Its working for me now.

它现在对我来说有效。

BONUS:

奖金:

Always try to use view after its loaded successfully. Each and every position of one line is matters.

成功加载后始终尝试使用视图。一行的每一个位置都很重要。

Thank you.

谢谢你。

回答by Anu Martin

Wrap your layout with CoordinatorLayout

CoordinatorLayout包裹你的布局

<android.support.design.widget.CoordinatorLayout
     xmlns:android="http://schemas.android.com/apk/res/android"
     xmlns:app="http://schemas.android.com/apk/res-auto"
     xmlns:tools="http://schemas.android.com/tools"
     android:layout_width="match_parent"
     android:id="@+id/chat"
     android:layout_height="match_parent">
     <LinearLayout
          android:layout_width="match_parent"
          android:layout_height="match_parent"
          android:background="@color/bg_register"
          android:gravity="center"
          android:orientation="vertical"
          android:padding="10dp">
               ...
               ...
               ...
    </LinearLayout>
</android.support.design.widget.CoordinatorLayout>

回答by Richi

I had this problem too ... of course with a little difference ...

我也有这个问题......当然有一点不同......

PROBLEM:I used MVVM architecture and LiveData observer for showing SnackBar by the following code...This error occurred to me when I was displaying another fragment and returning back again.

问题:我使用 MVVM 架构和 LiveData 观察器通过以下代码显示 SnackBar...当我显示另一个片段并再次返回时发生了这个错误。

 myViewModel.mSnackbar.observe(this, new SnackBarText.SnackbarTextObserver() {
        @Override
        public void onNewMessage(@NotNull YourSnackBarClass msg) {
            // Showing the message on SnackBar
            Snackbar.make(view, msg.getMessage(), Snackbar.LENGTH_LONG).show();
        }
    });

SOLUTION:I remove this observer when fragment paused (Because I used replace()on fragment transaction)

解决方案:我在片段暂停时删除了这个观察者(因为我replace()在片段事务中使用过)

// fragment area
@Override
protected void onPause() {
    super.onPause();
    mSnackbarText.removeObservers(owner)
}

回答by Ashutosh Tiwari

Replace your View with this

用这个替换你的视图

getActivity().getCurrentFocus().

getActivity().getCurrentFocus().

but not in your Default Fragment

但不在你的默认片段中

回答by 4gus71n

Not sure if this is really that useful, but I stumbled across this issue when I was trying to display a Snackbar, using a CoordinatorLayoutview which had android:fitSystemWindows="true"and android:layout_behavior="...BottomSheetBehavior"apparently you cannot prompt a Snackbar on a root view which also has a behavior set.

不确定这是否真的那么有用,但是当我尝试显示 Snackbar 时,我偶然发现了这个问题,使用的CoordinatorLayout视图具有android:fitSystemWindows="true"并且android:layout_behavior="...BottomSheetBehavior"显然您无法在也具有行为集的根视图上提示 Snackbar。

I was doing some refactor and then realized that it didn't make any sense, having a behavior set on the root view. So I wrapped the CoordinatorLayoutinside another coordinator, use that new root view as the view for the Snackbar, and everything worked perfectly.

我正在做一些重构,然后意识到它没有任何意义,在根视图上设置了一个行为。所以我把CoordinatorLayout另一个协调器包裹在里面,使用这个新的根视图作为 Snackbar 的视图,一切都完美无缺。

回答by OmiK

You are passing invalidview argument to Snackbar. so you've to give RegisterActivity BaseLayout reference to it. you should try declare id to activity_register.xmlLinear / Relative or whatever you design.

您正在将invalid视图参数传递给 Snackbar。所以你必须给 RegisterActivity BaseLayout 引用它。您应该尝试将 id 声明为activity_register.xmlLinear/Relative 或您设计的任何内容。

  <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
              xmlns:tools="http://schemas.android.com/tools"
              android:layout_width="match_parent"
              android:layout_height="match_parent"
              android:orientation="vertical"
              android:background="#a7b6bdd6"
    android:id="@+id/ll1"  //here 
     >

    <android.support.v7.widget.Toolbar
        android:id="@+id/toolbar"
        android:layout_width="match_parent"
        android:layout_height="64dp"
        android:background="@color/colorPrimary"
        android:minHeight="?attr/actionBarSize" />

        //your design

</LinearLayout>

then initialise pass this layout to snackbar like below

然后初始化将此布局传递给小吃店,如下所示

 private void registerProcess(String name,String email,String password){

     final LinearLayout linearLayout = (LinearLayout)findViewById(R.id.ll1);// here change
      //Snackbar.make(linearLayout,"Hello", Snackbar.LENGTH_LONG).show();

    String tag_string_req = "req_register";
    //pDialog = new AlertDialog.Builder(getActivity());
    pDialog.setMessage("please wait");
    pDialog.show();


    Retrofit retrofit = new Retrofit.Builder()
            .baseUrl(Constants.BASE_URL)
            .addConverterFactory(GsonConverterFactory.create())
            .build();

    RequestInterface requestInterface = retrofit.create(RequestInterface.class);

    User user = new User();
    user.setName(name);
    user.setEmail(email);
    user.setPassword(password);
    ServerRequest request = new ServerRequest();
    request.setOperation(Constants.REGISTER_OPERATION);
    request.setUser(user);
    Call<ServerResponse> response = requestInterface.operation(request);

    response.enqueue(new Callback<ServerResponse>() {
        private View view;

        public View getView() {
            return view;

        }

        @Override
        public void onResponse(Call<ServerResponse> call, retrofit2.Response<ServerResponse> response) {

            ServerResponse resp = response.body();

           if(resp !=null)//tried to check if resp is null but its not

//crash occurs here
            Snackbar.make(linearLayout,resp.getMessage(), Snackbar.LENGTH_LONG).show();
            pDialog.dismiss();
        }


        @Override
        public void onFailure(Call<ServerResponse> call, Throwable t) {

           // progress.setVisibility(View.INVISIBLE);
            Log.d(Constants.TAG, "failed");
            Toast.makeText(getApplicationContext(), t.getLocalizedMessage(), Toast.LENGTH_LONG).show();
            pDialog.dismiss();


        }
    });
}

回答by diegoveloper

Instead of this :

而不是这个:

Snackbar.make(getView(),resp.getMessage(), Snackbar.LENGTH_LONG).show();

Replace getView() with an existing view component of your current activity, like this:

将 getView() 替换为当前活动的现有视图组件,如下所示:

Snackbar.make(findViewById(R.id. chat),resp.getMessage(), Snackbar.LENGTH_LONG).show();

回答by Liliana J.

To solve this Exception, you can do this.

要解决此异常,您可以这样做。

 private void CrearSnackBar(String mensaje)
{
    Snackbar snackbar = Snackbar
            .make(constraintLayout, mensaje, Snackbar.LENGTH_LONG)
            .setActionTextColor(getResources().getColor(R.color.colorWhite))
            .setAction(getResources().getString(R.string.label_settings), new View.OnClickListener() {
                @Override
                public void onClick(View view) {
                    Intent myIntent = new Intent(Settings.ACTION_APPLICATION_DETAILS_SETTINGS);
                    startActivity(myIntent);
                }
            });


    View sbView = snackbar.getView();
    snackbar.show();
}

Where constraintLayout is the layout parent where I want to show the message, declare the layout:

其中constraintLayout 是我要显示消息的布局父级,声明布局:

ConstraintLayout constraintLayout;

约束布局约束布局;

And find it by Id.

并通过 Id 找到它。

constraintLayout = findViewById(R.id.cl_layout);

约束布局 = findViewById(R.id.cl_layout);

The function works for me. I hope it could help you.

该功能对我有用。我希望它能帮助你。