您的位置:首页 > 移动开发 > Android开发

Android-图片的上传及加载

2016-03-21 17:36 447 查看
在Android端和服务器端之间,图片的传输是以经过Base64编码过的字符串进行的;

所以整个过程如下(在过程中使用post网络传输):

Android端:图片编码----》服务器端:接收、解码,然后转换成图片,从服务器端到Android端一样的流程;

在图片编解码的过程中,byte[] 字节流充当着中间者的角色,即:图片---》inputstream流----》byte[]----》字符串。

下面我们就说一下具体是如何实现的:

Android端:

1、获取图片:在开发的过程中可以从计算机本地和andorid机中获取到图片

以绝对路径来获取本地图片:

InputStream in = new FileInputStream("F://image//a.jpg");
Bitmap bitmap = BitmapFactory.decodeStream(in);//流转换成图片
从相册或拍照获取图片

private void UpdateHeadImage() {
// TODO Auto-generated method stub
MyHead_image.setOnClickListener(new OnClickListener() {

@Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent intent = new Intent();
/* 开启Pictures画面Type设定为image */
intent.setType("image/*");
/* 使用Intent.ACTION_GET_CONTENT这个Action */
intent.setAction(Intent.ACTION_GET_CONTENT);
/* 取得相片后返回本画面 */
startActivityForResult(intent, 1);
}
});
}
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if (resultCode == RESULT_OK) {//RESULT_OK:Standard activity result: operation succeeded.
Uri uri = data.getData();
Log.e("uri", uri.toString());
ContentResolver cr = this.getContentResolver();
try {
in = cr.openInputStream(uri);
bitmap = BitmapFactory.decodeStream(in);
ImageView imageView = (ImageView) findViewById(R.id.main_image);
/* 将Bitmap设定到ImageView */
imageView.setImageBitmap(bitmap);
} catch (FileNotFoundException e) {
Log.e("Exception", e.getMessage(),e);
}
}
super.onActivityResult(requestCode, resultCode, data);
}

下面是从相册和拍照获取图片

protected void getImageFromAlbum() {
Intent intent = new Intent(Intent.ACTION_PICK);
intent.setType("image/*");//相片类型
startActivityForResult(intent, 0);
}

protected void getImageFromCamera() {
String state = Environment.getExternalStorageState();
if (state.equals(Environment.MEDIA_MOUNTED)) {
Intent getImageByCamera = new Intent("android.media.action.IMAGE_CAPTURE");
startActivityForResult(getImageByCamera, 1);
}
else {
Toast.makeText(getActivity(), "请确认已经插入SD卡", Toast.LENGTH_LONG).show();
}
}
@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
// TODO Auto-generated method stub
if(requestCode==REQUEST_CODE_IMAGE){
Uri uri = data.getData();
ContentResolver cr = getActivity().getContentResolver();
try {
InputStream in = cr.openInputStream(uri);
Bitmap Head_bitmap_image = BitmapFactory.decodeStream(in);
LoadHead(Head_bitmap_image);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}else if(requestCode==REQUEST_CODE_CAMERA){
Uri uri = data.getData();
//手机的不同,拍照获取到图片方式也可能不同
if(uri==null){
Log.i("camera_uri", "为空");
Bundle b = data.getExtras();
if(b!=null){
Bitmap Head_bitmap_camera = (Bitmap) b.get("data");
LoadHead(Head_bitmap_camera);
}
}else{
Log.i("camera_uri", "不为空");
ContentResolver cr = getActivity().getContentResolver();
try {
InputStream in = cr.openInputStream(uri);
Bitmap Head_bitmap_camera = BitmapFactory.decodeStream(in);
LoadHead(Head_bitmap_camera);
} catch (FileNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
super.onActivityResult(requestCode, resultCode, data);
}
private void LoadHead(Bitmap head_bitmap_image) {
// TODO Auto-generated method stub
Person_Head.setImageBitmap(head_bitmap_image);
}


此时图片已经转换成Bitmap对象,要把图片以Base64编码字符串的形式传输,还需要对Bitmap对象压缩

ByteArrayOutputStream baos = new ByteArrayOutputStream();
//图片压缩并转换成流,
//bitmap.
bitmap.compress(Bitmap.CompressFormat.JPEG, 100,baos);
byte[] byteServer = baos.toByteArray();
String result = Base64.encodeToString(byteServer,Base64.DEFAULT);


以上是android端的上传

然后就是服务器端的接收与转换

byte[] bt = Base64.decodeBase64(String ss);
InputStream in = new ByteArrayInputStream(bt);
OutputStream out1 = new FileOutputStream("F://image//b.jpg");//储存图片的地址
ByteArrayOutputStream outstream = new ByteArrayOutputStream();
byte[] by = new byte[1024];
int len = 0;
while((len=in.read(by))!=-1){
outstream.write(by,0,len);
}
outstream.writeTo(out1);





android端的接收、服务器端的接收与返回都是流与byte[]的转换,但在不同端编解码的方式有点不同:

服务器端:
编码(字节流--->字符串):Base64.encode(byte[] input);(相关包,org.apache.catalina.util.Base64)
解码(字符串-->字节流):Base64.decodeBase64(String ss);(相关包,org.apache.tomcat.util.codec.binary.Base64)
在服务端的编解码的方法在tomcat8有效,在更早的版本,需要sun.misc.Base64Encoder和sun.misc.Base64Decoder包,

Android端:
解码(字符串-->字节流):Base64.decode(String ss,Base64.DEFAULT);(相关包,android.util.Base64)
编码:需要先压缩图片,然后再转换成字节流,再编码成字符串(图片-->压缩-->字节流-->字符串)
代码如下:
ByteArrayOutputStream baos = new ByteArrayOutputStream();
//图片压缩并转换成流,
//bitmap.
bitmap.compress(Bitmap.CompressFormat.JPEG, 100,baos);
byte[] byteServer = baos.toByteArray();
String result = Base64.encodeToString(byteServer,Base64.DEFAULT);


注意事项:

在导入sun.misc.Base64Decoder等包时,系统会提示找不到,解决办法如下;

Windows -> Preferences -> Java -> Compiler -> Errors/Warnings ->

Deprecated and trstricted API -> Forbidden reference (access rules): -> change to warning

小贴士:

二进制数据要转成字符串来传输是需要经过编码(例如BASE64)处理才可以的;

1.在发送端用BASE64Encoder将二进制数据编码成字符串后再发送;

byte[] bt = <bt是读取到的图片的二制数据>;

String temp = new sun.misc.BASE64Encoder().encodeBuffer(bt);

2.在接收端用BASE64Decoder对接收到的字符串解码成二进制数据;再输出生成图片;

byte[] bt = new sun.misc.BASE64Decoder().decodeBuffer(temp);



                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: