android - 在发送到 Wallpapermanager 之前调整位图大小

标签 android bitmap wallpaper

在将位图发送到壁纸管理器之前,我需要一些帮助来调整位图的大小,以便当用户将其设置为壁纸时,它合理地适合,100% 将是首选。

我正在使用墙纸管理器并从 ImageView 获取图像。

我遇到的问题是壁纸真的放大了。以前,当我直接从 drawable 目录设置壁纸时,它看起来很好,你可以看到更多的图像,而不是它的 1/4。从那时起,我更改了我的代码,并找到了更多获取图像和设置墙纸的有效方法。

我看过This link here并试图弄清楚如何实现向您展示如何在将图像发送到墙纸管理器之前调整图像大小的答案。

任何帮助将不胜感激,干杯。

问题相关代码:

        @Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {

    final View v = inflater.inflate(R.layout.image_detail_fragment,
            container, false);


    int Measuredwidth = 0;
    int Measuredheight = 0;         

    WindowManager w = getActivity().getWindowManager();

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB_MR2) {
        w.getDefaultDisplay().getSize(Size);
        Measuredwidth = Size.x;
    Measuredheight = Size.y;
    } else {
        Display d = w.getDefaultDisplay();
    Measuredwidth = d.getWidth();
    Measuredheight = d.getHeight();
    }




    mImageView = (RecyclingImageView) v.findViewById(R.id.imageView);
    mImageView.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View arg0) {

            BitmapDrawable drawable = (BitmapDrawable) mImageView
                    .getDrawable();
            Bitmap bitmap = drawable.getBitmap();

            WallpaperManager myWallpaperManager = WallpaperManager
                    .getInstance(getActivity());

            try {

                myWallpaperManager.setBitmap(bitmap);
                ;
                Toast.makeText(getActivity(),
                        "Wallpaper Successfully Set!", Toast.LENGTH_LONG)
                        .show();
            } catch (IOException e) {
                Toast.makeText(getActivity(), "Error Setting Wallpaper",
                        Toast.LENGTH_LONG).show();
            }

        }

我的整个类(class):

public class ImageDetailFragment extends Fragment {
private static final String IMAGE_DATA_EXTRA = "extra_image_data";
private static final Point Size = null;
private String mImageUrl;
private RecyclingImageView mImageView;
private ImageFetcher mImageFetcher;

public static ImageDetailFragment newInstance(String imageUrl) {
    final ImageDetailFragment f = new ImageDetailFragment();

    final Bundle args = new Bundle();
    args.putString(IMAGE_DATA_EXTRA, imageUrl);
    f.setArguments(args);

    return f;
}

public ImageDetailFragment() {
}

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    mImageUrl = getArguments() != null ? getArguments().getString(
            IMAGE_DATA_EXTRA) : null;

}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
        Bundle savedInstanceState) {

    final View v = inflater.inflate(R.layout.image_detail_fragment,
            container, false);


    int Measuredwidth = 0;
    int Measuredheight = 0;         

    WindowManager w = getActivity().getWindowManager();

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB_MR2) {
        w.getDefaultDisplay().getSize(Size);
        Measuredwidth = Size.x;
    Measuredheight = Size.y;
    } else {
        Display d = w.getDefaultDisplay();
    Measuredwidth = d.getWidth();
    Measuredheight = d.getHeight();
    }




    mImageView = (RecyclingImageView) v.findViewById(R.id.imageView);
    mImageView.setOnClickListener(new View.OnClickListener() {

        @Override
        public void onClick(View arg0) {

            BitmapDrawable drawable = (BitmapDrawable) mImageView
                    .getDrawable();
            Bitmap bitmap = drawable.getBitmap();

            WallpaperManager myWallpaperManager = WallpaperManager
                    .getInstance(getActivity());

            try {

                myWallpaperManager.setBitmap(bitmap);
                ;
                Toast.makeText(getActivity(),
                        "Wallpaper Successfully Set!", Toast.LENGTH_LONG)
                        .show();
            } catch (IOException e) {
                Toast.makeText(getActivity(), "Error Setting Wallpaper",
                        Toast.LENGTH_LONG).show();
            }

        }

    });

    return v;
}

@Override
public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);

    if (Batmanark.class.isInstance(getActivity())) {
        mImageFetcher = ((Batmanark) getActivity()).getImageFetcher();
        mImageFetcher.loadImage(mImageUrl, mImageView);
    }


}

@Override
public void onDestroy() {
    super.onDestroy();
    if (mImageView != null) {
        // Cancel any pending image work
        ImageWorker.cancelWork(mImageView);
        mImageView.setImageDrawable(null);
    }
}
}

最佳答案

如果你想让壁纸适合设备屏幕,那么你必须按照以下步骤操作:

  1. 获取设备屏幕的高和宽
  2. 采样位图图像
  3. 调整位图大小
  4. 将位图设置为墙纸之前,回收之前的位图

