2014-04-13 10 views
6

Mit der Kamera-API kann ich erfolgreich ein Bild aufnehmen und es in einem Ordner speichern. Hier ist der Code, den ich verwende:Aufnehmen von Bildern in Android alle 5 Sekunden

main.xml:

<FrameLayout 
     android:id="@+id/camera_preview" 
     android:layout_width="fill_parent" 
     android:layout_height="fill_parent" 
     android:layout_weight="1" /> 

    <Button 
     android:id="@+id/button_capture" 
     android:layout_width="wrap_content" 
     android:layout_height="wrap_content" 
     android:layout_gravity="center" 
     android:text="Capture" /> 

Eine Hilfsklasse:

import java.io.IOException; 

import android.content.Context; 
import android.hardware.Camera; 
import android.view.SurfaceHolder; 
import android.view.SurfaceView; 

public class CameraPreview extends SurfaceView implements 
     SurfaceHolder.Callback { 
    private SurfaceHolder mSurfaceHolder; 
    private Camera mCamera; 

    // Constructor that obtains context and camera 
    @SuppressWarnings("deprecation") 
    public CameraPreview(Context context, Camera camera) { 
     super(context); 
     this.mCamera = camera; 
     this.mSurfaceHolder = this.getHolder(); 
     this.mSurfaceHolder.addCallback(this); 
     this.mSurfaceHolder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); 
    } 

    @Override 
    public void surfaceCreated(SurfaceHolder surfaceHolder) { 
     try { 
      mCamera.setPreviewDisplay(surfaceHolder); 
      mCamera.setDisplayOrientation(90); 
      mCamera.startPreview(); 
     } catch (IOException e) { 
      // left blank for now 
     } 
    } 

    @Override 
    public void surfaceDestroyed(SurfaceHolder surfaceHolder) { 
     mCamera.stopPreview(); 
     mCamera.release(); 
    } 

    @Override 
    public void surfaceChanged(SurfaceHolder surfaceHolder, int format, 
      int width, int height) { 
     // start preview with new settings 
     try { 
      mCamera.setPreviewDisplay(surfaceHolder); 
      mCamera.startPreview(); 
     } catch (Exception e) { 
      // intentionally left blank for a test 
     } 
    } 

} 

Aktivität Klasse:

import java.io.File; 
import java.io.FileNotFoundException; 
import java.io.FileOutputStream; 
import java.io.IOException; 
import java.text.SimpleDateFormat; 
import java.util.Date; 

import android.os.Bundle; 
import android.os.Environment; 
import android.app.Activity; 
import android.hardware.Camera; 
import android.hardware.Camera.PictureCallback; 
import android.util.Log; 
import android.view.Menu; 
import android.view.View; 
import android.widget.Button; 
import android.widget.FrameLayout; 

public class MyCamera extends Activity { 
    private Camera mCamera; 
    private CameraPreview mCameraPreview; 

    @Override 
    protected void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     setContentView(R.layout.main); 
     mCamera = getCameraInstance(); 
     mCameraPreview = new CameraPreview(this, mCamera); 
     FrameLayout preview = (FrameLayout) findViewById(R.id.camera_preview); 
     preview.addView(mCameraPreview); 

     Button captureButton = (Button) findViewById(R.id.button_capture); 
     captureButton.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       mCamera.takePicture(null, null, mPicture); 
      } 
     }); 
    } 

    /** 
    * Helper method to access the camera returns null if it cannot get the 
    * camera or does not exist 
    * 
    * @return 
    */ 
    private Camera getCameraInstance() { 
     Camera camera = null; 
     try { 
      camera = Camera.open(); 
     } catch (Exception e) { 
      // cannot get camera or does not exist 
     } 
     return camera; 
    } 

    PictureCallback mPicture = new PictureCallback() { 
     @Override 
     public void onPictureTaken(byte[] data, Camera camera) { 
      File pictureFile = getOutputMediaFile(); 
      if (pictureFile == null) { 
       return; 
      } 
      try { 
       FileOutputStream fos = new FileOutputStream(pictureFile); 
       fos.write(data); 
       fos.close(); 
      } catch (FileNotFoundException e) { 

      } catch (IOException e) { 
      } 
     } 

    }; 

    private static File getOutputMediaFile() { 
     File mediaStorageDir = new File(
       Environment 
         .getExternalStoragePublicDirectory(Environment.DIRECTORY_PICTURES), 
       "MyCameraApp"); 
     if (!mediaStorageDir.exists()) { 
      if (!mediaStorageDir.mkdirs()) { 
       Log.d("MyCameraApp", "failed to create directory"); 
       return null; 
      } 
     } 
     // Create a media file name 
     String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss") 
       .format(new Date()); 
     File mediaFile; 
     mediaFile = new File(mediaStorageDir.getPath() + File.separator 
       + "IMG_" + timeStamp + ".jpg"); 

     return mediaFile; 
    } 

    @Override 
    public boolean onCreateOptionsMenu(Menu menu) { 
     // Inflate the menu; this adds items to the action bar if it is present. 
     getMenuInflater().inflate(R.menu.my_camera, menu); 
     return true; 
    } 

} 

