Android如何显示长图

本人无聊就喜欢看看微博,发现新浪微博的长图显示很有意思,于是去研究了一下。

首先如果你直接把一张长图set到imageView上,会提示你一个异常 W/OpenGLRenderer(6797): Bitmap too large to be uploaded into a texture (438x5309, max=4096x4096),然后什么都显示不出来,这个时候,你就需要一个东西的帮忙,BitmapRegionDecoder!


下面先上代码

public class MainActivity extends Activity implements OnTouchListener {

	/*private LinearLayout container;
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.activity_main);
		//Log.d("drawable", "aa");
		container = (LinearLayout)findViewById(R.id.container);
		ImageView iv = new ImageView(this);
		iv.setBackground(getResources().getDrawable(R.drawable.a));
		container.addView(iv,0);
		//Log.d("drawable", MyApplication.getmDrawable().toString());
	}
}*/
	    private final Rect mRect = new Rect();
	    private BitmapRegionDecoder mDecoder;
	    private ImageView mView;
	    private DisplayMetrics dm;
	    private int screenHeight;
	    private int screenWidth;
	    //private int downX;
	    private int downY;
	    private int startY;
	    private int showHeight;
	    private int imgHeight;
	     
	    @Override
	    public void onCreate(Bundle savedInstanceState) {
	        super.onCreate(savedInstanceState);
	        //setContentView(R.layout.activity_main);
	         
	        dm = new DisplayMetrics();   
	        
	        mView = new ImageView(this);
	        mView.setAdjustViewBounds(true);
	        mView.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
	        mView.setScaleType(ScaleType.CENTER);
	        mView.setOnTouchListener(this);
	        
	        mView.post(new Runnable() {
				
				@Override
				public void run() {
					getWindowManager().getDefaultDisplay().getMetrics(dm);       
					screenHeight = dm.heightPixels;  
					screenWidth = dm.widthPixels;
					
					mRect.set(0, 0, screenWidth, screenHeight);
			        Bitmap bm = mDecoder.decodeRegion(mRect, null);
			        mView.setImageBitmap(bm);	
			        
			        showHeight = screenHeight;
			        startY = 0;
			        
			        imgHeight = mDecoder.getHeight();
			        
			        //System.out.println(imgHeight);
			        //System.out.println(mDecoder.getHeight());
			        //System.out.println(mView.getWidth());
			        //System.out.println(mView.getHeight());
				}
			});
	        
	        setContentView(mView);
	         
	        try {
	            InputStream is = getResources().openRawResource(R.drawable.a);
	            mDecoder = BitmapRegionDecoder.newInstance(is, true);
	        } catch (IOException e) {
	            e.printStackTrace();
	        }
	    }
	     
	    @Override
	    public boolean onTouch(View v, MotionEvent event) {
	        final int action = event.getAction() & MotionEvent.ACTION_MASK;
	        
	        switch (action) {
	        case MotionEvent.ACTION_DOWN:
	        	//downX = (int) event.getX();;
	        	downY = (int) event.getY();
	        	break;
	        case MotionEvent.ACTION_MOVE:
	            //setImageRegion(x, y);
	        	int x = (int) event.getX();
		        int y = (int) event.getY();
		        
		        int deltaY = downY - y;
				downY = y;
				
				System.out.println(showHeight);
				System.out.println(deltaY);
				if(showHeight <= screenHeight && deltaY < 0){
					break;
				}else if(showHeight >= imgHeight + 500 && deltaY > 0){
					//System.out.println("else if");
					break;
				}
				showHeight += deltaY;
				startY += deltaY;
				mRect.set(0, startY, screenWidth, showHeight);
		        Bitmap bm = mDecoder.decodeRegion(mRect, null);
		        mView.setImageBitmap(bm);	
				//System.out.println(deltaY);
				
	            break;
	        }
	        return true;
	    }
	     
	}

首先 一个ImageView并给它set上onTouchListener

初始化一个BitmapRegionDecoder 

InputStream is = getResources().openRawResource(R.drawable.a);

mDecoder = BitmapRegionDecoder.newInstance(is, true);


然后获取屏幕的宽高并使用 mDecoder.decodeRegion(mRect, null);去初始化一张bitmap,这个函数的作用就类似于切图,用BitmapRegionDecoder 把原来很长的图切成只有一屏幕大的图。


最后在onTouch中获得手指滑动的y坐标,根据这个y坐标对切图的rect进行修改,注意要判断边界,不然还是会OOM。





  • 2
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值