One more time -- rationalize log levels, mostly downward, and pull out 1-2 more state...
[zxing.git] / android / src / com / google / zxing / client / android / CaptureActivityHandler.java
1 /*
2  * Copyright (C) 2008 ZXing authors
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 package com.google.zxing.client.android;
18
19 import com.google.zxing.BarcodeFormat;
20 import com.google.zxing.Result;
21 import com.google.zxing.client.android.camera.CameraManager;
22
23 import android.app.Activity;
24 import android.content.Intent;
25 import android.graphics.Bitmap;
26 import android.net.Uri;
27 import android.os.Bundle;
28 import android.os.Handler;
29 import android.os.Message;
30 import android.util.Log;
31
32 import java.util.Vector;
33
34 /**
35  * This class handles all the messaging which comprises the state machine for capture.
36  *
37  * @author dswitkin@google.com (Daniel Switkin)
38  */
39 public final class CaptureActivityHandler extends Handler {
40
41   private static final String TAG = CaptureActivityHandler.class.getSimpleName();
42
43   private final CaptureActivity activity;
44   private final DecodeThread decodeThread;
45   private State state;
46
47   private enum State {
48     PREVIEW,
49     SUCCESS,
50     DONE
51   }
52
53   CaptureActivityHandler(CaptureActivity activity,
54                          Vector<BarcodeFormat> decodeFormats,
55                          String characterSet,
56                          boolean beginScanning) {
57     this.activity = activity;
58     decodeThread = new DecodeThread(activity, decodeFormats, characterSet,
59         new ViewfinderResultPointCallback(activity.getViewfinderView()));
60     decodeThread.start();
61     state = State.SUCCESS;
62
63     // Start ourselves capturing previews and decoding.
64     CameraManager.get().startPreview();
65     if (beginScanning) {
66       restartPreviewAndDecode();
67     }
68   }
69
70   @Override
71   public void handleMessage(Message message) {
72     switch (message.what) {
73       case R.id.auto_focus:
74         //Log.d(TAG, "Got auto-focus message");
75         // When one auto focus pass finishes, start another. This is the closest thing to
76         // continuous AF. It does seem to hunt a bit, but I'm not sure what else to do.
77         if (state == State.PREVIEW) {
78           CameraManager.get().requestAutoFocus(this, R.id.auto_focus);
79         }
80         break;
81       case R.id.restart_preview:
82         Log.d(TAG, "Got restart preview message");
83         restartPreviewAndDecode();
84         break;
85       case R.id.decode_succeeded:
86         Log.d(TAG, "Got decode succeeded message");
87         state = State.SUCCESS;
88         Bundle bundle = message.getData();
89         Bitmap barcode = bundle == null ? null : (Bitmap) bundle.getParcelable(DecodeThread.BARCODE_BITMAP);
90         activity.handleDecode((Result) message.obj, barcode);
91         break;
92       case R.id.decode_failed:
93         // We're decoding as fast as possible, so when one decode fails, start another.
94         state = State.PREVIEW;
95         CameraManager.get().requestPreviewFrame(decodeThread.getHandler(), R.id.decode);
96         break;
97       case R.id.return_scan_result:
98         Log.d(TAG, "Got return scan result message");
99         activity.setResult(Activity.RESULT_OK, (Intent) message.obj);
100         activity.finish();
101         break;
102       case R.id.launch_product_query:
103         Log.d(TAG, "Got product query message");
104         String url = (String) message.obj;
105         Intent intent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
106         intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET);        
107         activity.startActivity(intent);
108         break;
109     }
110   }
111
112   public void quitSynchronously() {
113     state = State.DONE;
114     CameraManager.get().stopPreview();
115     Message quit = Message.obtain(decodeThread.getHandler(), R.id.quit);
116     quit.sendToTarget();
117     try {
118       decodeThread.join();
119     } catch (InterruptedException e) {
120     }
121
122     // Be absolutely sure we don't send any queued up messages
123     removeMessages(R.id.decode_succeeded);
124     removeMessages(R.id.decode_failed);
125   }
126
127   private void restartPreviewAndDecode() {
128     if (state == State.SUCCESS) {
129       state = State.PREVIEW;
130       CameraManager.get().requestPreviewFrame(decodeThread.getHandler(), R.id.decode);
131       CameraManager.get().requestAutoFocus(this, R.id.auto_focus);
132       activity.drawViewfinder();
133     }
134   }
135
136 }