1

I have been researching and researching this problem

  • Libs is labelled as libs
  • The activity IS declared in the manifest

It's what I've come up with so far, and I've been stuck for the past hour.

Someone please help.

The error:

10-31 18:58:23.654: E/AndroidRuntime(398): FATAL EXCEPTION: main
10-31 18:58:23.654: E/AndroidRuntime(398): java.lang.RuntimeException: Unable to instantiate activity ComponentInfo{com.mikenning.chemistrywizard/com.mikenning.chemistrywizard.EquationBalancer}: java.lang.NullPointerException
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1569)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1663)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread.access$1500(ActivityThread.java:117)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread$H.handleMessage(ActivityThread.java:931)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.os.Handler.dispatchMessage(Handler.java:99)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.os.Looper.loop(Looper.java:123)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread.main(ActivityThread.java:3683)
10-31 18:58:23.654: E/AndroidRuntime(398):  at java.lang.reflect.Method.invokeNative(Native Method)
10-31 18:58:23.654: E/AndroidRuntime(398):  at java.lang.reflect.Method.invoke(Method.java:507)
10-31 18:58:23.654: E/AndroidRuntime(398):  at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:839)
10-31 18:58:23.654: E/AndroidRuntime(398):  at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:597)
10-31 18:58:23.654: E/AndroidRuntime(398):  at dalvik.system.NativeStart.main(Native Method)
10-31 18:58:23.654: E/AndroidRuntime(398): Caused by: java.lang.NullPointerException
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.Activity.findViewById(Activity.java:1647)
10-31 18:58:23.654: E/AndroidRuntime(398):  at com.mikenning.chemistrywizard.EquationBalancer.<init>(EquationBalancer.java:13)
10-31 18:58:23.654: E/AndroidRuntime(398):  at java.lang.Class.newInstanceImpl(Native Method)
10-31 18:58:23.654: E/AndroidRuntime(398):  at java.lang.Class.newInstance(Class.java:1409)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.Instrumentation.newActivity(Instrumentation.java:1021)
10-31 18:58:23.654: E/AndroidRuntime(398):  at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1561)
10-31 18:58:23.654: E/AndroidRuntime(398):  ... 11 more

The class file:

public class EquationBalancer extends Activity {

    HorizontalScrollView reactants;

    EditText editText = new EditText(this);

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.balancelayout);

        reactants = (HorizontalScrollView) findViewById(R.id.reactants);

        EditText reactantNumberField = (EditText) findViewById(R.id.reactantsNumber);
        final int reactantNom = Integer.parseInt(reactantNumberField.getText().toString());

        Button ok = (Button) findViewById(R.id.reactantsNumberOk);
        ok.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                for (int i = 1; i < reactantNom; i++) {
                    editText.setHint("compound");
                    reactants.addView(editText);
                }
            }
        });
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.balancelayout, menu);
        return true;
    }

}

The Android Manifest:

<manifest 
    xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.mikenning.chemistrywizard"
    android:versionCode="1"
    android:versionName="1.0" >

    <uses-sdk
        android:minSdkVersion="9"
        android:targetSdkVersion="15" />

    <application
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme"
        android:screenOrientation="portrait" >
        <activity
            android:name="EquationBalancer"
            android:label="@string/title_activity_equation_balancer" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

The XML Layout File:

<RelativeLayout 
    xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent" >

    <TextView
        android:id="@+id/reactantsHowMany"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:paddingTop="10dp"
        android:text="@string/reactantsHowMany"
        android:textSize="18dp"
        android:layout_alignParentTop="true"
        android:layout_centerHorizontal="true" />

    <EditText
        android:id="@+id/reactantsNumber"
        android:paddingTop="5dp"
        android:layout_width="65dp"
        android:layout_height="wrap_content"
        android:layout_below="@id/reactantsHowMany"
        android:layout_marginLeft="60dp"
        android:inputType="number"
        android:hint="e.g. 4" />

    <Button 
        android:id="@+id/reactantsNumberOk"
        android:paddingTop="5dp"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_below="@id/reactantsHowMany"
        android:layout_alignParentRight="true"
        android:layout_marginRight="60dp"
        android:layout_alignBottom="@id/reactantsNumber"
        android:text="Set" />

    <HorizontalScrollView
        android:id="@+id/reactants"
        android:paddingTop="5dp"
        android:layout_width="match_parent"
        android:layout_height="50dp"
        android:layout_below="@id/reactantsNumber" >

    </HorizontalScrollView>

</RelativeLayout>