代码:

第 1 步:

int Measuredwidth = 0;
int Measuredheight = 0; 

Point size = new Point();
// if you are doing it from an activity
WindowManager w = getWindowManager();
// otherwise use this
WindowManager w = context.getWindowManager();

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB_MR2) {
    w.getDefaultDisplay().getSize(size);
    Measuredwidth = size.x;
Measuredheight = size.y;
} else {
    Display d = w.getDefaultDisplay();
Measuredwidth = d.getWidth();
Measuredheight = d.getHeight();
}

步骤 2+3:

public Bitmap resizeBitmap(Resources res, int reqWidth, int reqHeight, 
                           InputStream inputStream, int fileLength) {
    Bitmap bitmap = null;
    InputStream in = null; 
    InputStream in2 = null;
    InputStream in3 = null;  

    try {
        in3 = inputStream;              

        ByteArrayOutputStream out = new ByteArrayOutputStream();
        ByteArrayOutputStream out2 = new ByteArrayOutputStream();

        copy(in3,out,fileLength);
        out2 = out;
        in2 = new ByteArrayInputStream(out.toByteArray());
        in = new ByteArrayInputStream(out2.toByteArray());

        BitmapFactory.Options options = new BitmapFactory.Options();
        options.inJustDecodeBounds = true;
        BitmapFactory.decodeStream(in, null, options);

                    if(options.outHeight == -1 || options.outWidth == 1 || options.outMimeType == null){
            return null;
    }                           

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

        options.inJustDecodeBounds = false; 

        bitmap = BitmapFactory.decodeStream(in2, null, options);

        if(bitmap != null){
            bitmap = Bitmap.createScaledBitmap(bitmap, reqWidth, reqHeight, false);                     
        }
        in.close();
        in2.close();
        in3.close();
    } catch (IOException e1) {          
        e1.printStackTrace();
    }
    return bitmap;   
}

public 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 > reqHeight || width > reqWidth) {

        // Calculate ratios of height and width to requested height and width
        final int heightRatio = Math.round((float) height / (float) reqHeight);
        final int widthRatio = Math.round((float) width / (float) reqWidth);

        // Choose the smallest ratio as inSampleSize value, this will guarantee a final image
        // with both dimensions larger than or equal to the requested height and width.
        inSampleSize = heightRatio < widthRatio ? heightRatio : widthRatio;

        // This offers some additional logic in case the image has a strange
        // aspect ratio. For example, a panorama may have a much larger
        // width than height. In these cases the total pixels might still
        // end up being too large to fit comfortably in memory, so we should
        // be more aggressive with sample down the image (=larger inSampleSize).

        final float totalPixels = width * height;

        // Anything more than 2x the requested pixels we'll sample down further
        final float totalReqPixelsCap = reqWidth * reqHeight * 2;

        while (totalPixels / (inSampleSize * inSampleSize) > totalReqPixelsCap) {
            inSampleSize++;
        }
    }
    return inSampleSize;
}

public int copy(InputStream input, OutputStream output, int fileLength) throws IOException{
    byte[] buffer = new byte[8*1024];
    int count = 0;
    int n = 0;

    while (-1 != (n = input.read(buffer))) {
        output.write(buffer, 0, n);
        count += n;
        publishProgress((int) (count * 100 / fileLength));
    }
    return count;
}

第 4 步:

回收位图使用:

bitmap.recycle();
bitmap = null;

resizeBitmap(context.getResources(), Measuredwidth, Measuredheight, THE_INPUTSTREAM_FROM_WHERE_YOU_ARE_DOWNLOADING_THE_IMAGE, FILELENGTH_FROM_THE_INPUTSTREAM);.

如果您从 Activity 中调用该函数,请像这样调用它:resizeBitmap(getResources(), Measuredwidth, Measuredheight, THE_INPUTSTREAM_FROM_WHERE_YOU_ARE_DOWNLOADING_THE_IMAGE,FILELENGTH_FROM_THE_INPUTSTREAM);

该函数将返回适合设备分辨率的调整大小的位图。 如果您已经将位图设置为墙纸,那么在将新位图设置为墙纸之前不要忘记回收位图。

关于android - 在发送到 Wallpapermanager 之前调整位图大小,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/19196219/

相关文章:

java - 使用 Iterator.next() 避免 ConcurrentModificationException

android - 使用操作菜单打开带有 "Powered By Chrome"的自定义 WebView

java - 将位图与标准 Java 合并

java - 在Java中将BMP图像转换为PNG或JPG,无需将整个图像加载到内存中

java - 应用后壁纸会自动裁剪

c++ - VC++改变桌面背景的方法

android - 如何在android中每天自动设置动态壁纸

java - 以编程方式获取 Android 设备的 MAC

android - 在位图上绘图?

Android 抽屉导航 ExpandableListView