NavigationView - Setting `app:itemBackground` causes menu items to lose start padding - android

I am running into an issue when setting the app:itemBackground for the NavigationView. I am trying to create a custom background for the selected menu item. The custom background works, but when I use it, it seems to kill the start padding of the menu items.
Without the background(default)
With the custom background
You can see that the menu items are flush to the left of the menu when the itemBackground is set.
Here is the relevant xml...
layout
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:id="#+id/DrawerLayout"
android:fitsSystemWindows="false">
<!-- your content layout -->
<include
layout="#layout/MainLayout" />
<android.support.design.widget.NavigationView
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:background="#color/primary_color"
android:id="#+id/NavigationView"
app:itemTextColor="?android:textColorPrimary"
app:headerLayout="#layout/navigationheaderlayout"
app:itemBackground="#drawable/navigation_item_selector"
app:menu="#menu/navigation_menu" />
</android.support.v4.widget.DrawerLayout>
selector
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:drawable="#drawable/navigation_item_selected_background" android:state_selected="true" />
<item android:drawable="#drawable/navigation_item_selected_background" android:state_pressed="true" />
<item android:drawable="#drawable/navigation_item_selected_background" android:state_checked="true" />
<item android:drawable="#drawable/navigation_item_not_selected_background" />
</selector>
selected backgroud
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:left="0dp"
android:right="2dp"
android:drawable="#color/accent_color" />
<item
android:left="2dp"
android:right="2dp"
android:drawable="#color/navigation_selected_item_color" />
</layer-list>
not selected background
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape android:shape="rectangle">
<solid android:color="#android:color/transparent" />
</shape>
</item>
</layer-list>
Has anybody run into something like this before?

Please note below solution will work for pre-lollipop versions. But will add extra padding in lollipop and above. Please apply different theme for different versions to avoid this.
After setting app:theme, padding left issue is fixed.
<android.support.design.widget.NavigationView
android:id="#+id/nav_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:fitsSystemWindows="false"
android:background="#drawable/your_menu_bg"
app:itemBackground="#drawable/your_menu_item_bg"
app:headerLayout="#layout/nav_header_main"
app:menu="#menu/activity_main_drawer"
app:theme="#style/NavigationDrawerStyle"
app:itemIconTint="#color/your_color"
app:itemTextColor="#android:color/white"
app:itemTextAppearance="?android:attr/textAppearanceLarge"/>
This is my custom theme.
<style name="NavigationDrawerStyle">
<item name="android:paddingLeft">20dp</item>
</style>
How to apply different themes for different versions? Check the other link below.
Change theme according to android version

Add for Android 4 versions a padding at the end of the layer-list in your drawable.
Like this way:
<layer-list xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:left="0dp"
android:right="2dp"
android:drawable="#color/accent_color" />
<item
android:left="2dp"
android:right="2dp"
android:drawable="#color/navigation_selected_item_color" />
<item>
<shape android:shape="rectangle" >
<padding android:left="12dp" android:right="12dp"/>
</shape>
</item>
</layer-list>

Related

How to implement the round border and ?selectableItemBackground in textview android?

