Aung Kaung Hein
Aung Kaung Hein

Reputation: 1576

Android: Java cannot refer to a non-final variable

In my Android application, when the users click on Sales button, it will show another view to perform the sales.

My application is working without having any problems before I have implemented an alert dialog to display a warning message to users if GST License expiry date of selected customer is less than 7 days and going to expire soon. Now I am getting the following error message if I don't declare final to these two variables, customer and v.

Cannot refer to a non-final variable customer inside an inner class defined in a different method

Cannot refer to a non-final variable v inside an inner class defined in a different method

I understand that

The reference declared as final cannot be modified once it is initialized.

So, what will happen if I assign these two variables as final? It always contain the same value? Can someone please explain to me why the compiler giving me these errors and why I should declare final to these two variables?

Here is my source code:

private OnClickListener salesBtnClick = new OnClickListener() {
    @Override
    public void onClick(View v) {
        Customer customer = salesCustAdpt.getSelectedCustomer();
        if (customer != null) {                                
            Date expiryDate = customer.getGSTLicenseExpiryDate();
            if (checkCustomerGSTLicenseExpiryDate(expiryDate)) {
                AlertDialog.Builder builder = new AlertDialog.Builder(SalesCustomerActivity.this);
                builder.setCancelable(false)
                    .setPositiveButton(
                        "OK",
                        new DialogInterface.OnClickListener() {
                            @Override
                            public void onClick(DialogInterface dialog, int which) {
                                try {
                                    //Perform sales here!
                                    Intent intent = null;
                                    intent = new Intent(v.getContext(), SalesActivity.class);//Error msg here!
                                    Bundle bundle = new Bundle();
                                    bundle.putSerializable("selCustomer", customer);//Error msg here!
                                    intent.putExtra("bundle", bundle);
                                    startActivity(intent);
                                    finish();
                                } catch (Exception ex) {
                                    AddPlusUtil.displayErrorMsg(
                                                    SalesCustomerActivity.this,
                                                    ex);
                                }
                            }
                        });

                AlertDialog alert = builder.create();
                alert.setTitle("Warning Message");
                String errMsg = "GST License Expiry Date of selected customer is \n" + expiryDate + " and going to expire soon.";
                alert.setMessage(errMsg);
                alert.setIcon(android.R.drawable.stat_notify_error);
                alert.show();
            } else {
                //Perform Sales
            }
        } 
    }
}

Upvotes: 1

Views: 1433

Answers (2)

KDeogharkar
KDeogharkar

Reputation: 10959

Define that customer and v globally in your class. It will resolve the issue.

Create one global view object than assign it with your v

globalView = v;

and use that globalView for calling intent.

and by the way you can use yourClass.this as context instead of your view context.

Upvotes: 1

Gil Moshayof
Gil Moshayof

Reputation: 16761

When defining Customer, use final:

final Customer customer = salesCustAdpt.getSelectedCustomer();

Also, in your onClick method, set the View as final:

public void onClick(final View v) {

Hope this helps :)

Upvotes: 2

Related Questions