Ich habe auch hinzugefügt die Manifest-Datei die folgenden:

<uses-feature android:name="android.hardware.camera" /> 
    <uses-permission android:name="android.permission.CAMERA" /> 
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> 

Ich habe folgende Probleme:

ich folgendes tun:

  1. Nach dem Drücken der Aufnahmetaste, i die Kamera wollen automatisch weiter Bilder alle 5 Sekunden aufnehmen, durch eine mit Countdown-Timer. So habe ich hinzugefügt, um die folgenden:

    while(true){ 
        new CountDownTimer(5000,1000){ 
    
          @Override 
          public void onFinish() { 
           mCamera.takePicture(null, null, mPicture); 
          } 
    
          @Override 
          public void onTick(long millisUntilFinished) { 
    
          } 
    
         }.start(); 
    } 
    

Allerdings bin ich nicht mehr ein Bild zu bekommen. Ich fügte die while (true) hinzu, um den Code durch sein nicht zu wiederholen. Ich habe es ohne die Zeit versucht (wahr) und wie erwartet ist die Bilderfassung für 5 Sekunden verzögert

Zweite Sache ist: Wie kann ich die Qualität der aufgenommenen Bilder ändern?

Jede Hilfe wird sehr geschätzt.

+0

Hallo user2262955, können Sie bitte eine funktionierende Probe davon auf Github setzen? Thnaks – Amir

Antwort

2

Entfernen Sie die while(true), Sie brauchen es nicht und erstellen unbegrenzte Countdown-Timer.

Ihr Countdown zu diesen

starten ändern
new CountDownTimer(5000,1000){ 

    @Override 
    public void onFinish() { 

    } 

    @Override 
    public void onTick(long millisUntilFinished) { 
     mCamera.startPreview(); 
     mCamera.takePicture(null, null, mPicture); 
    } 

}.start(); 

onTick alle 1000 ms in diesem Fall aufgerufen wird, und onFinish aufgerufen, wenn der Timer-Countdown beendet ist.

Wenn Sie etwas alle 5 Sekunden wiederholen wollen, glaube ich nicht, dass ein CountDownTimer Ihren Bedürfnissen entspricht ... ein Timer wäre besser.

Timer timer = new Timer(); 
timer.schedule(new TimerTask() 
{ 
    @Override 
    public void run() 
    { 
     mCamera.startPreview(); 
     mCamera.takePicture(null, null, mPicture); 
    } 
}, 0, 1000); 

Remeber Timer instace zu speichern, ihn zu stoppen!

+0

Funktioniert nicht. Ich bekomme nur ein Bild – user2262955

+1

Vielleicht, weil, um mehr Bilder zu machen, sollten Sie zuerst startPreview() aufrufen.- Siehe die aktualisierte Antwort. –

+0

Habe noch nicht mit Timer gearbeitet. Ich bekomme Quelle nicht gefunden: Der Quellanhang enthält nicht die Quelle für die Datei Timer.class – user2262955

0
while (true) { 
    new CountDownTimer(5000, 1000) { 
     @Override 
     public void onFinish() { 
      releaseCamera(); 
     } 

     @Override 
     public void onTick(long millisUntilFinished) { 
      mCamera.takePicture(null, null, mPicture); 
     } 

     }.start(); 
} 

Sie benötigen Bild zu erfassen, wenn onTick genannt wird, nicht wenn onFinish genannt wird. onTick wird jedes Mal nach 10 Sekunden (d.h. das spezifizierte Intervall) aufgerufen, wohingegen onFinish aufgerufen wird, sobald countDownTimer beendet ist. Dies ist der Grund, warum Sie nur ein Bild erhalten.