-2

I have this Json which I parse on the first activity of my app but when i try to recreate the same thing with the same json on the other activity, it just wont work.

I've been reading about this and about nullpointers to see if I can see where can i fix this problem but I am out of ideas. Since I have a lot more Jsons to read in other activities and I cant get one to work, i wont be able to do the rest.

When i call for getData, i input a function, the username and the password, which in turn will be part of an url which gives me the json content and where i try to read and parse.

Here's the MainActivity:

public class MainActivity extends AppCompatActivity
{
Button logindaapp; // Botão de Login
EditText username; // Secção username
EditText password; // Secção password

private String user;
private String pass;

User userEntry = null;

ArrayList<CarDataset> carsDataset = new ArrayList<>();

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

    // Botão Login
    logindaapp = (Button) findViewById(R.id.btn_login); // Associa o id do botão

    logindaapp.setOnClickListener(new View.OnClickListener()
    {
        @Override
        public void onClick(View v)
        { // Quando é clicado o botão
            disableButton(v);
            String funcao = "wslogin";
            username = (EditText)findViewById(R.id.et_username);
            user = username.getText().toString();
            password = (EditText)findViewById(R.id.et_password);
            pass = password.getText().toString();
            getData(funcao, user, pass);

        }
    });
}

String mLogTag;
// "wslogin"
public void getData(String funcao, String username, String password)
{


    String url = "http://www.xxxxxxxxx.xxx/index.php/site/" + funcao + "?u="+username+"&p="+ password;
    Log.e(mLogTag, "getting car data\n" + url);
    DownloadJsonFile downloadCarData = new DownloadJsonFile();
    downloadCarData.execute(url);
}

// Método para prevenir Duplo click
public static void disableButton(final View v)
{
    try
    {
        v.setEnabled(false);
        v.setAlpha((float) 0.5);
        v.postDelayed(new Runnable()
        {
            @Override
            public void run()
            {
                try
                {
                    v.setEnabled(true);
                    v.setAlpha((float) 1.0);
                } catch (Exception e)
                {
                    Log.d("disableButton","Exception while un hiding the view: " + e.getMessage());
                }
            }
        }, 1000);
    } catch (Exception e)
    {
        Log.d("disableButton","Exception while hiding the view : " + e.getMessage());
    }
}

private void updateCarDataset(String json) throws JSONException
{
    JSONArray array = new JSONArray(json);

    for (int i = 0; i < array.length(); i++)
    {
        JSONObject object = array.getJSONObject(i);
        Integer carID = object.getInt("viaturaID");
        String lPlate = object.getString("matricula");
        Integer companyID = object.getInt("empresaID");
        Integer modelID = object.getInt("modeloID");
        Integer driverID = object.getInt("condutorID");
        Integer departmentID = object.getInt("departamentoID");
        Integer fuelID = object.getInt("combustivelID");
        Integer image = object.getInt("imagem");
        Integer idTypeVehicle = object.getInt("idtipoviatura");
        Long locationID = object.getLong("localizacaoID");
        Double latit = object.getDouble("lat");
        Double longt = object.getDouble("lon");
        String dateTime = object.getString("datahora");
        Double speed = object.getDouble("speed");
        Integer brandID = object.getInt("marcaID");
        String model = object.getString("modelo");
        String brand = object.getString("marca");
        String company = object.getString("empresa");
        Long nif = object.getLong("NIF");
        String address = object.getString("morada");
        String place = object.getString("local");
        String cp = object.getString("cp");
        String phone = object.getString("telefone");
        String email = object.getString("mail");
        String responsable = object.getString("responsavel");
        String expirationLicense = object.getString("validadeLicenca");
        Integer litersWarningDepot = object.getInt("LitrosAvisoDeposito");
        Integer kmsReminder = object.getInt("KmsLembrete");
        Integer daysReminder = object.getInt("diasLembrete");
        Integer outsiderNr = object.getInt("nrexterno");
        String name = object.getString("nome");
        String fuel = object.getString("combustivel");
        Double lastPrice = object.getDouble("ultimoPreco");


        carsDataset.add(new CarDataset(carID,lPlate, companyID, modelID, driverID, departmentID, fuelID, image, locationID, idTypeVehicle, latit, longt, dateTime, speed, brandID, model, brand, company, nif, address, place, cp, phone, email, responsable, expirationLicense, litersWarningDepot, kmsReminder, daysReminder, outsiderNr, name, fuel, lastPrice));
    }
    Log.d("my Tag", carsDataset.get(1).licencePlate);
    if (ValidateCredentials(carsDataset) == true)
    {
        userEntry = new User(user, pass);
        Intent login = new Intent();
        login.putExtra("user", userEntry);

        login.setClass(MainActivity.this, Menu.class);
        startActivity(login); // Começa a nova Actividade
        MainActivity.this.finish(); // Termina esta atividade
    }
    else
    {
        Toast.makeText(MainActivity.this, "Credencias Erradas. Tente de Novo", Toast.LENGTH_LONG).show();
    }
}

