Нарисуйте растровое изображение фиксированного размера на холсте - PullRequest
0 голосов
/ 02 июня 2018

Я создаю карточную игру, для этого я создал собственный вид поверхности, в котором загружаются изображения.Поскольку изображения загружаются из Интернета, они имеют разные размеры и выглядят визуально плохо на экране.Здесь я хочу добиться двух вещей.

  1. Загрузка изображений фиксированного размера или динамическое изменение размеров изображений.
  2. Рисование изображений снизу экрана в направлении вверх.

Для 1-го пункта я использовал метод CreateBitmap, но получил исключение ниже.

java.lang.OutOfMemoryError: Failed to allocate a 1915060280 byte allocation with 4194304 free bytes and 123MB until OOM error

Чтобы исправить проблему, я думал об использовании Glide / Picasso, основываясь на этом вопросе и this , но я обнаружил, что Glide / Picasso загружают только изображенияна изображении, но у меня нет изображения, я получил только пользовательский вид поверхности внутри линейного разметки.

Для 2-й точки я использовал поворот изображения.Ниже приведен код этого кода.

  public  void Render(Canvas paramCanvas)
    {

        try
        {
            // paramCanvas.DrawColor(Android.Graphics.Color.Blue);


            int i = 0;
            Down_Card_Gap = 0;
            foreach (Cards localcard in FaceDownDeck.ToList())
            {


                Bitmap localimage = BitmapFactory.DecodeResource(Resources, localcard.GetImageId(context));  
                Bitmap rotatedimage = RotateBitmap(localimage, 180);
                paramCanvas.DrawBitmap(rotatedimage, (Screen_Center_X - Card_Width / 2)+Down_Card_Gap, (Screen_Height - Card_Height), null);
               //   paramCanvas.DrawBitmap(localimage, (Screen_Center_X - Card_Width / 2), (Screen_Center_Y - Card_Height), null);


                if (i++ == 7)
                { break; }
                if (Down_Card_Gap > 0)
                {
                    Down_Card_Gap += Card_Width / 2; 
                }
                else
                {
                    Down_Card_Gap -= Card_Width / 2;
                }
                Down_Card_Gap *= -1;
            }
        }
        catch (Exception ex)
        {
            System.Diagnostics.Debug.WriteLine(ex.ToString());
        }
    }

    private Bitmap RotateBitmap(Bitmap localimage, float angle)
    {
         Matrix matrix = new Matrix();
        matrix.PostRotate(angle);
        matrix.PostScale(Card_Width, Card_Height);
        Bitmap resized= Bitmap.CreateBitmap(localimage, 0, 0, localimage.Width, localimage.Height, matrix, true);
        localimage.Recycle();
        return resized;
    }

Я хочу знать, является ли это правильным подходом или же существует какой-либо более эффективный способ достижения функциональности.

1 Ответ

0 голосов
/ 05 июня 2018

Загрузка изображений фиксированного размера или динамическое изменение размеров изображений.

О фиксированном размере и размере можно обратиться к этому , найти decodeFile метод:

   protected Bitmap decodeFile(File f) {
        try { 
            //decode image size 
            BitmapFactory.Options o = new BitmapFactory.Options();
            o.inJustDecodeBounds = true;
            BitmapFactory.decodeStream(new FileInputStream(f), null, o);

            //Find the correct scale value. It should be the power of 2. 
            final int REQUIRED_SIZE = 150;
            int width_tmp = o.outWidth, height_tmp = o.outHeight;
            int scale = 1;
            while (true) { 
                if (width_tmp / 2 < REQUIRED_SIZE || height_tmp / 2 < REQUIRED_SIZE)
                    break; 
                width_tmp /= 2;
                height_tmp /= 2;
                scale *= 2;
            } 

            //decode with inSampleSize 
            BitmapFactory.Options o2 = new BitmapFactory.Options();
            o2.inSampleSize = scale;
            return BitmapFactory.decodeStream(new FileInputStream(f), null, o2);
        } catch (FileNotFoundException e) {
        } 
        return null; 
    } 

Как видите, он использует BitmapFactory.Options.inJustDecodeBounds= true для предварительной загрузки растрового изображения и масштабирования растрового изображения.Также вы можете сослаться на официальный документ .Прочитайте this , чтобы сжать качество растрового изображения.

Кроме этого, вам также необходимо рассмотреть кэш изображений. Это говорит о том, как создать эффективный кэш памяти для растровых изображений.

...