Scaling drawables not to density (dip), but actual pixel resolution (px) - android

I've been working on an app where it is important that drawables are always the same size relative to the display's width, e.g. always 1/8 of the screen height in pixels. I understand how density independent pixels work, but as their goal is to always represent the same physical size, it is pretty much the opposite of what i need. How can I achive this? I have tried using a .png-file with a very high resolution and downscale accordingly, but its always blurry and the quality loss is unbelievable.
Thank you for your help, best regards.

Had the exact same issue. Here's my solution:
DisplayMetrics displayMetrics = getApplicationContext().getResources().getDisplayMetrics();
Double newHeight = 0.125 * displayMetrics.heightPixels;
yourImageView.getLayoutParams().height = newHeight.intValue();
Alternatively, use a LinearLayout. Set your ImageView's weight to 1, and the LinearLayout's weightSum to 8.

Related

Android how to evaluate view size to keep same proportion in all devices

I'm searching for a way to keep view size proportioned on all devices. I experimented with many maths calculations (e.g. mixing screen size, density, percentage, etc.) but haven't found any solutions, just different results for each device tested.
Let me present an example: Suppose I'm testing an app on a sw-360dp and eventually I find a size view that works.
relativeLayoutParams.width = 150;
relativeLayoutParams.height = 250;
This has the effect of creating a view with size about 1/3 of screen width and 1/2 screen height.
How can I dynamically arrive at value for width and height, that lets the view keep the aspect ratio of 1/3 width to 1/2 height? At least I think that's what the documentation is suggesting when it says: "calculate exact view size (or margin, padding, etc.) from a percentage of screen size".
Or have I misinterpreted it?
Any help will be appreciated.
You can get the device screen size and there by define the ratio,
Display display = getWindowManager().getDefaultDisplay();
Point size = new Point();
display.getSize(size);
Then,
width = (int) size.x * 1/3 ;
height = (int) size.y * 1/2 ;

LibGDX - how do I make my game work on all screen resolutions?

I am currently using the Orthographic Camera. Before I get too much into the game, I want to fix the screen size first. Currently, I have the screen size set for 800 x 480. Will this work well on other devices and screen sizes? Right now all I have is a splash screen and game screen. What lines of code would I have to add to achieve this.
Having a static width on your camera is perfectly ok as it gives your game a single fixed dimension that you can work with reliably. This works because the camera is used to define world coordinates which are not always one to one with screen coordinates.
Your issues come from the fixed camera height. Having a fixed height will cause your screen to stretch taller or shorter depending on the aspect ratio of the device screen. If you want to account for the different aspect ratios, you'll need to multiply your camera height (currently 480) by the display ratio. You can get the screen ratio by dividing the height by the width by the height. This would look something like:
float width = Gdx.graphics.getWidth();
float height = Gdx.graphics.getHeight();
OrthographicCamera camera = new OrthographicCamera(800, 480 * (height / width));
As pointed out by BennX in the comments, LibGDX introduced viewports which allow you do very much the same thing as above, just in a different way. To achieve the same effect as I outlined above, only using a viewport, you'd use an ExtendViewport. What this does is maintain the world size in one direction while stretching it in the other direction. So the world will first scale up to fill the screen, then the shorter dimension is expanded while maintaining aspect ratio. To create this type of viewport, it'd look something like this:
OrthographicCamera camera = new OrthographicCamera(800, 480);
ExtendViewport viewport = new ExtendViewport(800, 480, camera);
The viewport above will have a minimum width of 800 and a minimum height of 480. One of these values will be the same after the viewport is applied and the other will change based on the aspect ratio of the screen. More narrow screens will have more vertical space while wider screens will have more horizontal space. For more on viewports, visit the LibGDX wiki page here.
I am using below approach and it's works for almost all screen sizes with ignoble minor scaling issue.
I always uses graphics images for screen size 1920.0x1080.0
ScreenViewport screenViewport=new ScreenViewport(camera);
screenViewport.setUnitsPerPixel(Math.min(1920.0f/Gdx.graphics.getWidth(),1080.0f/Gdx.graphics.getHeight()));
Here you can set your approach from Math.min() or Math.max().
It will result your camera view-port size near to 1920.0*1080.0
Device screen-size Math.max() Math.max()
800.0x480.0 1800.0x1080.0 1920.0x1152.0
1920.0x1080.0 1920.0x1080.0 1920.0x1080.0
2048.0x1440.0 1536.0x1080.0 1920.0x1350.0
Note: Always use camera.viewportWidth and camera.viewportHeight for set positions of Games UI screens.

how can i know the actual size of an imageView in my device?

I have an ImageView with matchParent property in width.
how can i know its runtime width on my device (using eclipse, without adding code programmatically)?
how can I know the conversion ratio between dpi to pxls in my device?
I have an ImageView ... how can i know its runtime width on my device
You can get the width when the ImageView is measured, i.e. later than the runtime. However you can get the screen's width and height like this:
DisplayMetrics metrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(metrics);
int height = metrics.heightPixels;
int width = metrics.widthPixels;
And if for example your ImageView takes up a specific portion of your screen you can measure it using the screen's width and height.
how can I know the conversion ratio between dpi to pxls in my device?
To convert say 20 pixels to DP do (adding to the above code):
int dp = 20 / metrics.density:
Extra: Here's a dpi to pixel calculator
If you don't want to use the TreeObserverListener way, you can try to get the View to measure itself and give you what the dimensions would be if it were calculated. In my experience, this has worked in most cases but not all; especially if the View is in some special dynamic layout or the ordering of the hierarchy prevents the dimensions from being calculated in the correct order. You might find luck in refering to this popular answer.

Image Height Appear Different on different density

I'm new in designing the layouts. I am getting the bitmap from the server and I'm setting the imageview height such that it look good on every density either ldpi, mdpi, hdpi, xhdpi.
stripImageView.getLayoutParams().height = (int) ((Util.screenWidth(this) * strip.getHeight() / strip.getWidth()) * getResources().getDisplayMetrics().density);
But This code not working for me. Some device images looking very small and Some device it look fine
Try just setting the dimensions in your layout using dp instead of px. Dp (or dip) stands for density independent pixels and will automatically scale based on density.
EDIT: another issue I see is that you're referencing both the screen width and height so your screen aspect ratio would also affect that calculation.
convert them to DIP:
stripImageView.getLayoutParams(). height =
(int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, <HEIGHT>,
getResources().getDisplayMetrics());
where HEIGHT is the height in px you want. You could base it off the strip height or something.

Get full display height of the device, specified in the device spec.

Is there an API in Android that returns the full screen height of the device? I'm interested in the full height as specified in the device spec, not the height of the viewable screen as returned by
android.view.Display.getHeight();
I spent some time looking for this and didn't find anything like what you're asking for. Part of the problem is that the bar that takes up the pixels they're not including can potentially be of different sizes.
What I ended up doing is measuring the width of the device (which is the full width) and the not-quite-full-height to match against the standard resolutions with an approximate. It's not great. If you really need it exact, you can force an orientation change to match both dimensions exactly. That's pretty gross, though.
The real answer is that you're not supposed to care about the exact dimensions of the hardware and design using the OS-provided size buckets.
Does this not work for you?
DisplayMetrics dm = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(dm);
displayHeight = dm.heightPixels;
For me, displayHeight returns 960 pixels on my HTC Sensation
Try heightPixels on a DisplayMetrics object.

Categories

Resources