Android-片段中SearchView上的NullPointerException [英] Android - NullPointerException on SearchView in Fragment
问题描述
我总是在片段类的下面一行获得searchView null:
SearchView searchView =(SearchView)MenuItemCompat.getActionView(searchItem);
这是我的片段类,请在底部找到onCreateOptionsMenu方法:
public class FriendsListActivity extends Fragment implements EventListener {
ArrayList<Users> friendList = new ArrayList<Users>();
ArrayList<Users> blockedList = new ArrayList<Users>();
ArrayList<Users> famliyList = new ArrayList<Users>();
ArrayList<Users> newContactList = new ArrayList<Users>();
ArrayList<JSONObject> finalContactList = new ArrayList<JSONObject>();
ArrayList<JSONObject> modifiedContactList = new ArrayList<JSONObject>();
static int count;
private Menu optionsMenu;
private DBHelper mydb ;
Map<String , String> dbContectMap;
SocketOperator socket;
boolean isGetResult = false;
List<String> mobileList = new ArrayList<String>();
JSONObject changeCategoryJobj = new JSONObject();
CutsomAdapter customFriendListAdapter;
String headerpixurl = "images/b58a34f2-ec57-494f-821e-09ecf584449e/profileImage/stickyHeader/82508da9-bf53-488f-a09b-3bb250cc1bd2.PNG";
String startCategory;
String lastCategory = "start";
int isHeader = 0;
ListView lv1;
private boolean isActivityInitialized = false;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
FragmentActivity faActivity = (FragmentActivity) super.getActivity();
// main layout which contains list
LinearLayout llLayout = (LinearLayout) inflater.inflate(R.layout.friends_activity_main, container, false);
//sqlite DB
mydb = new DBHelper(FriendsListActivity.super.getActivity());
dbContectMap = mydb.getAllCotacts();
socket = new SocketOperator(this);
fetchContactsFromPhone();// from phone
int count = 0;
try {
while(!isGetResult && count <= 6){
Thread.sleep(5000);
count++;
}
} catch (InterruptedException e) {
e.printStackTrace();
}
//fetchContactsFromServer(mobileList);
// friends_activity_list_row_layout , represents one item in list view
customFriendListAdapter = new CutsomAdapter(FriendsListActivity.super.getActivity().getApplicationContext(),
R.layout.friends_activity_list_row_layout , finalContactList );
// this will be list which conain items
lv1= (ListView) llLayout.findViewById(R.id.friends_activity_custom_list);
lv1.setStackFromBottom(false);
lv1.setAdapter(customFriendListAdapter);
setHasOptionsMenu(true);
setupActionBar();
isActivityInitialized = true;
return llLayout;
}
// give a delete button to remove permanatly from list
// same code is in LoginActivity, when ever change here also code review the LoginActivity code too
public void fetchContactsFromPhone() {
String phoneNumber = null;
String email = null;
Uri CONTENT_URI = ContactsContract.Contacts.CONTENT_URI;
String _ID = ContactsContract.Contacts._ID;
String DISPLAY_NAME = ContactsContract.Contacts.DISPLAY_NAME;
String HAS_PHONE_NUMBER = ContactsContract.Contacts.HAS_PHONE_NUMBER;
Uri PhoneCONTENT_URI = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;
String Phone_CONTACT_ID = ContactsContract.CommonDataKinds.Phone.CONTACT_ID;
String NUMBER = ContactsContract.CommonDataKinds.Phone.NUMBER;
Uri EmailCONTENT_URI = ContactsContract.CommonDataKinds.Email.CONTENT_URI;
String EmailCONTACT_ID = ContactsContract.CommonDataKinds.Email.CONTACT_ID;
String DATA = ContactsContract.CommonDataKinds.Email.DATA;
//StringBuffer output = new StringBuffer();
ContentResolver contentResolver = FriendsListActivity.super.getActivity().getContentResolver();
Cursor cursor = contentResolver.query(CONTENT_URI, null, null, null,
null);
// Loop for every contact in the phone
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
String contact_id = cursor
.getString(cursor.getColumnIndex(_ID));
String name = cursor.getString(cursor
.getColumnIndex(DISPLAY_NAME));
int hasPhoneNumber = Integer.parseInt(cursor.getString(cursor
.getColumnIndex(HAS_PHONE_NUMBER)));
if (hasPhoneNumber > 0) {
// Query and loop for every phone number of the contact
Cursor phoneCursor = contentResolver.query(
PhoneCONTENT_URI, null, Phone_CONTACT_ID + " = ?",
new String[] { contact_id }, null);
while (phoneCursor.moveToNext()) {
phoneNumber = phoneCursor.getString(phoneCursor
.getColumnIndex(NUMBER));
// output.append("\n Phone number:" + phoneNumber);
}
phoneCursor.close();
Users user = new Users();
user.name = name;
user.mobileNumber = phoneNumber;
//friendList.add(user);
// check if this user/phone number is already added to server friendList
if( !dbContectMap.containsKey(phoneNumber)){
mobileList.add(phoneNumber);
}
}
}
// outputText.setText(output);
}
// send to server and update mydb
try {
JSONObject jsonObj = new JSONObject();
jsonObj.put("action", "addNewContactInFriendList");
jsonObj.put("userid", MyData.getMyDataInstance().getString(MyData.USERID));
JSONArray mobileListArray = new JSONArray(mobileList);
jsonObj.put("mobileList", mobileListArray);
socket.sendMessage(jsonObj);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
/**
* The Class CutsomAdapter is the adapter class for Activity ListView. The
* currently implementation of this adapter simply display static dummy
* contents. You need to write the code for displaying actual contents.
*/
private class CutsomAdapter extends ArrayAdapter<JSONObject> implements
PinnedSectionListAdapter, Filterable {
private LayoutInflater layoutInflater;
private Context context;
List<Users> userList;
String radioGroupType;
private OnCustomClickListener callback;
int itemListSize = 0;
ArrayList<JSONObject> listData;
ArrayList<JSONObject> tempListData;
private FriendsFilter friendsFilter;
public CutsomAdapter(Context context, int textViewResourceId, ArrayList<JSONObject> finalArrayList) {
super(context, textViewResourceId, finalArrayList);
layoutInflater = LayoutInflater.from(context);
this.context = context;
this.listData = finalArrayList;
this.tempListData = finalArrayList;
}
View convertView = null;
class ViewHolder {
ImageView headerImage;
TextView name;
TextView mobile;
RadioGroup radioCategory;
RadioButton radioButton;
}
class HeaderViewHolder {
TextView categoryName;
}
public void setContext(Context context) {
this.context = context;
}
@Override
public int getCount() {
itemListSize = listData.size();
return listData.size();
}
public void setListData(List<JSONObject> list) {
this.listData = (ArrayList<JSONObject>) list;
}
@Override
public JSONObject getItem(int position) {
return listData.get(position);
}
@Override
public boolean isItemViewTypePinned(int viewType) {
boolean toBePinned = false;
if (viewType == 1)
toBePinned = true;
// System.out.println("toBePinned: "+toBePinned);
return toBePinned;
}
@Override
public int getItemViewType(int position) {
JSONObject jo = this.listData.get(position);
int k = 0;
isHeader = 0;
try {
String header = jo.getString("headerStr");
if(header != null && "headerStr".equalsIgnoreCase("headerStr")){
k=1;
isHeader = 1;
}
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return k;
}
@Override
public int getViewTypeCount() {
return 2;
}
/*
* (non-Javadoc)
*
* @see android.widget.Adapter#getItemId(int)
*/
@Override
public long getItemId(int arg0) {
return arg0;
}
/*
* (non-Javadoc)
*
* @see android.widget.Adapter#getView(int, android.view.View,
* android.view.ViewGroup)
*/
@Override
public View getView(final int position, View convertViewx, ViewGroup parent) {
final JSONObject jObj = (JSONObject) listData.get(position);
View convertView = null;
//int isHeader = 0;
try {
//isHeader = jObj.getInt("TYPE");
String header = jObj.getString("headerStr");
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
//if (lastCategory.equalsIgnoreCase("start") || !startCategory.equalsIgnoreCase(lastCategory)) {
if(isHeader == 1){
final JSONObject jObjX = (JSONObject) listData.get(position);
convertView = layoutInflater.inflate(R.layout.friends_activity_sticky_header,
null);
final HeaderViewHolder headerViewHolder = new HeaderViewHolder();
convertView.setBackgroundColor(Color.WHITE);
headerViewHolder.categoryName = (TextView) convertView
.findViewById(R.id.header);
try {
String header = jObjX.getString("headerStr");
headerViewHolder.categoryName.setText(header);
//headerViewHolder.userProfilePic.seti();
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
else {
try {
final ViewHolder holder;
if (convertView == null) {
convertView = layoutInflater.inflate(
R.layout.friends_activity_list_row_layout, null);
}
holder = new ViewHolder();
holder.headerImage = (ImageView)convertView.findViewById(R.id.headerImage);
Picasso.with(context).load(MyData.SERVER_URL+jObj.getString("headerpixurl")).into(holder.headerImage);
holder.name = (TextView) convertView.findViewById(R.id.name);
holder.name.setText(jObj.getString("name"));
holder.mobile = (TextView) convertView.findViewById(R.id.mobile);
holder.mobile.setText(jObj.getString("mobile"));
if(jObj.getString("category").equalsIgnoreCase("friends")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.friend);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("family")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.family);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("blocked")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.block);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("newuser")){
// dont do any thing let user select , which category he choose for this user
}
holder.radioCategory = (RadioGroup) convertView.findViewById(R.id.radioCategory);
holder.radioCategory.setTag(position);
holder.radioCategory.setOnCheckedChangeListener(listener);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
lastCategory = startCategory;
}
return convertView;
}
// https://stackoverflow.com/questions/28574000/fill-a-listview-with-radio-button-groups-with-an-onclick-listener-in-the-adapter
RadioGroup.OnCheckedChangeListener listener = new RadioGroup.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(RadioGroup radioGroup, int id) {
RadioButton radio = (RadioButton)radioGroup.findViewById(radioGroup.getCheckedRadioButtonId());
int index = (Integer) radioGroup.getTag();
JSONObject selected = (JSONObject) getItem(index);
try{
switch (id) {
case R.id.friend:
System.out.println("friend");
selected.put("newCategory", "friends");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
case R.id.family:
System.out.println("family");
selected.put("newCategory", "family");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
case R.id.block:
System.out.println("block");
selected.put("newCategory", "blocked");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
}
}catch(Exception ex){
}
}
};
public void resetData() {
listData = tempListData ;
}
@Override
public Filter getFilter() {
if (friendsFilter == null)
friendsFilter = new FriendsFilter();
return friendsFilter;
}
// https://github.com/survivingwithandroid/Surviving-with-android/blob/master/ListView_Filter_Tutorial/src/com/survivingwithandroid/listview/SimpleList/PlanetAdapter.java
private class FriendsFilter extends Filter {
@Override
protected FilterResults performFiltering(CharSequence constraint) {
FilterResults results = new FilterResults();
// We implement here the filter logic
if (constraint == null || constraint.length() == 0) {
// No filter implemented we return all the list
results.values = tempListData;
results.count = tempListData.size();
}
else {
// We perform filtering operation
List<JSONObject> nPlanetList = new ArrayList<JSONObject>();
for (JSONObject p : listData) {
try {
if (p.getString("name").toUpperCase().startsWith(constraint.toString().toUpperCase()))
nPlanetList.add(p);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
results.values = nPlanetList;
results.count = nPlanetList.size();
}
return results;
}
@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
// Now we have to inform the adapter about the new list filtered
if (results.count == 0)
notifyDataSetInvalidated();
else {
listData = (ArrayList<JSONObject>) results.values;
notifyDataSetChanged();
}
}
}
}
private void toList(List<Users> contactList, JSONArray array) throws JSONException {
int size = array.length();
for (int i = 0; i < size; i++) {
JSONObject jobj = array.getJSONObject(i);
Users user = new Users();
user.userid = jobj.getString("userid");
user.name = jobj.getString("name");
//user.category = jobj.getString("category");
user.imageURL = jobj.getString("headerpixurl");
// #### FOR TESTING
headerpixurl = jobj.getString("headerpixurl");
user.mobileNumber = jobj.getString("mobile");
contactList.add(user);
}
//return contactList;
}
// #### FOR TESTING ####
private void testing(JSONArray jArray, String category){
for (count= 0; count < 5; count++) {
try {
JSONObject jObj = new JSONObject();
jObj.put("userid", "1234"+count);
jObj.put("name", "vichi"+count);
jObj.put("mobile", "9999");
jObj.put("headerpixurl", headerpixurl);
jObj.put("category", category);
jArray.put(jObj);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
private void mergeInList(JSONArray jArray){
for(int i=0; i < jArray.length(); i++){
try {
finalContactList.add(jArray.getJSONObject(i));
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
@Override
public void eventReceived(String event) throws JSONException {
// when we will get return phone number then only we will update sqlite table
final JSONObject eventJObjx = new JSONObject(event);
if(isActivityInitialized){
FriendsListActivity.super.getActivity().runOnUiThread(new Runnable() {
@Override
public void run() {
try {
intilizeContactsList(eventJObjx);
customFriendListAdapter.notifyDataSetChanged();
}catch(Exception ex){
}
}
});
}else{
intilizeContactsList(eventJObjx);
}
//mydb.insertContact(phone, "Y");
}
private void intilizeContactsList(JSONObject eventJObjx) throws JSONException{
//#### ALWAYS MAINTAIN THIS ORDER ####
finalContactList.clear();
modifiedContactList.clear();
JSONArray newuserArray = eventJObjx.getJSONArray("newuser");
if(newuserArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " New User");
finalContactList.add(jObj1);
mergeInList(newuserArray);
}
JSONArray friendsArray = eventJObjx.getJSONArray("friends");
//testing(friendsArray, "friends");
if(friendsArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Friends ");
finalContactList.add(jObj1);
mergeInList(friendsArray);
}
JSONArray familyArray = eventJObjx.getJSONArray("family");
//testing(familyArray, "family");
if(familyArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Family ");
finalContactList.add(jObj1);
mergeInList(familyArray);
}
JSONArray blockedArray = eventJObjx.getJSONArray("blocked");
//testing(blockedArray, "blocked");
if(blockedArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Blocked ");
finalContactList.add(jObj1);
mergeInList(blockedArray);
}
for(int i=0; i < newuserArray.length(); i++){
//mobileToAddInFriendList.add(mobileListArray.getString(i));
mydb.insertContact(newuserArray.getJSONObject(i).getString("mobile"), "Y");
}
isGetResult = true;
}
protected void setupActionBar() {
final ActionBar actionBar = FriendsListActivity.super.getActivity().getActionBar();
actionBar.setDisplayShowTitleEnabled(true);
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setDisplayUseLogoEnabled(true);
actionBar.setLogo(R.drawable.icon);
actionBar.setBackgroundDrawable(getResources().getDrawable(
R.drawable.actionbar_bg));
// actionBar.setDisplayHomeAsUpEnabled(true);
// actionBar.setHomeButtonEnabled(true);
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
FriendsListActivity.super.getActivity().getMenuInflater().inflate(R.menu.friends_activity_menu, menu);
this.optionsMenu = menu;
super.onCreateOptionsMenu(menu, inflater);
SearchManager searchManager = (SearchManager) FriendsListActivity.super.getActivity().getSystemService(Context.SEARCH_SERVICE);
//SearchView searchView = (SearchView) menu.findItem(R.id.action_search).getActionView();
MenuItem searchItem = menu.findItem(R.id.action_search);
SearchView searchView = (SearchView) MenuItemCompat.getActionView(searchItem);
searchView.setSearchableInfo(searchManager.getSearchableInfo(FriendsListActivity.super.getActivity().getComponentName()));
searchView.setIconifiedByDefault(false);
SearchView.OnQueryTextListener textChangeListener = new SearchView.OnQueryTextListener()
{
@Override
public boolean onQueryTextChange(String newText)
{
// this is your adapter that will be filtered
customFriendListAdapter.getFilter().filter(newText);
System.out.println("on text chnge text: "+newText);
return true;
}
@Override
public boolean onQueryTextSubmit(String query)
{
// this is your adapter that will be filtered
customFriendListAdapter.getFilter().filter(query);
System.out.println("on query submit: "+query);
return true;
}
};
searchView.setOnQueryTextListener(textChangeListener);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
super.onOptionsItemSelected(item);
switch (item.getItemId()) {
case R.id.done:
try {
JSONObject jsonObj = new JSONObject();
jsonObj.put("action", "moveContact");
jsonObj.put("userid", MyData.getMyDataInstance().getString(MyData.USERID));
JSONArray mobileListArray = new JSONArray(modifiedContactList);
jsonObj.put("modifiedList", mobileListArray);
socket.sendMessage(jsonObj);
modifiedContactList.clear();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
break;
}
return super.onOptionsItemSelected(item);
}
}
这是我的menu.xml文件
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item
android:id="@+id/done"
android:icon="@drawable/ic_action_accept"
app:showAsAction="always"
android:title="@string/upload"/>
<item
android:id="@+id/action_search"
app:actionViewClass="android.support.v7.widget.SearchView"
android:icon="@drawable/ic_launcher"
app:showAsAction="always|collapseActionView"
android:maxWidth="100dp"
android:title="Search"/>
</menu>
这是日志摘要:
07-23 15:18:59.015 1841-1841/com.woohoo E/AndroidRuntime? FATAL EXCEPTION: main
Process: com.woohoo, PID: 1841
java.lang.NullPointerException
at com.woohoo.FriendsListActivity.onCreateOptionsMenu(FriendsListActivity.java:797)
at android.support.v4.app.Fragment.performCreateOptionsMenu(Fragment.java:1871)
at android.support.v4.app.FragmentManagerImpl.dispatchCreateOptionsMenu(FragmentManager.java:2001)
at android.support.v4.app.FragmentActivity.onCreatePanelMenu(FragmentActivity.java:278)
at com.android.internal.policy.impl.PhoneWindow.preparePanel(PhoneWindow.java:436)
at com.android.internal.policy.impl.PhoneWindow.doInvalidatePanelMenu(PhoneWindow.java:800)
at com.android.internal.policy.impl.PhoneWindow$1.run(PhoneWindow.java:221)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
at android.view.Choreographer.doCallbacks(Choreographer.java:574)
at android.view.Choreographer.doFrame(Choreographer.java:543)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:747)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5001)
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:785)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
at dalvik.system.NativeStart.main(Native Method)
令人惊讶的是,它在Eclipse中运行良好,但在Android Studio中提供了nullpointerexception.
我已经尝试过使用与以下链接相同的配置: Android-操作栏中SearchView上的NullPointerException >
问题出在您的片段中.根据这一行:
at com.woohoo.FriendsListActivity.onCreateOptionsMenu(FriendsListActivity.java:797)
NullPointerException在您的FriendsListActivity中,特别是在onCreateOptionsMenu的第797行中
我查看了您的onCreateOptionsMenu,可能有几件事称为NullPointerException.找到797行会容易得多(请检查 或此(如果您)不知道如何在IDE中转换行号)
也不要将片段称为FriendsListActivity.例如,将其重命名为FriendsListFragment以避免混淆.
I am always getting searchView null at below line in my fragment class:
SearchView searchView = (SearchView) MenuItemCompat.getActionView(searchItem);
here is my fragment class, Please find onCreateOptionsMenu method at bottom:
public class FriendsListActivity extends Fragment implements EventListener {
ArrayList<Users> friendList = new ArrayList<Users>();
ArrayList<Users> blockedList = new ArrayList<Users>();
ArrayList<Users> famliyList = new ArrayList<Users>();
ArrayList<Users> newContactList = new ArrayList<Users>();
ArrayList<JSONObject> finalContactList = new ArrayList<JSONObject>();
ArrayList<JSONObject> modifiedContactList = new ArrayList<JSONObject>();
static int count;
private Menu optionsMenu;
private DBHelper mydb ;
Map<String , String> dbContectMap;
SocketOperator socket;
boolean isGetResult = false;
List<String> mobileList = new ArrayList<String>();
JSONObject changeCategoryJobj = new JSONObject();
CutsomAdapter customFriendListAdapter;
String headerpixurl = "images/b58a34f2-ec57-494f-821e-09ecf584449e/profileImage/stickyHeader/82508da9-bf53-488f-a09b-3bb250cc1bd2.PNG";
String startCategory;
String lastCategory = "start";
int isHeader = 0;
ListView lv1;
private boolean isActivityInitialized = false;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
FragmentActivity faActivity = (FragmentActivity) super.getActivity();
// main layout which contains list
LinearLayout llLayout = (LinearLayout) inflater.inflate(R.layout.friends_activity_main, container, false);
//sqlite DB
mydb = new DBHelper(FriendsListActivity.super.getActivity());
dbContectMap = mydb.getAllCotacts();
socket = new SocketOperator(this);
fetchContactsFromPhone();// from phone
int count = 0;
try {
while(!isGetResult && count <= 6){
Thread.sleep(5000);
count++;
}
} catch (InterruptedException e) {
e.printStackTrace();
}
//fetchContactsFromServer(mobileList);
// friends_activity_list_row_layout , represents one item in list view
customFriendListAdapter = new CutsomAdapter(FriendsListActivity.super.getActivity().getApplicationContext(),
R.layout.friends_activity_list_row_layout , finalContactList );
// this will be list which conain items
lv1= (ListView) llLayout.findViewById(R.id.friends_activity_custom_list);
lv1.setStackFromBottom(false);
lv1.setAdapter(customFriendListAdapter);
setHasOptionsMenu(true);
setupActionBar();
isActivityInitialized = true;
return llLayout;
}
// give a delete button to remove permanatly from list
// same code is in LoginActivity, when ever change here also code review the LoginActivity code too
public void fetchContactsFromPhone() {
String phoneNumber = null;
String email = null;
Uri CONTENT_URI = ContactsContract.Contacts.CONTENT_URI;
String _ID = ContactsContract.Contacts._ID;
String DISPLAY_NAME = ContactsContract.Contacts.DISPLAY_NAME;
String HAS_PHONE_NUMBER = ContactsContract.Contacts.HAS_PHONE_NUMBER;
Uri PhoneCONTENT_URI = ContactsContract.CommonDataKinds.Phone.CONTENT_URI;
String Phone_CONTACT_ID = ContactsContract.CommonDataKinds.Phone.CONTACT_ID;
String NUMBER = ContactsContract.CommonDataKinds.Phone.NUMBER;
Uri EmailCONTENT_URI = ContactsContract.CommonDataKinds.Email.CONTENT_URI;
String EmailCONTACT_ID = ContactsContract.CommonDataKinds.Email.CONTACT_ID;
String DATA = ContactsContract.CommonDataKinds.Email.DATA;
//StringBuffer output = new StringBuffer();
ContentResolver contentResolver = FriendsListActivity.super.getActivity().getContentResolver();
Cursor cursor = contentResolver.query(CONTENT_URI, null, null, null,
null);
// Loop for every contact in the phone
if (cursor.getCount() > 0) {
while (cursor.moveToNext()) {
String contact_id = cursor
.getString(cursor.getColumnIndex(_ID));
String name = cursor.getString(cursor
.getColumnIndex(DISPLAY_NAME));
int hasPhoneNumber = Integer.parseInt(cursor.getString(cursor
.getColumnIndex(HAS_PHONE_NUMBER)));
if (hasPhoneNumber > 0) {
// Query and loop for every phone number of the contact
Cursor phoneCursor = contentResolver.query(
PhoneCONTENT_URI, null, Phone_CONTACT_ID + " = ?",
new String[] { contact_id }, null);
while (phoneCursor.moveToNext()) {
phoneNumber = phoneCursor.getString(phoneCursor
.getColumnIndex(NUMBER));
// output.append("\n Phone number:" + phoneNumber);
}
phoneCursor.close();
Users user = new Users();
user.name = name;
user.mobileNumber = phoneNumber;
//friendList.add(user);
// check if this user/phone number is already added to server friendList
if( !dbContectMap.containsKey(phoneNumber)){
mobileList.add(phoneNumber);
}
}
}
// outputText.setText(output);
}
// send to server and update mydb
try {
JSONObject jsonObj = new JSONObject();
jsonObj.put("action", "addNewContactInFriendList");
jsonObj.put("userid", MyData.getMyDataInstance().getString(MyData.USERID));
JSONArray mobileListArray = new JSONArray(mobileList);
jsonObj.put("mobileList", mobileListArray);
socket.sendMessage(jsonObj);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
/**
* The Class CutsomAdapter is the adapter class for Activity ListView. The
* currently implementation of this adapter simply display static dummy
* contents. You need to write the code for displaying actual contents.
*/
private class CutsomAdapter extends ArrayAdapter<JSONObject> implements
PinnedSectionListAdapter, Filterable {
private LayoutInflater layoutInflater;
private Context context;
List<Users> userList;
String radioGroupType;
private OnCustomClickListener callback;
int itemListSize = 0;
ArrayList<JSONObject> listData;
ArrayList<JSONObject> tempListData;
private FriendsFilter friendsFilter;
public CutsomAdapter(Context context, int textViewResourceId, ArrayList<JSONObject> finalArrayList) {
super(context, textViewResourceId, finalArrayList);
layoutInflater = LayoutInflater.from(context);
this.context = context;
this.listData = finalArrayList;
this.tempListData = finalArrayList;
}
View convertView = null;
class ViewHolder {
ImageView headerImage;
TextView name;
TextView mobile;
RadioGroup radioCategory;
RadioButton radioButton;
}
class HeaderViewHolder {
TextView categoryName;
}
public void setContext(Context context) {
this.context = context;
}
@Override
public int getCount() {
itemListSize = listData.size();
return listData.size();
}
public void setListData(List<JSONObject> list) {
this.listData = (ArrayList<JSONObject>) list;
}
@Override
public JSONObject getItem(int position) {
return listData.get(position);
}
@Override
public boolean isItemViewTypePinned(int viewType) {
boolean toBePinned = false;
if (viewType == 1)
toBePinned = true;
// System.out.println("toBePinned: "+toBePinned);
return toBePinned;
}
@Override
public int getItemViewType(int position) {
JSONObject jo = this.listData.get(position);
int k = 0;
isHeader = 0;
try {
String header = jo.getString("headerStr");
if(header != null && "headerStr".equalsIgnoreCase("headerStr")){
k=1;
isHeader = 1;
}
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return k;
}
@Override
public int getViewTypeCount() {
return 2;
}
/*
* (non-Javadoc)
*
* @see android.widget.Adapter#getItemId(int)
*/
@Override
public long getItemId(int arg0) {
return arg0;
}
/*
* (non-Javadoc)
*
* @see android.widget.Adapter#getView(int, android.view.View,
* android.view.ViewGroup)
*/
@Override
public View getView(final int position, View convertViewx, ViewGroup parent) {
final JSONObject jObj = (JSONObject) listData.get(position);
View convertView = null;
//int isHeader = 0;
try {
//isHeader = jObj.getInt("TYPE");
String header = jObj.getString("headerStr");
} catch (Exception e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
//if (lastCategory.equalsIgnoreCase("start") || !startCategory.equalsIgnoreCase(lastCategory)) {
if(isHeader == 1){
final JSONObject jObjX = (JSONObject) listData.get(position);
convertView = layoutInflater.inflate(R.layout.friends_activity_sticky_header,
null);
final HeaderViewHolder headerViewHolder = new HeaderViewHolder();
convertView.setBackgroundColor(Color.WHITE);
headerViewHolder.categoryName = (TextView) convertView
.findViewById(R.id.header);
try {
String header = jObjX.getString("headerStr");
headerViewHolder.categoryName.setText(header);
//headerViewHolder.userProfilePic.seti();
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
else {
try {
final ViewHolder holder;
if (convertView == null) {
convertView = layoutInflater.inflate(
R.layout.friends_activity_list_row_layout, null);
}
holder = new ViewHolder();
holder.headerImage = (ImageView)convertView.findViewById(R.id.headerImage);
Picasso.with(context).load(MyData.SERVER_URL+jObj.getString("headerpixurl")).into(holder.headerImage);
holder.name = (TextView) convertView.findViewById(R.id.name);
holder.name.setText(jObj.getString("name"));
holder.mobile = (TextView) convertView.findViewById(R.id.mobile);
holder.mobile.setText(jObj.getString("mobile"));
if(jObj.getString("category").equalsIgnoreCase("friends")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.friend);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("family")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.family);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("blocked")){
holder.radioButton = (RadioButton) convertView.findViewById(R.id.block);
holder.radioButton.setChecked(true);
}else if(jObj.getString("category").equalsIgnoreCase("newuser")){
// dont do any thing let user select , which category he choose for this user
}
holder.radioCategory = (RadioGroup) convertView.findViewById(R.id.radioCategory);
holder.radioCategory.setTag(position);
holder.radioCategory.setOnCheckedChangeListener(listener);
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
lastCategory = startCategory;
}
return convertView;
}
// https://stackoverflow.com/questions/28574000/fill-a-listview-with-radio-button-groups-with-an-onclick-listener-in-the-adapter
RadioGroup.OnCheckedChangeListener listener = new RadioGroup.OnCheckedChangeListener() {
@Override
public void onCheckedChanged(RadioGroup radioGroup, int id) {
RadioButton radio = (RadioButton)radioGroup.findViewById(radioGroup.getCheckedRadioButtonId());
int index = (Integer) radioGroup.getTag();
JSONObject selected = (JSONObject) getItem(index);
try{
switch (id) {
case R.id.friend:
System.out.println("friend");
selected.put("newCategory", "friends");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
case R.id.family:
System.out.println("family");
selected.put("newCategory", "family");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
case R.id.block:
System.out.println("block");
selected.put("newCategory", "blocked");
modifiedContactList.add(selected);
//finalContactList.remove(index);
break;
}
}catch(Exception ex){
}
}
};
public void resetData() {
listData = tempListData ;
}
@Override
public Filter getFilter() {
if (friendsFilter == null)
friendsFilter = new FriendsFilter();
return friendsFilter;
}
// https://github.com/survivingwithandroid/Surviving-with-android/blob/master/ListView_Filter_Tutorial/src/com/survivingwithandroid/listview/SimpleList/PlanetAdapter.java
private class FriendsFilter extends Filter {
@Override
protected FilterResults performFiltering(CharSequence constraint) {
FilterResults results = new FilterResults();
// We implement here the filter logic
if (constraint == null || constraint.length() == 0) {
// No filter implemented we return all the list
results.values = tempListData;
results.count = tempListData.size();
}
else {
// We perform filtering operation
List<JSONObject> nPlanetList = new ArrayList<JSONObject>();
for (JSONObject p : listData) {
try {
if (p.getString("name").toUpperCase().startsWith(constraint.toString().toUpperCase()))
nPlanetList.add(p);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
results.values = nPlanetList;
results.count = nPlanetList.size();
}
return results;
}
@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
// Now we have to inform the adapter about the new list filtered
if (results.count == 0)
notifyDataSetInvalidated();
else {
listData = (ArrayList<JSONObject>) results.values;
notifyDataSetChanged();
}
}
}
}
private void toList(List<Users> contactList, JSONArray array) throws JSONException {
int size = array.length();
for (int i = 0; i < size; i++) {
JSONObject jobj = array.getJSONObject(i);
Users user = new Users();
user.userid = jobj.getString("userid");
user.name = jobj.getString("name");
//user.category = jobj.getString("category");
user.imageURL = jobj.getString("headerpixurl");
// #### FOR TESTING
headerpixurl = jobj.getString("headerpixurl");
user.mobileNumber = jobj.getString("mobile");
contactList.add(user);
}
//return contactList;
}
// #### FOR TESTING ####
private void testing(JSONArray jArray, String category){
for (count= 0; count < 5; count++) {
try {
JSONObject jObj = new JSONObject();
jObj.put("userid", "1234"+count);
jObj.put("name", "vichi"+count);
jObj.put("mobile", "9999");
jObj.put("headerpixurl", headerpixurl);
jObj.put("category", category);
jArray.put(jObj);
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
private void mergeInList(JSONArray jArray){
for(int i=0; i < jArray.length(); i++){
try {
finalContactList.add(jArray.getJSONObject(i));
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
@Override
public void eventReceived(String event) throws JSONException {
// when we will get return phone number then only we will update sqlite table
final JSONObject eventJObjx = new JSONObject(event);
if(isActivityInitialized){
FriendsListActivity.super.getActivity().runOnUiThread(new Runnable() {
@Override
public void run() {
try {
intilizeContactsList(eventJObjx);
customFriendListAdapter.notifyDataSetChanged();
}catch(Exception ex){
}
}
});
}else{
intilizeContactsList(eventJObjx);
}
//mydb.insertContact(phone, "Y");
}
private void intilizeContactsList(JSONObject eventJObjx) throws JSONException{
//#### ALWAYS MAINTAIN THIS ORDER ####
finalContactList.clear();
modifiedContactList.clear();
JSONArray newuserArray = eventJObjx.getJSONArray("newuser");
if(newuserArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " New User");
finalContactList.add(jObj1);
mergeInList(newuserArray);
}
JSONArray friendsArray = eventJObjx.getJSONArray("friends");
//testing(friendsArray, "friends");
if(friendsArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Friends ");
finalContactList.add(jObj1);
mergeInList(friendsArray);
}
JSONArray familyArray = eventJObjx.getJSONArray("family");
//testing(familyArray, "family");
if(familyArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Family ");
finalContactList.add(jObj1);
mergeInList(familyArray);
}
JSONArray blockedArray = eventJObjx.getJSONArray("blocked");
//testing(blockedArray, "blocked");
if(blockedArray.length() > 0){
JSONObject jObj1 = new JSONObject();
jObj1.put("headerStr", " Blocked ");
finalContactList.add(jObj1);
mergeInList(blockedArray);
}
for(int i=0; i < newuserArray.length(); i++){
//mobileToAddInFriendList.add(mobileListArray.getString(i));
mydb.insertContact(newuserArray.getJSONObject(i).getString("mobile"), "Y");
}
isGetResult = true;
}
protected void setupActionBar() {
final ActionBar actionBar = FriendsListActivity.super.getActivity().getActionBar();
actionBar.setDisplayShowTitleEnabled(true);
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
actionBar.setDisplayUseLogoEnabled(true);
actionBar.setLogo(R.drawable.icon);
actionBar.setBackgroundDrawable(getResources().getDrawable(
R.drawable.actionbar_bg));
// actionBar.setDisplayHomeAsUpEnabled(true);
// actionBar.setHomeButtonEnabled(true);
}
@Override
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
FriendsListActivity.super.getActivity().getMenuInflater().inflate(R.menu.friends_activity_menu, menu);
this.optionsMenu = menu;
super.onCreateOptionsMenu(menu, inflater);
SearchManager searchManager = (SearchManager) FriendsListActivity.super.getActivity().getSystemService(Context.SEARCH_SERVICE);
//SearchView searchView = (SearchView) menu.findItem(R.id.action_search).getActionView();
MenuItem searchItem = menu.findItem(R.id.action_search);
SearchView searchView = (SearchView) MenuItemCompat.getActionView(searchItem);
searchView.setSearchableInfo(searchManager.getSearchableInfo(FriendsListActivity.super.getActivity().getComponentName()));
searchView.setIconifiedByDefault(false);
SearchView.OnQueryTextListener textChangeListener = new SearchView.OnQueryTextListener()
{
@Override
public boolean onQueryTextChange(String newText)
{
// this is your adapter that will be filtered
customFriendListAdapter.getFilter().filter(newText);
System.out.println("on text chnge text: "+newText);
return true;
}
@Override
public boolean onQueryTextSubmit(String query)
{
// this is your adapter that will be filtered
customFriendListAdapter.getFilter().filter(query);
System.out.println("on query submit: "+query);
return true;
}
};
searchView.setOnQueryTextListener(textChangeListener);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
super.onOptionsItemSelected(item);
switch (item.getItemId()) {
case R.id.done:
try {
JSONObject jsonObj = new JSONObject();
jsonObj.put("action", "moveContact");
jsonObj.put("userid", MyData.getMyDataInstance().getString(MyData.USERID));
JSONArray mobileListArray = new JSONArray(modifiedContactList);
jsonObj.put("modifiedList", mobileListArray);
socket.sendMessage(jsonObj);
modifiedContactList.clear();
} catch (Exception e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
break;
}
return super.onOptionsItemSelected(item);
}
}
here is my menu.xml file
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item
android:id="@+id/done"
android:icon="@drawable/ic_action_accept"
app:showAsAction="always"
android:title="@string/upload"/>
<item
android:id="@+id/action_search"
app:actionViewClass="android.support.v7.widget.SearchView"
android:icon="@drawable/ic_launcher"
app:showAsAction="always|collapseActionView"
android:maxWidth="100dp"
android:title="Search"/>
</menu>
here is log snippet:
07-23 15:18:59.015 1841-1841/com.woohoo E/AndroidRuntime? FATAL EXCEPTION: main
Process: com.woohoo, PID: 1841
java.lang.NullPointerException
at com.woohoo.FriendsListActivity.onCreateOptionsMenu(FriendsListActivity.java:797)
at android.support.v4.app.Fragment.performCreateOptionsMenu(Fragment.java:1871)
at android.support.v4.app.FragmentManagerImpl.dispatchCreateOptionsMenu(FragmentManager.java:2001)
at android.support.v4.app.FragmentActivity.onCreatePanelMenu(FragmentActivity.java:278)
at com.android.internal.policy.impl.PhoneWindow.preparePanel(PhoneWindow.java:436)
at com.android.internal.policy.impl.PhoneWindow.doInvalidatePanelMenu(PhoneWindow.java:800)
at com.android.internal.policy.impl.PhoneWindow$1.run(PhoneWindow.java:221)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
at android.view.Choreographer.doCallbacks(Choreographer.java:574)
at android.view.Choreographer.doFrame(Choreographer.java:543)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:747)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5001)
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:785)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
at dalvik.system.NativeStart.main(Native Method)
surprisingly it is working fine in Eclipse but giving nullpointerexception in Android Studio.
I already have tried with same configuration like below links: Android - NullPointerException on SearchView in Action Bar
The problem is in your fragment. According to this line:
at com.woohoo.FriendsListActivity.onCreateOptionsMenu(FriendsListActivity.java:797)
NullPointerException is in your FriendsListActivity, specifically in the onCreateOptionsMenu, line 797
I looked through your onCreateOptionsMenu and there might be couple of things calling NullPointerException. It would be much easier for you to find line 797 (check this or this if you don't know how to turn line numbers in your IDE)
Also it is not a good idea to call your fragment FriendsListActivity. Rename it to FriendsListFragment for instance to avoid confusion.
这篇关于Android-片段中SearchView上的NullPointerException的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!