web-dev-qa-db-ja.com

java.lang.IllegalArgumentException:指定されたビューから適切な親が見つかりませんでした。有効なビューを提供してください

サーバーメッセージを表示しようとするとアプリがクラッシュし、問題は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

  <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>

以下は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$3.onResponse(RegisterActivity.Java:143)
                                                              at retrofit2.ExecutorCallAdapterFactory$ExecutorCallbackCall$1$1.run(ExecutorCallAdapterFactory.Java:68)
                                                              at Android.os.Handler.handleCallback(Handler.Java:739)
                                                              at Android.os.Handler.dispatchMessage(Handler.Java:95)
9
Mani

findViewById(Android.R.id.content)を試してみることをお勧めします。

これは私のためにトリックをしたものです:

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

Android.R.id.contentは、ビューのルート要素を提供します(詳細については、 Android:Android.R.id.contentの用途は? を確認してください)。

13
Normando

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>
1
Anu Martin

ビューをこれに置き換えます

getActivity().getCurrentFocus()

ただし、デフォルトのフラグメントには含まれません

1
Ashutosh Tiwari

一般的な解決策を探している他の人を助けるかもしれない解決策を見つけました。

XMLファイル全体を読み込む前にSnackbarでメッセージを表示しようとすると、このエラーが発生しました。

フラグメントでは、次のようにonCreateView();でAPIを呼び出し、_Internet connection is off_のSnackbarメッセージを表示しようとしました。

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

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

    getData();

    return mBindingObject.getRoot();
}
_

そのメソッドをonViewCreated()に入れるだけです

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

    getData();
}
_

今私のために働いています。

ボーナス:

正常にロードされた後は、常にビューを使用してみてください。 1行のすべての位置が重要です。

ありがとうございました。

0
Pratik Butani

これの代わりに :

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

次のように、getView()を現在のアクティビティの既存のビューコンポーネントに置き換えます。

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

invalid view引数をSnackbarに渡します。したがって、RegisterActivity BaseLayout参照を提供する必要があります。 idをactivity_register.xml Linear/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>

次に、このレイアウトを以下のようにスナックバーに渡します

 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();


        }
    });
}
0
OmiK