package cz.uhk.fim.dragonboatassistant.core;

import com.google.android.gms.common.ConnectionResult;
import com.google.android.gms.common.api.GoogleApiClient;
import com.google.android.gms.common.api.GoogleApiClient.ConnectionCallbacks;
import com.google.android.gms.common.api.GoogleApiClient.OnConnectionFailedListener;
import com.google.android.gms.common.api.PendingResult;
import com.google.android.gms.common.api.ResultCallback;
import com.google.android.gms.common.api.Status;
import com.google.android.gms.location.LocationListener;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationServices;
import com.google.android.gms.location.LocationSettingsRequest;
import com.google.android.gms.location.LocationSettingsResult;
import com.google.android.gms.location.LocationSettingsStatusCodes;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.MapFragment;
import com.google.android.gms.maps.OnMapReadyCallback;
import com.google.android.gms.maps.model.LatLng;

import android.app.Activity;
import android.content.IntentSender.SendIntentException;
import android.location.Location;
import android.os.Bundle;
import android.view.WindowManager;

public class GoogleAPIActivity extends Activity
		implements ConnectionCallbacks, OnConnectionFailedListener, OnMapReadyCallback, LocationListener {

	// mrknout na status.startResolutionForResult(GoogleAPIActivity.this, 1);

	GoogleApiClient googleApiClient;
	public Location lastKnownLocation;
	LocationRequest locationRequest;
	protected MapFragment mapFragment;
	protected GoogleMap map;

	protected float DISPLACEMENT = 30;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		System.out.println("Vytvářím třídu GoogleAPIActivity");
		// wake lock
		getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);

		// Create an instance of GoogleAPIClient.
		System.out.println("Vytvářím instanci GoogleAPIClient");
		if (googleApiClient == null) {
			googleApiClient = new GoogleApiClient.Builder(this).addConnectionCallbacks(this)
					.addOnConnectionFailedListener(this).addApi(LocationServices.API).build();
		}
		createLocationRequest();
	}

	@Override
	protected void onStart() {
		System.out.println("Připojuji GoogleAPIClient");
		googleApiClient.connect();
		super.onStart();
	}

	// nedat to spíše až do onDestroy ?
	@Override
	protected void onStop() {
		System.out.println("Odpojuji GoogleAPIClient");
		googleApiClient.disconnect();
		super.onStop();
	}

	protected void createLocationRequest() {
		// Create an instance of LocationRequest.
		System.out.println("Vytvářím instanci LocationRequest");
		locationRequest = new LocationRequest();
		locationRequest.setSmallestDisplacement(DISPLACEMENT);
		locationRequest.setInterval(10000);
		locationRequest.setFastestInterval(5000);
		locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);
		locationRequest.setPriority(100);

		LocationSettingsRequest.Builder builder = new LocationSettingsRequest.Builder()
				.addLocationRequest(locationRequest);

		PendingResult<LocationSettingsResult> result = LocationServices.SettingsApi
				.checkLocationSettings(googleApiClient, builder.build());

		result.setResultCallback(new ResultCallback<LocationSettingsResult>() {
			@Override
			public void onResult(LocationSettingsResult result) {
				final Status status = result.getStatus();

				switch (status.getStatusCode()) {
				case LocationSettingsStatusCodes.SUCCESS:
					// All location settings are satisfied. The client can
					// initialize location requests here.
					System.out.println("Všechna nastavení jsou v pořádku.");
					break;
				case LocationSettingsStatusCodes.RESOLUTION_REQUIRED:
					// Location settings are not satisfied, but this can be
					// fixed
					// by showing the user a dialog.
					System.out.println("Nastavení nejsou v pořádku a vyžaduje se interakce s uživatelem.");
					try {
						// Show the dialog by calling
						// startResolutionForResult(),
						// and check the result in onActivityResult().
						status.startResolutionForResult(GoogleAPIActivity.this, 1);
					} catch (SendIntentException e) {
						// Ignore the error.
					}
					break;
				case LocationSettingsStatusCodes.SETTINGS_CHANGE_UNAVAILABLE:
					// Location settings are not satisfied. However, we have no
					// way
					// to fix the settings so we won't show the dialog.
					System.out.println("Nastavení nejsou v pořádku a zároveň není k dispozici možné nastavení.");
					break;
				}
			}
		});
	}

	// Metody rozhraní ConnectionCallbacks, OnConnectionFailedListener
	@Override
	public void onConnected(Bundle connectionHint) {
		System.out.println("Byla vyvolána metoda onConnected()");
		lastKnownLocation = LocationServices.FusedLocationApi.getLastLocation(googleApiClient);
		//if (lastKnownLocation != null) {
			// ...
		//}
		startLocationUpdates();
	}

	protected void startLocationUpdates() {
		System.out.println("Spouštím pravidelné aktualizace polohy");
		LocationServices.FusedLocationApi.requestLocationUpdates(googleApiClient, locationRequest, this);
	}

	@Override
	public void onConnectionFailed(ConnectionResult arg0) {
		System.out.println("Byla vyvolána metoda onConnectionFailed()");
	}

	@Override
	public void onConnectionSuspended(int arg0) {
		System.out.println("Byla vyvolána metoda onConnectionSuspended()");
	}

	// Metoda rozhraní LocationListener
	@Override
	public void onLocationChanged(Location location) {
		System.out.println("Aktualizace polohy");
		lastKnownLocation = location;
		// updateMap(location);
		// renderTextViews();
	}

	// Metoda rozhraní OnMapReadyCallback
	@Override
	public void onMapReady(GoogleMap map) {
		System.out.println("Map is ready");
		this.map = map;
		map.setMapType(GoogleMap.MAP_TYPE_SATELLITE);
		map.setMyLocationEnabled(true);
	}

	protected void updateMap(Location loc, GoogleMap map) {
		//LatLng newPosition = new LatLng(loc.getLatitude(), loc.getLongitude());
		map.animateCamera(CameraUpdateFactory.newLatLng(new LatLng(loc.getLatitude(), loc.getLongitude())));
	}

}