public boolean ValidateCredentials(ArrayList<CarDataset> testArray)
{
    if (testArray.isEmpty())
    {
        return false;
    }
    else
    {
        return true;
    }

}

public class DownloadJsonFile extends AsyncTask<String, Void, String> {
    @Override

    protected String doInBackground(String... params)
    {
        try
        {
            URL url = new URL(params[0]);

            // Open a stream from the URL
            InputStream stream = new URL(params[0]).openStream();

            String line;
            StringBuilder result = new StringBuilder();
            BufferedReader reader = new BufferedReader(new InputStreamReader(stream));

            while ((line = reader.readLine()) != null)
            {
                result.append(line);
                Log.e(mLogTag, "reading ...");
            }

            // Close the stream
            reader.close();
            stream.close();

            return result.toString();// + params[1];
        }
        catch (IOException e)
        {
            Log.e(mLogTag, "download data could not be read");
        }
        return null;
    }

    @Override
    protected void onPostExecute(String jsonObject)
    {
        if (jsonObject != null)
        {
            try
            {
                Log.e(mLogTag, "data received ->" + jsonObject);

                if (!jsonObject.contains("noDataAvailable"))
                {
                    try
                    {
                        updateCarDataset(jsonObject);
                    } catch (JSONException e)
                    {
                        e.printStackTrace();
                    }
                }
                else
                {
                    Log.e(mLogTag, "heello");
                }
            }
            catch (Exception ex)
            {
                ex.printStackTrace();
            }
        }
    }
}

}

Heres my Second Activity:

public class SelectCarToTrack extends AppCompatActivity
{
private String mLogTag;
private User userEntry = null;
RecyclerView recyclerView;
ArrayList<String> matriculas = new ArrayList<>();;
ArrayList<CarDataset> carros = new ArrayList<>();;
CarDataset selecionado = null;

private String user;
private String pass;


// Necessário para o RecyclerView
@Override
protected void onSaveInstanceState(Bundle outState)
{
    super.onSaveInstanceState(outState);
    ((CarExpandableAdapter)recyclerView.getAdapter()).onSaveInstanceState(outState);
}

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

    String carFuncao = "wslogin";

    Intent i = getIntent();
    userEntry = (User) i.getExtras().getParcelable("user");
    user = userEntry.getUsername();
    pass = userEntry.getPassword();

    String Url = "http://www.xxxxxxxx.xxx/index.php/site/"+ carFuncao + "?u=" + user + "&p=" + pass;
    Log.d("myTag", user);
    Log.d("myTag", pass);


    getData(carFuncao, user, pass);


    obtainLicensePlates(carros);

    Log.d("myTag", carros.get(0).licencePlate); // ERROR COMING THROUGH HERE!
    recyclerView = (RecyclerView)findViewById(R.id.rv_listcars);
    recyclerView.setLayoutManager(new LinearLayoutManager(this));

    CarExpandableAdapter adapter = new CarExpandableAdapter(this,initData(matriculas));
    adapter.setParentClickableViewAnimationDefaultDuration();
    adapter.setParentAndIconExpandOnClick(true);

