What am I doing wrong with my handling of Contex ( Java - Android)
Solution 1
NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference
Because firstElement,secondElement and thirdElement
TextView's is created using con
before calling class constructor in which you are initializing con
. do it as:
private TextView firstElement,secondElement,thirdElement;
public ToDoItem(Context c){
con = c;
firstElement= new TextView(con);
secondElement = new TextView(con);
thirdElement = new TextView(con);
}
Suggestion:
Use current application component context instead of getApplicationContext()
to create Views.
ToDoItem test = new ToDoItem(ActivityName.this);
Solution 2
Never initialize class members with data that is not constant or already set.
You are creating the objects using a reference to the Context before the actual constructor of the class is called and the context is set.
public ToDoItem(Context c){
con = c;
firstElement = new TextView(con);
secondElement = new TextView(con);
thirdElement = new TextView(con);
}
MrSquirreleo
Updated on June 04, 2022Comments
-
MrSquirreleo about 2 years
I made a class (first block of code) that take in a bunch of data, creates 3 TextViews and then returns a RelativeLayout with all three them as children. Do accomplish this I needed to make the constructor of the class take in a argument for 'Context' since I need 'Context' to create the TextView. However when I try to create the class and pass in context (through getApplicationContex)I get an error (please see the log below in the second block of code)
Class:
package com.pp.camry.schoolprojectorganizer; //These imports are used to setup the android widgets that the class generates import android.content.Context; import android.view.View; import android.widget.TextView; import android.widget.RelativeLayout; //Imports for the date handling in the createPartTwo method import java.util.Date; import org.joda.time.DateTime; import java.util.GregorianCalendar; import org.joda.time.Interval; import org.joda.time.Period; public class ToDoItem { //Context Variable private Context con; // Variable Storage for the three different TextView instances private TextView firstElement = new TextView(con); private TextView secondElement = new TextView(con); private TextView thirdElement = new TextView(con); //Class Version (to prevent errors in serialization public final double version = 1.0; //Calaender input variable private DateTime finalInputDate; //Main Return Variable private RelativeLayout finalLayout = new RelativeLayout(con); /** * This is the main public constructor method of the class * @param c The current context of the program */ public ToDoItem(Context c){ con = c; } /** * This method calls the create method on all three other views and cobines them into a view container * @param eventName Name of the event for the first text box * @param className Name of the class for the third text box * @param year Year of the end of the timer * @param month Month of the end of the timer * @param day Day of the end of the timer * @param hour Hour of the end of the timer * @param minute Minute of the end of the timer */ public RelativeLayout createViews(String eventName, String className, int year, int month, int day, int hour, int minute){ firstElement = createPartOne(eventName); secondElement= createPartTwo(year, month, day, hour, minute); thirdElement = createPartThree(className); finalLayout.addView(firstElement); finalLayout.addView(secondElement); finalLayout.addView(thirdElement); //TODO Finish this method, so that the layout looks nice when its returned return finalLayout; } /** * The next three methods are the main constructors of the elements of the class. These methods * create the various TextView that get put together in the later methods */ /** *Creates a TextView with from the given string * @param title Title used for the Text View * @return Returns a TextView Instance */ public TextView createPartOne(String title){ //Create and apply the various properties to the new TextView before returning it //TODO add some more configuration code in here once we see what the feild looks like TextView tempText = new TextView(con); tempText.setText(title); tempText.setHeight(150); tempText.setWidth(950); tempText.setTextSize(40); tempText.setTextAlignment(View.TEXT_ALIGNMENT_CENTER); return tempText; } /** * Sets up the second TextView for the block. This one contains the countdown timer to the * date passed into it * @param year Int number representing the year * @param month Int number representing the month * @param day Int number representing the day * @param hour Int number representing the hour * @param minute Int number representing the minute * @return Returns a TextView with the specified countdown timer */ public TextView createPartTwo(int year, int month, int day, int hour, int minute){ //Construct the current time Date currentDate = new Date(); DateTime currentTime = new DateTime(currentDate); //Construct the inputed time GregorianCalendar input = new GregorianCalendar(); input.set(year, month, day, hour, minute); DateTime inputTime = new DateTime(input.getTime()); finalInputDate = inputTime.toDateTime(); //Do the Comparison Interval timeBet = new Interval(inputTime, currentTime); //Create the Ui Element TextView tempText = new TextView(con); Period outputTime = timeBet.toPeriod(); //Formating stuff down here (really borring, and propaly has the bug your looking for) int outcome; if(outputTime.getYears()<1 && outputTime.getMonths()<1 && outputTime.getDays()<1 && outputTime.getHours()<1){ tempText.setText(outputTime.getMinutes() + " Minutes"); outcome = 0; } if(outputTime.getYears()<1 && outputTime.getMonths()<1 && outputTime.getDays()<1){ tempText.setText(outputTime.getHours() + " Hours " + outputTime.getMinutes() + " Minutes "); outcome = 1; } if(outputTime.getYears()<1 && outputTime.getMonths()<1){ tempText.setText(outputTime.getDays() + " Days " + outputTime.getHours() + " Hours " + outputTime.getMinutes() + " Minutes "); outcome = 2; } if(outputTime.getYears() < 1){ tempText.setText(outputTime.getMonths() + " Months " + outputTime.getDays() + " Days " + outputTime.getHours() + " Hours " + outputTime.getMinutes() + " Minutes "); outcome = 3; } else{ tempText.setText( outputTime.getYears() + " Years " + outputTime.getMonths() + " Months " + outputTime.getDays() + " Days " + outputTime.getHours() + " Hours " + outputTime.getMinutes() + " Minutes "); outcome = 4; } //Setup the basics of the textView tempText.setWidth(950); tempText.setHeight(250); //Modify the Text box further according to the outcome variable. Bigger amounts of numbers need smaller font if(outcome == 0){ tempText.setTextSize(25); } if(outcome == 1){ tempText.setTextSize(20); } if(outcome == 2 ){ tempText.setTextSize(15); } if(outcome == 3){ tempText.setTextSize(10); } if(outcome == 4){ tempText.setTextSize(5); } //Return tempText return tempText; } /** * This method creates the class name box, the last of the three * @param className Name of the school class provided by the user * @return Returns a TextView with the passed in text in it */ public TextView createPartThree(String className){ TextView tempText = new TextView(con); tempText.setText(className); tempText.setHeight(125); tempText.setWidth(950); tempText.setTextSize(30); tempText.setTextAlignment(View.TEXT_ALIGNMENT_CENTER); return tempText; } /** * The following methods are for the utility of the class */ public void updatePartTwo(){ createPartTwo(finalInputDate.getYear(), finalInputDate.getMonthOfYear(), finalInputDate.getDayOfMonth(), finalInputDate.getHourOfDay(), finalInputDate.getMinuteOfHour()); } }
And here is the error log:
01-30 23:22:02.077 13627-13627/com.pp.camry.schoolprojectorganizer E/AndroidRuntime﹕ FATAL EXCEPTION: main Process: com.pp.camry.schoolprojectorganizer, PID: 13627 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.pp.camry.schoolprojectorganizer/com.pp.camry.schoolprojectorganizer.MainScreen}: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2298) at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2360) at android.app.ActivityThread.access$800(ActivityThread.java:144) at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1278) at android.os.Handler.dispatchMessage(Handler.java:102) at android.os.Looper.loop(Looper.java:135) at android.app.ActivityThread.main(ActivityThread.java:5221) at java.lang.reflect.Method.invoke(Native Method) at java.lang.reflect.Method.invoke(Method.java:372) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694) Caused by: java.lang.NullPointerException: Attempt to invoke virtual method 'android.content.res.Resources android.content.Context.getResources()' on a null object reference at android.view.ViewConfiguration.get(ViewConfiguration.java:359) at android.view.View.<init>(View.java:3580) at android.view.View.<init>(View.java:3675) at android.widget.TextView.<init>(TextView.java:634) at android.widget.TextView.<init>(TextView.java:629) at android.widget.TextView.<init>(TextView.java:625) at android.widget.TextView.<init>(TextView.java:621) at com.pp.camry.schoolprojectorganizer.ToDoItem.<init>(ToDoItem.java:26) at com.pp.camry.schoolprojectorganizer.MainScreen.onCreate(MainScreen.java:19) at android.app.Activity.performCreate(Activity.java:5933) at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1105) at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2251) at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2360) at android.app.ActivityThread.access$800(ActivityThread.java:144) at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1278) at android.os.Handler.dispatchMessage(Handler.java:102) at android.os.Looper.loop(Looper.java:135) at android.app.ActivityThread.main(ActivityThread.java:5221) at java.lang.reflect.Method.invoke(Native Method) at java.lang.reflect.Method.invoke(Method.java:372) at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899) at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694)
and here is the call that is cuasing the error:
ToDoItem test = new ToDoItem(getApplicationContext());
If I understand the error my code is giving me then it seems that my call for context is returning a null object. I however don't understand why this is happening. Any help would be greatly apprecitated, and just a heads up this is my first android app so if I am missing something heavily evident or simple