I am trying to have two text views inside a Linear Layout with a horizontal orientation. Now I want to have the following things for each text view:
An icon at left - implemented using android:drawableLeft="#drawable/ic_lightbulb_outline_blue_24dp"
A round border around the text view - implemented using android:background="#drawable/round_border"
Also, need that ripple effect on touching a touch item
The 3rd point is implemented in other text views using the att.
android:background="?selectableItemBackground"
android:clickable="true"
But there is already a background att. for the round border. Now my question is how to achieve that ripple effect? Is using following att. only way:
android:foreground="?selectableItemBackground"
Android shows this att. is not supported in lower api versions so worried.
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<TextView
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="wrap_content"
android:text="#string/vision_mission"
android:gravity="center"
android:layout_margin="8dp"
android:padding="8dp"
android:textSize="16sp"
android:onClick="openVisionMission"
android:drawableLeft="#drawable/ic_lightbulb_outline_blue_24dp"
android:background="#drawable/round_border"
android:clickable="true"
android:focusable="true"/>
<TextView
android:layout_width="0dp"
android:layout_weight="1"
android:layout_height="wrap_content"
android:text="#string/team"
android:textSize="16sp"
android:drawableLeft="#drawable/ic_people_blue_24dp"
android:background="#drawable/round_border"
android:clickable="true"
android:focusable="true"
android:padding="8dp"
android:layout_marginTop="8dp"
android:layout_marginBottom="8dp"
android:layout_marginRight="8dp"
android:gravity="center"/>
</LinearLayout>
You can achieve ripple effect and text view rounded background at the same time using the following code.
Custom ripple drawable, it require API level 21+
<?xml version="1.0" encoding="utf-8"?>
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
android:color="#color/grey">
<item android:state_pressed="true">
<shape android:shape="rectangle">
<corners android:radius="10dp" />
<stroke
android:width="1dp"
android:color="#android:color/holo_blue_dark" />
</shape>
</item>
<item>
<shape android:shape="rectangle">
<corners android:radius="10dp" />
<stroke
android:width="1dp"
android:color="#android:color/holo_blue_dark" />
</shape>
</item>
</ripple>
After that set background of your text view
android:background="#drawable/custom_ripple"
For pre lollypop ie. below API level 21
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_enabled="false">
<shape android:shape="rectangle">
<solid android:color="#color/colorDarkGray"/>
</shape>
</item>
<item android:state_pressed="false">
<shape android:shape="rectangle">
<solid android:color="#color/colorButtonGreen"/>
</shape>
</item>
<item android:state_pressed="true">
<shape android:shape="rectangle">
<solid android:color="#color/colorButtonGreenFocused"/>
</shape>
</item>
</selector>
It is not exactly what you are looking for.
You can achieve easily something similar with a MaterialButton with a OutlinedButton style.
Something like:
<com.google.android.material.button.MaterialButton
style="#style/Widget.MaterialComponents.Button.OutlinedButton.Icon"
app:icon="#drawable/ic_add_24px"
android:text="...."
.../>
You can customize the padding between the icon and the text, the textColor, the strokeWidth, the strokeColor and also the color selector used for the app:rippleColor
<com.google.android.material.button.MaterialButton
style="#style/Widget.MaterialComponents.Button.OutlinedButton.Icon"
app:icon="#drawable/ic_add_24px"
app:strokeColor="#color/primaryDarkColor"
app:strokeWidth="2dp"
app:iconPadding="16dp"
.../>
you can change your background drawable with selector tag
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_pressed="true"
android:drawable="#drawable/button_pressed" /> <!-- pressed -->
<item android:state_focused="true"
android:drawable="#drawable/button_focused" /> <!-- focused -->
<item android:state_hovered="true"
android:drawable="#drawable/button_focused" /> <!-- hovered -->
<item android:drawable="#drawable/button_normal" /> <!-- default -->
</selector>

How would I create a tab indicator in NavigationDrawer?

How do I create a navigation draw tab indicator like this? Does the NavigationDrawer class have an indicator like TabLayout?
You can define a custom drawable with a left border and set it as the background of the selected item. Follow the steps given below,
Step 1: Define a drawable with left border(selected_item.xml) in drawables
<?xml version="1.0" encoding="utf-8"?>
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape android:shape="rectangle">
<solid android:color="#000000" />
</shape>
</item>
<item android:left="2dp">
<shape android:shape="rectangle">
<solid android:color="#FF0000" />
</shape>
</item>
</layer-list>
Step 2: Define a selector(navi_selector.xml) in drawables
<?xml version="1.0" encoding="utf-8"?>
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:state_checked="true" android:drawable="#drawable/selected_item"/>
<item android:state_pressed="true" android:drawable="#000000"/>
</selector>
Step 3: set the navi_selector for app:itemBackground
<android.support.design.widget.NavigationView
app:itemTextColor="#android:color/white"
android:fitsSystemWindows="true"
android:id="#+id/nav_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:menu="#menu/activity_main_drawer"
android:background="#000000"
app:itemBackground="#drawable/navi_selector"/>

How to create a ripple with rounded corners for drawer menu items?

