I am adapting an application written for a Galaxy Tab 2 (10".1) screen size to a Nexus 7 (7").
Following the suggestions here in stackoverflow I created different image sizes for all densities (l|m|h|xh)dpi and also a specific layout-sw600dp folder which contains my layouts modified for the 7 inches screen.
[EDIT]
And I added
<supports-screens android:anyDensity="true"
android:largeScreens="true"
android:normalScreens="true"
android:resizeable="true"
android:smallScreens="true" />
to my Androidmanifest file.
[/EDIT]
Notwithstanding all these modifications I am still struggling having the drawableBottom (and Top, Left, Right) of my Buttons correctly scaling between the two devices.
The physical size of the rendered images is the same. So the Nexus is making the icons as large as the Galaxy (or viceversa).
From what I understood the two devices, although being of different physical size, they share the same density of pixels (xhdpi), that makes the Nexus picking up from the xhdpi folder.
Am I missing something important?
How should I adapt my drawableBottoms?
Have you made sure the app is designed for high density displays? Try adding this to your manifest after permissions:
<supports-screens android:largeScreens="true"
android:normalScreens="true"
android:smallScreens="true"
android:anyDensity="true"/>
OK.
Probably this is not "THE" solution as it is meant to be. But it worked for me straight away and with a minimum effort considered the size of the application I had to adapt.
This following solution basically works quite nicely but (probably) only for this specific case since the Galaxy Tab 2 and the Nexus 7 share the same resolution.
How I fixed it with almost no work:
Do not create the smaller resolution images (you don't really need it), unless you are going to install (or have installed) your app in many other devices.
Create two values- folders. One for the Galaxy Tab 2 ( = xlarge), the other one for the Nexus 7 ( = large). The modifier is the size of the screen.
Inside each of the folders place a dimen.xml file which you will fill respectively like.
For the Galaxy Tab 2:
<?xml version="1.0" encoding="utf-8"?>
<resources>
[...]
<dimen name="s25sp">25sp</dimen>
<dimen name="s30sp">30sp</dimen>
<dimen name="s35sp">35sp</dimen>
[...]
<dimen name="s25dp">25dp</dimen>
<dimen name="s30dp">30dp</dimen>
<dimen name="s35dp">35dp</dimen>
[...]
</resources>
For the Nexus 7:
<?xml version="1.0" encoding="utf-8"?>
<resources>
[...]
<dimen name="s25sp">17sp</dimen>
<dimen name="s30sp">21sp</dimen>
<dimen name="s35sp">24sp</dimen>
[...]
<dimen name="s25dp">17dp</dimen>
<dimen name="s30dp">21dp</dimen>
<dimen name="s35dp">24dp</dimen>
[...]
</resources>
Each value for the Nexus 7 is obtained like: Galaxy_value/10.1*7
After that you have to use the #dimen/s[0-9]*dp whenever you want to use that specific dimension.
PS:
If you have a big application with many layouts already formatted you could use this PERL script to convert every [0-9]*dp and [0-9]*sp into #dimen/s[0-9]*dp #dimen/s[0-9]*sp automatically.
Here it is:
#!/usr/bin/perl
$filename = $ARGV[0];
open (FILE, $filename);
while (<FILE>) {
chomp;
if ( $_ =~ /\"[0-9]*(di?p|sp)\"/) {
my $pre = $`;
my $mat = $&;
my $pos = $';
$mat =~ s/["]+//g;
print "$pre\"\#dimen/s$mat\"$pos\n";
} elsif ( ($_ !~ /\"[0-9]*dp\"/) && ($_ !~ /\"[0-9]*sp\"/) ) {
print "$_\n";
}
}
close (FILE);
exit;
Related
I am working with different screen resoultions for android devices, i have added the layout folders for default, small and xlarge size devices and also the dimens as below :
<!-- Default screen margins, per the Android Design guidelines. -->
<dimen name="activity_horizontal_margin">16dp</dimen>
<dimen name="activity_vertical_margin">16dp</dimen>
<dimen name="activity_horizontal_margin_small">8dp</dimen>
<dimen name="activity_vertical_margin_small">8dp</dimen>
<dimen name="activity_horizontal_margin_large">64dp</dimen>
<dimen name="activity_vertical_margin_large">64dp</dimen>
and added the below code into the manifest file :
<supports-screens android:smallScreens="true"
android:normalScreens="true"
android:largeScreens="true"
android:xlargeScreens="true"
android:anyDensity="true" />
folder format for layouts looks as :
res-
--layout
--layout-large
--layout-small
The layout file consists dimensions specific to the resolution and everything is being followed as per the guideline
But the changes are not reflected on the actual devices with different resolutions. i.e. I always see small margin on all devices. Am i missing something.
The grade version I am using is, 2.14.1
I read a lot about supporting multiple screens problems in Android, but I didn't solve mines yet. If I understood well, there are at least 2 ways to show images on different screens and to make it look normal. First, to make many images (xhdpi, hdpi, mdpi, ldpi). Second, is to create layouts(big, medium, small and etc.) My question is: which method is better? Now, my problem. I took first method, create my image in different sizes and copied to folders according to image's size. I used DEVS BITMAP app to get size, which I want my image to look like for different screens. I'm getting perfect view when I look on the 7' screen, but the view gets terrible on 3' screen. I copied this code to my Manifest:
<supports-screens
android:anyDensity="true"
android:largeScreens="true"
android:normalScreens="true"
android:smallScreens="true"
android:xlargeScreens="true" />
I think it isn't necessary, but I wanted to be sure I am doing everything good. Could anyone answer my question and solve my problem? I would appreciate your help! ;)
Create a new Project.
There is a layout folder ,values-sw600dp,values-dw720dp-land. In both these folders, there is a dimens.xml file. What is written in it is this :-
<resources>
<!--
Customize dimensions originally defined in res/values/dimens.xml (such as
screen margins) for sw720dp devices (`e.g. 10" tablets)` in landscape here.
-->
<dimen name="activity_horizontal_margin">128dp</dimen>
That mean folders with sw-720 dp are for 10 inch devices, similar 600dp are for 7 inch devices and default layout folders vary from 3 to 5 inch device.
layout-sw600dp -> This folder will have xml in PORTRAIL Orientation for 7 inch devices
layout-sw600dp-land -> This folder will have xml in LANDSCAPE Orientation for 7 inch devices. When you rotate your device, view will be formed from this folder
Based on the dpi/resoulution of your devices, you can create unlimited number of layout folders.
Similarly, there are folders for images called drawable ->hdpi ldpi mdpi xhdpi xxhdpi. Based on the resolution of devices, images are picked from their respective category.
xxhdpi will contain images with the highest resolution. So try to download big resolution images and downsize them and put them in the other folders.
Now how to know which device will take which image ? See the image below :-
See the drop down. It contains a list of devices with their resolutions and image type -hdpi ldpi mdpi xhdpi xxhdpi. Moreover, you can GOOGLE for the devices and their resolutions and dpi's.
So whatever app you are making for a device, choose that device and look at its resolution and see whether it is hdpi or ldpi etc. Accordingly, put the images and layouts.
This is my understanding. I create my layouts with this understanding. I hope you got a clear picture
For Multiple Screen Support
Add Different size of images to
drawable-ldpi/
drawable-mdpi/
drawable-hdpi/
drawable-xhdpi/
drawable-xxhdpi/
Suppose you have Imageview in layout folder
<ImageView
android:layout_width="#dimen/horizontal_len"
android:layout_height="#dimen/vertical_len" />
Do the following values
values/dimens.xml (Normal mobile)
<!-- Default screen margins, per the Android Design guidelines. -->
<dimen name="horizontal_len">16dp</dimen>
<dimen name="vertical_len">16dp</dimen>
values-large/dimens.xml (7 inch)
<dimen name="horizontal_len">20dp</dimen>
<dimen name="vertical_len">20dp</dimen>
values-xlarge/dimens. xml (10 inch)
<dimen name="horizontal_len">22dp</dimen>
<dimen name="vertical_len">22dp</dimen>
So you have to try like this.
So I used the following code below to have my application to scale screen size on different android devices but when I am testing on my Nexus 7 its does not scale and its as if it was on a 4 inch screen. When I run it in the emulator on a 7 inch screen it works. Anything wrong with my manifest file?
<supports-screens
android:resizeable="true"
android:smallScreens="true"
android:largeScreens="true"
android:xlargeScreens="true"
android:normalScreens="true"
android:anyDensity="true"
/>
this code goes right before the "application" part right?
Ok, so what you have to know is that support-screens doesn't make your application look 'nice' on screens you are supporting (check this link). It just tells that users with such screens will be able to download your application, but it's up to you to make it display properly. You have to create layouts for specific screens on your own.
More about it you can read in Android's documentation: http://developer.android.com/guide/practices/screens_support.html
Basically, you have to properly name your directories in which layout files are stored in order to let Android know which one should it pick up for specific device. If for example your layout's file was "layout.xml" you should have:
/res/layout/layout.xml // Default layout
/res/layout-small/layout.xml // Small screens
/res/layout-large/layout.xml // Large screens
/res/layout-xlarge/layout.xml // Extra large screens
You can go even further and make also different layouts for portrait and landscape views by specyfing another keyword in directory's name:
/res/layout-small-land/layout.xml // Small screens, landscape view
/res/layout-small-portrait/layout.xml // Small screens, portrait view
Remember that tags order is important, so you can't write layout-portrait-small.
Use Relative layout it will solve most of your problem .Additional use Folder name with given below
the way i am dealing with multiple screen is this way and its working fine.....if any one has improved wayso do guide me
Screen size 480x800
layout-normal-hdpi-480x800
drawable-normal-hdpi-480x800
Screen size Galaxy Nexus--- though its size is 1280x720 but in actual due to system bar its dimension(screen size) differs
layout-normal-xhdpi
drawable-normal-xhdpi
Screen size Note 5.3---
layout-normal-xhdpi-1280x800
drawable-normal-xhdpi-1280x800
Screen size S3---
layout-normal-xhdpi-1280x720
drawable-normal-xhdpi-1280x720
Screen size 7inch tab 2 supporting OS version 3 and above--- dont write dimension 1026x600 bsz in actual due to system bar its dimension(screen size) differs
layout-large-mdpi
drawable-large-mdpi
Screen size 7inch tab p1000 etc supoorting os verion less than 3---
layout-large-hdpi-1024x600
drawable-large-hdpi-1024x600
Screen size 1280x800 tab 10.1,10.2,note 10.1 etc--- you can add dimension if you want other wise it is fine
layout-xlarge-mdpi
drawable-xlarge-mdpi
So I used the following code below to have my application to scale screen size on different android devices but when I am testing on my Nexus 7 its does not scale and its as if it was on a 4 inch screen. When I run it in the emulator on a 7 inch screen it works. Anything wrong with my manifest file?
<supports-screens
android:resizeable="true"
android:smallScreens="true"
android:largeScreens="true"
android:xlargeScreens="true"
android:normalScreens="true"
android:anyDensity="true"
/>
this code goes right before the "application" part right?
Ok, so what you have to know is that support-screens doesn't make your application look 'nice' on screens you are supporting (check this link). It just tells that users with such screens will be able to download your application, but it's up to you to make it display properly. You have to create layouts for specific screens on your own.
More about it you can read in Android's documentation: http://developer.android.com/guide/practices/screens_support.html
Basically, you have to properly name your directories in which layout files are stored in order to let Android know which one should it pick up for specific device. If for example your layout's file was "layout.xml" you should have:
/res/layout/layout.xml // Default layout
/res/layout-small/layout.xml // Small screens
/res/layout-large/layout.xml // Large screens
/res/layout-xlarge/layout.xml // Extra large screens
You can go even further and make also different layouts for portrait and landscape views by specyfing another keyword in directory's name:
/res/layout-small-land/layout.xml // Small screens, landscape view
/res/layout-small-portrait/layout.xml // Small screens, portrait view
Remember that tags order is important, so you can't write layout-portrait-small.
Use Relative layout it will solve most of your problem .Additional use Folder name with given below
the way i am dealing with multiple screen is this way and its working fine.....if any one has improved wayso do guide me
Screen size 480x800
layout-normal-hdpi-480x800
drawable-normal-hdpi-480x800
Screen size Galaxy Nexus--- though its size is 1280x720 but in actual due to system bar its dimension(screen size) differs
layout-normal-xhdpi
drawable-normal-xhdpi
Screen size Note 5.3---
layout-normal-xhdpi-1280x800
drawable-normal-xhdpi-1280x800
Screen size S3---
layout-normal-xhdpi-1280x720
drawable-normal-xhdpi-1280x720
Screen size 7inch tab 2 supporting OS version 3 and above--- dont write dimension 1026x600 bsz in actual due to system bar its dimension(screen size) differs
layout-large-mdpi
drawable-large-mdpi
Screen size 7inch tab p1000 etc supoorting os verion less than 3---
layout-large-hdpi-1024x600
drawable-large-hdpi-1024x600
Screen size 1280x800 tab 10.1,10.2,note 10.1 etc--- you can add dimension if you want other wise it is fine
layout-xlarge-mdpi
drawable-xlarge-mdpi
I have different layout files for
different screens size like
Folder Structure:
layout
layout-large
layout-small
For emulators like HVGA and QVGA there
is no problem, the respective
layout.xml file being refereed. But
the layout-large folder is ignored
when I run the emulator of
WVGA(480x854) , here it is referring
the "layout" folder of the
application. Please point me to the
right direction which is right way to
handle this situation.
I tried using
layout-large-hdpi layout-large-mdpi layout-large-ldpi
layout-normal-hdpi layout-normal-mdpi layout-normal-ldpi
And in the AndroidManifest.xml I
specified
<supports-screens
android:largeScreens="true"
android:normalScreens="true"
android:smallScreens="true"
android:anyDensity="true" />
but no success
I think the Problem is that people always create a large screen by AVD Manager and it sets the default density to 240 which is not supported by /res/layout-large
If you want to want to test /res/layout-large/any_layout.xml then you should see the density of your virtual device it should be set to 160 not 240 or 120
Make sure the set up emulator's default size is "large" and not "xlarge".
For example if the emulator size is "xlarge", then the "layout-large" folder will be ignored and the default "layout" folder will be used, because it can't find a "layout-xlarge" folder.
This is easy to identify if your using Android Studio.
Have you checked if your API Level is already supporting this? I had this issue as well. In my case I used following line in the manifest, which set the TargetSDK to 4 (1.6), where the support of those different layouts started.
<uses-sdk android:minSdkVersion="3" android:targetSdkVersion="4" />
Links:
Screen Support