my app crashes when trying to display server message and I think the problem could be with my getView()
. below is the registerActivity
were the crash occurs and my 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>
below is logcat message
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)
I suggest that you to try with 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.content
will give you the root element of the view (for more information on that, please check Android: What is android.R.id.content used for?).
Replace your View with this
getActivity().getCurrentFocus()
.
but not in your Default Fragment
Wrap your layout with 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>
You are passing invalid
view argument to Snackbar. so you've to give RegisterActivity BaseLayout reference to it.
you should try declare id to activity_register.xml
Linear / Relative or whatever you design.
<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();
}
});
}
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:
Snackbar.make(findViewById(R.id. chat),resp.getMessage(), Snackbar.LENGTH_LONG).show();
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 Snackbar before loading our whole XML file.
In fragment I have tried to call API in onCreateView();
and showing Snackbar
message of Internet connection is off
as below:
@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()
@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.
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;
And find it by Id.
constraintLayout = findViewById(R.id.cl_layout);
The function works for me. I hope it could help you.
来源:https://stackoverflow.com/questions/47666685/java-lang-illegalargumentexception-no-suitable-parent-found-from-the-given-view