0

I use the openweathermap api and retrieve the json data such as temperature,city name,weather icon etc successfully. However,when I rotate the screen,the webservice is running again,and this shouldn't be happening.

What I do is the following. I save the state or the fragment.

public class MainActivity extends AppCompatActivity implements  
GoogleApiClient.OnConnectionFailedListener,

GoogleApiClient.ConnectionCallbacks{
private static final int PLAY_SERVICES_CODE = 90;
GoogleApiClient googleApiClient;
private static final String TAG = "Location";
private static final String TODAY_FRAGMENT = "today_fragment";

public static double lat = 0;
public static double log = 0;

TodayForecast ff;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    FragmentManager fragmentManager = getSupportFragmentManager();
    ff = (TodayForecast) fragmentManager.findFragmentByTag(TODAY_FRAGMENT);

    if (savedInstanceState != null) {
        //Restore the fragment's instance
        ff = (TodayForecast) 
     getSupportFragmentManager().getFragment(savedInstanceState,   
     "mContent");
    }



    if(checkPlayServices()){
        initializeGoogleApiClient();
    }
}

private void initializeGoogleApiClient() {
    googleApiClient = new GoogleApiClient.Builder(this)
            .addApi(LocationServices.API)
            .addOnConnectionFailedListener(this)
            .addConnectionCallbacks(this)
            .build();

}

public boolean checkPlayServices(){
    int result = GooglePlayServicesUtil.isGooglePlayServicesAvailable(getApplicationContext());

    if(result!= ConnectionResult.SUCCESS){
        if(GooglePlayServicesUtil.isUserRecoverableError(result)){
            GooglePlayServicesUtil.getErrorDialog(result, this, PLAY_SERVICES_CODE).show();
        }
        return false;
    }
    return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
    return super.onOptionsItemSelected(item);
}

@Override
public boolean onCreateOptionsMenu(Menu menu) {
    return super.onCreateOptionsMenu(menu);
}


@Override
public void onConnected(@Nullable Bundle bundle) {

    Location loc = LocationServices.FusedLocationApi.getLastLocation(googleApiClient);

    if(loc!=null){

        //Log.v(TAG,"lat: "+lat);
        //Log.v(TAG,"lon: "+log);

        if(ff == null) {

            lat = loc.getLatitude();
            log = loc.getLongitude();
            ff = new TodayForecast();


 getSupportFragmentManager().beginTransaction().replace(R.id.main_container,  
 TodayForecast.newInstance(lat,log),TODAY_FRAGMENT).commit();

        }

    }else{
        Toast.makeText(getApplicationContext(),"No location 
        obtained",Toast.LENGTH_SHORT).show();
    }
}

@Override
public void onConnectionSuspended(int i) {

}

@Override
public void onConnectionFailed(@NonNull ConnectionResult connectionResult) {

}

@Override
protected void onStart() {
    super.onStart();
    googleApiClient.connect();
}

@Override
protected void onStop() {
    super.onStop();

    if(googleApiClient.isConnected()){
        googleApiClient.disconnect();
    }
  }
 }

And in the actual fragment I used the onSaveInstanceState method to store the retrieved data from my webservice. This is the whole fragment's code.

public class TodayForecast extends Fragment {
private static  String NEW_BASE_URL = "" ;
public static String URL= "http://api.openweathermap.org/data/2.5/weather?";
public static String NEW_URL= "http://api.openweathermap.org/data/2.5/weather?q=";
public static String BASE_URL= "";

public String time;
public String setTime;
String IMG_URL = "http://api.openweathermap.org/img/w/";
static double mlat;
static double mlot;
TextView cityText;
ImageView imageView;
private String cityName;
private String humidity;
private String pressure;
private String speed;
private String imageIcon;
private String temperature;
TextView tempTextView;
TextView windTextView;
TextView pressureTextView;
TextView humidityTextView;
TextView sunriseTextView;
TextView sunSetTextView;
Button btn;

private String icon;

public static TodayForecast newInstance(double lat, double log) {
    TodayForecast fragment = new TodayForecast();

    mlat = lat;
    mlot = log;
    return fragment;
}

public TodayForecast() {
    // Required empty public constructor
}
@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setHasOptionsMenu(true);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
                         Bundle savedInstanceState) {
    // Inflate the layout for this fragment
    View rootView = inflater.inflate(R.layout.fragment_today_forecast, container, false);

    Log.v("Theo","lot: " + mlot);
    Log.v("Theo","lat: " + mlat);

    cityText = (TextView)rootView.findViewById(R.id.cityText);
    imageView = (ImageView) rootView.findViewById(R.id.thumbnailIcon);
    windTextView = (TextView) rootView.findViewById(R.id.windTextValue);
    tempTextView = (TextView)rootView.findViewById(R.id.tempText);
    pressureTextView = (TextView)rootView.findViewById(R.id.pressureTextValue);
    humidityTextView = (TextView)rootView.findViewById(R.id.humidTextValue);
    sunriseTextView = (TextView)rootView.findViewById(R.id.riseTextValue);
    sunSetTextView = (TextView)rootView.findViewById(R.id.setTextValue);

    btn = (Button)rootView.findViewById(R.id.change_city);

    btn.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {


            //showInputDialog();




        }

    });
    //http://api.openweathermap.org/data/2.5/weather?lat=39.6304951&lon=22.4206619&appid=d48708e1e4d8e2b60da14778acd8d56a
    BASE_URL = URL +"lat="+mlat+"&lon="+mlot+"&units=metric&appid=d48708e1e4d8e2b60da14778acd8d56a";
    if(savedInstanceState!=null) {
        String city_name = savedInstanceState.getString("CityName");
        String city_temp = savedInstanceState.getString("CityTemp");
        String city_pressure = savedInstanceState.getString("CityPressure");
        String city_humidity = savedInstanceState.getString("CityHumidity");
        String wind_speed = savedInstanceState.getString("WindSpeed");
        String weather_icon = savedInstanceState.getString("weatherIcon");
        String sunrise_time = savedInstanceState.getString("sunrise");
        String sunset_time = savedInstanceState.getString("sunset");



        cityText.setText(city_name);
        tempTextView.setText(city_temp);
        pressureTextView.setText(city_pressure);
        humidityTextView.setText(city_humidity);
        windTextView.setText(wind_speed);


        Picasso.with(getActivity()).load(weather_icon).into(imageView);

        sunriseTextView.setText(sunrise_time);
        sunSetTextView.setText(sunset_time);


    }else{
      weatherData();

    }

    //http://api.openweathermap.org/data/2.5/weather?q=Newcastle,uk&units=metric&appid=d48708e1e4d8e2b60da14778acd8d56a


    return rootView;



}


