How to keep drawer menu open after item selection? - android

I have used drawer menu from android.support.v4.widget.DrawerLayout for my xamarin application. Currently when I click each item in the drawer list the drawer layout closes automatically. I don't remember that I have set up anywhere that I want to close the layout after selection! If this is the default behavior please tell me where can I say I want to keep it open after I select an Item?

In the NavigationDrawerFragment class
just comment the line where it closes the drawer after item selection
private void selectItem(int position) {
mCurrentSelectedPosition = position;
if (mDrawerListView != null) {
mDrawerListView.setItemChecked(position, true);
}
if (mDrawerLayout != null) {
//mDrawerLayout.closeDrawer(mFragmentContainerView);
}
if (mCallbacks != null) {
mCallbacks.onNavigationDrawerItemSelected(position);
}
}

Related

How to check if Up button enabled?

Some where in code I add
ActionBar ab = ((AuthActivity) getActivity()).getSupportActionBar();
if (ab != null) {
ab.hide();
ab.show();
ab.setTitle(R.string.auth_tt_title);
ab.setDisplayHomeAsUpEnabled(true);
}
Later, I add fiew fragments one of which may change title and display home button.Thus, I wat to save state for ActionBar before I made changes, to be able to restore it asfter fragment will be gone.
I can get title as
private String getAbStatus(AppCompatActivity activity) {
String title="";
boolean visible;
ActionBar ab = activity.getSupportActionBar();
if (ab != null) {
if (ab.getTitle() != null) title = ab.getTitle().toString();
}
return title;
}
But how can I get state of HomeAsUp?
Short answer:
if (ab.getDisplayOptions() & ActionBar.DISPLAY_HOME_AS_UP != 0) {}
Long answer here: How do I get ActionBar attribute in my class

How to use searchView.setIconified(false) method without showing the softkeyboard at the same time

I'm using this method to show opened searchview at the start of activity.
As I'm using few fragments in activity I'm calling this method in onPrepareOptionsMenu callback. Behavior I was going for was, show opened searchView and softkeyboard at the start of activity, user would search for something and clicking on ListView items would show particular fragment.
But when user closes all fragments and comes back to the search results in the activity this method is triggered again to open searchView. What really bugs me here is that at the same time softkeyboard is showed also overlapping search results.
Is there a way to open searchView without showing softkeyboard?
#Override
public boolean onPrepareOptionsMenu(Menu menu) {
if(MyApp.fragments.size() == 0) {
searchView.setIconified(false);
title.setText("");
if(menu.findItem(R.id.ma_search) != null) menu.findItem(R.id.ma_search).setVisible(true);
}else if(MyApp.fragments.get(MyApp.fragments.size()-1) instanceof Fragment1){
title.setText("Title1");
if(menu.findItem(R.id.ma_search) != null) menu.findItem(R.id.ma_search).setVisible(false);
}else if(MyApp.fragments.get(MyApp.fragments.size()-1) instanceof Fragment2){
title.setText("Title2");
if(menu.findItem(R.id.ma_search) != null) menu.findItem(R.id.ma_search).setVisible(false);
}else if(MyApp.fragments.get(MyApp.fragments.size()-1) instanceof Fragment3){
title.setText("Title3");
if(menu.findItem(R.id.ma_search) != null) menu.findItem(R.id.ma_search).setVisible(false);
}else if(MyApp.fragments.get(MyApp.fragments.size()-1) instanceof Fragment4){
title.setText("Title4");
if(menu.findItem(R.id.ma_search) != null) menu.findItem(R.id.ma_search).setVisible(false);
}
return true;
}

How do I close a navigation drawer after an item is selected?

I have implemented a navigation drawer and everything functions properly. The navigation drawer contains a listview and when an item is selected, the main fragment is replaced properly.
This is the onClickListener code:
mDrawerListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
HeaderViewListAdapter headerView = (HeaderViewListAdapter) parent.getAdapter();
AccountAdapter adapter = (AccountAdapter) headerView.getWrappedAdapter();
Cursor cursor = adapter.getCursor();
if(cursor != null && cursor.moveToPosition(position)){
((NavigationDrawerCallbacks) getActivity()).onNavigationDrawerItemSelected(cursor.getLong(cursor.getColumnIndex(ID_COLUMN)));
}
}
});
And in my activity, the onNavigationDrawerItemSelected method is like this:
#Override
public void onNavigationDrawerItemSelected(long accountId) {
// update the main content by replacing fragments
FragmentManager fragmentManager = getSupportFragmentManager();
fragmentManager.beginTransaction()
.replace(R.id.mainFragment, AccountDetailFragment.newInstance(accountId))
.commit();
}
As I said, this functions, but the navigation drawer remains open. It's a hassle for the user to have to select an account from the listview and then have to close the drawer to see the main fragment, so how can I have it close automatically, so that when an item is selected the only visible element is the main fragment (and everything inside of it)?
Call closeDrawer() on the DrawerLayout object with either the Drawer View, or the Drawer's Gravity as an argument.
You need to call the closeDrawer inside the onItemClick, when the Drawer Layout is not null.
if (mDrawerLayout != null) {
mDrawerLayout.closeDrawer(mFragmentContainerView);
}

