I develop a message application using parse.com, there is a few class my data browser in parse com.
If class type custom, i can bind data's in column to my list view. Is class type User or Installation, i can't get my datas and bind to listview. I guess there is a security rule about this. well, how can i get values for "User" and "Installation" class type?
there is my codes, what can i add this?
#Override
protected Void doInBackground(Void... params) {
// Locate the class table named "User" in Parse.com
ParseQuery<ParseObject> query = new ParseQuery<ParseObject>(
"User");
//query.orderByDescending("_created_at");
try {
ob = query.find();
} catch (ParseException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void result) {
// Locate the listview in listview_main.xml
listview = (ListView) findViewById(R.id.listview);
// Pass the results into an ArrayAdapter
adapter = new ArrayAdapter<String>(MainActivity.this,
R.layout.listview_item);
// Retrieve object "name" from Parse.com database
for (ParseObject users : ob) {
adapter.add((String) users.get("username"));
}
// Binds the Adapter to the ListView
listview.setAdapter(adapter);
// Close the progressdialog
mProgressDialog.dismiss();
// Capture button clicks on ListView items
listview.setOnItemClickListener(new OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
// Send single item click data to SingleItemView Class
Intent i = new Intent(MainActivity.this,
SingleItemView.class);
// Pass data "username" followed by the position
i.putExtra("username", ob.get(position).getString("username")
.toString());
// Open SingleItemView.java Activity
startActivity(i);
}
});
}
The User objects are private, quick google search gave me this: https://parse.com/questions/how-can-i-find-parse-users-that-are-facebook-friends-with-the-current-user
Also you can only get your own installation object.
If you only need to list the users for the purpose of, say, Highscores, you could create a Highscore object containing:
username, score
When saving a score you can add a score column to you User or Parseinstallation depending on your needs. This way a user can easily get a reference to his own highscores. Make sure it has no ACL that makes it publically unreadable.
Now you are free to query the Highscores object.
Long answer short, factor out the things you wish to query in it's own object and add a reference to the user/installation.
Or perhaps even easier, the other way around, keeping a reference to the owner in the highscore:
username, score, owner
I am pretty confident that you are allowed to get the objectId of owner, whether it is user or installation. So a query like 'find Highscores where owner.objectId.equals(myUser.objectId)' should be valid.
Here is a snippet of my application. I have an option to save settings (sharedpreferences) in a parse.com object, thus sharing profiles between devices (parse is an object that I have implemented my self as a controller for all parse centric code, just not to be confused with anything from the parse library itself):
private void create() {
cat.removeAll();
switchPrefs = new ArrayList<SwitchPreference>();
currentProfile = parse.getParseProfile().getProfile();
parse.getParseProfile().getProfiles(new FindCallback<ParseObject>() {
#Override public void done(List<ParseObject> objects,
ParseException e) {
if (e == null) {
profiles = objects;
for (ParseObject profile : profiles) {
addProfile(profile);
}
}
}
});
}
private void addProfile(ParseObject profile) {
SwitchPreference switchPref = new SwitchPreference(getActivity());
switchPref.setTitle(profile.getString(ParseObjectHelper.Profile.name));
switchPref.setOrder(switchPrefs.size());
// switchPref.setKey(String.valueOf(profiles.size()));
if (currentProfile != null
&& profile.getObjectId().equals(currentProfile.getObjectId())) {
switchPref.setChecked(true);
} else {
switchPref.setChecked(false);
}
switchPref.setOnPreferenceChangeListener(new OnProfileChanged());
cat.addPreference(switchPref);
switchPrefs.add(switchPref);
if (!profiles.contains(profile)) {
profiles.add(profile);
}
}
So for each profile found attached to the current user adds a SwitchPreference.
Here is the code for getProfiles(..):
public void getProfiles(FindCallback<ParseObject> callback) {
ParseQuery<ParseObject> query = ParseQuery
.getQuery(ParseObjectHelper.Profile.objectname);
query.whereEqualTo(ParseObjectHelper.Profile.owner, parseUser);
query.findInBackground(callback);
}
To create a new Profile I do the following:
public void createProfile(final String profilename,
final GetCallback<ParseObject> callback) {
final ParseObject newProfile = new ParseObject(
ParseObjectHelper.Profile.objectname);
newProfile.put(ParseObjectHelper.Profile.name, profilename);
// the users ParseUser object
newProfile.put(ParseObjectHelper.Profile.owner, parseUser);
Map<String, ?> preferences = PreferenceManager
.getDefaultSharedPreferences(context).getAll();
for (String key : preferences.keySet()) {
if (key.startsWith("key")) {
newProfile.put(key, preferences.get(key));
}
}
newProfile.saveEventually(new SaveCallback() {
#Override public void done(ParseException e) {
callback.done(newProfile, e);
}
});
}
Related
i have a query that retrieves a parse objects:
i tried to debug the callback function, and i found that i am getting a correct number of objects but all of their values are null.
allthough there is a value called "state" in which i am getting the values
what am i doing wrong? how do i get the values properly?
final List<Kehila> newKehilas = new ArrayList<>();
ParseQuery<ParseObject> query = ParseQuery.getQuery("Kehila");
query.findInBackground(new FindCallback<ParseObject>() {
#Override
public void done(List<ParseObject> list, ParseException e) {
if (e != null) {
Log.e("UNITE", e.toString());
} else {
for (ParseObject k : list) {
Kehila newKehila = new Kehila();
newKehila.setObjectId(k.getString("objectId"));
newKehila.setName(k.getString("name"));
newKehila.setCity(k.getString("city"));
newKehila.setNeighborhood(k.getString("neighborhood"));
newKehila.setStreet(k.getString("street"));
newKehila.setHouseNumber(k.getInt("houseNumber"));
newKehilas.add(newKehila);
}
}
}
});
return newKehilas;
I think you need to call save() or saveEventually() on your new objects.
I am trying to populate an Array from a parse.com query and I am stock in the part of getting the element from query. basically i dont know where to get the current location for exercise_object.get(location) thanks.
ParseQuery<ParseObject> query = ParseQuery.getQuery("Programs");
query.whereEqualTo("name", objname);
query.orderByAscending("name");
query.findInBackground(new FindCallback<ParseObject>() {
#Override
public void done(List<ParseObject> list, ParseException e) {
if (e == null) {
//success
String [] exercice = new String[3];
exercise_object = list;
Toast.makeText(Wko_Display.this, "Workouts", Toast.LENGTH_LONG).show();
ParseObject program_object = exercise_object.get(location);
exercice [0] = exercise_object.getString("wk0");
exercice [1] = exercise_object.getString("wk1");
exercice [2] = exercise_object.getString("wk2");
}
If I understand what you're trying to do correctly, then this should work:
#Override
public void done(List<ParseObject> list, ParseException e){
if (e == null){
for (ParseObject pObj : list){
String[] exercise = new String[3];
// assuming each ParseObject has a pointer to a Program object in the database
ParseObject programObject = pObj.getParseObject("location");
// do whatever you want with this programObject
// then do any further stuff with the current pObj in the list
exercise[0] = pObj.getString("wk0");
// ...
}
} else{
Log.e(TAG, e.getMessage());
}
}
This would be wrong if you're expecting only one object to be returned from the query though. Let me know.
I used AndroidBegin guide to populate my ListView with data from Parse.com table (http://www.androidbegin.com/tutorial/android-parse-com-simple-listview-tutorial/) and it shows an empty ListView.
// RemoteDataTask AsyncTask
private class RemoteDataTask extends AsyncTask<Void, Void, Void> {
#Override
protected void onPreExecute() {
super.onPreExecute();
// Create a progressdialog
mProgressDialog = new ProgressDialog(QuestionsList.this);
// Set progressdialog title
mProgressDialog.setTitle("Parse.com Simple ListView Tutorial");
// Set progressdialog message
mProgressDialog.setMessage("Loading...");
mProgressDialog.setIndeterminate(false);
// Show progressdialog
mProgressDialog.show();
}
#Override
protected Void doInBackground(Void... params) {
// Locate the class table named "Country" in Parse.com
if (AnswerActivity.friend.isEmpty()) {
if (AnswerActivity.wantedTop == AnswerActivity.all) {
// Locate the class table named "Info" in Parse.com
ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("Info");
// Locate the column named "Views" in Parse.com and order list by ascending
query.orderByDescending("Views");
try {
ob = query.find();
} catch (ParseException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
} else {
// Locate the class table named "Info" in Parse.com
ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("Info");
// Search for the wanted topic
query.whereContains("User_Topic", AnswerActivity.wantedTop);
// Locate the column named "Views" in Parse.com and order list by ascending
query.orderByDescending("Views");
try {
ob = query.find();
} catch (ParseException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
}
} else {
if (AnswerActivity.wantedTop == AnswerActivity.all) {
// Locate the class table named "Info" in Parse.com
ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("Info");
// Search for the wanted topic
query.whereContains("User_Name", AnswerActivity.friend);
// Locate the column named "Views" in Parse.com and order list by ascending
query.orderByDescending("Views");
try {
ob = query.find();
} catch (ParseException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
} else {
// Locate the class table named "Info" in Parse.com
ParseQuery<ParseObject> query = new ParseQuery<ParseObject>("Info");
// Search for the wanted topic
query.whereContains("User_Topic", AnswerActivity.wantedTop);
query.whereContains("User_Name", AnswerActivity.friend);
// Locate the column named "Views" in Parse.com and order list by ascending
query.orderByDescending("Views");
try {
ob = query.find();
} catch (ParseException e) {
Log.e("Error", e.getMessage());
e.printStackTrace();
}
return null;
}
}
}
#Override
protected void onPostExecute(Void result) {
// Locate the listview in listview_main.xml
listview = (ListView) findViewById(R.id.listview);
// Pass the results into an ArrayAdapter
adapter = new ArrayAdapter<String>(QuestionsList.this,
R.layout.listview_item);
// Retrieve object "name" from Parse.com database
for (ParseObject country : ob) {
adapter.add((String) country.get("name"));
}
// Binds the Adapter to the ListView
listview.setAdapter(adapter);
// Close the progressdialog
mProgressDialog.dismiss();
// Capture button clicks on ListView items
listview.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
// Send single item click data to SingleItemView Class
Intent i = new Intent(QuestionsList.this,
SingleItemView.class);
// Pass data "name" followed by the position
i.putExtra("name", ob.get(position).getString("name")
.toString());
// Open SingleItemView.java Activity
startActivity(i);
}
});
}
}
Later, I used ParseQueryAdapter tutorial, but still, it doesn't work.
Someone knows how to do it?
make a parse query factory
ParseQueryAdapter.QueryFactory<Post> factory;
factory = new ParseQueryAdapter.QueryFactory<Post>() {
#Override
public ParseQuery<Post> create() {
ParseQuery query = new ParseQuery("YourParseObject");
return query;
}
};
make a parse query adapter
private ParseQueryAdapter<Post> adapter;
adapter = new ParseQueryAdapter<Post>(this, factory) {
#Override
public View getItemView(final Post object, View v, ViewGroup parent) {
if (v == null) {
v = View.inflate(getContext(), R.layout.post_item, null);
}
return v;
}
};
adapter.setPaginationEnabled(true);
adapter.setTextKey("title");
adapter.setImageKey("Image");
adapter.loadObjects();
ListView your_list_view = (ListView) findViewById(R.id.list);
your_list_view.setAdapter(adapter);
done, now objects are in a list
make sure that you have a sperate xml file for each parseobject, here i have it labaled as (R.id.post_item)
You really don't need an AsyncTask for that...
Just create your query, invoke findInBackGround() which will create a Async for you, and on the callback, populate your listview.
query.findInBackground(new FindCallback<ParseObject>() {
#Override
public void done(List<ParseObject> results, ParseException e) {
if (results != null && results.size() > 0) {
YourAdapter adapter = new YourAdapter(context, results);
list.setAdapter(adapter);
Alternatively, if you want to use a ParseQueryAdapter, it's even simpler:
// create your query before, but do no call findInBackground.
YourParseQueryAdapter adapter = new YourParseQueryAdapter(context, new ParseQueryAdapter.QueryFactory<ParseObject>() {
public ParseQuery<ParseObject> create() {
return query;
}
});
list.setAdapter(adapter);
Have a good read at the documentation again in case of any issues
Hope this helps!
I have a class named UserData on parse.com, containing column name as usersports which is of array type,i successfully added strings in the array, but i got stuck while fetching the array values and displaying to a list.
say: parse array type is like this,
["Cycling","Diving","Equestrian"]
I have tested using JsonArray for parsing the array values from parse but not succeed. In my code getting checkuserSportarray as null. Please help me out.
Below is my code:
private void userDetailfromParse(){
ParseQuery<ParseObject> query = ParseQuery.getQuery(Sportapp.USERDATA);
query.whereEqualTo(Sportapp.USER_GOOGLE_ID, google_id_from_preference.trim());
query.getFirstInBackground(new GetCallback<ParseObject>() {
#SuppressWarnings("unchecked")
public void done(final ParseObject login_data, ParseException e) {
if (login_data == null) {
Log.d("Data", "The getFirst request failed. in profile"+e.getCode());
}
else{
userEmail = login_data.getString(Sportapp.USER_EMAIL);
userName = login_data.getString(Sportapp.USER_NAME);
userGender = login_data.getString(Sportapp.USER_GENDER);
checkuserSportarray = login_data.getJSONArray(Sportapp.USERDATA);
}
}
});
}
works fine for me:
List<String> list11 = new ArrayList<String>();
ParseQuery<ParseObject> pQuery = ParseQuery.getQuery("UserData");
pQuery.whereEqualTo(Sportapp.USER_GOOGLE_ID, google_id_from_preference.trim());
pQuery.findInBackground(new FindCallback<ParseObject>() {
#Override
public void done(List<ParseObject> list, ParseException e) {
if (e==null) {
if (list.size()>0) {
ParseObject p = list.get(0);
if (p.getList("usersports")!=null) {
list11 = p.getList("usersports");
}
else
{
list11= null;
}
}}
}
});
use getList method to get the data from array column of parse table
now if you want to get all individual data of parsed array ,you can simply apply looping on **list11**.
For more info see this link: Parse Object
pass your column name in getJSONArray method like this:-
checkuserSportarray = login_data.getJSONArray("usersports");
I have a json feed from this URL which contains 20 fields and I parse all the datas..but again I need to load more data from the json feed after showing the 20 fields in listview.
I have created a AsyncTask and loaded the json in listview. this is my class
public void onCreate(Bundle savedInstanceState) {
new DoInBackgrd().execute();
}
private class DoInBackgrd extends AsyncTask<Void, Void, Void> implements
DialogInterface.OnCancelListener {
private ProgressDialog processDialog;
#Override
protected void onPreExecute() {
processDialog = ProgressDialog.show(List.this, "",
getString(R.string.loading), true);
processDialog.setCancelable(true);
}
public void onCancel(DialogInterface arg0) {
// TODO Auto-generated method stub
if (processDialog.isShowing()) {
processDialog.dismiss();
}
}
#Override
protected Void doInBackground(Void... arg0) {
// TODO Auto-generated method stub
Jsonfunctions jParser = new Jsonfunctions();
JSONObject json = jParser.getJSONFromUrl(url);
try {
// Getting Array of Contacts
results = json.getJSONArray(TAG_RESULTS);
// looping through All Contacts
for (int i = 0; i < results.length(); i++) {
JSONObject c = results.getJSONObject(i);
id = c.getString(TAG_ID);
name = c.getString(TAG_NAME);
adress = c.getString(TAG_ADRRESS);
latitude = c.getString(TAG_LATITUDE);
latitudeAry.add(c.getString(TAG_LATITUDE).toString());
longitude = c.getString(TAG_lONGITUDE);
latitudeAry.add(c.getString(TAG_lONGITUDE).toString());
distance = c.getString(TAG_DISTANCE);
image = c.getString(TAG_IMAGE);
phone = c.getString(TAG_TELEPHONE);
telphonenumberAry
.add(c.getString(TAG_TELEPHONE).toString());
NameAry.add(c.getString(TAG_NAME).toString());
resourceAry.add(new ResourceClass(point, id, name, adress,
distance, latitude, longitude, phone));
}
} catch (JSONException e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(Void unused) {
if (processDialog.isShowing()) {
processDialog.dismiss();
}
listView.setAdapter(new ASyncAdapter());
listView.setDividerHeight(2);
listView.setOnItemClickListener(new OnItemClickListener() {
public void onItemClick(AdapterView<?> arg0, View arg1,
int position, long id) {
Intent details = new Intent(List.this, Details.class);
details.putExtra("position", position + 1);
details.putExtra("name", resourceAry.get(position)
.getName());
details.putExtra("adress", resourceAry.get(position)
.getAdress());
details.putExtra("phone", resourceAry.get(position)
.getTelephone());
details.putExtra("latitudes", latitude);
details.putExtra("longitudes", longitude);
startActivity(details);
}
});
}
}
Thanks in advance
I had just finished working on similar kind of requirement(issue faced on is specified in)
Hence I'm hoping to provide you proper solution that is helpful to you and saves ur time.
If I'm not wrong you need to populate same ListView with next 20(i.e. 21 - 40) fields obtained in response for server api.
In that case u need to call server api again and again for that u need an event. Say u add a 'Next' button and on its click u retrive next 20 fields(21 - 40).
Currently in ur code in 'DoInBackgrd', you are binding/setting Adapter(ASyncAdapter) each time you need to bind new records/fields to ListView. This is not a good practice, also it at a instance it will not refresh fields of newly assigned adapter in listView.
Hence you should :
Just retrieve/parse new fileds from JSon and set them in adapter. Adapter will notify your listView about data change and listView will refresh its view.
Considering that 'ASyncAdapter' is your custom adapter that implements ArrayAdapter, just add following(change Variable type from Restaurant to as per your requirement) method to it.
public void reSet(ArrayList<Resturant> resturantsCache) {
//This will clear your current fields/records in adpter
clear();
//This will new fields/records in adpter from provided resturantsCache ArrayList.
for (Resturant resturant : resturantsCache) {
add(resturant);
}
}
Hope you will be able to replace variable types in provided method and use it as per you requirements, In case you need more help please provide ASyncAdapter code.
Thanks.