在有一些程序开发中,有时候会用到圆形,截取一张图片的一部分圆形,作为头像或者其他.

本实例就是截图圆形,设置头像的.

  

 

首先讲解一些代码

<ImageView android:id="@+id/screenshot_img"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:scaleType="matrix"/>

图片属性要设置成android:scaleType="matrix",这样图片才可以通过触摸,放大缩小.

主类功能:点击按钮选择图片或者拍照

public class MainActivity extends Activity {

	private Button btnImg;

	/**
* 表示选择的是相机--0
*/
private final int IMAGE_CAPTURE = 0;
/**
* 表示选择的是相册--1
*/
private final int IMAGE_MEDIA = 1; /**
* 图片保存SD卡位置
*/
private final static String IMG_PATH = Environment
.getExternalStorageDirectory() + "/chillax/imgs/"; @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); btnImg = (Button)findViewById(R.id.btn_find_img);
btnImg.setOnClickListener(BtnClick);
} OnClickListener BtnClick = new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
setImage();
}
}; /**
* 选择图片
*/
public void setImage() {
final AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setTitle("选择图片");
builder.setNegativeButton("取消", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {}
});
builder.setPositiveButton("相机", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent intent = new Intent("android.media.action.IMAGE_CAPTURE");
startActivityForResult(intent, IMAGE_CAPTURE);
}
});
builder.setNeutralButton("相册", new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
Intent intent = new Intent(Intent.ACTION_GET_CONTENT);
intent.setType("image/*");
startActivityForResult(intent, IMAGE_MEDIA);
}
});
AlertDialog alert = builder.create();
alert.show();
} /**
* 根据用户选择,返回图片资源
*/
public void onActivityResult(int requestCode, int resultCode, Intent data) { ContentResolver resolver = this.getContentResolver(); BitmapFactory.Options options = new BitmapFactory.Options();
options.inSampleSize = 2;// 图片高宽度都为本来的二分之一,即图片大小为本来的大小的四分之一
options.inTempStorage = new byte[5 * 1024]; if (data != null){
if (requestCode == IMAGE_MEDIA){
try {
if(data.getData() == null){
}else{ // 获得图片的uri
Uri uri = data.getData(); // 将字节数组转换为ImageView可调用的Bitmap对象
Bitmap bitmap = BitmapFactory.decodeStream(
resolver.openInputStream(uri), null,options); //图片路径
String imgPath = IMG_PATH+"Test.png"; //保存图片
saveFile(bitmap, imgPath); Intent i = new Intent(MainActivity.this,ScreenshotImg.class);
i.putExtra("ImgPath", imgPath);
this.startActivity(i); }
} catch (Exception e) {
System.out.println(e.getMessage());
} }else if(requestCode == IMAGE_CAPTURE) {// 相机
if (data != null) {
if(data.getExtras() == null){
}else{ // 相机返回的图片数据
Bitmap bitmap = (Bitmap) data.getExtras().get("data"); //图片路径
String imgPath = IMG_PATH+"Test.png"; //保存图片
saveFile(bitmap, imgPath); Intent i = new Intent(MainActivity.this,ScreenshotImg.class);
i.putExtra("ImgPath", imgPath);
this.startActivity(i);
}
}
}
}
} /**
* 保存图片到app指定路径
* @param bm头像图片资源
* @param fileName保存名称
*/
public static void saveFile(Bitmap bm, String filePath) {
try {
String Path = filePath.substring(0, filePath.lastIndexOf("/"));
File dirFile = new File(Path);
if (!dirFile.exists()) {
dirFile.mkdirs();
}
File myCaptureFile = new File(filePath);
BufferedOutputStream bo = null;
bo = new BufferedOutputStream(new FileOutputStream(myCaptureFile));
bm.compress(Bitmap.CompressFormat.PNG, 100, bo); bo.flush();
bo.close(); } catch (FileNotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
} @Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
} }

