MapFragment gets a dark overlay when used in DialogActivity - android

I'm trying to show a MapFragment of the Android Maps v2 API in an Activity with the #android:style/Theme.DeviceDefault.Light.Dialog.NoActionBar theme. This works fine. However, the map gets a dark overlay:
When I change the theme to #android:style/Theme.DeviceDefault.Light.NoActionBar, the map is shown as it should:
This is my xml layout file:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<fragment
android:id="#+id/mapfragment"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"
class="com.google.android.gms.maps.MapFragment" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="HELLO"
android:textSize="#dimen/textsize_large" />
</LinearLayout>
What is happening here?

I got the same problem. After some research, I found two hacks :
Add this param for your theme in the styles.xml :
<item name="android:backgroundDimEnabled">false</item>
Bad part : it removes the black overlays behind the activity.
Set the z order on the top for the map object :
GoogleMapOptions googleMapsOptions = new GoogleMapOptions();
googleMapsOptions.zOrderOnTop( true );
MapFragment mapFragment = MapFragment.newInstance(googleMapsOptions);
Bad part : The map is above the Zoom control and MyLocation button.
Personnaly, I choose the first solution.
Hope this help !
Link to the source

For DialogFragment:
getDialog().getWindow().clearFlags(WindowManager.LayoutParams.FLAG_DIM_BEHIND);

To add on to Audrel's solution, one can dynamically un-dim the dialog's window whenever the map is shown and dim it back when the map is gone (e.g. when your dialog has multiple pages, one of them is a map):
private float mDimAmount;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
WindowManager.LayoutParams params = getWindow().getAttributes();
mDimAmount = params.dimAmount; // remember original dim amount
...
}
private void undim() {
WindowManager.LayoutParams params = getWindow().getAttributes();
params.dimAmount = 0.0f;
getWindow().setAttributes(params);
}
private void dim() {
WindowManager.LayoutParams params = getWindow().getAttributes();
params.dimAmount = mDimAmount;
getWindow().setAttributes(params);
}
Still just another workaround rather than tackling the root cause...

Depending on what your purpose is for the map in the dialog, if you don't need any of the map controls, you can use liteMode in which just an image of the map is displayed with whatever location you load. It doesn't have this z-layer overlay problem.
You can add this to the MapView layout xml:
map:liteMode="true"
This worked for me, because I didn't want my map to be interactive anyway.
You can read the Google docs here: https://developers.google.com/maps/documentation/android-api/lite

Simply add this line to your style !
<item name="android:backgroundDimEnabled">false</item>
This is my style :
<style name="AppTheme" parent="Theme.AppCompat.Light.NoActionBar">
<item name="colorPrimary">#color/colorPrimary</item>
<item name="colorPrimaryDark">#color/dark</item>
<item name="colorAccent">#color/colorAccent</item>
<item name="android:backgroundDimEnabled">false</item>
<item name="windowActionBar">false</item>
</style>

Related

Toolbar logo and title are centered even though they're not supposed to be

