I have this scenario:
I have a activity, lets call itAcitivty1 with
#Override
public boolean onCreateOptionsMenu(Menu menu) {
return false;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
return false;
}
I open a fragment from Activity1 lets call it Fragment1 with:
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
setHasOptionsMenu(true);
View view = inflater.inflate(R.layout.layout, container, false);
return view;
}
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
if (menu != null){
menu.clear();
}
if (!boolean) {
inflater.inflate(R.menu.menu1, menu);
} else {
inflater.inflate(R.menu.menu2, menu);
}
}
This fragment will be called again from activity as a new instance.
Based on the boolean in onCreateOptionsMenu() I'm deciding what menu should be loaded in the fragment so, during the second instance if I click on a menu item, I see the objects of first instance fragment.
I have no clue, why is this happening?
How is the workflow for displaying menu options...
if (menu != null){
menu.clear();
}
That piece of code might be the root cause.
You're telling the system to clear the menu if it's null. Well, FYI, the menu will never be null in the first place; it is supplied by the system. It might have no items inside, but it'll never be null.
One way to check if a menu already contains an item (or more) is to call hasVisibleItems().
From the documentations:
public abstract boolean hasVisibleItems()
Returns True if there is one or more item visible, else false.
Therefore, this is how you should do it:
if (menu.hasVisibleItems()){
menu.clear();
}
In a case like this, you need to put the menu in activity and update the menu dynamically in onPrepareOptionsMenu()
You need to inflate menu in onCreateOptionsMenu(..) of your Activity1 and need to make return true to display menu.
#Override
public boolean onCreateOptionsMenu(Menu menu) {
//Your code here
getMenuInflater().inflate(R.menu.main1, menu);//My menu
return true;
}
After that you get menu in your fragment also.
Edits:
If you use single menu file and show / hide MenuItem of your menu. it will solve your problem.
Add all menu in single file.by default all menu items are visible false using android:visible="false"
See example code:
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
MenuItem item1 = menu.getItem(0);
MenuItem item2 = menu.getItem(1);
MenuItem item3 = menu.getItem(2);
MenuItem item4 = menu.getItem(3);
if(!boolean){
//visible items which you want to show when boolean is false
item1.setVisible(true);
item2.setVisible(true);
}
else
{
//visible items which you want to show when boolean is true
item3.setVisible(true);
item4.setVisible(true);
}
super.onCreateOptionsMenu(menu, inflater);
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if (id == R.id.menuItem1) {
return true;
}
if (id == R.id.menuItem2) {
return true;
}
...
return super.onOptionsItemSelected(item);
}
Related
I have an activity with menu items. Every time when user come to this activity, i want to update the value of textView with some Utility value. This is my code.
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.menu_my2, menu);
return true;
}
#Override
public boolean onPrepareOptionsMenu(Menu menu){
RelativeLayout badgeLayout = (RelativeLayout) menu.findItem(R.id.badge).getActionView();
TextView tv = (TextView) badgeLayout.findViewById(R.id.actionbar_notifcation_textview);
tv.setText(String.valueOf(Utility.ShoppingCartItemCount()));
return true;
}
This is updating the value only once (when launching activity). But when user moves from this activity and come on this activity again, this is not getting updated even value for Utility.ShoppingCartItemCount() is updated.
How to solve this?
Try invalidateOptionsMenu()
This will be call onCreateOptionsMenu(Menu) again.
edit)
I have some code like below
#Override
public boolean onCreateOptionsMenu(Menu menu) {
if (currentPage == 8) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.menu_p, menu);
return true;
} else {
return false;
}
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.purchaseRestore:
// TODO: Restore purchase
return true;
case R.id.purchaseTerm:
// TODO: Show Term by WebView
return true;
default:
return super.onOptionsItemSelected(item);
}
}
When my user click other button, put invalidateOptionsMenu() after currentPage = 8 in Button's OnClickListener. In result, User can show Option Menu.
edit))
invalidateOptionsMenu() will force reload onCreateOptionsMenu and onPrepareOptionsMenu.
If this methods doesn't working for you, try to debug Utility.ShoppingCartItemCount().
I have a TabGroup in my app. How can I have different actions items for each Tab ? I just found an example from here, but it is not enough for me.
Can someone provide some hints or at least a link ?
I'm using SlidingTabLayout, and this is the way i changed the Toolbar icons for each Tab.
I've 3 tabs, each tab got its own fragment, and in each fragment I've created the following:
Tab 1 fragment:
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.tab_1_menu, menu);
}
Tab 2 fragment:
#Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.tab_2_menu, menu);
}
And so on, hope this help .
Full Example with getItemId / Click
#Override
public boolean onCreateOptionsMenu(Menu menu) {
//Set The Menu View
getMenuInflater().inflate(R.menu.main, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
//Menu Items, every fragment menu item
//Must have different ID
if (id == R.id.settings) {
//Do Something here
);
return true;
}
if (id == R.id.About) {
//Do Something here
);
return true;
}
if ( id == R.id.exit)
{
finish();
return true;
}
return super.onOptionsItemSelected(item);
}
So, that´s what I wanna know. How can I set the visibility of the menu programatically in Android?? This is how I have my menu:
public boolean onCreateOptionsMenu(Menu menu){
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.menu, menu);
return true;
}
public boolean onOptionsItemSelected (MenuItem item){
switch (item.getItemId()){
case R.id.menuregistrar:
break;
case R.id.menusalir:
break;
}
return true;
}
But this code is not on the onCreate, so I don´t know how to set one item visible or invisible programmatically (in my case, I want the "menuregistrar" to be invisible once I have registered my application and forever.
Put this method in your Activity
public boolean onPrepareOptionsMenu(Menu menu)
{
MenuItem register = menu.findItem(R.id.menuregistrar);
if(userRegistered)
{
register.setVisible(false);
}
else
{
register.setVisible(true);
}
return true;
}
in shorter version you could write:
MenuItem register = menu.findItem(R.id.menuregistrar);
register.setVisible(!userRegistered); //userRegistered is boolean, pointing if the user has registered or not.
return true;
I would simplify Adil's solution even further with the following:
public boolean onPrepareOptionsMenu(Menu menu)
{
MenuItem registrar = menu.findItem(R.id.menuregistrar);
registrar.setVisible(!isRegistered);
return true;
}
Simply do one thing get the id of the item of menu from this line:
Menu menu =navigationView.getMenu();
MenuItem nav_dashboard = menu.findItem(R.id.nav_dashboard);
and than make it visible it accourding to you by this line:
nav_dashboard.setVisible(true/false);
Menu Object has a property to set the visibility of a menu's item using setVisible(boolean)//
Example
private Menu menu_change_language;
...
...
#Override
public boolean onCreateOptionsMenu(Menu menu) {
...
...
menu_change_language = menu;
...
...
return super.onCreateOptionsMenu(menu);
}
use code below for hiding Menu Item:
if(menu_change_language != null){
menu_change_language.findItem(R.id.menu_change_language)
.setVisible(false);
}
Use public boolean onPrepareOptionsMenu (Menu menu) it is called everytime you press the menu button and do your stuff there. or use your oncreateoptionsmenu() in different activities to inflate different menus - this one is called only once.
Cheers
If you want to change the visibility inside the onOptionsItemSelected whenever you click the menu
#Override
public boolean onOptionsItemSelected(MenuItem item) {
item.setVisible(true);
return true;
}
OR
for item in the menu that you didn't click on
private Menu globalMenuItem;
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu."menu Xml Name", menu);
globalMenuItem = menu;
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
globalMenuItem.findItem(R.id."id of the menu item").setVisible(true);
return true;
}
So, that´s what I wanna know. How can I set the visibility of the menu programatically in Android?? This is how I have my menu:
public boolean onCreateOptionsMenu(Menu menu){
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.menu, menu);
return true;
}
public boolean onOptionsItemSelected (MenuItem item){
switch (item.getItemId()){
case R.id.menuregistrar:
break;
case R.id.menusalir:
break;
}
return true;
}
But this code is not on the onCreate, so I don´t know how to set one item visible or invisible programmatically (in my case, I want the "menuregistrar" to be invisible once I have registered my application and forever.
Put this method in your Activity
public boolean onPrepareOptionsMenu(Menu menu)
{
MenuItem register = menu.findItem(R.id.menuregistrar);
if(userRegistered)
{
register.setVisible(false);
}
else
{
register.setVisible(true);
}
return true;
}
in shorter version you could write:
MenuItem register = menu.findItem(R.id.menuregistrar);
register.setVisible(!userRegistered); //userRegistered is boolean, pointing if the user has registered or not.
return true;
I would simplify Adil's solution even further with the following:
public boolean onPrepareOptionsMenu(Menu menu)
{
MenuItem registrar = menu.findItem(R.id.menuregistrar);
registrar.setVisible(!isRegistered);
return true;
}
Simply do one thing get the id of the item of menu from this line:
Menu menu =navigationView.getMenu();
MenuItem nav_dashboard = menu.findItem(R.id.nav_dashboard);
and than make it visible it accourding to you by this line:
nav_dashboard.setVisible(true/false);
Menu Object has a property to set the visibility of a menu's item using setVisible(boolean)//
Example
private Menu menu_change_language;
...
...
#Override
public boolean onCreateOptionsMenu(Menu menu) {
...
...
menu_change_language = menu;
...
...
return super.onCreateOptionsMenu(menu);
}
use code below for hiding Menu Item:
if(menu_change_language != null){
menu_change_language.findItem(R.id.menu_change_language)
.setVisible(false);
}
Use public boolean onPrepareOptionsMenu (Menu menu) it is called everytime you press the menu button and do your stuff there. or use your oncreateoptionsmenu() in different activities to inflate different menus - this one is called only once.
Cheers
If you want to change the visibility inside the onOptionsItemSelected whenever you click the menu
#Override
public boolean onOptionsItemSelected(MenuItem item) {
item.setVisible(true);
return true;
}
OR
for item in the menu that you didn't click on
private Menu globalMenuItem;
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu."menu Xml Name", menu);
globalMenuItem = menu;
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
globalMenuItem.findItem(R.id."id of the menu item").setVisible(true);
return true;
}
My XML menu definition sets the item R.id.menu_refresh's enabled state to false. When the app runs the menu item is greyed and disabled. Why is this code in the app not enabling the item?
public boolean onCreateOptionsMenu(Menu menu)
{
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.main, menu);
MenuItem refresh = menu.getItem(R.id.menu_refresh);
refresh.setEnabled(true);
return true;
}
What am I missing?
Try menu.findItem() instead of getItem(). getItem() takes an index from [0, size) while findItem() takes an id.
this is what I do in my activity for the menu handling ...
//Android Activity Lifecycle Method
// This is only called once, the first time the options menu is displayed.
#Override
public boolean onCreateOptionsMenu(Menu menu)
{
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.mainmenu, menu);
return true;
}
//Android Activity Lifecycle Method
// Called when a panel's menu is opened by the user.
#Override
public boolean onMenuOpened(int featureId, Menu menu)
{
MenuItem mnuLogOut = menu.findItem(R.id.main_menu_log_out_id);
MenuItem mnuLogIn = menu.findItem(R.id.main_menu_log_in_id);
MenuItem mnuOptions = menu.findItem(R.id.main_menu_options_id);
MenuItem mnuProfile = menu.findItem(R.id.main_menu_profile_id);
//set the menu options depending on login status
if (mBoolLoggedIn == true)
{
//show the log out option
mnuLogOut.setVisible(true);
mnuLogIn.setVisible(false);
//show the options selection
mnuOptions.setVisible(true);
//show the edit profile selection
mnuProfile.setVisible(true);
}
else
{
//show the log in option
mnuLogOut.setVisible(false);
mnuLogIn.setVisible(true);
//hide the options selection
mnuOptions.setVisible(false);
//hide the edit profile selection
mnuProfile.setVisible(false);
}
return true;
}
//Android Activity Lifecycle Method
// called whenever an item in your options menu is selected
#Override
public boolean onOptionsItemSelected(MenuItem item)
{
// Handle item selection
switch (item.getItemId())
{
case R.id.main_menu_log_in_id:
{
ShowLoginUI();
return true;
}
case R.id.main_menu_log_out_id:
{
ShowGoodbyeUI();
return true;
}
case R.id.main_menu_options_id:
{
ShowOptionsUI();
return true;
}
case R.id.main_menu_profile_id:
{
ShowProfileUI();
return true;
}
default:
return super.onOptionsItemSelected(item);
}
}
I like this approach because it makes the code nice and modular
Use menu.findItem() instead of getItem().
because findItem is used to find item by id.