I m using drawer list for my android application.
Got a issue.
When I click randomly (very fast) then I get forcestop and java.lang.IllegalStateException: Content view not yet created showing in Log.
I m using fragments
I m also getting the following Runtime error
at android.support.v4.app.ListFragment.ensureList(ListFragment.java:32
Here is a part of my code in selecting from drawer list and
Fragment home = new Home();
Fragment feeds = new Feeds_ListView();
.....
private void selectItem(int position)
{
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
switch (position)
{
case 0:
setTitle(title[position]);
ft.replace(R.id.content_frame, feeds);
break;
case 1:
setTitle(title[position]);
ft.replace(R.id.content_frame, NewPostFragment);
break;
case 2:
setTitle(title[position]);
ft.replace(R.id.content_frame, SearchDetailsFragment);
break;
case 3:
setTitle(title[position]);
ft.replace(R.id.content_frame, feeds1);
break;
case 4:
setTitle(title[position]);
ft.replace(R.id.content_frame, UserDetailsFragment);
break;
case 5:
setTitle(title[position]);
ft.replace(R.id.content_frame, FBActivity);
break;
}
ft.commit();
mDrawerList.setItemChecked(position, true);
setTitle(title[position]);
mDrawerLayout.closeDrawer(mDrawerList);
}
#Override
protected void onPostCreate(Bundle savedInstanceState)
{
super.onPostCreate(savedInstanceState);
mDrawerToggle.syncState();
}
#Override
public void onConfigurationChanged(Configuration newConfig)
{
super.onConfigurationChanged(newConfig);
mDrawerToggle.onConfigurationChanged(newConfig);
}
#Override
public void setTitle(CharSequence title)
{
mTitle = title;
getSupportActionBar().setTitle(mTitle);
}
Here is the part of Feeds_ListView();
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
{
context=container.getContext();
rootView = inflater.inflate(R.layout.feeds_listview_layout, container, false);
list = (ListView) rootView.findViewById(android.R.id.list);
mRelativeLayout=rootView.findViewById(R.id.mRelativeLayout);
saveProgress =(ProgressBar) rootView.findViewById(R.id.loadpost);
saveProgress.setVisibility(View.INVISIBLE);
userAdapter = new CustomListAdapter(getActivity(), R.layout.feeds_listview_item,userArray);
mRelativeLayout.setVisibility(View.GONE);
list.setItemsCanFocus(false);
list.setAdapter(userAdapter);
return rootView;
}
#Override
public void onActivityCreated(Bundle savedInstanceState)
{
super.onActivityCreated(savedInstanceState);
SharedPreferences settings =getActivity().getSharedPreferences("newdatabase",0);
String user_id=settings.getString("user_id", "--");
if(user_id.equals("--") || user_id.equals(""))
{ FragmentTransaction ft = getActivity().getSupportFragmentManager().beginTransaction();
ft.replace(R.id.content_frame, FBActivity);
ft.commit();
}else{
new Onscrollasync().execute();
((PullToRefresh_Master) getListView()).setOnRefreshListener(new OnRefreshListener()
{
#Override
public void onRefresh()
{
new Onscrollasync().execute();
}
});
}
}
The problem is with the code in the Fragment Home that you wrote in the onCreateView. Move the code in your onCreateView() to either onActivityCreated() or onViewCreated(). There are several similar question on StackOverlfow like here.
Try this instead of inflating a container,try to inflate your view without the container ie
rootView = inflater.inflate(R.layout.feeds_listview_layout,null);
Let me know if this works.
Related
Suppose I have a MainActivity with FragmentContainerView.
This FragmentContainerView's size matches the MainActivity.
Then I want to show one fragment at a time in this FragmentContainerView.
Fragment1, Fragment2, and Fragment3.
Each fragment will have one button. When button is pressed, next fragment is loaded.
Fragment1 (Press button)--> Fragment2 (Press button)--> Fragment3 (Press button)--> Fragment1 --> and so on.
So far, I was able to implement, but I am not sure how to make my fragments such that, when I press the back button,
Fragment1 should exit app
Fragment2 should load Fragment1
Fragment3 should load Fragment2
Here is my MainActivity
public class MainActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
FirstFragment fragment = new FirstFragment();
Bundle bundle = new Bundle();
bundle.putString("CLASS_NAME", " ");
fragment.setArguments(bundle);
getSupportFragmentManager().beginTransaction()
.add(R.id.fragment_container_view, fragment, null)
.commit();
}
}
Here is my Fragment1
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
binding = FragmentFirstBinding.bind(getView());
String previous_class = getArguments().getString("CLASS_NAME");
if(!previous_class.equals(" ")){
binding.textViewFirstFragment.setText(previous_class);
}
//On button click, navigate to MainActivity
binding.buttonFirstFragment.setOnClickListener(this);
}
#Override
public void onClick(View v) {
//Log.i("BACKSTACK", "debug: current status of fragment back stack " + getFragmentManager().getBackStackEntryCount());
Fragment fragment = new SecondFragment();
putBundleArgument(fragment);
replaceFragment(fragment);
debug();
}
public void replaceFragment(Fragment fragment) {
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.replace(R.id.fragment_container_view, fragment);
transaction.addToBackStack(null);
transaction.commit();
}
Here is my Fragment2
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
binding = FragmentSecondBinding.bind(getView());
String previous_class = getArguments().getString("CLASS_NAME");
binding.textViewSecondFragment.setText(previous_class);
//On button click, navigate to MainActivity
binding.buttonSecondFragment.setOnClickListener(this);
}
#Override
public void onClick(View v) {
//Log.i("BACKSTACK", "debug: current status of fragment back stack " + getFragmentManager().getBackStackEntryCount());
Fragment fragment = new ThirdFragment();
putBundleArgument(fragment);
replaceFragment(fragment);
debug();
}
public void replaceFragment(Fragment fragment) {
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.replace(R.id.fragment_container_view, fragment);
transaction.addToBackStack(null);
transaction.commit();
}
Lastly, here is my Fragment3
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
binding = FragmentThirdBinding.bind(getView());
String previous_class = getArguments().getString("CLASS_NAME");
binding.textViewThirdFragment.setText(previous_class);
//On button click, navigate to MainActivity
binding.buttonThirdFragment.setOnClickListener(this);
}
#Override
public void onClick(View v) {
Fragment fragment = new FirstFragment();
putBundleArgument(fragment);
replaceFragment(fragment);
debug();
}
public void replaceFragment(Fragment fragment) {
FragmentTransaction transaction = getFragmentManager().beginTransaction();
/*
ThirdFragment fragment3 = new ThirdFragment();
transaction.remove(fragment3);
SecondFragment fragment2 = new SecondFragment();
transaction.remove(fragment2);
*/
getFragmentManager().popBackStack();
getFragmentManager().popBackStack();
getFragmentManager().popBackStack();
transaction.replace(R.id.fragment_container_view, fragment);
transaction.addToBackStack(null);
transaction.commit();
}
#Override // override this in MainActivity
public void onBackPressed(){
int count = getSupportFragmentManager().getBackStackEntryCount();
if(count == 1)//When there is only 1 fragment left in the stack ie Fragment 1.
finsh();
else
getSupportFragmentManager().popBackStack(); //Fragment 2 and 3 are popped here.
super.onBackPressed();
}
public class HomeFragment extends Fragment {
BottomNavigationView bottomNavigationView;
FragmentManager manager = getFragmentManager() ;
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_home,container,false);
}
#Override
public void onStart() {
super.onStart();
bottomNavigationView = bottomNavigationView.findViewById(R.id.bottom_navigation);
bottomNavigationView.setOnNavigationItemSelectedListener(navListener);
}
private BottomNavigationView.OnNavigationItemSelectedListener navListener=
new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem menuItem) {
Fragment selectedFragment = null;
switch (menuItem.getItemId()){
case R.id.nav_home1 :
selectedFragment = new Home1Fragment();
break;
case R.id.nav_favourites :
selectedFragment = new FavouriteFragment();
break;
case R.id.nav_search:
selectedFragment = new SearchFragment();
break;
}
manager.beginTransaction().replace(R.id.fragment_container,selectedFragment).commit();
return true;
}
};
}
No error shown but the fragment isn't opening
add container framelayout to your parent fragment then on every click set fragment using this :
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.replace(R.id.parent_fragment_container, new ParentFragment());
ft.commit();
your code will look like :
public class HomeFragment extends Fragment {
BottomNavigationView bottomNavigationView;
FragmentManager manager = getFragmentManager() ;
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_home,container,false);
}
private void setFragment(Fragment fragment){
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.replace(R.id.parent_fragment_container,fragment);
ft.commit();
}
#Override
public void onStart() {
super.onStart();
bottomNavigationView = bottomNavigationView.findViewById(R.id.bottom_navigation);
bottomNavigationView.setOnNavigationItemSelectedListener(navListener);
}
private BottomNavigationView.OnNavigationItemSelectedListener navListener=
new BottomNavigationView.OnNavigationItemSelectedListener() {
#Override
public boolean onNavigationItemSelected(#NonNull MenuItem menuItem) {
Fragment selectedFragment = null;
switch (menuItem.getItemId()){
case R.id.nav_home1 :
selectedFragment = new Home1Fragment();
setFragment(selectedFragment);
break;
case R.id.nav_favourites :
selectedFragment = new FavouriteFragment();
break;
case R.id.nav_search:
selectedFragment = new SearchFragment();
break;
}
manager.beginTransaction().replace(R.id.fragment_container,selectedFragment).commit();
return true;
}
};
}
I have a fragment like this
...
public class Dashboard extends Fragment{
private RecyclerView mTopSellersListView;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.main_dashboard, container, false);
mTopSellersListView = (RecyclerView) view.findViewById(R.id.topSellersListView);
return view;
}
public void setTopSellersListView(MyRecycleAdapter adapter){
mTopSellersListView.setHasFixedSize(true);
mTopSellersListView.setAdapter(adapter);
mTopSellersListView.setLayoutManager(new LinearLayoutManager(getActivity()));
mTopSellersListView.addItemDecoration(new DividerItemDecoration(getActivity(), LinearLayoutManager.VERTICAL));
mTopSellersListView.setItemAnimator(new DefaultItemAnimator());
}
}
I have total 4 fragment, all of them can be switch in MainActivity by a bottombar used this method, when user tap on menu, it will replace current fragment with another one (Default: Dashboard):
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mDashboardFragment = new Dashboard();
mOrdersFragment = new Orders();
mProductsFragment = new Products();
mSettingFragment = new Setting();
settingMenu(savedInstanceState);
}
...
public void selectMenu(String menu){
Fragment fr = null;
switch (menu) {
case "Dashboard":
fr = mDashboardFragment;
break;
case "Orders":
fr = mOrdersFragment;
break;
case "Products":
fr = mProductsFragment;
break;
case "Setting":
fr = mSettingFragment;
break;
}
FragmentManager fm = getFragmentManager();
FragmentTransaction fragmentTransaction = fm.beginTransaction();
fragmentTransaction.replace(R.id.fragment, fr);
fragmentTransaction.addToBackStack(null);
fragmentTransaction.commit();
}
I access the setTopSellersListView() in another class (not activity class)
MainActivity.mDashboardFragment.setTopSellersListView(mProductAdapter);
and got NullPointerExceptions at mTopSellersListView.setHasFixedSize(true)
First set your layoutManager than use setHasFizedSize(true).Since the layoutManager determines the size of your recyclerView.
I've fixed it by call setTopSellersListView() in onStart() in Fragment and it works great
I have a floating button in one of my fragments.On click of which an
activity pops up.Now the problem is when I go back from the activity
to the fragment the fragment does not auto refresh.Also I want it to
refresh on back pressed.
Within the fragment I have a refresh button in the action bar on
pressed of which I call a refreshFragment() method.Is there a way in
android that I can call a method from a fragment from within an
activity.
This is my refreshFragment() method code.
public void refreshFragment()
{
Fragment fragment = new BillingFragment();
android.support.v4.app.FragmentManager fragmentMg = getActivity().getSupportFragmentManager();
FragmentTransaction fragmentTrans = fragmentMg.beginTransaction();
fragmentTrans.replace(R.id.container_body, fragment, "TABBILLING");
fragmentTrans.addToBackStack(null);
fragmentTrans.commit();
((AppCompatActivity) getActivity()).getSupportActionBar().setTitle("Billing");
//adapter.notifyDataSetChanged();
}
And I call it inside my on create view method as follows :-
((MainActivity)getActivity()).setFragmentRefreshListener(new MainActivity.FragmentRefreshListener()
{
#Override
public void onRefresh() {
refreshFragment();
}
});
I even tried calling displayView() method of my main activity from
another activity by creating an object of MainActivity as follows:-
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case android.R.id.home:
super.onBackPressed();
MainActivity main = new MainActivity();
main.displayView(1);
count = 0;
return true;
But it gave me a null pointer exception.This is my displayView() method.
public void onDrawerItemSelected(View view, int position) {
displayView(position);
}
public void displayView(int position) {
Fragment fragment = null;
String title = getString(R.string.app_name);
switch (position) {
case 0:
fragment = new HomeFragment();
title = getString(R.string.title_home);
break;
case 1:
fragment = new BillingFragment();
title =getString(R.string.title_billing);
break;
case 2:
fragment = new StockViewFragment();
title =getString(R.string.title_stockview);
break;
case 3:
fragment = new BhishiManagementFragment();
title= getString(R.string.title_bhishiview);
break;
case 4:
fragment = new ReportingFragment();
title=getString(R.string.title_reporting);
break;
case 5:
fragment = new VendorManagementFragment();
title=getString(R.string.title_vendormanagement);
break;
case 6:
fragment = new CustomerMgmt();
title = getString(R.string.title_custmgmt);
break;
default:
break;
}
Any help is appreciated.Thank you :)
I assume you are trying to refresh fragment when coming back from an activity (that activity does not hosting the fragment which needs to be refreshed), if my assumption is correct please try the below approach, incase not please clarify the question with more info.
Try : Have a boolean variable in fragment and update its value true or false based on fragment visible state using its lifecycle methods.
public class SampleFragment extends Fragment {
private boolean shouldRefreshOnResume = false;
public static SampleFragment newInstance() {
SampleFragment fragment = new SampleFragment();
return fragment;
}
public SampleFragment() {
// Required empty public constructor
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater,
ViewGroup container,
Bundle savedInstanceState) {
return inflater.inflate(R.layout.fragment_blank,
container, false);
}
#Override
public void onResume() {
super.onResume();
// Check should we need to refresh the fragment
if(shouldRefreshOnResume){
// refresh fragment
}
}
#Override
public void onStop() {
super.onStop();
shouldRefreshOnResume = true;
}
}
in an application , I wish I would pass a string fragment and display it in a toast.
The problem is with my code, the creation of the fragment I have a toast that appears, but empty ...
I do not understand where did my problem ( it's the first time I try to do that )
My code :
MainActivity :
public class MainActivity extends ActionBarActivity
implements NavigationDrawerCallbacks {
private NavigationDrawerFragment mNavigationDrawerFragment;
private Toolbar mToolbar;
private CharSequence mUrl;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mToolbar = (Toolbar) findViewById(R.id.toolbar_actionbar);
setSupportActionBar(mToolbar);
mNavigationDrawerFragment = (NavigationDrawerFragment)
getFragmentManager().findFragmentById(R.id.fragment_drawer);
// Set up the drawer.
mNavigationDrawerFragment.setup(R.id.fragment_drawer, (DrawerLayout) findViewById(R.id.drawer), mToolbar);
}
#Override
public void onNavigationDrawerItemSelected(int position) {
Fragment objFragment = null;
switch (position) {
case 0:
Intent intent = new Intent(MainActivity.this, fragment_test.class);
intent.putExtra("message", "test");
objFragment = new fragment_test();
break;
case 1:
objFragment = new menu2_Fragment();
break;
case 2:
objFragment = new menu3_Fragment();
break;
case 3:
objFragment = new menu4_Fragment();
break;
case 4:
objFragment = new menu5_Fragment();
break;
case 5:
objFragment = new menu6_Fragment();
break;
case 6:
objFragment = new menu8_Fragment();
break;
case 7:
objFragment = new menu9_Fragment();
break;
case 8:
objFragment = new menu7_Fragment();
break;
}
FragmentManager fragmentManager = getFragmentManager();
fragmentManager.beginTransaction()
.replace(R.id.container, objFragment)
.commit();
}
#Override
public void onBackPressed() {
if (mNavigationDrawerFragment.isDrawerOpen())
mNavigationDrawerFragment.closeDrawer();
else
super.onBackPressed();
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
if (!mNavigationDrawerFragment.isDrawerOpen()) {
// Only show items in the action bar relevant to this screen
// if the drawer is not showing. Otherwise, let the drawer
// decide what to show in the action bar.
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
return super.onCreateOptionsMenu(menu);
}
/*#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
return super.onOptionsItemSelected(item);
}*/}
Fragment_test :
public class fragment_test extends Fragment {
View rootview;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
rootview = inflater.inflate(R.layout.xml1, container, false);
Intent intent = getActivity().getIntent();
String message = intent.getStringExtra("message");
Toast toast = Toast.makeText(getActivity(), message, Toast.LENGTH_LONG);
toast.show();
return rootview;
}}
thx in advance
ps : sorry for my english french
Your code
FragmentManager fragmentManager = getFragmentManager();
fragmentManager.beginTransaction().replace(R.id.container, objFragment).commit();
Replace with
FragmentManager fragmentManager = getFragmentManager();
fragmentManager.beginTransaction().replace(R.id.container, objFragment).commit();
Bundle bundle = new Bundle();
bundle.putString(key, value);
objFragment.setArguments(bundle);
Write below code in your another activity
if (getArguments() != null)
{
m_searchText = getArguments().getString(Key);
}