2015-05-22 2 views
4

Я создаю простое приложение Flashlight, но каждый раз, когда я оставляю приложение и снова его открываю, он падает. Я что-то пропустил в своем коде, потому что не уверен, что ниже ошибка при сбоях. Пожалуйста, дайте мне знать, что мне нужно сделать, чтобы решить эту проблему резюме:App crashes when Resumed

package com.example.gkvxm.materiallight; 
 

 
import android.animation.ValueAnimator; 
 
import android.app.Activity; 
 
import android.content.Context; 
 
import android.content.pm.PackageManager; 
 
import android.hardware.Camera; 
 
import android.os.Bundle; 
 
import android.util.Log; 
 
import android.view.KeyEvent; 
 
import android.view.SurfaceHolder; 
 
import android.view.SurfaceView; 
 
import android.view.View; 
 
import android.view.animation.AccelerateDecelerateInterpolator; 
 
import android.widget.Toast; 
 

 
import com.dd.CircularProgressButton; 
 

 
import java.io.IOException; 
 

 

 
public class FlashLightActivity extends Activity implements SurfaceHolder.Callback { 
 

 
    private boolean isLigtOn = false; 
 

 
    private Camera camera; 
 

 
    @Override 
 
    protected void onStart(){ 
 
     super.onStart(); 
 

 
     SurfaceView preview = (SurfaceView)findViewById(R.id.PREVIEW); 
 
      SurfaceHolder mHolder = preview.getHolder(); 
 
     mHolder.addCallback(this); 
 
    } 
 

 
    @Override 
 
    protected void onStop(){ 
 
     super.onStop(); 
 

 
     if(camera!=null){ 
 
      camera.release(); 
 
     } 
 
    } 
 
    @Override 
 
    protected void onCreate(Bundle savedInstanceState) { 
 
     super.onCreate(savedInstanceState); 
 
     setContentView(R.layout.activity_flash_light); 
 

 
     Context context = this; 
 
     PackageManager pm = context.getPackageManager(); 
 

 
     if (!pm.hasSystemFeature(PackageManager.FEATURE_CAMERA)) { 
 
      Toast.makeText(FlashLightActivity.this, "Your Device is not supported", Toast.LENGTH_SHORT).show(); 
 
      Log.e("err", "Device is not supported"); 
 
      return; 
 
     } 
 

 
     camera = Camera.open(); 
 
     final Camera.Parameters p = camera.getParameters(); 
 

 

 
     final CircularProgressButton circularButton1 = (CircularProgressButton) findViewById(R.id.btnWithText); 
 
     circularButton1.setIndeterminateProgressMode(true); 
 
     circularButton1.setOnClickListener(new View.OnClickListener() { 
 
      @Override 
 
      public void onClick(View v) { 
 
       if (isLigtOn) { 
 
        turnOffFlash(p); 
 
        Toast.makeText(FlashLightActivity.this, "Lights Off!", Toast.LENGTH_SHORT).show(); 
 

 
       } else { 
 
        turnOnFlash(p); 
 
        Toast.makeText(FlashLightActivity.this, "Lights On!", Toast.LENGTH_SHORT).show(); 
 

 
       } 
 

 
       if (circularButton1.getProgress() == 0) { 
 
        simulateSuccessProgress(circularButton1); 
 
       } else { 
 
        circularButton1.setProgress(0); 
 
       } 
 
      } 
 
     }); 
 
    } 
 

 
    private void turnOnFlash(Camera.Parameters p){ 
 
     p.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH); 
 

 
     camera.setParameters(p); 
 
     camera.startPreview(); 
 