注意:有时候要对图片进行压缩,不然在程序中很容易就造成内存溢出.

BitmapFactory.Options options = new BitmapFactory.Options();

options.inSampleSize = 2;// 图片高宽度都为本来的二分之一

options.inTempStorage = new byte[5 * 1024];

// 获得图片的uri

Uri uri = data.getData();



// 将字节数组转换为ImageView可调用的Bitmap对象

Bitmap bitmap = BitmapFactory.decodeStream(resolver.openInputStream(uri), null,options);

图片缩放,截图类:

public class ScreenshotImg extends Activity {

	private LinearLayout imgSave;
private ImageView imgView,imgScreenshot;
private String imgPath; private static final int NONE = 0;
private static final int DRAG = 1;
private static final int ZOOM = 2; private int mode = NONE;
private float oldDist;
private Matrix matrix = new Matrix();
private Matrix savedMatrix = new Matrix();
private PointF start = new PointF();
private PointF mid = new PointF(); @Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
this.setContentView(R.layout.img_screenshot); imgView = (ImageView)findViewById(R.id.screenshot_img);
imgScreenshot = (ImageView)findViewById(R.id.screenshot);
imgSave = (LinearLayout)findViewById(R.id.img_save); Intent i = getIntent();
imgPath = i.getStringExtra("ImgPath"); Bitmap bitmap = getImgSource(imgPath); if(bitmap!=null){
imgView.setImageBitmap(bitmap);
imgView.setOnTouchListener(touch);
imgSave.setOnClickListener(imgClick);
} } OnClickListener imgClick = new OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
imgView.setDrawingCacheEnabled(true);
Bitmap bitmap = Bitmap.createBitmap(imgView.getDrawingCache()); int w = imgScreenshot.getWidth();
int h = imgScreenshot.getHeight(); int left = imgScreenshot.getLeft();
int right = imgScreenshot.getRight();
int top = imgScreenshot.getTop();
int bottom = imgScreenshot.getBottom(); Bitmap targetBitmap = Bitmap.createBitmap(w,h,Bitmap.Config.ARGB_8888); Canvas canvas = new Canvas(targetBitmap);
Path path = new Path(); path.addCircle((float)((right-left) / 2),((float)((bottom-top)) / 2), (float)(w / 2),
Path.Direction.CCW); canvas.clipPath(path); canvas.drawBitmap(bitmap,new Rect(left,top,right,bottom),new Rect(left,top,right,bottom),null); MainActivity.saveFile(targetBitmap, imgPath); Toast.makeText(getBaseContext(), "保存成功", Toast.LENGTH_LONG).show(); finish();
}
}; /**
* 触摸事件
*/
OnTouchListener touch = new OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
ImageView view = (ImageView) v;
switch (event.getAction() & MotionEvent.ACTION_MASK) {
case MotionEvent.ACTION_DOWN:
savedMatrix.set(matrix); // 把原始 Matrix对象保存起来
start.set(event.getX(), event.getY()); // 设置x,y坐标
mode = DRAG;
break;
case MotionEvent.ACTION_UP:
case MotionEvent.ACTION_POINTER_UP:
mode = NONE;
break;
case MotionEvent.ACTION_POINTER_DOWN:
oldDist = spacing(event);
if (oldDist > 10f) {
savedMatrix.set(matrix);
midPoint(mid, event); // 求出手指两点的中点
mode = ZOOM;
}
break;
case MotionEvent.ACTION_MOVE:
if (mode == DRAG) {
matrix.set(savedMatrix); matrix.postTranslate(event.getX() - start.x, event.getY()
- start.y);
} else if (mode == ZOOM) {
float newDist = spacing(event);
if (newDist > 10f) {
matrix.set(savedMatrix);
float scale = newDist / oldDist;
matrix.postScale(scale, scale, mid.x, mid.y);
}
}
break;
}
System.out.println(event.getAction());
view.setImageMatrix(matrix);
return true;
}
}; //求两点距离
private float spacing(MotionEvent event) {
float x = event.getX(0) - event.getX(1);
float y = event.getY(0) - event.getY(1);
return FloatMath.sqrt(x * x + y * y);
} //求两点间中点
private void midPoint(PointF point, MotionEvent event) {
float x = event.getX(0) + event.getX(1);
float y = event.getY(0) + event.getY(1);
point.set(x / 2, y / 2);
} /**
* 從指定路徑讀取圖片資源
*/
public Bitmap getImgSource(String pathString) { Bitmap bitmap = null;
BitmapFactory.Options opts = new BitmapFactory.Options();
// opts.inSampleSize = 2; try {
File file = new File(pathString);
if (file.exists()) {
bitmap = BitmapFactory.decodeFile(pathString, opts);
}
if (bitmap == null) {
return null;
} else {
return bitmap;
}
} catch (Exception e) {
e.printStackTrace();
return null;
}
} }

