Intereting Posts
Уведомление о статусе в телефонной трубке Android Исключение исключений в Firebase runloop (3.0.0) Обратный вызов Ble scan вызывает только несколько раз, а затем останавливается Заменить (или «переопределить») строку в проекте библиотеки Android Что такое атрибут android: ems в редакторе текста? Растровые изображения ALPHA_8 и getPixel FragmentPagerAdapter getItem не запускается Как я могу получить контактные события, синхронизированные с контактами Google без года? PhoneGap Android получит код версии приложения Различные макеты для разных размеров экрана на Android? Создание собственного приложения для камеры + Автоматический захват изображения Android: Как получить текущее смещение X для RecyclerView? Дублируемая запись: com / google / firebase / FirebaseApiNotAvailableException.class Установка Ellipsize в TextView уменьшает линии, показанные одним (вместо того, чтобы только эллипсизация последней) Проверка использования кнопки громкости при выключенном экране

Android: масштабировать графическое или фоновое изображение?

На макете я хочу масштабировать фоновое изображение (сохраняя его соотношение сторон) до места, выделенного при создании страницы. Кто-нибудь знает, как это сделать?

Я использую layout.setBackgroundDrawable (), и я использую BitmapDrawable для setGravity для отсечения и заполнения, но не вижу возможности для масштабирования.

Solutions Collecting From Web of "Android: масштабировать графическое или фоновое изображение?"

Чтобы настроить масштабирование фонового изображения, создайте такой ресурс:

<?xml version="1.0" encoding="utf-8"?> <bitmap xmlns:android="http://schemas.android.com/apk/res/android" android:gravity="center" android:src="@drawable/list_bkgnd" /> 

Затем он будет центрирован в представлении, если он используется в качестве фона. Существуют и другие флаги: http://developer.android.com/guide/topics/resources/drawable-resource.html

Не пытались сделать именно то, что вы хотите, но вы можете масштабировать ImageView с помощью android:scaleType="fitXY"
И размер будет соответствовать размеру, который вы даете ImageView.

Таким образом, вы можете создать FrameLayout для своего макета, поместить в него ImageView, а затем любой другой контент, который вам нужен в FrameLayout, а также прозрачный фон.

 <FrameLayout android:layout_width="fill_parent" android:layout_height="fill_parent"> <ImageView android:layout_width="fill_parent" android:layout_height="fill_parent" android:src="@drawable/back" android:scaleType="fitXY" /> <LinearLayout>your views</LinearLayout> </FrameLayout> 

Существует простой способ сделать это из доступных:

your_drawable.xml

 <?xml version="1.0" encoding="utf-8"?> <layer-list xmlns:android="http://schemas.android.com/apk/res/android" > <item android:drawable="@color/bg_color"/> <item> <bitmap android:gravity="center|bottom|clip_vertical" android:src="@drawable/your_image" /> </item> </layer-list> 

Единственным недостатком является то, что, если места недостаточно, ваше изображение не будет полностью показано, но оно будет обрезано, я не смог бы найти способ сделать это прямо из drawable. Но из тестов я сделал это очень хорошо, и он не обрезает большую часть изображения. Вы можете играть больше с возможностями гравитации.

Другой способ – просто создать макет, где вы будете использовать ImageView и установить scaleType для fitCenter .

Чтобы сохранить соотношение сторон, вы должны использовать android:scaleType=fitCenter или fitStart и т. Д. Использование fitXY не сохранит исходное соотношение сторон изображения!

Обратите внимание, что это работает только для изображений с атрибутом src , а не для фонового изображения.

Использовать изображение в качестве фона для макета:

 <?xml version="1.0" encoding="utf-8"?> <FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="wrap_content" > <ImageView android:id="@+id/imgPlaylistItemBg" android:layout_width="match_parent" android:layout_height="match_parent" android:adjustViewBounds="true" android:maxHeight="0dp" android:scaleType="fitXY" android:src="@drawable/img_dsh" /> <LinearLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="vertical" > </LinearLayout> </FrameLayout> 

