如果无法获得尺寸,您应该如何“有效地加载大位图”?

时间:2017-01-24 06:35:00

标签: android file bitmap imageview

我对所有这些官方Android文档感到非常沮丧,这些文档很方便地掩盖了这样一个事实:即使将Bitmap应用于ImageView,ImageView的尺寸也是0,0,但是你无法获得之前的尺寸映射,或者!

https://developer.android.com/training/displaying-bitmaps/load-bitmap.html

所有这些方法都假设你已经知道ImageView的像素高度和宽度的固定尺寸,但这几乎是无用的,因为在实践中你应该使用dp单位或layout_weight,所以事情缩放到可视区域所以在各种手机上看起来都很正常。

看起来唯一的方法是获得尺寸是为了无法有效地映射位图,然后以这种方式获得尺寸,但即使你这样做,尺寸也会显示为0如果你这样做imageView.getWidth()getHeight()!你必须做一堆奇怪的异步东西,等到维度以某种方式“解决”,然后你最终可以获得维度,但在这个阶段,当你已经浪费时间进行效率低下的映射时,重点是什么?

谷歌没有在文档中解释,是否有一些众所周知的解决方法?当您不使用XML中的像素时,您应该如何知道ImageView尺寸?对我来说令人难以置信的是,这不是更多的记录。

以下是问题的示例:

<ImageView
android:id="@+id/my_imageview"
android:layout_width="match_parent"
android:layout_height="0dp"
android:layout_weight="1"/>

我在DialogFragment中有这个ImageView。我的想法是我可以将一个Bitmap映射到这个ImageView,它将通过类似myImageView.setImageBitmap(BitmapFactory.decodeFile(path_to_file));之类的东西放入DialogFragment中,但如果Bitmap很大,这本身就是低效的。

但是,为了有效加载Bitmap,您需要已经知道ImageView的尺寸 - 以像素为单位!但是,在您已经有效地 中映射的位图并且等待维度已经确定的某种后执行阶段之前,您无法获得ImageView的维度英寸

这些是我用来进行有效映射的方法(假设你已经知道了大小 - 如果其中一个维度是0,它会中断,所以我添加了一个修复)。此代码来自Google:

public static int calculateInSampleSize(
        BitmapFactory.Options options, int reqWidth, int reqHeight) {
    // Raw height and width of image
    final int height = options.outHeight;
    final int width = options.outWidth;
    int inSampleSize = 1;
    if (height == 0 || width == 0) {
        return 0; //my fix
    }

    if (height > reqHeight || width > reqWidth) {

        final int halfHeight = height / 2;
        final int halfWidth = width / 2;

        // Calculate the largest inSampleSize value that is a power of 2 and keeps both
        // height and width larger than the requested height and width.
        while ((halfHeight / inSampleSize) >= reqHeight
                && (halfWidth / inSampleSize) >= reqWidth) {
            inSampleSize *= 2;
        }
    }

    return inSampleSize;
}

public static Bitmap decodeSampledBitmapFromFilePath(String pathName, int reqWidth, int reqHeight) {

    // First decode with inJustDecodeBounds=true to check dimensions
    final BitmapFactory.Options options = new BitmapFactory.Options();
    options.inJustDecodeBounds = true;
    BitmapFactory.decodeFile(pathName, options);

    // Calculate inSampleSize
    options.inSampleSize = calculateInSampleSize(options, reqWidth, reqHeight);

    // Decode bitmap with inSampleSize set
    options.inJustDecodeBounds = false;
    return BitmapFactory.decodeFile(pathName, options);
}

例如,这不起作用:

    myImageView.post(new Runnable() {
        @Override
        public void run() {
            int reqHeight = myImageView.getHeight(); //height = 0
            int reqWidth = myImageView.getWidth(); //width = 528

            final BitmapFactory.Options options = new BitmapFactory.Options();
            options.inJustDecodeBounds = true;
            BitmapFactory.decodeFile(picFullPath, options);
            int realWidth = options.outWidth;
            int realHeight = options.outHeight;

            reqHeight = realHeight * reqWidth / realWidth; //reqHeight = 396, reqWidth = 528
            Bitmap bm = decodeSampledBitmapFromFilePath(picFullPath, reqWidth, reqHeight);

            myImageView.setImageBitmap(bm);
        }
    });

    myImageView.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            int finalHeight = myImageView.getHeight(); //480!
            int finalWidth = myImageView.getWidth(); //608!
        }
    });

2 个答案:

答案 0 :(得分:0)

从XML或动态扩展任何视图后,您应该获得视图的高度和宽度,然后使用下面的代码来获取渲染视图的高度和宽度:

        imageView.measure(0,0);
        imageView.getMeasuredHeight();
        imageView.getMeasuredWidth();

但是如果您没有从XML传递任何高度和宽度,或者您没有在相对布局中使用任何相对属性,则Above方法的高度和宽度可能为0;

答案 1 :(得分:0)

在我知道(sentence) | (sentence) ::= (noun phrase) (verb phrase) (noun phrase) (verb phrase) | (noun phrase) ::= (determiner) (noun) (determiner) (noun) (verb phrase) | (determiner) ::= "a" "a" (noun) (verb phrase) | (noun) ::= "bug" "a" "bug" (verb phrase) | (verb phrase) ::= (transitive verb) (noun phrase) "a" "bug" (transitive verb) (noun phrase) | (transitive verb) ::= "liked" "a" "bug" "liked" (noun phrase) | (noun phrase) ::= (pronoun) "a" "bug" "liked" (pronoun) | (pronoun) ::= "you" "a" "bug" "liked" "you" size:

之后我需要加载位图时,我使用这种方法
ImageView