Drawable的getIntrinsicHeight()和getIntrinsicWidth()

简介:

版权声明:本文为博主原创文章,未经博主允许不得转载。

今天遇到一个问题,一个Bitmap封装到BitmapDrawable中 ,BitmapDrawable drawable = new BitmapDrawable(bmp),

Bitmap.getWidth() != BitmapDrawable.getIntrinsicWidth().导致一些问题:

查看源代码,问题如下:

在BitmapDrawable中,给mBitmapWidth赋值时,要根据density缩放,其默认值是160,mdpi的情况:

 mTargetDensity = DisplayMetrics.DENSITY_DEFAULT;

而在Bitmap的density是240情况下,将缩放:

公式约等于为:drawableDensity * bmpWidth / bmpDensity  ======>>  160 * 72 / 240  ,所以getIntrinsicHeight()为48

在BitmapDrawable中:

 

 

[java]  view plain  copy
 
print?
  1. private void computeBitmapSize() {  
  2.       mBitmapWidth = mBitmap.getScaledWidth(mTargetDensity);  
  3.       mBitmapHeight = mBitmap.getScaledHeight(mTargetDensity);  
  4.   }  
  private void computeBitmapSize() {
        mBitmapWidth = mBitmap.getScaledWidth(mTargetDensity);
        mBitmapHeight = mBitmap.getScaledHeight(mTargetDensity);
    }

 

[java]  view plain  copy
 
print?
  1. @Override  
  2.    public int getIntrinsicWidth() {  
  3.        return mBitmapWidth;  
  4.    }  
  5.   
  6.    @Override  
  7.    public int getIntrinsicHeight() {  
  8.        return mBitmapHeight;  
  9.    }  
 @Override
    public int getIntrinsicWidth() {
        return mBitmapWidth;
    }

    @Override
    public int getIntrinsicHeight() {
        return mBitmapHeight;
    }

[java]  view plain  copy
 
print?
  1. private BitmapDrawable(BitmapState state, Resources res) {  
  2.         mBitmapState = state;  
  3.         if (res != null) {  
  4.             mTargetDensity = res.getDisplayMetrics().densityDpi;  
  5.         } else if (state != null) {  
  6.             mTargetDensity = state.mTargetDensity;  
  7.         } else {  
  8.             mTargetDensity = DisplayMetrics.DENSITY_DEFAULT;  
  9.         }  
  10.         setBitmap(state.mBitmap);  
  11.     }  
private BitmapDrawable(BitmapState state, Resources res) {
        mBitmapState = state;
        if (res != null) {
            mTargetDensity = res.getDisplayMetrics().densityDpi;
        } else if (state != null) {
            mTargetDensity = state.mTargetDensity;
        } else {
            mTargetDensity = DisplayMetrics.DENSITY_DEFAULT;
        }
        setBitmap(state.mBitmap);
    }

 

在ButtonState中,mTargetDensity的值默认为:

int mTargetDensity = DisplayMetrics.DENSITY_DEFAULT;

注意:res == null时,且state != null时,mTargetDensity = state.mTargetDensity;

 

[java]  view plain  copy
 
print?
  1. /** 
  2.     * Create an empty drawable, setting initial target density based on 
  3.     * the display metrics of the resources. 
  4.     */  
  5.    public BitmapDrawable(Resources res) {  
  6.        mBitmapState = new BitmapState((Bitmap) null);  
  7.        mBitmapState.mTargetDensity = mTargetDensity;  
  8.    }  
  9.   
  10.    /** 
  11.     * Create drawable from a bitmap, not dealing with density. 
  12.     * @deprecated Use {@link #BitmapDrawable(Resources, Bitmap)} to ensure 
  13.     * that the drawable has correctly set its target density. 
  14.     */  
  15.    @Deprecated  
  16.    public BitmapDrawable(Bitmap bitmap) {  
  17.        this(new BitmapState(bitmap), null);  
  18.    }  
 /**
     * Create an empty drawable, setting initial target density based on
     * the display metrics of the resources.
     */
    public BitmapDrawable(Resources res) {
        mBitmapState = new BitmapState((Bitmap) null);
        mBitmapState.mTargetDensity = mTargetDensity;
    }

    /**
     * Create drawable from a bitmap, not dealing with density.
     * @deprecated Use {@link #BitmapDrawable(Resources, Bitmap)} to ensure
     * that the drawable has correctly set its target density.
     */
    @Deprecated
    public BitmapDrawable(Bitmap bitmap) {
        this(new BitmapState(bitmap), null);
    }