    recyclerView.setAdapter(adapter);
    recyclerView.addOnItemTouchListener(new RecyclerItemClickListener(SelectCarToTrack.this, recyclerView, new RecyclerItemClickListener.OnItemClickListener()
    {
        @Override
        public void onItemClick(View view, int position)
        {
            selecionado = carros.get(position);
            Intent geolocalizarSpecific = new Intent();
            geolocalizarSpecific.putExtra("select", selecionado);
            geolocalizarSpecific.setClass(SelectCarToTrack.this, Geolocalizcao.class);
            startActivity(geolocalizarSpecific);
        }

        @Override
        public void onItemLongCLick(View view, int position)
        {
        }
    }));
}

private void obtainLicensePlates(ArrayList<CarDataset> cars)
{
    if(cars != null)
    {
        for(int i=0; i < carros.size(); i++)
        {
            String temp = "";
            temp = carros.get(i).licencePlate;
            matriculas.add(i,temp);
        }
    }
    else
    {
        Toast.makeText(SelectCarToTrack.this, "Não foram recebidos dados", Toast.LENGTH_LONG).show();
    }
}

// O que acontece quando clico o botão para voltar para atrás
@Override
public void onBackPressed() {
    Intent goBack = new Intent();
    goBack.putExtra("user", userEntry );
    goBack.setClass(SelectCarToTrack.this, Menu.class);
    startActivity(goBack);
    SelectCarToTrack.this.finish();
}

private List<ParentObject> initData(ArrayList<String> licensePlates)
{
    CarCreator carCreator = CarCreator.get(this, licensePlates);
    List<CarParent> cars = carCreator.getAll();
    List<ParentObject> parentObject = new ArrayList<>();
    for(CarParent car:cars)
    {
        List<Object> childList = new ArrayList<>();
        childList.add(new CarChild("Track your vehicle","See Details"));
        car.setChildObjectList(childList);
        parentObject.add(car);
    }
    return parentObject;
}

public void getData(String funcao, String username, String password)
{
    // funcao = wslogin

    String Url = "http://www.xxxxx.xxx/index.php/site/"+ funcao + "?u=" + username + "&p=" + password;
    Log.e(mLogTag, "getting car data\n" + Url);
    DownloadJsonFile downloadCarData = new DownloadJsonFile();
    downloadCarData.execute(Url);
}

private void updateCarDataset(String json) throws JSONException
{
    JSONArray array = new JSONArray(json);

    for (int i = 0; i < array.length(); i++)
    {
        JSONObject object = array.getJSONObject(i);
        Integer carID = object.getInt("viaturaID");
        String lPlate = object.getString("matricula");
        Integer companyID = object.getInt("empresaID");
        Integer modelID = object.getInt("modeloID");
        Integer driverID = object.getInt("condutorID");
        Integer departmentID = object.getInt("departamentoID");
        Integer fuelID = object.getInt("combustivelID");
        Integer image = object.getInt("imagem");
        Integer idTypeVehicle = object.getInt("idtipoviatura");
        Long locationID = object.getLong("localizacaoID");
        Double latit = object.getDouble("lat");
        Double longt = object.getDouble("lon");
        String dateTime = object.getString("datahora");
        Double speed = object.getDouble("speed");
        Integer brandID = object.getInt("marcaID");
        String model = object.getString("modelo");
        String brand = object.getString("marca");
        String company = object.getString("empresa");
        Long nif = object.getLong("NIF");
        String address = object.getString("morada");
        String place = object.getString("local");
        String cp = object.getString("cp");
        String phone = object.getString("telefone");
        String email = object.getString("mail");
        String responsable = object.getString("responsavel");
        String expirationLicense = object.getString("validadeLicenca");
        Integer litersWarningDepot = object.getInt("LitrosAvisoDeposito");
        Integer kmsReminder = object.getInt("KmsLembrete");
        Integer daysReminder = object.getInt("diasLembrete");
        Integer outsiderNr = object.getInt("nrexterno");
        String name = object.getString("nome");
        String fuel = object.getString("combustivel");
        Double lastPrice = object.getDouble("ultimoPreco");


        carros.add(new CarDataset(carID, lPlate, companyID, modelID, driverID, departmentID, fuelID, image, locationID, idTypeVehicle, latit, longt, dateTime, speed, brandID, model, brand, company, nif, address, place, cp, phone, email, responsable, expirationLicense, litersWarningDepot, kmsReminder, daysReminder, outsiderNr, name, fuel, lastPrice));
    }
}