Up navigation not appearing for single activity app with multiple fragments

I have an android application that has a single main activity that employs many fragments that switch into view. I'm not sure if that's the right way to do it, but I have inherited this project and would like to avoid doing any major refactors like changing the fragments to all be activities or something like that.
According to the android documentation, it looks like calling the setDisplayHomeAsUp(bool) function should just display the up button by default:
Set whether home should be displayed as an "up" affordance. Set this
to true if selecting "home" returns up by a single level in your UI
rather than back to the top level or front page.
The main issue is that when I use the function:
actionBar.setDisplayHomeAsUpEnabled(true);
It does not set the button that opens the navigation drawer to instead turn into an 'Up' button. It just removes the 'hamburger' ic_drawer icon from the side. The navigation drawer still opens.
Here is the custom code for the NavigationDrawerFragment (I copy+pasted the exact file that you get when you create a new application with a navigation drawer within android studio):
NavigationDrawerFragment.java
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
mDrawerListView = (ListView) inflater.inflate(
R.layout.fragment_navigation_drawer, container, false);
mDrawerListView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
selectItem(position);
}
});
PopulateAppDrawerList();
return mDrawerListView;
}
public void PopulateAppDrawerList() {
List<AppOption> allApps = getAllApps();
List<AppOption> filteredApps = new ArrayList<AppOption>();
for (int i = 0; i < allApps.size(); i++) {
if (allApps.get(i).getLaunchable()) {
filteredApps.add(allApps.get(i));
}
}
NavDrawerListAdapter adapter = new NavDrawerListAdapter(filteredApps, MainActivity.getInstance());
mDrawerListView.setAdapter(adapter);
mDrawerListView.setItemChecked(mCurrentSelectedPosition, true);
}
Then, I have the other fragments that all extend 'BaseAppFragment', which contains the following:
BaseAppFragment.java
public class BaseAppFragment extends Fragment {
#Override
public void onStart() {
super.onStart();
MainActivity.getInstance().onSectionAttached(this);
}
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
} }
This is what allows me to change the title on the action bar in one single area and set whether or not it should have the back button set by default.
MainActivity.java
public void onSectionAttached(android.app.Fragment fragment) {
Class fragmentType = fragment.getClass();
ActionBar actionBar = getActionBar();
mNavigationDrawerFragment.PopulateAppDrawerList();
if (fragmentType != null) {
if (fragmentType.equals(AuthenticationFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(false);
mTitle = "Login";
} else if (fragmentType.equals(MyOptionsFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(false);
mTitle = "My Options";
} else if (fragmentType.equals(GLAuthenticationFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(false);
mTitle = "Login";
} else if (fragmentType.equals(InitialLoginFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(false);
mTitle = "Login";
} else if (fragmentType.equals(LoginFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(false);
mTitle = "Login";
} else if (fragmentType.equals(DailyOverviewFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(true);
mTitle = "Overview";
} else if (fragmentType.equals(SingleComponentFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(true);
SingleComponentFragment singleComponentFragment = (SingleComponentFragment) fragment;
if (singleComponentFragment != null && singleComponentFragment .mComponent != null) {
mTitle = String.format("Back To Day %s", singleComponentFragment.mComponent.getDay() + "");
}
else {
mTitle = "";
}
} else if (fragmentType.equals(singleDayOverviewFragment.class)) {
actionBar.setDisplayHomeAsUpEnabled(true);
mTitle = "Back To Overview";
}
}
actionBar.setTitle(mTitle);
}
The title setting works perfectly and there are no errors when the setDisplayHomeAsUpEnabled(true) is called, but it still shows no Up button. I know that right now I am not setting any type of fragment navigation hierarchy other than the addToBackStack(null) call in the Fragment Transaction, but it still seems like this code should be enough to have the up button replace the navigation drawer button.
The problem is that the navigation drawer icon hijacks the up indicator. In terms of which View in the action bar is displaying the icon, the navigation drawer icon is also the up icon. This is why you need to call actionBar.setDisplayHomeAsUpEnabled(true); for the navigation drawer icon to show.
To fix this, you need to use ActionBarDrawerToggle#setDrawerIndicatorEnabled(false). This will replace the navigation drawer icon with the up icon. From the documentation for this method:
When the indicator is disabled, the ActionBar will revert to displaying the home-as-up indicator provided by the Activity's theme in the android.R.attr.homeAsUpIndicator attribute instead of the animated drawer glyph.
Had the same problem as you, and I struggled getting a consistent Up arrow behaviour. I made this example to show how to properly do it when using a single activity with navigation drawer and multiple levels.
https://github.com/tskulbru/android-navdrawer-up-pattern-example

Android refresh actionbar and title on fragment change

in my app i am developing an activity using the actionbar in NAVIGATION_MODE_TABS-mode.
Each tab is showing a fragment (list, detail).
Initially the list-tab is visibile.
The list is implementing setMultiChoicheModeListener() and modifies the ActionBar and the title of the activity if one or more items are selected.
How can i reset the title and the ActionBar to the inital value (title and actions) when the user clicks on the detail-tab without deselecting the items?
BTW Target-Platform is > 4.1 and i am not using the support library.
Thanks.
public class MyActivity extends Activity {
#Override
protected void onCreate (Bundle savedInstanceState) {
this.actionBar = getActionBar();
this.actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
....
for (Tab tab : getTabs())
{
//here are two tabs added (List and Detail)
this.actionBar.addTab(tab);
}
....
}
protected class NavigationTabListener implements ActionBar.TabListener {
private Fragment fragment;
....
public void onTabSelected(Tab tab, FragmentTransaction ft) {
ft.replace(newFragmentResourceId, this.fragment);
}
}
}
public class MyListViewFragment extends LinearLayout implements IListViewFragment {
....
#Override
public void initialize() {
inflate(getContext(), listLayoutResourceId, this);
this.myList.setChoiceMode(AbsListView.CHOICE_MODE_MULTIPLE_MODAL);
this.myList.setMultiChoiceModeListener(new MultiChoiceModeListener() {
....
#Override
public boolean onCreateActionMode(ActionMode mode, Menu menu)
{
MenuInflater inflater = mode.getMenuInflater();
inflater.inflate(selectedItemsMenuResourceId, menu);
return true;
}
public void onItemCheckedStateChanged(ActionMode mode, int position, long id, boolean checked)
{
if (checked)
{
this.numberItemsSelected++;
adapter.setNewSelection(position);
}
else
{
this.numberItemsSelected--;
adapter.removeSelection(position);
}
mode.setTitle(getContext().getResources().getQuantityString(
R.plurals.items_selected, this.numberItemsSelected,
Integer.valueOf(this.numberItemsSelected)));
}
....
}
}
I am trying to implement the MVP pattern, but it's still in evaluation phase. The Activity acts as the presenter, the views are in separate classes.
For each Fragment i am also implementing the MVP apttern, but i think this is not interesting to solve the problem.
Some notes to the classes:
MyActivity creates two fragments (one for List, one for Detail view, the detail view has nothing to do with the selected items).
The initial view of the activity is the fragment with the list.
If the user selects some entries I am updating the action bar and the title through the callback of MultiChoiceModeListener.
But the user can now change the fragment by clicking on the "Detail" tab without deselecting the items or clicking to the new elements in the action bar, the result is that the detail fragment is shown, but the title of the activity is still the one I modified in the MultiChoiceModeListener, and there is also the check mark of the action bar visible (auto created by the system).
So the best way is I think to get somehow the current ActionMode, so I can invoke finish() to "reset" the ActionBar and the title.
Make sure you keep reference of the ActionMode in the ActionMode.Callback methods inside your activity which has the ActionBar.TabListener.
When a new tab is selected just finish the action mode, like:
public void onTabSelected(Tab tab, FragmentTransaction ft) {
if(mActionMode != null){
mActionMode.finish();
}
ft.replace(newFragmentResourceId, this.fragment);
}
Make the ActionMode reference back to null when onDestroyActionMode(ActionMode) is called.

Categories

Resources