1

据我所知(如果我错了,请纠正我),如果你想在多种尺寸的设备上拥有看起来不错的图形按钮(具有很好的抗锯齿功能),你必须创建不同的一组不同尺寸的图像并将图像放在不同目录的集合中。我正在寻找一个工作示例,准确显示要使用的目录集以及这些目录需要的相对大小。

顺便说一句,当我说 ImageButtons 时,我的意思是包含一个图像而不是文本 - 所以 9patch 图像不会起作用。

编辑:让我特别困惑的一件事是,我经常看到人们使用不同屏幕密度的例子(例如chuck258的答案) ......但是如果你制作的按钮的宽度和高度针对密度进行了调整,那么您的按钮占用的屏幕可能会以各种不受控制的方式变化,如果您的屏幕密度高但尺寸较小,那么您的按钮将过大。

编辑:在我上次编辑之后,也许我应该更具体地说明我想要什么......让我们说我想要一个大约 10% 的方形 ImageButton(我会接受从 8% 到 13% 的变化) (仅限纵向)屏幕的宽度......我将制作多大尺寸的图像以及它们将在哪些目录中?

编辑:我收到的信息是,如果你有更多的屏幕空间,那么标准的做法是让图标占据屏幕的一小部分。这大概是因为允许图标变得非常大,使它们看起来更像玩具或幼稚。但问题是,我正在为儿童制作游戏应用程序!所以这正是我想要的。

4

8 回答 8

11

首先你需要了解屏幕密度和屏幕尺寸的区别。

屏幕尺寸是物理尺寸,以屏幕的对角线测量。Android 将所有实际屏幕尺寸分为四种通用尺寸:小、普通、大和特大。一部手机的屏幕尺寸可能为 4.9 英寸,这被认为是正常的,Nexus 7(2012 年的旧款和 2013 年的新款)的屏幕尺寸都是 7 英寸,这很大,Nexus 10 的屏幕尺寸10 英寸,这是超大的。

另一方面,屏幕密度是屏幕物理区域内的像素数量;通常称为 dpi(每英寸点数)。例如,与“正常”或“高”密度屏幕相比,“低”密度屏幕在给定物理区域内的像素较少。为简单起见,Android 将所有实际屏幕密度分为四种通用密度:低、中、高和超高(加上新的 xxhdpi)。旧的 Nexus 7 的屏幕尺寸与新的 Nexus 7 相同,但旧的分辨率为 1280x800,即 216 dpi 或 hdpi,而新的分辨率为 1920×1200 像素,即 323 dpi 或 xhdpi(更多像素在同一物理区域内意味着更高的 dpi 像素密度)。

如果屏幕具有相同的屏幕密度,则可绘制文件夹中的图像在小屏幕、普通屏幕、大屏幕和超大屏幕上将具有相同的物理尺寸。因为屏幕具有不同的尺寸,所以图像将占据屏幕的不同部分。在小屏幕上,它会比在大屏幕上占据更大的百分比。

如果相同的图像位于屏幕大小的文件夹之一(drawable-small、drawable-normal、drawable-large、drawable-xlarge)中,则不会发生任何变化,但您可以决定将较大版本的图像放在 drawable-xlarge 中。在这种情况下,Nexus 10 上的图像会比新 Nexus 7 上的大(两者都有 xhdpi 像素密度)。

如果屏幕具有不同的像素密度,则相同的图像看起来会有所不同。与 mdpi 屏幕相比,xhdpi 屏幕上的图像大小只有一半(因为 xhdpi 屏幕的像素密度大约是两倍):http:
//developer.android.com/images/screens_support/density-test-bad.png

对于一个图标,您通常希望它在不同的屏幕上具有相同的大小。这就是为什么 mdpi 屏幕的菜单图标是 32x32 而 xhdpi 屏幕的菜单图标是 64x64 并且两者都在适当的可绘制文件夹(drawable-mdpi 和 drawable-xhdpi)中:http:
//developer.android.com/images/screens_support/density -test-good.png

现在什么时候使用像素密度,什么时候使用屏幕大小的可绘制文件夹?

