`
aokunsang
  • 浏览: 815685 次
  • 性别: Icon_minigender_1
  • 来自: 北京
社区版块
存档分类
最新评论

Android拍照,上传,预览综合【修改】

 
阅读更多

   最近需要做手机拍照【两种方式:调用系统相机(博客最后);自己写照相机布局】,预览,上传功能。特地研究了下android的手机拍照。

参考地址:

http://blog.csdn.net/cfwdl/article/details/5746708

http://mjbb.iteye.com/blog/1018006

http://blog.csdn.net/hellogv/article/details/5962494

 

1、上传文件功能网上很多讲的,只要细心点,按照格式来写发送的数据,都是没有问题的。

2、预览使用Gallery和ImageSwitcher就行,我做的很简单(参考代码)。

 

 

----------------------------------------------------------------------------------------------------------------------

修改内容

          1、照相功能使用系统自带照相机(自己写的照相机属性设置根据不同照相机会有问题,所以舍弃)

          2、预览功能不再使用Gallery+ImageSwitcher;实用性不强,并且显示慢且卡。改用异步加载

          3、上传图片时,对图片进行压缩,增加上传速度。

          4、长按gridView进入编辑模式,批量删除图片。参考http://aokunsang.iteye.com/blog/1668902

          5、今天又做修改,之前写的压缩图片方法的竟然会变形(没有测试大的图片),修改后不会变形了。

  以此,希望能做到最好的用户体验。

 

附上流程图:


 
拍照功能:【预览尺寸有知道的朋友留言告知。】
 * 拍照
 * @author Administrator
 */
public class TakePhotoAct extends Activity implements SurfaceHolder.Callback{
	
	private static String imgPath = Environment.getExternalStorageDirectory().getPath() + "/"+Const.imageDir;
	
	private SurfaceView surfaceView;   //相机画布
	private SurfaceHolder surfaceHolder; 
	private Button takePicView,exitView;
	
	private Camera mCamera;    //照相机
	
	@Override
    public void onCreate(Bundle savedInstanceState) {
		
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
//这里我在AndroidManifest.xml的activity中添加了android:theme="@android:style/Theme.NoTitleBar.Fullscreen"

        /**
         * 隐藏状态栏和标题栏
         
        this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
        requestWindowFeature(Window.FEATURE_NO_TITLE);
        */
        //setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE);  //横屏
        /**
         * 获取Button并且设置事件监听
         */
        takePicView = (Button)this.findViewById(R.id.takepic);
        takePicView.setOnClickListener(TakePicListener);
        exitView = (Button)this.findViewById(R.id.exit);
        exitView.setOnClickListener(new OnClickListener() {
			@Override
			public void onClick(View v) {
				finish();
			}
		});
        surfaceView = (SurfaceView)this.findViewById(R.id.surface_camera);
        surfaceHolder = surfaceView.getHolder();
        surfaceHolder.addCallback(this);
        surfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS);
        
        checkSoftStage();  //首先检测SD卡是否存在
    }
	
	/**
	 * 检测手机是否存在SD卡,网络连接是否打开
	 */
	private void checkSoftStage(){
		if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){  //判断是否存在SD卡
//			String rootPath = Environment.getExternalStorageDirectory().getPath();  //获取SD卡的根目录
			File file = new File(imgPath);
			if(!file.exists()){
				file.mkdir();
			}
		}else{
			new AlertDialog.Builder(this).setMessage("检测到手机没有存储卡!请插入手机存储卡再开启本应用。")
				.setPositiveButton("确定", new DialogInterface.OnClickListener() {
					@Override
					public void onClick(DialogInterface dialog, int which) {
						finish();
					}
				}).show();
		}
	}
	
	/**
	 * 点击拍照按钮,启动拍照
	 */
	private final OnClickListener TakePicListener = new OnClickListener(){
		@Override
		public void onClick(View v) {
			mCamera.autoFocus(new AutoFoucus());  //自动对焦
		}
	};
	
	/**
	 * 自动对焦后拍照
	 * @author aokunsang
	 * @Date 2011-12-5
	 */
	private final class AutoFoucus implements AutoFocusCallback{
		@Override
		public void onAutoFocus(boolean success, Camera camera) {
			if(success && mCamera!=null){
				mCamera.takePicture(mShutterCallback, null, mPictureCallback);
			}
		}
	}
	/**
	 * 重点对象、 此处实例化了一个本界面的PictureCallback
	 * 当用户拍完一张照片的时候触发,这时候对图片处理并保存操作。
	 * 
	 */
	private final PictureCallback mPictureCallback = new PictureCallback() {
		@Override
		public void onPictureTaken(byte[] data, Camera camera) {
			try {
				String fileName = System.currentTimeMillis()+".jpg";
				File file = new File(imgPath,fileName);
				Bitmap bm = BitmapFactory.decodeByteArray(data, 0, data.length);
				BufferedOutputStream bos = new BufferedOutputStream(new FileOutputStream(file));
				bm.compress(Bitmap.CompressFormat.JPEG, 60, bos);
				bos.flush();
				bos.close();
				
				Intent intent = new Intent(TakePhotoAct.this,PictureViewAct.class);
				intent.putExtra("imagePath", file.getPath());
				startActivity(intent);
			} catch (Exception e) {
				e.printStackTrace();
			}
		}
	};
	/** 
	* 在相机快门关闭时候的回调接口,通过这个接口来通知用户快门关闭的事件, 
	* 普通相机在快门关闭的时候都会发出响声,根据需要可以在该回调接口中定义各种动作, 例如:使设备震动 
	*/  
	private final ShutterCallback mShutterCallback = new ShutterCallback() {  
		public void onShutter() {  
			Log.d("ShutterCallback", "...onShutter...");  
		}  
	};
	
	@Override
	/**
	 * 初始化相机参数,比如相机的参数: 像素, 大小,格式
	 */
	public void surfaceChanged(SurfaceHolder holder, int format, int width,
			int height) {
		Camera.Parameters param = mCamera.getParameters();
		/**
		 * 设置拍照图片格式
		 */
		param.setPictureFormat(PixelFormat.JPEG);
		/**
		 * 设置预览尺寸【这里需要注意:预览尺寸有些数字正确,有些会报错,不清楚为啥】
		 */
		//param.setPreviewSize(320, 240);
		/**
		 * 设置图片大小
		 */
		param.setPictureSize(Const.width, Const.height);
		mCamera.setParameters(param);
		/**
		 * 开始预览
		 */
		mCamera.startPreview();
	}
	@Override
	/**
	 * 打开相机,设置预览
	 */
	public void surfaceCreated(SurfaceHolder holder) {
		try {
			mCamera = Camera.open();  //打开摄像头
			mCamera.setPreviewDisplay(holder);
		} catch (IOException e) {
			mCamera.release();
			mCamera = null;
		}
	}
	
	@Override
	/**
	 * 预览界面被关闭时,或者停止相机拍摄;释放相机资源
	 */
	public void surfaceDestroyed(SurfaceHolder holder) {
		mCamera.stopPreview();
		if(mCamera!=null) mCamera.release();
		mCamera = null;
	}
	
	@Override
	public boolean onKeyDown(int keyCode, KeyEvent event) {
		if(keyCode == KeyEvent.KEYCODE_CAMERA){   //按下相机实体按键,启动本程序照相功能
			mCamera.autoFocus(new AutoFoucus());  //自动对焦
			return true;
		}else{
			return false;
		}
	}
}
  xml:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    >
	<SurfaceView 
		android:id="@+id/surface_camera"
		android:layout_width="fill_parent"
		android:layout_height="fill_parent"
		android:layout_weight="1"
	/>
<LinearLayout 
	android:orientation="horizontal"
	android:layout_width="fill_parent"
	android:layout_height="wrap_content">
	
	<Button 
		android:text="拍照"
		android:layout_width="wrap_content"
		android:layout_height="wrap_content"
		android:id="@+id/takepic"
	/>
	<Button 
		android:text="退出"
		android:layout_width="wrap_content"
		android:layout_height="wrap_content"
		android:id="@+id/exit"
	/>
</LinearLayout>
</LinearLayout>
 预览功能:
 /**
 * 图片预览
 * @author: aokunsang
 * @date: 2012-8-1
 */
public class PictureScanAct extends Activity {

	private GridView gridView;
	private ImageAdapter imgAdapter;
	private List<String> fileNameList = new ArrayList<String>();
	
	@Override
	protected void onCreate(Bundle savedInstanceState) {
		
		super.onCreate(savedInstanceState);
		setContentView(R.layout.picturescan);
		
		gridView = (GridView)findViewById(R.id.picture_grid);
		imgAdapter = new ImageAdapter(this);
		gridView.setAdapter(imgAdapter);
		gridView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
			@Override
			public void onItemClick(AdapterView<?> parent, View view,
					int position, long id) {
				String fileName = fileNameList.get(position);
				startActivity(new Intent(PictureScanAct.this, PictureViewAct.class).putExtra("flag","upload").putExtra("imagePath",fileName));
			}
		});
		//setProgressBarIndeterminateVisibility(true);
		Toast.makeText(this, "加载图片中....", Toast.LENGTH_LONG).show();
	    new AsyncLoadedImage().execute();
	}
	/**
	 * 向适配器添加图片
	 * @param bitmap
	 */
	private void addImage(Bitmap... loadImages){
		for(Bitmap loadImage:loadImages){
			imgAdapter.addPhoto(loadImage);
		}
	}
	/**
	 * 释放内存
	 */
	protected void onDestroy() {
        super.onDestroy();
        final GridView grid = gridView;
        final int count = grid.getChildCount();
        ImageView v = null;
        for (int i = 0; i < count; i++) {
            v = (ImageView) grid.getChildAt(i);
            ((BitmapDrawable) v.getDrawable()).setCallback(null);
        }
    }
	/**
	 * 异步加载图片展示
	 * @author: aokunsang
	 * @date: 2012-8-1
	 */
	 class AsyncLoadedImage extends AsyncTask<Object, Bitmap, Boolean> {

		@Override
		protected Boolean doInBackground(Object... params) {
			File fileDir = new File(Const.imgPath);
			File[] files = fileDir.listFiles();
			boolean result = false;
			if(files!=null){
				for(File file:files){
					String fileName = file.getName();
					if (fileName.lastIndexOf(".") > 0  
							&& fileName.substring(fileName.lastIndexOf(".") + 1,  
							fileName.length()).equals("jpg")){
						Bitmap bitmap;
		                Bitmap newBitmap;
						 try {
	                        BitmapFactory.Options options = new BitmapFactory.Options();
	                        options.inSampleSize = 10;
	                        bitmap = BitmapFactory.decodeFile(file.getPath(), options);
	                        newBitmap = ThumbnailUtils.extractThumbnail(bitmap, 100, 100);
	                        bitmap.recycle();
	                        if (newBitmap != null) {
	                        	fileNameList.add(file.getPath());
	                            publishProgress(newBitmap);
	                            result = true;
	                        }
	                    } catch (Exception e) {
	                        e.printStackTrace();
	                    }
					}
				}
			}
			return result;
		}
		@Override
        public void onProgressUpdate(Bitmap... value) {
			addImage(value);
        }
		@Override
        protected void onPostExecute(Boolean result) {
			if(!result){
				showDialog(1);
			}
        }
	 }
	 @Override
	protected Dialog onCreateDialog(int id) {
		 AlertDialog dialog = new AlertDialog.Builder(PictureScanAct.this).setTitle("温馨提示").setMessage("暂时还没有照片,请先采集照片!")
			.setPositiveButton("确定", new DialogInterface.OnClickListener(){
				@Override
				public void onClick(DialogInterface dialog, int which) {
					startActivity(new Intent(PictureScanAct.this,TakePhotoAct.class));
				}
			}).setNegativeButton("取消", new DialogInterface.OnClickListener() {
				@Override
				public void onClick(DialogInterface dialog, int which) {
					finish();
				}
			}).show();
		 return dialog;
	}
}

 

   GridView适配器:
     public class ImageAdapter extends BaseAdapter {
	private List<Bitmap> picList = new ArrayList<Bitmap>();
	private Context mContext;
	public ImageAdapter(Context mContext){
		this.mContext = mContext;
	}
	
	@Override
	public int getCount() {
		return picList.size();
	}

	/* (non-Javadoc)
	 * @see android.widget.Adapter#getItem(int)
	 */
	@Override
	public Object getItem(int position) {
		// TODO Auto-generated method stub
		return picList.get(position);
	}
	/**
	 * 添加图片
	 * @param bitmap
	 */
	public void addPhoto(Bitmap loadImage){
		picList.add(loadImage);
		notifyDataSetChanged();
	}
	
	/* (non-Javadoc)
	 * @see android.widget.Adapter#getItemId(int)
	 */
	@Override
	public long getItemId(int position) {
		// TODO Auto-generated method stub
		return position;
	}

	@Override
	public View getView(int position, View convertView, ViewGroup parent) {
		ImageView imageView = null;
		if(convertView == null){
			imageView = new ImageView(mContext);
			imageView.setLayoutParams(new GridView.LayoutParams(110, 110));  
			imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);  
			imageView.setPadding(5,5,5,5);
		}else{
			imageView = (ImageView)convertView;
		}
		imageView.setImageBitmap(picList.get(position));
		return imageView;
	}
}

 

   图片预览界面:
  
     <?xml version="1.0" encoding="utf-8"?>
<GridView xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/picture_grid"
    android:layout_width="match_parent"
    android:layout_height="match_parent" 
	android:numColumns="4"
	android:verticalSpacing="5dip"
	android:horizontalSpacing="5dip"
	android:stretchMode="columnWidth"
	android:columnWidth="120dip"
	android:gravity="center"    
    >
</GridView>

 

   
   预览图片:
   



   
 
   上传工具类:
import java.io.BufferedReader;
import java.io.DataOutputStream;
import java.io.FileInputStream;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.util.Map;
import java.util.Map.Entry;

import android.util.Log;

import com.peacemap.photo.po.FileInfo;

/**
 * POST上传文件
 * @author aokunsang
 * @Date 2011-12-6
 */
public class PostFile {

	private static PostFile postFile = new PostFile();
	
	private final static String LINEND = "\r\n";
	private final static String BOUNDARY = "---------------------------7da2137580612"; //数据分隔线
	private final static String PREFIX = "--";
	private final static String MUTIPART_FORMDATA = "multipart/form-data";
	private final static String CHARSET = "utf-8";
	private final static String CONTENTTYPE = "application/octet-stream";
	
	private PostFile(){}
	public static PostFile getInstance(){
		return postFile;
	}
	
	/**
	 * HTTP上传文件
	 * @param actionUrl  请求服务器的路径
	 * @param params     传递的表单内容
	 * @param files      多个文件信息
	 * @return
	 */
	public String post(String actionUrl,Map<String,String> params,FileInfo[] files){
		try {
			URL url = new URL(actionUrl);
			HttpURLConnection urlConn = (HttpURLConnection)url.openConnection();
			urlConn.setDoOutput(true);   //允许输出
			urlConn.setDoInput(true);   //允许输入
			urlConn.setUseCaches(false);
			urlConn.setRequestMethod("POST");
			urlConn.setRequestProperty("connection", "Keep-Alive");
			urlConn.setRequestProperty("Charset", CHARSET);
			urlConn.setRequestProperty("Content-Type", MUTIPART_FORMDATA+";boundary="+BOUNDARY);
			
			DataOutputStream dos = new DataOutputStream(urlConn.getOutputStream());
			//构建表单数据
			String entryText = bulidFormText(params);
			Log.i("-------描述信息---------------", entryText);
			dos.write(entryText.getBytes());
			
			StringBuffer sb = new StringBuffer("");
	
			for(FileInfo file : files){
				sb.append(PREFIX).append(BOUNDARY).append(LINEND);
				sb.append("Content-Disposition: form-data; name=\""+file.getFileTextName()+"\"; filename=\""+file.getFile().getAbsolutePath()+"\""+LINEND);
				sb.append("Content-Type:"+CONTENTTYPE+";charset="+CHARSET+LINEND);
				sb.append(LINEND);
				dos.write(sb.toString().getBytes());
				
				InputStream is = new FileInputStream(file.getFile());
				byte[] buffer = new byte[1024];
                int len = 0;
                while ((len = is.read(buffer)) != -1) {
                	dos.write(buffer, 0, len);
                }
                is.close();
                dos.write(LINEND.getBytes());
			}
			//请求的结束标志
			byte[] end_data = (PREFIX + BOUNDARY + PREFIX + LINEND).getBytes();
			dos.write(end_data);
			dos.flush();
	//-----------------------------------  发送请求数据结束  ----------------------------
			
    //----------------------------------   接收返回信息 ------------------------
			
			int code = urlConn.getResponseCode();
			if(code!=200){
				urlConn.disconnect();
				return "";
			}else{
				BufferedReader br = new BufferedReader(new InputStreamReader(urlConn.getInputStream()));
				String result = "";
				String line = null;
				while((line = br.readLine())!=null){
					result += line;
				}
				br.close();
				urlConn.disconnect();
				return result;
			}
		} catch (Exception e) {
			Log.e("--------上传图片错误--------", e.getMessage());
			return null;
		}
	}
	
	/**
	 * HTTP上传单个文件
	 * @param actionUrl  请求服务器的路径
	 * @param params     传递的表单内容
	 * @param files      单个文件信息
	 * @return
	 */
	public String post(String actionUrl,Map<String,String> params,FileInfo fileInfo){
		return post(actionUrl, params, new FileInfo[]{fileInfo});
	}
	
	/**
	 * 封装表单文本数据
	 * @param paramText
	 * @return
	 */
	private String bulidFormText(Map<String,String> paramText){
		if(paramText==null || paramText.isEmpty()) return "";
		StringBuffer sb = new StringBuffer("");
		for(Entry<String,String> entry : paramText.entrySet()){ 
			sb.append(PREFIX).append(BOUNDARY).append(LINEND);
			sb.append("Content-Disposition:form-data;name=\""
                    + entry.getKey() + "\"" + LINEND);
//			sb.append("Content-Type:text/plain;charset=" + CHARSET + LINEND);
			sb.append(LINEND);
			sb.append(entry.getValue());
			sb.append(LINEND);
		}
		return sb.toString();
	}
	/**
	 * 封装文件文本数据
	 * @param files
	 * @return
	 */
	private String buildFromFile(FileInfo[] files){
		StringBuffer sb = new StringBuffer();
		for(FileInfo file : files){
			sb.append(PREFIX).append(BOUNDARY).append(LINEND);
			sb.append("Content-Disposition: form-data; name=\""+file.getFileTextName()+"\"; filename=\""+file.getFile().getAbsolutePath()+"\""+LINEND);
			sb.append("Content-Type:"+CONTENTTYPE+";charset="+CHARSET+LINEND);
			sb.append(LINEND);
		}
		return sb.toString();
	}
}
    上传图片时对图片进行压缩处理(压缩处理程序):
    /**
		 * 压缩图片上传
		 * @param picPath
		 * @return
		 */
		private synchronized File compressPicture(String picPath){
			
		    int maxWidth = 640,maxHeight=480;  //设置新图片的大小
	            String fileName = picPath.substring(picPath.lastIndexOf("/"));
			
		    BitmapFactory.Options options = new BitmapFactory.Options();  
		    options.inJustDecodeBounds = true;  
		    Bitmap image = BitmapFactory.decodeFile(picPath, options);  
		    double ratio = 1D;  
		    if (maxWidth > 0 && maxHeight <= 0) {  
		        // 限定宽度,高度不做限制  
		        ratio = Math.ceil(options.outWidth / maxWidth);  
		    } else if (maxHeight > 0 && maxWidth <= 0) {  
		        // 限定高度,不限制宽度  
		        ratio = Math.ceil(options.outHeight / maxHeight);  
		    } else if (maxWidth > 0 && maxHeight > 0) {  
		        // 高度和宽度都做了限制,这时候我们计算在这个限制内能容纳的最大的图片尺寸,不会使图片变形  
		        double _widthRatio = Math.ceil(options.outWidth / maxWidth);  
		        double _heightRatio = (double) Math.ceil(options.outHeight / maxHeight);  
		        ratio = _widthRatio > _heightRatio ? _widthRatio : _heightRatio;  
		    }  
		    if (ratio > 1)
		        options.inSampleSize = (int) ratio;
		    options.inJustDecodeBounds = false;  
		    options.inPreferredConfig = Bitmap.Config.RGB_565;  
		    image = BitmapFactory.decodeFile(picPath, options);  
           //保存入sdCard  
           File file = new File(Const.thumbnailPath+fileName);  
           try {  
	            FileOutputStream out = new FileOutputStream(file);  
	            if(image.compress(Bitmap.CompressFormat.JPEG, 100, out)){  
	                out.flush();  
	                out.close();  
	            }
	        } catch (Exception e) { 
	            e.printStackTrace();
	            return new File(picPath);
	        }finally{
	        	if(image!=null && !image.isRecycled()){
	        		image.recycle();
	        	}
	        }
			return file;
		}

 

 
-------------------------------------我是个华丽的分割线,哇哈哈-----------------------------------------------
 
做完这个拍照后,感觉功能太简单,比如:设置图片大小,白天夜晚照相等等一些系统照相机带的功能都没有,因此用在项目中感觉不炫。 然后就用了简单点的,直接调用系统照相机了。本来想着简单呢,后来也遇到点问题。
    (1)根据Camera Activity返回的时候,会带一个名为data的Bitmap对象,照片的缩略图(这个地方可以做各种修改,我没用到不说了),上代码
 @Override  
   public void onCreate(Bundle savedInstanceState) {
	   super.onCreate(savedInstanceState);
	   checkSoftStage();
	   
	   try {
		   Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
		   startActivityForResult(intent, TAKE_PICTURE); 
	   } catch (Exception e) {
		   e.printStackTrace();
	   }
}
 /**
	 * 检测手机是否存在SD卡,网络连接是否打开
	 */
	private void checkSoftStage(){
		if(Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED)){  //判断是否存在SD卡
			File file = new File(imgPath);
			if(!file.exists()){
				file.mkdir();
			}
		}else{
			new AlertDialog.Builder(this).setMessage("检测到手机没有存储卡!请插入手机存储卡再开启本应用。")
				.setPositiveButton("确定", new DialogInterface.OnClickListener() {
					@Override
					public void onClick(DialogInterface dialog, int which) {
						finish();
					}
				}).show();
		}
	}
 protected void onActivityResult(int requestCode, int resultCode, Intent data)  {         
    		if (resultCode == TAKE_PICTURE)      {          
    			//  拍照Activity保存图像数据的key是data,返回的数据类型是Bitmap对象          
    			Bitmap cameraBitmap = (Bitmap) data.getExtras().get("/sdcard/rtest.jpg");         
				//  在ImageView组件中显示拍摄的照片         
    			image.setImageBitmap(cameraBitmap); 

                // 做自己的业务操作。。。。
    			}      
      super.onActivityResult(requestCode, resultCode, data);  
    		    } 
 
   (2)以上代码在我的小米手机上测试时,出现问题了。 返回的name为data的Bitmap对象是个Null,我发现小米照完相片之后,他会先跳到一个预览的界面(系统自带的页面),所以得不到Bitmap对象了。
因此我就先保存照片以及其路径,然后在onActivityResult中获取图片,做业务操作,代码如下:
   public void onCreate(Bundle savedInstanceState) {
	   super.onCreate(savedInstanceState);
	   checkSoftStage();
	   
	   try {
		   Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
		   startActivityForResult(intent, TAKE_PICTURE); 
	   } catch (Exception e) {
		   e.printStackTrace();
	   }
	   
	   try {
		   Intent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
		   String fileName = System.currentTimeMillis()+".jpg";
		   newImgPath = imgPath + "/" + fileName;
		   Uri uri = Uri.fromFile(new File(imgPath,fileName));
		   intent.putExtra(MediaStore.EXTRA_OUTPUT, uri);
		   startActivityForResult(intent, TAKE_PICTURE); 
		  } catch (Exception e) {
			  e.printStackTrace();
		  } 
   }
 @Override 
   protected void onActivityResult(int requestCode, 
	   int resultCode, Intent data) { 
	   	   Log.i("--------图片路径---------", "------"+newImgPath+"---------");
		  //.....做一些业务操作
		} catch (Exception e) {
			e.printStackTrace();
		}
		super.onActivityResult(requestCode, resultCode, data);
   }
 
 
 
  • 大小: 132.7 KB
  • 大小: 127.2 KB
  • 大小: 161.4 KB
分享到:
评论
37 楼 a19279741 2015-08-19  
楼主,求源码~~~~~19279741@qq.com
谢谢~~~~~~~~~
36 楼 czltx224 2015-03-12  
能发个源码吗,谢谢。784621997@qq.com
35 楼 wwlishijie 2014-10-01  
能发个源码吗,急需,,谢谢。1750992257@qq.com
34 楼 kong_yu2123 2014-09-20  
大虾,还有源码没?求发一份学习一下!灰常的有这个需求呢~493096250@qq.com
33 楼 zyj0825cn 2014-07-18  
哥们,写的很好,求源码,不胜感激,zyj0825cn@163.com
32 楼 zyj0825cn 2014-07-18  
你好,请发一份源码到我的邮箱: zyj0825cn@163.com 谢谢
31 楼 eclothy 2014-01-17  
我去,这么点代码这么多错误,真是难得啊。。
30 楼 liu_zheng 2013-11-14  
不错 谢谢博主  收藏学习了
29 楼 aokunsang 2013-07-12  
wenqiang0718 写道
楼主好人,可否发一份源码243608467@qq.com

亲,不好意思。这个是我在项目中摘出来的部分备忘的,源码逻辑复杂了点,不能外放。
28 楼 wenqiang0718 2013-07-11  
楼主好人,可否发一份源码243608467@qq.com
27 楼 aokunsang 2013-07-06  
Sev7en_jun 写道
[/**
139.     * 设置预览尺寸【这里需要注意:预览尺寸有些数字正确,有些会报错,不清楚为啥】
140.     */ 
141.    //param.setPreviewSize(320, 240); 
}

宽和高可以通过如下方式获取,不知道是不是你想要的那样
WindowManager wm = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
// 获取屏幕的宽和高
screenWidth = display.getWidth();
screenHeight = display.getHeight();

你好,你这是获取屏幕的宽和高,应该跟它没关系。我认为这个预览尺寸是每个手机系统摄像头内置的预览和照相的大小,比如:320*480,600*800等、
26 楼 Sev7en_jun 2013-07-05  
[/**
139.     * 设置预览尺寸【这里需要注意:预览尺寸有些数字正确,有些会报错,不清楚为啥】
140.     */ 
141.    //param.setPreviewSize(320, 240); 
}

宽和高可以通过如下方式获取,不知道是不是你想要的那样
WindowManager wm = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
// 获取屏幕的宽和高
screenWidth = display.getWidth();
screenHeight = display.getHeight();
25 楼 aokunsang 2013-05-21  
a8723832 写道
你好,博主,我想做一个这样的界面,能否将系统摄像头的照相VIEW进行修改?或者是在那个界面新添加一些东西?

系统摄像机貌似不能改动的吧,没有spring那样可以随意扩展吧、兄台可以研究下。当然就算可以,那你也需要针对每个手机进行更改,毕竟照相机这玩意,每个手机绝对是不一样的。
24 楼 a8723832 2013-05-14  
你好,博主,我想做一个这样的界面,能否将系统摄像头的照相VIEW进行修改?或者是在那个界面新添加一些东西?
23 楼 xiaoji123pt 2012-11-17  
大哥~~求一个源码demo不甚感激。。zp8170508@126.com
22 楼 shuyuze 2012-10-23  
学习,求源码一份QQ542319503@qq.com
21 楼 kfjihailong 2012-10-22  
求源码呀,楼主 269565478@qq.com
20 楼 aokunsang 2012-10-16  
messigoogle 写道
楼主,怎么没有项目附件呢,好人到底啊

哎呀,哥哥,这个真没有demo,都是做项目时候自己解决问题后备忘的。项目肯定不能发布出去了。 
以上这些代码组装后,基本上已经可以使用了,根据自己的需要修改下,就行了。又没那么难
19 楼 messigoogle 2012-10-13  
楼主,怎么没有项目附件呢,好人到底啊
18 楼 hylandtecliulei 2012-09-28  
能否发份源码? 很需要,谢谢。

相关推荐

    android 不预览拍照 后台拍照

    在Android开发中,有时我们需要实现一些特殊的相机功能,比如不预览的拍照或者后台拍照。这些需求可能出现在一些需要高效能、低资源消耗或者隐私保护的场景。本篇将详细探讨如何实现这样的功能。 首先,要理解“不...

    android 无预览 拍照

    在Android平台上,无预览拍照是指在用户拍摄照片时,不显示实时的摄像头预览画面。这种功能在某些特定的应用场景下很有用,比如后台拍摄、安全应用或者是为了节省资源和提升性能。以下是对实现这一功能的详细讲解。 ...

    android TextureVIew实现摄像头预览和拍照

    在Android开发中,TextureView是一种可以显示动态图形的视图,它可以用来实现实时的视频流,例如摄像头预览和拍照功能。本教程将详细讲解如何利用TextureView来实现这一目标,并讨论如何优化用户界面。 首先,理解...

    Android圆形相机预览窗口,圆形SurfaceView

    在Android开发中,有时我们可能需要创建一个独特的用户体验,比如设计一个圆形的相机预览窗口。这个场景就涉及到了Android的SurfaceView以及如何定制它的显示效果。本文将深入探讨如何实现一个圆形的相机预览窗口。 ...

    android 视频图片预览

    在Android开发中,实现视频和图片的预览功能是一项常见的需求。这通常涉及到用户界面设计、多媒体处理以及性能优化等多个方面。"android 视频图片预览"这一主题,主要涵盖了以下几个关键知识点: 1. **多媒体文件...

    android实现附件预览效果

    在Android应用开发中,"附件预览效果"通常是指用户能够查看和操作各种类型的文件,如文档、图片、音频或视频等。这个过程涉及到多个关键知识点,包括文件管理、权限控制、第三方应用交互以及Android系统版本的兼容性...

    Android 端本地预览 PDF 文件

    Android 端本地预览 PDF 文件,使用 AS2.3.3 Gradle 4.1 下载下来可以直接编译运行,内部支持加载本地 File ,也可以加载一个 URL 类型的 PDF 文件,如果恰恰你的 APP 不想调用第三方软件的话 这个 DEMO 非常适合你...

    android 8.0 webview 拍照预览、二维码扫描

    android 8.0 webview 拍照、预览、二维码扫描比较完整的例子,对于权限检查控制,有比较完善的提示写法。可以下载后,直接在android studid上运行,编译版本和target版本均是SDK android 8.0,最低版本设置成了...

    Android自定义照相机 预览拍照 切换前后置摄像头

    本文将深入探讨如何在Android中实现自定义相机,包括预览、拍照以及切换前后置摄像头的功能。 一、Android Camera API基础 Android提供了两个主要的相机API:Camera API1(在API level 9引入)和Camera2 API(在...

    android camera2实现实时预览和拍照

    本文将深入探讨如何使用`Android Studio`和`Camera2` API来实现实时预览以及拍照功能,并将照片以`.fpg`格式保存到手机中。 首先,我们需要在`build.gradle`文件中添加必要的依赖项,确保项目可以使用`Camera2` API...

    android无预览静默拍照

    在Android平台上,有时候开发者需要实现一个功能,即在用户不知情的情况下进行拍照,这通常被称为“无预览静默拍照”。这种技术常用于自动化测试、安全监控或者后台数据获取等场景。下面我们将深入探讨如何在Android...

    Android原生Camera2完成预览和拍照

    本文将深入探讨如何使用Camera2 API来实现预览和拍照功能。 一、Camera2 API概述 Camera2 API是Android Lollipop(API级别21)引入的,旨在提供对相机硬件更直接和全面的访问。它包含了一系列类和接口,如...

    Android 本地预览Excel,Word,PPT,PDF 源代码

    这个“Android本地预览Excel,Word,PPT,PDF源代码”项目提供了解决这一需求的解决方案。它允许用户在不离开应用程序的情况下,在Android设备上预览这些常见办公格式的文件。 首先,我们要关注的是“asposed转Excel...

    Android图片上传,可以选择多张图片,缩放预览,拍照上传等.rar

    这个压缩包"Android图片上传,可以选择多张图片,缩放预览,拍照上传等.rar"提供了实现这一功能的具体代码示例,可以帮助开发者理解并实现在自己的项目中集成类似功能。这个功能包括了以下几个重要的知识点: 1. **...

    Android前后摄像头同时预览

    在API Level 9(Android 2.3)及更高版本中,我们可以使用`Camera`类来实现摄像头的预览、拍照和录像功能。而在API Level 14(Android 4.0)引入的`Camera2` API则提供了更高级的功能和更好的性能,但同时对设备硬件...

    Android5.0 launcher 小部件预览图片

    修改Android5.0 launcher 小部件预览图片大小

    Android调用相机拍照,view截屏,无预览、静默拍照

    在Android应用开发中,有时我们需要实现一些特殊的功能,如调用相机拍照、截取界面视图,甚至在没有用户预览的情况下进行静默拍照。这些功能在特定场景下有着广泛的应用,例如创建自定义相机应用或者需要后台拍摄的...

    Android通过相机预览使用原生接口捕捉人脸并取框,androidstuido工程

    在Android平台上,开发一款应用程序以实现通过相机预览来捕捉并标定人脸是一项常见的任务。这个项目名为"Android通过相机预览使用原生接口捕捉人脸并取框",使用了Android Studio作为集成开发环境(IDE),并且直接...

    Android实现后台连续静默拍照

    在Android平台上实现后台连续静默拍照是一项技术挑战,涉及到多个关键知识点。首先,我们要理解Android系统的权限管理和运行机制,然后是相机API的使用,以及如何在后台执行任务。以下是对这些核心概念的详细阐述。 ...

    android拍照上传代码

    本文将详细解析如何实现这样一个功能,并基于给出的“android拍照上传代码”进行讨论。 首先,Android拍照功能主要依赖于`Intent`系统服务。在Android中,可以启动相机应用来捕获图片,通过创建一个`Intent`对象并...

Global site tag (gtag.js) - Google Analytics