Когда вы устанавливаете Drawable ImageView с помощью метода setBackgroundDrawable , изображение всегда будет масштабироваться. Параметры как adjustViewBounds или различные ScaleTypes будут просто проигнорированы. Единственное решение для сохранения соотношения сторон, которое я нашел, заключается в изменении размера ImageView после загрузки вашего рисунка. Вот фрагмент кода, который я использовал:

 // bmp is your Bitmap object int imgHeight = bmp.getHeight(); int imgWidth = bmp.getWidth(); int containerHeight = imageView.getHeight(); int containerWidth = imageView.getWidth(); boolean ch2cw = containerHeight > containerWidth; float h2w = (float) imgHeight / (float) imgWidth; float newContainerHeight, newContainerWidth; if (h2w > 1) { // height is greater than width if (ch2cw) { newContainerWidth = (float) containerWidth; newContainerHeight = newContainerWidth * h2w; } else { newContainerHeight = (float) containerHeight; newContainerWidth = newContainerHeight / h2w; } } else { // width is greater than height if (ch2cw) { newContainerWidth = (float) containerWidth; newContainerHeight = newContainerWidth / h2w; } else { newContainerWidth = (float) containerHeight; newContainerHeight = newContainerWidth * h2w; } } Bitmap copy = Bitmap.createScaledBitmap(bmp, (int) newContainerWidth, (int) newContainerHeight, false); imageView.setBackgroundDrawable(new BitmapDrawable(copy)); LayoutParams params = new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT); imageView.setLayoutParams(params); imageView.setMaxHeight((int) newContainerHeight); imageView.setMaxWidth((int) newContainerWidth); 

В приведенном выше фрагменте кода показан BMP объект Bitmap, который должен быть показан, а imageView – это объект ImageView

Важно отметить изменение параметров макета . Это необходимо, потому что setMaxHeight и setMaxWidth будут иметь значение только в том случае, если ширина и высота определены для обертывания содержимого, а не для заполнения родителя. Заполните родителя с другой стороны, это желаемый параметр в начале, потому что иначе containerWidth и containerHeight оба будут иметь значения, равные 0. Итак, в вашем файле макета у вас будет что-то вроде этого для вашего ImageView:

 ... <ImageView android:id="@+id/my_image_view" android:layout_width="fill_parent" android:layout_height="fill_parent"/> ... 

Это не самое эффективное решение, но, как кто-то предложил вместо фона, вы можете создать FrameLayout или RelativeLayout и использовать ImageView в качестве псевдо-фона – другие элементы будут находиться над ним просто над ним:

 <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_height="match_parent" android:layout_width="match_parent"> <ImageView android:id="@+id/ivBackground" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_alignParentLeft="true" android:layout_alignParentTop="true" android:scaleType="fitStart" android:src="@drawable/menu_icon_exit" /> <Button android:id="@+id/bSomeButton" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_alignParentLeft="true" android:layout_alignParentTop="true" android:layout_marginLeft="61dp" android:layout_marginTop="122dp" android:text="Button" /> </RelativeLayout> 

Проблема с ImageView заключается в том, что доступны только типы scaleTypes: CENTER, CENTER_CROP, CENTER_INSIDE, FIT_CENTER, FIT_END, FIT_START, FIT_XY, MATRIX ( http://etcodehome.blogspot.de/2011/05/android-imageview-scaletype-samples.html )

И «масштабировать фоновое изображение (сохраняя его соотношение сторон)» в некоторых случаях, когда вы хотите, чтобы изображение заполняло весь экран (например, фоновое изображение), а соотношение сторон экрана отличается от изображения, необходимый тип scaleType является добрым TOP_CROP, потому что:

CENTER_CROP центрирует масштабированное изображение вместо выравнивания верхнего края к верхнему краю изображения, а FIT_START соответствует высоте экрана и не заполняет ширину. И как пользователь Anke заметил, что FIT_XY не поддерживает соотношение сторон.

С радостью кто-то расширил ImageView для поддержки TOP_CROP

 public class ImageViewScaleTypeTopCrop extends ImageView { public ImageViewScaleTypeTopCrop(Context context) { super(context); setup(); } public ImageViewScaleTypeTopCrop(Context context, AttributeSet attrs) { super(context, attrs); setup(); } public ImageViewScaleTypeTopCrop(Context context, AttributeSet attrs, int defStyle) { super(context, attrs, defStyle); setup(); } private void setup() { setScaleType(ScaleType.MATRIX); } @Override protected boolean setFrame(int frameLeft, int frameTop, int frameRight, int frameBottom) { float frameWidth = frameRight - frameLeft; float frameHeight = frameBottom - frameTop; if (getDrawable() != null) { Matrix matrix = getImageMatrix(); float scaleFactor, scaleFactorWidth, scaleFactorHeight; scaleFactorWidth = (float) frameWidth / (float) getDrawable().getIntrinsicWidth(); scaleFactorHeight = (float) frameHeight / (float) getDrawable().getIntrinsicHeight(); if (scaleFactorHeight > scaleFactorWidth) { scaleFactor = scaleFactorHeight; } else { scaleFactor = scaleFactorWidth; } matrix.setScale(scaleFactor, scaleFactor, 0, 0); setImageMatrix(matrix); } return super.setFrame(frameLeft, frameTop, frameRight, frameBottom); } } 

https://stackoverflow.com/a/14815588/2075875

Теперь IMHO был бы идеальным, если бы кто-нибудь написал пользовательский Drawable, который масштабирует изображение таким образом. Затем он может использоваться в качестве фонового параметра.


Reflog предлагает предварительно масштабировать перед использованием. Вот инструкция, как это сделать: Java (Android): Как масштабировать чертеж без растрового изображения? Хотя это имеет недостаток, что масштабируемое масштабируемое / растровое изображение будет использовать больше ОЗУ, а масштабирование «на лету», используемое ImageView, не требует больше памяти. Преимущество может быть меньше нагрузки процессора.

Что предлагает Dweebo. Но по моему скромному мнению это не нужно. Одиночный вес фонаря сам по себе. Представление должно иметь фиксированную ширину и высоту, как в следующем примере:

  < RelativeLayout android:layout_width="fill_parent" android:layout_height="fill_parent" android:background="@android:color/black"> <LinearLayout android:layout_width="500dip" android:layout_height="450dip" android:layout_centerInParent="true" android:background="@drawable/my_drawable" android:orientation="vertical" android:padding="30dip" > ... </LinearLayout> < / RelativeLayout> 

Код «Ниже» делает растровое изображение совершенно одинаковым размером изображения. Получите высоту и ширину растрового изображения, а затем вычислите новую высоту и ширину с помощью параметров изображения. Это даст вам требуемое изображение с наилучшим соотношением сторон.

 int bwidth=bitMap1.getWidth(); int bheight=bitMap1.getHeight(); int swidth=imageView_location.getWidth(); int sheight=imageView_location.getHeight(); new_width=swidth; new_height = (int) Math.floor((double) bheight *( (double) new_width / (double) bwidth)); Bitmap newbitMap = Bitmap.createScaledBitmap(bitMap1,new_width,new_height, true); imageView_location.setImageBitmap(newbitMap) 

Один из вариантов – разместить изображение в папке drawable-nodpi и установить фон макета для идентификатора ресурса.

Это определенно работает с уменьшением масштаба, но я еще не тестировал его масштабирование.

Вам придется предварительно масштабировать эту возможность, прежде чем использовать ее в качестве фона

Вы можете использовать один из следующих вариантов:

Android: гравитация = "fill_horizontal | clip_vertical"

Или

Android: гравитация = "fill_vertical | clip_horizontal"