如果图像在具有不同屏幕密度的屏幕上应具有相同的物理尺寸,则使用像素密度文件夹,这通常是您想要的。如果您对旧的和新的 Nexus 7 使用相同的图像,即使屏幕具有相同的物理尺寸,它也会有不同的尺寸,这不是您想要的。因此,使用密度相关图像势在必行。

如果您希望图像在小、普通、大和超大屏幕上具有不同的物理尺寸,则使用屏幕尺寸文件夹。如果我在主屏幕上有一个带有 6 个图标的网格导航,并且我不想在大屏幕上使用额外的屏幕空间(例如通过添加更多图标),那么我会为小屏幕提供一个小图像和大屏幕的大图像。如前所述,您仍然必须在依赖于屏幕尺寸的图像之上提供依赖于密度的图像(例如旧的 Nexus 7 与新的 Nexus 7)。

所以理论上你需要 16 个不同的资源来处理同一个图像(4 个屏幕尺寸,4 个屏幕密度,或者使用新的 xxhdpi 密度,甚至 5 个密度 -> 20 个资源)。现在当然没有人想创建那么多资源,尤其是如果你有很多图像。一种方法是按照某人的建议使用仪表板:http: //developer.android.com/about/dashboards/index.html#Screens
并选择最常用的组合,即 small/ldpi、normal/mdpi、normal/ hdpi 和 normal/xhdpi(所有设备的 81%)。这样你就可以将资源减少到只有 4
个。另一种方法是为屏幕大小或屏幕密度提供资源(同样只需要 4 个资源),然后在代码中进行一些缩放。

如果您有与屏幕密度相关的资源,那么您将使用例如此https://stackoverflow.com/a/5016350/534471来缩小图像(从不放大)。

如果您有依赖于屏幕尺寸的资源,那么您将使用此http://developer.android.com/reference/android/util/DisplayMetrics.html 来缩小图像。

这里有一个很好的例子(包括源代码): https ://www.captechconsulting.com/blog/steven-byle/understanding-density-independence-android

现在,对于您的具体问题,您可以在可绘制文件夹中使用一个通用图像。该图像的大小应该不会被放大(因为那看起来很难看)。您可以像这样在布局中定义按钮:

<ImageButton
    android:id="@+id/myButton"
    android:src="@drawable/myDrawable"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:scaleType="centerCrop"
    android:adjustViewBounds="true"
/>

连同这段代码,按钮缩放到屏幕的 10%:

Display display = getWindowManager().getDefaultDisplay();
Point screenSize = new Point();
display.getRealSize(screenSize);
int size = Math.min(screenSize.x, screenSize.y);
int buttonSize = Math.round(size * 0.1f);
ImageButton button = (ImageButton) findViewById(R.id.myButton);
button.setMaxWidth(buttonSize);
button.setMaxHeight(buttonSize);

原图应该多大?
Nexus 10 可能是目前所有 Android 设备中屏幕分辨率最高的。1600 像素将在其 xhdpi 显示器上转换为 3200 密度独立像素。3200 的 10% 是 320。如果您使用 320x320 图像,那么您将在所有现有设备上获得良好的结果。
不过,这种方法有一个问题。
320x320 相当大(可能是 24/32 位色深),因此您可能会遇到内存问题。如果您在与密度相关的可绘制文件夹中提供相同的资源,您可以降低 hdpi、mdpi 和 ldpi 设备的内存占用:

  • 可绘制 xhdpi:320x320
  • 可绘制的 hdpi:240x240
  • 可绘制 mdpi:160x160
  • 可绘制的 ldpi:120x120

屏幕大小的可绘制文件夹可用于进一步改善这一点(较小的屏幕需要较小的图像),但您必须提供前面提到的 16 或 20 个资源。最后,它是一方面的内存占用/速度与另一方面的可维护性/创建资源/ apk 大小的时间之间的权衡。

于 2013-10-19T03:33:44.190 回答
1

Android 平台通常的做法是只为不同的屏幕密度提供图像,而不是为屏幕尺寸提供图像。如果我使用平板电脑,我不想看到大图像,我想看到更多信息。所以最好不要增加视图的大小,而是为更大的屏幕提供不同的布局。