I'm having trouble implementing a Toolbar in my Android application. I have several problems, really.
First off, here's my MainActivity.java:
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Toolbar toolbar = (Toolbar)findViewById(R.id.toolbar_Main);
toolbar.setLogo(R.drawable.logo);
toolbar.setTitle(R.string.app_name);
toolbar.inflateMenu(R.menu.main_actions);
setActionBar(toolbar);
}
}
activity_main.xml:
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:context=".MainActivity"
android:nestedScrollingEnabled="false">
<Toolbar
android:layout_width="match_parent"
android:layout_height="?android:attr/actionBarSize"
android:id="#+id/toolbar_Main"
android:background="?android:attr/colorPrimary" />
<!-- There's an EditText here, but I think that's not the problem -->
</LinearLayout>
styles.xml:
<?xml version="1.0" encoding="utf-8"?>
<resources>
<style name="AppTheme" parent="android:Theme.Material.Light">
<item name="android:windowNoTitle">true</item>
<item name="android:windowActionBar">false</item>
<item name="android:colorPrimary">#color/primaryColor</item>
<item name="android:colorPrimaryDark">#color/primaryColorDark</item>
</style>
</resources>
The problems I'm having are:
the menu is gone;
the logo and title text are centered in the Toolbar, even though I'm pretty sure I haven't set any property to center or whatever.
Now the first problem I can fix by removing the setActionBar part (not sure if that's good practice though), but second one, not so much. The logo and text remain centered no matter what I try. I've tried setting the Toolbar's gravity to top|left, as well as some other things, all to no avail.
When searching on Google (or StackOverflow), all I get are results asking to center the text, which is what I don't want.
I should also mention that I'm developing the app only for API level 21, so no AppCompat and all that fancy stuff, just a Toolbar that I wish to use as the app's main ActionBar.
I'm probably just missing some tiny thing, so thanks in advance.
To me:
You should not remove the setActionBar() call;
Your menu might be disappearing because maybe you have a hardware menu button on your device. Try tapping and see what happens. To fix however, try deleting the inflateMenu() line and inflate the menu during onCreateOptionsMenu(), as usual;
Title and logo issues, as well as menu disappearing, might be due to:
<item name="android:windowNoTitle">true</item>
<item name="android:windowActionBar">false</item>
Why these lines? Just remove them if you don't need.
If this doesn't fix, try calling setActionBar(toolbar) first, and then set title using getActionBar().setTitle() . However I'm pretty sure that removing the two window lines from your style will be enough, so do that first.

How to display custom view in ActionBar?

I want to display custom search in actionbar (I'm using ActionBarSherlock for that).
I got that:
But I want make custom layout (edittext field) to occupy the entire available width.
I've implemented custom layout as suggested here.
There is my custom layout search.xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
style="?attr/actionButtonStyle"
android:layout_width="fill_parent"
android:layout_height="match_parent"
android:layout_gravity="fill_horizontal"
android:focusable="true" >
<FrameLayout
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical|fill_horizontal" >
<EditText
android:id="#+id/search_query"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_gravity="left|center"
android:background="#drawable/bg_search_edit_text"
android:imeOptions="actionSearch"
android:inputType="text" />
<ImageView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="right|center_vertical"
android:src="#drawable/ic_search_arrow" />
</FrameLayout>
</LinearLayout>
And in MyActivity:
ActionBar actionBar = getSupportActionBar();
actionBar.setDisplayHomeAsUpEnabled(true);
actionBar.setDisplayShowCustomEnabled(true);
actionBar.setDisplayShowTitleEnabled(false);
actionBar.setIcon(R.drawable.ic_action_search);
LayoutInflater inflator = (LayoutInflater) this .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
View v = inflator.inflate(R.layout.search, null);
actionBar.setCustomView(v);
How can I make custom layout to occupy all the available width of actionBar?
Help, please.
There is a trick for this. All you have to do is to use RelativeLayout instead of LinearLayout as the main container. It's important to have android:layout_gravity="fill_horizontal" set for it. That should do it.
I struggled with this myself, and tried Tomik's answer.
However, this didn't made the layout to full available width on start, only when you add something to the view.
You'll need to set the LayoutParams.FILL_PARENT when adding the view:
//I'm using actionbarsherlock, but it's the same.
LayoutParams layout = new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT);
getSupportActionBar().setCustomView(overlay, layout);
This way it completely fills the available space. (You may need to use Tomik's solution too).
This is how it worked for me (from above answers it was showing both default title and my custom view also).
ActionBar.LayoutParams layout = new ActionBar.LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
// actionBar.setCustomView(view); //last view item must set to android:layout_alignParentRight="true" if few views are there
actionBar.setCustomView(view, layout); // layout param width=fill/match parent
actionBar.setDisplayShowCustomEnabled(true);//must other wise its not showing custom view.
What I noticed is that both setCustomView(view) and setCustomView(view,params) the view width=match/fill parent. setDisplayShowCustomEnabled (boolean showCustom)
The answers from Tomik and Peterdk work when you want your custom view to occupy the entire action bar, even hiding the native title.
But if you want your custom view to live side-by-side with the title (and fill all remaining space after the title is displayed), then may I refer you to the excellent answer from user Android-Developer here:
https://stackoverflow.com/a/16517395/614880
His code at bottom worked perfectly for me.
For example, you can define a layout file which contains a EditText element.
<?xml version="1.0" encoding="utf-8"?>
<EditText xmlns:android="http://schemas.android.com/apk/res/android"
android:id="#+id/searchfield"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:inputType="textFilter" >
</EditText>
you can do
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ActionBar actionBar = getActionBar();
// add the custom view to the action bar
actionBar.setCustomView(R.layout.actionbar_view);
EditText search = (EditText) actionBar.getCustomView().findViewById(R.id.searchfield);
search.setOnEditorActionListener(new OnEditorActionListener() {
#Override
public boolean onEditorAction(TextView v, int actionId,
KeyEvent event) {
Toast.makeText(MainActivity.this, "Search triggered",
Toast.LENGTH_LONG).show();
return false;
}
});
actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM
| ActionBar.DISPLAY_SHOW_HOME);
}
There is an example in the launcher app of Android (that I've made a library out of it, here), inside the class that handles wallpapers-picking ("WallpaperPickerActivity") .
The example shows that you need to set a customized theme for this to work. Sadly, this worked for me only using the normal framework, and not the one of the support library.
Here're the themes:
styles.xml
<style name="Theme.WallpaperPicker" parent="Theme.WallpaperCropper">
<item name="android:windowBackground">#android:color/transparent</item>
<item name="android:colorBackgroundCacheHint">#null</item>
<item name="android:windowShowWallpaper">true</item>
</style>
<style name="Theme.WallpaperCropper" parent="#android:style/Theme.DeviceDefault">
<item name="android:actionBarStyle">#style/WallpaperCropperActionBar</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowActionBarOverlay">true</item>
</style>
<style name="WallpaperCropperActionBar" parent="#android:style/Widget.DeviceDefault.ActionBar">
<item name="android:displayOptions">showCustom</item>
<item name="android:background">#88000000</item>
</style>
value-v19/styles.xml
<style name="Theme.WallpaperCropper" parent="#android:style/Theme.DeviceDefault">
<item name="android:actionBarStyle">#style/WallpaperCropperActionBar</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowActionBarOverlay">true</item>
<item name="android:windowTranslucentNavigation">true</item>
</style>
<style name="Theme" parent="#android:style/Theme.DeviceDefault.Wallpaper.NoTitleBar">
<item name="android:windowTranslucentStatus">true</item>
<item name="android:windowTranslucentNavigation">true</item>
</style>
EDIT: there is a better way to do it, which works on the support library too. Just add this line of code instead of what I've written above:
getSupportActionBar().setDisplayShowCustomEnabled(true);

How to set a default layout in a theme

I'm using a custom titlebar in my app, but everytime I create a new layout I have to call:
<include
android:id="#+id/titlebar"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="#integer/titlebar_weight"
layout="#layout/titlebar" />
Instead calling this in all the layouts how can I define it in a theme (in other words: define a default layout for the theme)?
My default layout:
Although the old title bar can be customized a bit via a theme (windowTitleStyle, windowTitleSize, windowTitleBackgroundStyle), you cannot set your own layout. Also the title bar was replaced by the ActionBar in Android 3.0, so that won't help you anyway.
Setting a default layout in a theme is not possible, at least I could not find a way to do it. But you still have several options to reduce repetition when adding your header layout:
Create a master layout with your header and a ViewStub for your content, then set the inflatedId by code.
Consider building your screens with fragments and add/remove them programmatically from your master layout.
Add the header programmatically in a base activity (suggested by user1527136)
Include it (that is what you are already doing, and it is not that bad imho)
I would recommend against creating the actionbar yourself, you can either try:
Actionbar Sherlock or ActionbarCompat (from the Google samples in your SDK).
<resources>
<style name="Theme.Transparent" parent="android:Theme">
<item name="android:windowIsTranslucent">true</item>
<item name="android:windowBackground">#android:color/transparent</item>
<item name="android:windowContentOverlay">#null</item>
<item name="android:windowNoTitle">true</item>
<item name="android:windowIsFloating">true</item>
<item name="android:backgroundDimEnabled">false</item>
</style>
</resources>
<activity
android:theme="#style/Theme.Transparent"
</activity>
I don't think this can be achieved through theming alone. You would need to create an abstract Activity that will include your title bar and wrap the content view set by the extended Activity classes. Here's an example:
XML
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<include
android:id="#+id/titleBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
layout="#layout/titlebar" />
<FrameLayout
android:id="#+id/content"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</LinearLayout>
Abstract Activity
public abstract class TitleBarActivity extends Activity {
#Override
protected void onCreate( Bundle savedInstanceState ) {
super.onCreate( savedInstanceState );
super.setContentView( R.layout.title_bar_activity );
}
#Override
public void setContentView( int layoutResId ) {
FrameLayout contentFrameLayout = (FrameLayout) findViewById( R.id.content );
contentFrameLayout.removeAllViews();
getLayoutInflater().inflate( layoutResId, contentFrameLayout );
}
}
This is a very simple implementation, but should give you the general idea of what you need to do. Now for any Activity that extends TitleBarActivity, you'll already have the title bar at the top by default. Any customization of the title you want your activities to control, add methods in TitleBarActivity to do so.

Creating a custom dialog in Android

I am trying to create a custom dialog in Android. But whatever I tried to do, I am not able to change the width of the dialog. It just remains the same. The following is the view that I am setting as the content for the dialog.
<RelativeLayout
android:id="#+id/current_stats"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:visibility="visible">
<ImageView android:id="#+id/player_image"
android:src="#drawable/person"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_centerHorizontal="true"/>
<TextView
android:id="#+id/player_name"
android:layout_below="#id/player_image"
android:layout_centerHorizontal="true"
android:text="Raja Ram"
android:layout_width="wrap_content"
android:layout_height="wrap_content"/>
<ImageButton android:id="#+id/dialog_close"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_alignParentRight="true"
android:background="#00000000"
android:src="#drawable/close_button_selector"/>
<ImageButton android:id="#+id/dialog_flip"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:layout_alignParentLeft="true"
android:background="#00000000"
android:src="#drawable/rotate"/>
</RelativeLayout>
As you can see, everywhere I am using wrap_content in this code sample. Also I tried the following options
1) Setting a custom style while creating the Dialog like this.
dialog = new Dialog(this,R.style.Theme_Dialog);
And the style as follows
<resources>
<style name="Theme" parent="android:Theme">
</style>
<style name="Theme.Dialog">
<item name="android:layout_width">wrap_content</item>
<item name="android:layout_height">wrap_content</item>
<item name="android:windowIsFloating">true</item>
<item name="android:windowContentOverlay">#null</item>
<item name="android:windowAnimationStyle">#android:style/Animation.Dialog</item>
<item name="android:windowSoftInputMode">stateUnspecified|adjustPan</item>
</style>
</resources>
2) Setting the parameters for the view in the onCreateDialog() like this
LayoutInflater inflater = (LayoutInflater)this.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
v = inflater.inflate(R.layout.player_info, null, false);
ViewGroup.LayoutParams p = new ViewGroup.LayoutParams(ViewGroup.LayoutParams.FILL_PARENT,ViewGroup.LayoutParams.WRAP_CONTENT);
dialog.setContentView(v,p);
3) I also tried to set the Window parameters like this in the onCreateDialog() method
WindowManager.LayoutParams params = dialog.getWindow().getAttributes();
params.width=WindowManager.LayoutParams.WRAP_CONTENT;
dialog.getWindow().setAttributes(params);
But again no luck. Can someone help me out with this issue. Am I doing something wrong?? Also can you please suggest me how to set the x and y postions for the Dialog window?
Thanks
dialog = new Dialog(this,android.R.style.Theme_Translucent_NoTitleBar);
dialog.setContentView(R.layout.custom_dialog);
LayoutParams lp=dialog.getWindow().getAttributes();
lp.x=100;lp.y=100;lp.width=100;lp.height=200;lp.gravity=Gravity.TOP | Gravity.LEFT;
lp.dimAmount=0;
lp.flags=LayoutParams.FLAG_LAYOUT_NO_LIMITS | LayoutParams.FLAG_NOT_TOUCH_MODAL;
// dialog.getWindow().setAttributes(lp);
dialog.show();
This worked well for me....
Is your problem that it takes the full width of the screen, or that you can't control how much of the screen is it taking up?
To make your activity act as a dialog, and not take up the full with you should set your activity to have the dialog theme in the manifest:
<activity android:theme="#android:style/Theme.Dialog">
The dialog will be as large as is required by your layout. If you want it to be wider, you need to make your layout wider. (Adjust size of images, add padding, etc).
I'm not aware of a way to position the dialog window.. I think it is always centered, I could be wrong though.
I figured out the problem after a long time. The problem was with the way I used Relative layout. I guess I have not specified the relative position properly. When I changed that to linear layout it worked fine. It was not using up the whole screen but only whatever is required.
I could change the width,height and the position of the Dialog using getWindow().setAttributes(params)
in the onCreate() method of yout custom dialog class do the next
#Override
protected void onCreate(Bundle savedInstanceState) {
getWindow().setLayout(x, y);
}

