问题
I wanted navigation drawer in all my activities.So i used a BaseActivity for Navigation drawer and extended other activities from base activity.Base activity has Navigation drawers. Dashboard activity is extending base activity but it raises exception when i try to use butterknife to bind views saying
java.lang.IllegalStateException: Required view 'dashboard_frameLayout' with ID 2131558517 for field 'frameLayout' was not found.
here are the relevant files
BaseActivity.java
public class BaseActivity extends AppCompatActivity {
@BindView(R.id.toolbar) Toolbar toolbar;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_base);
ButterKnife.bind(this);
//set toolbar and both Navigation Drawer
}
DashboardActivity.java
public class DashBoardActivity extends BaseActivity {
@BindView(R.id.dashboard_frameLayout)
FrameLayout frameLayout;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
View view = getLayoutInflater().inflate(R.layout.activity_dashboard,frameLayout);
ButterKnife.bind(this,view);
init();
}
private void init() {
Fragment fragment = getSupportFragmentManager().findFragmentById(R.id.dashboard_frameLayout);
if(fragment != null){
Utils.getInstance().addFragment(this,new Fragment_Dashboard(),R.id.dashboard_frameLayout);
}
}
}
activity_dashboard.xml
<FrameLayout
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/dashboard_frameLayout"
android:layout_height="match_parent"
android:layout_width="match_parent"
app:layout_behavior="@string/appbar_scrolling_view_behavior" />
why the framelayout was not found in dashboard activity?
回答1:
My wrong I didn't check the question carefully.
Edited:
In your example you have bound the views twice. One in BaseActivity and the other in DashBoardActivity.
- No need to do that in BaseActivity. But make sure you have a toolbar with id R.id.toolbar in sub-class activities.
No need to inflate layout R.layout.activity_dashboard, you've done that in setContentView. It should be like this:
@Override protected void onCreate(@Nullable Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_dashboard); ButterKnife.bind(this); init(); }
After you trigger ButterKnife.bind(this), the frameLayout is ready for use. Make sure framelayout id dashboard_frameLayout
exists in your activity layout file.
回答2:
In your case "ButterKnife.bind(this)" (from onCreate() of BaseActivity) is being called before OnCreate() of DashBoardActivity. So when ButterKnife try's to bind the views of activity_base, it is not able to find the view id R.id.dashboard_frameLayout in activity_base layout, that throws the exception.
To bind the view one should add a container like view group such as RelativeLayout to activity_base. Create a addViews() method in BaseActivity. Then add the view activity_dashboard layout to that container from onCreate() of DashBoardActivity by calling addViews() of Baseactivity. Now you can add "ButterKnife.bind(this)" to addViews() method (and you should not call ButterKnife.bind anywhere else in both activity). One thing to note here you have to get the view id reference of container in BaseActivity simply by using findViewById, remaining views will get bind by ButterKnife.
回答3:
I did something similar in my code.
My goal is to have a base drawer activity with one drawer that i reuse in different activities, so i want to be able to use activity_base_drawer
layout in all activities, but change the content by inflating new views into it.
in my base activity (which is a nav drawer activity) i have this protected method
protected void inflateContent(@LayoutRes int inflatedResID){
setContentView(R.layout.activity_base_drawer);
LinearLayout contentContainer = ButterKnife.findById(this, R.id.content_container);
getLayoutInflater().inflate(inflatedResID, contentContainer);
ButterKnife.bind(this);
setSupportActionBar(toolbar);
setupNavDrawer();
}
I send the base nav drawer layout to setContentView()
which has a linear layout that is the container that i want to inflate new layouts into it for each activity that extends my base activtiy
As you can see, LinearLayout contentContainer
is using findById
not @BindView
. I have to do it this way because I need to inflate a view into the content container before i call ButterKnife.bind(this);
After finding the content container layout I inflate a view into it using getLayoutInflater().inflate(inflatedResID, contentContainer);
Then I call ButterKnife.bind(this);
Finally, I do some setup methods that depend on layouts that are being bound using @BindView
in the base activity class.
and in any extending activity the onCreate() looks like this, where i send the ID of the layout I want to inflate to inflateContent()
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
inflateContent(R.layout.content_main);
}
来源:https://stackoverflow.com/questions/40583239/androiduse-butterknife-in-activity-extending-from-another-activity