2 * Copyright © 2016 Keith Packard <keithp@keithp.com>
4 * This program is free software; you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation; version 2 of the License.
8 * This program is distributed in the hope that it will be useful, but
9 * WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
11 * General Public License for more details.
13 * You should have received a copy of the GNU General Public License along
14 * with this program; if not, write to the Free Software Foundation, Inc.,
15 * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.
18 package org.altusmetrum.AltosDroid;
20 import java.lang.ref.WeakReference;
22 import org.altusmetrum.AltosDroid.R;
24 import android.app.Activity;
25 import android.bluetooth.BluetoothAdapter;
26 import android.bluetooth.BluetoothDevice;
27 import android.content.*;
28 import android.graphics.*;
30 import android.view.*;
31 import android.view.View.*;
32 import android.widget.*;
33 import android.widget.AdapterView.*;
35 import org.altusmetrum.altoslib_10.*;
40 public LinearLayout igniter_view = null;
41 public TextView name_view = null;
42 public TextView status_view = null;
44 private void update() {
45 AltosDebug.debug("update item %s %s", name, status);
46 if (name_view != null)
47 name_view.setText(name);
48 if (status_view != null)
49 status_view.setText(status);
52 public void set(String name, String status) {
53 if (!name.equals(this.name) || !status.equals(this.status)) {
60 public void realize(LinearLayout igniter_view,
62 TextView status_view) {
63 if (igniter_view != this.igniter_view ||
64 name_view != this.name_view ||
65 status_view != this.status_view)
67 this.igniter_view = igniter_view;
68 this.name_view = name_view;
69 this.status_view = status_view;
74 public IgniterItem() {
75 AltosDebug.debug("New igniter item");
79 class IgniterAdapter extends ArrayAdapter<IgniterItem> {
81 int selected_item = -1;
83 public IgniterAdapter(Context context, int in_resource) {
84 super(context, in_resource);
85 resource = in_resource;
89 public View getView(int position, View convertView, ViewGroup parent) {
90 IgniterItem item = getItem(position);
91 if (item.igniter_view == null) {
92 LinearLayout igniter_view = new LinearLayout(getContext());
93 String inflater = Context.LAYOUT_INFLATER_SERVICE;
94 LayoutInflater li = (LayoutInflater) getContext().getSystemService(inflater);
95 li.inflate(resource, igniter_view, true);
97 item.realize(igniter_view,
98 (TextView) igniter_view.findViewById(R.id.igniter_name),
99 (TextView) igniter_view.findViewById(R.id.igniter_status));
100 AltosDebug.debug("Realize new igniter view");
102 AltosDebug.debug("Reuse existing igniter view");
103 if (position == selected_item)
104 item.igniter_view.setBackgroundColor(Color.RED);
106 item.igniter_view.setBackgroundColor(Color.BLACK);
107 return item.igniter_view;
111 public class IgniterActivity extends Activity {
112 private ListView igniters_view;
113 private ToggleButton arm;
116 private HashMap<String,IgniterItem> igniters = new HashMap<String,IgniterItem>();;
118 private IgniterAdapter igniters_adapter;
120 private boolean is_bound;
121 private boolean timer_running;
122 private Messenger service = null;
123 private final Messenger messenger = new Messenger(new IncomingHandler(this));
127 public static final int IGNITER_QUERY = 1;
128 public static final int IGNITER_FIRE = 2;
130 // The Handler that gets information back from the Telemetry Service
131 static class IncomingHandler extends Handler {
132 private final WeakReference<IgniterActivity> igniter_activity;
133 IncomingHandler(IgniterActivity ia) { igniter_activity = new WeakReference<IgniterActivity>(ia); }
136 public void handleMessage(Message msg) {
137 IgniterActivity ia = igniter_activity.get();
140 case AltosDroid.MSG_IGNITER_STATUS:
141 ia.igniter_status((HashMap <String,Integer>) msg.obj);
148 private ServiceConnection connection = new ServiceConnection() {
149 public void onServiceConnected(ComponentName className, IBinder binder) {
150 service = new Messenger(binder);
153 public void onServiceDisconnected(ComponentName className) {
154 // This is called when the connection with the service has been unexpectedly disconnected - process crashed.
159 void doBindService() {
160 bindService(new Intent(this, TelemetryService.class), connection, Context.BIND_AUTO_CREATE);
164 void doUnbindService() {
166 // If we have received the service, and hence registered with it, then now is the time to unregister.
167 unbindService(connection);
172 private void done() {
173 Intent intent = new Intent();
174 setResult(Activity.RESULT_OK, intent);
178 private void fire_igniter() {
181 private void arm_igniter(boolean is_checked) {
184 private synchronized void timer_tick() {
187 timer_running = true;
189 Message msg = Message.obtain(null, TelemetryService.MSG_IGNITER_QUERY);
190 msg.replyTo = messenger;
192 } catch (RemoteException re) {
196 private boolean set_igniter(HashMap <String,Integer> status, String name, String pretty) {
197 if (!status.containsKey(name))
201 if (!igniters.containsKey(name)) {
202 item = new IgniterItem();
203 igniters.put(name, item);
204 igniters_adapter.add(item);
206 item = igniters.get(name);
208 item.set(pretty, AltosIgnite.status_string(status.get(name)));
212 private synchronized void igniter_status(HashMap <String,Integer> status) {
213 timer_running = false;
214 if (status == null) {
215 AltosDebug.debug("no igniter status");
218 set_igniter(status, "drogue", "Apogee");
219 set_igniter(status, "main", "Main");
220 for (int extra = 0;; extra++) {
221 String name = String.format("%d", extra);
222 String pretty = String.format("%c", 'A' + extra);
223 if (!set_igniter(status, name, pretty))
226 // if (igniters_adapter.selected_item >= 0)
227 // igniters_view.setSelection(selected_item);
230 private class IgniterItemClickListener implements ListView.OnItemClickListener {
232 public void onItemClick(AdapterView<?> av, View v, int position, long id) {
233 if (igniters_adapter.selected_item >= 0)
234 igniters_view.setItemChecked(igniters_adapter.selected_item, false);
235 igniters_view.setItemChecked(position, true);
236 igniters_adapter.selected_item = position;
241 protected void onCreate(Bundle savedInstanceState) {
242 super.onCreate(savedInstanceState);
245 requestWindowFeature(Window.FEATURE_INDETERMINATE_PROGRESS);
246 setContentView(R.layout.igniters);
248 igniters_view = (ListView) findViewById(R.id.igniters);
249 igniters_view.setClickable(true);
251 igniters_adapter = new IgniterAdapter(this, R.layout.igniter_status);
253 igniters_view.setAdapter(igniters_adapter);
254 igniters_view.setOnItemClickListener(new IgniterItemClickListener());
256 fire = (Button) findViewById(R.id.igniter_fire);
257 fire.setOnClickListener(new OnClickListener() {
258 public void onClick(View v) {
263 arm = (ToggleButton) findViewById(R.id.igniter_arm);
264 arm.setOnCheckedChangeListener(new ToggleButton.OnCheckedChangeListener() {
265 public void onCheckedChanged(CompoundButton v, boolean is_checked) {
266 arm_igniter(is_checked);
270 // Set result CANCELED incase the user backs out
271 setResult(Activity.RESULT_CANCELED);
275 protected void onStart() {
281 protected void onResume() {
283 timer = new Timer(true);
284 timer.scheduleAtFixedRate(new TimerTask() {
292 protected void onPause() {
299 protected void onStop() {