截图关键语句:

Bitmap targetBitmap = Bitmap.createBitmap(w,h,Bitmap.Config.ARGB_8888);

               

 Canvas canvas = new Canvas(targetBitmap);

Path path = new Path();

       

path.addCircle((float)((right-left) / 2),((float)((bottom-top)) / 2), (float)(w / 2),

Path.Direction.CCW);     //绘制圆形

       

canvas.clipPath(path);

       

canvas.drawBitmap(bitmap,new Rect(left,top,right,bottom),new Rect(left,top,right,bottom),null);    //截图

项目源码:http://download.csdn.net/detail/chillax_li/7120673

(有人说保存图片之后,没打开图片.这是因为我没打开它,要看效果的话,要自己用图库打开,就能看到效果了.这里说明一下)

尊重原创,转载请注明出处:http://blog.csdn.net/chillax_li/article/details/22591681

《Android开发卷——设置圆形头像,Android截取圆形图片》的更多相关文章

  1. 简单物联网:外网访问内网路由器下树莓派Flask服务器

    最近做一个小东西,大概过程就是想在教室,宿舍控制实验室的一些设备. 已经在树莓上搭了一个轻量的flask服务器,在实验室的路由器下,任何设备都是可以访问的:但是有一些限制条件,比如我想在宿舍控制我种花 ...

  2. 利用ssh反向代理以及autossh实现从外网连接内网服务器

    前言 最近遇到这样一个问题,我在实验室架设了一台服务器,给师弟或者小伙伴练习Linux用,然后平时在实验室这边直接连接是没有问题的,都是内网嘛.但是回到宿舍问题出来了,使用校园网的童鞋还是能连接上,使 ...

  3. 外网访问内网Docker容器

    外网访问内网Docker容器 本地安装了Docker容器,只能在局域网内访问,怎样从外网也能访问本地Docker容器? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装并启动Docker容器 ...

  4. 外网访问内网SpringBoot

    外网访问内网SpringBoot 本地安装了SpringBoot,只能在局域网内访问,怎样从外网也能访问本地SpringBoot? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装Java 1 ...

  5. 外网访问内网Elasticsearch WEB

    外网访问内网Elasticsearch WEB 本地安装了Elasticsearch,只能在局域网内访问其WEB,怎样从外网也能访问本地Elasticsearch? 本文将介绍具体的实现步骤. 1. ...

  6. 怎样从外网访问内网Rails

    外网访问内网Rails 本地安装了Rails,只能在局域网内访问,怎样从外网也能访问本地Rails? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装并启动Rails 默认安装的Rails端口 ...

  7. 怎样从外网访问内网Memcached数据库

    外网访问内网Memcached数据库 本地安装了Memcached数据库,只能在局域网内访问,怎样从外网也能访问本地Memcached数据库? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装 ...

  8. 怎样从外网访问内网CouchDB数据库

    外网访问内网CouchDB数据库 本地安装了CouchDB数据库,只能在局域网内访问,怎样从外网也能访问本地CouchDB数据库? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装并启动Cou ...

  9. 怎样从外网访问内网DB2数据库

    外网访问内网DB2数据库 本地安装了DB2数据库,只能在局域网内访问,怎样从外网也能访问本地DB2数据库? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装并启动DB2数据库 默认安装的DB2 ...

  10. 怎样从外网访问内网OpenLDAP数据库

    外网访问内网OpenLDAP数据库 本地安装了OpenLDAP数据库,只能在局域网内访问,怎样从外网也能访问本地OpenLDAP数据库? 本文将介绍具体的实现步骤. 1. 准备工作 1.1 安装并启动 ...

