diff options
21 files changed, 2287 insertions, 475 deletions
| diff --git a/altosdroid/.classpath b/altosdroid/.classpath index 0ca188f9..fce248e6 100644 --- a/altosdroid/.classpath +++ b/altosdroid/.classpath @@ -1,8 +1,10 @@  <?xml version="1.0" encoding="UTF-8"?>  <classpath>  	<classpathentry kind="con" path="com.android.ide.eclipse.adt.ANDROID_FRAMEWORK"/> +	<classpathentry exported="true" kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/>  	<classpathentry kind="src" path="src"/>  	<classpathentry kind="src" path="gen"/> -	<classpathentry exported="true" kind="con" path="com.android.ide.eclipse.adt.LIBRARIES"/> +	<classpathentry kind="lib" path="libs/android-support-v4.jar"/> +	<classpathentry kind="lib" path="libs/altoslib_1.jar"/>  	<classpathentry kind="output" path="bin/classes"/>  </classpath> diff --git a/altosdroid/.gitignore b/altosdroid/.gitignore index 0d2ee6e0..7f0858ea 100644 --- a/altosdroid/.gitignore +++ b/altosdroid/.gitignore @@ -2,4 +2,6 @@ local.properties  bin  gen  libs +google-play-services_lib  src/org/altusmetrum/AltosDroid/BuildInfo.java +res/drawable/*led.png diff --git a/altosdroid/AndroidManifest.xml b/altosdroid/AndroidManifest.xml index 8ecfcbb5..237c6dcf 100644 --- a/altosdroid/AndroidManifest.xml +++ b/altosdroid/AndroidManifest.xml @@ -16,18 +16,35 @@   * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.  -->  <manifest xmlns:android="http://schemas.android.com/apk/res/android" -      package="org.altusmetrum.AltosDroid" -      android:versionCode="1" -      android:versionName="1.1.9.3"> +          package="org.altusmetrum.AltosDroid" +          android:versionCode="1" +          android:versionName="1.1.9.3">      <uses-sdk android:targetSdkVersion="10" android:minSdkVersion="10"/> +    <!-- Google Maps --> +    <uses-feature android:glEsVersion="0x00020000" android:required="true"/> + +    <!-- Permissions needed to access bluetooth -->      <uses-permission android:name="android.permission.BLUETOOTH_ADMIN" />      <uses-permission android:name="android.permission.BLUETOOTH" /> +    <!-- Permissions needed to save Telemetry logs to SD card -->      <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" /> +    <!-- Permissions needed for GoogleMaps --> +    <uses-permission android:name="android.permission.INTERNET"/> +    <uses-permission android:name="com.google.android.providers.gsf.permission.READ_GSERVICES"/> +    <uses-permission android:name="android.permission.ACCESS_COARSE_LOCATION"/> +    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/> + +    <permission android:name="org.altusmetrum.AltosDroid.permission.MAPS_RECEIVE" +                android:protectionLevel="signature"/> +    <uses-permission android:name="org.altusmetrum.AltosDroid.permission.MAPS_RECEIVE"/> +      <application android:label="@string/app_name" -                 android:icon="@drawable/app_icon" > -        <activity android:label="@string/app_name" -                  android:configChanges="orientation|keyboardHidden" android:name="org.altusmetrum.AltosDroid.AltosDroid"> +                 android:icon="@drawable/app_icon" +                 android:allowBackup="true" > +        <activity android:name="org.altusmetrum.AltosDroid.AltosDroid" +                  android:label="@string/app_name" +                  android:configChanges="orientation|keyboardHidden" >              <intent-filter>                  <action android:name="android.intent.action.MAIN" />                  <category android:name="android.intent.category.LAUNCHER" /> @@ -38,9 +55,9 @@                    android:theme="@android:style/Theme.Dialog"                    android:configChanges="orientation|keyboardHidden" /> -          <service android:name=".TelemetryService" /> - +        <meta-data android:name="com.google.android.maps.v2.API_KEY" +                   android:value="AIzaSyDSr6u4i9TJmVGhgGk4g0wUUhTy9FGyn0s"/>      </application>  </manifest> diff --git a/altosdroid/Makefile.am b/altosdroid/Makefile.am index 39f3c2b6..3dbabdd7 100644 --- a/altosdroid/Makefile.am +++ b/altosdroid/Makefile.am @@ -1,12 +1,11 @@  if ANDROID -all_target=bin/AltosDroid-debug.apk bin/AltosDroid-release.apk -clean_command=ant clean +all_target=bin/AltosDroid-debug.apk bin/AltosDroid-release-unsigned.apk  else  all_target= -clean_command=echo done  endif  SDK=$(ANDROID_SDK) +SDK_TARGET=$(shell sed -ne 's/^target=//p' project.properties)  DX=$(SDK)/platform-tools/dx  ADB=$(SDK)/platform-tools/adb @@ -14,34 +13,52 @@ AAPT=$(SDK)/platform-tools/aapt  APKBUILDER=$(SDK)/tools/apkbuilder  ZIPALIGN=$(SDK)/tools/zipalign -SRC_DIR=src/org/altusmetrum/AltosDroid +JAVA_SRC_DIR=src/org/altusmetrum/AltosDroid  EXT_LIBDIR=libs +DRAWABLE_DIR=res/drawable  ALTOSLIB_SRCDIR=../altoslib  ALTOSLIB_JAR=altoslib_$(ALTOSLIB_VERSION).jar  ALTOSLIB=$(EXT_LIBDIR)/$(ALTOSLIB_JAR) -SRC=\ -	$(SRC_DIR)/AltosDroid.java \ -	$(SRC_DIR)/AltosDroidPreferences.java \ -	$(SRC_DIR)/AltosVoice.java \ -	$(SRC_DIR)/TelemetryService.java \ -	$(SRC_DIR)/TelemetryReader.java \ -	$(SRC_DIR)/TelemetryLogger.java \ -	$(SRC_DIR)/AltosBluetooth.java \ -	$(SRC_DIR)/DeviceListActivity.java \ -	$(SRC_DIR)/BuildInfo.java \ -	$(SRC_DIR)/Dumper.java +SUPPORT_V4_SRCDIR=$(SDK)/extras/android/support/v4 +SUPPORT_V4_JAR=android-support-v4.jar + +SUPPORT_V4=$(EXT_LIBDIR)/$(SUPPORT_V4_JAR) + +GOOGLE_PLAY_SERVICES_LIB_SRCDIR=$(SDK)/extras/google/google_play_services/libproject +GOOGLE_PLAY_SERVICES_LIB=google-play-services_lib + +JAVA_SRC=$(JAVA_SRC_DIR)/*.java + +DRAWABLES=\ +    $(DRAWABLE_DIR)/redled.png \ +    $(DRAWABLE_DIR)/greenled.png \ +    $(DRAWABLE_DIR)/grayled.png + +SRC=$(JAVA_SRC) $(DRAWABLES)  all: $(all_target) -$(ALTOSLIB): $(ALTOSLIB_SRCDIR)/$(ALTOSLIB_JAR) +$(EXT_LIBDIR):  	mkdir -p $(EXT_LIBDIR) -	cd $(EXT_LIBDIR) && ln -s $(shell echo $(EXT_LIBDIR) | sed 's|[^/]\+|..|g')/$(ALTOSLIB_SRCDIR)/$(ALTOSLIB_JAR) . -$(SRC_DIR)/BuildInfo.java: +$(ALTOSLIB): $(EXT_LIBDIR) $(ALTOSLIB_SRCDIR)/$(ALTOSLIB_JAR) +	cd $(EXT_LIBDIR) && ln -sf $(shell echo $(EXT_LIBDIR) | sed 's|[^/]\+|..|g')/$(ALTOSLIB_SRCDIR)/$(ALTOSLIB_JAR) . + +$(SUPPORT_V4): $(EXT_LIBDIR) $(SUPPORT_V4_SRCDIR)/$(SUPPORT_V4_JAR) +	cd $(EXT_LIBDIR) && ln -sf $(SUPPORT_V4_SRCDIR)/$(SUPPORT_V4_JAR) . + +$(GOOGLE_PLAY_SERVICES_LIB): $(GOOGLE_PLAY_SERVICES_LIB_SRCDIR)/$(GOOGLE_PLAY_SERVICES_LIB) +	cp -a $(GOOGLE_PLAY_SERVICES_LIB_SRCDIR)/$(GOOGLE_PLAY_SERVICES_LIB) . +	cd $(GOOGLE_PLAY_SERVICES_LIB) && $(SDK)/tools/android update project --target $(SDK_TARGET) --path . + +$(JAVA_SRC_DIR)/BuildInfo.java: $(JAVA_SRC)  	./buildinfo.sh +$(DRAWABLE_DIR)/%.png: ../icon/%.png +	cd $(DRAWABLE_DIR) && ln -sf $(shell echo $(DRAWABLE_DIR) | sed 's|[^/]\+|..|g')/$< . +  if ANDROID  install-release: bin/AltosDroid-release.apk  	$(ADB) install -r bin/AltosDroid-release.apk @@ -49,26 +66,29 @@ install-release: bin/AltosDroid-release.apk  install-debug: bin/AltosDroid-debug.apk  	$(ADB) install -r bin/AltosDroid-debug.apk -bin/AltosDroid-debug.apk: $(SRC) $(ALTOSLIB) +bin/AltosDroid-debug.apk: $(SRC) $(ALTOSLIB) $(SUPPORT_V4) $(GOOGLE_PLAY_SERVICES_LIB)  	ant debug -bin/AltosDroid-release.apk: $(SRC) $(ALTOSLIB) +bin/AltosDroid-release-unsigned.apk: $(SRC) $(ALTOSLIB) $(SUPPORT_V4) $(GOOGLE_PLAY_SERVICES_LIB)  	ant release -sign: +release: bin/AltosDroid-release-unsigned.apk  	jarsigner -keystore release.keystore \  	   -signedjar bin/AltosDroid-release-signed.apk \  	   bin/AltosDroid-release-unsigned.apk AltosDroid -	$(SDK)/tools/zipalign -f 4 \ +	$(ZIPALIGN) -f 4 \  	   bin/AltosDroid-release-signed.apk \  	   bin/AltosDroid-release.apk -endif +clean: $(GOOGLE_PLAY_SERVICES_LIB) +	ant clean +	rm -rf $(EXT_LIBDIR) +	rm -f $(DRAWABLES) +	rm -rf $(GOOGLE_PLAY_SERVICES_LIB) -clean: clean-local -	$(clean_command) +else -clean-local: -	rm -rf $(EXT_LIBDIR) +clean: + +endif -.PHONY: $(SRC_DIR)/BuildInfo.java diff --git a/altosdroid/project.properties b/altosdroid/project.properties index 0a80e644..96b9551c 100644 --- a/altosdroid/project.properties +++ b/altosdroid/project.properties @@ -8,4 +8,5 @@  # project structure.  # Project target. -target=Google Inc.:Google APIs:10 +target=android-10 +android.library.reference.1=google-play-services_lib/ diff --git a/altosdroid/res/layout/altosdroid.xml b/altosdroid/res/layout/altosdroid.xml index 691c5e04..ce812414 100644 --- a/altosdroid/res/layout/altosdroid.xml +++ b/altosdroid/res/layout/altosdroid.xml @@ -1,364 +1,196 @@  <?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2009 The Android Open Source Project +<!-- +	 Copyright © 2012-2013 Mike Beattie <mike@ethernal.org> -     Licensed under the Apache License, Version 2.0 (the "License"); -     you may not use this file except in compliance with the License. -     You may obtain a copy of the License at +	 This program is free software; you can redistribute it and/or modify +	 it under the terms of the GNU General Public License as published by +	 the Free Software Foundation; version 2 of the License. -          http://www.apache.org/licenses/LICENSE-2.0 +	 This program is distributed in the hope that it will be useful, but +	 WITHOUT ANY WARRANTY; without even the implied warranty of +	 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +	 General Public License for more details. -     Unless required by applicable law or agreed to in writing, software -     distributed under the License is distributed on an "AS IS" BASIS, -     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -     See the License for the specific language governing permissions and -     limitations under the License. +	 You should have received a copy of the GNU General Public License along +	 with this program; if not, write to the Free Software Foundation, Inc., +	 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.  --> -    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" -        android:layout_width="fill_parent" -        android:layout_height="wrap_content" -        android:layout_weight="0" > - -        <RelativeLayout -            android:id="@+id/strut" -            android:layout_width="10dip" -            android:layout_height="wrap_content" -            android:layout_centerHorizontal="true" > - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/callsign_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentLeft="true" -            android:layout_toLeftOf="@+id/strut" > - -            <TextView -                android:id="@+id/callsign_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/callsign_label" /> - -            <TextView -                android:id="@+id/callsign_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@id/callsign_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/rssi_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_toRightOf="@id/strut" -            android:layout_alignParentRight="true" > - -            <TextView -                android:id="@+id/rssi_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/rssi_label" /> - -            <TextView -                android:id="@+id/rssi_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/rssi_label" -                android:textAppearance="?android:attr/textAppearanceLarge" /> -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/serial_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_below="@+id/callsign_container" -            android:layout_toLeftOf="@+id/strut" > - -            <TextView -                android:id="@+id/serial_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/serial_label" /> - -            <TextView -                android:id="@+id/serial_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/serial_label" -                android:textAppearance="?android:attr/textAppearanceLarge" /> -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/flight_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_below="@+id/callsign_container" -            android:layout_toRightOf="@+id/strut" -            android:layout_alignParentRight="true" > - -            <TextView -                android:id="@+id/flight_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/flight_label" /> - -            <TextView -                android:id="@+id/flight_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/flight_label" -                android:textAppearance="?android:attr/textAppearanceLarge" /> -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/state_container" -            android:layout_width="fill_parent" -            android:layout_height="wrap_content" -            android:layout_below="@+id/serial_container" > - -            <TextView -                android:id="@+id/state_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/state_label" /> - -            <TextView -                android:id="@+id/state_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_below="@+id/state_label" -                android:layout_centerInParent="true" -                android:textAppearance="?android:attr/textAppearanceLarge" -                android:textSize="50dip" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/speed_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentLeft="true" -            android:layout_below="@+id/state_container" -            android:layout_toLeftOf="@+id/strut" > - -            <TextView -                android:id="@+id/speed_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/speed_label" /> - -            <TextView -                android:id="@+id/speed_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@id/speed_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/accel_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentRight="true" -            android:layout_below="@+id/state_container" -            android:layout_toRightOf="@+id/strut" > - -            <TextView -                android:id="@+id/accel_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/accel_label" /> - -            <TextView -                android:id="@+id/accel_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/accel_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/range_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentLeft="true" -            android:layout_below="@+id/speed_container" -            android:layout_toLeftOf="@+id/strut" > - -            <TextView -                android:id="@+id/range_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/range_label" /> - -            <TextView -                android:id="@+id/range_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/range_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/height_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentRight="true" -            android:layout_below="@id/speed_container" -            android:layout_toRightOf="@id/strut" > - -            <TextView -                android:id="@+id/height_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/height_label" /> - -            <TextView -                android:id="@+id/height_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/height_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/elevation_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentLeft="true" -            android:layout_below="@id/range_container" -            android:layout_toLeftOf="@id/strut" > - -            <TextView -                android:id="@+id/elevation_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/elevation_label" /> - -            <TextView -                android:id="@+id/elevation_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/elevation_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/bearing_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_alignParentRight="true" -            android:layout_below="@+id/range_container" -            android:layout_toRightOf="@+id/strut" > - -            <TextView -                android:id="@+id/bearing_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/bearing_label" /> - -            <TextView -                android:id="@+id/bearing_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/bearing_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/latitude_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_below="@+id/elevation_container" > - -            <TextView -                android:id="@+id/latitude_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/latitude_label" /> - -            <TextView -                android:id="@+id/latitude_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/latitude_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - -        <RelativeLayout -            android:id="@+id/longitude_container" -            android:layout_width="wrap_content" -            android:layout_height="wrap_content" -            android:layout_below="@id/latitude_container" > - -            <TextView -                android:id="@+id/longitude_label" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:text="@string/longitude_label" /> - -            <TextView -                android:id="@+id/longitude_value" -                android:layout_width="wrap_content" -                android:layout_height="wrap_content" -                android:layout_alignParentRight="true" -                android:layout_below="@+id/longitude_label" -                android:text="" -                android:textAppearance="?android:attr/textAppearanceLarge" /> - -        </RelativeLayout> - - -        <RelativeLayout -            android:id="@+id/text_container" -            android:layout_width="wrap_content" -            android:layout_height="fill_parent" -            android:layout_below="@id/longitude_container" > - -        	<TextView -        	    android:id="@+id/text" -        	    android:layout_width="fill_parent" -        	    android:layout_height="fill_parent" -        	    android:layout_above="@+id/version" -        	    android:scrollbars="vertical" -        	    android:textSize="7dp" -        	    android:typeface="monospace" /> -         -            <TextView -                android:id="@+id/version" -                android:layout_width="fill_parent" -                android:layout_height="10dip" -                android:layout_alignParentBottom="true" -                android:gravity="bottom|right" -                android:textSize="7dp" -                android:typeface="monospace" /> - -        </RelativeLayout> - -    </RelativeLayout> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" +	android:layout_width="fill_parent" +	android:layout_height="wrap_content" +	android:layout_weight="0" +	android:orientation="vertical" > + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" > + +		<RelativeLayout +			android:id="@+id/callsign_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/callsign_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/callsign_label" /> + +			<TextView +				android:id="@+id/callsign_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/callsign_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:id="@+id/serial_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/serial_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/serial_label" /> + +			<TextView +				android:id="@+id/serial_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/serial_label" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:id="@+id/flight_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/flight_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/flight_label" /> + +			<TextView +				android:id="@+id/flight_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/flight_label" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:id="@+id/state_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/state_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/state_label" /> + +			<TextView +				android:id="@+id/state_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/state_label" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:id="@+id/rssi_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/rssi_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/rssi_label" /> + +			<TextView +				android:id="@+id/rssi_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/rssi_label" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:id="@+id/age_container" +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/age_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/age_label" /> + +			<TextView +				android:id="@+id/age_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_below="@+id/age_label" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> +	</LinearLayout> + +	<TabHost +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:id="@android:id/tabhost" +		android:layout_width="fill_parent" +		android:layout_height="0dp" +		android:layout_weight="1" > + +		<LinearLayout +			android:layout_width="match_parent" +			android:layout_height="match_parent" +			android:orientation="vertical" > + +			<TabWidget +				android:id="@android:id/tabs" +				android:layout_width="match_parent" +				android:layout_height="wrap_content" +				android:layout_weight="0" +				android:orientation="horizontal" /> + +			<FrameLayout +				android:id="@android:id/tabcontent" +				android:layout_width="0dp" +				android:layout_height="0dp" +				android:layout_weight="0" /> + +			<android.support.v4.view.ViewPager +				android:id="@+id/pager" +				android:layout_width="match_parent" +				android:layout_height="0dp" +				android:layout_weight="1" /> +		</LinearLayout> +	</TabHost> + +	<TextView +		android:id="@+id/version" +		android:layout_width="fill_parent" +		android:layout_height="10dip" +		android:layout_weight="0" +		android:gravity="bottom|right" +		android:textSize="7sp" +		android:typeface="monospace" /> + +</LinearLayout> diff --git a/altosdroid/res/layout/tab_ascent.xml b/altosdroid/res/layout/tab_ascent.xml new file mode 100644 index 00000000..b7e97086 --- /dev/null +++ b/altosdroid/res/layout/tab_ascent.xml @@ -0,0 +1,299 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +     Copyright © 2013 Mike Beattie <mike@ethernal.org> + +     This program is free software; you can redistribute it and/or modify +     it under the terms of the GNU General Public License as published by +     the Free Software Foundation; version 2 of the License. + +     This program is distributed in the hope that it will be useful, but +     WITHOUT ANY WARRANTY; without even the implied warranty of +     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +     General Public License for more details. + +     You should have received a copy of the GNU General Public License along +     with this program; if not, write to the Free Software Foundation, Inc., +     59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +--> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" +	android:layout_width="fill_parent" +	android:layout_height="wrap_content" +	android:orientation="vertical" > + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/height_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/height_label" /> + +			<TextView +				android:id="@+id/height_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/height_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/max_height_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/max_height_label" /> + +			<TextView +				android:id="@+id/max_height_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/max_height_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> +	</LinearLayout> + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/speed_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/speed_label" /> + +			<TextView +				android:id="@+id/speed_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/speed_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/max_speed_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/max_speed_label" /> + +			<TextView +				android:id="@+id/max_speed_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/max_speed_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> +	</LinearLayout> + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/accel_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/accel_label" /> + +			<TextView +				android:id="@+id/accel_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/accel_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/max_accel_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/max_accel_label" /> + +			<TextView +				android:id="@+id/max_accel_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/max_accel_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> +	</LinearLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lat_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/latitude_label" /> + +		<TextView +			android:id="@+id/lat_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lat_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lon_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/longitude_label" /> + +		<TextView +			android:id="@+id/lon_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lon_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/apogee_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/apogee_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/apogee_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_redled" +			android:contentDescription="@string/apogee_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/apogee_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="@string/apogee_voltage_label" /> + +		<TextView +			android:id="@+id/apogee_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/apogee_voltage_label" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/main_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/main_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/main_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_redled" +			android:contentDescription="@string/main_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/main_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_greenled" +			android:text="@string/main_voltage_label" /> + +		<TextView +			android:id="@+id/main_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/main_voltage_label" +			android:layout_toRightOf="@id/main_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +</LinearLayout>
\ No newline at end of file diff --git a/altosdroid/res/layout/tab_descent.xml b/altosdroid/res/layout/tab_descent.xml new file mode 100644 index 00000000..4b62acf9 --- /dev/null +++ b/altosdroid/res/layout/tab_descent.xml @@ -0,0 +1,339 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +     Copyright © 2013 Mike Beattie <mike@ethernal.org> + +     This program is free software; you can redistribute it and/or modify +     it under the terms of the GNU General Public License as published by +     the Free Software Foundation; version 2 of the License. + +     This program is distributed in the hope that it will be useful, but +     WITHOUT ANY WARRANTY; without even the implied warranty of +     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +     General Public License for more details. + +     You should have received a copy of the GNU General Public License along +     with this program; if not, write to the Free Software Foundation, Inc., +     59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +--> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" +	android:layout_width="fill_parent" +	android:layout_height="wrap_content" +	android:orientation="vertical" > + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/speed_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/speed_label" /> + +			<TextView +				android:id="@+id/speed_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/speed_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/height_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/height_label" /> + +			<TextView +				android:id="@+id/height_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/height_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +	</LinearLayout> + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/elevation_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/elevation_label" /> + +			<TextView +				android:id="@+id/elevation_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/elevation_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/range_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/range_label" /> + +			<TextView +				android:id="@+id/range_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/range_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +	</LinearLayout> + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/bearing_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/bearing_label" /> + +			<TextView +				android:id="@+id/bearing_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/bearing_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/compass_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="" /> + +			<TextView +				android:id="@+id/compass_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/compass_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +	</LinearLayout> + +	<LinearLayout +		xmlns:android="http://schemas.android.com/apk/res/android" +		android:layout_width="fill_parent" +		android:layout_height="wrap_content" +		android:layout_weight="0" +		android:baselineAligned="true" +		android:orientation="horizontal" +		android:paddingTop="5dp" > + +		<RelativeLayout +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > + +			<TextView +				android:id="@+id/distance_label" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:text="@string/gnd_distance_label" /> + +			<TextView +				android:id="@+id/distance_value" +				android:layout_width="wrap_content" +				android:layout_height="wrap_content" +				android:layout_alignParentRight="true" +				android:layout_below="@id/distance_label" +				android:text="" +				android:textAppearance="?android:attr/textAppearanceLarge" /> +		</RelativeLayout> + +		<TextView +			android:layout_width="0dp" +			android:layout_height="wrap_content" +			android:layout_weight="1" > +		</TextView> + +	</LinearLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lat_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/latitude_label" /> + +		<TextView +			android:id="@+id/lat_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lat_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lon_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/longitude_label" /> + +		<TextView +			android:id="@+id/lon_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lon_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/apogee_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/apogee_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/apogee_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_redled" +			android:contentDescription="@string/apogee_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/apogee_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="@string/apogee_voltage_label" /> + +		<TextView +			android:id="@+id/apogee_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/apogee_voltage_label" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/main_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/main_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/main_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_redled" +			android:contentDescription="@string/main_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/main_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_greenled" +			android:text="@string/main_voltage_label" /> + +		<TextView +			android:id="@+id/main_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/main_voltage_label" +			android:layout_toRightOf="@id/main_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +</LinearLayout> diff --git a/altosdroid/res/layout/tab_landed.xml b/altosdroid/res/layout/tab_landed.xml new file mode 100644 index 00000000..b5c8d8c2 --- /dev/null +++ b/altosdroid/res/layout/tab_landed.xml @@ -0,0 +1,169 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +     Copyright © 2013 Mike Beattie <mike@ethernal.org> + +     This program is free software; you can redistribute it and/or modify +     it under the terms of the GNU General Public License as published by +     the Free Software Foundation; version 2 of the License. + +     This program is distributed in the hope that it will be useful, but +     WITHOUT ANY WARRANTY; without even the implied warranty of +     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +     General Public License for more details. + +     You should have received a copy of the GNU General Public License along +     with this program; if not, write to the Free Software Foundation, Inc., +     59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +--> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" +	android:layout_width="fill_parent" +	android:layout_height="wrap_content" +	android:orientation="vertical" > + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" > + +		<TextView +			android:id="@+id/bearing_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/bearing_label" /> + +		<TextView +			android:id="@+id/bearing_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@+id/bearing_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/distance_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/distance_label" /> + +		<TextView +			android:id="@+id/distance_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@+id/distance_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lat_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/latitude_label" /> + +		<TextView +			android:id="@+id/lat_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lat_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/lon_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/longitude_label" /> + +		<TextView +			android:id="@+id/lon_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/lon_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/max_height_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/max_height_label" /> + +		<TextView +			android:id="@+id/max_height_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/max_height_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/max_speed_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/max_speed_label" /> + +		<TextView +			android:id="@+id/max_speed_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/max_speed_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/max_accel_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:text="@string/max_accel_label" /> + +		<TextView +			android:id="@+id/max_accel_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_alignParentRight="true" +			android:layout_below="@id/max_accel_label" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +</LinearLayout>
\ No newline at end of file diff --git a/altosdroid/res/layout/tab_map.xml b/altosdroid/res/layout/tab_map.xml new file mode 100644 index 00000000..4737fae0 --- /dev/null +++ b/altosdroid/res/layout/tab_map.xml @@ -0,0 +1,22 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +     Copyright © 2013 Mike Beattie <mike@ethernal.org> + +     This program is free software; you can redistribute it and/or modify +     it under the terms of the GNU General Public License as published by +     the Free Software Foundation; version 2 of the License. + +     This program is distributed in the hope that it will be useful, but +     WITHOUT ANY WARRANTY; without even the implied warranty of +     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +     General Public License for more details. + +     You should have received a copy of the GNU General Public License along +     with this program; if not, write to the Free Software Foundation, Inc., +     59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +--> +<fragment xmlns:android="http://schemas.android.com/apk/res/android" +	android:id="@+id/map" +	android:layout_width="match_parent" +	android:layout_height="match_parent" +	class="com.google.android.gms.maps.SupportMapFragment"/> diff --git a/altosdroid/res/layout/tab_pad.xml b/altosdroid/res/layout/tab_pad.xml new file mode 100644 index 00000000..f5ec46b5 --- /dev/null +++ b/altosdroid/res/layout/tab_pad.xml @@ -0,0 +1,320 @@ +<?xml version="1.0" encoding="utf-8"?> +<!-- +     Copyright © 2013 Mike Beattie <mike@ethernal.org> + +     This program is free software; you can redistribute it and/or modify +     it under the terms of the GNU General Public License as published by +     the Free Software Foundation; version 2 of the License. + +     This program is distributed in the hope that it will be useful, but +     WITHOUT ANY WARRANTY; without even the implied warranty of +     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +     General Public License for more details. + +     You should have received a copy of the GNU General Public License along +     with this program; if not, write to the Free Software Foundation, Inc., +     59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +--> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" +	android:layout_width="fill_parent" +	android:layout_height="wrap_content" +	android:layout_weight="0" +	android:orientation="vertical" > + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" > + +		<ImageView +			android:id="@+id/battery_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/battery_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/battery_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/battery_redled" +			android:contentDescription="@string/battery_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/battery_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/battery_greenled" +			android:text="@string/battery_voltage_label" /> + +		<TextView +			android:id="@+id/battery_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/battery_voltage_label" +			android:layout_toRightOf="@id/battery_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/apogee_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/apogee_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/apogee_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_redled" +			android:contentDescription="@string/apogee_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/apogee_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="@string/apogee_voltage_label" /> + +		<TextView +			android:id="@+id/apogee_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/apogee_voltage_label" +			android:layout_toRightOf="@id/apogee_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/main_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/main_voltage_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/main_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_redled" +			android:contentDescription="@string/main_voltage_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/main_voltage_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/main_greenled" +			android:text="@string/main_voltage_label" /> + +		<TextView +			android:id="@+id/main_voltage_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/main_voltage_label" +			android:layout_toRightOf="@id/main_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/logging_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/logging_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/logging_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/logging_redled" +			android:contentDescription="@string/logging_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/logging_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/logging_greenled" +			android:text="@string/logging_label" /> + +		<TextView +			android:id="@+id/logging_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/logging_label" +			android:layout_toRightOf="@id/logging_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/gps_locked_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/gps_locked_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/gps_locked_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_locked_redled" +			android:contentDescription="@string/gps_locked_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/gps_locked_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_locked_greenled" +			android:text="@string/gps_locked_label" /> + +		<TextView +			android:id="@+id/gps_locked_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/gps_locked_label" +			android:layout_toRightOf="@id/gps_locked_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingTop="5dp" > + +		<ImageView +			android:id="@+id/gps_ready_redled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:contentDescription="@string/gps_ready_label" +			android:src="@drawable/redled" /> + +		<ImageView +			android:id="@+id/gps_ready_greenled" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_ready_redled" +			android:contentDescription="@string/gps_ready_label" +			android:paddingRight="5dp" +			android:src="@drawable/grayled" /> + +		<TextView +			android:id="@+id/gps_ready_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="@string/gps_ready_label" /> + +		<TextView +			android:id="@+id/gps_ready_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/gps_ready_label" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingLeft="69dp" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/pad_lat_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="@string/pad_lat_label" /> + +		<TextView +			android:id="@+id/pad_lat_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/pad_lat_label" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingLeft="69dp" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/pad_lon_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="@string/pad_lon_label" /> + +		<TextView +			android:id="@+id/pad_lon_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/pad_lon_label" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +	<RelativeLayout +		android:layout_width="wrap_content" +		android:layout_height="wrap_content" +		android:paddingLeft="69dp" +		android:paddingTop="5dp" > + +		<TextView +			android:id="@+id/pad_alt_label" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="@string/pad_alt_label" /> + +		<TextView +			android:id="@+id/pad_alt_value" +			android:layout_width="wrap_content" +			android:layout_height="wrap_content" +			android:layout_below="@id/pad_alt_label" +			android:layout_toRightOf="@id/gps_ready_greenled" +			android:text="" +			android:textAppearance="?android:attr/textAppearanceLarge" /> +	</RelativeLayout> + +</LinearLayout>
\ No newline at end of file diff --git a/altosdroid/res/values/strings.xml b/altosdroid/res/values/strings.xml index 1b28284a..639611c2 100644 --- a/altosdroid/res/values/strings.xml +++ b/altosdroid/res/values/strings.xml @@ -1,60 +1,79 @@  <?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2009 The Android Open Source Project +<!-- +	 Copyright © 2012-2013 Mike Beattie <mike@ethernal.org> -     Licensed under the Apache License, Version 2.0 (the "License"); -     you may not use this file except in compliance with the License. -     You may obtain a copy of the License at +	 This program is free software; you can redistribute it and/or modify +	 it under the terms of the GNU General Public License as published by +	 the Free Software Foundation; version 2 of the License. -          http://www.apache.org/licenses/LICENSE-2.0 +	 This program is distributed in the hope that it will be useful, but +	 WITHOUT ANY WARRANTY; without even the implied warranty of +	 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU +	 General Public License for more details. -     Unless required by applicable law or agreed to in writing, software -     distributed under the License is distributed on an "AS IS" BASIS, -     WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -     See the License for the specific language governing permissions and -     limitations under the License. +	 You should have received a copy of the GNU General Public License along +	 with this program; if not, write to the Free Software Foundation, Inc., +	 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA.  --> -  <resources> -    <string name="app_name">AltosDroid</string> -    <!--  AltosDroid --> -    <string name="bt_not_enabled">Bluetooth was not enabled.</string> -    <string name="title_connecting">connecting…</string> -    <string name="title_connected_to">connected: </string> -    <string name="title_not_connected">not connected</string> +	<string name="app_name">AltosDroid</string> -    <!-- Options Menu --> -    <string name="connect_device">Connect a device</string> -    <string name="select_freq">Select radio frequency</string> +	<!-- AltosDroid --> +	<string name="bt_not_enabled">Bluetooth was not enabled.</string> +	<string name="title_connecting">connecting…</string> +	<string name="title_connected_to">connected: </string> +	<string name="title_not_connected">not connected</string> -    <!--  DeviceListActivity --> -    <string name="scanning">scanning for devices…</string> -    <string name="select_device">select a device to connect</string> -    <string name="none_paired">No devices have been paired</string> -    <string name="none_found">No devices found</string> -    <string name="title_paired_devices">Paired Devices</string> -    <string name="title_other_devices">Other Available Devices</string> -    <string name="button_scan">Scan for devices</string> +	<!-- Options Menu --> +	<string name="connect_device">Connect a device</string> +	<string name="select_freq">Select radio frequency</string> -    <!-- Service --> -    <string name="telemetry_service_label">AltosDroid Telemetry Service</string> -    <string name="telemetry_service_started">Telemetry Service Started</string> -    <string name="telemetry_service_stopped">Telemetry Service Stopped</string> +	<!-- DeviceListActivity --> +	<string name="scanning">scanning for devices…</string> +	<string name="select_device">select a device to connect</string> +	<string name="none_paired">No devices have been paired</string> +	<string name="none_found">No devices found</string> +	<string name="title_paired_devices">Paired Devices</string> +	<string name="title_other_devices">Other Available Devices</string> +	<string name="button_scan">Scan for devices</string> +	<!-- Service --> +	<string name="telemetry_service_label">AltosDroid Telemetry Service</string> +	<string name="telemetry_service_started">Telemetry Service Started</string> +	<string name="telemetry_service_stopped">Telemetry Service Stopped</string>  	<!-- UI fields --> -    <string name="callsign_label">Callsign</string> -    <string name="serial_label">Serial no.</string> -    <string name="flight_label">Flight no.</string> -    <string name="rssi_label">RSSI</string> -    <string name="state_label">State</string> -    <string name="speed_label">Speed</string> -    <string name="accel_label">Acceleration</string> -    <string name="range_label">Range</string> -    <string name="height_label">Height</string> -    <string name="elevation_label">Elevation</string> -    <string name="bearing_label">Bearing</string> -    <string name="latitude_label">Latitude</string> -    <string name="longitude_label">Longitude</string> +	<!-- Header --> +	<string name="callsign_label">Callsign</string> +	<string name="serial_label">Serial</string> +	<string name="flight_label">Flight</string> +	<string name="state_label">State</string> +	<string name="rssi_label">RSSI</string> +	<string name="age_label">Age</string> + +	<!-- Tab fields --> +	<string name="height_label">Height</string> +	<string name="speed_label">Speed</string> +	<string name="accel_label">Acceleration</string> +	<string name="bearing_label">Bearing</string> +	<string name="elevation_label">Elevation</string> +	<string name="range_label">Range</string> +	<string name="distance_label">Distance</string> +	<string name="gnd_distance_label">Ground Distance</string> +	<string name="max_height_label">Max Height</string> +	<string name="max_speed_label">Max Speed</string> +	<string name="max_accel_label">Max Accel</string> +	<string name="battery_voltage_label">Battery Voltage</string> +	<string name="apogee_voltage_label">Apogee Igniter Voltage</string> +	<string name="main_voltage_label">Main Igniter Voltage</string> +	<string name="logging_label">On-board Data Logging</string> +	<string name="gps_locked_label">GPS Locked</string> +	<string name="gps_ready_label">GPS Ready</string> +	<string name="latitude_label">Latitude</string> +	<string name="longitude_label">Longitude</string> +	<string name="pad_lat_label">Pad Latitude</string> +	<string name="pad_lon_label">Pad Longitude</string> +	<string name="pad_alt_label">Pad Altitude</string>  </resources> diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java index 61931731..63043abd 100644 --- a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroid.java @@ -1,5 +1,5 @@  /* - * Copyright © 2012 Mike Beattie <mike@ethernal.org> + * Copyright © 2012-2013 Mike Beattie <mike@ethernal.org>   *   * This program is free software; you can redistribute it and/or modify   * it under the terms of the GNU General Public License as published by @@ -18,6 +18,9 @@  package org.altusmetrum.AltosDroid;  import java.lang.ref.WeakReference; +import java.util.ArrayList; +import java.util.Timer; +import java.util.TimerTask;  import android.app.Activity;  import android.bluetooth.BluetoothAdapter; @@ -33,18 +36,21 @@ import android.os.Handler;  import android.os.Message;  import android.os.Messenger;  import android.os.RemoteException; +import android.support.v4.app.FragmentActivity; +import android.support.v4.view.ViewPager;  import android.util.Log;  import android.view.Menu;  import android.view.MenuInflater;  import android.view.MenuItem;  import android.view.Window; +import android.widget.TabHost;  import android.widget.TextView;  import android.widget.Toast;  import android.app.AlertDialog;  import org.altusmetrum.altoslib_1.*; -public class AltosDroid extends Activity { +public class AltosDroid extends FragmentActivity {  	// Debugging  	private static final String TAG = "AltosDroid";  	private static final boolean D = true; @@ -52,6 +58,7 @@ public class AltosDroid extends Activity {  	// Message types received by our Handler  	public static final int MSG_STATE_CHANGE    = 1;  	public static final int MSG_TELEMETRY       = 2; +	public static final int MSG_UPDATE_AGE      = 3;  	// Intent request codes  	private static final int REQUEST_CONNECT_DEVICE = 1; @@ -66,18 +73,21 @@ public class AltosDroid extends Activity {  	private TextView mSerialView;  	private TextView mFlightView;  	private TextView mStateView; -	private TextView mSpeedView; -	private TextView mAccelView; -	private TextView mRangeView; -	private TextView mHeightView; -	private TextView mElevationView; -	private TextView mBearingView; -	private TextView mLatitudeView; -	private TextView mLongitudeView; +	private TextView mAgeView;  	// field to display the version at the bottom of the screen  	private TextView mVersion; +	// Tabs +	TabHost     mTabHost; +	ViewPager   mViewPager; +	TabsAdapter mTabsAdapter; +	ArrayList<AltosDroidTab> mTabs = new ArrayList<AltosDroidTab>(); + +	// Timer and Saved flight state for Age calculation +	private Timer timer = new Timer(); +	AltosState saved_state; +  	// Service  	private boolean mIsBound   = false;  	private Messenger mService = null; @@ -127,6 +137,11 @@ public class AltosDroid extends Activity {  			case MSG_TELEMETRY:  				ad.update_ui((AltosState) msg.obj);  				break; +			case MSG_UPDATE_AGE: +				if (ad.saved_state != null) { +					ad.mAgeView.setText(String.format("%d", (System.currentTimeMillis() - ad.saved_state.report_time + 500) / 1000)); +				} +				break;  			}  		}  	}; @@ -150,7 +165,6 @@ public class AltosDroid extends Activity {  		}  	}; -  	void doBindService() {  		bindService(new Intent(this, TelemetryService.class), mConnection, Context.BIND_AUTO_CREATE);  		mIsBound = true; @@ -174,26 +188,53 @@ public class AltosDroid extends Activity {  		}  	} +	public void registerTab(AltosDroidTab mTab) { +		mTabs.add(mTab); +	} + +	public void unregisterTab(AltosDroidTab mTab) { +		mTabs.remove(mTab); +	} +  	void update_ui(AltosState state) { +		if (saved_state != null) { +			if (saved_state.state != state.state) { +				String currentTab = mTabHost.getCurrentTabTag(); +				switch (state.state) { +				case AltosLib.ao_flight_boost: +					if (currentTab.equals("pad")) mTabHost.setCurrentTabByTag("ascent"); +					break; +				case AltosLib.ao_flight_drogue: +					if (currentTab.equals("ascent")) mTabHost.setCurrentTabByTag("descent"); +					break; +				case AltosLib.ao_flight_landed: +					if (currentTab.equals("descent")) mTabHost.setCurrentTabByTag("landed"); +					break; +				} +			} +		} +		saved_state = state; +  		mCallsignView.setText(state.data.callsign); -		mRSSIView.setText(String.format("%d", state.data.rssi));  		mSerialView.setText(String.format("%d", state.data.serial));  		mFlightView.setText(String.format("%d", state.data.flight));  		mStateView.setText(state.data.state()); -		mSpeedView.setText(String.format("%6.0f m/s", state.speed())); -		mAccelView.setText(String.format("%6.0f m/s²", state.acceleration)); -		mRangeView.setText(String.format("%6.0f m", state.range)); -		mHeightView.setText(String.format("%6.0f m", state.height)); -		mElevationView.setText(String.format("%3.0f°", state.elevation)); -		if (state.from_pad != null) -			mBearingView.setText(String.format("%3.0f°", state.from_pad.bearing)); -		mLatitudeView.setText(pos(state.gps.lat, "N", "S")); -		mLongitudeView.setText(pos(state.gps.lon, "W", "E")); +		mRSSIView.setText(String.format("%d", state.data.rssi)); + +		for (AltosDroidTab mTab : mTabs) +			mTab.update_ui(state);  		mAltosVoice.tell(state);  	} -	String pos(double p, String pos, String neg) { +	private void onTimerTick() { +		try { +			mMessenger.send(Message.obtain(null, MSG_UPDATE_AGE)); +		} catch (RemoteException e) { +		} +	} + +	static String pos(double p, String pos, String neg) {  		String	h = pos;  		if (p < 0) {  			h = neg; @@ -228,6 +269,21 @@ public class AltosDroid extends Activity {  		setContentView(R.layout.altosdroid);  		getWindow().setFeatureInt(Window.FEATURE_CUSTOM_TITLE, R.layout.custom_title); +		mTabHost = (TabHost)findViewById(android.R.id.tabhost); +		mTabHost.setup(); + +		mViewPager = (ViewPager)findViewById(R.id.pager); +		mViewPager.setOffscreenPageLimit(4); + +		mTabsAdapter = new TabsAdapter(this, mTabHost, mViewPager); + +		mTabsAdapter.addTab(mTabHost.newTabSpec("pad").setIndicator("Pad"), TabPad.class, null); +		mTabsAdapter.addTab(mTabHost.newTabSpec("ascent").setIndicator("Ascent"), TabAscent.class, null); +		mTabsAdapter.addTab(mTabHost.newTabSpec("descent").setIndicator("Descent"), TabDescent.class, null); +		mTabsAdapter.addTab(mTabHost.newTabSpec("landed").setIndicator("Landed"), TabLanded.class, null); +		mTabsAdapter.addTab(mTabHost.newTabSpec("map").setIndicator("Map"), TabMap.class, null); + +  		// Set up the custom title  		mTitle = (TextView) findViewById(R.id.title_left_text);  		mTitle.setText(R.string.app_name); @@ -244,14 +300,9 @@ public class AltosDroid extends Activity {  		mSerialView    = (TextView) findViewById(R.id.serial_value);  		mFlightView    = (TextView) findViewById(R.id.flight_value);  		mStateView     = (TextView) findViewById(R.id.state_value); -		mSpeedView     = (TextView) findViewById(R.id.speed_value); -		mAccelView     = (TextView) findViewById(R.id.accel_value); -		mRangeView     = (TextView) findViewById(R.id.range_value); -		mHeightView    = (TextView) findViewById(R.id.height_value); -		mElevationView = (TextView) findViewById(R.id.elevation_value); -		mBearingView   = (TextView) findViewById(R.id.bearing_value); -		mLatitudeView  = (TextView) findViewById(R.id.latitude_value); -		mLongitudeView = (TextView) findViewById(R.id.longitude_value); +		mAgeView       = (TextView) findViewById(R.id.age_value); + +		timer.scheduleAtFixedRate(new TimerTask(){ public void run() {onTimerTick();}}, 1000L, 100L);  		mAltosVoice = new AltosVoice(this);  	} @@ -300,9 +351,6 @@ public class AltosDroid extends Activity {  		mAltosVoice.stop();  	} - - -  	public void onActivityResult(int requestCode, int resultCode, Intent data) {  		if(D) Log.d(TAG, "onActivityResult " + resultCode);  		switch (requestCode) { diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidTab.java b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidTab.java new file mode 100644 index 00000000..68bbe593 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/AltosDroidTab.java @@ -0,0 +1,24 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.AltosState; + +public interface AltosDroidTab { +	public void update_ui(AltosState state); +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/GoNoGoLights.java b/altosdroid/src/org/altusmetrum/AltosDroid/GoNoGoLights.java new file mode 100644 index 00000000..0f95bc22 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/GoNoGoLights.java @@ -0,0 +1,55 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import android.content.res.Resources; +import android.graphics.drawable.Drawable; +import android.widget.ImageView; + +public class GoNoGoLights { +	private Boolean state; + +	private ImageView red; +	private ImageView green; + +	private Drawable dRed; +	private Drawable dGreen; +	private Drawable dGray; + +	public GoNoGoLights(ImageView in_red, ImageView in_green, Resources r) { +		red = in_red; +		green = in_green; +		state = false; + +		dRed   = r.getDrawable(R.drawable.redled); +		dGreen = r.getDrawable(R.drawable.greenled); +		dGray  = r.getDrawable(R.drawable.grayled); +	} + +	public void set(Boolean s) { +		if (s == state) return; +		state = s; +		if (state) { +			red.setImageDrawable(dGray); +			green.setImageDrawable(dGreen); +		} else { +			red.setImageDrawable(dRed); +			green.setImageDrawable(dGray); +		} +	} +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabAscent.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabAscent.java new file mode 100644 index 00000000..bda6b1fd --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabAscent.java @@ -0,0 +1,104 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.AltosState; + +import android.app.Activity; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ImageView; +import android.widget.TextView; + +public class TabAscent extends Fragment implements AltosDroidTab { +	AltosDroid mAltosDroid; + +	private TextView mHeightView; +	private TextView mMaxHeightView; +	private TextView mSpeedView; +	private TextView mMaxSpeedView; +	private TextView mAccelView; +	private TextView mMaxAccelView; +	private TextView mLatitudeView; +	private TextView mLongitudeView; +	private TextView mApogeeVoltageView; +	private GoNoGoLights mApogeeLights; +	private TextView mMainVoltageView; +	private GoNoGoLights mMainLights; + +	@Override +	public void onAttach(Activity activity) { +		super.onAttach(activity); +		mAltosDroid = (AltosDroid) activity; +		mAltosDroid.registerTab(this); +	} + +	@Override +	public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { +		View v = inflater.inflate(R.layout.tab_ascent, container, false); + +		mHeightView    = (TextView) v.findViewById(R.id.height_value); +		mMaxHeightView = (TextView) v.findViewById(R.id.max_height_value); +		mSpeedView     = (TextView) v.findViewById(R.id.speed_value); +		mMaxSpeedView  = (TextView) v.findViewById(R.id.max_speed_value); +		mAccelView     = (TextView) v.findViewById(R.id.accel_value); +		mMaxAccelView  = (TextView) v.findViewById(R.id.max_accel_value); +		mLatitudeView  = (TextView) v.findViewById(R.id.lat_value); +		mLongitudeView = (TextView) v.findViewById(R.id.lon_value); + +		mApogeeVoltageView = (TextView) v.findViewById(R.id.apogee_voltage_value); +		mApogeeLights = new GoNoGoLights((ImageView) v.findViewById(R.id.apogee_redled), +		                                 (ImageView) v.findViewById(R.id.apogee_greenled), +		                                 getResources()); + +		mMainVoltageView = (TextView) v.findViewById(R.id.main_voltage_value); +		mMainLights = new GoNoGoLights((ImageView) v.findViewById(R.id.main_redled), +		                               (ImageView) v.findViewById(R.id.main_greenled), +		                               getResources()); + +		return v; +	} + +	@Override +	public void onDestroy() { +		super.onDestroy(); +		mAltosDroid.unregisterTab(this); +		mAltosDroid = null; +	} + +	public void update_ui(AltosState state) { +		mHeightView.setText(String.format("%6.0f m", state.height)); +		mMaxHeightView.setText(String.format("%6.0f m", state.max_height)); +		mSpeedView.setText(String.format("%6.0f m/s", state.speed())); +		mMaxSpeedView.setText(String.format("%6.0f m/s", state.max_speed())); +		mAccelView.setText(String.format("%6.0f m/s²", state.acceleration)); +		mMaxAccelView.setText(String.format("%6.0f m/s²", state.max_acceleration)); + +		mLatitudeView.setText(AltosDroid.pos(state.gps.lat, "N", "S")); +		mLongitudeView.setText(AltosDroid.pos(state.gps.lon, "W", "E")); + +		mApogeeVoltageView.setText(String.format("%4.2f V", state.drogue_sense)); +		mApogeeLights.set(state.drogue_sense > 3.2); + +		mMainVoltageView.setText(String.format("%4.2f V", state.main_sense)); +		mMainLights.set(state.main_sense > 3.2); +	} +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabDescent.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabDescent.java new file mode 100644 index 00000000..3805b7e7 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabDescent.java @@ -0,0 +1,112 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.AltosGreatCircle; +import org.altusmetrum.altoslib_1.AltosState; + +import android.app.Activity; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ImageView; +import android.widget.TextView; + +public class TabDescent extends Fragment implements AltosDroidTab { +	AltosDroid mAltosDroid; + +	private TextView mSpeedView; +	private TextView mHeightView; +	private TextView mElevationView; +	private TextView mRangeView; +	private TextView mBearingView; +	private TextView mCompassView; +	private TextView mDistanceView; +	private TextView mLatitudeView; +	private TextView mLongitudeView; +	private TextView mApogeeVoltageView; +	private GoNoGoLights mApogeeLights; +	private TextView mMainVoltageView; +	private GoNoGoLights mMainLights; + + +	@Override +	public void onAttach(Activity activity) { +		super.onAttach(activity); +		mAltosDroid = (AltosDroid) activity; +		mAltosDroid.registerTab(this); +	} + +	@Override +	public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { +		View v = inflater.inflate(R.layout.tab_descent, container, false); + +		mSpeedView     = (TextView) v.findViewById(R.id.speed_value); +		mHeightView    = (TextView) v.findViewById(R.id.height_value); +		mElevationView = (TextView) v.findViewById(R.id.elevation_value); +		mRangeView     = (TextView) v.findViewById(R.id.range_value); +		mBearingView   = (TextView) v.findViewById(R.id.bearing_value); +		mCompassView   = (TextView) v.findViewById(R.id.compass_value); +		mDistanceView  = (TextView) v.findViewById(R.id.distance_value); +		mLatitudeView  = (TextView) v.findViewById(R.id.lat_value); +		mLongitudeView = (TextView) v.findViewById(R.id.lon_value); + +		mApogeeVoltageView = (TextView) v.findViewById(R.id.apogee_voltage_value); +		mApogeeLights = new GoNoGoLights((ImageView) v.findViewById(R.id.apogee_redled), +		                                 (ImageView) v.findViewById(R.id.apogee_greenled), +		                                 getResources()); + +		mMainVoltageView = (TextView) v.findViewById(R.id.main_voltage_value); +		mMainLights = new GoNoGoLights((ImageView) v.findViewById(R.id.main_redled), +		                               (ImageView) v.findViewById(R.id.main_greenled), +		                               getResources()); + +		return v; +	} + + +	@Override +	public void onDestroy() { +		super.onDestroy(); +		mAltosDroid.unregisterTab(this); +		mAltosDroid = null; +	} + +	public void update_ui(AltosState state) { +		mSpeedView.setText(String.format("%6.0f m/s", state.speed())); +		mHeightView.setText(String.format("%6.0f m", state.height)); +		mElevationView.setText(String.format("%3.0f°", state.elevation)); +		mRangeView.setText(String.format("%6.0f m", state.range)); +		if (state.from_pad != null) { +			mBearingView.setText(String.format("%3.0f°", state.from_pad.bearing)); +			mCompassView.setText(state.from_pad.bearing_words(AltosGreatCircle.BEARING_LONG)); +		} +		mDistanceView.setText(String.format("%6.0f m", state.range)); +		mLatitudeView.setText(AltosDroid.pos(state.gps.lat, "N", "S")); +		mLongitudeView.setText(AltosDroid.pos(state.gps.lon, "W", "E")); + +		mApogeeVoltageView.setText(String.format("%4.2f V", state.drogue_sense)); +		mApogeeLights.set(state.drogue_sense > 3.2); + +		mMainVoltageView.setText(String.format("%4.2f V", state.main_sense)); +		mMainLights.set(state.main_sense > 3.2); +	} + +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabLanded.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabLanded.java new file mode 100644 index 00000000..a95e9145 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabLanded.java @@ -0,0 +1,83 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.AltosState; + +import android.app.Activity; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.TextView; + +public class TabLanded extends Fragment implements AltosDroidTab { +	AltosDroid mAltosDroid; + +	private TextView mBearingView; +	private TextView mDistanceView; +	private TextView mLatitudeView; +	private TextView mLongitudeView; +	private TextView mMaxHeightView; +	private TextView mMaxSpeedView; +	private TextView mMaxAccelView; + + +	@Override +	public void onAttach(Activity activity) { +		super.onAttach(activity); +		mAltosDroid = (AltosDroid) activity; +		mAltosDroid.registerTab(this); +	} + +	@Override +	public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { +		View v = inflater.inflate(R.layout.tab_landed, container, false); + +		mBearingView   = (TextView) v.findViewById(R.id.bearing_value); +		mDistanceView  = (TextView) v.findViewById(R.id.distance_value); +		mLatitudeView  = (TextView) v.findViewById(R.id.lat_value); +		mLongitudeView = (TextView) v.findViewById(R.id.lon_value); +		mMaxHeightView = (TextView) v.findViewById(R.id.max_height_value); +		mMaxSpeedView  = (TextView) v.findViewById(R.id.max_speed_value); +		mMaxAccelView  = (TextView) v.findViewById(R.id.max_accel_value); + +		return v; +	} + +	@Override +	public void onDestroy() { +		super.onDestroy(); +		mAltosDroid.unregisterTab(this); +		mAltosDroid = null; +	} + +	public void update_ui(AltosState state) { +		if (state.from_pad != null) { +			mBearingView.setText(String.format("%3.0f°", state.from_pad.bearing)); +			mDistanceView.setText(String.format("%6.0f m", state.from_pad.distance)); +		} +		mLatitudeView.setText(AltosDroid.pos(state.gps.lat, "N", "S")); +		mLongitudeView.setText(AltosDroid.pos(state.gps.lon, "W", "E")); +		mMaxHeightView.setText(String.format("%6.0f m", state.max_height)); +		mMaxAccelView.setText(String.format("%6.0f m/s²", state.max_acceleration)); +		mMaxSpeedView.setText(String.format("%6.0f m/s", state.max_speed())); +	} + +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java new file mode 100644 index 00000000..b30b4694 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabMap.java @@ -0,0 +1,72 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.AltosState; + +import com.google.android.gms.maps.GoogleMap; + +import android.app.Activity; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.support.v4.app.FragmentTransaction; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; + +public class TabMap extends Fragment implements AltosDroidTab { +	AltosDroid mAltosDroid; + +	private GoogleMap mMap; + + +	@Override +	public void onAttach(Activity activity) { +		super.onAttach(activity); +		mAltosDroid = (AltosDroid) activity; +		mAltosDroid.registerTab(this); +	} + +	@Override +	public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { +		View v = inflater.inflate(R.layout.tab_map, container, false); +		return v; +	} + +	@Override +	public void onDestroyView() { +		super.onDestroyView(); + +		mAltosDroid.unregisterTab(this); +		mAltosDroid = null; + +		//Fragment fragment = (getFragmentManager().findFragmentById(R.id.map)); +		//FragmentTransaction ft = getActivity().getSupportFragmentManager().beginTransaction(); +		//ft.remove(fragment); +		//ft.commit(); +	} + +	public void update_ui(AltosState state) { +//		mRangeView.setText(String.format("%6.0f m", state.range)); +//		if (state.from_pad != null) +//			mBearingView.setText(String.format("%3.0f°", state.from_pad.bearing)); +//		mLatitudeView.setText(pos(state.gps.lat, "N", "S")); +//		mLongitudeView.setText(pos(state.gps.lon, "W", "E")); +	} + +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabPad.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabPad.java new file mode 100644 index 00000000..41776c10 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabPad.java @@ -0,0 +1,139 @@ +/* + * Copyright © 2013 Mike Beattie <mike@ethernal.org> + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; version 2 of the License. + * + * This program is distributed in the hope that it will be useful, but + * WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU + * General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. + */ + +package org.altusmetrum.AltosDroid; + +import org.altusmetrum.altoslib_1.*; + +import android.app.Activity; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ImageView; +import android.widget.TextView; + +public class TabPad extends Fragment implements AltosDroidTab { +	AltosDroid mAltosDroid; + +	private TextView mBatteryVoltageView; +	private GoNoGoLights mBatteryLights; +	private TextView mApogeeVoltageView; +	private GoNoGoLights mApogeeLights; +	private TextView mMainVoltageView; +	private GoNoGoLights mMainLights; +	private TextView mDataLoggingView; +	private GoNoGoLights mDataLoggingLights; +	private TextView mGPSLockedView; +	private GoNoGoLights mGPSLockedLights; +	private TextView mGPSReadyView; +	private GoNoGoLights mGPSReadyLights; +	private TextView mPadLatitudeView; +	private TextView mPadLongitudeView; +	private TextView mPadAltitudeView; + +	@Override +	public void onAttach(Activity activity) { +		super.onAttach(activity); +		mAltosDroid = (AltosDroid) activity; +		mAltosDroid.registerTab(this); +	} + +	@Override +	public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { +		View v = inflater.inflate(R.layout.tab_pad, container, false); +		mBatteryVoltageView = (TextView) v.findViewById(R.id.battery_voltage_value); +		mBatteryLights = new GoNoGoLights((ImageView) v.findViewById(R.id.battery_redled), +		                                  (ImageView) v.findViewById(R.id.battery_greenled), +		                                  getResources()); + +		mApogeeVoltageView = (TextView) v.findViewById(R.id.apogee_voltage_value); +		mApogeeLights = new GoNoGoLights((ImageView) v.findViewById(R.id.apogee_redled), +		                                 (ImageView) v.findViewById(R.id.apogee_greenled), +		                                 getResources()); + +		mMainVoltageView = (TextView) v.findViewById(R.id.main_voltage_value); +		mMainLights = new GoNoGoLights((ImageView) v.findViewById(R.id.main_redled), +		                               (ImageView) v.findViewById(R.id.main_greenled), +		                               getResources()); + +		mDataLoggingView = (TextView) v.findViewById(R.id.logging_value); +		mDataLoggingLights = new GoNoGoLights((ImageView) v.findViewById(R.id.logging_redled), +		                                      (ImageView) v.findViewById(R.id.logging_greenled), +		                                      getResources()); + +		mGPSLockedView = (TextView) v.findViewById(R.id.gps_locked_value); +		mGPSLockedLights = new GoNoGoLights((ImageView) v.findViewById(R.id.gps_locked_redled), +		                                    (ImageView) v.findViewById(R.id.gps_locked_greenled), +		                                    getResources()); + +		mGPSReadyView = (TextView) v.findViewById(R.id.gps_ready_value); +		mGPSReadyLights = new GoNoGoLights((ImageView) v.findViewById(R.id.gps_ready_redled), +		                                   (ImageView) v.findViewById(R.id.gps_ready_greenled), +		                                   getResources()); + +		mPadLatitudeView = (TextView) v.findViewById(R.id.pad_lat_value); +		mPadLongitudeView = (TextView) v.findViewById(R.id.pad_lon_value); +		mPadAltitudeView = (TextView) v.findViewById(R.id.pad_alt_value); +        return v; +	} + +	@Override +	public void onDestroy() { +		super.onDestroy(); +		mAltosDroid.unregisterTab(this); +		mAltosDroid = null; +	} + +	public void update_ui(AltosState state) { +		mBatteryVoltageView.setText(String.format("%4.2f V", state.battery)); +		mBatteryLights.set(state.battery > 3.7); + +		mApogeeVoltageView.setText(String.format("%4.2f V", state.drogue_sense)); +		mApogeeLights.set(state.drogue_sense > 3.2); + +		mMainVoltageView.setText(String.format("%4.2f V", state.main_sense)); +		mMainLights.set(state.main_sense > 3.2); + +		if (state.data.flight != 0) { +			if (state.data.state <= AltosLib.ao_flight_pad) +				mDataLoggingView.setText("Ready to record"); +			else if (state.data.state < AltosLib.ao_flight_landed) +				mDataLoggingView.setText("Recording data"); +			else +				mDataLoggingView.setText("Recorded data"); +		} else { +			mDataLoggingView.setText("Storage full"); +		} +		mDataLoggingLights.set(state.data.flight != 0); + +		mGPSLockedView.setText(String.format("%4d sats", state.gps.nsat)); +		mGPSLockedLights.set(state.gps.locked && state.gps.nsat >= 4); + +		if (state.gps_ready) +			mGPSReadyView.setText("Ready"); +		else +			mGPSReadyView.setText(String.format("Waiting %d", state.gps_waiting)); +		mGPSReadyLights.set(state.gps_ready); + +		mPadLatitudeView.setText(AltosDroid.pos(state.pad_lat, "N", "S")); +		mPadLongitudeView.setText(AltosDroid.pos(state.pad_lon, "W", "E")); +		mPadAltitudeView.setText(String.format("%4.0f m", state.pad_alt)); +	} + +} diff --git a/altosdroid/src/org/altusmetrum/AltosDroid/TabsAdapter.java b/altosdroid/src/org/altusmetrum/AltosDroid/TabsAdapter.java new file mode 100644 index 00000000..a4758c37 --- /dev/null +++ b/altosdroid/src/org/altusmetrum/AltosDroid/TabsAdapter.java @@ -0,0 +1,133 @@ +/* + * Copyright (C) 2009 The Android Open Source Project + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + *      http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +package org.altusmetrum.AltosDroid; + +import java.util.ArrayList; + +import android.content.Context; +import android.os.Bundle; +import android.support.v4.app.Fragment; +import android.support.v4.app.FragmentActivity; +import android.support.v4.app.FragmentPagerAdapter; +import android.support.v4.view.ViewPager; +import android.view.View; +import android.view.ViewGroup; +import android.widget.TabHost; +import android.widget.TabWidget; + + + +/** + * This is a helper class that implements the management of tabs and all + * details of connecting a ViewPager with associated TabHost.  It relies on a + * trick.  Normally a tab host has a simple API for supplying a View or + * Intent that each tab will show.  This is not sufficient for switching + * between pages.  So instead we make the content part of the tab host + * 0dp high (it is not shown) and the TabsAdapter supplies its own dummy + * view to show as the tab content.  It listens to changes in tabs, and takes + * care of switch to the correct paged in the ViewPager whenever the selected + * tab changes. + */ +public class TabsAdapter extends FragmentPagerAdapter +		implements TabHost.OnTabChangeListener, ViewPager.OnPageChangeListener { +	private final Context mContext; +	private final TabHost mTabHost; +	private final ViewPager mViewPager; +	private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>(); + +	static final class TabInfo { +		private final String tag; +		private final Class<?> clss; +		private final Bundle args; + +		TabInfo(String _tag, Class<?> _class, Bundle _args) { +			tag = _tag; +			clss = _class; +			args = _args; +		} +	} + +	static class DummyTabFactory implements TabHost.TabContentFactory { +		private final Context mContext; + +		public DummyTabFactory(Context context) { +			mContext = context; +		} + +		public View createTabContent(String tag) { +			View v = new View(mContext); +			v.setMinimumWidth(0); +			v.setMinimumHeight(0); +			return v; +		} +	} + +	public TabsAdapter(FragmentActivity activity, TabHost tabHost, ViewPager pager) { +		super(activity.getSupportFragmentManager()); +		mContext = activity; +		mTabHost = tabHost; +		mViewPager = pager; +		mTabHost.setOnTabChangedListener(this); +		mViewPager.setAdapter(this); +		mViewPager.setOnPageChangeListener(this); +	} + +	public void addTab(TabHost.TabSpec tabSpec, Class<?> clss, Bundle args) { +		tabSpec.setContent(new DummyTabFactory(mContext)); +		String tag = tabSpec.getTag(); + +		TabInfo info = new TabInfo(tag, clss, args); +		mTabs.add(info); +		mTabHost.addTab(tabSpec); +		notifyDataSetChanged(); +	} + +	@Override +	public int getCount() { +		return mTabs.size(); +	} + +	@Override +	public Fragment getItem(int position) { +		TabInfo info = mTabs.get(position); +		return Fragment.instantiate(mContext, info.clss.getName(), info.args); +	} + +	public void onTabChanged(String tabId) { +		int position = mTabHost.getCurrentTab(); +		mViewPager.setCurrentItem(position); +	} + +	public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) { +	} + +	public void onPageSelected(int position) { +		// Unfortunately when TabHost changes the current tab, it kindly +		// also takes care of putting focus on it when not in touch mode. +		// The jerk. +		// This hack tries to prevent this from pulling focus out of our +		// ViewPager. +		TabWidget widget = mTabHost.getTabWidget(); +		int oldFocusability = widget.getDescendantFocusability(); +		widget.setDescendantFocusability(ViewGroup.FOCUS_BLOCK_DESCENDANTS); +		mTabHost.setCurrentTab(position); +		widget.setDescendantFocusability(oldFocusability); +	} + +	public void onPageScrollStateChanged(int state) { +	} +} | 
