Java tutorial
/* * MIT License * * Copyright (c) 2016 - Valentin Polo * * Permission is hereby granted, free of charge, to any person obtaining a copy * of this software and associated documentation files (the "Software"), to deal * in the Software without restriction, including without limitation the rights * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell * copies of the Software, and to permit persons to whom the Software is * furnished to do so, subject to the following conditions: * * The above copyright notice and this permission notice shall be included in all * copies or substantial portions of the Software. * * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE * SOFTWARE. */ package xyz.valentin.marineoh; import android.*; import android.Manifest; import android.app.Activity; import android.app.ProgressDialog; import android.content.DialogInterface; import android.content.Intent; import android.content.pm.PackageManager; import android.location.Location; import android.net.Uri; import android.support.annotation.NonNull; import android.support.annotation.Nullable; import android.support.v4.app.ActivityCompat; import android.support.v7.app.AlertDialog; import android.support.v7.app.AppCompatActivity; import android.os.Bundle; import android.text.TextUtils; import android.util.Log; import android.view.Menu; import android.view.MenuInflater; import android.view.View; import android.view.inputmethod.InputMethodManager; import android.widget.AdapterView; import android.widget.AutoCompleteTextView; import android.widget.Button; import android.widget.ProgressBar; import android.widget.Toast; import android.widget.ToggleButton; import com.google.android.gms.common.ConnectionResult; import com.google.android.gms.common.api.GoogleApiClient; import com.google.android.gms.common.api.PendingResult; import com.google.android.gms.common.api.ResultCallback; 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.places.AutocompletePrediction; import com.google.android.gms.location.places.Place; import com.google.android.gms.location.places.PlaceBuffer; import com.google.android.gms.location.places.Places; import com.google.android.gms.maps.model.LatLng; import com.google.android.gms.maps.model.LatLngBounds; import com.onesignal.OneSignal; import butterknife.Bind; import butterknife.ButterKnife; import butterknife.OnCheckedChanged; import butterknife.OnClick; import retrofit2.Call; import retrofit2.Callback; import retrofit2.Response; import xyz.valentin.marineoh.adapters.PlaceAutocompleteAdapter; import xyz.valentin.marineoh.fragments.TestFragment; import xyz.valentin.marineoh.models.GoogleMaps.Itinerary; import xyz.valentin.marineoh.models.ItinerarySearch; public class BaseActivity extends AppCompatActivity implements GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener, LocationListener, TestFragment.OnFragmentInteractionListener { @Bind(R.id.originEditTextBaseActivity) public AutoCompleteTextView mOriginEditText; @Bind(R.id.destinationEditTextBaseActivity) public AutoCompleteTextView mDestinationEditText; @Bind(R.id.useGeolocationToggleButtonBaseActivity) public ToggleButton mUseGeolocationToggleButton; @Bind(R.id.findItineraryButtonBaseActivity) public Button mFindItineraryButton; @Bind(R.id.displayTimetablesButtonBaseActivity) public Button mDisplayScheduleButton; protected GoogleApiClient mGoogleApiClient; protected LocationRequest mLocationRequest; protected Location mCurrentLocation; private static final String TAG = "BaseActivity"; private static final int PERMS_LOCATION = 42; private ItinerarySearch mItinerarySearch; private PlaceAutocompleteAdapter mAdapter; private static final LatLngBounds BOUNDS_GREATER_BSM = new LatLngBounds(new LatLng(50.580934, 1.580658), new LatLng(50.751975, 1.692581)); private TestFragment mTestFragment; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_base); ButterKnife.bind(this); // Push notifications OneSignal.startInit(this).init(); // Google Play Services buildGooglePlayServicesClient(); // Autocomplete buildAutocomplete(); // if (findViewById(R.id.testFragmentContainerLinearLayout) != null) { // if (savedInstanceState != null) { // System.out.println("saved instance!"); // return; // } // // mTestFragment = TestFragment.newInstance("PARAM1", "PARAM2"); // getSupportFragmentManager() // .beginTransaction() // .add(R.id.testFragmentContainerLinearLayout, mTestFragment) // .hide(mTestFragment) // .commit(); // } else { // System.out.println("no view"); // } } @Override public boolean onCreateOptionsMenu(Menu menu) { MenuInflater menuInflater = getMenuInflater(); menuInflater.inflate(R.menu.options_menu, menu); return true; } @OnClick(R.id.useGeolocationToggleButtonBaseActivity) public void toggleGeolocationButton() { if (ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { ActivityCompat.requestPermissions(this, new String[] { Manifest.permission.ACCESS_FINE_LOCATION }, PERMS_LOCATION); } mOriginEditText.setEnabled(!mUseGeolocationToggleButton.isChecked()); mOriginEditText.setText(""); } @OnClick(R.id.findItineraryButtonBaseActivity) public void findItineraries() { // getSupportFragmentManager() // .beginTransaction() // .show(mTestFragment) // .commit(); final ProgressDialog progressDialog = ProgressDialog.show(this, "", "Recherche en cours...", true); if ((TextUtils.isEmpty(mOriginEditText.getText()) && !mUseGeolocationToggleButton.isChecked()) || TextUtils.isEmpty(mDestinationEditText.getText())) { progressDialog.hide(); return; } final Intent intent = new Intent(this, ItinerariesActivity.class); if (mUseGeolocationToggleButton.isChecked()) { mItinerarySearch = new ItinerarySearch(mCurrentLocation, mDestinationEditText.getText().toString()); } else { mItinerarySearch = new ItinerarySearch(mOriginEditText.getText().toString(), mDestinationEditText.getText().toString()); } mItinerarySearch.search().enqueue(new Callback<Itinerary>() { @Override public void onResponse(Call<Itinerary> call, Response<Itinerary> response) { progressDialog.hide(); mItinerarySearch.setItinerary(response.body()); if (mItinerarySearch.getItinerary().getRoutes().size() == 0) { displayNoItineraryFoundDialog(); return; } intent.putExtra("itinerarySearch", mItinerarySearch); startActivity(intent); } @Override public void onFailure(Call<Itinerary> call, Throwable t) { progressDialog.hide(); } }); } @OnClick(R.id.displayTimetablesButtonBaseActivity) public void displaySchedules() { Intent intent = new Intent(this, SchedulesActivity.class); startActivity(intent); } @Override public void onConnected(@Nullable Bundle pBundle) { if (ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { return; } if (mCurrentLocation == null) { mCurrentLocation = LocationServices.FusedLocationApi.getLastLocation(mGoogleApiClient); } startLocationUpdates(); } @Override public void onConnectionSuspended(int pI) { mGoogleApiClient.connect(); } @Override public void onLocationChanged(Location pLocation) { mCurrentLocation = pLocation; Log.i(TAG, "onLocationChanged()" + pLocation.toString()); } @Override public void onConnectionFailed(ConnectionResult pConnectionResult) { Log.e(TAG, "onConnectionFailed: ConnectionResult.getErrorCode() = " + pConnectionResult.getErrorCode()); } @Override public void onRequestPermissionsResult(int requestCode, @NonNull String[] permissions, @NonNull int[] grantResults) { switch (requestCode) { case PERMS_LOCATION: { if (grantResults.length > 0 && grantResults[0] == PackageManager.PERMISSION_GRANTED) { startLocationUpdates(); } else { mUseGeolocationToggleButton.setChecked(false); mOriginEditText.setEnabled(true); mOriginEditText.setText(""); } } } } protected synchronized void buildGooglePlayServicesClient() { mGoogleApiClient = new GoogleApiClient.Builder(this).enableAutoManage(this, this) .addConnectionCallbacks(this).addApi(Places.GEO_DATA_API).addApi(Places.PLACE_DETECTION_API) .addApi(LocationServices.API).build(); createLocationRequest(); } protected synchronized void buildAutocomplete() { mAdapter = new PlaceAutocompleteAdapter(this, mGoogleApiClient, BOUNDS_GREATER_BSM, null); mOriginEditText.setAdapter(mAdapter); mDestinationEditText.setAdapter(mAdapter); mOriginEditText.setOnItemClickListener(mAutocompleteClickListener); mDestinationEditText.setOnItemClickListener(mAutocompleteClickListener); } protected void createLocationRequest() { mLocationRequest = new LocationRequest(); mLocationRequest.setInterval(5000); mLocationRequest.setFastestInterval(1000); mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY); } protected void startLocationUpdates() { if (ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED && ActivityCompat.checkSelfPermission(this, android.Manifest.permission.ACCESS_COARSE_LOCATION) != PackageManager.PERMISSION_GRANTED) { return; } LocationServices.FusedLocationApi.requestLocationUpdates(mGoogleApiClient, mLocationRequest, this); } private void hideKeyboard() { InputMethodManager inputMethodManager = (InputMethodManager) this .getSystemService(Activity.INPUT_METHOD_SERVICE); inputMethodManager.hideSoftInputFromWindow(this.getCurrentFocus().getWindowToken(), 0); } private void displayNoItineraryFoundDialog() { new AlertDialog.Builder(this).setMessage(getString(R.string.please_retry_with_other_points)) .setTitle(getString(R.string.no_result)) .setPositiveButton(getString(R.string.ok), new DialogInterface.OnClickListener() { @Override public void onClick(DialogInterface dialog, int which) { dialog.dismiss(); } }).show(); } private AdapterView.OnItemClickListener mAutocompleteClickListener = new AdapterView.OnItemClickListener() { @Override public void onItemClick(AdapterView<?> parent, View view, int position, long id) { final AutocompletePrediction item = mAdapter.getItem(position); final String placeId = item.getPlaceId(); final CharSequence primaryText = item.getPrimaryText(null); hideKeyboard(); PendingResult<PlaceBuffer> placeResult = Places.GeoDataApi.getPlaceById(mGoogleApiClient, placeId); placeResult.setResultCallback(mUpdatePlaceDetailsCallback); Toast.makeText(getApplicationContext(), primaryText + " " + getString(R.string.selected), Toast.LENGTH_SHORT).show(); } }; private ResultCallback<PlaceBuffer> mUpdatePlaceDetailsCallback = new ResultCallback<PlaceBuffer>() { @Override public void onResult(PlaceBuffer places) { if (!places.getStatus().isSuccess()) { Log.e(PlaceAutocompleteAdapter.TAG, "Place query did not complete. Error: " + places.getStatus().toString()); places.release(); return; } final Place place = places.get(0); Log.i(PlaceAutocompleteAdapter.TAG, "Place details received: " + place.getName()); places.release(); } }; @Override public void onFragmentInteraction(Uri uri) { } }