public class DownloadJsonFile extends AsyncTask<String, Void, String> {
    @Override

    protected String doInBackground(String... params)
    {
        try
        {
            URL url = new URL(params[0]);

            // Open a stream from the URL
            InputStream stream = new URL(params[0]).openStream();

            String line;
            StringBuilder result = new StringBuilder();
            BufferedReader reader = new BufferedReader(new InputStreamReader(stream));

            while ((line = reader.readLine()) != null)
            {
                result.append(line);
                Log.e(mLogTag, "reading ...");
            }

            // Close the stream
            reader.close();
            stream.close();

            return result.toString();// + params[1];
        }
        catch (IOException e)
        {
            Log.e(mLogTag, "download data could not be read");
        }
        return null;
    }

    @Override
    protected void onPostExecute(String jsonObject)
    {
        if (jsonObject != null)
        {
            try
            {
                Log.e(mLogTag, "data received ->" + jsonObject);

                if (!jsonObject.contains("noDataAvailable"))
                {
                    try
                    {
                        updateCarDataset(jsonObject);
                    } catch (JSONException e)
                    {
                        e.printStackTrace();
                    }
                }
                else
                {
                    Log.e(mLogTag, "heello");
                }
            }
            catch (Exception ex)
            {
                ex.printStackTrace();
            }
        }
    }
}

}

Logcat:

                                                       [ 11-18 17:29:58.579 10015:10015 E/         ]
                                                       getting car data
                                                       http://www.gescar3w.com/index.php/site/wslogin?u=xxxxxxx@xxxxx.xxx&p=xxxxxxx
11-18 17:29:58.580 10015-10015/g3w.gescarcopytest D/AndroidRuntime: Shutting down VM
11-18 17:29:58.582 10015-10015/g3w.gescarcopytest E/AndroidRuntime: FATAL EXCEPTION: main
                                                                Process: g3w.gescarcopytest, PID: 10015
                                                                java.lang.RuntimeException: Unable to start activity ComponentInfo{g3w.gescarcopytest/g3w.gescarcopytest.SelectCarToTrack}: java.lang.IndexOutOfBoundsException: Index: 0, Size: 0
                                                                    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2817)
                                                                    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2892)
                                                                    at android.app.ActivityThread.-wrap11(Unknown Source:0)
                                                                    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1593)
                                                                    at android.os.Handler.dispatchMessage(Handler.java:105)
                                                                    at android.os.Looper.loop(Looper.java:164)
                                                                    at android.app.ActivityThread.main(ActivityThread.java:6541)
                                                                    at java.lang.reflect.Method.invoke(Native Method)
                                                                    at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:240)
                                                                    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:767)
                                                                 Caused by: java.lang.IndexOutOfBoundsException: Index: 0, Size: 0
                                                                    at java.util.ArrayList.get(ArrayList.java:437)
                                                                    at g3w.gescarcopytest.SelectCarToTrack.onCreate(SelectCarToTrack.java:79)
                                                                    at android.app.Activity.performCreate(Activity.java:6975)
                                                                    at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1213)
                                                                    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2770)
                                                                    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2892) 
                                                                    at android.app.ActivityThread.-wrap11(Unknown Source:0) 
                                                                    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1593) 
                                                                    at android.os.Handler.dispatchMessage(Handler.java:105) 
                                                                    at android.os.Looper.loop(Looper.java:164) 
                                                                    at android.app.ActivityThread.main(ActivityThread.java:6541) 
                                                                    at java.lang.reflect.Method.invoke(Native Method) 
                                                                    at com.android.internal.os.Zygote$MethodAndArgsCaller.run(Zygote.java:240) 
                                                                    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:767) 
11-18 17:29:58.592 10015-10020/g3w.gescarcopytest I/zygote: Do partial code cache collection, code=118KB, data=102KB
11-18 17:29:58.592 10015-10020/g3w.gescarcopytest I/zygote: After code cache collection, code=118KB, data=102KB
11-18 17:29:58.592 10015-10020/g3w.gescarcopytest I/zygote: Increasing code cache capacity to 512KB
11-18 17:29:58.592 10015-10020/g3w.gescarcopytest I/zygote: JIT allocated 56KB for compiled code of void android.view.View.<init>(android.content.Context, android.util.AttributeSet, int, int)