随机推荐

  1. 手把手教你PolarDB-X中的表设计——用户表

    简介: 本系列旨在描述一个具体的业务场景,给出建表的例子,帮助大家更好的使用PolarDB-X.本期的主题是:用户表. 本系列旨在描述一个具体的业务场景,给出建表的例子,帮助大家更好的使用PolarD ...

  2. ModelScope初探:一行代码调用成熟AI模型。

    简介: 如何用一行代码调用成熟AI模型?试试ModelScope,让AI开发者解放生产力! ModelScope是阿里推出的下一代开源的模型即服务共享平台,为泛AI开发者提供灵活.易用.低成本的一站式 ...

  3. 数百万台车联网设备同时在线0故障,中瑞集团的云原生探索之路 | 云原生Talk

    简介: 在保持对业界趋势调度关注的同时,始终选用最适合自身的技术,这可能是中瑞能在车联网领域引领行业的重要原因之一,正如中瑞CTO所说"阿里云云原生产品体系带给我们的,不是单纯的IT工具,而 ...

  4. 深度解析PolarDB数据库并行查询技术

    简介: 随着数据规模的不断扩大,用户SQL的执行时间越来越长,这不仅对数据库的优化能力提出更高的要求,并且对数据库的执行模式也提出了新的挑战.本文将介绍基于代价进行并行优化.并行执行的云数据库的并行查 ...

  5. UWP WinRT 使用系统自带的分词库对字符串文本进行分词

    本文将和大家介绍在 UWP 应用,或其他能接入 WinRT 的应用里,使用系统自带的分词库,对中文.英文等等自然语言的字符串文本进行分词 开始之前需要说明的是,现在不仅仅 UWP 应用,其他的 UI ...

  6. JavaScript之变量解构赋值的使用

    引言 解构赋值是ES6中引入的一种能快速方便的进行变量赋值的方法,其主要也就是分为解构和赋值两部分内容.解构者,也就是匹配结构,然后分解结构进行赋值. 数组的解构赋值 使用 const arr = [ ...

  7. EPAI手绘建模APP资源管理和模型编辑器2

    g) 矩形   图 26模型编辑器-矩形 i. 修改矩形的中心位置. ii. 修改矩形的长度和宽度. h) 正多边形 图 27模型编辑器-内接正多边形 图 28模型编辑器-外切正多边形 i. 修改正多 ...

  8. JAVA也能用上Seq啦

    前言 在.NET生态中,Serilog凭借其强大的结构化日志记录功能和与Seq的无缝集成,已经成为许多开发者的首选日志记录工具.Seq作为一个日志检索和仪表板工具,能够将日志中的插值转换为结构化数据, ...

  9. Headless BI

    Headless的概念最初的来源与内容管理平台有关,一般是指内容管理平台中的一些应用不提供可视化界面,只是通过API方式把内容以数据的方式给前端.前端根据不同的设备类型,可以再去进行针对性地渲染和展现 ...

  10. 小程序真机报错errMsg: “hideLoading:fail:toast can‘t be found“ ?

    showLoading 和 showToast 同时只能显示一个: showLoading 应与hideLoading 配对使用: 把请求接口统一封装,开始请求接口时showLoading,请求接口后 ...