但是,如果您有特定的理由提供屏幕宽度的 10% 的图像,您可以使用具有不同限定符的“可绘制”文件夹。您对“可用宽度”、“屏幕尺寸”和“屏幕像素密度”限定词感兴趣。例如提供此图像:

  • drawable-sw320dp-mdpi - 图像 32px 宽度
  • drawable-sw320dp-hdpi - 图像 48px 宽度
  • drawable-sw320dp-xhdpi - 图像 64px 宽度
  • drawable-sw400dp-mdpi - 图像 40px 宽度
  • ...为您想要支持的所有设备提供图像
于 2013-10-18T11:10:40.680 回答
1

您应该始终为所有密度创建图像。大多数像图标这样的图像应该在dp方面是固定的高度。非固定高度的表面图像应该是可拉伸的 9patch 图像

更多关于 9patch 的信息:http: //developer.android.com/guide/topics/graphics/2d-graphics.html#nine-patch

于 2013-10-15T13:27:24.357 回答
1

我不知道我的问题是否正确,但有关图像的相对大小,请参阅:http: //developer.android.com/design/style/devices-displays.html

您可以为要支持的最大屏幕使用足够大的图像。然后scaleType="fitCenter"在您的图像中使用。这样做的一些缺点:

是的:ScaleType.FIT_CENTER是程序等效的fitCenter属性。一般来说,您可以期望 XML 中的每个属性都有一个 getter 和 setter。

于 2013-10-15T13:09:44.927 回答
0

转到您的项目-->Ctrl+n-->Android-->Android 图标集-->下一步-->输入图标名称-->下一步-->图像-->浏览->从您的PC-->无-->完成。就是这样,它将自动在 4 个名为的文件夹中创建 4 种不同尺寸的单个图像

1.drawable-hdpi 2.drawable-mdpi 3.drawable-xhdpi 4.drawable-xxhdpi

因此您可以在应用程序中使用此图像,它将根据设备屏幕尺寸获取该图像。

于 2013-10-22T16:10:19.527 回答
0

你可以这样做:

package com.example.test;

import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Point;
import android.os.Bundle;
import android.view.Display;
import android.view.Menu;
import android.widget.ImageButton;

public class MainActivity extends Activity {

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        //Get ImageButton from XML
        ImageButton ib = (ImageButton) findViewById(R.id.imageButton);
        //Get the screen size
        Display display = getWindowManager().getDefaultDisplay();
        Point size = new Point();
        display.getSize(size);
        //10% of the screen width
        int width = (int) (size.x * 0.1);
        //Get and scale the Bitmap (10% of screen width)
        Bitmap bitmap = getImage(R.drawable.ic_launcher, width, width);
        ib.setImageBitmap(bitmap);
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.main, menu);
        return true;
    }


    public Bitmap getImage (int id, int width, int height) {
        Bitmap bmp = BitmapFactory.decodeResource( getResources(), id );
        Bitmap img = Bitmap.createScaledBitmap( bmp, width, height, true );
        bmp.recycle();
        return img;
    }
}

和图像按钮:

<ImageButton
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:id="@+id/imageButton" />
于 2013-10-24T07:43:40.970 回答
0

这并不能完全回答你的问题。但是,如果您只是在寻找通用图标,请查看 t IconicDroid 库,它对我有很大帮助。您将能够根据需要调整图标的大小而无需查看质量,并且还可以节省大量空间,因此 apk 会更小。google Play上有这个库的演示。

于 2013-10-24T13:29:46.460 回答
0

假设您 nedd imageButotn 10% 的宽度对于不同的屏幕尺寸它将是 32 for (320x480) mdpi 48 for(480x800|854) hdpi 64 for(640x1024 (galaxy tab 7")) large-hdpi 72 for(720x1280 (nexus) 7)) large-tvdipi 72 for(720x1280 (xperia sp,etc) xhdpi 80 for(800x1280 (motorola xoom 10") xlarge-mdpi 108 for(1080x1920 (xperia z,etc) xxhdpi 所以你可以制作所有这些尺寸和将它们放在应有的文件夹中。

于 2013-10-25T09:45:16.180 回答