I'm trying to create a ripple with rounded corners for the Drawer items. However, I can't figure out how to achieve that. I tried to create a custom ripple and assign it to the NavigationView through app:itemBackground property as follows:
<com.google.android.material.navigation.NavigationView
android:id="#+id/navigation_view"
style="#style/Widget.MaterialComponents.NavigationView"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:menu="#menu/menu_navigation"
app:itemBackground="#drawable/custom_ripple"/>
custom_ripple
<ripple xmlns:android="http://schemas.android.com/apk/res/android"
android:color="?android:attr/colorControlHighlight">
<item android:id="#android:id/mask">
<shape android:shape="rectangle">
<solid android:color="#000000" />
<corners android:radius="15dp" />
</shape>
</item>
<item android:drawable="#drawable/rounded_corner" />
</ripple>
rounded_corner
<shape xmlns:android="http://schemas.android.com/apk/res/android">
<solid android:color="#color/colorAccentTransparent" />
<corners android:radius="6dp" />
</shape>
However, this doesn't work as expected. There seem to be two ripples: a rectangle and a ripple with rounded corners as you can see below.
Output
Have you any idea how to solve this? Thanks
Here's what I have done. It removed the rectangular ripple for me. Give it a try and let me know if it's helpful.
<com.google.android.material.navigation.NavigationView
android:id="#+id/navigation_view"
android:theme="#style/NavigationItemNoRipple"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:menu="#menu/menu_navigation"
app:itemBackground="#drawable/custom_ripple"/>
styles.xml:
<style name="NavigationItemNoRipple">
<item name="android:colorControlHighlight">#android:color/transparent</item>
</style>

Bottom navigation item menu custom background

I am trying to add a background as shown in the image, to the menu item in the android bottom navigation.
I have used the following selector as item background (selector_bottom_nav.xml)
<selector xmlns:android="http://schemas.android.com/apk/res/android">
<item android:top="-6dp" android:left="-6dp" android:right="-6dp" android:drawable="#color/blue_light" android:state_checked="true">
<shape android:shape="rectangle">
<solid android:color="#color/blue_light"/>
<size android:width="2dp" android:height="6dp"/>
</shape>
</item>
<item android:drawable="#color/blue"/>
</selector>
And included in the bottom navigation like
<android.support.design.widget.BottomNavigationView
android:id="#+id/navigation"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="bottom"
android:background="?android:attr/windowBackground"
app:itemBackground="#drawable/selector_bottom_nav"
android:foreground="?attr/selectableItemBackground"
app:itemIconTint="#android:color/white"
app:itemTextColor="#android:color/white"
app:menu="#menu/bottom_navigation" />
But I end up getting like this.

Custom section separator for Navigation Drawer

I'm trying to add a section separator for Navigation Drawer with this code which is working but I want to customize it like this example :
example
xml code :
<group
android:id="#+id/menu_center"
android:checkableBehavior="none">
<item
android:id="#+id/Fragment_R"
android:icon="#mipmap/r"
android:title="#string/r" />
<item
android:id="#+id/Fragment_t"
android:icon="#mipmap/t"
android:title="#string/t" />
<item
android:id="#+id/Fragment_Re"
android:icon="#mipmap/real"
android:title="#string/Real" />
</group>
You Needs To Create A Drawable Resource File Like This.
drawer_items_bg
<layer-list xmlns:android="http://schemas.android.com/apk/res/android">
<item>
<shape android:shape="rectangle" >
<solid android:color="#363636" />
</shape>
</item>
<item android:top="2dp" android:right="-2dp" android:left="-2dp" android:bottom="-2dp" >
<shape>
<solid android:color="#363636" />
<stroke
android:width="1dp"
android:color="#777776" />
</shape>
android:dashGap="10px"
android:dashWidth="10px"
</item>
</layer-list>
Then Add It In Your NavigationView
<android.support.design.widget.NavigationView
android:id="#+id/nav_view"
android:background="#drawable/side_nav_bar"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
android:fitsSystemWindows="true"
app:itemTextColor="#FFF"
app:headerLayout="#layout/nav_header_main"
app:menu="#menu/activity_main_drawer"
app:itemBackground="#drawable/drawer_item_bg" //you need to add as background here
app:itemIconTint="#FFF"
android:textSize="22sp"/>
Hope That will works great!

Categories

Resources