[java]  view plain  copy
 
print?
  1.     /** 
  2.      * Create drawable from a bitmap, setting initial target density based on 
  3.      * the display metrics of the resources. 
  4.      */  
  5.     public BitmapDrawable(Resources res, Bitmap bitmap) {  
  6.         this(new BitmapState(bitmap), res);  
  7.         mBitmapState.mTargetDensity = mTargetDensity;  
  8.     }  
    /**
     * Create drawable from a bitmap, setting initial target density based on
     * the display metrics of the resources.
     */
    public BitmapDrawable(Resources res, Bitmap bitmap) {
        this(new BitmapState(bitmap), res);
        mBitmapState.mTargetDensity = mTargetDensity;
    }

其中,BitmapDrawable(Bitmap bmp)已经被弃用,如果使用 BitmapDrawable(Bitmap bmp,Resources res)构造函数

 

 

在DisplayMetrics:

[java]  view plain  copy
 
print?
  1.  public static final int DENSITY_DEFAULT = DENSITY_MEDIUM;  
 public static final int DENSITY_DEFAULT = DENSITY_MEDIUM;

 

在Bitmap中:

 

[java]  view plain  copy
 
print?
  1. /** 
  2.   * Convenience method that returns the width of this bitmap divided 
  3.   * by the density scale factor. 
  4.   * 
  5.   * @param targetDensity The density of the target canvas of the bitmap. 
  6.   * @return The scaled width of this bitmap, according to the density scale factor. 
  7.   */  
  8.  public int getScaledWidth(int targetDensity) {  
  9.      return scaleFromDensity(getWidth(), mDensity, targetDensity);  
  10.  }  
  11.   
  12.  /** 
  13.   * Convenience method that returns the height of this bitmap divided 
  14.   * by the density scale factor. 
  15.   * 
  16.   * @param targetDensity The density of the target canvas of the bitmap. 
  17.   * @return The scaled height of this bitmap, according to the density scale factor. 
  18.   */  
  19.  public int getScaledHeight(int targetDensity) {  
  20.      return scaleFromDensity(getHeight(), mDensity, targetDensity);  
  21.  }  
  22.    
  23.  /** 
  24.   * @hide 
  25.   */  
  26.  static public int scaleFromDensity(int size, int sdensity, int tdensity) {  
  27.      if (sdensity == DENSITY_NONE || sdensity == tdensity) {  
  28.          return size;  
  29.      }  
  30.        
  31.      // Scale by tdensity / sdensity, rounding up.  
  32.      return ( (size * tdensity) + (sdensity >> 1) ) / sdensity;  
  33.  }  
   /**
     * Convenience method that returns the width of this bitmap divided
     * by the density scale factor.
     *
     * @param targetDensity The density of the target canvas of the bitmap.
     * @return The scaled width of this bitmap, according to the density scale factor.
     */
    public int getScaledWidth(int targetDensity) {
        return scaleFromDensity(getWidth(), mDensity, targetDensity);
    }

    /**
     * Convenience method that returns the height of this bitmap divided
     * by the density scale factor.
     *
     * @param targetDensity The density of the target canvas of the bitmap.
     * @return The scaled height of this bitmap, according to the density scale factor.
     */
    public int getScaledHeight(int targetDensity) {
        return scaleFromDensity(getHeight(), mDensity, targetDensity);
    }
    
    /**
     * @hide
     */
    static public int scaleFromDensity(int size, int sdensity, int tdensity) {
        if (sdensity == DENSITY_NONE || sdensity == tdensity) {
            return size;
        }
        
        // Scale by tdensity / sdensity, rounding up.
        return ( (size * tdensity) + (sdensity >> 1) ) / sdensity;
    }

