title: Country, state and city spinner not working correctly
body: <p>I've been working on a registration form app with few spinner widgets being used in it. The spinners are to be used to select <strong>Country</strong>, <strong>State</strong> and <strong>City</strong>. Hence, these spinners need to be interconnected somehow (The code below would show how I have tried to achieve that).</p>
  
  <p>Form code:</p>
  
  <h3>fragment_register.xml</h3>
  
  <pre><code>&lt;?xml version="1.0" encoding="utf-8"?&gt;
  
  &lt;ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:fillViewport="true"&gt;
  
  &lt;LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
  android:orientation="vertical"
  android:layout_marginLeft="40dp"
  android:layout_marginRight="40dp"
  android:gravity="center"
  android:layout_width="match_parent"
  android:layout_height="wrap_content"
  android:nestedScrollingEnabled="true"&gt;
  
  
  &lt;TextView
      android:text="Student Registration Form"
      android:textSize="22sp"
      android:textAlignment="center"
      android:layout_marginBottom="20dp"
      android:layout_width="wrap_content"
      android:layout_height="wrap_content" /&gt;
  
      &lt;Spinner
          android:layout_width="match_parent"
          android:layout_height="wrap_content"
          android:id="@+id/country_spinner"
          android:foregroundTint="#222"
          android:background="#001c47"
          android:layout_marginBottom="20dp" /&gt;
  
      &lt;Spinner
          android:layout_width="match_parent"
          android:layout_height="wrap_content"
          android:id="@+id/state_spinner"
          android:foregroundTint="#222"
          android:background="#001c47"
          android:layout_marginBottom="20dp" /&gt;
  
      &lt;Spinner
          android:layout_width="match_parent"
          android:layout_height="wrap_content"
          android:id="@+id/city_spinner"
          android:foregroundTint="#222"
          android:background="#001c47"
          android:layout_marginBottom="20dp" /&gt;
  
  &lt;/LinearLayout&gt;
  &lt;/ScrollView&gt;
  </code></pre>
  
  <p>The code above has more widgets which you might find in the java file; I haven't included them in above code as it would make it too long.</p>
  
  <h3>RegisterFragement.java</h3>
  
  <pre><code>import android.app.Fragment;
  import android.app.FragmentTransaction;
  import android.content.SharedPreferences;
  import android.nfc.Tag;
  import android.support.v7.app.AppCompatActivity;
  import android.os.Bundle;
  
  
  import android.view.View;
  import android.widget.AdapterView;
  import android.widget.ArrayAdapter;
  import android.widget.TextView;
  
  import com.android.volley.RequestQueue;
  import com.android.volley.Response;
  import com.android.volley.VolleyError;
  import com.android.volley.toolbox.StringRequest;
  import com.android.volley.toolbox.Volley;
  
  import org.json.JSONArray;
  import org.json.JSONException;
  import org.json.JSONObject;
  
  import java.util.ArrayList;
  import android.support.design.widget.Snackbar;
  import android.support.v7.widget.AppCompatButton;
  import android.util.Log;
  import android.view.LayoutInflater;
  import android.view.View;
  import android.view.ViewGroup;
  import android.widget.EditText;
  import android.widget.ProgressBar;
  import android.widget.Spinner;
  import android.widget.TextView;
  import android.widget.Toast;
  
  
  public class RegisterFragment extends Fragment  implements View.OnClickListener, Spinner.OnItemSelectedListener{
  
  private AppCompatButton btn_register;
  private EditText et_email,et_password,et_name;
  private TextView tv_login;
  private ProgressBar progress;
  //Declaring the Spinners
  private Spinner country_spinner;
  private Spinner state_spinner;
  private Spinner city_spinner;
  
  
  //An ArrayList for Spinner Items
  private ArrayList&lt;String&gt; results;
  // countGetData: It will keep a count of how many times get data has been run and for 0 times
  // it would set the spinners to default state
  private int countGetData;
  ArrayList student1 = new ArrayList();
  
  
  //JSON Array
  private JSONArray resultArray;
  
  
  @Override
  public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
  
      View view = inflater.inflate(R.layout.fragment_register,container,false);
      initViews(view);
      return view;
  
  }
  
  private void initViews(View view){
  
      btn_register = (AppCompatButton)view.findViewById(R.id.btn_register);
      tv_login = (TextView)view.findViewById(R.id.tv_login);
      et_name = (EditText)view.findViewById(R.id.et_name);
      et_email = (EditText)view.findViewById(R.id.et_email);
      et_password = (EditText)view.findViewById(R.id.et_password);
  
      progress = (ProgressBar)view.findViewById(R.id.progress);
  
      btn_register.setOnClickListener(this);
      tv_login.setOnClickListener(this);
      //Initializing the ArrayList
      results = new ArrayList&lt;String&gt;();
      // Initializing countGetData
      countGetData = 0;
  
      //Initializing Spinner
      country_spinner = (Spinner) view.findViewById(R.id.country_spinner);
      state_spinner = (Spinner) view.findViewById(R.id.state_spinner);
      city_spinner = (Spinner) view.findViewById(R.id.city_spinner);
  
  
      //Adding an Item Selected Listener to our Spinner
      //As we have implemented the class Spinner.OnItemSelectedListener to this class iteself we are passing this to setOnItemSelectedListener
      country_spinner.setOnItemSelectedListener(this);
      state_spinner.setOnItemSelectedListener(this);
      city_spinner.setOnItemSelectedListener(this);
      university_spinner.setOnItemSelectedListener(this);
      college_spinner.setOnItemSelectedListener(this);
      ca_spinner.setOnItemSelectedListener(this);
  
  
      getData("getCountries", "", 0);
  }
  
  
  @Override
  public void onClick(View v) {
  
      switch (v.getId()){
          case R.id.tv_login:
              goToLogin();
              break;
  
          case R.id.btn_register:
  
              String name = et_name.getText().toString();
              String email = et_email.getText().toString();
              String password = et_password.getText().toString();
  
              if(!name.isEmpty() &amp;&amp; !email.isEmpty() &amp;&amp; !password.isEmpty()) {
  
                  progress.setVisibility(View.VISIBLE);
                  registerProcess(name,email,password);
  
              } else {
  
                  Snackbar.make(getView(), "Fields are empty !", Snackbar.LENGTH_LONG).show();
              }
              break;
  
      }
  
  }
  
  private void getData(String urlPart1,String urlPart2, long itemId) {
      //Creating a string request
      StringRequest stringRequest = new StringRequest(Config.DATA_URL+urlPart1+"&amp;"+urlPart2+"="+itemId,
              new Response.Listener&lt;String&gt;() {
                  @Override
                  public void onResponse(String response) {
                      JSONObject j = null;
                      try {
                          //Parsing the fetched Json String to JSON Object
                          j = new JSONObject(response);
  
                          //Storing the Array of JSON String to our JSON Array
                          resultArray = j.getJSONArray(Config.JSON_ARRAY);
  
                          //Calling method getStudents to get the students from the JSON Array
                          getResults(resultArray);
  
                      } catch (JSONException e) {
                          e.printStackTrace();
                      }
                  }
              },
              new Response.ErrorListener() {
                  @Override
                  public void onErrorResponse(VolleyError error) {
  
                  }
              });
  
  //Creating a request queue
          RequestQueue requestQueue = Volley.newRequestQueue(getActivity().getApplicationContext());
      //Adding request to the queue
      requestQueue.add(stringRequest);
  
  }
  
  private void getResults(JSONArray j) {
      //Traversing through all the items in the json array
      for (int i = 0; i &lt; j.length(); i++) {
          try {
              //Getting json object
              JSONObject json = j.getJSONObject(i);
  
              //Adding the name of the student to array list
              results.add(json.getString(Config.TAG_NAME));
          } catch (JSONException e) {
              e.printStackTrace();
          }
      }
  
      if(countGetData == 0) {
          student1.add("Select This");
          //Setting adapter to show the items in the spinner
          country_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, results));
          state_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, student1));
          city_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, student1));
          countGetData += 1;
      }
  }
  
  
  
  //this method will execute when we pic an item from the spinner
  @Override
  public void onItemSelected(AdapterView&lt;?&gt; parent, View view, int position, long id) {
  
      if(country_spinner.getSelectedItem().toString().equals("Austria")){
          long itemId = country_spinner.getSelectedItemId();
          getData("getStates","countryId",itemId);
          state_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, results));
      }
      else{
          long itemId = country_spinner.getSelectedItemId();
          getData("getStates","countryId",itemId);
          state_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, results));
      }
  
  
  }
  }
  </code></pre>
  
  <p>There is a PHP API which returns the json for Country, State or City based on the url. For ex.:
      <code>http://www.example.com/location_api/api.php?type=getCountries
  http://www.example.com/location_api/api.php?type=getStates&amp;countryId=12
  http://www.example.com/location_api/api.php?type=getCities&amp;stateId=1</code></p>
  
  <p>In <strong>onItemSelected</strong> I'm trying to dynamically set spinners with respect to the previous spinner. For ex., I'm setting the <strong>state</strong> spinner whenever a <strong>country</strong> spinner item is selected. I'm checking this through a <strong>if-else</strong> block; if condition checks if <strong>Austria</strong>(one of the countries in the list; random choice) is selected then set the <strong>state</strong> spinner <strong>else</strong> also set the <strong>state</strong> spinner. This way I end up setting the state spinner according to the country spinner element.</p>
  
  <p>To specify to the API which <strong>country</strong> is being chosen I'm using the itemId which contains the Id of the selected item in country spinner.
  <code>long itemId = country_spinner.getSelectedItemId();</code></p>
  
  <p>Then when I have the Id I call the <strong>getData</strong> method which sets the <strong>result</strong> ArraryList and I assign it to the spinner <strong>state</strong>.</p>
  
  <p><code>getData("getStates","countryId",itemId);
  state_spinner.setAdapter(new ArrayAdapter&lt;String&gt;(getActivity().getApplicationContext(), android.R.layout.simple_spinner_dropdown_item, results));</code></p>
  
  <p>The above code is making the app crash at run time with following error(only part of it which I think might be useful, full Logcat file here: <a href="http://pastebin.com/Wvz4udtG">Link</a>):</p>
  
  <blockquote>
    <p>--------- beginning of crash 04-13 21:05:09.782 9288-9600/com.gouravchawla.loginregistration E/AndroidRuntime: FATAL
    EXCEPTION: Thread-503
                                                                                     Process: com.gouravchawla.loginregistration, PID: 9288
                                                                                     java.lang.NegativeArraySizeException: -110
                                                                                         at
    com.android.volley.toolbox.DiskBasedCache.streamToBytes(DiskBasedCache.java:316)
                                                                                         at
    com.android.volley.toolbox.DiskBasedCache.get(DiskBasedCache.java:117)
                                                                                         at com.android.volley.CacheDispatcher.run(CacheDispatcher.java:101)</p>
    
    <p>Throwing OutOfMemoryError "Failed to allocate a 1667853436 byte
    allocation with 777786 free bytes and 381MB until OOM"</p>
  </blockquote>