     isLigtOn = true; 
 
    } 
 
    private void turnOffFlash(Camera.Parameters p){ 
 
     p.setFlashMode(Camera.Parameters.FLASH_MODE_OFF); 
 
     camera.setParameters(p); 
 
     camera.stopPreview(); 
 
     isLigtOn = false; 
 
    } 
 
    @Override 
 
    public void surfaceChanged(SurfaceHolder holder,int format,int width,int height){ 
 

 
    } 
 
    @Override 
 
    public void surfaceCreated(SurfaceHolder holder){ 
 
     try{ 
 
      Log.i("SurfaceHolder","Setting preview"); 
 
      camera.setPreviewDisplay(holder); 
 
     } catch (IOException e){ 
 
      e.printStackTrace(); 
 
     } 
 
    } 
 

 
    @Override 
 
    public void surfaceDestroyed(SurfaceHolder holder){ 
 
     Log.i("SurfaceHOlder", "stopping preview"); 
 
     camera.stopPreview(); 
 
     holder = null; 
 
    } 
 

 
    private void simulateSuccessProgress(final CircularProgressButton button) { 
 
     ValueAnimator widthAnimation = ValueAnimator.ofInt(1, 100); 
 
     widthAnimation.setDuration(1500); 
 
     widthAnimation.setInterpolator(new AccelerateDecelerateInterpolator()); 
 
     widthAnimation.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
 
      @Override 
 
      public void onAnimationUpdate(ValueAnimator animation) { 
 
       Integer value = (Integer) animation.getAnimatedValue(); 
 
       button.setProgress(value); 
 
      } 
 
     }); 
 
     widthAnimation.start(); 
 
    } 
 

 
    private void simulateErrorProgress(final CircularProgressButton button) { 
 
     ValueAnimator widthAnimation = ValueAnimator.ofInt(1, 99); 
 
     widthAnimation.setDuration(1500); 
 
     widthAnimation.setInterpolator(new AccelerateDecelerateInterpolator()); 
 
     widthAnimation.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
 
      @Override 
 
      public void onAnimationUpdate(ValueAnimator animation) { 
 
       Integer value = (Integer) animation.getAnimatedValue(); 
 
       button.setProgress(value); 
 
       if (value == 99) { 
 
        button.setProgress(-1); 
 
       } 
 
      } 
 
     }); 
 
     widthAnimation.start(); 
 
    } 
 

 

 
}

05-22 03:08:35.646 13909-13909/com.example.gkvxm.materiallight E/AndroidRuntime﹕ FATAL EXCEPTION: main 
Process: com.example.gkvxm.materiallight, PID: 13909 
java.lang.RuntimeException: Camera is being used after Camera.release() was called 
     at android.hardware.Camera._stopPreview(Native Method) 
     at android.hardware.Camera.stopPreview(Camera.java:732) 
     at com.example.gkvxm.materiallight.FlashLightActivity.surfaceDestroyed(FlashLightActivity.java:129) 
     at android.view.SurfaceView.updateWindow(SurfaceView.java:564) 
     at android.view.SurfaceView.onWindowVisibilityChanged(SurfaceView.java:238) 
     at android.view.View.dispatchWindowVisibilityChanged(View.java:8785) 
     at android.view.ViewGroup.dispatchWindowVisibilityChanged(ViewGroup.java:1164) 
     at android.view.ViewGroup.dispatchWindowVisibilityChanged(ViewGroup.java:1164) 
     at android.view.ViewGroup.dispatchWindowVisibilityChanged(ViewGroup.java:1164) 
     at android.view.ViewGroup.dispatchWindowVisibilityChanged(ViewGroup.java:1164) 
     at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1318) 
     at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1061) 
     at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:5885) 
     at android.view.Choreographer$CallbackRecord.run(Choreographer.java:767) 
     at android.view.Choreographer.doCallbacks(Choreographer.java:580) 
     at android.view.Choreographer.doFrame(Choreographer.java:550) 
     at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:753) 
     at android.os.Handler.handleCallback(Handler.java:739) 
     at android.os.Handler.dispatchMessage(Handler.java:95) 
     at android.os.Looper.loop(Looper.java:135) 
     at android.app.ActivityThread.main(ActivityThread.java:5254) 
     at java.lang.reflect.Method.invoke(Native Method) 
     at java.lang.reflect.Method.invoke(Method.java:372) 
     at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:903) 
     at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:698) 
+0

overrite on Pause() и onResume(). Это может вам помочь. – akshay

+0

Возможно, из-за того, что вы снимаете камеру на OnStop и пытаетесь использовать камеру после этого в методе onResume. Добавьте/откройте камеру в методе onResume. – Shvet

+0

У меня также была такая же проблема, я исправил ее, используя [http://stackoverflow.com/a/34064944/4531507](http://stackoverflow.com/a/34064944/4531507) –

ответ

1

камера используется после Camera.release() называется. Итак, глядя на жизненный цикл деятельности, вам нужно открыть камеру в onStart() или в onRestart(). Так что, возможно, этот код будет работать нормально ...

package com.example.gkvxm.materiallight; 

    import android.animation.ValueAnimator; 
    import android.app.Activity; 
    import android.content.Context; 
    import android.content.pm.PackageManager; 
    import android.hardware.Camera; 
    import android.os.Bundle; 
    import android.util.Log; 
    import android.view.KeyEvent; 
    import android.view.SurfaceHolder; 
    import android.view.SurfaceView; 
    import android.view.View; 
    import android.view.animation.AccelerateDecelerateInterpolator; 
    import android.widget.Toast; 

    import com.dd.CircularProgressButton; 

    import java.io.IOException; 


    public class FlashLightActivity extends Activity implements SurfaceHolder.Callback { 

     private boolean isLigtOn = false; 

     private Camera camera; 

     @Override 
     protected void onStart(){ 
      super.onStart(); 
      camera = Camera.open(); 
     final Camera.Parameters p = camera.getParameters(); 
      SurfaceView preview = (SurfaceView)findViewById(R.id.PREVIEW); 
       SurfaceHolder mHolder = preview.getHolder(); 
      mHolder.addCallback(this); 
     } 

     @Override 
     protected void onStop(){ 
      super.onStop(); 

      if(camera!=null){ 
       camera.release(); 
      } 
     } 
     @Override 
     protected void onCreate(Bundle savedInstanceState) { 
      super.onCreate(savedInstanceState); 
      setContentView(R.layout.activity_flash_light); 

      Context context = this; 
      PackageManager pm = context.getPackageManager(); 

      if (!pm.hasSystemFeature(PackageManager.FEATURE_CAMERA)) { 
       Toast.makeText(FlashLightActivity.this, "Your Device is not supported", Toast.LENGTH_SHORT).show(); 
       Log.e("err", "Device is not supported"); 
       return; 
      } 

      camera = Camera.open(); 
      final Camera.Parameters p = camera.getParameters(); 


      final CircularProgressButton circularButton1 = (CircularProgressButton) findViewById(R.id.btnWithText); 
      circularButton1.setIndeterminateProgressMode(true); 
      circularButton1.setOnClickListener(new View.OnClickListener() { 
       @Override 
       public void onClick(View v) { 
        if (isLigtOn) { 
         turnOffFlash(p); 
         Toast.makeText(FlashLightActivity.this, "Lights Off!", Toast.LENGTH_SHORT).show(); 

        } else { 
         turnOnFlash(p); 
         Toast.makeText(FlashLightActivity.this, "Lights On!", Toast.LENGTH_SHORT).show(); 

        } 

        if (circularButton1.getProgress() == 0) { 
         simulateSuccessProgress(circularButton1); 
        } else { 
         circularButton1.setProgress(0); 
        } 
       } 
      }); 
     } 

     private void turnOnFlash(Camera.Parameters p){ 
      p.setFlashMode(Camera.Parameters.FLASH_MODE_TORCH); 

      camera.setParameters(p); 
      camera.startPreview(); 
      isLigtOn = true; 
     } 
     private void turnOffFlash(Camera.Parameters p){ 
      p.setFlashMode(Camera.Parameters.FLASH_MODE_OFF); 
      camera.setParameters(p); 
      camera.stopPreview(); 
      isLigtOn = false; 
     } 
     @Override 
     public void surfaceChanged(SurfaceHolder holder,int format,int width,int height){ 

     } 
     @Override 
     public void surfaceCreated(SurfaceHolder holder){ 
      try{ 
       Log.i("SurfaceHolder","Setting preview"); 
       camera.setPreviewDisplay(holder); 
      } catch (IOException e){ 
       e.printStackTrace(); 
      } 
     } 

     @Override 
     public void surfaceDestroyed(SurfaceHolder holder){ 
      Log.i("SurfaceHOlder", "stopping preview"); 
      camera.stopPreview(); 
      holder = null; 
     } 

     private void simulateSuccessProgress(final CircularProgressButton button) { 
      ValueAnimator widthAnimation = ValueAnimator.ofInt(1, 100); 
      widthAnimation.setDuration(1500); 
      widthAnimation.setInterpolator(new AccelerateDecelerateInterpolator()); 
      widthAnimation.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
       @Override 
       public void onAnimationUpdate(ValueAnimator animation) { 
        Integer value = (Integer) animation.getAnimatedValue(); 
        button.setProgress(value); 
       } 
      }); 
      widthAnimation.start(); 
     } 

     private void simulateErrorProgress(final CircularProgressButton button) { 
      ValueAnimator widthAnimation = ValueAnimator.ofInt(1, 99); 
      widthAnimation.setDuration(1500); 
      widthAnimation.setInterpolator(new AccelerateDecelerateInterpolator()); 
      widthAnimation.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() { 
       @Override 
       public void onAnimationUpdate(ValueAnimator animation) { 
        Integer value = (Integer) animation.getAnimatedValue(); 
        button.setProgress(value); 
        if (value == 99) { 
         button.setProgress(-1); 
        } 
       } 
      }); 
      widthAnimation.start(); 
     } 


    } 
1

В журнале говорит Camera is being used after Camera.release() was called. Так, глядя на activity lifecycle вам необходимо открыть камеру в onStart() или onRestart()

1

Это исключение из camera.release(); вызывается в onStop() методе вашей деятельности. После освобождения экземпляра камеры вы повторно используете выпущенный экземпляр.

camera = Camera.open(); 

движения выше линии от OnCreate() до onStart()

1

Вы освобождаетесь экземпляром камеры в OnPause(), который является правильным благодаря документации:

общественность окончательного недействительный выпуск()

Добавлено в уровень API 1 Отключает и освобождает объект камеры ресурсов.

Вы должны называть это, как только вы закончите с объектом Camera.

Но вы также должны повторно открыть его в onResume(), как и в onCreate, поскольку onCreate() не всегда вызывается при возобновлении приложения.

Как они утверждают here:

Важно: отбой вызова(), чтобы освободить камеру для использования другими приложений. Приложения должны немедленно отпустить камеру в onPause() (и снова открыть() в onResume()).

См. this для получения дополнительной информации о жизненном цикле приложений Android.

Удачи вам!

1

Возможно, вы являетесь camera.release(); по адресу onStop(). И когда surfaceDestroyed вызова вы использовали camera.stopPreview();

так camera является release и настроек уже вы собираетесь stopePreview. таким образом вы получаете Camera is being used after Camera.release() was called эту ошибку.

так что вам нужно это сделать.

@Override 
protected void onStop(){ 
    super.onStop(); 
} 

и surfaceDestroyed

@Override 
public void surfaceDestroyed(SurfaceHolder holder){ 
    Log.i("SurfaceHOlder", "stopping preview"); 
    camera.stopPreview(); 
    camera.release(); 
    holder = null; 
} 
0

У меня такая же проблема с камерой класс. Используйте эту линию onResume()

mCameraPreview.getHolder().removeCallback(mCameraPreview); 

и его работа сейчас.