How can I get a Dialog style activity window to fill the screen?

I am using an activity with the dialog theme set, and I want it to be full screen. I tried all sorts of things, even going through the WindowManager to expand the window to full width and height manually, but nothing works.
Apparently, a dialog window (or an activity with the dialog theme) will only expand according to its contents, but even that doesn't always work. For instance, I show a progress bar circle which has width and height set to FILL_PARENT (so does its layout container), but still, the dialog wraps around the much smaller progress bar instead of filling the screen.
There must be a way of displaying something small inside a dialog window but have it expand to full screen size without its content resizing as well?
I found the solution:
In your activity which has the Theme.Dialog style set, do this:
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.your_layout);
getWindow().setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
}
It's important that you call Window.setLayout() after you call setContentView(), otherwise it won't work.
You may add this values to your style android:windowMinWidthMajor and android:windowMinWidthMinor
<style name="Theme_Dialog" parent="android:Theme.Holo.Dialog">
...
<item name="android:windowMinWidthMajor">97%</item>
<item name="android:windowMinWidthMinor">97%</item>
</style>
I just want to fill only 80% of the screen for that I did like this below
DisplayMetrics metrics = getResources().getDisplayMetrics();
int screenWidth = (int) (metrics.widthPixels * 0.80);
setContentView(R.layout.mylayout);
getWindow().setLayout(screenWidth, LayoutParams.WRAP_CONTENT); //set below the setContentview
it works only when I put the getwindow().setLayout... line below the setContentView(..)
thanks #Matthias
Wrap your dialog_custom_layout.xml into RelativeLayout instead of any other layout.That worked for me.
For Dialog
This may helpful for someone.
I want a dialog to take full width of screen. searched a lot but nothing found useful. Finally this worked for me:
mDialog.setContentView(R.layout.my_custom_dialog);
mDialog.getWindow().setBackgroundDrawable(null);
after adding this, my dialog appears in full width of screen.
This answer is a workaround for those who use "Theme.AppCompat.Dialog" or any other "Theme.AppCompat.Dialog" descendants like "Theme.AppCompat.Light.Dialog", "Theme.AppCompat.DayNight.Dialog", etc.
I myself has to use AppCompat dialog because i use AppCompatActivity as extends for all my activities. There will be a problem that make the dialog has padding on every sides(top, right, bottom and left) if we use the accepted answer.
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.your_layout);
getWindow().setLayout(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT);
}
On your Activity's style, add these code
<style name="DialogActivityTheme" parent="Theme.AppCompat.Dialog">
<item name="windowNoTitle">true</item>
<item name="android:windowBackground">#null</item>
</style>
As you may notice, the problem that generate padding to our dialog is "android:windowBackground", so here i make the window background to null.
Set a minimum width at the top most layout.
android:minWidth="300dp"
For example:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout android:orientation="vertical" android:layout_width="fill_parent" android:layout_height="fill_parent"
xmlns:android="http://schemas.android.com/apk/res/android" android:minWidth="300dp">
<!-- Put remaining contents here -->
</LinearLayout>
Matthias' answer is mostly right but it's still not filling the entire screen as it has a small padding on each side (pointed out by #Holmes). In addition to his code, we could fix this by extending Theme.Dialog style and add some attributes like this.
<style name="MyDialog" parent="#android:style/Theme.Dialog">
<item name="android:windowBackground">#android:color/transparent</item>
<item name="android:windowNoTitle">true</item>
</style>
Then we simply declare Activity with theme set to MyDialog:
<activity
android:name=".FooActivity"
android:theme="#style/MyDialog" />
This would be helpful for someone like me. Create custom dialog style:
<style name="MyDialog" parent="Theme.AppCompat.Light.Dialog">
<item name="windowNoTitle">true</item>
<item name="android:windowFullscreen">true</item>
<item name="android:windowIsFloating">false</item>
</style>
In AndroidManifest.xml file set theme for wanted activity:
<activity
android:name=".CustomDialog"
...
android:theme="#style/MyDialog"/>
That is all, no need to call methods programaticaly.
In your manifest file where our activity is defined
<activity
android:name=".YourPopUpActivity"
android:theme="#android:style/Theme.Holo.Dialog" >
</activity>
without action bar
<activity android:name=".YourPopUpActivity"
android:theme="#android:style/Theme.Holo.Dialog.NoActionBar"/>

Categories

Resources