diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/InformDialog.java b/app/src/main/java/de/apps4ics/mountainnavigation/InformDialog.java new file mode 100644 index 0000000..e87c336 --- /dev/null +++ b/app/src/main/java/de/apps4ics/mountainnavigation/InformDialog.java @@ -0,0 +1,30 @@ +package de.apps4ics.mountainnavigation; + +import android.app.AlertDialog; +import android.app.Dialog; +import android.app.DialogFragment; +import android.os.Bundle; + +/** + * Created by Vinz on 12.03.2016. + */ +public class InformDialog extends DialogFragment { + private String title; + private String msg; + + public InformDialog(String title, String msg){ + this.title = title; + this.msg = msg; + } + + @Override + public Dialog onCreateDialog(Bundle savedInstanceState) { + AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); + builder.setTitle(title) + .setMessage(msg) + .setCancelable(false) + //.setIcon(res.getDrawable(R.mipmap.ic_info_icon)) + .setPositiveButton(R.string.inform_positive_button, null); + return builder.create(); + } +} \ No newline at end of file diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/InformListDialog.java b/app/src/main/java/de/apps4ics/mountainnavigation/InformListDialog.java new file mode 100644 index 0000000..c137380 --- /dev/null +++ b/app/src/main/java/de/apps4ics/mountainnavigation/InformListDialog.java @@ -0,0 +1,37 @@ +package de.apps4ics.mountainnavigation; + +import android.app.AlertDialog; +import android.app.Dialog; +import android.app.DialogFragment; +import android.content.DialogInterface; +import android.os.Bundle; +import android.widget.ListAdapter; + +/** + * Created by Vinz on 12.03.2016. + */ +public class InformListDialog extends DialogFragment { + private String title; + private ListAdapter adapter; + + public InformListDialog(String title, ListAdapter adapter){ + this.title = title; + this.adapter = adapter; + } + + @Override + public Dialog onCreateDialog(Bundle savedInstanceState) { + AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); + builder.setTitle(title) + .setAdapter(adapter, new DialogInterface.OnClickListener() { + @Override + public void onClick(DialogInterface dialog, int which) { + //nothing to do... + } + }) + .setCancelable(false) + //.setIcon(res.getDrawable(R.mipmap.ic_info_icon)) + .setPositiveButton(R.string.inform_positive_button, null); + return builder.create(); + } +} diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/MainActivity.java b/app/src/main/java/de/apps4ics/mountainnavigation/MainActivity.java index a17aac8..7732ccd 100644 --- a/app/src/main/java/de/apps4ics/mountainnavigation/MainActivity.java +++ b/app/src/main/java/de/apps4ics/mountainnavigation/MainActivity.java @@ -1,11 +1,6 @@ package de.apps4ics.mountainnavigation; -import android.app.Activity; -import android.app.AlertDialog; -import android.app.Dialog; -import android.app.DialogFragment; import android.content.Context; -import android.content.DialogInterface; import android.content.Intent; import android.content.res.Resources; import android.location.Criteria; @@ -25,14 +20,10 @@ import android.telephony.PhoneStateListener; import android.telephony.TelephonyManager; import android.util.Log; -import android.view.LayoutInflater; import android.view.View; -import android.view.ViewGroup; import android.support.v4.widget.DrawerLayout; import android.widget.AdapterView; -import android.widget.ArrayAdapter; import android.widget.ImageView; -import android.widget.ListAdapter; import android.widget.ListView; import android.widget.RelativeLayout; import android.widget.TableLayout; @@ -40,18 +31,6 @@ import android.widget.TextView; import android.widget.Toast; -import com.survivingwithandroid.weather.lib.WeatherClient; -import com.survivingwithandroid.weather.lib.WeatherCode; -import com.survivingwithandroid.weather.lib.WeatherConfig; -import com.survivingwithandroid.weather.lib.exception.WeatherLibException; -import com.survivingwithandroid.weather.lib.exception.WeatherProviderInstantiationException; -import com.survivingwithandroid.weather.lib.model.DayForecast; -import com.survivingwithandroid.weather.lib.model.HistoricalWeather; -import com.survivingwithandroid.weather.lib.model.Weather; -import com.survivingwithandroid.weather.lib.model.WeatherForecast; -import com.survivingwithandroid.weather.lib.provider.openweathermap.OpenweathermapProviderType; -import com.survivingwithandroid.weather.lib.request.WeatherRequest; - import org.osmdroid.api.IMapController; import org.osmdroid.bonuspack.overlays.Marker; import org.osmdroid.tileprovider.tilesource.TileSourceFactory; @@ -61,8 +40,6 @@ import java.text.SimpleDateFormat; import java.util.ArrayList; -import java.util.Arrays; -import java.util.Date; import java.util.List; import de.apps4ics.mountainnavigation.adapters.ImageListAdapter; @@ -84,7 +61,6 @@ private CharSequence mDrawerTitle; private static final int GPS_MIN_TIME = 5000; private static final int GPS_MIN_DIST = 5; - private static final String API_KEY = "fd4034defae557fd5f2fdaaf73c3402c"; private static ConnectivityManager cm; private static TelephonyManager tm; private static WifiManager wm; @@ -95,20 +71,10 @@ public static SimpleDateFormat df_hm; public static SimpleDateFormat df_full; - private Resources res; + private static Resources res; private FloatingActionButton fab; - private Weather todaysWeather; - private Weather tomorrowsWeather; - private HistoricalWeather histWeather; - private DayForecast todaysForecast; - private DayForecast tomorrowsForecast; - private WeatherClient weatherClient; - private static Integer[] severeWeatherCodes; - private static float minHotTemp; - private static float maxColdTemp; - private static float minWindySpeed; - private boolean showWeatherHints; + private static boolean showWeatherHints; private DatabaseHandler dbHandler; private PoiHandler poiHandler; @@ -170,70 +136,8 @@ initGps(); - WeatherClient.ClientBuilder weatherBuilder = new WeatherClient.ClientBuilder(); - WeatherConfig weatherConfig = new WeatherConfig(); - weatherConfig.unitSystem = WeatherConfig.UNIT_SYSTEM.M; - weatherConfig.ApiKey = API_KEY; - weatherConfig.lang = res.getString(R.string.lang_identifier); - weatherConfig.numDays = 2; - - minWindySpeed = 8; //http://www.wettergefahren-fruehwarnung.de/Artikel/beaufort.html - if(weatherConfig.unitSystem.equals(WeatherConfig.UNIT_SYSTEM.I)){ - minHotTemp = celsiusToFahrenheit(30); - maxColdTemp = celsiusToFahrenheit(10); - } else { - minHotTemp = 30; - maxColdTemp = 10; - } - showWeatherHints = true; - //TODO split into severe weather and foggy, windy, sunny, ... - severeWeatherCodes = new Integer[]{ - WeatherCode.TORNADO.getCode(), - WeatherCode.TROPICAL_STORM.getCode(), - WeatherCode.HURRICANE.getCode(), - WeatherCode.SEVERE_THUNDERSTORMS.getCode(), - WeatherCode.THUNDERSTORMS.getCode(), - WeatherCode.MIXED_RAIN_SNOW.getCode(), - WeatherCode.MIXED_RAIN_SLEET.getCode(), - WeatherCode.MIXED_SNOW_SLEET.getCode(), - WeatherCode.FREEZING_DRIZZLE.getCode(), - WeatherCode.FREEZING_RAIN.getCode(), - WeatherCode.HEAVY_SHOWERS.getCode(), - WeatherCode.SNOW_FLURRIES.getCode(), - WeatherCode.LIGHT_SNOW_SHOWERS.getCode(), - WeatherCode.BLOWING_SNOW.getCode(), - WeatherCode.SNOW.getCode(), - WeatherCode.HAIL.getCode(), - WeatherCode.SLEET.getCode(), - WeatherCode.FOGGY.getCode(), - WeatherCode.HAZE.getCode(), - WeatherCode.WINDY.getCode(), - WeatherCode.COLD.getCode(), - WeatherCode.SUNNY.getCode(), - WeatherCode.MIXED_RAIN_AND_HAIL.getCode(), - WeatherCode.ISOLATED_THUNDERSTORMS.getCode(), - WeatherCode.SCATTERED_THUNDERSTORMS.getCode(), - WeatherCode.HEAVY_SNOW.getCode(), - WeatherCode.SCATTERED_SNOW_SHOWERS.getCode(), - WeatherCode.THUNDERSHOWERS.getCode(), - WeatherCode.SNOW_SHOWERS.getCode(), - WeatherCode.ISOLATED_THUDERSHOWERS.getCode(), - WeatherCode.TORNADO.getCode() - }; - - weatherClient = null; - try { - weatherClient = weatherBuilder.attach(getApplicationContext()) - .provider(new OpenweathermapProviderType()) - .httpClient(com.survivingwithandroid.weather.lib.client.okhttp.WeatherDefaultClient.class) - .config(weatherConfig) - .build(); - } catch (WeatherProviderInstantiationException e) { - e.printStackTrace(); - } - fab = (FloatingActionButton) findViewById(R.id.fab); fab.setOnClickListener(new View.OnClickListener() { @Override @@ -277,14 +181,6 @@ long f_id = dbHandler.addPoi(fountain); } - public static float celsiusToFahrenheit(float c) { - return c * 9.0f/5.0f + 32; - } - - public static float fahrenheitToCelsius(float f) { - return (f - 32.0f) * 5.0f/9.0f; - } - private void toggleDrawerItems(TableLayout layout, int position){ TableRow tr = (TableRow) layout.getChildAt(0); //TODO is tablerow? TextView tv = null; @@ -325,6 +221,14 @@ } } + public static Resources getRes() { + return res; + } + + public static boolean showWeatherHints() { + return showWeatherHints; + } + public static List getFoundLocations() { return foundLocations; } @@ -535,91 +439,8 @@ double lat = location.getLatitude(); double lon = location.getLongitude(); GeoPoint gp = new GeoPoint(lat, lon); - addSimpleMarker(gp); - mapController.setCenter(gp); - - //TODO Move this to the not-yet-implemented upload method - weatherClient.getForecastWeather(new WeatherRequest(lon, lat), new WeatherClient.ForecastWeatherEventListener() { - @Override - public void onWeatherRetrieved(WeatherForecast forecast) { - todaysForecast = forecast.getForecast(0); - tomorrowsForecast = forecast.getForecast(1); - todaysWeather = todaysForecast.weather; - tomorrowsWeather = tomorrowsForecast.weather; - Log.d(TAG, "City [" + todaysWeather.location.getCity() + "] Current temp: " + todaysWeather.temperature.getTemp()); - - String title = String.format("Weather for %s in %s", todaysWeather.location.getCity(), todaysWeather.location.getCountry()); - String msg = String.format("%1$.1f%2$s (%3$.1f%4$s/%5$.1f%6$s)\nSunrise: %7$s\nSunset: %8$s\nWeatherCode: %9$d\nWeatherId: %10$d", - todaysForecast.forecastTemp.day, - forecast.getUnit().tempUnit, - todaysForecast.forecastTemp.min, - forecast.getUnit().tempUnit, - todaysForecast.forecastTemp.max, - forecast.getUnit().tempUnit, - df_hm.format(new Date(todaysWeather.location.getSunrise() * 1000)), - df_hm.format(new Date(todaysWeather.location.getSunset() * 1000)), - todaysWeather.currentCondition.getWeatherCode().getCode(), - todaysWeather.currentCondition.getWeatherId()); - //InformDialog informWeatherDialog = new InformDialog(title, msg); - //informWeatherDialog.show(getFragmentManager(), "Inform Dialog"); - boolean isSevereWeather = isSevereWeather(todaysWeather.currentCondition.getWeatherCode().getCode()); - Log.d(TAG, title + ": " + msg); - Log.d(TAG, "isSevereWeather? " + isSevereWeather); - //TODO add more hints - if (showWeatherHints) { - List titles = new ArrayList<>(); - List descs = new ArrayList<>(); - if (isSunny()) { - titles.add("Sunny"); - descs.add("The weather might be sunny. You should take some suncream with you!"); - } - if (isHot()) { - titles.add("Hot"); - descs.add("It is hot outside. Remember to take enough to drink with you."); - } - if (isCold()) { - titles.add("Cold"); - descs.add("The weather might be cold. You should take some warm clothes with you!"); - } - if (isWindy()) { - titles.add("Windy"); - descs.add("The weather might be windy. You should take some windproof clothes with you!"); - } - if (isAfterSunset()) { - titles.add("Sunset"); - descs.add("It is already after sunset. Better take a head lamp with you."); - } - if (titles.size() > 0 && descs.size() > 0) { - String[] titleArr = new String[titles.size()]; - String[] descArr = new String[descs.size()]; - titleArr = titles.toArray(titleArr); - descArr = descs.toArray(descArr); - WarningListAdapter warningAdapter = new WarningListAdapter(MainActivity.this, titleArr, descArr); - InformListDialog weatherHintDialog = new InformListDialog(getString(R.string.hint_dialog_title), warningAdapter); - weatherHintDialog.show(getFragmentManager(), "Warning Hint Dialog"); - } - } - if (isSevereWeather) { - String warnMsg = String.format(getString(R.string.weather_warning_dialog_msg), todaysWeather.location.getCity(), todaysWeather.currentCondition.getWeatherCode().getLabel(getApplicationContext())); - InformDialog informAlertDialog = new InformDialog(getString(R.string.weather_warning_dialog_title), warnMsg); - informAlertDialog.show(getFragmentManager(), "Inform Dialog - Weather Warning"); - } - } - - @Override - public void onWeatherError(WeatherLibException wle) { - Log.e(TAG, "Weather error - parsing data"); - wle.printStackTrace(); - } - - @Override - public void onConnectionError(Throwable t) { - Log.e(TAG, "Connection Error"); - t.printStackTrace(); - } - }); } @Override @@ -637,118 +458,6 @@ Log.d(TAG, "onProviderDisabled: " + provider); } - private boolean isSevereWeather(int weatherCode){ - return Arrays.asList(severeWeatherCodes).contains(weatherCode); - } - - private boolean isAfterSunset(){ - return isAfterSunset(System.currentTimeMillis()); - } - - private boolean isAfterSunset(long time){ - return time > (todaysWeather.location.getSunset() * 1000) && time < (tomorrowsWeather.location.getSunrise() * 1000); - } - - private boolean isHot(){ - return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.SUNNY.getCode() || - (todaysWeather.temperature.getTemp() >= minHotTemp || todaysWeather.temperature.getMaxTemp() >= minHotTemp); - } - - private boolean isSunny(){ - return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.SUNNY.getCode(); - } - - private boolean isCold(){ - return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.COLD.getCode() || - (todaysWeather.temperature.getTemp() <= maxColdTemp || todaysWeather.temperature.getMinTemp() <= maxColdTemp); - } - - private boolean isWindy(){ - return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.WINDY.getCode() || - (todaysWeather.wind.getSpeed() >= minWindySpeed); - } - - private boolean isDark(long length){ - return isDark(System.currentTimeMillis(), length); - } - - private boolean isDark(long time, long length){ - return isAfterSunset(time) || isAfterSunset(time + length); - } - - private HistoricalWeather getWeather(float lat, float lon, long start, long end){ - Date startDate = new Date(start / 1000); //OWM uses seconds instead of milliseconds - Date endDate = new Date(end / 1000); - histWeather = null; - weatherClient.getHistoricalWeather(new WeatherRequest(lon, lat), startDate, endDate, new WeatherClient.HistoricalWeatherEventListener() { - @Override - public void onWeatherRetrieved(HistoricalWeather historicalWeather) { - //TODO check if it was sunny/rainy and set fountain options based on this - histWeather = historicalWeather; - } - - @Override - public void onWeatherError(WeatherLibException wle) { - Log.e(TAG, "Weather error - parsing data"); - wle.printStackTrace(); - } - - @Override - public void onConnectionError(Throwable t) { - Log.e(TAG, "Connection Error"); - t.printStackTrace(); - } - }); - return histWeather; - } - - public class InformDialog extends DialogFragment { - private String title; - private String msg; - - public InformDialog(String title, String msg){ - this.title = title; - this.msg = msg; - } - - @Override - public Dialog onCreateDialog(Bundle savedInstanceState) { - AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); - builder.setTitle(title) - .setMessage(msg) - .setCancelable(false) - //.setIcon(res.getDrawable(R.mipmap.ic_info_icon)) - .setPositiveButton(R.string.inform_positive_button, null); - return builder.create(); - } - } - - public class InformListDialog extends DialogFragment { - private String title; - private ListAdapter adapter; - - public InformListDialog(String title, ListAdapter adapter){ - this.title = title; - this.adapter = adapter; - } - - @Override - public Dialog onCreateDialog(Bundle savedInstanceState) { - AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); - builder.setTitle(title) - .setAdapter(adapter, new DialogInterface.OnClickListener() { - @Override - public void onClick(DialogInterface dialog, int which) { - //nothing to do... - } - }) - .setCancelable(false) - //.setIcon(res.getDrawable(R.mipmap.ic_info_icon)) - .setPositiveButton(R.string.inform_positive_button, null); - return builder.create(); - } - } - public static NetworkInfo getActiveNetwork() { return activeNetwork; } @@ -766,32 +475,6 @@ return activeNetwork != null && activeNetwork.isConnected(); } - private class WarningListAdapter extends ArrayAdapter { - - private final Activity context; - private final String[] texts; - private final String[] descs; - - public WarningListAdapter(Activity context, String[] texts, String[] descs) { - super(context, R.layout.warning_list_item, texts); - this.context = context; - this.texts = texts; - this.descs = descs; - } - - @Override - public View getView(int position, View view, ViewGroup parent) { - LayoutInflater inflater = context.getLayoutInflater(); - View rowView= inflater.inflate(R.layout.warning_list_item, null, true); - TextView txtTitle = (TextView) rowView.findViewById(R.id.warning_text_title); - - TextView txtDesc = (TextView) rowView.findViewById(R.id.warning_text_desc); - txtTitle.setText(texts[position]); - txtDesc.setText(descs[position]); - return rowView; - } - } - @Override protected void onActivityResult(int requestCode, int resultCode, Intent data) { super.onActivityResult(requestCode, resultCode, data); @@ -832,4 +515,4 @@ protected void onDestroy() { super.onDestroy(); } -} +} \ No newline at end of file diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/MyWeather.java b/app/src/main/java/de/apps4ics/mountainnavigation/MyWeather.java index bd126c1..06d1650 100644 --- a/app/src/main/java/de/apps4ics/mountainnavigation/MyWeather.java +++ b/app/src/main/java/de/apps4ics/mountainnavigation/MyWeather.java @@ -1,7 +1,28 @@ package de.apps4ics.mountainnavigation; +import com.survivingwithandroid.weather.lib.model.DayForecast; +import com.survivingwithandroid.weather.lib.model.HistoricalWeather; +import com.survivingwithandroid.weather.lib.model.Weather; +import com.survivingwithandroid.weather.lib.model.WeatherForecast; + /** * Created by Vinz on 07.03.2016. */ public class MyWeather { + + public MyWeather(HistoricalWeather historicalWeather) { + ; //TODO + } + + public MyWeather(WeatherForecast weatherForecast) { + ; //TODO + } + + public MyWeather(DayForecast dayForecast) { + ; //TODO + } + + public MyWeather(Weather weather) { + ; //TODO + } } diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/adapters/WarningListAdapter.java b/app/src/main/java/de/apps4ics/mountainnavigation/adapters/WarningListAdapter.java new file mode 100644 index 0000000..0e4c13f --- /dev/null +++ b/app/src/main/java/de/apps4ics/mountainnavigation/adapters/WarningListAdapter.java @@ -0,0 +1,39 @@ +package de.apps4ics.mountainnavigation.adapters; + +import android.app.Activity; +import android.view.LayoutInflater; +import android.view.View; +import android.view.ViewGroup; +import android.widget.ArrayAdapter; +import android.widget.TextView; + +import de.apps4ics.mountainnavigation.R; + +/** + * Created by Vinz on 12.03.2016. + */ +public class WarningListAdapter extends ArrayAdapter { + + private final Activity context; + private final String[] texts; + private final String[] descs; + + public WarningListAdapter(Activity context, String[] texts, String[] descs) { + super(context, R.layout.warning_list_item, texts); + this.context = context; + this.texts = texts; + this.descs = descs; + } + + @Override + public View getView(int position, View view, ViewGroup parent) { + LayoutInflater inflater = context.getLayoutInflater(); + View rowView= inflater.inflate(R.layout.warning_list_item, null, true); + TextView txtTitle = (TextView) rowView.findViewById(R.id.warning_text_title); + + TextView txtDesc = (TextView) rowView.findViewById(R.id.warning_text_desc); + txtTitle.setText(texts[position]); + txtDesc.setText(descs[position]); + return rowView; + } +} diff --git a/app/src/main/java/de/apps4ics/mountainnavigation/handlers/WeatherHandler.java b/app/src/main/java/de/apps4ics/mountainnavigation/handlers/WeatherHandler.java index 8df971f..c5117e2 100644 --- a/app/src/main/java/de/apps4ics/mountainnavigation/handlers/WeatherHandler.java +++ b/app/src/main/java/de/apps4ics/mountainnavigation/handlers/WeatherHandler.java @@ -1,22 +1,128 @@ package de.apps4ics.mountainnavigation.handlers; +import android.app.Activity; +import android.app.FragmentManager; import android.content.Context; +import android.content.res.Resources; +import android.util.Log; +import com.survivingwithandroid.weather.lib.WeatherClient; +import com.survivingwithandroid.weather.lib.WeatherCode; +import com.survivingwithandroid.weather.lib.WeatherConfig; +import com.survivingwithandroid.weather.lib.exception.WeatherLibException; +import com.survivingwithandroid.weather.lib.exception.WeatherProviderInstantiationException; +import com.survivingwithandroid.weather.lib.model.DayForecast; +import com.survivingwithandroid.weather.lib.model.HistoricalWeather; import com.survivingwithandroid.weather.lib.model.Weather; +import com.survivingwithandroid.weather.lib.model.WeatherForecast; +import com.survivingwithandroid.weather.lib.provider.openweathermap.OpenweathermapProviderType; +import com.survivingwithandroid.weather.lib.request.WeatherRequest; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Date; +import java.util.List; + +import de.apps4ics.mountainnavigation.InformDialog; +import de.apps4ics.mountainnavigation.InformListDialog; import de.apps4ics.mountainnavigation.MainActivity; import de.apps4ics.mountainnavigation.MyWeather; +import de.apps4ics.mountainnavigation.R; import de.apps4ics.mountainnavigation.WeatherDatabase; +import de.apps4ics.mountainnavigation.adapters.WarningListAdapter; /** * Created by Vinz on 06.03.2016. */ public class WeatherHandler { + private static final String API_KEY = "fd4034defae557fd5f2fdaaf73c3402c"; //OpenWeatherMap API Key private Context context; private WeatherDatabase weatherDb; + private WeatherClient weatherClient; + private Weather todaysWeather; + private Weather tomorrowsWeather; + private HistoricalWeather histWeather; + private DayForecast todaysForecast; + private DayForecast tomorrowsForecast; + private static float minHotTemp; + private static float maxColdTemp; + private static float minWindySpeed; + + private static Activity activity; + private static FragmentManager fragmentManager; + + //TODO split into severe weather and foggy, windy, sunny, ... + private static final Integer[] severeWeatherCodes = new Integer[]{ + WeatherCode.TORNADO.getCode(), + WeatherCode.TROPICAL_STORM.getCode(), + WeatherCode.HURRICANE.getCode(), + WeatherCode.SEVERE_THUNDERSTORMS.getCode(), + WeatherCode.THUNDERSTORMS.getCode(), + WeatherCode.MIXED_RAIN_SNOW.getCode(), + WeatherCode.MIXED_RAIN_SLEET.getCode(), + WeatherCode.MIXED_SNOW_SLEET.getCode(), + WeatherCode.FREEZING_DRIZZLE.getCode(), + WeatherCode.FREEZING_RAIN.getCode(), + WeatherCode.HEAVY_SHOWERS.getCode(), + WeatherCode.SNOW_FLURRIES.getCode(), + WeatherCode.LIGHT_SNOW_SHOWERS.getCode(), + WeatherCode.BLOWING_SNOW.getCode(), + WeatherCode.SNOW.getCode(), + WeatherCode.HAIL.getCode(), + WeatherCode.SLEET.getCode(), + WeatherCode.FOGGY.getCode(), + WeatherCode.HAZE.getCode(), + WeatherCode.WINDY.getCode(), + WeatherCode.COLD.getCode(), + WeatherCode.SUNNY.getCode(), + WeatherCode.MIXED_RAIN_AND_HAIL.getCode(), + WeatherCode.ISOLATED_THUNDERSTORMS.getCode(), + WeatherCode.SCATTERED_THUNDERSTORMS.getCode(), + WeatherCode.HEAVY_SNOW.getCode(), + WeatherCode.SCATTERED_SNOW_SHOWERS.getCode(), + WeatherCode.THUNDERSHOWERS.getCode(), + WeatherCode.SNOW_SHOWERS.getCode(), + WeatherCode.ISOLATED_THUDERSHOWERS.getCode(), + WeatherCode.TORNADO.getCode() + }; public WeatherHandler(Context context) { weatherDb = new WeatherDatabase(context); + + try { + activity = (Activity) context; + fragmentManager = activity.getFragmentManager(); + } catch(ClassCastException e) { + Log.e(MainActivity.TAG, "Could not get fragment manager!"); + //TODO close app? + } + + WeatherClient.ClientBuilder weatherBuilder = new WeatherClient.ClientBuilder(); + WeatherConfig weatherConfig = new WeatherConfig(); + weatherConfig.unitSystem = WeatherConfig.UNIT_SYSTEM.M; + weatherConfig.ApiKey = API_KEY; + weatherConfig.lang = MainActivity.getRes().getString(R.string.lang_identifier); + weatherConfig.numDays = 2; + + minWindySpeed = 8; //http://www.wettergefahren-fruehwarnung.de/Artikel/beaufort.html + if(weatherConfig.unitSystem.equals(WeatherConfig.UNIT_SYSTEM.I)){ + minHotTemp = celsiusToFahrenheit(30); + maxColdTemp = celsiusToFahrenheit(10); + } else { + minHotTemp = 30; + maxColdTemp = 10; + } + + weatherClient = null; + try { + weatherClient = weatherBuilder.attach(context) + .provider(new OpenweathermapProviderType()) + .httpClient(com.survivingwithandroid.weather.lib.client.okhttp.WeatherDefaultClient.class) + .config(weatherConfig) + .build(); + } catch (WeatherProviderInstantiationException e) { + e.printStackTrace(); + } } public void getCurrentWeather() { @@ -42,20 +148,84 @@ return null; } - public void getForecast(long start, long end, int step) { - getForecast(start, end, step, 0); + public void getForecast(double lat, double lon, int days) { + getForecast(lat, lon, days, 0); } - public void getForecast(long start, long end, int step, int offset) { + public void getForecast(double lat, double lon, int days, int offset) { +//TODO Move this to the not-yet-implemented upload method + weatherClient.getForecastWeather(new WeatherRequest(lon, lat), new WeatherClient.ForecastWeatherEventListener() { + @Override + public void onWeatherRetrieved(WeatherForecast forecast) { + todaysForecast = forecast.getForecast(0); + tomorrowsForecast = forecast.getForecast(1); + todaysWeather = todaysForecast.weather; + tomorrowsWeather = tomorrowsForecast.weather; + Log.d(MainActivity.TAG, "City [" + todaysWeather.location.getCity() + "] Current temp: " + todaysWeather.temperature.getTemp()); + String title = String.format("Weather for %s in %s", todaysWeather.location.getCity(), todaysWeather.location.getCountry()); + String msg = String.format("%1$.1f%2$s (%3$.1f%4$s/%5$.1f%6$s)\nSunrise: %7$s\nSunset: %8$s\nWeatherCode: %9$d\nWeatherId: %10$d", + todaysForecast.forecastTemp.day, + forecast.getUnit().tempUnit, + todaysForecast.forecastTemp.min, + forecast.getUnit().tempUnit, + todaysForecast.forecastTemp.max, + forecast.getUnit().tempUnit, + MainActivity.df_hm.format(new Date(todaysWeather.location.getSunrise() * 1000)), + MainActivity.df_hm.format(new Date(todaysWeather.location.getSunset() * 1000)), + todaysWeather.currentCondition.getWeatherCode().getCode(), + todaysWeather.currentCondition.getWeatherId()); + Log.d(MainActivity.TAG, title + ": " + msg); + displayHints(); + displaySevereWeather(); + } + + @Override + public void onWeatherError(WeatherLibException wle) { + Log.e(MainActivity.TAG, "Weather error - parsing data"); + wle.printStackTrace(); + } + + @Override + public void onConnectionError(Throwable t) { + Log.e(MainActivity.TAG, "Connection Error"); + t.printStackTrace(); + } + }); } - public void getForecastOnline(long start, long end, int step) { - + public MyWeather getForecastOnline(long start, long end, int step) { + return new MyWeather(new WeatherForecast()); } - public void getForecastCached(long start, long end, int step, int offset) { + public MyWeather getForecastCached(long start, long end, int step, int offset) { + return new MyWeather(new WeatherForecast()); + } + public MyWeather getHistoricalWeather(float lat, float lon, long start, long end){ + Date startDate = new Date(start / 1000); //OWM uses seconds instead of milliseconds + Date endDate = new Date(end / 1000); + histWeather = null; + weatherClient.getHistoricalWeather(new WeatherRequest(lon, lat), startDate, endDate, new WeatherClient.HistoricalWeatherEventListener() { + @Override + public void onWeatherRetrieved(HistoricalWeather historicalWeather) { + //TODO check if it was sunny/rainy and set fountain options based on this + histWeather = historicalWeather; + } + + @Override + public void onWeatherError(WeatherLibException wle) { + Log.e(MainActivity.TAG, "Weather error - parsing data"); + wle.printStackTrace(); + } + + @Override + public void onConnectionError(Throwable t) { + Log.e(MainActivity.TAG, "Connection Error"); + t.printStackTrace(); + } + }); + return new MyWeather(histWeather); } private void convertWeatherLibWeather(Weather weather) { @@ -65,4 +235,98 @@ private void insertIntoDatabase(MyWeather weather) { weatherDb.insertWeather(weather); } + + private void displayHints() { + //TODO add more hints + if (MainActivity.showWeatherHints()) { + List titles = new ArrayList<>(); + List descs = new ArrayList<>(); + if (isSunny()) { + titles.add("Sunny"); + descs.add("The weather might be sunny. You should take some suncream with you!"); + } + if (isHot()) { + titles.add("Hot"); + descs.add("It is hot outside. Remember to take enough to drink with you."); + } + if (isCold()) { + titles.add("Cold"); + descs.add("The weather might be cold. You should take some warm clothes with you!"); + } + if (isWindy()) { + titles.add("Windy"); + descs.add("The weather might be windy. You should take some windproof clothes with you!"); + } + if (isAfterSunset()) { + titles.add("Sunset"); + descs.add("It is already after sunset. Better take a head lamp with you."); + } + if (titles.size() > 0 && descs.size() > 0) { + String[] titleArr = new String[titles.size()]; + String[] descArr = new String[descs.size()]; + titleArr = titles.toArray(titleArr); + descArr = descs.toArray(descArr); + WarningListAdapter warningAdapter = new WarningListAdapter(activity, titleArr, descArr); + InformListDialog weatherHintDialog = new InformListDialog(MainActivity.getRes().getString(R.string.hint_dialog_title), warningAdapter); + weatherHintDialog.show(fragmentManager, "Warning Hint Dialog"); + } + } + } + + private void displaySevereWeather() { + if (isSevereWeather(todaysWeather.currentCondition.getWeatherCode().getCode())) { + Log.d(MainActivity.TAG, "It is severe weather! :("); + Resources res = MainActivity.getRes(); + String warnMsg = String.format(res.getString(R.string.weather_warning_dialog_msg), todaysWeather.location.getCity(), todaysWeather.currentCondition.getWeatherCode().getLabel(context)); + InformDialog informAlertDialog = new InformDialog(res.getString(R.string.weather_warning_dialog_title), warnMsg); + informAlertDialog.show(fragmentManager, "Inform Dialog - Weather Warning"); + } + } + + private boolean isSevereWeather(int weatherCode){ + return Arrays.asList(severeWeatherCodes).contains(weatherCode); + } + + private boolean isAfterSunset(){ + return isAfterSunset(System.currentTimeMillis()); + } + + private boolean isAfterSunset(long time){ + return time > (todaysWeather.location.getSunset() * 1000) && time < (tomorrowsWeather.location.getSunrise() * 1000); + } + + private boolean isHot(){ + return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.SUNNY.getCode() || + (todaysWeather.temperature.getTemp() >= minHotTemp || todaysWeather.temperature.getMaxTemp() >= minHotTemp); + } + + private boolean isSunny(){ + return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.SUNNY.getCode(); + } + + private boolean isCold(){ + return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.COLD.getCode() || + (todaysWeather.temperature.getTemp() <= maxColdTemp || todaysWeather.temperature.getMinTemp() <= maxColdTemp); + } + + private boolean isWindy(){ + return todaysWeather.currentCondition.getWeatherCode().getCode() == WeatherCode.WINDY.getCode() || + (todaysWeather.wind.getSpeed() >= minWindySpeed); + } + + private boolean isDark(long length){ + return isDark(System.currentTimeMillis(), length); + } + + private boolean isDark(long time, long length){ + return isAfterSunset(time) || isAfterSunset(time + length); + } + + public static float celsiusToFahrenheit(float c) { + return c * 9.0f/5.0f + 32; + } + + public static float fahrenheitToCelsius(float f) { + return (f - 32.0f) * 5.0f/9.0f; + } }