我一直试图运行我的应用程序,但每次按下按钮都会将我重定向到"管理约会"页面,应用程序崩溃。以下是我的代码:
ManageAppointments.java
public class ManageAppointments extends FragmentActivity implements AppDialogFragmentListener {
private Fragment contentFragment;
private AppListFrag appListFragment;
private AppAddFrag appAddFragment;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.manage_appointments);
java.text.DateFormat formatter = android.text.format.DateFormat.getDateFormat(getApplicationContext());
FragmentManager fragmentManager = getSupportFragmentManager();
/*
* This is called when orientation is changed.
*/
if (savedInstanceState != null) {
if (savedInstanceState.containsKey("content")) {
String content = savedInstanceState.getString("content");
if (content.equals(AppAddFrag.ARG_ITEM_ID)) {
if (fragmentManager.findFragmentByTag(AppAddFrag.ARG_ITEM_ID) != null) {
setFragmentTitle(R.string.add_appointment);
contentFragment = fragmentManager.findFragmentByTag(AppAddFrag.ARG_ITEM_ID);
}
}
}
if (fragmentManager.findFragmentByTag(AppListFrag.ARG_ITEM_ID) != null) {
appListFragment = (AppListFrag) fragmentManager.findFragmentByTag(AppListFrag.ARG_ITEM_ID);
contentFragment = appListFragment;
}
} else {
appListFragment = new AppListFrag();
setFragmentTitle(R.string.app_name);
switchContent(appListFragment, AppListFrag.ARG_ITEM_ID);
}
}
@Override
protected void onSaveInstanceState(Bundle outState) {
if (contentFragment instanceof AppAddFrag) {
outState.putString("content", AppAddFrag.ARG_ITEM_ID);
} else {
outState.putString("content", AppListFrag.ARG_ITEM_ID);
}
super.onSaveInstanceState(outState);
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_main, menu);
return true;
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.action_add:
setFragmentTitle(R.string.add_appointment);
appAddFragment = new AppAddFrag();
switchContent(appAddFragment, AppAddFrag.ARG_ITEM_ID);
return true;
}
return super.onOptionsItemSelected(item);
}
/*
* We consider PatientListFragment as the home fragment and it is not added to
* the back stack.
*/
public void switchContent(Fragment fragment, String tag) {
FragmentManager fragmentManager = getSupportFragmentManager();
while (fragmentManager.popBackStackImmediate())
;
if (fragment != null) {
FragmentTransaction transaction = fragmentManager
.beginTransaction();
transaction.replace(R.id.content_frame, fragment, tag);
// Only PatientAddFragment is added to the back stack.
if (!(fragment instanceof AppListFrag)) {
transaction.addToBackStack(tag);
}
transaction.commit();
contentFragment = fragment;
}
}
protected void setFragmentTitle(int resourseId) {
setTitle(resourseId);
getActionBar().setTitle(resourseId);
}
/*
* We call super.onBackPressed(); when the stack entry count is > 0. if it
* is instanceof PatientListFragment or if the stack entry count is == 0, then
* we prompt the user whether to quit the app or not by displaying dialog.
* In other words, from PatientListFragment on back press it quits the app.
*/
@Override
public void onBackPressed() {
FragmentManager fm = getSupportFragmentManager();
if (fm.getBackStackEntryCount() > 0) {
super.onBackPressed();
} else if (contentFragment instanceof AppListFrag
|| fm.getBackStackEntryCount() == 0) {
//Shows an alert dialog on quit
onShowQuitDialog();
}
}
public void onShowQuitDialog() {
AlertDialog.Builder builder = new AlertDialog.Builder(this);
builder.setCancelable(false);
builder.setMessage("Do You Want To Quit?");
builder.setPositiveButton(android.R.string.yes,
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int id) {
finish();
}
});
builder.setNegativeButton(android.R.string.no,
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
dialog.cancel();
}
});
builder.create().show();
}
@Override
public void onFinishDialog() {
if (appListFragment != null) {
appListFragment.updateView();
}
}
}
AppListFragment.java
public class AppListFrag extends Fragment implements AdapterView.OnItemClickListener, AdapterView.OnItemLongClickListener {
public static final String ARG_ITEM_ID = "appointment_list";
Activity activity;
ListView appListView;
ArrayList<Appointment> appointments;
AppListAdapter appListAdapter;
AppointmentDAO appointmentDAO;
private GetAppointmentTask task;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
activity = getActivity();
appointmentDAO = new AppointmentDAO(activity);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.frag_app_list, container, false);
findViewsById(view);
task = new GetAppointmentTask(activity);
task.execute((Void) null);
appListView.setOnItemClickListener(this);
appListView.setOnItemLongClickListener(this);
return view;
}
private void findViewsById(View view) {
appListView = (ListView) view.findViewById(R.id.list);
}
@Override
public void onResume() {
getActivity().setTitle(R.string.app_name);
getActivity().getActionBar().setTitle(R.string.app_name);
super.onResume();
}
@Override
public void onItemClick(AdapterView<?> list, View arg1, int position, long arg3) {
Appointment appointment = (Appointment) list.getItemAtPosition(position);
if (appointment != null) {
Bundle arguments = new Bundle();
arguments.putParcelable("selectedAppointment", appointment);
CustomAppDialogFragment customAppDialogFragment = new CustomAppDialogFragment();
customAppDialogFragment.setArguments(arguments);
customAppDialogFragment.show(getFragmentManager(), CustomAppDialogFragment.ARG_ITEM_ID);
}
}
@Override
public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long arg3) {
Appointment appointment = (Appointment) parent.getItemAtPosition(position);
// Use AsyncTask to delete from database
appointmentDAO.delete(appointment);
appListAdapter.remove(appointment);
return true;
}
public class GetAppointmentTask extends AsyncTask<Void, Void, ArrayList<Appointment>> {
private final WeakReference<Activity> activityWeakRef;
public GetAppointmentTask(Activity context) {
this.activityWeakRef = new WeakReference<Activity>(context);
}
@Override
protected ArrayList<Appointment> doInBackground(Void... arg0) {
ArrayList<Appointment> appointmentList = appointmentDAO.getAppointments();
return appointmentList;
}
@Override
protected void onPostExecute(ArrayList<Appointment> appList) {
if (activityWeakRef.get() != null && !activityWeakRef.get().isFinishing()) {
Log.d("appointments", appList.toString());
appointments = appList;
if (appList != null) {
if (appList.size() != 0) {
appListAdapter = new AppListAdapter(activity, appList);
appListView.setAdapter(appListAdapter);
} else {
Toast.makeText(activity, "No Appointments", Toast.LENGTH_LONG).show();
}
}
}
}
}
/*
* This method is invoked from MainActivity onFinishDialog() method. It is
* called from CustomPatientDialogFragment when an patient record is updated.
* This is used for communicating between fragments.
*/
public void updateView() {
task = new GetAppointmentTask(activity);
task.execute((Void) null);
}
}
AppAddFragment.java
public class AppAddFrag extends Fragment implements View.OnClickListener {
// UI references
private EditText appDate, startTime;
private Button addButton, resetButton;
private static final SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd", Locale.ENGLISH);
DatePickerDialog datePickerDialog;
Calendar dateCalendar;
Appointment appointment = null;
private AppointmentDAO appointmentDAO;
private AddAppointmentTask task;
public static final String ARG_ITEM_ID = "app_add_fragment";
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appointmentDAO = new AppointmentDAO(getActivity());
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.frag_add_app, container, false);
findViewsById(rootView);
setListeners();
//For orientation change.
if (savedInstanceState != null) {
dateCalendar = Calendar.getInstance();
if (savedInstanceState.getLong("dateCalendar") != 0)
dateCalendar.setTime(new Date(savedInstanceState
.getLong("dateCalendar")));
}
return rootView;
}
private void setListeners() {
appDate.setOnClickListener(this);
Calendar newCalendar = Calendar.getInstance();
datePickerDialog = new DatePickerDialog(getActivity(),
new DatePickerDialog.OnDateSetListener() {
public void onDateSet(DatePicker view, int year, int monthOfYear, int dayOfMonth) {
dateCalendar = Calendar.getInstance();
dateCalendar.set(year, monthOfYear, dayOfMonth);
appDate.setText(formatter.format(dateCalendar.getTime()));
}
}, newCalendar.get(Calendar.YEAR),
newCalendar.get(Calendar.MONTH),
newCalendar.get(Calendar.DAY_OF_MONTH));
addButton.setOnClickListener(this);
resetButton.setOnClickListener(this);
}
protected void resetAllFields() {
appDate.setText("");
startTime.setText("");
}
private void setAppointment() {
appointment = new Appointment();
if(dateCalendar != null) {
appointment.setAppointmentDate(dateCalendar.getTime());
}
//appointment.setStartTime(startTime.getText().toString());
}
@Override
public void onResume() {
getActivity().setTitle(R.string.add_appointment);
getActivity().getActionBar().setTitle(R.string.add_appointment);
super.onResume();
}
@Override
public void onSaveInstanceState(Bundle outState) {
if (dateCalendar != null)
outState.putLong("dateCalendar", dateCalendar.getTime().getTime());
}
private void findViewsById(View rootView) {
appDate = (EditText) rootView.findViewById(R.id.app_date);
appDate.setInputType(InputType.TYPE_NULL);
startTime = (EditText) rootView.findViewById(R.id.start_time);
addButton = (Button) rootView.findViewById(R.id.button_add);
resetButton = (Button) rootView.findViewById(R.id.button_reset);
}
@Override
public void onClick(View view) {
if (view == appDate) {
datePickerDialog.show();
} else if (view == addButton) {
setAppointment();
task = new AddAppointmentTask(getActivity());
task.execute((Void) null);
} else if (view == resetButton) {
resetAllFields();
}
}
public class AddAppointmentTask extends AsyncTask<Void, Void, Long> {
private final WeakReference<Activity> activityWeakRef;
public AddAppointmentTask(Activity context) {
this.activityWeakRef = new WeakReference<Activity>(context);
}
@Override
protected Long doInBackground(Void... arg0) {
long result = appointmentDAO.save(appointment);
return result;
}
@Override
protected void onPostExecute(Long result) {
if (activityWeakRef.get() != null && !activityWeakRef.get().isFinishing()) {
if (result != -1)
Toast.makeText(activityWeakRef.get(), "Appointment Saved", Toast.LENGTH_LONG).show();
}
}
}
}
错误讯息:
04-11 19:02:12.608 25872-25872/? E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.xpresspatients.fyp, PID: 25872
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.xpresspatients.fyp/com.xpresspatients.fyp.ManageAppointments}: java.lang.NullPointerException
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2237)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2286)
at android.app.ActivityThread.access$800(ActivityThread.java:145)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1243)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5127)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:825)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:641)
at dalvik.system.NativeStart.main(Native Method)
Caused by: java.lang.NullPointerException
at com.xpresspatients.fyp.ManageAppointments.setFragmentTitle(ManageAppointments.java:108)
at com.xpresspatients.fyp.ManageAppointments.onCreate(ManageAppointments.java:50)
at android.app.Activity.performCreate(Activity.java:5231)
at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1087)
at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2201)
at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2286)
at android.app.ActivityThread.access$800(ActivityThread.java:145)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1243)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5127)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
我查看了类似的问题,并尝试相应地进行更改,但仍然遇到此错误。请帮忙。提前谢谢。
答案 0 :(得分:0)
似乎在您的函数setFragmentTitle()
中,getActionBar()
返回null。你似乎没有ActionBar
。你在使用SupportActionBar
吗?试试这个:
protected void setFragmentTitle(int resourseId) {
if (getSupportActionBar() != null) {
getSupportActionBar().setTitle(getString(resourseId));
}
}