Updated class file (updated for every suggestion):

    public class EquationBalancer extends Activity {

    HorizontalScrollView reactants;
    EditText reactantNumberField;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.balancelayout);

        reactants = (HorizontalScrollView) findViewById(R.id.reactants);

        final EditText editText = new EditText(this);
        editText.setHint("compound");

        reactantNumberField = (EditText) findViewById(R.id.reactantsNumber);


        Button ok = (Button) findViewById(R.id.reactantsNumberOk);
        ok.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // TODO Auto-generated method stub
                int reactantNom = 0;
                try{
                    reactantNom = Integer.parseInt(reactantNumberField.getText().toString());
                } catch (NullPointerException e) {
                    //ignore error
                }
                if (reactantNom != 0) {
                    for (int i = 1; i < reactantNom; i++) {
                        try{
                            reactants.addView(editText);
                        } catch (Exception e) {
                            //ignore
                        }
                    }
                } else if (reactantNom == 1) {
                    try {
                        reactants.addView(editText);
                    } catch (Exception e) {
                        //ignore
                    }
                } else {
                    Toast toast = Toast.makeText(EquationBalancer.this, "Please input the number of reactants", 
                            Toast.LENGTH_SHORT);
                    toast.show();
                }
            }
        });
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.balancelayout, menu);
        return true;
    }

}
MPKenning
  • 569
  • 1
  • 7
  • 22
  • What's at line 13 in EquationBalancer? – soren.qvist Oct 31 '12 at 19:06
  • @soren.qvist; the onCreate method... – MPKenning Oct 31 '12 at 19:07
  • Move the `findViewById`(`Button` + `HorizontalScrollView`, also the `EditText` instantiation) initializations in the `onCreate` method. – user Oct 31 '12 at 19:11
  • @Luksprog, done and edited original post. Still force closing. – MPKenning Oct 31 '12 at 19:22
  • Did you also move the instantiation of the `EditText` *editText* in the `onCreate` method? In your code I don't see this. Also, the line where you parse the string from the `EditText` into an `int` will throw an exception as the `EditText` is empty at that moment. Also, `reactants.addView(editText);` will throw an exception if that loop runs for more than an iteration. – user Oct 31 '12 at 19:25
  • @Luksprog; Moved editText, think I found a solution around that parsing problem, and how can I fix that exception if it's in a loop? – MPKenning Oct 31 '12 at 19:37
  • Try to initialize `editText ` inside `onCreate()`. – yugidroid Oct 31 '12 at 19:38
  • Simple, create a new `EditText` **inside** the `for` loop for each iteration(make it a local variable or make a global array/list if you need a reference to them for later use). – user Oct 31 '12 at 19:40
  • Okay, the application is working. To conclude; I was parsing an integer within the onCreate bundle which threw an exception. To solve this, I make a try-catch block. Same with anything else within the onCreate method. Will paste final code in description under question. – MPKenning Oct 31 '12 at 19:51
  • @Luksprog; problem now is that it's not creating the specified number of EditText views, it's only creating one. – MPKenning Oct 31 '12 at 19:52
  • Of course it's only creating one. You declare it outside the loop and then set it i times. As I said in my other comment. Time to read some tutorials, especially how to add a view to an existing layout. You cannot do this effectively using XML only. – Simon Oct 31 '12 at 19:57
  • @Simon; Can you suggest how I do so? I'm on a tutorial at the moment. – MPKenning Oct 31 '12 at 20:10
  • See http://stackoverflow.com/questions/3210599/android-add-two-text-views-programmatically – Simon Oct 31 '12 at 20:31
  • @Simon; I'm thinking going about it another way; utilising PopupWindows. Looking for tutorials on the internet. Thank you very much for your effort, anyway. – MPKenning Oct 31 '12 at 21:30

2 Answers2

1

Your code is invalid. This line:

Button ok = (Button) findViewById(R.id.reactantsNumberOk);

is your culprit. You initialize ok variable before your view is inflated, therefore ok is null. You have to move ok = (Button) findViewById(R.id.reactantsNumberOk); to your onCreate() after setViewContent() method, to let findViewById() actually find anything useful.

The same applies to following lines:

final EditText reactantNumberField = (EditText) findViewById(R.id.reactantsNumber);
final int reactantNom = Integer.parseInt(reactantNumberField.getText().toString());
HorizontalScrollView reactants = (HorizontalScrollView) findViewById(R.id.reactants);

these all are null and your app will still be crashing once you fix above ok initialization for the same reasons.

There's also no point of having refence to your UI elements in global scope. Valid code should look like this:

public class EquationBalancer extends Activity {

    HorizontalScrollView reactants;

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.balancelayout);

        EditText reactantNumberField = (EditText) findViewById(R.id.reactantsNumber);
        int reactantNom = Integer.parseInt(reactantNumberField.getText().toString());

        reactants = (HorizontalScrollView) findViewById(R.id.reactants);

        Button ok = (Button) findViewById(R.id.reactantsNumberOk);    
        ok.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                EditText editText;
                for (int i=1; i < reactantNom; i++) {
                    editText = new EditText(this);
                    editText.setHint("compound");
                    reactants.addView(editText);
                }
            }
        });
    }

    @Override
    public boolean onCreateOptionsMenu(Menu menu) {
        getMenuInflater().inflate(R.menu.balancelayout, menu);
        return true;
    }
}
Marcin Orlowski
  • 72,056
  • 11
  • 123
  • 141
  • The line "editText = new EditText(this);" was global for a reason. Other than that, everything has been altered as you so have, and still it force closes. – MPKenning Oct 31 '12 at 19:27
  • I'm on a (completely pointless) personal crusade. "There's also no point of having refence to your UI elements in global scope." Moving the reference to a class field does not make it global. Global is application wide. You are talking about class level scope. – Simon Oct 31 '12 at 19:49
  • Yes, I meant class level scope, but there's nothing like "application wide" anyway. Application is just a bunch of classes. – Marcin Orlowski Oct 31 '12 at 20:09
  • @Simon, yeah, sorry, that's what I meant. – MPKenning Oct 31 '12 at 20:12
1

You can't set references to views in your layout before you inflate the root layout with setContentView().

 final EditText reactantNumberField;

Then in onCreate, after setContentView()

 reactantNumberField = (EditText) findViewById(R.id.reactantsNumber);
Simon
  • 14,407
  • 8
  • 46
  • 61
  • Still force closing, thanks anyway. Will update given code to include this. – MPKenning Oct 31 '12 at 19:19
  • Please remove the old code and error and post the new error. You should also read some tutorials and in particular, how to properly create an Activity. There are many problems in your code. – Simon Oct 31 '12 at 19:47