I'm getting the info of the user, no problem there... And the code is practically the same, except the part where it has a recycler view and all. But I don't see where I went wrong...

Manuel Cruz
  • 53
  • 1
  • 1
  • 8
  • 2
    `getData()` is using an `AsyncTask`, so `carros` is still empty when your `Log.d()` statement is executed. – Ben P. Nov 18 '17 at 17:52

1 Answers1

0

Thanks to what Ben P. said, I managed to figure it. AsyncTask takes a bit of time to read the data, takes about 2/3 seconds. So asking for the information right off the bat won't work and will result in a crash.

I had to take everything after the getData call I did in the second activity and placed it after I update my ArrayList. It looks like this now:

private void updateCarDataset(String json) throws JSONException {
    JSONArray array = new JSONArray(json);

    for (int i = 0; i < array.length(); i++) {
        JSONObject object = array.getJSONObject(i);
        Integer carID = object.getInt("viaturaID");
        String lPlate = object.getString("matricula");
        Integer companyID = object.getInt("empresaID");
        Integer modelID = object.getInt("modeloID");
        Integer driverID = object.getInt("condutorID");
        Integer departmentID = object.getInt("departamentoID");
        Integer fuelID = object.getInt("combustivelID");
        Integer image = object.getInt("imagem");
        Integer idTypeVehicle = object.getInt("idtipoviatura");
        Long locationID = object.getLong("localizacaoID");
        Double latit = object.getDouble("lat");
        Double longt = object.getDouble("lon");
        String dateTime = object.getString("datahora");
        Double speed = object.getDouble("speed");
        Integer brandID = object.getInt("marcaID");
        String model = object.getString("modelo");
        String brand = object.getString("marca");
        String company = object.getString("empresa");
        Long nif = object.getLong("NIF");
        String address = object.getString("morada");
        String place = object.getString("local");
        String cp = object.getString("cp");
        String phone = object.getString("telefone");
        String email = object.getString("mail");
        String responsable = object.getString("responsavel");
        String expirationLicense = object.getString("validadeLicenca");
        Integer litersWarningDepot = object.getInt("LitrosAvisoDeposito");
        Integer kmsReminder = object.getInt("KmsLembrete");
        Integer daysReminder = object.getInt("diasLembrete");
        Integer outsiderNr = object.getInt("nrexterno");
        String name = object.getString("nome");
        String fuel = object.getString("combustivel");
        Double lastPrice = object.getDouble("ultimoPreco");


        carros.add(new CarDataset(carID, lPlate, companyID, modelID, driverID, departmentID, fuelID, image, locationID, idTypeVehicle, latit, longt, dateTime, speed, brandID, model, brand, company, nif, address, place, cp, phone, email, responsable, expirationLicense, litersWarningDepot, kmsReminder, daysReminder, outsiderNr, name, fuel, lastPrice));
    }

    obtainLicensePlates(carros);

    recyclerView = (RecyclerView) findViewById(R.id.rv_listcars);
    recyclerView.setLayoutManager(new LinearLayoutManager(this));

    CarExpandableAdapter adapter = new CarExpandableAdapter(this, initData(matriculas));
    adapter.setParentClickableViewAnimationDefaultDuration();
    adapter.setParentAndIconExpandOnClick(true);

    recyclerView.setAdapter(adapter);
    recyclerView.addOnItemTouchListener(new RecyclerItemClickListener(SelectCarToTrack.this, recyclerView, new RecyclerItemClickListener.OnItemClickListener() {

        @Override
        public void onItemClick(View view, int position) {
            selecionado = carros.get(position);
            Intent geolocalizarSpecific = new Intent();
            geolocalizarSpecific.putExtra("select", selecionado);
            geolocalizarSpecific.setClass(SelectCarToTrack.this, Geolocalizcao.class);
            startActivity(geolocalizarSpecific);
        }

        @Override
        public void onItemLongCLick(View view, int position) {
        }
    }));
} 
Manuel Cruz
  • 53
  • 1
  • 1
  • 8