android 大图片拖拽缩放
这篇图片拖拽缩放也是我在项目中用到的,今天整理一下,将源码奉献给大家,希望对大家以后碰到相似的问题有帮助。
这篇就不做过多介绍了,直接上源码:
001 |
public class SpacePageActivity extends Activity { |
002 |
|
003 |
private LinearLayout linnerLayout_spacepage; |
004 |
private RelativeLayout relativeLayout_spacepage; |
005 |
private Button btn_spacepage_back; |
006 |
private Button btn_spacepage_save; |
007 |
private static Boolean isTrue= false ; |
008 |
|
009 |
private static String IMAGE_MIME_TYPE ; |
010 |
|
011 |
private ImageView image_spacePage; |
012 |
private ProgressDialog dialog; |
013 |
private Bitmap bitmap; |
014 |
@Override |
015 |
protected void onCreate(Bundle savedInstanceState) { |
016 |
// TODO Auto-generated method stub |
017 |
super .onCreate(savedInstanceState); |
018 |
requestWindowFeature(Window.FEATURE_NO_TITLE); //隐藏标题 |
019 |
setContentView(R.layout.spacepage); |
020 |
setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); |
021 |
initHead(); |
022 |
|
023 |
if (isNetworkAvailable()){ |
024 |
image_spacePage=(ImageView) findViewById(R.id.image_spacepage); |
025 |
btn_spacepage_save=(Button) findViewById(R.id.btn_spacepage_save); |
026 |
image_spacePage.setOnTouchListener( new MulitPointTouchListener(image_spacePage)); |
027 |
image_spacePage.setScaleType(ScaleType.CENTER_INSIDE); |
028 |
|
029 |
//加载成功 |
030 |
String urls= "http://epaper.yzdsb.com.cn/201201/04/yz2104_7.jpg" ; |
031 |
bitmap=returnBitMap(urls); |
032 |
if ( null !=bitmap){ |
033 |
image_spacePage.setImageBitmap(bitmap); |
034 |
} |
035 |
|
036 |
} |
037 |
} |
038 |
|
039 |
|
040 |
public Bitmap returnBitMap(String url) { |
041 |
|
042 |
if ( null ==url || "" .equals(url)){ |
043 |
return null ; |
044 |
} |
045 |
URL myFileUrl = null ; |
046 |
Bitmap bitmap = null ; |
047 |
try { |
048 |
myFileUrl = new URL(url); |
049 |
} catch (MalformedURLException e) { |
050 |
e.printStackTrace(); |
051 |
} |
052 |
try { |
053 |
HttpURLConnection conn = (HttpURLConnection) myFileUrl.openConnection(); |
054 |
conn.setConnectTimeout( 2000 ); |
055 |
conn.setDoInput( true ); |
056 |
conn.connect(); |
057 |
InputStream is = conn.getInputStream(); |
058 |
bitmap = BitmapFactory.decodeStream(is); |
059 |
is.close(); |
060 |
} catch (IOException e) { |
061 |
e.printStackTrace(); |
062 |
} |
063 |
|
064 |
|
065 |
|
066 |
return bitmap; |
067 |
} |
068 |
public class MulitPointTouchListener implements OnTouchListener { |
069 |
|
070 |
Matrix matrix = new Matrix(); |
071 |
Matrix savedMatrix = new Matrix(); |
072 |
|
073 |
public ImageView image; |
074 |
static final int NONE = 0 ; |
075 |
static final int DRAG = 1 ; |
076 |
static final int ZOOM = 2 ; |
077 |
int mode = NONE; |
078 |
|
079 |
PointF start = new PointF(); |
080 |
PointF mid = new PointF(); |
081 |
float oldDist = 1f; |
082 |
|
083 |
|
084 |
public MulitPointTouchListener(ImageView image) { |
085 |
super (); |
086 |
this .image = image; |
087 |
} |
088 |
|
089 |
@Override |
090 |
public boolean onTouch(View v, MotionEvent event) { |
091 |
this .image.setScaleType(ScaleType.MATRIX); |
092 |
|
093 |
ImageView view = (ImageView) v; |
094 |
// dumpEvent(event); |
095 |
|
096 |
switch (event.getAction() & MotionEvent.ACTION_MASK) { |
097 |
|
098 |
case MotionEvent.ACTION_DOWN: |
099 |
|
100 |
Log.w( "FLAG" , "ACTION_DOWN" ); |
101 |
matrix.set(view.getImageMatrix()); |
102 |
savedMatrix.set(matrix); |
103 |
start.set(event.getX(), event.getY()); |
104 |
mode = DRAG; |
105 |
break ; |
106 |
case MotionEvent.ACTION_POINTER_DOWN: |
107 |
Log.w( "FLAG" , "ACTION_POINTER_DOWN" ); |
108 |
oldDist = spacing(event); |
109 |
if (oldDist > 10f) { |
110 |
savedMatrix.set(matrix); |
111 |
midPoint(mid, event); |
112 |
mode = ZOOM; |
113 |
} |
114 |
break ; |
115 |
case MotionEvent.ACTION_UP: |
116 |
Log.w( "FLAG" , "ACTION_UP" ); |
117 |
case MotionEvent.ACTION_POINTER_UP: |
118 |
Log.w( "FLAG" , "ACTION_POINTER_UP" ); |
119 |
mode = NONE; |
120 |
break ; |
121 |
case MotionEvent.ACTION_MOVE: |
122 |
Log.w( "FLAG" , "ACTION_MOVE" ); |
123 |
if (mode == DRAG) { |
124 |
matrix.set(savedMatrix); |
125 |
matrix.postTranslate(event.getX() - start.x, event.getY() |
126 |
- start.y); |
127 |
} else if (mode == ZOOM) { |
128 |
float newDist = spacing(event); |
129 |
if (newDist > 10f) { |
130 |
matrix.set(savedMatrix); |
131 |
float scale = newDist / oldDist; |
132 |
matrix.postScale(scale, scale, mid.x, mid.y); |
133 |
} |
134 |
} |
135 |
break ; |
136 |
} |
137 |
|
138 |
view.setImageMatrix(matrix); |
139 |
return true ; |
140 |
} |
141 |
|
142 |
|
143 |
private float spacing(MotionEvent event) { |
144 |
float x = event.getX( 0 ) - event.getX( 1 ); |
145 |
float y = event.getY( 0 ) - event.getY( 1 ); |
146 |
return FloatMath.sqrt(x * x + y * y); |
147 |
} |
148 |
|
149 |
private void midPoint(PointF point, MotionEvent event) { |
150 |
float x = event.getX( 0 ) + event.getX( 1 ); |
151 |
float y = event.getY( 0 ) + event.getY( 1 ); |
152 |
point.set(x / 2 , y / 2 ); |
153 |
} |
154 |
} |
155 |
private void initHead() { |
156 |
linnerLayout_spacepage = (LinearLayout) findViewById(R.id.linnerLayout_spacepage); |
157 |
relativeLayout_spacepage=(RelativeLayout) findViewById(R.id.relativeLayout_spacepage); |
158 |
btn_spacepage_back = (Button) findViewById(R.id.btn_spacepage_back); |
159 |
btn_spacepage_back.setOnClickListener( new OnClickListener() { |
160 |
|
161 |
@Override |
162 |
public void onClick(View v) { |
163 |
// TODO Auto-generated method stub |
164 |
|
165 |
finish(); |
166 |
} |
167 |
}); |
168 |
btn_spacepage_save = (Button) findViewById(R.id.btn_spacepage_save); |
169 |
|
170 |
} |
171 |
protected boolean isNetworkAvailable() { |
172 |
ConnectivityManager connectivity = (ConnectivityManager)getSystemService(Context.CONNECTIVITY_SERVICE); |
173 |
if (connectivity == null ) { |
174 |
Log.i( "NetWorkState" , "Unavailabel" ); |
175 |
return false ; |
176 |
} else { |
177 |
NetworkInfo[] info = connectivity.getAllNetworkInfo(); |
178 |
if (info != null ) { |
179 |
for ( int i = 0 ; i < info.length; i++) { |
180 |
if (info[i].getState() == NetworkInfo.State.CONNECTED) { |
181 |
Log.i( "NetWorkState" , "Availabel" ); |
182 |
return true ; |
183 |
} |
184 |
} |
185 |
} |
186 |
} |
187 |
return false ; |
188 |
} |
189 |
@Override |
190 |
protected void onStop() { |
191 |
// TODO Auto-generated method stub |
192 |
if (bitmap!= null ){ |
193 |
if (!bitmap.isRecycled()){ |
194 |
bitmap.recycle(); //回收图片所占的内存 |
195 |
bitmap= null ; |
196 |
System.gc(); //提醒系统及时回收 |
197 |
} |
198 |
} |
199 |
super .onStop(); |
200 |
} |
201 |
@Override |
202 |
protected void onDestroy() { |
203 |
// TODO Auto-generated method stub |
204 |
super .onDestroy(); |
205 |
if (bitmap!= null ){ |
206 |
if (!bitmap.isRecycled()){ |
207 |
bitmap.recycle(); //回收图片所占的内存 |
208 |
bitmap= null ; |
209 |
System.gc(); //提醒系统及时回收 |
210 |
} |
211 |
} |
212 |
} |
213 |
} |
因为是大图片,在onDestroy的时候要recycle掉,这样系统才会定时回收掉,System.gc();是提醒系统回收,虽然java这种垃圾 回收机制不用我们自己关心对象的回收,但是这也给android开发人员带来了不好的一面,如果系统回收不及时很可能就造成了内存溢出了。什么时候手机不 担心内存使用了就好了。
运行一下看看效果:
转自:http://blog.csdn.net/wangkuifeng0118/article/details/7648692
分类:
手机开发(Android)
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 如何编写易于单元测试的代码
· 10年+ .NET Coder 心语,封装的思维:从隐藏、稳定开始理解其本质意义
· .NET Core 中如何实现缓存的预热?
· 从 HTTP 原因短语缺失研究 HTTP/2 和 HTTP/3 的设计差异
· AI与.NET技术实操系列:向量存储与相似性搜索在 .NET 中的实现
· 地球OL攻略 —— 某应届生求职总结
· 周边上新:园子的第一款马克杯温暖上架
· Open-Sora 2.0 重磅开源!
· 提示词工程——AI应用必不可少的技术
· .NET周刊【3月第1期 2025-03-02】