Android:如何根据屏幕大小缩放布局 [英] Android: how to scale a layout with screen size

查看:85
本文介绍了Android:如何根据屏幕大小缩放布局的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

考虑这种布局(从 但我觉得对于这样一个简单的问题应该有一个更简单的解决方案,不需要求助于太多的非 XML.

解决方案

这在很大程度上取决于您要创建的自定义 ViewViewGroup 类的数量.我能想到的具有最少自定义类的实现将是这样的(与您所描述的非常相似):

  • 为最大正方形定制FrameLayout,使用自定义onMeasure() 实现将高度与可用宽度相匹配(您已经提到过这个).
  • 嵌套 LinearLayout 实例使用权重使所有网格按钮的大小相同.

这种方法的最大缺点是效率.您需要大约 36 个 LinearLayout 实例来在较大的 9x9 网格内创建小的 9x9 网格......这是纯布局开销的 36 个视图.

<小时>

就文字大小而言,我可以想到几种方法来处理这个问题.一种是使用 Paint.measureTextBounds()(您可以获取任何 TextViewPaint 对象来进行测量)来确定大小您需要在测量后在每个按钮中制作文本.不幸的是,这将是一个有点迭代的过程,因为 Paint 根据给定文本的当前设置测量给定文本,因此您需要:

  1. 设置文字大小
  2. 测量边界
  3. 检查高度
  4. 重复直到大小合适

好消息是您只需要执行一次并将其应用于所有网格按钮,但您需要等到网格按钮被测量.

这里的另一个选择是在诸如 ImageView 之类的东西中显示图像而不是文本,它可以为您缩放内容到其大小.您可以使用我编写的 TextDrawable 之类的东西来将文本内容设置为可缩放而不会损失质量的图像.

<小时>

现在回到布局.您可以通过创建自定义 ViewGroup 来测量和布置网格(名称 GridLayout 已经被采用...用于此目的,所以我们称之为 BlockLayout).创建自定义 BlockLayout 将允许您测量每个块的大小并在具有单个父级而不是 4 个 LinearLayout 实例的网格中布置 9 个子视图.这与测量整个正方形的方法基本相同,只是平均划分.

然后,您可以仅使用 10 个布局开销实例来构建整个布局……如果您可以将整个内容编码到单个 ViewGroup 中,则甚至更少.

基本上,您可以编写越多的代码来扁平化视图层次结构,您的应用程序的整体运行效果就越好.

HTH

Consider this layout (pulled from here):

I'd like to understand the principles behind making this layout scale with screen size. For the square, a custom onMeasure function works nicely:

@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
    super.onMeasure(widthMeasureSpec, widthMeasureSpec);
}

The width and height of the custom Togglebuttons and Imagebuttons below should scale to fill the remainder of the screen, minus layout_margins, and the text and images within should scale to fill the buttons, minus padding. The outer margin should also scale.

My first thought was to use a relative layout to position the buttons, and layout_margin/padding attributes to create margins. However, relative layouts and layout_margin/padding require fixed pixel values, so they aren't scalable.

I then thought of using nested linear layouts with layout_weights to position the buttons, and placeholder views to create margins. Although these techniques are scalable, they don't work with buttons, because buttons have many attributes (text size, image size, corner radius, etc.) that require fixed pixel values. This limitation means, for example, that the following xml:

<ToggleButton 
    android:layout_weight="1"
    style="@style/myButton"
    [...] />
<View 
    android:layout_weight="1"/>
<ImageButton 
    android:layout_weight="1"
    style="@style/myButton"
    [...] />

won't necessarily make the two buttons, and the space between them, all the same width. It all depends on the text size, image size, etc. etc. of the buttons.

I've taken a look at this question but I feel there should be a simpler solution for such a simple problem, that shouldn't require resorting to too much non-XML.

解决方案

It depends a lot on the number of custom View and ViewGroup classes you want to create. An implementation with the least number of custom classes that I could think of would be something like this (very similar to what you've described):

  • Customized FrameLayout for the largest square, with a custom onMeasure() implementation to match the height to the available width (you mentioned this one already).
  • Nested LinearLayout instances using weight to get all the grid buttons to be the same size.

The big drawback to this approach is efficiency. You would need roughly 36 LinearLayout instances to create the small 9x9 grids inside of a larger 9x9 grid...that's 36 views of pure layout overhead.


As far as text sizing, there are a couple ways I could think of to handle this. One would be to use Paint.measureTextBounds() (you can get the Paint object of any TextView to do the measurements) to determine what size you need to make the text in each button after they have been measured. Unfortunately this would be a somewhat iterative process because the Paint measures a given text based on its current settings, so you would need to:

  1. Set the text size
  2. Measure bounds
  3. Check height
  4. Repeat until the size just fits

The good news is you would only need to do this once and just apply it to all the grid buttons, but you would need to wait until the grid buttons are measured.

Another option here would be to display an image instead of text inside of something like ImageView, which can scale the content for you to its size. You could use something like the TextDrawable that I wrote to set text content as an image that is scalable without quality loss.


Now back to the layout. You could gain back a ton of efficiency by creating a custom ViewGroup to measure and lay out the grid (the name GridLayout is already taken...and it doesn't quite serve this purpose, so let's call it BlockLayout). Creating a custom BlockLayout will allow you to measure the size of each block and lay out 9 subviews in a grid with a single parent instead of 4 LinearLayout instances. This is basically the same way that you measure the overall square, just divided evenly.

You could then build the entire layout with only 10 instances of layout overhead...and even less if you can code the entire thing into a single ViewGroup.

Basically the more code you can write to flatten the view hierarchy, the better your application will run overall.

HTH

这篇关于Android:如何根据屏幕大小缩放布局的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