├── .classpath
├── .gitignore
├── .project
├── .settings
└── org.eclipse.jdt.core.prefs
├── AndroidManifest.xml
├── README.md
├── assets
└── fonts
│ ├── dash_digital_7.ttf
│ └── digital_7.ttf
├── ic_launcher-web.png
├── proguard-project.txt
├── project.properties
├── res
├── anim
│ ├── flipin.xml
│ ├── flipin_reverse.xml
│ ├── flipout.xml
│ └── flipout_reverse.xml
├── drawable-hdpi
│ ├── access_alarms.png
│ ├── action_settings.png
│ ├── content_save.png
│ ├── ic_action_search.png
│ ├── ic_action_share.png
│ ├── ic_launcher.png
│ ├── ic_launcher_gs.png
│ └── states_warning.png
├── drawable-ldpi
│ ├── ic_launcher.png
│ └── ic_launcher_gs.png
├── drawable-mdpi
│ ├── access_alarms.png
│ ├── action_settings.png
│ ├── content_save.png
│ ├── ic_action_search.png
│ ├── ic_action_share.png
│ ├── ic_launcher.png
│ ├── ic_launcher_gs.png
│ └── states_warning.png
├── drawable-xhdpi
│ ├── access_alarms.png
│ ├── action_settings.png
│ ├── content_save.png
│ ├── ic_action_search.png
│ ├── ic_action_share.png
│ ├── ic_launcher.png
│ ├── ic_launcher_gs.png
│ └── states_warning.png
├── drawable
│ ├── afr.png
│ ├── afrtwo.png
│ ├── boost_vac.png
│ ├── boost_vac_15.png
│ ├── cell_value_widget.png
│ ├── cell_value_widget_big_down.png
│ ├── cell_value_widget_big_up.png
│ ├── cell_value_widget_small_down.png
│ ├── cell_value_widget_small_up.png
│ ├── digital_background.xml
│ ├── digital_gauge_gradient_background.xml
│ ├── iatgauge.png
│ ├── iatgauge_celsius.png
│ ├── iload.png
│ ├── irpm.png
│ ├── iwait.png
│ ├── mapgauge.png
│ ├── needle_middle.png
│ ├── needle_middle_green.png
│ ├── needle_middle_yellow.png
│ ├── needle_offset.png
│ ├── rectangle_green.xml
│ ├── rectangle_yellow.xml
│ ├── shape_gradient_background.xml
│ ├── shape_gradient_blue_to_green.xml
│ ├── shape_gradient_green_to_red.xml
│ ├── shape_gradient_slider.xml
│ ├── shape_textview_border.xml
│ ├── slider.png
│ ├── tachometer.png
│ ├── tiny_list_item_border.xml
│ └── watertemp.png
├── layout-large-port
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── layout-large
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── gauges_tab.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── layout-port
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── edit_cell_dialog.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── layout-xlarge-port
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── layout-xlarge
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── gauges_tab.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── layout
│ ├── activity_main.xml
│ ├── adaptive_grid_item.xml
│ ├── adaptive_tab.xml
│ ├── digital_gauge.xml
│ ├── edit_cell_dialog.xml
│ ├── fuel_tab.xml
│ ├── gauges_tab.xml
│ ├── seekbar.xml
│ ├── tiny_list_item.xml
│ └── tiny_list_item_bold.xml
├── menu
│ └── activity_main.xml
├── raw
│ └── changelog.txt
├── values-large
│ └── dimens.xml
├── values-v11
│ └── styles.xml
├── values-xlarge
│ └── dimens.xml
├── values
│ ├── arrays.xml
│ ├── attrs.xml
│ ├── dimens.xml
│ ├── strings.xml
│ └── styles.xml
└── xml
│ └── device_filter.xml
├── src
└── com
│ └── shellware
│ └── adaptronic
│ └── adaptivetuner
│ ├── MainActivity.java
│ ├── MainActivityBackupAgentHelper.java
│ ├── bluetooth
│ ├── BluetoothConnectThread.java
│ └── BluetoothConnectedThread.java
│ ├── changelog
│ └── ChangeLog.java
│ ├── fragments
│ ├── AdaptiveFragment.java
│ ├── FuelFragment.java
│ └── GaugesFragment.java
│ ├── logging
│ └── AdaptiveLogger.java
│ ├── modbus
│ ├── ConnectedThread.java
│ └── ModbusRTU.java
│ ├── preferences
│ ├── AdaptivePreferences.java
│ └── SeekBarPreference.java
│ ├── receivers
│ └── BatteryStatusReceiver.java
│ ├── services
│ └── ConnectionService.java
│ ├── usb
│ ├── CL431SerialToUsbConnector.java
│ ├── FTDISerialToUsbConnector.java
│ ├── PL2303SerialToUsbConnector.java
│ ├── SelectECUConnector.java
│ ├── UsbConnectedThread.java
│ └── UsbDeviceConnector.java
│ ├── valueobjects
│ └── LogItems.java
│ └── widgets
│ ├── AdaptiveAdapter.java
│ ├── CellValueWidget.java
│ ├── DigitalGauge.java
│ ├── GaugeNeedle.java
│ └── GaugeSlider.java
├── web_hi_res_1024.png
└── web_hi_res_512.png
/.classpath:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/.gitignore:
--------------------------------------------------------------------------------
1 | /gen
2 | /bin
3 | /libs
4 | /lint.xml
5 |
--------------------------------------------------------------------------------
/.project:
--------------------------------------------------------------------------------
1 |
2 |
3 | Adaptive Tuner
4 |
5 |
6 |
7 |
8 |
9 | com.android.ide.eclipse.adt.ResourceManagerBuilder
10 |
11 |
12 |
13 |
14 | com.android.ide.eclipse.adt.PreCompilerBuilder
15 |
16 |
17 |
18 |
19 | org.eclipse.jdt.core.javabuilder
20 |
21 |
22 |
23 |
24 | com.android.ide.eclipse.adt.ApkBuilder
25 |
26 |
27 |
28 |
29 |
30 | com.android.ide.eclipse.adt.AndroidNature
31 | org.eclipse.jdt.core.javanature
32 |
33 |
34 |
--------------------------------------------------------------------------------
/.settings/org.eclipse.jdt.core.prefs:
--------------------------------------------------------------------------------
1 | eclipse.preferences.version=1
2 | org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode=enabled
3 | org.eclipse.jdt.core.compiler.codegen.methodParameters=do not generate
4 | org.eclipse.jdt.core.compiler.codegen.targetPlatform=1.5
5 | org.eclipse.jdt.core.compiler.codegen.unusedLocal=preserve
6 | org.eclipse.jdt.core.compiler.compliance=1.5
7 | org.eclipse.jdt.core.compiler.debug.lineNumber=generate
8 | org.eclipse.jdt.core.compiler.debug.localVariable=generate
9 | org.eclipse.jdt.core.compiler.debug.sourceFile=generate
10 | org.eclipse.jdt.core.compiler.problem.assertIdentifier=error
11 | org.eclipse.jdt.core.compiler.problem.enumIdentifier=error
12 | org.eclipse.jdt.core.compiler.source=1.5
13 |
--------------------------------------------------------------------------------
/AndroidManifest.xml:
--------------------------------------------------------------------------------
1 |
19 |
24 |
25 |
28 |
29 |
30 |
31 |
32 |
33 |
34 |
35 |
41 |
42 |
46 |
47 |
48 |
49 |
50 |
51 |
52 |
53 |
54 |
55 |
56 |
57 |
58 |
59 |
61 |
62 |
65 |
66 |
67 |
68 |
69 |
70 |
71 |
72 |
73 |
74 |
75 |
76 |
77 |
78 |
79 |
80 |
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 |
2 | Copyright 2012-2015 Shell M. Shrader
3 |
4 | Contributors
5 | ============
6 | Shell M. Shrader (Maintainer)
7 | Evan H. Dekker (initial OTG implementation)
8 | Matt Waddilove (RS232 Converter Support)
9 | Tim Kent (AUX-T Logging)
10 |
11 | License
12 | =======
13 | Licensed under the Apache License, Version 2.0 (the "License");
14 | you may not use this file except in compliance with the License.
15 | You may obtain a copy of the License at
16 |
17 | http://www.apache.org/licenses/LICENSE-2.0
18 |
19 | Unless required by applicable law or agreed to in writing, software
20 | distributed under the License is distributed on an "AS IS" BASIS,
21 | WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
22 | See the License for the specific language governing permissions and
23 | limitations under the License.
24 |
25 | AdaptiveTuner
26 | =============
27 |
28 | Adaptronic Select ECU Tuning Aid for Android.
29 |
30 | Adaptive Tuner displays key gauge data: RPM, MAP, MAT, WAT, and AFR. It
31 | additionally presents the status of the 6 Adaptive Mode Learning State
32 | flags using a big visual graphic for each, alleviating the need to wire
33 | up LEDs if you use Adaptive Closed Loop for learning.
34 |
--------------------------------------------------------------------------------
/assets/fonts/dash_digital_7.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/assets/fonts/dash_digital_7.ttf
--------------------------------------------------------------------------------
/assets/fonts/digital_7.ttf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/assets/fonts/digital_7.ttf
--------------------------------------------------------------------------------
/ic_launcher-web.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/ic_launcher-web.png
--------------------------------------------------------------------------------
/proguard-project.txt:
--------------------------------------------------------------------------------
1 | # To enable ProGuard in your project, edit project.properties
2 | # to define the proguard.config property as described in that file.
3 | #
4 | # Add project specific ProGuard rules here.
5 | # By default, the flags in this file are appended to flags specified
6 | # in ${sdk.dir}/tools/proguard/proguard-android.txt
7 | # You can edit the include path and order by changing the ProGuard
8 | # include property in project.properties.
9 | #
10 | # For more details, see
11 | # http://developer.android.com/guide/developing/tools/proguard.html
12 |
13 | # Add any project specific keep options here:
14 |
15 | # If your project uses WebView with JS, uncomment the following
16 | # and specify the fully qualified class name to the JavaScript interface
17 | # class:
18 | #-keepclassmembers class fqcn.of.javascript.interface.for.webview {
19 | # public *;
20 | #}
21 |
--------------------------------------------------------------------------------
/project.properties:
--------------------------------------------------------------------------------
1 | # This file is automatically generated by Android Tools.
2 | # Do not modify this file -- YOUR CHANGES WILL BE ERASED!
3 | #
4 | # This file must be checked in Version Control Systems.
5 | #
6 | # To customize properties used by the Ant build system edit
7 | # "ant.properties", and override values to adapt the script to your
8 | # project structure.
9 | #
10 | # To enable ProGuard to shrink and obfuscate your code, uncomment this (available properties: sdk.dir, user.home):
11 | #proguard.config=${sdk.dir}/tools/proguard/proguard-android.txt:proguard-project.txt
12 |
13 | # Project target.
14 | target=android-12
15 |
--------------------------------------------------------------------------------
/res/anim/flipin.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
8 |
--------------------------------------------------------------------------------
/res/anim/flipin_reverse.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
8 |
--------------------------------------------------------------------------------
/res/anim/flipout.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
8 |
--------------------------------------------------------------------------------
/res/anim/flipout_reverse.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
8 |
--------------------------------------------------------------------------------
/res/drawable-hdpi/access_alarms.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/access_alarms.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/action_settings.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/action_settings.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/content_save.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/content_save.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/ic_action_search.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/ic_action_search.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/ic_action_share.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/ic_action_share.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/ic_launcher.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/ic_launcher_gs.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/ic_launcher_gs.png
--------------------------------------------------------------------------------
/res/drawable-hdpi/states_warning.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-hdpi/states_warning.png
--------------------------------------------------------------------------------
/res/drawable-ldpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-ldpi/ic_launcher.png
--------------------------------------------------------------------------------
/res/drawable-ldpi/ic_launcher_gs.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-ldpi/ic_launcher_gs.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/access_alarms.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/access_alarms.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/action_settings.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/action_settings.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/content_save.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/content_save.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/ic_action_search.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/ic_action_search.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/ic_action_share.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/ic_action_share.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/ic_launcher.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/ic_launcher_gs.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/ic_launcher_gs.png
--------------------------------------------------------------------------------
/res/drawable-mdpi/states_warning.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-mdpi/states_warning.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/access_alarms.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/access_alarms.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/action_settings.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/action_settings.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/content_save.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/content_save.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/ic_action_search.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/ic_action_search.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/ic_action_share.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/ic_action_share.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/ic_launcher.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/ic_launcher.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/ic_launcher_gs.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/ic_launcher_gs.png
--------------------------------------------------------------------------------
/res/drawable-xhdpi/states_warning.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable-xhdpi/states_warning.png
--------------------------------------------------------------------------------
/res/drawable/afr.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/afr.png
--------------------------------------------------------------------------------
/res/drawable/afrtwo.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/afrtwo.png
--------------------------------------------------------------------------------
/res/drawable/boost_vac.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/boost_vac.png
--------------------------------------------------------------------------------
/res/drawable/boost_vac_15.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/boost_vac_15.png
--------------------------------------------------------------------------------
/res/drawable/cell_value_widget.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/cell_value_widget.png
--------------------------------------------------------------------------------
/res/drawable/cell_value_widget_big_down.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/cell_value_widget_big_down.png
--------------------------------------------------------------------------------
/res/drawable/cell_value_widget_big_up.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/cell_value_widget_big_up.png
--------------------------------------------------------------------------------
/res/drawable/cell_value_widget_small_down.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/cell_value_widget_small_down.png
--------------------------------------------------------------------------------
/res/drawable/cell_value_widget_small_up.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/cell_value_widget_small_up.png
--------------------------------------------------------------------------------
/res/drawable/digital_background.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
--------------------------------------------------------------------------------
/res/drawable/digital_gauge_gradient_background.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
--------------------------------------------------------------------------------
/res/drawable/iatgauge.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/iatgauge.png
--------------------------------------------------------------------------------
/res/drawable/iatgauge_celsius.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/iatgauge_celsius.png
--------------------------------------------------------------------------------
/res/drawable/iload.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/iload.png
--------------------------------------------------------------------------------
/res/drawable/irpm.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/irpm.png
--------------------------------------------------------------------------------
/res/drawable/iwait.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/iwait.png
--------------------------------------------------------------------------------
/res/drawable/mapgauge.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/mapgauge.png
--------------------------------------------------------------------------------
/res/drawable/needle_middle.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/needle_middle.png
--------------------------------------------------------------------------------
/res/drawable/needle_middle_green.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/needle_middle_green.png
--------------------------------------------------------------------------------
/res/drawable/needle_middle_yellow.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/needle_middle_yellow.png
--------------------------------------------------------------------------------
/res/drawable/needle_offset.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/needle_offset.png
--------------------------------------------------------------------------------
/res/drawable/rectangle_green.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/res/drawable/rectangle_yellow.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/res/drawable/shape_gradient_background.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
--------------------------------------------------------------------------------
/res/drawable/shape_gradient_blue_to_green.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/res/drawable/shape_gradient_green_to_red.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
--------------------------------------------------------------------------------
/res/drawable/shape_gradient_slider.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
8 |
9 |
--------------------------------------------------------------------------------
/res/drawable/shape_textview_border.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
--------------------------------------------------------------------------------
/res/drawable/slider.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/slider.png
--------------------------------------------------------------------------------
/res/drawable/tachometer.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/tachometer.png
--------------------------------------------------------------------------------
/res/drawable/tiny_list_item_border.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
--------------------------------------------------------------------------------
/res/drawable/watertemp.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/res/drawable/watertemp.png
--------------------------------------------------------------------------------
/res/layout-large-port/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout-large-port/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/res/layout-large-port/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/layout-large/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout-large/gauges_tab.xml:
--------------------------------------------------------------------------------
1 |
19 |
26 |
27 |
31 |
32 |
39 |
40 |
49 |
50 |
54 |
55 |
60 |
61 |
62 |
68 |
69 |
70 |
76 |
77 |
78 |
84 |
85 |
92 |
93 |
102 |
103 |
104 |
111 |
112 |
119 |
120 |
126 |
127 |
133 |
134 |
142 |
143 |
144 |
145 |
153 |
154 |
162 |
163 |
171 |
172 |
173 |
181 |
182 |
190 |
191 |
199 |
200 |
201 |
209 |
210 |
218 |
219 |
227 |
228 |
236 |
237 |
238 |
246 |
247 |
255 |
256 |
264 |
265 |
266 |
--------------------------------------------------------------------------------
/res/layout-large/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/res/layout-large/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/layout-port/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout-port/edit_cell_dialog.xml:
--------------------------------------------------------------------------------
1 |
2 |
20 |
26 |
27 |
33 |
34 |
42 |
43 |
51 |
52 |
53 |
54 |
63 |
64 |
--------------------------------------------------------------------------------
/res/layout-port/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
9 |
--------------------------------------------------------------------------------
/res/layout-port/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/layout-xlarge-port/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout-xlarge-port/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/res/layout-xlarge-port/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/layout-xlarge/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout-xlarge/gauges_tab.xml:
--------------------------------------------------------------------------------
1 |
19 |
26 |
27 |
31 |
32 |
37 |
38 |
47 |
48 |
52 |
53 |
58 |
59 |
60 |
66 |
67 |
68 |
74 |
75 |
76 |
82 |
83 |
90 |
91 |
100 |
101 |
102 |
109 |
110 |
118 |
119 |
125 |
126 |
132 |
133 |
141 |
142 |
143 |
144 |
152 |
153 |
162 |
163 |
171 |
172 |
173 |
181 |
182 |
191 |
192 |
200 |
201 |
202 |
210 |
211 |
220 |
221 |
229 |
230 |
238 |
239 |
240 |
248 |
249 |
258 |
259 |
267 |
268 |
269 |
270 |
--------------------------------------------------------------------------------
/res/layout-xlarge/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/res/layout-xlarge/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/layout/activity_main.xml:
--------------------------------------------------------------------------------
1 |
19 |
23 |
24 |
30 |
31 |
37 |
38 |
44 |
45 |
51 |
52 |
60 |
61 |
69 |
70 |
77 |
78 |
79 |
86 |
87 |
88 |
--------------------------------------------------------------------------------
/res/layout/adaptive_grid_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
16 |
17 |
--------------------------------------------------------------------------------
/res/layout/digital_gauge.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
10 |
11 |
20 |
21 |
25 |
26 |
31 |
32 |
38 |
39 |
40 |
41 |
--------------------------------------------------------------------------------
/res/layout/edit_cell_dialog.xml:
--------------------------------------------------------------------------------
1 |
2 |
20 |
26 |
27 |
33 |
34 |
42 |
43 |
49 |
50 |
51 |
52 |
60 |
61 |
62 |
--------------------------------------------------------------------------------
/res/layout/fuel_tab.xml:
--------------------------------------------------------------------------------
1 |
19 |
36 |
37 |
44 |
45 |
53 |
54 |
62 |
63 |
71 |
72 |
73 |
79 |
80 |
86 |
87 |
93 |
94 |
100 |
101 |
109 |
110 |
118 |
119 |
128 |
129 |
--------------------------------------------------------------------------------
/res/layout/gauges_tab.xml:
--------------------------------------------------------------------------------
1 |
19 |
26 |
27 |
31 |
32 |
39 |
40 |
49 |
50 |
54 |
55 |
60 |
61 |
67 |
68 |
74 |
75 |
76 |
83 |
84 |
92 |
93 |
102 |
103 |
104 |
111 |
112 |
119 |
120 |
126 |
127 |
133 |
134 |
142 |
143 |
144 |
145 |
146 |
154 |
155 |
163 |
164 |
172 |
173 |
174 |
182 |
183 |
191 |
192 |
200 |
201 |
202 |
210 |
211 |
219 |
220 |
228 |
229 |
237 |
238 |
239 |
247 |
248 |
256 |
257 |
265 |
266 |
267 |
--------------------------------------------------------------------------------
/res/layout/seekbar.xml:
--------------------------------------------------------------------------------
1 |
2 |
4 |
5 |
7 |
8 |
9 |
10 |
12 |
13 |
14 |
15 |
--------------------------------------------------------------------------------
/res/layout/tiny_list_item.xml:
--------------------------------------------------------------------------------
1 |
2 |
8 |
--------------------------------------------------------------------------------
/res/layout/tiny_list_item_bold.xml:
--------------------------------------------------------------------------------
1 |
2 |
9 |
--------------------------------------------------------------------------------
/res/menu/activity_main.xml:
--------------------------------------------------------------------------------
1 |
19 |
71 |
--------------------------------------------------------------------------------
/res/raw/changelog.txt:
--------------------------------------------------------------------------------
1 |
2 |
3 |
20 |
21 |
22 |
23 | $ 1.2.15
24 | % Adaptive Tuner is governed by the terms of the Apache 2.0 License. You must agree to these terms if you choose to use Adaptive Tuner in any manner whatsoever.
25 |
Version 1.2.15
26 | _ 2015-05-06
27 | ! Going Digital
28 | * Digital Gauges on the Adaptive Tab
29 | $ 1.2.14
30 | _ 2015-04-04
31 | ! Safety Cut
32 | * Added Safety Cut reason to status and log
33 | $ 1.2.13.1
34 | % Version 1.2.13.1
35 | _ 2015-04-02
36 | ! UOM for Pressure
37 | * Fixed UOM calculation for fuel and oil pressure
38 | $ 1.2.13
39 | % Version 1.2.13
40 | _ 2015-04-01
41 | ! UOM for Pressure
42 | * Added UOM selection for fuel and oil pressure
43 | $ 1.2.12
44 | % Version 1.2.12
45 | _ 2015-03-31
46 | ! Fixes for stuff
47 | * Fixed fuel pressure and oil pressure being reversed
48 | * Hardcoded fuel and oil pressure to be in PSI
49 | * Save log on exit / disconnect if one exists
50 | $ 1.2.11
51 | % Version 1.2.11
52 | _ 2015-03-30
53 | ! Initial SSI-4 Support
54 | * SSI-4 support enabled in General Prefs. Fuel and Oil Pressure will display on Adaptive tab
55 | $ 1.2.10
56 | % Version 1.2.10
57 | _ 2015-03-27
58 | ! Boost / Vacuum vs MAP
59 | * Select boost (psi) / vacuum (inhg) gauge instead of MAP kPa in General Prefs
60 | $ 1.2.9
61 | % Version 1.2.9
62 | _ 2015-03-23
63 | ! Swipe and Tach
64 | * You can now swipe between tabs
65 | * Reskinned tachometer
66 | * Fixed various 5.0 issues
67 | * Refactored logger as static
68 | * Explicit intents for startService()
69 | $ 1.2.7
70 | % Version 1.2.7
71 | _ 2014-04-02
72 | ! AUX-T Display & Logging (Long overdue)
73 | * Added logging and display of AUX-T (Tim Kent)
74 | * Added Preference Checkbox for displaying AUX-T on the Adaptive Tab
75 | $ 1.2.6
76 | % Version 1.2.6
77 | _ 2013-08-04
78 | ! Fuel Cut Switch
79 | * Cranking fuel table (initial / unstable)
80 | * Additional RS232 to USB adapters (unstable)
81 | * Fuel cut switch (initial)
82 | * Fuel Cut will currently reset your master fuel trim to ZERO
83 | * Disabled editing for fuel map 2 and crank table (bug)
84 | $ 1.2.5
85 | % Version 1.2.5
86 | _ 2013-06-21
87 | ! Winchiphead CH341 Support
88 | * Integrated Matt Waddilove's RS232 to USB adapter contributions into the Adaptive Tuner main branch
89 | $ 1.2.1
90 | % Version 1.2.1
91 | _ 2013-05-14
92 | ! Fuel Cell Edit Widget TTS Alerts & Digital 7
93 | * Added Android TTS alerts and preferences
94 | * Added cell value modifier widget
95 | * Added Digital 7 font to Adaptive Tab
96 | * Cleaned up positioning on Adaptive Tab
97 | * Enabled Save ECU File (it is buggy - do not use)
98 | * TODO: improve precision for RPM crosshairs
99 | * TODO: more clean up for connect / disconnect logic
100 | $ 1.2.0
101 | % Version 1.2.0
102 | _ 2013-04-09
103 | ! TERMS OF USE & FUEL MAP EDITING
104 | * Added fuel table cell edit capability
105 | * Added redundancy check for updating map values
106 | * Fuel Map crosshairs green for closed loop and yellow for open loop
107 | * TODO: improve precision for RPM crosshairs
108 | * TODO: more clean up for connect / disconnect logic
109 | $ 1.1.11
110 | % Version 1.1.11
111 | _ 2013-04-06
112 | ! Interim Release
113 | * Fixed range of RPM crosshairs on fuel map
114 | * Added check for fuel map type on connect
115 | * Added check for max map value on connect
116 | * Added check for rpm step size on connect
117 | * Added check for tuning mode on connect
118 | * Added radio buttons for fuel map #1 and #2
119 | * Added Knock to log items
120 | * Added Voltage to log items & debug text
121 | * New AFR gauge
122 | * TODO: improve precision for RPM crosshairs
123 | * TODO: add support for variable MAP crosshairs
124 | * TODO: more clean up for connect / disconnect logic
125 | $ 1.1.10
126 | % Version 1.1.10
127 | _ 2013-03-12
128 | ! Fuel Map & Alarms
129 | * Added crosshairs to the fuel map
130 | * Added AFR display to the fuel map
131 | * Added AFR and water meter alarms
132 | * Added alarm to AFR display on the fuel map
133 | $ 1.1.9
134 | % Version 1.1.9
135 | _ 2013-01-20
136 | ! Orientation & Fuel Map
137 | * All kinds of orientation optimizations
138 | * Fuel Map spruced up and nearing completion
139 | * Play Store BackupAgent for Shared Preferences
140 | $ 1.1.8
141 | % Version 1.1.8
142 | _ 2013-01-19
143 | ! Bug Fix
144 | * OTG confirmed as functional
145 | * Low Density display optimizations
146 | * TODO: Finish fuel table
147 | * Pushed to Master
148 | * Honeycomb 3.1+ only
149 | $ 1.1.7
150 | % Version 1.1.7
151 | _ 2013-01-12
152 | ! Bug Fixes & Bulk Logging
153 | * Added Bulk Logging option to Preferences
154 | * Added "USB Connect" to Context Menu
155 | * Fixed AFR Alert Logging bug
156 | * Resized Gauges (layout-large) to better fit N7 density
157 | * Removed Landscape only display restriction
158 | * TODO: Finish fuel table
159 | * Pushed to Master
160 | * Honeycomb 3.1+ only
161 | $ 1.1.6
162 | % Version 1.1.6
163 | _ 2012-11-12
164 | ! Minor Tweaks
165 | * Moved wake lock acquire to service connect and release to disconnect
166 | * Added wake lock option to Preferences
167 | * Added auto-connect on Charge state Preference
168 | * Added TPS Slider gauge
169 | * Fixed Dashboard tab gauge refresh lag
170 | * Created a grayscale icon for foreground notifications
171 | * Fixed spamming auto-reconnects
172 | * Disabled debug logging (oops)
173 | * Honeycomb 3.1+ only
174 | $ 1.1.5
175 | % Version 1.1.5
176 | _ 2012-11-11
177 | ! Service Release (literally)
178 | * Merged to master branch
179 | * Honeycomb 3.1+ only
180 | * All reception logic moved to a stateful service
181 | * Removed fuel map data for now (work in progress)
182 | * Fixed a bug where USB logic was overwriting active Sockets
183 | * Implemented wake lock when MainActivity visible
184 | * Resized the gauges a smidge
185 | * TODO: USB support not verified
186 | * TODO: Add support for duty cycle and ignition maps
187 | * TODO: Add edit capability for maps
188 | $ 1.1.0
189 | % Version 1.1.0
190 | _ 2012-10-11
191 | ! USB Host Mode Connectivity by Evan H. Dekker
192 | * Merged to master branch
193 | * Honeycomb 3.1+ only
194 | * TODO: Add support for duty cycle and ignition maps
195 | * TODO: Add edit capability for maps
196 | $ 1.06
197 | % Version 1.06
198 | _ 2012-10-3
199 | ! 3D Fuel Map!
200 | * Additional data reception logic tuning -- down to 70ms
201 | * Bluetooth RFCOMM discovery & connection improvements for MID PD-10 (and likely other) devices
202 | * Incorporated a trial version of steema's Android charting library to illustrate Fuel Map #1 (must be VE)
203 | * TODO: Add support for duty cycle and ignition maps
204 | * TODO: Add edit capability for maps
205 | % Version 1.05
206 | _ 2012-09-27
207 | ! Faster COMMS!
208 | * Refactored data reception logic -- huge refresh rate boost
209 | * Changed Ignition and Fuel Waiting background colors to (dark) yellow rather than red as they are not error conditions
210 | % Version 1.04
211 | _ 2012-09-24
212 | ! Honeycomb Navigation Tabs!
213 | * Navigation tab framework complete
214 | * Added Gauges Dashboard navigation tab
215 | * Added Automatic Connection on Startup preference
216 | * Remember last tab selected
217 | * Android Lifecycle optimizations
218 | * Normal, Large, and X-Large display optimizations
219 | % Version 1.03
220 | _ 2012-09-15
221 | ! Initial Alarm Logging Implementation
222 | * Added AFR Alarm Logging - You can save and share the resulting log file. Log files are located in /sdcard/AdaptiveTuner and are saved in CSV format.
223 | % Version 1.02
224 | _ 2012-09-14
225 | ! Minor Enhancements
226 | * Redesigned Icon
227 | * Added AFR & Temperature Alerts
228 | * Added Changelog (you're reading it now)
229 | % Version 1.01
230 | _ 2012-09-14
231 | ! UoM
232 | * Added UoM Selection for Temperature
233 | % Version 1.0
234 | _ 2012-09-12
235 | ! Initial Release
236 | * Display Adaptive Learning Statuses
237 | * Display RPM, WAT, MAT, MAP, AFR
238 | % Need more help?
239 | * Adaptive Tuner Homepage
240 | * You can contact me directly at the above URL and you can send me an email at shell@shellware.com
241 | $ END_OF_CHANGE_LOG
242 |
243 |
--------------------------------------------------------------------------------
/res/values-large/dimens.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 | 8dp
21 | 16dp
22 | 16dp
23 |
24 | 10dp
25 | 15dp
26 | 5dp
27 |
28 |
--------------------------------------------------------------------------------
/res/values-v11/styles.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/res/values-xlarge/dimens.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 | 8dp
21 | 16dp
22 | 16dp
23 |
24 | 10dp
25 | 27dp
26 | 7dp
27 |
28 |
--------------------------------------------------------------------------------
/res/values/arrays.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 |
21 |
22 | - Celsius
23 | - Fahrenheit
24 |
26 |
27 |
28 |
29 | - 0
30 | - 1
31 |
33 |
34 |
35 |
36 | - 15 psi
37 | - 30 psi
38 |
39 |
40 |
41 | - 0
42 | - 1
43 |
44 |
45 |
46 | - kPa
47 | - psi
48 |
49 |
50 |
51 | - 0
52 | - 1
53 |
54 |
55 |
56 |
--------------------------------------------------------------------------------
/res/values/attrs.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
--------------------------------------------------------------------------------
/res/values/dimens.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 | 8dp
21 | 8dp
22 | 16dp
23 | 50dp
24 |
25 | 4dp
26 | 7dp
27 | 2dp
28 |
29 |
--------------------------------------------------------------------------------
/res/values/strings.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 |
21 | Adaptive Tuner
22 | Bluetooth Connect
23 | USB Connect
24 | Disconnect
25 | Save ECU File
26 | Debug Info
27 | Fuel Cut
28 | Quit
29 |
30 | Adaptive Tuner
31 | Bluetooth Device List
32 | Ignition Learning
33 | Fuel Learning
34 |
35 | Share AFR Alerts using
36 | Share Log using
37 | Log saved as %s
38 | Share ECU File using
39 |
40 | Adaptive Monitor
41 | Gauges Dashboard
42 | Fuel Map
43 |
44 | Preferences
45 | Adaptive Tuner Preferences
46 | General Preferences
47 |
48 | Unit of Measure
49 | Selected Temperature Unit of Measure
50 | Temperature
51 | Selected Pressure Unit of Measure
52 | Fuel and Oil Pressure
53 |
54 | Connection Settings
55 | Automatic Connection on Startup
56 | Autoconnect on Dock/Charge
57 | Time to wait before Connecting
58 | Keep Device Awake while Connected
59 |
60 | Display Settings
61 | Show AUX-T on Adaptive Tab
62 | Innovate SSI-4 Support
63 |
64 | Alerts & Logging
65 |
66 | Audible Alerts
67 | Android TTS Engine
68 |
69 | MAP Threshold
70 | Intake Temperature Threshold
71 | RPM Threshold
72 | Throttle Position Threshold
73 | Water Temperature Threshold
74 |
75 | Visual AFR Alerts
76 | Actual AFR vs Target AFR
77 | AFR Tolerance
78 | AFR Alert Logging
79 |
80 | Visual Temperature Alerts
81 | Water Temperature
82 | Minimum Water Temperature
83 | Maximum Water Temperature
84 |
85 | General Logging
86 | Log All Data
87 |
88 | Show Boost Gauge instead of MAP
89 | Maximum Boost Pressure
90 |
91 | AFR Gauge
92 | MAP Gauge
93 | Tachometer
94 | Water Temperature Gauge
95 | Intake Temperature Gauge
96 | Throttle
97 |
98 | Edit Fuel Cell
99 |
100 | Enabled
101 | Disabled
102 |
103 | ECU File
104 | Saving
105 |
106 | Fuel Map
107 | Reading map values
108 |
109 | Adaptive Tuner Change Log
110 | What\'s New in Adaptive Tuner
111 | OK
112 |
113 | Adaptive Tuner Connection Service
114 | Connecting to %s. . .
115 | Connected to %s
116 | Connected via USB
117 | Disconnected
118 |
119 | There is no MAP %d for the tuning mode selected
120 |
121 | warning: RPM is %d
122 | warning: map is %d kay pee ay
123 | warning: water temperature is %d degrees
124 | warning: intake temperature is %d degrees
125 | warning: throttle is %d percent open
126 |
127 |
--------------------------------------------------------------------------------
/res/values/styles.xml:
--------------------------------------------------------------------------------
1 |
19 |
20 |
21 |
22 |
--------------------------------------------------------------------------------
/res/xml/device_filter.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
4 |
5 |
6 |
7 |
8 |
9 |
10 |
11 |
12 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/MainActivityBackupAgentHelper.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2013 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner;
18 |
19 | import android.app.backup.BackupAgentHelper;
20 | import android.app.backup.SharedPreferencesBackupHelper;
21 |
22 | public class MainActivityBackupAgentHelper extends BackupAgentHelper {
23 | // The name of the SharedPreferences file
24 | static final String PREFS = "com.shellware.adaptronic.adaptive.tuner_preferences";
25 |
26 | // A key to uniquely identify the set of backup data
27 | static final String PREFS_BACKUP_KEY = "prefs";
28 |
29 | // Allocate a helper and add it to the backup agent
30 | @Override
31 | public void onCreate() {
32 | SharedPreferencesBackupHelper helper = new SharedPreferencesBackupHelper(this, PREFS);
33 | addHelper(PREFS_BACKUP_KEY, helper);
34 | }
35 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/bluetooth/BluetoothConnectThread.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.bluetooth;
18 |
19 | import java.io.IOException;
20 | import java.lang.reflect.Method;
21 | import java.util.UUID;
22 |
23 | import android.bluetooth.BluetoothAdapter;
24 | import android.bluetooth.BluetoothDevice;
25 | import android.bluetooth.BluetoothSocket;
26 | import android.os.Bundle;
27 | import android.os.Handler;
28 | import android.os.Message;
29 |
30 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
31 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger.Level;
32 | import com.shellware.adaptronic.adaptivetuner.services.ConnectionService;
33 |
34 | public class BluetoothConnectThread extends Thread {
35 |
36 | private static final UUID UUID_RFCOMM_GENERIC = UUID.fromString("00001101-0000-1000-8000-00805F9B34FB");
37 |
38 | private final Handler handler;
39 | private final String name;
40 | private final String addr;
41 | private final BluetoothConnectedThread connectedThread;
42 |
43 | private BluetoothAdapter bt = BluetoothAdapter.getDefaultAdapter();
44 | private BluetoothDevice btd;
45 | private BluetoothSocket bts;
46 |
47 | private boolean cancelled;
48 |
49 | public BluetoothConnectThread(final Handler handler, final String deviceName, final String addr, BluetoothConnectedThread connectedThread) {
50 | super();
51 | this.handler = handler;
52 | this.name = deviceName;
53 | this.addr = addr;
54 | this.connectedThread = connectedThread;
55 | }
56 |
57 | @Override
58 | public void run() {
59 |
60 | Bundle b = new Bundle();
61 | Message msg = new Message();
62 |
63 | int counter = 0;
64 |
65 | while (true) {
66 |
67 | // bail if cancelled
68 | if (cancelled) return;
69 |
70 | try {
71 | btd = bt.getRemoteDevice(addr);
72 |
73 | } catch (Exception ex) {
74 | // bail if cancelled
75 | if (cancelled) return;
76 |
77 | AdaptiveLogger.log(Level.ERROR, "bluetooth adapter error: " + ex.getMessage());
78 | }
79 |
80 | try {
81 | if (counter < 3) {
82 | AdaptiveLogger.log("Trying createRfcommSocketToServiceRecord");
83 | bts = btd.createRfcommSocketToServiceRecord(UUID_RFCOMM_GENERIC);
84 | } else {
85 | if (counter < 6) {
86 | AdaptiveLogger.log("Trying createInsecureRfcommSocketToServiceRecord");
87 | bts = btd.createInsecureRfcommSocketToServiceRecord(UUID_RFCOMM_GENERIC);
88 | } else {
89 | if (counter < 9) {
90 | AdaptiveLogger.log("Trying createInsecureRfcommSocket");
91 | Method m = btd.getClass().getMethod("createInsecureRfcommSocket", new Class[] { int.class });
92 | bts = (BluetoothSocket) m.invoke(btd, Integer.valueOf(1)); // 1==RFCOMM channel cod (class of device)
93 | } else {
94 | AdaptiveLogger.log("Trying createRfcommSocket");
95 | Method m = btd.getClass().getMethod("createRfcommSocket", new Class[] {int.class});
96 | bts = (BluetoothSocket) m.invoke(btd, Integer.valueOf(1));
97 | }
98 | }
99 | }
100 | } catch (Exception ex) {
101 | if (cancelled) return;
102 | AdaptiveLogger.log(Level.ERROR, "createRfcommSocket failed: " + ex.getMessage());
103 | }
104 |
105 | try {
106 | bt.cancelDiscovery();
107 | bts.connect();
108 | break;
109 | } catch (Exception e) {
110 | // bail if cancelled
111 | if (cancelled) return;
112 |
113 | counter++;
114 | AdaptiveLogger.log(Level.ERROR, "BT connect failed: " + e.getMessage());
115 |
116 | // bail if we've tried 15 times
117 | if (counter >= 15) {
118 |
119 | b.putShort("handle", ConnectionService.CONNECTION_ERROR);
120 | b.putString("title", name);
121 | b.putString("message", String.format("Unable to connect to %s: %s", name.trim(), e.getMessage()));
122 | msg.setData(b);
123 |
124 | AdaptiveLogger.log(Level.ERROR, "Unable to connect - " + e.getMessage());
125 | handler.sendMessage(msg);
126 | return;
127 | }
128 | }
129 | }
130 |
131 | connectedThread.setSocket(bts);
132 | connectedThread.start();
133 |
134 | b.putShort("handle", ConnectionService.CONNECTED);
135 | b.putString("name", name);
136 | b.putString("addr", addr);
137 |
138 | msg.setData(b);
139 |
140 | AdaptiveLogger.log(Level.INFO, "BT Connected");
141 | handler.sendMessage(msg);
142 | }
143 |
144 | public void cancel() {
145 | cancelled = true;
146 | AdaptiveLogger.log("Connect Thread Canceled");
147 |
148 | if (bts != null) {
149 | try {
150 | bts.close();
151 | } catch (IOException e) {
152 | // do nothing
153 | }
154 | }
155 |
156 | this.interrupt();
157 | }
158 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/bluetooth/BluetoothConnectedThread.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.bluetooth;
18 |
19 | import java.io.IOException;
20 | import java.io.InputStream;
21 | import java.io.OutputStream;
22 | import java.util.Locale;
23 |
24 | import android.bluetooth.BluetoothSocket;
25 | import android.os.Bundle;
26 | import android.os.Handler;
27 | import android.os.Message;
28 |
29 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
30 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger.Level;
31 | import com.shellware.adaptronic.adaptivetuner.modbus.ConnectedThread;
32 | import com.shellware.adaptronic.adaptivetuner.services.ConnectionService;
33 |
34 | public class BluetoothConnectedThread extends ConnectedThread {
35 |
36 | public BluetoothConnectedThread(Handler handler) {
37 | super(handler);
38 | }
39 |
40 | private BluetoothSocket mmSocket;
41 | private InputStream mmInStream;
42 | private OutputStream mmOutStream;
43 |
44 |
45 | private String name;
46 |
47 | public void setSocket(BluetoothSocket socket) {
48 | mmSocket = socket;
49 |
50 | try {
51 | mmInStream = socket.getInputStream();
52 | mmOutStream = socket.getOutputStream();
53 | } catch (IOException e) { }
54 | }
55 |
56 | public void run() {
57 | byte[] buffer = new byte[512]; // buffer store for the stream
58 | int bytes; // bytes returned from read()
59 |
60 | // Keep listening to the InputStream until an exception or cancel occurs
61 | while (!disconnecting) {
62 | try {
63 | // Read from the InputStream
64 | bytes = mmInStream.read(buffer);
65 |
66 | AdaptiveLogger.log(String.format(Locale.US, "Received %d bytes", bytes));
67 |
68 | // Send the obtained bytes to the UI activity
69 | Bundle b = new Bundle();
70 |
71 | b.putShort("handle", ConnectionService.DATA_READY);
72 | b.putByteArray("data", buffer);
73 | b.putInt("length", bytes);
74 |
75 | Message msg = new Message();
76 | msg.setData(b);
77 |
78 | handler.sendMessage(msg);
79 |
80 | } catch (IOException e) {
81 | if (disconnecting) break;
82 |
83 | Bundle b = new Bundle();
84 |
85 | b.putShort("handle", ConnectionService.CONNECTION_ERROR);
86 | b.putString("title", name);
87 | b.putString("message", "Connection lost");
88 |
89 | Message msg = new Message();
90 | msg.setData(b);
91 |
92 | AdaptiveLogger.log(Level.ERROR, "Connection lost on read - " + e.getMessage());
93 |
94 | handler.sendMessage(msg);
95 | break;
96 | }
97 | }
98 | }
99 |
100 | /* Call this from the main activity to send data to the remote device */
101 | public void write(byte[] bytes) {
102 | try {
103 | mmOutStream.write(bytes);
104 | mmOutStream.flush();
105 | } catch (IOException e) {
106 | if (disconnecting) return;
107 |
108 | Bundle b = new Bundle();
109 |
110 | b.putShort("handle", ConnectionService.CONNECTION_ERROR);
111 | b.putString("title", name);
112 | b.putString("message", "Connection lost");
113 |
114 | Message msg = new Message();
115 | msg.setData(b);
116 |
117 | AdaptiveLogger.log(Level.ERROR, "Connection lost on write - " + e.getMessage());
118 | handler.sendMessage(msg);
119 | }
120 | }
121 |
122 | /* Call this from the main activity to shutdown the connection */
123 | public void cancel() {
124 | disconnecting = true;
125 |
126 | AdaptiveLogger.log("BT Connected Thread Canceled");
127 |
128 | if (mmInStream != null) {
129 | try {mmInStream.close();} catch (Exception e) {}
130 | mmInStream = null;
131 | }
132 |
133 | if (mmOutStream != null) {
134 | try {mmOutStream.close();} catch (Exception e) {}
135 | mmOutStream = null;
136 | }
137 |
138 | if (mmSocket != null) {
139 | try {mmSocket.close();} catch (Exception e) {}
140 | mmSocket = null;
141 | }
142 | }
143 | }
144 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/changelog/ChangeLog.java:
--------------------------------------------------------------------------------
1 | /**
2 | * ChangeLog.java
3 | *
4 | * Copyright (C) 2011, Karsten Priegnitz
5 | *
6 | * Permission to use, copy, modify, and distribute this software for any
7 | * purpose with or without fee is hereby granted, provided that the above
8 | * copyright notice and this permission notice appear in all copies.
9 | *
10 | * @author: Karsten Priegnitz
11 | * @see: http://code.google.com/p/android-change-log/
12 | */
13 |
14 | package com.shellware.adaptronic.adaptivetuner.changelog;
15 |
16 | import java.io.BufferedReader;
17 | import java.io.IOException;
18 | import java.io.InputStream;
19 | import java.io.InputStreamReader;
20 |
21 | import android.app.AlertDialog;
22 | import android.content.Context;
23 | import android.content.DialogInterface;
24 | import android.content.SharedPreferences;
25 | import android.content.pm.PackageManager.NameNotFoundException;
26 | import android.graphics.Color;
27 | import android.preference.PreferenceManager;
28 | import android.util.Log;
29 | import android.webkit.WebView;
30 |
31 | import com.shellware.adaptronic.adaptive.tuner.R;
32 |
33 | public class ChangeLog {
34 |
35 | private final Context context;
36 | private String lastVersion, thisVersion;
37 |
38 | // this is the key for storing the version name in SharedPreferences
39 | private static final String VERSION_KEY = "PREFS_VERSION_KEY";
40 |
41 | /**
42 | * Constructor
43 | *
44 | * Retrieves the version names and stores the new version name in
45 | * SharedPreferences
46 | */
47 | public ChangeLog(Context context) {
48 | this.context = context;
49 |
50 | SharedPreferences sp = PreferenceManager
51 | .getDefaultSharedPreferences(context);
52 |
53 | // get version numbers
54 | this.lastVersion = sp.getString(VERSION_KEY, "");
55 | Log.d(TAG, "lastVersion: " + lastVersion);
56 | try {
57 | this.thisVersion = context.getPackageManager().getPackageInfo(
58 | context.getPackageName(), 0).versionName;
59 | } catch (NameNotFoundException e) {
60 | this.thisVersion = "?";
61 | Log.e(TAG, "could not get version name from manifest!");
62 | e.printStackTrace();
63 | }
64 | Log.d(TAG, "appVersion: " + this.thisVersion);
65 |
66 | // save new version number to preferences
67 | SharedPreferences.Editor editor = sp.edit();
68 | editor.putString(VERSION_KEY, this.thisVersion);
69 | editor.commit();
70 | }
71 |
72 | /**
73 | * @return The version name of the last installation of this app (as
74 | * described in the former manifest). This will be the same as
75 | * returned by getThisVersion()
from the second time
76 | * this version of the app is launched (more precisely: the
77 | * second time ChangeLog is instantiated).
78 | * @see AndroidManifest.xml#android:versionName
79 | */
80 | public String getLastVersion() {
81 | return this.lastVersion;
82 | }
83 |
84 | /**
85 | * manually set the last version name - for testing purposes only
86 | * @param lastVersion
87 | */
88 | void setLastVersion(String lastVersion) {
89 | this.lastVersion = lastVersion;
90 | }
91 |
92 | /**
93 | * @return The version name of this app as described in the manifest.
94 | * @see AndroidManifest.xml#android:versionName
95 | */
96 | public String getThisVersion() {
97 | return this.thisVersion;
98 | }
99 |
100 | /**
101 | * @return true
if this version of your app is started the
102 | * first time
103 | */
104 | public boolean firstRun() {
105 | return ! this.lastVersion.equals(this.thisVersion);
106 | }
107 |
108 | /**
109 | * @return true
if your app is started the first time ever.
110 | * Also true
if your app was deinstalled and
111 | * installed again.
112 | */
113 | public boolean firstRunEver() {
114 | return "".equals(this.lastVersion);
115 | }
116 |
117 | /**
118 | * @return an AlertDialog displaying the changes since the previous
119 | * installed version of your app (what's new).
120 | */
121 | public AlertDialog getLogDialog() {
122 | return this.getDialog(false);
123 | }
124 |
125 | /**
126 | * @return an AlertDialog with a full change log displayed
127 | */
128 | public AlertDialog getFullLogDialog() {
129 | return this.getDialog(true);
130 | }
131 |
132 | private AlertDialog getDialog(boolean full) {
133 |
134 | WebView wv = new WebView(this.context);
135 | // wv.setBackgroundColor(color.background_dark); // transparent
136 | wv.setBackgroundColor(Color.BLACK);
137 | wv.loadData(this.getLog(full), "text/html", "UTF-8");
138 |
139 | AlertDialog.Builder builder = new AlertDialog.Builder(this.context);
140 | builder.setTitle(context.getResources().getString(
141 | full
142 | ? R.string.changelog_full_title
143 | : R.string.changelog_title))
144 | .setView(wv)
145 | .setCancelable(false)
146 | .setPositiveButton(
147 | context.getResources().getString(
148 | R.string.changelog_ok_button),
149 | new DialogInterface.OnClickListener() {
150 | public void onClick(DialogInterface dialog, int id) {
151 | dialog.cancel();
152 | }
153 | });
154 | return builder.create();
155 | }
156 |
157 | /**
158 | * @return HTML displaying the changes since the previous
159 | * installed version of your app (what's new)
160 | */
161 | public String getLog() {
162 | return this.getLog(false);
163 | }
164 |
165 | /**
166 | * @return HTML which displays full change log
167 | */
168 | public String getFullLog() {
169 | return this.getLog(true);
170 | }
171 |
172 | /** modes for HTML-Lists (bullet, numbered) */
173 | private enum Listmode {
174 | NONE,
175 | ORDERED,
176 | UNORDERED,
177 | };
178 | private Listmode listMode = Listmode.NONE;
179 | private StringBuffer sb = null;
180 | private static final String EOCL = "END_OF_CHANGE_LOG";
181 |
182 | private String getLog(boolean full) {
183 | // read changelog.txt file
184 | sb = new StringBuffer();
185 | try {
186 | InputStream ins = context.getResources().openRawResource(
187 | R.raw.changelog);
188 | BufferedReader br = new BufferedReader(new InputStreamReader(ins));
189 |
190 | String line = null;
191 | boolean advanceToEOVS = false; // true = ignore further version sections
192 | while (( line = br.readLine()) != null){
193 | line = line.trim();
194 | if (line.startsWith("$")) {
195 | // begin of a version section
196 | this.closeList();
197 | String version = line.substring(1).trim();
198 | // stop output?
199 | if (! full) {
200 | if (this.lastVersion.equals(version))
201 | advanceToEOVS = true;
202 | else if (version.equals(EOCL))
203 | advanceToEOVS = false;
204 | }
205 | } else if (! advanceToEOVS) {
206 | if (line.startsWith("%")) {
207 | // line contains version title
208 | this.closeList();
209 | sb.append(""
210 | + line.substring(1).trim() + "
\n");
211 | } else if (line.startsWith("_")) {
212 | // line contains version title
213 | this.closeList();
214 | sb.append(""
215 | + line.substring(1).trim() + "
\n");
216 | } else if (line.startsWith("!")) {
217 | // line contains free text
218 | this.closeList();
219 | sb.append(""
220 | + line.substring(1).trim() + "
\n");
221 | } else if (line.startsWith("#")) {
222 | // line contains numbered list item
223 | this.openList(Listmode.ORDERED);
224 | sb.append(""
225 | + line.substring(1).trim() + "\n");
226 | } else if (line.startsWith("*")) {
227 | // line contains bullet list item
228 | this.openList(Listmode.UNORDERED);
229 | sb.append(""
230 | + line.substring(1).trim() + "\n");
231 | } else {
232 | // no special character: just use line as is
233 | this.closeList();
234 | sb.append(line + "\n");
235 | }
236 | }
237 | }
238 | this.closeList();
239 | br.close();
240 | } catch (IOException e) {
241 | e.printStackTrace();
242 | }
243 |
244 | return sb.toString();
245 | }
246 |
247 | private void openList(Listmode listMode) {
248 | if (this.listMode != listMode) {
249 | closeList();
250 | if (listMode == Listmode.ORDERED) {
251 | sb.append("\n");
252 | } else if (listMode == Listmode.UNORDERED) {
253 | sb.append("\n");
254 | }
255 | this.listMode = listMode;
256 | }
257 | }
258 | private void closeList() {
259 | if (this.listMode == Listmode.ORDERED) {
260 | sb.append("
\n");
261 | } else if (this.listMode == Listmode.UNORDERED) {
262 | sb.append("
\n");
263 | }
264 | this.listMode = Listmode.NONE;
265 | }
266 |
267 | private static final String TAG = "ChangeLog";
268 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/fragments/AdaptiveFragment.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.fragments;
18 |
19 | import android.app.Fragment;
20 | import android.os.Bundle;
21 | import android.view.LayoutInflater;
22 | import android.view.View;
23 | import android.view.ViewGroup;
24 |
25 | import com.shellware.adaptronic.adaptive.tuner.R;
26 |
27 | public class AdaptiveFragment extends Fragment {
28 |
29 | private View myView;
30 |
31 | @Override
32 | public void onActivityCreated(Bundle savedInstanceState) {
33 | super.onActivityCreated(savedInstanceState);
34 | }
35 |
36 | @Override
37 | public View onCreateView(LayoutInflater inflater, ViewGroup container,
38 | Bundle savedInstanceState) {
39 |
40 | myView = inflater.inflate(R.layout.adaptive_tab, null);
41 |
42 | return myView;
43 | }
44 |
45 | }
46 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/fragments/FuelFragment.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.fragments;
18 |
19 | import android.app.Fragment;
20 | import android.os.Bundle;
21 | import android.view.LayoutInflater;
22 | import android.view.View;
23 | import android.view.ViewGroup;
24 |
25 | import com.shellware.adaptronic.adaptive.tuner.R;
26 |
27 | public class FuelFragment extends Fragment {
28 |
29 | private View myView;
30 |
31 | @Override
32 | public void onActivityCreated(Bundle savedInstanceState) {
33 | super.onActivityCreated(savedInstanceState);
34 | }
35 |
36 | @Override
37 | public View onCreateView(LayoutInflater inflater, ViewGroup container,
38 | Bundle savedInstanceState) {
39 |
40 | myView = inflater.inflate(R.layout.fuel_tab, null);
41 |
42 | return myView;
43 | }
44 |
45 | }
46 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/fragments/GaugesFragment.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.fragments;
18 |
19 | import android.app.Fragment;
20 | import android.os.Bundle;
21 | import android.view.LayoutInflater;
22 | import android.view.View;
23 | import android.view.ViewGroup;
24 |
25 | import com.shellware.adaptronic.adaptive.tuner.R;
26 |
27 | public class GaugesFragment extends Fragment {
28 |
29 | private View myView;
30 |
31 | @Override
32 | public void onActivityCreated(Bundle savedInstanceState) {
33 | super.onActivityCreated(savedInstanceState);
34 | }
35 |
36 | @Override
37 | public View onCreateView(LayoutInflater inflater, ViewGroup container,
38 | Bundle savedInstanceState) {
39 |
40 | myView = inflater.inflate(R.layout.gauges_tab, null);
41 |
42 | return myView;
43 | }
44 |
45 | }
46 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/logging/AdaptiveLogger.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2013 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.logging;
18 |
19 | import android.util.Log;
20 |
21 | public final class AdaptiveLogger {
22 |
23 | private AdaptiveLogger() {
24 | super();
25 | }
26 |
27 | public static enum Level {
28 | DEBUG,
29 | INFO,
30 | ERROR,
31 | NONE
32 | }
33 |
34 | public static final Level DEFAULT_LEVEL = Level.DEBUG;
35 | public static final String DEFAULT_TAG = "Adaptive";
36 |
37 | // set releaseVersion to true when releasing Adaptive Tuner
38 | // to Google Play
39 | private static boolean releaseVersion = true;
40 |
41 | private static Level level = DEFAULT_LEVEL;
42 | private static String tag = DEFAULT_TAG;
43 | //
44 | // public AdaptiveLogger() {
45 | // }
46 |
47 | public static void log(String msg) {
48 | log(level, tag, msg);
49 | }
50 |
51 | public static void log(String tag, String msg) {
52 | log(level, tag, msg);
53 | }
54 |
55 | public static void log(Level level, String msg) {
56 | log(level, tag, msg);
57 | }
58 |
59 | public static void log(Level level, String tag, String msg) {
60 |
61 | if (releaseVersion) return;
62 |
63 | switch (level) {
64 | case DEBUG:
65 | Log.d(tag, msg);
66 | break;
67 |
68 | case INFO:
69 | Log.i(tag, msg);
70 | break;
71 |
72 | case ERROR:
73 | Log.e(tag, msg);
74 | break;
75 |
76 | default:
77 | }
78 | }
79 |
80 | /**
81 | * @return the level
82 | */
83 | public Level getLevel() {
84 | return level;
85 | }
86 |
87 | /**
88 | * @param level the level to set
89 | */
90 | public void setLevel(Level level) {
91 | AdaptiveLogger.level = level;
92 | }
93 |
94 | /**
95 | * @return the tag
96 | */
97 | public String getTag() {
98 | return tag;
99 | }
100 |
101 | /**
102 | * @param tag the tag to set
103 | */
104 | public void setTag(String tag) {
105 | AdaptiveLogger.tag = tag;
106 | }
107 | }
108 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/modbus/ConnectedThread.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.modbus;
2 |
3 | import android.os.Handler;
4 |
5 | abstract public class ConnectedThread extends Thread {
6 |
7 | abstract public void write(byte[] bytes);
8 | abstract public void cancel();
9 | abstract public void run();
10 |
11 | protected Handler handler;
12 | protected boolean disconnecting = false;
13 |
14 | public ConnectedThread(Handler handler) {
15 | this.handler = handler;
16 | }
17 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/modbus/ModbusRTU.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.modbus;
18 |
19 | import java.nio.ByteBuffer;
20 | import java.nio.ByteOrder;
21 |
22 | public class ModbusRTU {
23 |
24 | public static final byte[] getRegister(final byte slaveAddr, final byte function, final short register) {
25 | return getRegister(slaveAddr, function, register, (short) 1);
26 | }
27 | public static final byte[] getRegister(final byte slaveAddr, final byte function, final short register, final short count) {
28 | // convert our register into a 2 byte array -- (16 bit short integer)
29 | ByteBuffer rr = ByteBuffer.allocate(2);
30 | rr.order(ByteOrder.BIG_ENDIAN);
31 | rr.putShort(register);
32 | byte[] r = rr.array();
33 |
34 | // convert our count into a 2 byte array - (16 bit short integer)
35 | ByteBuffer cc = ByteBuffer.allocate(2);
36 | cc.order(ByteOrder.BIG_ENDIAN);
37 | cc.putShort(count);
38 | byte[] c = cc.array();
39 |
40 | final byte[] message = { slaveAddr, function, r[0], r[1], c[0], c[1], 0x00, 0x00 };
41 | int[] crc = ModbusRTU.getCRC(message, message.length - 2);
42 |
43 | message[message.length - 2] = (byte) crc[0];
44 | message[message.length - 1] = (byte) crc[1];
45 |
46 | return message;
47 | }
48 |
49 | public static final boolean validCRC(final String[] msg, final int length) {
50 |
51 | // discard short messages
52 | if (msg.length < length) return false;
53 |
54 | byte[] buf = new byte[512];
55 |
56 | for (int x = 0; x < length - 2; x++) {
57 | buf[x] = (byte) Integer.parseInt(msg[x], 16);
58 | }
59 |
60 | final int[] crc = ModbusRTU.getCRC(buf, length - 2);
61 | final int crc0 = Integer.parseInt(msg[length - 2], 16);
62 | final int crc1 = Integer.parseInt(msg[length - 1], 16);
63 |
64 | final boolean res = (crc[0] == crc0 && crc[1] == crc1);
65 |
66 | return res;
67 | }
68 |
69 | // !!!!!!!!!!!!! NOTE !!!!!!!!!!!!!
70 | // GNU GPL applies to following
71 | // code only.
72 | // !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
73 |
74 | /***
75 | * Java Modbus Scanner Copyright (c) 2009, Andrzej Sokulski andrzej@modbus.pl -
76 | * www.modbus.pl All rights reserved.
77 | *
78 | *
79 | * This software is free you can redistribute it and/or modify it under the
80 | * terms of the GNU Lesser General Public License as published by the Free
81 | * Software Foundation; either version 2.1 of the License, or (at your option)
82 | * any later version.
83 | *
84 | * This software is distributed in the hope that it will be useful, but WITHOUT
85 | * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
86 | * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
87 | * details. In no event shall the regents or contributors be liable for any
88 | * direct, indirect, incidential, special, exemplary, or consequential damages.
89 | *
90 | * If you want to remove the copyright notice, please donate me
91 | * (www.modbus.pl/donate.html).
92 | */
93 | public static final int[] getCRC(byte[] buffer, int length) {
94 |
95 | int[] crc = { 0xFF, 0xFF };
96 | int nextVal = 0;
97 | int index;
98 | if (length <= buffer.length)
99 |
100 | for (int i = 0; i < length; i++) {
101 | nextVal = 0xFF & ((int) buffer[i]);
102 | index = crc[0] ^ nextVal;
103 | crc[0] = crc[1] ^ CRCHigh[index];
104 | crc[1] = CRCLow[index];
105 | }
106 |
107 | return crc;
108 | }
109 |
110 | /* Hogh Table of CRC values */
111 | private final static short[] CRCHigh = { 0x00, 0xC1, 0x81, 0x40, 0x01,
112 | 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
113 | 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81,
114 | 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,
115 | 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00,
116 | 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41,
117 | 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
118 | 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,
119 | 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00,
120 | 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
121 | 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80,
122 | 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0,
123 | 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00,
124 | 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40,
125 | 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81,
126 | 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0,
127 | 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00,
128 | 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41,
129 | 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01, 0xC0, 0x80,
130 | 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1,
131 | 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80, 0x41, 0x01,
132 | 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x00, 0xC1, 0x81, 0x40,
133 | 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40, 0x01, 0xC0, 0x80,
134 | 0x41, 0x01, 0xC0, 0x80, 0x41, 0x00, 0xC1, 0x81, 0x40 };
135 |
136 | /* Low Table of CRC values */
137 | private final static short[] CRCLow = { 0x00, 0xC0, 0xC1, 0x01, 0xC3, 0x03,
138 | 0x02, 0xC2, 0xC6, 0x06, 0x07, 0xC7, 0x05, 0xC5, 0xC4, 0x04, 0xCC,
139 | 0x0C, 0x0D, 0xCD, 0x0F, 0xCF, 0xCE, 0x0E, 0x0A, 0xCA, 0xCB, 0x0B,
140 | 0xC9, 0x09, 0x08, 0xC8, 0xD8, 0x18, 0x19, 0xD9, 0x1B, 0xDB, 0xDA,
141 | 0x1A, 0x1E, 0xDE, 0xDF, 0x1F, 0xDD, 0x1D, 0x1C, 0xDC, 0x14, 0xD4,
142 | 0xD5, 0x15, 0xD7, 0x17, 0x16, 0xD6, 0xD2, 0x12, 0x13, 0xD3, 0x11,
143 | 0xD1, 0xD0, 0x10, 0xF0, 0x30, 0x31, 0xF1, 0x33, 0xF3, 0xF2, 0x32,
144 | 0x36, 0xF6, 0xF7, 0x37, 0xF5, 0x35, 0x34, 0xF4, 0x3C, 0xFC, 0xFD,
145 | 0x3D, 0xFF, 0x3F, 0x3E, 0xFE, 0xFA, 0x3A, 0x3B, 0xFB, 0x39, 0xF9,
146 | 0xF8, 0x38, 0x28, 0xE8, 0xE9, 0x29, 0xEB, 0x2B, 0x2A, 0xEA, 0xEE,
147 | 0x2E, 0x2F, 0xEF, 0x2D, 0xED, 0xEC, 0x2C, 0xE4, 0x24, 0x25, 0xE5,
148 | 0x27, 0xE7, 0xE6, 0x26, 0x22, 0xE2, 0xE3, 0x23, 0xE1, 0x21, 0x20,
149 | 0xE0, 0xA0, 0x60, 0x61, 0xA1, 0x63, 0xA3, 0xA2, 0x62, 0x66, 0xA6,
150 | 0xA7, 0x67, 0xA5, 0x65, 0x64, 0xA4, 0x6C, 0xAC, 0xAD, 0x6D, 0xAF,
151 | 0x6F, 0x6E, 0xAE, 0xAA, 0x6A, 0x6B, 0xAB, 0x69, 0xA9, 0xA8, 0x68,
152 | 0x78, 0xB8, 0xB9, 0x79, 0xBB, 0x7B, 0x7A, 0xBA, 0xBE, 0x7E, 0x7F,
153 | 0xBF, 0x7D, 0xBD, 0xBC, 0x7C, 0xB4, 0x74, 0x75, 0xB5, 0x77, 0xB7,
154 | 0xB6, 0x76, 0x72, 0xB2, 0xB3, 0x73, 0xB1, 0x71, 0x70, 0xB0, 0x50,
155 | 0x90, 0x91, 0x51, 0x93, 0x53, 0x52, 0x92, 0x96, 0x56, 0x57, 0x97,
156 | 0x55, 0x95, 0x94, 0x54, 0x9C, 0x5C, 0x5D, 0x9D, 0x5F, 0x9F, 0x9E,
157 | 0x5E, 0x5A, 0x9A, 0x9B, 0x5B, 0x99, 0x59, 0x58, 0x98, 0x88, 0x48,
158 | 0x49, 0x89, 0x4B, 0x8B, 0x8A, 0x4A, 0x4E, 0x8E, 0x8F, 0x4F, 0x8D,
159 | 0x4D, 0x4C, 0x8C, 0x44, 0x84, 0x85, 0x45, 0x87, 0x47, 0x46, 0x86,
160 | 0x82, 0x42, 0x43, 0x83, 0x41, 0x81, 0x80, 0x40 };
161 |
162 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/preferences/SeekBarPreference.java:
--------------------------------------------------------------------------------
1 | /* The following code was originally written by Matthew Wiggins
2 | * and later refactored by Shell M. Shrader
3 | * It is released under the APACHE 2.0 license
4 | *
5 | * http://www.apache.org/licenses/LICENSE-2.0
6 | */
7 | package com.shellware.adaptronic.adaptivetuner.preferences;
8 |
9 | import java.util.Locale;
10 |
11 | import android.content.Context;
12 | import android.preference.DialogPreference;
13 | import android.view.View;
14 | import android.widget.SeekBar;
15 | import android.widget.TextView;
16 |
17 | import com.shellware.adaptronic.adaptive.tuner.R;
18 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
19 |
20 | public class SeekBarPreference extends DialogPreference implements SeekBar.OnSeekBarChangeListener {
21 |
22 | private float startingValue = 0;
23 | private float barValue = 0;
24 | private float displayValue = 0;
25 | private String suffix = "";
26 | private float minValue = 0;
27 | private float maxValue = 0;
28 | private float scale = 1;
29 |
30 | @SuppressWarnings("unused")
31 | private Context ctx;
32 |
33 | private TextView splashTextView;
34 | private TextView valueTextView;
35 | private SeekBar seekBarView;
36 |
37 | public SeekBarPreference(Context context) {
38 | super(context, null);
39 | this.ctx = context;
40 | }
41 |
42 | @Override
43 | protected View onCreateDialogView() {
44 | setDialogLayoutResource(R.layout.seekbar);
45 | return super.onCreateDialogView();
46 | }
47 |
48 | @Override
49 | protected void onBindDialogView(View view) {
50 |
51 | seekBarView = (SeekBar) view.findViewById(R.id.seek);
52 | seekBarView.setMax( (int) ((maxValue - minValue) / scale));
53 | seekBarView.setProgress((int) barValue);
54 | seekBarView.setOnSeekBarChangeListener(this);
55 |
56 | valueTextView = (TextView) view.findViewById(R.id.currentValue);
57 | valueTextView.setText(String.format("%.2f%s", displayValue, suffix));
58 |
59 | splashTextView = (TextView) view.findViewById(R.id.splashText);
60 | splashTextView.setText(getTitle());
61 |
62 | AdaptiveLogger.log("SeekbarPreference bound");
63 | super.onBindDialogView(view);
64 | }
65 |
66 | public void onProgressChanged(SeekBar arg0, int progress, boolean fromUser) {
67 | barValue = progress;
68 | displayValue = barValue * scale + minValue;
69 | valueTextView.setText(String.format("%.2f%s", displayValue, suffix));
70 | AdaptiveLogger.log(String.format(Locale.US, "SeekbarPreference changed value %.2f/%.2f", displayValue, barValue));
71 | }
72 |
73 | @Override
74 | protected void onDialogClosed(boolean positiveResult) {
75 | if (positiveResult) {
76 | callChangeListener(displayValue);
77 | startingValue = displayValue;
78 | AdaptiveLogger.log(String.format(Locale.US, "SeekbarPreference close positive value %.2f/%.2f", displayValue, barValue));
79 | } else {
80 |
81 | displayValue = startingValue;
82 | barValue = (displayValue - minValue) / scale;
83 | seekBarView.setProgress((int) barValue);
84 |
85 | AdaptiveLogger.log(String.format(Locale.US, "SeekbarPreference close negative value %.2f/%.2f", displayValue, barValue));
86 | }
87 | super.onDialogClosed(positiveResult);
88 | }
89 |
90 | public void onStartTrackingTouch(SeekBar arg0) {}
91 | public void onStopTrackingTouch(SeekBar arg0) {}
92 |
93 | @Override
94 | protected void onSetInitialValue(boolean restorePersistedValue, Object defaultValue) {
95 | super.onSetInitialValue(restorePersistedValue, defaultValue);
96 | displayValue = (Float) defaultValue;
97 | barValue = (displayValue - minValue) / scale;
98 | startingValue = displayValue;
99 |
100 | AdaptiveLogger.log(String.format(Locale.US, "SeekbarPreference initial value %.2f/%.2f", displayValue, barValue));
101 | }
102 |
103 | public void setMinValue(float minValue) {
104 | this.minValue = minValue;
105 | }
106 |
107 | public void setMaxValue(float maxValue) {
108 | this.maxValue = maxValue;
109 | }
110 |
111 | public void setScale(float scale) {
112 | this.scale = scale;
113 | }
114 |
115 | public void setSuffix(String suffix) {
116 | this.suffix = suffix;
117 | }
118 | }
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/receivers/BatteryStatusReceiver.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.receivers;
18 |
19 | import android.content.BroadcastReceiver;
20 | import android.content.Context;
21 | import android.content.Intent;
22 | import android.content.SharedPreferences;
23 | import android.content.SharedPreferences.Editor;
24 | import android.os.BatteryManager;
25 | import android.os.Handler;
26 | import android.preference.PreferenceManager;
27 |
28 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
29 | import com.shellware.adaptronic.adaptivetuner.services.ConnectionService;
30 |
31 | public class BatteryStatusReceiver extends BroadcastReceiver {
32 |
33 | private final static int BATTERY_PLUGGED_UNPLUGGED = 0;
34 |
35 | @Override
36 | public void onReceive(final Context ctx, Intent intent) {
37 | if (intent.getAction().equals(Intent.ACTION_BATTERY_CHANGED)){
38 |
39 | final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(ctx);
40 |
41 | final int status = intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, BATTERY_PLUGGED_UNPLUGGED);
42 | final int lastStatus = prefs.getInt("last_battery_status", BATTERY_PLUGGED_UNPLUGGED);
43 |
44 | if (status != BATTERY_PLUGGED_UNPLUGGED && lastStatus == BATTERY_PLUGGED_UNPLUGGED) {
45 |
46 | final boolean enabled = prefs.getBoolean("prefs_connect_on_charge", false);
47 | final boolean waiting = prefs.getBoolean("prefs_connect_on_charge_waiting", false);
48 |
49 | if (enabled && !waiting && ConnectionService.state == ConnectionService.State.DISCONNECTED) {
50 |
51 | final int waitTime = (int) prefs.getFloat("prefs_connect_on_charge_wait_time", 30);
52 |
53 | final Editor edit = prefs.edit();
54 | edit.putBoolean("prefs_connect_on_charge_waiting", true);
55 | edit.commit();
56 |
57 | AdaptiveLogger.log("BatteryStatusReceiver submitting auto connect intent");
58 |
59 | new Handler().postDelayed(new Runnable() {
60 |
61 | public void run() {
62 |
63 | final String name = prefs.getString("prefs_remote_name", "");
64 | final String addr = prefs.getString("prefs_remote_mac", "");
65 | final boolean waiting = prefs.getBoolean("prefs_connect_on_charge_waiting", false);
66 |
67 | if (waiting && addr.length() > 0) {
68 | Intent service = new Intent(ConnectionService.ACTION_CONNECT_BT);
69 | service.setPackage(ctx.getPackageName());
70 | service.putExtra("name", name);
71 | service.putExtra("addr", addr);
72 |
73 | ctx.startService(service);
74 |
75 | AdaptiveLogger.log("BatteryStatusReceiver auto connect intent sent");
76 | }
77 |
78 | edit.putBoolean("prefs_connect_on_charge_waiting", false);
79 | edit.commit();
80 |
81 | }
82 |
83 | } , waitTime * 1000);
84 | }
85 | }
86 |
87 | final Editor edit = prefs.edit();
88 | edit.putInt("last_battery_status", status);
89 | edit.commit();
90 |
91 | AdaptiveLogger.log("BatteryStatusReceiver charge status: " + status);
92 | }
93 | }
94 |
95 | }
96 |
97 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/CL431SerialToUsbConnector.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.usb;
2 |
3 | /*
4 | * Copyright 2013 Matt Waddilove
5 | *
6 | * Licensed under the Apache License, Version 2.0 (the "License");
7 | * you may not use this file except in compliance with the License.
8 | * You may obtain a copy of the License at
9 | *
10 | * http://www.apache.org/licenses/LICENSE-2.0
11 | *
12 | * Unless required by applicable law or agreed to in writing, software
13 | * distributed under the License is distributed on an "AS IS" BASIS,
14 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | * See the License for the specific language governing permissions and
16 | * limitations under the License.
17 | *
18 | */
19 |
20 | import android.hardware.usb.UsbConstants;
21 | import android.hardware.usb.UsbDeviceConnection;
22 |
23 | public class CL431SerialToUsbConnector extends UsbDeviceConnector {
24 |
25 | @Override
26 | public String getConnectorName() {
27 | return "Winchiphead CH341 Serial -> USB Adapter";
28 | }
29 |
30 | public static final int[][] SERIAL_TO_USB_DEVICES = new int[][] {
31 | //Format: {USB_VENDOR_ID, USB_PRODUCT_ID}
32 | new int[] {0x1A86, 0x7523} //, // Serial -> USB adapter Winchiphead CH341
33 | // new int[] {0x4348, 0x5523}, // Serial -> USB adapter (no idea quite which device this is for, but the linux kernel driver supports it too, so might as well.
34 | // new int[] {0x0403, 0x6001} // FTDI FT232R UART
35 | };
36 |
37 | @Override
38 | public int[][] GetSupportedDevices() {
39 | return SERIAL_TO_USB_DEVICES;
40 | }
41 |
42 | @Override
43 | public boolean InitialiseConnection(UsbDeviceConnection connection) {
44 | final int USB_CONTROL_OUT = UsbConstants.USB_TYPE_VENDOR | UsbConstants.USB_DIR_OUT;
45 | final int USB_CONTROL_IN = UsbConstants.USB_TYPE_VENDOR | UsbConstants.USB_DIR_IN;
46 |
47 | // horrific magic numbers gleaned from calculations based on the Linux kernel driver source.
48 | // look for ch341.c, All the repetition of sending etc... is also based on the behaviour of ch341.c
49 |
50 | //configure CH341:
51 | byte buffer[] = new byte[8];
52 | connection.controlTransfer(USB_CONTROL_IN, 0x5f, 0x0000, 0x0000, buffer, 8, 0); //0x27 0x00
53 | connection.controlTransfer(USB_CONTROL_OUT, 0xa1, 0x0000, 0x0000, null, 0, 0);
54 |
55 | // set the baud rate to 57600 calculations used ch341_set_baudrate
56 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x1312, 0x9803, null, 0, 0);
57 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x0f2c, 0x0010, null, 0, 0);
58 |
59 | connection.controlTransfer(USB_CONTROL_IN, 0x95, 0x2518, 0x0000, buffer, 8, 0); //0x56 0x00
60 | connection.controlTransfer(USB_CONTROL_OUT, 0x95, 0x2518, 0x0050, null, 0, 0);
61 |
62 | //Get Status:
63 | connection.controlTransfer(USB_CONTROL_IN, 0x95, 0x0706, 0x0000, buffer, 8, 0); //0xff 0xee
64 |
65 | connection.controlTransfer(USB_CONTROL_OUT, 0xa1, 0x501f, 0xd90a, null, 0, 0);
66 |
67 | // set the baud rate to 57600 calculations used ch341_set_baudrate
68 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x1312, 0x9803, null, 0, 0);
69 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x0f2c, 0x0010, null, 0, 0);
70 |
71 | // handshake:
72 | connection.controlTransfer(USB_CONTROL_OUT, 0xa4, 0x00ff, 0x0000, null, 0, 0); // or maybe 0xffff?
73 |
74 | // Adaptronic would like 8-N-1, however there's no data on how to set it, the device defaults to 8n1, so hopefully it'll be OK :/
75 |
76 | //Get Status:
77 | connection.controlTransfer(USB_CONTROL_IN, 0x95, 0x0706, 0x0000, buffer, 8, 0); //0x9f 0xee
78 |
79 | // handshake:
80 | connection.controlTransfer(USB_CONTROL_OUT, 0xa4, 0x00ff, 0x0000, null, 0, 0); // or maybe 0xffff?
81 |
82 | // set the baud rate to 57600 calculations used ch341_set_baudrate
83 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x1312, 0x9803, null, 0, 0);
84 | connection.controlTransfer(USB_CONTROL_OUT, 0x9a, 0x0f2c, 0x0010, null, 0, 0);
85 |
86 | return true;
87 |
88 | }
89 | }
90 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/FTDISerialToUsbConnector.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.usb;
2 |
3 | /*
4 | * Copyright 2013 Matt Waddilove
5 | *
6 | * Licensed under the Apache License, Version 2.0 (the "License");
7 | * you may not use this file except in compliance with the License.
8 | * You may obtain a copy of the License at
9 | *
10 | * http://www.apache.org/licenses/LICENSE-2.0
11 | *
12 | * Unless required by applicable law or agreed to in writing, software
13 | * distributed under the License is distributed on an "AS IS" BASIS,
14 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | * See the License for the specific language governing permissions and
16 | * limitations under the License.
17 | *
18 | */
19 |
20 | import android.hardware.usb.UsbDeviceConnection;
21 |
22 | public class FTDISerialToUsbConnector extends UsbDeviceConnector {
23 |
24 | @Override
25 | public String getConnectorName() {
26 | return "FTDI FT232R Serial -> USB Adapter";
27 | }
28 |
29 | public static final int[][] SERIAL_TO_USB_DEVICES = new int[][] {
30 | //Format: {USB_VENDOR_ID, USB_PRODUCT_ID}
31 | new int[] {0x0403, 0x6001} // FTDI FT232R UART
32 | };
33 |
34 | @Override
35 | public int[][] GetSupportedDevices() {
36 | return SERIAL_TO_USB_DEVICES;
37 | }
38 |
39 | @Override
40 | public boolean InitialiseConnection(UsbDeviceConnection connection) {
41 |
42 | connection.controlTransfer(0x40, 0, 0, 0, null, 0, 0);// reset
43 | connection.controlTransfer(0x40, 0, 1, 0, null, 0, 0);// clear Rx
44 | connection.controlTransfer(0x40, 0, 2, 0, null, 0, 0);// clear Tx
45 | connection.controlTransfer(0x40, 0x02, 0x0000, 0, null, 0, 0); // flow control none
46 |
47 | /*
48 | * Calculate a Divisor at 48MHz 9600 : 0x4138 11400 : 0xc107 19200 : 0x809c
49 | * 38400 : 0xc04e 57600 : 0x0034 115200 : 0x001a 230400 : 0x000d
50 | */
51 | connection.controlTransfer(0x40, 0x03, 0x0034, 0, null, 0, 0);
52 |
53 | connection.controlTransfer(0x40, 0x04, 0x0008, 0, null, 0, 0); // n/8/1
54 |
55 | return true;
56 | }
57 | }
58 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/PL2303SerialToUsbConnector.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.usb;
2 |
3 | /*
4 | * Copyright 2013 Matt Waddilove
5 | *
6 | * Licensed under the Apache License, Version 2.0 (the "License");
7 | * you may not use this file except in compliance with the License.
8 | * You may obtain a copy of the License at
9 | *
10 | * http://www.apache.org/licenses/LICENSE-2.0
11 | *
12 | * Unless required by applicable law or agreed to in writing, software
13 | * distributed under the License is distributed on an "AS IS" BASIS,
14 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | * See the License for the specific language governing permissions and
16 | * limitations under the License.
17 | *
18 | * PORTIONS COPYRIGHT
19 | *
20 | * INDIserver is free software: you can redistribute it and/or modify
21 | * it under the terms of the GNU General Public License as published by
22 | * the Free Software Foundation, either version 3 of the License, or
23 | * (at your option) any later version.
24 | *
25 | * INDIserver is distributed in the hope that it will be useful,
26 | * but WITHOUT ANY WARRANTY; without even the implied warranty of
27 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
28 | * GNU General Public License for more details.
29 | *
30 | * You should have received a copy of the GNU General Public License
31 | * along with INDIserver. If not, see .
32 | *
33 | * Copyright (C) 2012 Alexander Tuschen
34 | */
35 |
36 | import java.io.IOException;
37 |
38 | import android.hardware.usb.UsbDeviceConnection;
39 |
40 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
41 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger.Level;
42 |
43 | public class PL2303SerialToUsbConnector extends UsbDeviceConnector {
44 |
45 | @Override
46 | public String getConnectorName() {
47 | return "Prolific PL2303 Serial -> USB Adapter";
48 | }
49 |
50 | public static final int[][] SERIAL_TO_USB_DEVICES = new int[][] {
51 | //Format: {USB_VENDOR_ID, USB_PRODUCT_ID}
52 | new int[] {0x4348, 0x5523} // Serial -> USB adapter (no idea quite which device this is for, but the linux kernel driver supports it too, so might as well.
53 | };
54 |
55 | @Override
56 | public int[][] GetSupportedDevices() {
57 | return SERIAL_TO_USB_DEVICES;
58 | }
59 |
60 | @Override
61 | public boolean InitialiseConnection(UsbDeviceConnection connection) {
62 |
63 | try {
64 |
65 | // Initialization of PL2303 according to linux pl2303.c driver
66 | setup(connection, BaudRate.B57600, DataBits.D8, StopBits.S1, Parity.NONE);
67 |
68 | byte[] buffer = new byte[1];
69 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8484, 0, buffer, 1, 100);
70 | connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 0x0404, 0, null, 0, 100);
71 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8484, 0, buffer, 1, 100);
72 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8383, 0, buffer, 1, 100);
73 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8484, 0, buffer, 1, 100);
74 | connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 0x0404, 1, null, 0, 100);
75 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8484, 0, buffer, 1, 100);
76 | connection.controlTransfer(VENDOR_READ_REQUEST_TYPE, VENDOR_READ_REQUEST, 0x8383, 0, buffer, 1, 100);
77 | connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 0, 1, null, 0, 100);
78 | connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 1, 0, null, 0, 100);
79 | connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 2, 0x24, null, 0, 100);
80 |
81 | AdaptiveLogger.log("PL2303 successfully opened");
82 | } catch (IOException e) {
83 | AdaptiveLogger.log(Level.ERROR, "unable to initialize PL2303 " + e.getMessage());
84 | }
85 | return true;
86 |
87 | }
88 |
89 | // Setup basic communication parameters according to linux pl2303.c driver
90 | public void setup(UsbDeviceConnection connection, BaudRate R, DataBits D, StopBits S, Parity P) throws IOException {
91 | byte[] oldSettings = new byte[7];
92 | byte[] buffer = new byte[7];
93 |
94 | if (connection == null) throw new IOException("Connection closed");
95 |
96 | // Get current settings
97 | connection.controlTransfer(GET_LINE_REQUEST_TYPE, GET_LINE_REQUEST, 0, 0, oldSettings, 7, 100);
98 |
99 | buffer = oldSettings;
100 |
101 | // Setup Baudrate
102 | int baud;
103 | switch (R) {
104 | case B0: baud = 0; break;
105 | case B75: baud = 75; break;
106 | case B150: baud = 150; break;
107 | case B300: baud = 300; break;
108 | case B600: baud = 600; break;
109 | case B1200: baud = 1200; break;
110 | case B1800: baud = 1800; break;
111 | case B2400: baud = 2400; break;
112 | case B4800: baud = 4800; break;
113 | case B9600: baud = 9600; break;
114 | case B19200: baud = 19200; break;
115 | case B38400: baud = 38400; break;
116 | case B57600: baud = 57600; break;
117 | case B115200: baud = 115200; break;
118 | case B230400: baud = 230400; break;
119 | case B460800: baud = 460800; break;
120 | case B614400: baud = 614400; break;
121 | case B921600: baud = 921600; break;
122 | case B1228800: baud = 1228800; break;
123 | case B2457600: baud = 2457600; break;
124 | case B3000000: baud = 3000000; break;
125 | case B6000000: baud = 6000000; break;
126 | default: baud = 9600; break;
127 | }
128 |
129 | if ((baud > 1228800) && (pl2303type == 0)) baud = 1228800; // Only PL2303HX supports higher baudrates
130 |
131 | buffer[0]=(byte) (baud & 0xff);
132 | buffer[1]=(byte) ((baud >> 8) & 0xff);
133 | buffer[2]=(byte) ((baud >> 16) & 0xff);
134 | buffer[3]=(byte) ((baud >> 24) & 0xff);
135 |
136 | // // Setup Stopbits
137 | // switch (S) {
138 | // case S1: buffer[4] = 0; break;
139 | // case S2: buffer[4] = 2; break;
140 | // default: buffer[4] = 0; break;
141 | // }
142 | //
143 | // // Setup Parity
144 | // switch (P) {
145 | // case NONE: buffer[5] = 0; break;
146 | // case ODD: buffer[5] = 1; break;
147 | // case EVEN: buffer[5] = 2; break;
148 | // default: buffer[5] = 0; break;
149 | // }
150 | //
151 | // // Setup Databits
152 | // switch (D) {
153 | // case D5: buffer[6] = 5; break;
154 | // case D6: buffer[6] = 6; break;
155 | // case D7: buffer[6] = 7; break;
156 | // case D8: buffer[6] = 8; break;
157 | // default: buffer[6] = 8; break;
158 | // }
159 |
160 | // Set new configuration on PL2303 only if settings have changed
161 | //if (buffer != oldSettings)
162 | connection.controlTransfer(SET_LINE_REQUEST_TYPE, SET_LINE_REQUEST, 0, 0, buffer, 7, 100);
163 |
164 | // // Disable BreakControl
165 | // connection.controlTransfer(BREAK_REQUEST_TYPE, BREAK_REQUEST, BREAK_OFF, 0, null, 0, 100);
166 | //
167 | // // Disable FlowControl
168 | // connection.controlTransfer(VENDOR_WRITE_REQUEST_TYPE, VENDOR_WRITE_REQUEST, 0, 0, null, 0, 100);
169 |
170 | //TODO: implement RTS/CTS FlowControl
171 | }
172 |
173 | // Type 0 = PL2303, type 1 = PL2303HX
174 | private int pl2303type = 0;
175 |
176 | public enum BaudRate {
177 | B0,
178 | B75,
179 | B150,
180 | B300,
181 | B600,
182 | B1200,
183 | B1800,
184 | B2400,
185 | B4800,
186 | B9600,
187 | B19200,
188 | B38400,
189 | B57600,
190 | B115200,
191 | B230400,
192 | B460800,
193 | B614400,
194 | B921600,
195 | B1228800,
196 | B2457600,
197 | B3000000,
198 | B6000000
199 | };
200 |
201 | public enum DataBits {
202 | D5,
203 | D6,
204 | D7,
205 | D8
206 | };
207 |
208 | public enum StopBits {
209 | S1,
210 | S2
211 | };
212 |
213 | public enum Parity {
214 | NONE,
215 | ODD,
216 | EVEN
217 | };
218 |
219 | // USB control commands
220 | private static final int SET_LINE_REQUEST_TYPE = 0x21;
221 | private static final int SET_LINE_REQUEST = 0x20;
222 | private static final int BREAK_REQUEST_TYPE = 0x21;
223 | private static final int BREAK_REQUEST = 0x23;
224 | private static final int BREAK_OFF = 0x0000;
225 | private static final int GET_LINE_REQUEST_TYPE = 0xa1;
226 | private static final int GET_LINE_REQUEST = 0x21;
227 | private static final int VENDOR_WRITE_REQUEST_TYPE = 0x40;
228 | private static final int VENDOR_WRITE_REQUEST = 0x01;
229 | private static final int VENDOR_READ_REQUEST_TYPE = 0xc0;
230 | private static final int VENDOR_READ_REQUEST = 0x01;
231 | }
232 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/SelectECUConnector.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.usb;
2 |
3 | /*
4 | * Copyright 2013 Matt Waddilove
5 | *
6 | * Licensed under the Apache License, Version 2.0 (the "License");
7 | * you may not use this file except in compliance with the License.
8 | * You may obtain a copy of the License at
9 | *
10 | * http://www.apache.org/licenses/LICENSE-2.0
11 | *
12 | * Unless required by applicable law or agreed to in writing, software
13 | * distributed under the License is distributed on an "AS IS" BASIS,
14 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 | * See the License for the specific language governing permissions and
16 | * limitations under the License.
17 | *
18 | */
19 |
20 | import android.hardware.usb.UsbDeviceConnection;
21 |
22 | public class SelectECUConnector extends UsbDeviceConnector {
23 |
24 | @Override
25 | public String getConnectorName() {
26 | return "Select ECU";
27 | }
28 |
29 | //Known ECUs
30 | protected static final int[][] ADAPTRONIC_USB_ECUS = new int[][] {
31 | //Format: {USB_VENDOR_ID, USB_PRODUCT_ID}
32 | new int[] {0x10C4, 0x858D} //Select ECU
33 | };
34 |
35 | @Override
36 | public int[][] GetSupportedDevices() {
37 | return ADAPTRONIC_USB_ECUS;
38 | }
39 |
40 | @Override
41 | public boolean InitialiseConnection(UsbDeviceConnection connection) {
42 |
43 | //Control codes for Silicon Labs CP201x USB to UART @ 250000 baud
44 | connection.controlTransfer(0x40, 0x00, 0xff, 0xff, null, 0, 0);
45 | connection.controlTransfer(0x40, 0x01, 0x00, 0x02, null, 0, 0);
46 | connection.controlTransfer(0x40, 0x01, 0x0f, 0x00, null, 0, 0);
47 |
48 | return true;
49 | }
50 |
51 | }
52 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/UsbConnectedThread.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Evan H. Dekker
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | *
17 | *
18 | * ----------------------------------------------------------------------
19 | *
20 | * USB API COMPATABILITY NOTE:
21 | * Tested on Acer A500 with Android 4.0.3
22 | *
23 | * Not all Android devices that claim to support the USB Host API introduced
24 | * in Android 3.1 actually do.
25 | *
26 | * For a guide, please see this list: http://usbhost.chainfire.eu/
27 | * If your device is not listed, please try this app: https://play.google.com/store/apps/details?id=eu.chainfire.usbhostdiagnostics
28 | *
29 | * (Author has no affiliation with this service or app)
30 | *
31 | */
32 | package com.shellware.adaptronic.adaptivetuner.usb;
33 |
34 | import java.util.HashMap;
35 | import java.util.Iterator;
36 | import java.util.Locale;
37 |
38 | import android.content.Context;
39 | import android.hardware.usb.UsbConstants;
40 | import android.hardware.usb.UsbDevice;
41 | import android.hardware.usb.UsbDeviceConnection;
42 | import android.hardware.usb.UsbEndpoint;
43 | import android.hardware.usb.UsbInterface;
44 | import android.hardware.usb.UsbManager;
45 | import android.os.Bundle;
46 | import android.os.Handler;
47 | import android.os.Message;
48 |
49 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
50 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger.Level;
51 | import com.shellware.adaptronic.adaptivetuner.modbus.ConnectedThread;
52 | import com.shellware.adaptronic.adaptivetuner.services.ConnectionService;
53 |
54 | public class UsbConnectedThread extends ConnectedThread {
55 |
56 | public static final int USB_VENDOR_ID = 0;
57 | public static final int USB_PRODUCT_ID = 1;
58 |
59 | public static final UsbDeviceConnector[] SUPPORTED_DEVICES = new UsbDeviceConnector[] {
60 | new SelectECUConnector(), // Select ECU
61 | new CL431SerialToUsbConnector(), // CL431
62 | new PL2303SerialToUsbConnector(), // PL2303
63 | new FTDISerialToUsbConnector() // FTDI FT232R UART
64 | };
65 |
66 | private static UsbManager mUsbManager = null;
67 |
68 | private UsbDevice mUsbDevice = null;
69 | private UsbDeviceConnection mConnection = null;
70 | private UsbEndpoint mInEndpoint = null;
71 | private UsbEndpoint mOutEndpoint = null;
72 |
73 | public UsbConnectedThread(Handler handler, UsbDevice device, UsbDeviceConnection connection, UsbEndpoint inEndpoint, UsbEndpoint outEndpoint) {
74 | super(handler);
75 |
76 | mUsbDevice = device;
77 | mConnection = connection;
78 | mInEndpoint = inEndpoint;
79 | mOutEndpoint = outEndpoint;
80 |
81 | AdaptiveLogger.log("UsbConnectedThread created");
82 |
83 | start();
84 | }
85 |
86 | public static UsbConnectedThread checkConnectedUsbDevice(Context context, Handler handler) {
87 | if (mUsbManager == null) {
88 | mUsbManager = (UsbManager)context.getSystemService(Context.USB_SERVICE);
89 | }
90 |
91 | AdaptiveLogger.log("Checking for connected USB devices");
92 |
93 | HashMap deviceList = mUsbManager.getDeviceList();
94 | Iterator deviceIterator = deviceList.values().iterator();
95 |
96 | while (deviceIterator.hasNext()) {
97 | UsbDevice device = deviceIterator.next();
98 |
99 | AdaptiveLogger.log("Found USB device");
100 |
101 | try {
102 |
103 | UsbDeviceConnector recognisedDeviceConnector = null;
104 |
105 | for (UsbDeviceConnector deviceConnector: SUPPORTED_DEVICES) {
106 | if (recognisedDeviceConnector == null) {
107 | for (int[] deviceVendorProductID : deviceConnector.GetSupportedDevices()) {
108 | if (device.getVendorId() == deviceVendorProductID[USB_VENDOR_ID] && device.getProductId() == deviceVendorProductID[USB_PRODUCT_ID]) {
109 | recognisedDeviceConnector = deviceConnector;
110 | break;
111 | }
112 | }
113 | }
114 | }
115 |
116 | if (recognisedDeviceConnector != null) {
117 | AdaptiveLogger.log(String.format("%s recognised", recognisedDeviceConnector.getConnectorName()));
118 |
119 | UsbDeviceConnection connection = mUsbManager.openDevice(device);
120 |
121 | if (!connection.claimInterface(device.getInterface(0), true)) {
122 | connectionError(device.getDeviceName(), "Could not claim device interface", handler);
123 | return null;
124 | }
125 |
126 | recognisedDeviceConnector.InitialiseConnection(connection);
127 |
128 | UsbEndpoint inEndpoint = null;
129 | UsbEndpoint outEndpoint = null;
130 |
131 | for (int interfaceIndex = 0; interfaceIndex < device.getInterfaceCount(); interfaceIndex++) {
132 | UsbInterface usbInterface = device.getInterface(interfaceIndex);
133 |
134 | for (int index = 0; index < usbInterface.getEndpointCount(); index++) {
135 | UsbEndpoint endpoint = usbInterface.getEndpoint(index);
136 |
137 | if (endpoint.getType() == UsbConstants.USB_ENDPOINT_XFER_BULK) {
138 | if (endpoint.getDirection() == UsbConstants.USB_DIR_IN) {
139 | AdaptiveLogger.log("In Endpoint Found");
140 | inEndpoint = endpoint;
141 | } else if (endpoint.getDirection() == UsbConstants.USB_DIR_OUT) {
142 | AdaptiveLogger.log("Out Endpoint Found");
143 | outEndpoint = endpoint;
144 | }
145 | }
146 | }
147 |
148 | if (inEndpoint != null && outEndpoint != null) {
149 | return new UsbConnectedThread(handler, device, connection, inEndpoint, outEndpoint);
150 | }
151 | }
152 | }
153 | } catch (Exception ex) {
154 | connectionError(device.getDeviceName(), ex.getMessage(), handler);
155 | return null;
156 | }
157 | }
158 |
159 | return null;
160 | }
161 |
162 | public void run() {
163 | byte[] buffer = new byte[512];
164 | int bytes;
165 |
166 | while (!disconnecting) {
167 | bytes = mConnection.bulkTransfer(mInEndpoint, buffer, buffer.length, 5);
168 |
169 | if (bytes == -1) {
170 | // if (DEBUG) Log.d(TAG, "Bulk Transfer In Error");
171 | } else {
172 | AdaptiveLogger.log(String.format(Locale.US, "Received %d bytes", bytes));
173 |
174 | // Send the obtained bytes to the connection service
175 | Bundle b = new Bundle();
176 |
177 | b.putShort("handle", ConnectionService.DATA_READY);
178 | b.putByteArray("data", buffer);
179 | b.putInt("length", bytes);
180 |
181 | Message msg = new Message();
182 | msg.setData(b);
183 |
184 | handler.sendMessage(msg);
185 | }
186 |
187 | try {
188 | Thread.sleep(5);
189 | } catch (Exception e) {}
190 |
191 | }
192 | }
193 |
194 | public void write(byte[] bytes) {
195 | if (mConnection.bulkTransfer(mOutEndpoint, bytes, bytes.length, 5) == -1) {
196 | AdaptiveLogger.log(Level.ERROR, "Bulk Transfer Out Error");
197 | } else {
198 | AdaptiveLogger.log("Bulk Transfer Out Successful");
199 | }
200 | }
201 |
202 | public void cancel() {
203 | disconnecting = true;
204 | AdaptiveLogger.log("USB Connected Thread Canceled");
205 |
206 | }
207 |
208 | public boolean isUsbDevice(UsbDevice usbDevice) {
209 | return mUsbDevice.getDeviceId() == usbDevice.getDeviceId();
210 | }
211 |
212 | private static void connectionError(String name, String message, Handler handler) {
213 | Bundle b = new Bundle();
214 |
215 | b.putShort("handle", ConnectionService.CONNECTION_ERROR);
216 | b.putString("title", name);
217 | b.putString("message", message);
218 |
219 | Message msg = new Message();
220 | msg.setData(b);
221 |
222 | AdaptiveLogger.log(Level.ERROR, "UsbConnectedThread Connection error - " + message);
223 | handler.sendMessage(msg);
224 | }
225 | }
226 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/usb/UsbDeviceConnector.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.usb;
2 |
3 | import android.hardware.usb.UsbDeviceConnection;
4 |
5 | /**
6 | * Created by Matt on 16/06/13.
7 | */
8 | abstract public class UsbDeviceConnector {
9 |
10 | abstract public String getConnectorName();
11 |
12 | abstract public int[][] GetSupportedDevices();
13 |
14 | abstract public boolean InitialiseConnection(UsbDeviceConnection connection);
15 | }
16 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/valueobjects/LogItems.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.valueobjects;
18 |
19 | import java.util.ArrayList;
20 | import java.util.Locale;
21 |
22 | public class LogItems {
23 |
24 | public static enum SafetyCutReason {
25 | NOCUT,
26 | REVSOFT,
27 | REVHARD,
28 | COLDREVLIMIT,
29 | HOTREVLIMIT,
30 | OVERBOOST,
31 | OVERRUN,
32 | FLATSHIFT,
33 | TURBOTIMER,
34 | LOWRPMOIL,
35 | HIGHRPMOIL,
36 | FUELP,
37 | AUXP,
38 | LEANOUT,
39 | INJOC,
40 | NOIGN,
41 | TCPITLANELAUNCH
42 | }
43 |
44 | private ArrayList items = new ArrayList(65535);
45 |
46 | public ArrayList getItems() {
47 | return items;
48 | }
49 |
50 | public void setItems(ArrayList items) {
51 | this.items = items;
52 | }
53 |
54 | public LogItem newLogItem() {
55 | return new LogItem();
56 | }
57 |
58 | public void addLogItem(LogItem item) {
59 | LogItem newItem = newLogItem();
60 |
61 | newItem.afr = item.afr;
62 | newItem.auxt = item.auxt;
63 | newItem.closedLoop = item.closedLoop;
64 | newItem.learningFLoad = item.learningFLoad;
65 | newItem.learningFRpm = item.learningFRpm;
66 | newItem.learningFWait = item.learningFWait;
67 | newItem.learningILoad = item.learningILoad;
68 | newItem.learningIRpm = item.learningIRpm;
69 | newItem.learningIWait = item.learningIWait;
70 | newItem.map = item.map;
71 | newItem.mat = item.mat;
72 | newItem.referenceAfr = item.referenceAfr;
73 | newItem.rpm = item.rpm;
74 | newItem.targetAfr = item.targetAfr;
75 | newItem.tps = item.tps;
76 | newItem.wat = item.wat;
77 | newItem.knock = item.knock;
78 | newItem.volts = item.volts;
79 | newItem.fuelpres = item.fuelpres;
80 | newItem.oilpres = item.oilpres;
81 | newItem.auxpres = item.auxpres;
82 | newItem.safetyCutReason = item.safetyCutReason;
83 |
84 | items.add(newItem);
85 | }
86 |
87 | public class LogItem {
88 |
89 | private final long timestamp = System.currentTimeMillis();
90 |
91 | private int rpm = 0;
92 | private int map = 0;
93 | private int wat = 0;
94 | private int mat = 0;
95 | private int auxt = 0;
96 | private int tps = 0;
97 | private int knock = 0;
98 | private int oilpres = 0;
99 | private int fuelpres = 0;
100 | private int auxpres = 0;
101 |
102 | //TODO: add safety cut functions
103 |
104 | private float afr = 0f;
105 | private float referenceAfr = 0f;
106 | private float targetAfr = 0f;
107 | private float volts = 0f;
108 | private float channelOneVolts = 0f;
109 |
110 | private boolean learningIWait = false;
111 | private boolean learningIRpm = false;
112 | private boolean learningILoad = false;
113 |
114 | private boolean learningFWait = false;
115 | private boolean learningFRpm = false;
116 | private boolean learningFLoad = false;
117 |
118 | private boolean closedLoop = false;
119 |
120 | private SafetyCutReason safetyCutReason = SafetyCutReason.NOCUT;
121 |
122 | public int getRpm() {
123 | return rpm;
124 | }
125 |
126 | public void setRpm(final int rpm) {
127 | this.rpm = rpm;
128 | }
129 |
130 | public int getMap() {
131 | return map;
132 | }
133 |
134 | public void setMap(final int map) {
135 | this.map = map;
136 | }
137 |
138 | public int getWat() {
139 | return wat;
140 | }
141 |
142 | public void setWat(final int wat) {
143 | this.wat = wat;
144 | }
145 |
146 | public int getMat() {
147 | return mat;
148 | }
149 |
150 | public void setMat(final int mat) {
151 | this.mat = mat;
152 | }
153 |
154 | public int getAuxt() {
155 | return auxt;
156 | }
157 |
158 | public void setAuxt(final int auxt) {
159 | this.auxt = auxt;
160 | }
161 |
162 | public int getTps() {
163 | return tps;
164 | }
165 |
166 | public void setTps(final int tps) {
167 | this.tps = tps;
168 | }
169 |
170 | public float getAfr() {
171 | return afr;
172 | }
173 |
174 | public void setAfr(final float afr) {
175 | this.afr = afr;
176 | }
177 |
178 | public float getReferenceAfr() {
179 | return referenceAfr;
180 | }
181 |
182 | public void setReferenceAfr(final float referenceAfr) {
183 | this.referenceAfr = referenceAfr;
184 | }
185 |
186 | public float getTargetAfr() {
187 | return targetAfr;
188 | }
189 |
190 | public void setTargetAfr(final float targetAfr) {
191 | this.targetAfr = targetAfr;
192 | }
193 |
194 | public float getVolts() {
195 | return volts;
196 | }
197 |
198 | public void setVolts(float volts) {
199 | this.volts = volts;
200 | }
201 |
202 | public int getKnock() {
203 | return knock;
204 | }
205 |
206 | public void setKnock(int knock) {
207 | this.knock = knock;
208 | }
209 |
210 | public int getOilpres() {
211 | return oilpres;
212 | }
213 |
214 | public void setOilpres(int oilpres) {
215 | this.oilpres = oilpres;
216 | }
217 |
218 | public int getFuelpres() {
219 | return fuelpres;
220 | }
221 |
222 | public void setFuelpres(int fuelpres) {
223 | this.fuelpres = fuelpres;
224 | }
225 |
226 | public int getAuxpres() {
227 | return auxpres;
228 | }
229 |
230 | public void setAuxpres(int auxpres) {
231 | this.auxpres = auxpres;
232 | }
233 |
234 | public boolean isLearningIWait() {
235 | return learningIWait;
236 | }
237 |
238 | public void setLearningIWait(final boolean learningIWait) {
239 | this.learningIWait = learningIWait;
240 | }
241 |
242 | public boolean isLearningIRpm() {
243 | return learningIRpm;
244 | }
245 |
246 | public void setLearningIRpm(final boolean learningIRpm) {
247 | this.learningIRpm = learningIRpm;
248 | }
249 |
250 | public boolean isLearningILoad() {
251 | return learningILoad;
252 | }
253 |
254 | public void setLearningILoad(final boolean learningILoad) {
255 | this.learningILoad = learningILoad;
256 | }
257 |
258 | public boolean isLearningFWait() {
259 | return learningFWait;
260 | }
261 |
262 | public void setLearningFWait(final boolean learningFWait) {
263 | this.learningFWait = learningFWait;
264 | }
265 |
266 | public boolean isLearningFRpm() {
267 | return learningFRpm;
268 | }
269 |
270 | public void setLearningFRpm(final boolean learningFRpm) {
271 | this.learningFRpm = learningFRpm;
272 | }
273 |
274 | public boolean isLearningFLoad() {
275 | return learningFLoad;
276 | }
277 |
278 | public void setLearningFLoad(final boolean learningFLoad) {
279 | this.learningFLoad = learningFLoad;
280 | }
281 |
282 | public boolean isClosedLoop() {
283 | return closedLoop;
284 | }
285 |
286 | public void setClosedLoop(final boolean closedLoop) {
287 | this.closedLoop = closedLoop;
288 | }
289 |
290 | public long getTimestamp() {
291 | return timestamp;
292 | }
293 |
294 | public SafetyCutReason getSafetyCutReason() {
295 | return safetyCutReason;
296 | }
297 |
298 | public void setSafetyCutReason(SafetyCutReason safetyCutReason) {
299 | this.safetyCutReason = safetyCutReason;
300 | }
301 |
302 | public String getLogString() {
303 |
304 | final String str = String.format(Locale.US, "%d, %d, %d, %d, %.1f, %.1f, %.1f, %d, %d, %d, %d, %d, %.1f, %d, %d, %d, %s\n",
305 | timestamp,
306 | rpm,
307 | map,
308 | closedLoop ? 1 : 0,
309 | targetAfr,
310 | afr,
311 | referenceAfr,
312 | tps,
313 | wat,
314 | mat,
315 | auxt,
316 | knock,
317 | volts,
318 | fuelpres,
319 | oilpres,
320 | auxpres,
321 | safetyCutReason.name());
322 | return str;
323 | }
324 |
325 | public byte[] getLogBytes() {
326 | return getLogString().getBytes();
327 | }
328 | }
329 | }
330 |
331 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/widgets/AdaptiveAdapter.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.widgets;
2 |
3 | import android.content.Context;
4 | import android.graphics.Typeface;
5 | import android.view.LayoutInflater;
6 | import android.view.View;
7 | import android.view.ViewGroup;
8 | import android.widget.ArrayAdapter;
9 | import android.widget.TextView;
10 |
11 | public class AdaptiveAdapter extends ArrayAdapter {
12 |
13 | private final static int ORIENTATION_PHONE = 0;
14 | private final static int ORIENTATION_PHONE_PORTRAIT = 1;
15 | // private final static int ORIENTATION_PHABLET = 2;
16 | // private final static int ORIENTATION_PHABLET_PORTRAIT = 3;
17 | // private final static int ORIENTATION_TABLET = 4;
18 | // private final static int ORIENTATION_TABLET_PORTRAIT = 5;
19 |
20 | private Context ctx;
21 | private LayoutInflater inflater;
22 | private int textViewResourceId;
23 |
24 | private Typeface typeface;
25 |
26 | private int orientation;
27 |
28 | public AdaptiveAdapter(Context ctx, int textViewResourceId) {
29 | super(ctx, textViewResourceId);
30 |
31 | this.ctx = ctx;
32 | inflater = (LayoutInflater)this.ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
33 | this.textViewResourceId = textViewResourceId;
34 | }
35 |
36 | public AdaptiveAdapter(Context ctx, int textViewResourceId, Typeface typeface) {
37 | super(ctx, textViewResourceId);
38 |
39 | this.ctx = ctx;
40 | inflater = (LayoutInflater)this.ctx.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
41 | this.textViewResourceId = textViewResourceId;
42 | this.typeface = typeface;
43 | }
44 |
45 | @Override
46 | public View getView(int position, View convertView, ViewGroup parent) {
47 |
48 | if (convertView == null) {
49 | convertView = (TextView) inflater.inflate(textViewResourceId, null);
50 | orientation = Integer.parseInt((String) ((TextView) convertView).getText());
51 |
52 | ((TextView) convertView).setTypeface(typeface);
53 |
54 | if (orientation == ORIENTATION_PHONE || orientation == ORIENTATION_PHONE_PORTRAIT) {
55 | ((TextView) convertView).setTextSize(16);
56 | ((TextView) convertView).setLineSpacing(2, 1);
57 | } else {
58 | ((TextView) convertView).setTextSize(28);
59 | ((TextView) convertView).setLineSpacing(4, 1);
60 | }
61 | }
62 |
63 | return super.getView(position, convertView, parent);
64 | }
65 | }
66 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/widgets/CellValueWidget.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2013 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.widgets;
18 |
19 | import android.content.Context;
20 | import android.util.AttributeSet;
21 | import android.view.MotionEvent;
22 | import android.widget.EditText;
23 | import android.widget.ImageView;
24 |
25 | import com.shellware.adaptronic.adaptive.tuner.R;
26 |
27 |
28 | public class CellValueWidget extends ImageView {
29 |
30 | private enum CellValueWidgetChangeType {
31 | INCREMENT_SMALL,
32 | DECREMENT_SMALL,
33 | INCREMENT_BIG,
34 | DECREMENT_BIG
35 | }
36 |
37 | private EditText editText;
38 | private CellValueWidgetChangeType pendingChangeType;
39 |
40 | public CellValueWidget(Context context) {
41 | super(context);
42 | }
43 |
44 | public CellValueWidget(Context context, AttributeSet attrs, int defStyle) {
45 | super(context, attrs, defStyle);
46 | }
47 |
48 | public CellValueWidget(Context context, AttributeSet attrs) {
49 | super(context, attrs);
50 | }
51 |
52 | public void setEditText(final EditText editText) {
53 | this.editText = editText;
54 | }
55 |
56 | @Override
57 | public boolean onTouchEvent(MotionEvent event) {
58 |
59 | switch (event.getAction()) {
60 | case MotionEvent.ACTION_DOWN:
61 | DetermineChangeType(event.getX(), event.getY());
62 | break;
63 | case MotionEvent.ACTION_UP:
64 | ProcessChange();
65 | break;
66 | }
67 |
68 | return true;
69 | }
70 |
71 | private void DetermineChangeType(final float x, final float y) {
72 |
73 | final float smallWidth = this.getWidth() / 2 - this.getWidth() / 4;
74 | final float smallHeight = this.getHeight() / 2 - this.getHeight() / 4;
75 |
76 | // determine which zone was pressed
77 | if (x > smallWidth && x < this.getWidth() - smallWidth && y > smallHeight && y < this.getHeight() - smallHeight) {
78 | if (y < this.getHeight() / 2) {
79 | this.setImageResource(R.drawable.cell_value_widget_small_up);
80 | pendingChangeType = CellValueWidgetChangeType.INCREMENT_SMALL;
81 | } else {
82 | this.setImageResource(R.drawable.cell_value_widget_small_down);
83 | pendingChangeType = CellValueWidgetChangeType.DECREMENT_SMALL;
84 | }
85 | } else {
86 | if (y < this.getHeight() / 2) {
87 | this.setImageResource(R.drawable.cell_value_widget_big_up);
88 | pendingChangeType = CellValueWidgetChangeType.INCREMENT_BIG;
89 | } else {
90 | this.setImageResource(R.drawable.cell_value_widget_big_down);
91 | pendingChangeType = CellValueWidgetChangeType.DECREMENT_BIG;
92 | }
93 | }
94 | }
95 |
96 |
97 | private void ProcessChange() {
98 | this.setImageResource(R.drawable.cell_value_widget);
99 |
100 | final float value;
101 | try {
102 | value = Float.parseFloat(editText.getText().toString());
103 | } catch (Exception ex) {
104 | return;
105 | }
106 |
107 | switch (pendingChangeType) {
108 | case INCREMENT_SMALL:
109 | editText.setText(String.format("%.2f", value + .01f));
110 | break;
111 | case DECREMENT_SMALL:
112 | editText.setText(String.format("%.2f", value - .01f));
113 | break;
114 | case INCREMENT_BIG:
115 | editText.setText(String.format("%.2f", value + 1f));
116 | break;
117 | case DECREMENT_BIG:
118 | editText.setText(String.format("%.2f", value - 1f));
119 | break;
120 | }
121 | }
122 |
123 | }
124 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/widgets/DigitalGauge.java:
--------------------------------------------------------------------------------
1 | package com.shellware.adaptronic.adaptivetuner.widgets;
2 |
3 | import com.shellware.adaptronic.adaptive.tuner.R;
4 |
5 | import android.content.Context;
6 | import android.content.res.TypedArray;
7 | import android.graphics.Color;
8 | import android.graphics.Paint;
9 | import android.graphics.Typeface;
10 | import android.util.AttributeSet;
11 | import android.util.DisplayMetrics;
12 | import android.util.TypedValue;
13 | import android.widget.RelativeLayout;
14 | import android.widget.TextView;
15 |
16 | public class DigitalGauge extends RelativeLayout {
17 |
18 | private RelativeLayout digitalBorder;
19 |
20 | private TextView gaugeTitleView;
21 | private TextView gaugeValueView;
22 | private TextView gaugeUnitsView;
23 |
24 | private String title = "title";
25 | private String value = "000";
26 | private String units = "\u00B0 F";
27 | private int width = 140;
28 |
29 | private float minimumValue = -999999;
30 | private float maximumValue = 999999;
31 |
32 | public DigitalGauge(Context context) {
33 | super(context);
34 | init();
35 | }
36 | public DigitalGauge(Context context, AttributeSet attrs, int defStyleAttr) {
37 | super(context, attrs, defStyleAttr);
38 | getAttributes(attrs);
39 | init();
40 | }
41 | public DigitalGauge(Context context, AttributeSet attrs) {
42 | super(context, attrs);
43 | getAttributes(attrs);
44 | init();
45 | }
46 |
47 | private void getAttributes(AttributeSet attrs) {
48 |
49 | final TypedArray a = getContext().obtainStyledAttributes(attrs, R.styleable.DigitalGauge);
50 | final int N = a.getIndexCount();
51 |
52 | for (int i = 0; i < N; ++i) {
53 | final int attr = a.getIndex(i);
54 |
55 | switch (attr) {
56 | case R.styleable.DigitalGauge_title:
57 | title = a.getString(attr);
58 | break;
59 | case R.styleable.DigitalGauge_value:
60 | value = a.getString(attr);
61 | break;
62 | case R.styleable.DigitalGauge_units:
63 | units = a.getString(attr);
64 | break;
65 | case R.styleable.DigitalGauge_width:
66 | width = a.getInt(attr, 140);
67 | break;
68 | }
69 | }
70 |
71 | a.recycle();
72 | };
73 |
74 | private void init() {
75 | inflate(getContext(), R.layout.digital_gauge, this);
76 |
77 | digitalBorder = (RelativeLayout) findViewById(R.id.digitalborder);
78 |
79 | gaugeTitleView = (TextView) findViewById(R.id.digitaltitle);
80 | gaugeValueView = (TextView) findViewById(R.id.digitalvalue);
81 | gaugeUnitsView = (TextView) findViewById(R.id.digitalunits);
82 |
83 | if (!isInEditMode()) gaugeTitleView.setTypeface(Typeface.createFromAsset(getContext().getAssets(), "fonts/digital_7.ttf"), Typeface.NORMAL);
84 | gaugeTitleView.setTextColor(Color.parseColor("#ffa500"));;
85 | gaugeTitleView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, (int) getResources().getDimension(R.dimen.gauge_title_size));
86 |
87 | if (!isInEditMode()) gaugeValueView.setTypeface(Typeface.createFromAsset(getContext().getAssets(), "fonts/digital_7.ttf"), Typeface.BOLD);
88 | gaugeValueView.setTextColor(Color.GREEN);
89 | gaugeValueView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, (int) getResources().getDimension(R.dimen.gauge_value_size));
90 |
91 | if (!isInEditMode()) gaugeUnitsView.setTypeface(Typeface.createFromAsset(getContext().getAssets(), "fonts/digital_7.ttf"), Typeface.BOLD);
92 | gaugeUnitsView.setPaintFlags(Paint.UNDERLINE_TEXT_FLAG);
93 | gaugeUnitsView.setTextColor(Color.parseColor("#eee9e9"));;
94 | gaugeUnitsView.setTextSize(TypedValue.COMPLEX_UNIT_DIP, (int) getResources().getDimension(R.dimen.gauge_units_size));
95 |
96 | gaugeTitleView.setText(title);
97 | gaugeValueView.setText(value);
98 | gaugeUnitsView.setText(units);
99 |
100 | RelativeLayout.LayoutParams parms = (RelativeLayout.LayoutParams) digitalBorder.getLayoutParams();
101 | parms.width = convertDpToPx(width);
102 | digitalBorder.setLayoutParams(parms);
103 | }
104 |
105 | private int convertDpToPx(final int dp) {
106 | DisplayMetrics metrics = getContext().getResources().getDisplayMetrics();
107 | return (int) (metrics.density * dp + 0.5f);
108 | }
109 |
110 | public void setValue(final int value) {
111 | if (value == 0) {
112 | this.value = "- - -";
113 | } else {
114 | this.value = String.valueOf(value);
115 | }
116 | setGaugeValue(value);
117 | }
118 |
119 | public void setValue(final float value) {
120 | if (value == 0) {
121 | this.value = "- -.-";
122 | } else {
123 | this.value = String.format("%.1f", value);
124 | }
125 | setGaugeValue(value);
126 | }
127 |
128 | private void setGaugeValue(final float value) {
129 |
130 | if (value > maximumValue) {
131 | gaugeValueView.setTextColor(Color.RED);
132 | } else {
133 | if (value < minimumValue) {
134 | gaugeValueView.setTextColor(Color.BLUE);
135 | } else {
136 | gaugeValueView.setTextColor(Color.GREEN);
137 | }
138 | }
139 |
140 | gaugeValueView.setText(this.value);
141 | }
142 |
143 | public void setTitle(final String title) {
144 | this.title = title;
145 | gaugeTitleView.setText(this.title);
146 | }
147 |
148 | public void setUnits(final String units) {
149 | this.units = units;
150 | gaugeUnitsView.setText(this.units);
151 | }
152 |
153 | public void setMinimumValue(float minimumValue) {
154 | this.minimumValue = minimumValue;
155 | }
156 | public void setMaximumValue(float maximumValue) {
157 | this.maximumValue = maximumValue;
158 | }
159 | public void setGaugeValueTextColor(final int color) {
160 | gaugeValueView.setTextColor(color);
161 | }
162 | }
163 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/widgets/GaugeNeedle.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.widgets;
18 |
19 | import android.content.Context;
20 | import android.util.AttributeSet;
21 | import android.widget.ImageView;
22 |
23 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
24 |
25 | public class GaugeNeedle extends ImageView {
26 |
27 | private final int NOT_SET_YET = Integer.MAX_VALUE;
28 |
29 | private int offsetCenterInDegrees = NOT_SET_YET;
30 | // private float lastValue;
31 |
32 | private int minValue = 0;
33 | private int maxValue = 360;
34 | private int minDegrees = -180;
35 | private int maxDegrees = 180;
36 | private float pivotPoint = .5f;
37 |
38 | public GaugeNeedle(Context context) {
39 | super(context);
40 | }
41 | public GaugeNeedle(Context context, AttributeSet attrs, int defStyle) {
42 | super(context, attrs, defStyle);
43 | }
44 | public GaugeNeedle(Context context, AttributeSet attrs) {
45 | super(context, attrs);
46 | }
47 |
48 | public void setValue(final float value) {
49 |
50 | // calculate our center point if it has not yet been calculated
51 | if (offsetCenterInDegrees == NOT_SET_YET) {
52 | offsetCenterInDegrees = maxDegrees - (maxDegrees - minDegrees) / 2 ;
53 | }
54 |
55 | final float scale = (float) (maxDegrees - minDegrees) / (maxValue - minValue) ;
56 | float newValue = (value - minValue) * scale - ((maxDegrees - minDegrees) / 2) + offsetCenterInDegrees;
57 |
58 | // peg the needle if our values are significantly beyond our borders (20+ degrees)
59 | if (newValue > maxDegrees + 20) newValue = maxDegrees + 20;
60 | if (newValue < minDegrees - 20) newValue = minDegrees - 20;
61 |
62 | // final RotateAnimation rotateAnimation = new RotateAnimation(lastValue, newValue,
63 | // Animation.RELATIVE_TO_SELF, 0.5f,
64 | // Animation.RELATIVE_TO_SELF, pivotPoint);
65 | //
66 | // rotateAnimation.setInterpolator(new LinearInterpolator());
67 | // rotateAnimation.setDuration(100);
68 | //
69 | // rotateAnimation.setFillEnabled(true);
70 | // rotateAnimation.setFillAfter(true);
71 | //
72 | // startAnimation(rotateAnimation);
73 |
74 | setPivotY(getHeight() * pivotPoint);
75 | setPivotX(getWidth() / 2);
76 |
77 | setRotation(newValue);
78 |
79 | // lastValue = newValue;
80 | AdaptiveLogger.log(String.format("GaugeNeedle %s - %s - %s", String.valueOf(value), String.valueOf(newValue), String.valueOf(scale)));
81 | }
82 |
83 | public int getMinValue() {
84 | return minValue;
85 | }
86 | public void setMinValue(int minValue) {
87 | if (minValue != this.minValue) {
88 | offsetCenterInDegrees = NOT_SET_YET;
89 | this.minValue = minValue;
90 | }
91 | }
92 | public int getMaxValue() {
93 | return maxValue;
94 | }
95 | public void setMaxValue(int maxValue) {
96 | if (maxValue != this.maxValue) {
97 | offsetCenterInDegrees = NOT_SET_YET;
98 | this.maxValue = maxValue;
99 | }
100 | }
101 | public int getMinDegrees() {
102 | return minDegrees;
103 | }
104 | public void setMinDegrees(int minDegrees) {
105 | if (minDegrees != this.minDegrees) {
106 | offsetCenterInDegrees = NOT_SET_YET;
107 | this.minDegrees = minDegrees;
108 | }
109 | }
110 | public int getMaxDegrees() {
111 | return maxDegrees;
112 | }
113 | public void setMaxDegrees(int maxDegrees) {
114 | if (maxDegrees != this.maxDegrees) {
115 | offsetCenterInDegrees = NOT_SET_YET;
116 | this.maxDegrees = maxDegrees;
117 | }
118 | }
119 | public float getPivotPoint() {
120 | return pivotPoint;
121 | }
122 | public void setPivotPoint(float pivotPoint) {
123 | this.pivotPoint = pivotPoint;
124 | }
125 | }
126 |
--------------------------------------------------------------------------------
/src/com/shellware/adaptronic/adaptivetuner/widgets/GaugeSlider.java:
--------------------------------------------------------------------------------
1 | /*
2 | * Copyright 2012 Shell M. Shrader
3 | *
4 | * Licensed under the Apache License, Version 2.0 (the "License");
5 | * you may not use this file except in compliance with the License.
6 | * You may obtain a copy of the License at
7 | *
8 | * http://www.apache.org/licenses/LICENSE-2.0
9 | *
10 | * Unless required by applicable law or agreed to in writing, software
11 | * distributed under the License is distributed on an "AS IS" BASIS,
12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 | * See the License for the specific language governing permissions and
14 | * limitations under the License.
15 | *
16 | */
17 | package com.shellware.adaptronic.adaptivetuner.widgets;
18 |
19 | import android.content.Context;
20 | import android.graphics.Typeface;
21 | import android.util.AttributeSet;
22 | import android.widget.ImageView;
23 | import android.widget.RelativeLayout;
24 | import android.widget.RelativeLayout.LayoutParams;
25 | import android.widget.TextView;
26 |
27 | import com.shellware.adaptronic.adaptivetuner.logging.AdaptiveLogger;
28 |
29 | public class GaugeSlider extends ImageView {
30 |
31 | private Context context;
32 | private int minValue = 0;
33 | private int maxValue = 360;
34 |
35 | private int usableUnits = 0;
36 |
37 | private String suffix = "";
38 |
39 | public GaugeSlider(Context context) {
40 | super(context);
41 | this.context = context;
42 | }
43 | public GaugeSlider(Context context, AttributeSet attrs, int defStyle) {
44 | super(context, attrs, defStyle);
45 | this.context = context;
46 | }
47 | public GaugeSlider(Context context, AttributeSet attrs) {
48 | super(context, attrs);
49 | this.context = context;
50 | }
51 |
52 | public void setValue(final float value) {
53 |
54 | if (value < minValue || value > maxValue) return;
55 |
56 | if (usableUnits == 0) {
57 | final RelativeLayout parent = (RelativeLayout) getParent();
58 | usableUnits = parent.getWidth();
59 | AdaptiveLogger.log("GaugeSlider usable units: " + usableUnits);
60 | }
61 |
62 | final float multiplier = usableUnits / (float) (maxValue - minValue);
63 |
64 | final LayoutParams params = (LayoutParams) getLayoutParams();
65 | params.leftMargin = (int) ((value - minValue) * multiplier) - (getWidth() / 2);
66 |
67 | setLayoutParams(params);
68 |
69 | AdaptiveLogger.log("GaugeSlider value and left margin: " + value + " - " + params.leftMargin);
70 | this.setLayoutParams(params);
71 |
72 | final RelativeLayout frame = (RelativeLayout) getParent().getParent();
73 | final TextView text = (TextView) frame.getChildAt(frame.getChildCount() - 1);
74 | text.setText(String.format("%.0f%s", value, suffix));
75 | }
76 |
77 | public int getMinValue() {
78 | return minValue;
79 | }
80 | public void setMinValue(int minValue) {
81 | RelativeLayout frame = (RelativeLayout) getParent().getParent();
82 | TextView text = (TextView) frame.getChildAt(frame.getChildCount() - 3);
83 | text.setText(String.format("%d", minValue));
84 |
85 | this.minValue = minValue;
86 | }
87 | public int getMaxValue() {
88 | return maxValue;
89 | }
90 | public void setMaxValue(int maxValue) {
91 | RelativeLayout frame = (RelativeLayout) getParent().getParent();
92 | TextView text = (TextView) frame.getChildAt(frame.getChildCount() - 2);
93 | text.setText(String.format("%d", maxValue));
94 |
95 | this.maxValue = maxValue;
96 | }
97 | public String getSuffix() {
98 | return suffix;
99 | }
100 | public void setSuffix(String suffix) {
101 | this.suffix = suffix;
102 |
103 | final RelativeLayout frame = (RelativeLayout) getParent().getParent();
104 |
105 | for (int i = 3;i > 0; i--) {
106 | final TextView text = (TextView) frame.getChildAt(frame.getChildCount() - i);
107 | text.setTypeface(Typeface.createFromAsset(context.getAssets(), "fonts/digital_7.ttf"), Typeface.BOLD);
108 | }
109 | }
110 | }
111 |
--------------------------------------------------------------------------------
/web_hi_res_1024.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/web_hi_res_1024.png
--------------------------------------------------------------------------------
/web_hi_res_512.png:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/synman/AdaptiveTuner/41ed77014ccab54609375225511d4736e45e8608/web_hi_res_512.png
--------------------------------------------------------------------------------