private void weatherData() {
    JsonObjectRequest jsonObjReq = new JsonObjectRequest(Request.Method.GET,
            BASE_URL,
            new Response.Listener<JSONObject>() {


                @Override
                public void onResponse(JSONObject response) {

                    Log.d("TAG", response.toString());
                    try {
                        cityName = response.getString("name");
                        cityText.setText(cityName);
                        //cityTextView.setText(cityName);

                        JSONObject main = response.getJSONObject("main");

                        temperature = main.getString("temp");
                        //String temperatureSbstr = temperature.substring(0, 2);
                        tempTextView.setText(temperature+""+"\u00b0 \u0043");

                        humidity = main.getString("humidity");

                        humidityTextView.setText(humidity + " %");

                        pressure = main.getString("pressure");

                        pressureTextView.setText(pressure + " hPa");

                        JSONObject windValue = response.getJSONObject("wind");

                        speed = windValue.getString("speed");

                        windTextView.setText(speed + " km/h");

                        JSONObject sysJSONObject = response.getJSONObject("sys");

                        long sunrise = sysJSONObject.getLong("sunrise");
                        Date dayTime = new Date(sunrise * 1000L);

                        SimpleDateFormat timeFormat = new SimpleDateFormat("HH:mm:ss");
                        time = timeFormat.format(dayTime);

                        sunriseTextView.setText(time);

                        long sunset = sysJSONObject.getLong("sunset");

                        Date sunsetTime = new Date(sunset * 1000L);

                        SimpleDateFormat sunsettimeFormat = new SimpleDateFormat("HH:mm:ss");
                        setTime = sunsettimeFormat.format(sunsetTime);

                        sunSetTextView.setText(setTime);

                        JSONArray weather = response.getJSONArray("weather");

                        for(int i=0; i<weather.length();i++){

                            JSONObject weatherJSONObject = weather.getJSONObject(i);

                            String mainWeather = weatherJSONObject.getString("main");

                            //mainText.setText(mainWeather);

                            icon = weatherJSONObject.getString("icon");
                            //Volley's Image request
                            ImageLoader imageLoader = AppController.getInstance().getImageLoader();

                            imageIcon = IMG_URL + icon;

                            imageLoader.get(imageIcon, new ImageLoader.ImageListener() {

                                @Override
                                public void onErrorResponse(VolleyError error) {

                                }

                                @Override
                                public void onResponse(ImageLoader.ImageContainer response, boolean arg1) {
                                    if (response.getBitmap() != null) {
                                        // load image into imageview
                                        imageView.setImageBitmap(response.getBitmap());
                                    }
                                }
                            });
                            Log.d("icon", icon);
                        }
                    } catch (JSONException e) {
                        Log.e("TAG", e.toString());
                    }

                }
            }, new Response.ErrorListener() {

        @Override
        public void onErrorResponse(VolleyError error) {


        }
    });
    // Adding request to request queue
    AppController.getInstance().addToRequestQueue(jsonObjReq);
}




@Override
public void onSaveInstanceState(Bundle outState) {
    super.onSaveInstanceState(outState);

    outState.putString("CityName",cityName);
    outState.putString("CityTemp",temperature);
    outState.putString("CityPressure",pressure);
    outState.putString("CityHumidity",humidity);
    outState.putString("WindSpeed",speed);
    outState.putString("sunrise",time);
    outState.putString("sunset",setTime);
    outState.putString("weatherIcon",imageIcon);


}


}

You see that after storing the retrieved data I read them inside the onCreateView(...) method when the Bundle object(ie savedInstanceState reference) is not null. If it null meaning tha there is no screen rotation,then the webservice is running.

I fixed this problem when I had to display data in a recyclerview using the Parceable object.

Any ideas,

Thanks!

Theo
  • 361
  • 3
  • 5
  • 16

1 Answers1

0

If the system must recreate the activity instance later, it passes the same Bundle object to both the onRestoreInstanceState() and onCreate() methods. So you can retrieve the data in either of these two methods. I have not tested the solution.This is according to the https://developer.android.com/training/basics/activity-lifecycle/recreating.html.

  • I think this post answers your questions. http://stackoverflow.com/questions/20550016/savedinstancestate-is-always-null-in-fragment – Manish Mishra May 21 '16 at 19:04