使用SurfaceView打开/关闭手电筒

7

我正在编写一个Android相机应用程序,并尝试实现闪光灯功能,我正在使用SurfaceView,每当我点击闪光按钮时开关可以工作,但是闪光灯没有亮起来...请看下面的代码,我已经用它来打开/关闭闪光灯。

完整代码:--

 @Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_camera);

          preview=(SurfaceView)findViewById(R.id.surface);     
                previewHolder=preview.getHolder();    
                previewHolder.addCallback(surfaceCallback);    
                previewHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); 
                previewHolder.setFixedSize(getWindow().getWindowManager()     
                        .getDefaultDisplay().getWidth(), getWindow().getWindowManager() 
                        .getDefaultDisplay().getHeight()); 


            btnFlash = (ImageButton) findViewById(R.id.btnFlash);               
            /*
             * First check if device is supporting flashlight or not
             */
            hasFlash = getApplicationContext().getPackageManager()
                    .hasSystemFeature(PackageManager.FEATURE_CAMERA_FLASH);

            if (!hasFlash) {
                // device doesn't support flash
                // Show alert message and close the application
                AlertDialog alert = new AlertDialog.Builder(CameraLauncherActivity.this)
                        .create();
                alert.setTitle("Error");
                alert.setMessage("Sorry, your device doesn't support flash light!");
                alert.setButton("OK", new DialogInterface.OnClickListener() {
                    public void onClick(DialogInterface dialog, int which) {
                        // closing the application
                        finish();
                    }
                });
                alert.show();
                return;     
            }

            // displaying button image
            toggleButtonImage();

            btnFlash.setOnClickListener(new View.OnClickListener() {
                @Override
                public void onClick(View v) {
                    if (isFlashOn) {
                        // turn off flash
                        turnOffFlash();
                    } else {
                        // turn on flash
                        turnOnFlash();
                    }                  
                }
            });                    
    }       

/*
 * Turning On flash
 */
private void turnOnFlash() {
    if (!isFlashOn) {
        if (camera == null || params == null) {
            return;
        }

        params = camera.getParameters();
        params.setFlashMode(Parameters.FLASH_MODE_ON);
        camera.setParameters(params);
        isFlashOn = true;

        // changing button/switch image
        toggleButtonImage();
    }
}

/*
 * Turning Off flash
 */
private void turnOffFlash() {
    if (isFlashOn) {
        if (camera == null || params == null) {
            return;
        }

        params = camera.getParameters();
        params.setFlashMode(Parameters.FLASH_MODE_OFF);
        camera.setParameters(params);
        isFlashOn = false;

        // changing button/switch image
        toggleButtonImage();
    }
}

/*
 * Toggle switch button images
 * changing image states to on / off
 * */
private void toggleButtonImage(){
    if(isFlashOn){
        btnFlash.setImageResource(R.drawable.green_button);
    }else{
        btnFlash.setImageResource(R.drawable.red_button);
    }
}

@Override
public void onResume() {  
    super.onResume();   
    camera=Camera.open(); 
    }  

@Override   
public void onPause() {  
    super.onPause();  
    if (inPreview) {  
    camera.stopPreview();   }   
    camera.release();   
    camera=null;   
    inPreview=false;         
    }   


private Camera.Size getBestPreviewSize(int width, int height,Camera.Parameters parameters){   
    Camera.Size result=null;   
    for (Camera.Size size : parameters.getSupportedPreviewSizes()) 
    {   
        if (size.width<=width && size.height<=height)
        {
            if (result==null) {  
                result=size;   
            }   else {  
                int resultArea=result.width*result.height; 
                int newArea=size.width*size.height;  
                if (newArea>resultArea) {   
                    result=size;   
                    }  
                }   
            }   
        }   
    return(result);   
    }    
    SurfaceHolder.Callback surfaceCallback=new SurfaceHolder.Callback(){

    public void surfaceCreated(SurfaceHolder holder) {     
        try {        
            camera.setPreviewDisplay(previewHolder); 
            }   catch (Throwable t) {   
                Log.e("PreviewDemo-surfaceCallback",
                        "Exception in setPreviewDisplay()", t);
                Toast.makeText(CameraLauncherActivity.this, t.getMessage(), Toast.LENGTH_LONG).show();       
                }     
            }      

    public void surfaceChanged(SurfaceHolder holder,int format, int width,int height) {
        params = camera.getParameters();       
        params.setFlashMode(Camera.Parameters.FLASH_MODE_ON);
        Camera.Size size=getBestPreviewSize(width, height,                                           
                params);       
        if (size!=null) {      
            params.setPreviewSize(size.width, size.height);
            camera.setParameters(params);       
            camera.startPreview();       
            inPreview=true;   
            ZoomControls zoomControls = (ZoomControls) findViewById(R.id.zoomControls);

            if (params.isZoomSupported()) {
                final int maxZoomLevel = params.getMaxZoom();
                Log.i("max ZOOM ", "is " + maxZoomLevel);
                zoomControls.setIsZoomInEnabled(true);
                zoomControls.setIsZoomOutEnabled(true);

                zoomControls.setOnZoomInClickListener(new OnClickListener(){
                    public void onClick(View v){
                        if(currentZoomLevel < maxZoomLevel){
                            currentZoomLevel++;
                            //mCamera.startSmoothZoom(currentZoomLevel);
                            params.setZoom(currentZoomLevel);
                            camera.setParameters(params);
                        }
                    }
                });

                zoomControls.setOnZoomOutClickListener(new OnClickListener(){
                    public void onClick(View v){
                        if(currentZoomLevel > 0){
                            currentZoomLevel--;
                            params.setZoom(currentZoomLevel);
                            camera.setParameters(params);
                        }
                    }
                });    
            }
            else
                zoomControls.setVisibility(View.GONE);
            }     
        }      

    public void surfaceDestroyed(SurfaceHolder holder) {

        }   
    };            
    }

您的设备可能有多个摄像头(例如前置和后置),但并非所有摄像头都有闪光灯。请在所有摄像头上进行迭代,直到找到支持闪光灯的摄像头,并打开该摄像头。 - yoah
@yoah 我正在使用Galaxy EK-GC100相机,它只有后置摄像头。 - Sun
2个回答

12

我能想到一些事情:

记得在相机应用程序的清单上添加功能和要求:

<!-- Camera Requirement -->
<uses-feature android:name="android.hardware.camera" />

<!-- Camera Permissions -->
<uses-permission android:name="android.permission.CAMERA" />     

<!-- Features -->
<uses-feature android:name="android.hardware.camera.flash" />
<uses-feature android:name="android.hardware.camera.autofocus" />

如果您想将它用作手电筒,可以按照@yoah所说的做:

parameters.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH)
如果没有开启闪光灯,需要在拍照时打开它,使用以下方法:
parameters.setFlashMode(Camera.Parameters.FLASH_MODE_ON)

最近我写了一个自定义相机应用程序,但还没有上传到Github上,它已经具备了所有基本功能。


嗨@AbrahimNeil,我刚刚将它上传到Github:https://github.com/agustinjuarez/android-camera-api,这是一个基本的WIP,所以它可能包含很多错误,并且几乎没有文档,但对于你来说可能足够了解一下。 - CodingDuckling

3
尝试使用

parameters.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH)

将FLASH_MODE_ON设置为开启状态,可以在拍照时显示闪光灯。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接