如此,只有做如下改动:

方法一:

BitmapDrawable bmpDrawable = new BitmapDrawable(bmp,getResources);

方法二:

BitmapDrawable bmpDrawable = new BitmapDrawable(bmp);

bmpDrawable.setTargetDensity(getResources().getResources().getDisplayMetrics());

 

借鉴: http://blog.csdn.net/jason_wks/article/details/8283224




    本文转自 一点点征服   博客园博客,原文链接:http://www.cnblogs.com/ldq2016/p/5377670.html,如需转载请自行联系原作者


相关文章
|
Ubuntu Linux Docker
Docker安装和卸载
一:卸载旧版本 老版本的Docker被称为docker或docker-engine。如果安装了这些,请卸载它们以及相关的依赖项。 $ sudo yum remove docker \ docker-common \ docker-selinux \ docker-engine 如果yum报告说没有安装这些软件包,那么也行。
19951 0
|
Android开发
【RecyclerView】 五、RecyclerView 布局 ( 瀑布流 | 交错网格局管理器 StaggeredGridLayoutManager )
【RecyclerView】 五、RecyclerView 布局 ( 瀑布流 | 交错网格局管理器 StaggeredGridLayoutManager )
845 0
【RecyclerView】 五、RecyclerView 布局 ( 瀑布流 | 交错网格局管理器 StaggeredGridLayoutManager )
|
消息中间件 前端开发 安全
简化部署流程:Rainbond让Jeepay支付系统部署更轻松
在如今的开发环境中,部署一套像 Jeepay 这样的 Java 支付系统往往需要开发者面对繁琐的配置、依赖环境管理以及服务的高可用性保障,手动部署和运维变得异常艰巨和费时。然而,借助 Rainbond 这样的云原生 PaaS 平台,这一过程变得前所未有的简单。通过 Rainbond 的“点点点”式应用管理和自动化运维功能,开发者可以轻松完成 Jeepay 系统的部署,极大减少了传统的部署难度和复杂性,让你更专注于业务的快速迭代和创新。 本文将详细介绍如何通过 Rainbond 平台一步步部署 Jeepay 系统,无需复杂的配置,只需简单操作即可完成,帮助开发者快速构建一个稳定、安全的支付系统
简化部署流程:Rainbond让Jeepay支付系统部署更轻松
|
Java Android开发 芯片
使用Android Studio导入Android源码:基于全志H713 AOSP,方便解决编译、编码问题
本文介绍了如何将基于全志H713芯片的AOSP Android源码导入Android Studio以解决编译和编码问题,通过操作步骤的详细说明,展示了在Android Studio中利用代码提示和补全功能快速定位并修复编译错误的方法。
1042 0
使用Android Studio导入Android源码:基于全志H713 AOSP,方便解决编译、编码问题
|
存储 Java
Java运算符及运算符的优先级【超详细】
Java运算符及运算符的优先级【超详细】
1980 0
|
缓存 Java Maven
Maven找不到依赖终极解决方案
Maven找不到依赖终极解决方案
1732 0
|
Java API Apache
maven常见问题汇总
child module ….pom.xml does not exist a.注意module的名称是否正确,有时候命名问题会导致找不到项目的 b.注意一开始项目命名的规则问题注意一开始项目命名的规则问题         使用maven-compiler-plugin 时 POM...
19570 0
|
Android开发
Android 10.0 锁屏壁纸 LockscreenWallpaper(三)
Android 10.0 锁屏壁纸 LockscreenWallpaper(三)
Android 10.0 锁屏壁纸 LockscreenWallpaper(三)