Android Can't change imageview [duplicate] - java

This question already has answers here:
CalledFromWrongThreadException: Only the original thread that created a view hierarchy can touch views
(6 answers)
Closed 5 years ago.
I have code that gets an image by its name from drawables, but for some reason it can't update it.
package com.infonuascape.osrshelper.fragments;
import android.content.Context;
import android.content.SharedPreferences;
import android.graphics.drawable.Drawable;
import android.media.Image;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.os.Looper;
import android.support.annotation.Nullable;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.ListAdapter;
import android.widget.ListView;
import android.widget.SimpleAdapter;
import android.widget.TextView;
import android.widget.Toast;
import com.android.volley.toolbox.ImageLoader;
import com.infonuascape.osrshelper.R;
import com.infonuascape.osrshelper.activities.MainActivity;
import com.infonuascape.osrshelper.models.Account;
import org.json.JSONException;
import org.json.JSONObject;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
public class BankViewFragment extends OSRSFragment {
private static final String TAG = "BankViewFragment";
private static Account account;
private ListView lv;
private ImageView iv;
Handler handler;
ArrayList<HashMap<String, String>> ItemList;
public static BankViewFragment newInstance(final Account account) {
BankViewFragment fragment = new BankViewFragment();
Bundle b = new Bundle();
fragment.setArguments(b);
return fragment;
}
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
View view = inflater.inflate(R.layout.bank_view, null);
ItemList = new ArrayList<>();
new GetItems().execute();
lv = (ListView) view.findViewById(R.id.list);
handler = new Handler(Looper.getMainLooper());
SharedPreferences sharedPref = getActivity().getPreferences(Context.MODE_PRIVATE);
String nikas = sharedPref.getString("bankname", "null");
return view;
}
public static int getResId(String resourceName, Class<?> c) {
try {
Field idField = c.getDeclaredField(resourceName);
return idField.getInt(idField);
} catch (Exception e) {
throw new RuntimeException("No resource ID found for: "
+ resourceName + " / " + c, e);
}
}
private class GetItems extends AsyncTask<Void, Void, Void> {
#Override
protected void onPreExecute() {
super.onPreExecute();
}
#Override
protected Void doInBackground(Void... arg0) {
HttpHandler sh = new HttpHandler();
SharedPreferences sharedpreferences = getContext().getSharedPreferences("minescape", Context.MODE_PRIVATE);
String nikas = sharedpreferences.getString("bankname", "null");
String url = "https://api.minesca.pe/game/classic/stats?username=" + nikas;
String jsonStr = sh.makeServiceCall(url);
Log.e(TAG, "NIKAS: " + nikas);
Log.e(TAG, "ACCOUNT: " + account);
Log.e(TAG, "Response from url: " + jsonStr);
if (jsonStr != null) {
try {
JSONObject jsonObj = new JSONObject(jsonStr);
JSONObject items = jsonObj.getJSONObject("bank");
Iterator keys = items.keys();
while(keys.hasNext()) {
String dynamicKey = (String)keys.next();
JSONObject line = items.getJSONObject(dynamicKey);
String item = line.getString("item");
//Integer image = getResId(item, Drawable.class);
final Integer image = getResources().getIdentifier(item, "drawable", getActivity().getPackageName());
String amount = line.getString("amount");
Log.e(TAG, "DAIKTAS: " + item);
Log.e(TAG, "KIEKIS: " + amount);
HashMap<String, String> contact = new HashMap<>();
String itembank = item.replaceAll("i_", "");
String itembanks = itembank.replaceAll("_", " ");
contact.put("name", itembanks);
contact.put("email", amount);
LayoutInflater inflater = LayoutInflater.from(getContext());
View view = inflater.inflate(R.layout.bank_view, null);
lv = (ListView) view.findViewById(R.id.list);
// iv = (ImageView) view.findViewById(R.id.logo);
final ImageView ims = (ImageView) lv.findViewById(R.id.logo);
handler.post(new Runnable() {
public void run() {
if(image != null) {
Log.e(TAG, "kas cia jam netinka?: " + image);
if(image == 0) {
ims.setImageResource(R.drawable.i_noted);
Log.e(TAG, "kas cia jam netinka?: " + image);
} else {
Log.e(TAG, "kas cia jam netinka?: " + image);
ims.setImageResource(image);
}
} else {
Log.e(TAG, "null?: " + image);
}
}
});
ItemList.add(contact);
}
} catch (final JSONException e) {
Log.e(TAG, "Json parsing error: " + e.getMessage());
new Runnable() {
#Override
public void run() {
Toast.makeText(getContext(),
"Json parsing error: " + e.getMessage(),
Toast.LENGTH_LONG).show();
}
};
}
} else {
Log.e(TAG, "Couldn't get json from server.");
new Runnable() {
#Override
public void run() {
Toast.makeText(getContext(),
"Couldn't get json from server!",
Toast.LENGTH_LONG).show();
}
};
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
ListAdapter adapter = new SimpleAdapter(getContext(), ItemList,
R.layout.list_item, new String[]{ "email","name"},
new int[]{R.id.email, R.id.name});
lv.setAdapter(adapter);
}
}
}
Error:
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.infonuascape.osrshelper, PID: 31024
java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.ImageView.setImageResource(int)' on a null object reference
at com.infonuascape.osrshelper.fragments.BankViewFragment$GetItems$1.run(BankViewFragment.java:128)
at android.os.Handler.handleCallback(Handler.java:815)
at android.os.Handler.dispatchMessage(Handler.java:104)
at android.os.Looper.loop(Looper.java:194)
at android.app.ActivityThread.main(ActivityThread.java:5637)
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:959)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:754)
The problem is that there's a lot of items, and most of them have the resources, but some don't and i would like to just skip those who don't have, but the main problem is that the app crashes while trying to see the bank.

You can't change Views in a non UI thread.
So in order to fix your problem just access UI related stuff in the UI thread, e.g. in onPostExecute()

Do not do this : View should not be touched in another thread except UI thread.
#Override
protected void onPostExecute(Void result) {
-->>>>> DONOT DO THIS --->>>>>lv.setAdapter(adapter);
}

Related

NullPointerException in adapter holding viewholders

ElementAdapter class
package com.example.sierendeelementeninbreda;
import android.content.Context;
import android.view.ViewGroup;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.squareup.picasso.Picasso;
import java.util.ArrayList;
import java.util.List;
public class ElementAdapter extends RecyclerView.Adapter<ElementAdapter.ViewHolder> {
private static final String TAG = ElementAdapter.class.getSimpleName();
private List<Element> mElements = new ArrayList<>();
private final ElementOnClickHandler mElementClickHandler;
public ElementAdapter(List<Element> mElements, ElementOnClickHandler mElementClickHandler) {
this.mElements = mElements;
this.mElementClickHandler = mElementClickHandler;
}
#NonNull
#Override
public ElementAdapter.ViewHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) {
Log.v(TAG, "++++++++ onCreateViewHolder - viewGroup-class: " + viewGroup.getClass().getSimpleName());
Log.v(TAG, "++++++++ onCreateViewHolder - viewGroup-resourceName: " + viewGroup.getContext().getResources().getResourceName(viewGroup.getId()));
Log.v(TAG, "++++++++ onCreateViewHolder - viewGroup-resourceEntryName: " + viewGroup.getContext().getResources().getResourceEntryName(viewGroup.getId()));
Context context = viewGroup.getContext();
LayoutInflater inflator = LayoutInflater.from(context);
// create a new view
View elementListItem = inflator.inflate(R.layout.element_item, viewGroup, false);
ElementAdapter.ViewHolder viewHolder = new ViewHolder(elementListItem);
return viewHolder;
}
#Override
public void onBindViewHolder(ViewHolder holder, int position) {
Log.v(TAG, "++++ onBindViewHolder-type: " + holder.getClass().getSimpleName());
holder.title.setText(mElements.get(position).getTitle());
holder.geographicalLocation.setText(mElements.get(position).getGeographicalLocation());
holder.identificationNumber.setText(mElements.get(position).getIdentificationNumber());
Picasso.get()
.load(mElements.get(position).getImage())
.into(holder.image);
}
#Override
public int getItemCount() {
return mElements.size();
}
public class ViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
//one drinkItem has 3 views
// Provide a reference to each view in the drinkItem
private ImageView image;
private TextView title;
private TextView geographicalLocation;
private TextView identificationNumber;
public ViewHolder(View listItemView) {
super(listItemView);
title = (TextView) listItemView.findViewById(R.id.element_item_name);
geographicalLocation = (TextView) listItemView.findViewById(R.id.element_Location);
identificationNumber = (TextView) listItemView.findViewById(R.id.element_idNumber);
image = (ImageView) listItemView.findViewById(R.id.element_item_imageview);
// image.setOnClickListener(this);
// name.setOnClickListener(this);
// description.setOnClickListener(this);
// listItemView.setOnClickListener(this);
}
#Override
public void onClick(View view) {
int itemIndex = getAdapterPosition();
mElementClickHandler.onElementClick(view, itemIndex);
}
}
}
NetworkUtils class
package com.example.sierendeelementeninbreda;
import android.os.AsyncTask;
import android.util.Log;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.io.IOException;
import java.io.InputStream;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.Scanner;
public class NetworkUtils extends AsyncTask<String, Void, String> {
private static final String TAG = NetworkUtils.class.getSimpleName();
private OnElementApiListener listener;
private final static String url = "https://services7.arcgis.com/21GdwfcLrnTpiju8/arcgis/rest/services/Sierende_elementen/FeatureServer/0/query?where=1%3D1&outFields=*&outSR=4326&f=json";
public NetworkUtils(OnElementApiListener listener) {
this.listener = listener;
}
#Override
protected String doInBackground(String... input) {
//De methode begint met een log zodat je kunt zien wat er gebeurt in de run.
Log.d(TAG, "doInBackground was called");
String response = null;
HttpURLConnection httpURLConnection = null;
// ToDo: Url maken op basis van internet adres
try {
URL mUrl = new URL(url);
URLConnection mConnection = mUrl.openConnection();
httpURLConnection = (HttpURLConnection) mConnection;
httpURLConnection.setRequestMethod("GET");
httpURLConnection.setRequestProperty("Content-Type", "application/json");
httpURLConnection.connect();
int responseCode = httpURLConnection.getResponseCode();
if(responseCode != HttpURLConnection.HTTP_OK){
Log.e(TAG, "Aanroep naar de server is mislukt!");
} else {
InputStream in = httpURLConnection.getInputStream();
Scanner scanner = new Scanner(in);
scanner.useDelimiter("\\A");
boolean hasInput = scanner.hasNext();
if (hasInput) {
response = scanner.next();
}
}
Log.d(TAG, response);
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
if(httpURLConnection != null)
httpURLConnection.disconnect();
}
return response;
}
#Override
protected void onPreExecute() {
super.onPreExecute();
Log.d(TAG, "onPreExecute: ");
}
#Override
protected void onPostExecute(String response) {
super.onPostExecute(response);
Log.i(TAG, "createElementFromJson called");
ArrayList<Element> elements = new ArrayList<>();
if (response == null || response.equals("")) {
Log.e(TAG, "onPostExecute: empty response!");
return;
}
try {
JSONObject jsonResults = new JSONObject(response);
JSONArray elementList = jsonResults.getJSONArray("features");
Log.d(TAG, "onPostExecute: " + jsonResults);
Log.i(TAG, "elementArray length = " + elementList.length());
for(int i = 0; i < elementList.length(); i++) {
JSONObject element = elementList.getJSONObject(i);
//all info
JSONObject elementAttributes = element.getJSONObject("attributes");
String image = elementAttributes.getString("URL");
String title = elementAttributes.getString("AANDUIDINGOBJECT");
String geographicalLocation = elementAttributes.getString("GEOGRAFISCHELIGGING");
String identificationNumber = elementAttributes.getString("IDENTIFICATIE");
Element element_item = new Element(title, geographicalLocation, identificationNumber);
element_item.setImage(image);
elements.add(element_item);
Log.i(TAG, String.valueOf(elements.size()));
}
listener.onElementAvailable(elements);
} catch (JSONException e) {
e.printStackTrace();
}
}
public interface OnElementApiListener {
void onElementAvailable(ArrayList<Element> elements);
}
MainActivity class
package com.example.sierendeelementeninbreda;
import androidx.appcompat.app.AppCompatActivity;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import android.content.Context;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.Toast;
import java.util.ArrayList;
public class MainActivity extends AppCompatActivity
implements View.OnClickListener,NetworkUtils.OnElementApiListener,
ElementOnClickHandler{
private static String TAG = MainActivity.class.getName();
private final static String url = "https://services7.arcgis.com/21GdwfcLrnTpiju8/arcgis/rest/services/Sierende_elementen/FeatureServer/0/query?where=1=1&outFields=&outSR=4326&f=json";
private ArrayList<Element> mElementList;
private RecyclerView elementRecyclerView;
private ElementAdapter mElementAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
elementRecyclerView= findViewById(R.id.recyclerView_element_list);
elementRecyclerView.setLayoutManager(new LinearLayoutManager(this));
mElementAdapter = new ElementAdapter(mElementList,this);
elementRecyclerView.setAdapter(mElementAdapter);
// Start background task
NetworkUtils networkingTask = new NetworkUtils(this);
networkingTask.execute(url);
}
#Override
public void onElementAvailable(ArrayList<Element> elements) {
Log.i(TAG, "elements = " + elements.size());
this.mElementList = new ArrayList<>();
mElementList.clear();
mElementList.addAll(elements);
mElementAdapter.notifyDataSetChanged();
Log.i(TAG, "new elements = " + mElementList.size());
}
#Override
public void onElementClick(View view, int itemIndex) {
Log.v(TAG, "clicked on " + view.getClass().getSimpleName());
int viewId = view.getId();
Context context = this;
String toastMessage = "";
// if (viewId == R.id.product_imageview) {
// toastMessage = "clicked on image of drink item";
// } else if (viewId == R.id.product_item_name || viewId == R.id.product_item_description) {
// toastMessage = "clicked on name or description of drink item";
// } else if (viewId == R.id.product_list_item) {
// toastMessage = "clicked on drink list-item nr: " + itemIndex;
// }
Toast.makeText(context, toastMessage, Toast.LENGTH_LONG)
.show();
}
#Override
public void onClick(View v) {
}
}
Error
D/NetworkUtils: onPreExecute:
D/NetworkUtils: doInBackground was called
D/HostConnection: HostConnection::get() New Host Connection established 0xd4a13c30, tid 27630
D/HostConnection: HostComposition ext ANDROID_EMU_CHECKSUM_HELPER_v1 ANDROID_EMU_native_sync_v2 ANDROID_EMU_native_sync_v3 ANDROID_EMU_native_sync_v4 ANDROID_EMU_dma_v1 ANDROID_EMU_direct_mem ANDROID_EMU_host_composition_v1 ANDROID_EMU_host_composition_v2 ANDROID_EMU_YUV420_888_to_NV21 ANDROID_EMU_YUV_Cache ANDROID_EMU_async_unmap_buffer GL_OES_EGL_image_external_essl3 GL_OES_vertex_array_object GL_KHR_texture_compression_astc_ldr ANDROID_EMU_gles_max_version_3_0
D/AndroidRuntime: Shutting down VM
E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.sierendeelementeninbreda, PID: 27595
java.lang.NullPointerException: Attempt to invoke interface method 'int java.util.List.size()' on a null object reference
at com.example.sierendeelementeninbreda.ElementAdapter.getItemCount(ElementAdapter.java:64)
at androidx.recyclerview.widget.RecyclerView.dispatchLayoutStep1(RecyclerView.java:4044)
at androidx.recyclerview.widget.RecyclerView.dispatchLayout(RecyclerView.java:3849)
at androidx.recyclerview.widget.RecyclerView.onLayout(RecyclerView.java:4404)
at android.view.View.layout(View.java:21912)
at android.view.ViewGroup.layout(ViewGroup.java:6260)
That is the error I get when I run the app, I have tried solving this by looking things up but it is not working. The NullPointerException happens in line 64 of my adapter class. The app basically uses an API to get data from a site and then showcases it in a recylerView.
your not init mElementList before passed to adapter so when adapter call size method
will throw null pointer
edit your code here
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
elementRecyclerView= findViewById(R.id.recyclerView_element_list);
elementRecyclerView.setLayoutManager(new LinearLayoutManager(this));
// init mElementList here
mElementList = new ArrayList<>();
mElementAdapter = new ElementAdapter(mElementList,this);
elementRecyclerView.setAdapter(mElementAdapter);
// Start background task
NetworkUtils networkingTask = new NetworkUtils(this);
networkingTask.execute(url);
}
It is always better to do null check
#Override
public int getItemCount() {
if(mElements!=null)
return mElements.size();
else return 0
}
and initialize mElements in constructor

identify incoming caller android and display in toast

I'm trying to build a simple phonebook application where I can perform a search and an API will return the information. So far this is the part that I've got working.
I also want incoming caller to be identified with the same API, that would require the incoming number from Broastcastreceiver to be put into the API query and the returned information should be displayed in a toast. This is the part I'm having problems with.
So far this is what I have. Apologize if its really messy, this is what I've been playing around with recently and made small adjustments. Also its alot of copy-paste, I'm a beginner at java/Android and trying to learn.
HttpHandler.java
package se.xx.api_test;
import android.util.Log;
import java.io.BufferedInputStream;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.ProtocolException;
import java.net.URL;
public class HttpHandler extends PhoneCallReceiver {
private static final String TAG = HttpHandler.class.getSimpleName();
public HttpHandler() {
}
public String makeServiceCall(String reqUrl) {
String response = null;
try {
URL url = new URL(reqUrl);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
// read the response
InputStream in = new BufferedInputStream(conn.getInputStream());
response = convertStreamToString(in);
} catch (MalformedURLException e) {
Log.e(TAG, "MalformedURLException: " + e.getMessage());
} catch (ProtocolException e) {
Log.e(TAG, "ProtocolException: " + e.getMessage());
} catch (IOException e) {
Log.e(TAG, "IOException: " + e.getMessage());
} catch (Exception e) {
Log.e(TAG, "Exception: " + e.getMessage());
}
return response;
}
private String convertStreamToString(InputStream is) {
BufferedReader reader = new BufferedReader(new InputStreamReader(is));
StringBuilder sb = new StringBuilder();
String line;
try {
while ((line = reader.readLine()) != null) {
sb.append(line).append('\n');
}
} catch (IOException e) {
e.printStackTrace();
} finally {
try {
is.close();
} catch (IOException e) {
e.printStackTrace();
}
}
return sb.toString();
}
}
PhoneCallReceiver.java
package se.xx.api_test;
import java.util.Date;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.TelephonyManager;
import org.json.JSONArray;
import org.json.JSONObject;
import org.json.JSONException;
import android.util.Log;
public class PhoneCallReceiver extends BroadcastReceiver {
//The receiver will be recreated whenever android feels like it. We need a static variable to remember data between instantiations
private static int lastState = TelephonyManager.CALL_STATE_IDLE;
private static Date callStartTime;
private static boolean isIncoming;
public static String savedNumber; //because the passed incoming is only valid in ringing
#Override
public void onReceive(Context context, Intent intent) {
//We listen to two intents. The new outgoing call only tells us of an outgoing call. We use it to get the number.
if (intent.getAction().equals("android.intent.action.NEW_OUTGOING_CALL")) {
savedNumber = intent.getExtras().getString("android.intent.extra.PHONE_NUMBER");
}
else{
String stateStr = intent.getExtras().getString(TelephonyManager.EXTRA_STATE);
String number = intent.getExtras().getString(TelephonyManager.EXTRA_INCOMING_NUMBER);
int state = 0;
if(stateStr.equals(TelephonyManager.EXTRA_STATE_IDLE)){
state = TelephonyManager.CALL_STATE_IDLE;
}
else if(stateStr.equals(TelephonyManager.EXTRA_STATE_OFFHOOK)){
state = TelephonyManager.CALL_STATE_OFFHOOK;
}
else if(stateStr.equals(TelephonyManager.EXTRA_STATE_RINGING)){
state = TelephonyManager.CALL_STATE_RINGING;
}
onCallStateChanged(context, state, number);
}
}
//Derived classes should override these to respond to specific events of interest
protected void onIncomingCallStarted(Context ctx, String number, Date start){}
protected void onOutgoingCallStarted(Context ctx, String number, Date start){}
protected void onIncomingCallEnded(Context ctx, String number, Date start, Date end){}
protected void onOutgoingCallEnded(Context ctx, String number, Date start, Date end){}
protected void onMissedCall(Context ctx, String number, Date start){}
//Deals with actual events
//Incoming call- goes from IDLE to RINGING when it rings, to OFFHOOK when it's answered, to IDLE when its hung up
//Outgoing call- goes from IDLE to OFFHOOK when it dials out, to IDLE when hung up
public void onCallStateChanged(Context context, int state, String number) {
if(lastState == state){
//No change, debounce extras
return;
}
switch (state) {
case TelephonyManager.CALL_STATE_RINGING:
isIncoming = true;
callStartTime = new Date();
savedNumber = number;
onIncomingCallStarted(context, number, callStartTime);
break;
case TelephonyManager.CALL_STATE_OFFHOOK:
//Transition of ringing->offhook are pickups of incoming calls. Nothing done on them
if(lastState != TelephonyManager.CALL_STATE_RINGING){
isIncoming = false;
callStartTime = new Date();
onOutgoingCallStarted(context, savedNumber, callStartTime);
}
break;
case TelephonyManager.CALL_STATE_IDLE:
//Went to idle- this is the end of a call. What type depends on previous state(s)
if(lastState == TelephonyManager.CALL_STATE_RINGING){
//Ring but no pickup- a miss
onMissedCall(context, savedNumber, callStartTime);
}
else if(isIncoming){
onIncomingCallEnded(context, savedNumber, callStartTime, new Date());
}
else{
onOutgoingCallEnded(context, savedNumber, callStartTime, new Date());
}
break;
}
lastState = state;
}
}
MainActivity.java
package se.xx.api_test;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import android.widget.AutoCompleteTextView;
import android.widget.Button;
import android.widget.ListAdapter;
import android.widget.ListView;
import android.widget.SearchView;
import android.widget.SimpleAdapter;
import android.widget.TextView;
import android.widget.Toast;
import org.json.JSONException;
import org.json.JSONObject;
import org.json.JSONArray;
import java.util.ArrayList;
import java.util.HashMap;
import android.view.View.OnFocusChangeListener;
import android.view.inputmethod.InputMethodManager;
public class MainActivity extends AppCompatActivity {
private TextView tv;
private String TAG = MainActivity.class.getSimpleName();
private ListView lv;
ArrayList<HashMap<String, String>> contactList;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
contactList = new ArrayList<>();
lv = (ListView) findViewById(R.id.list);
tv = (TextView) findViewById(R.id.textInput);
Button queryButton = (Button) findViewById(R.id.queryButton);
queryButton.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
try {
InputMethodManager imm = (InputMethodManager)getSystemService(INPUT_METHOD_SERVICE);
imm.hideSoftInputFromWindow(getCurrentFocus().getWindowToken(), 0);
} catch (Exception e) {
// TODO: handle exception
}
contactList.clear();
new GetContacts().execute();
}
});
}
private class GetContacts extends AsyncTask<Void, Void, Void> {
#Override
protected void onPreExecute() {
super.onPreExecute();
//Toast.makeText(MainActivity.this,"Json Data is downloading",Toast.LENGTH_LONG).show();
}
#Override
protected Void doInBackground(Void... arg0) {
String id = tv.getText().toString();
HttpHandler sh = new HttpHandler();
// Making a request to url and getting response
String url = "http://10.0.2.2/api/api.php?id="+id;
String jsonStr = sh.makeServiceCall(url);
Log.e(TAG, "Response from url: " + jsonStr);
if (jsonStr != null) {
try {
JSONObject jsonObj = new JSONObject(jsonStr);
// Getting JSON Array node
JSONArray contacts = jsonObj.getJSONArray("data");
// looping through All Contacts
for (int i = 0; i < contacts.length(); i++) {
JSONObject c = contacts.getJSONObject(i);
String namn = c.getString("namn");
String avdelning = c.getString("avdelning");
//String telnr = c.getString("telnr");
//JSONObject data = jsonObj.getJSONObject("data");
//String namn = data.getString("namn");
//String avdelning = data.getString("avdelning");
//String telnr = data.getString("telnr");
// Phone node is JSON Object
JSONObject phone = c.getJSONObject("phone");
String mobil = phone.getString("mobil");
String telnr = phone.getString("telnr");
//String office = phone.getString("office");
// tmp hash map for single contact
//HashMap<String, String> contact = new HashMap<>();
HashMap<String, String> contact = new HashMap<>();
// adding each child node to HashMap key => value
contact.put("namn", namn);
contact.put("avdelning", avdelning);
contact.put("mobil", mobil);
contact.put("telnr", telnr);
//contact.put("phone", phone);
//contact.put("namn", namn);
//contact.put("avdelning", avdelning);
//contact.put("telnr", telnr);
// adding contact to contact list
contactList.add(contact);
}
} catch (final JSONException e) {
Log.e(TAG, "Json parsing error: " + e.getMessage());
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Json parsing error: " + e.getMessage(),
Toast.LENGTH_LONG).show();
}
});
}
} else {
Log.e(TAG, "Couldn't get json from server.");
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Couldn't get json from server. Check LogCat for possible errors!",
Toast.LENGTH_LONG).show();
}
});
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
ListAdapter adapter = new SimpleAdapter(MainActivity.this, contactList,
R.layout.list_item, new String[]{ "namn","avdelning","mobil", "telnr"},
new int[]{R.id.email, R.id.mobile, R.id.mobil, R.id.telnr});
lv.setAdapter(adapter);
}
}
}
CallReceiver.java (this is what I've been playing around with)
package se.xx.api_test;
import java.util.Date;
import java.util.HashMap;
import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.telephony.TelephonyManager;
import android.util.Log;
import android.widget.ListView;
import android.widget.Toast;
import android.widget.TextView;
import android.widget.RelativeLayout;
import android.view.ViewGroup;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.util.ArrayList;
import java.util.HashMap;
import android.widget.ListAdapter;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v7.app.AppCompatActivity;
import android.util.Log;
import android.view.View;
import java.lang.String;
import android.telephony.TelephonyManager;
public class CallReceiver extends PhoneCallReceiver {
#Override
public void onIncomingCallStarted(Context ctx, String number, Date start) {
final String phnr = String.valueOf(R.id.mobile);
Toast toast = Toast.makeText(ctx.getApplicationContext(), , Toast.LENGTH_SHORT);
ViewGroup group = (ViewGroup) toast.getView();
TextView messageTextView = (TextView) group.getChildAt(0);
messageTextView.setTextSize(25);
toast.show();
}
#Override
public void onOutgoingCallStarted(Context ctx, String number, Date start) {
}
#Override
protected void onIncomingCallEnded(Context ctx, String number, Date start, Date end) {
}
#Override
protected void onOutgoingCallEnded(Context ctx, String number, Date start, Date end) {
}
#Override
protected void onMissedCall(Context ctx, String number, Date start) {
}
private class APICall extends MainActivity {
String number = getIntent().getStringExtra(TelephonyManager.EXTRA_INCOMING_NUMBER);
protected Void doInBackground(Void... arg0) {
String TAG = MainActivity.class.getSimpleName();
HttpHandler sh = new HttpHandler();
// Making a request to url and getting response
String url = "http://10.0.2.2/api/api.php?id="+number;
String jsonStr = sh.makeServiceCall(url);
Log.e(TAG, "Response from url: " + jsonStr);
if (jsonStr != null) {
try {
JSONObject jsonObj = new JSONObject(jsonStr);
// Getting JSON Array node
JSONArray contacts = jsonObj.getJSONArray("data");
// looping through All Contacts
for (int i = 0; i < contacts.length(); i++) {
JSONObject c = contacts.getJSONObject(i);
final String namn = c.getString("namn");
String avdelning = c.getString("avdelning");
//String telnr = c.getString("telnr");
//JSONObject data = jsonObj.getJSONObject("data");
//String namn = data.getString("namn");
//String avdelning = data.getString("avdelning");
//String telnr = data.getString("telnr");
// Phone node is JSON Object
JSONObject phone = c.getJSONObject("phone");
String mobil = phone.getString("mobil");
String telnr = phone.getString("telnr");
//String office = phone.getString("office");
// tmp hash map for single contact
//HashMap<String, String> contact = new HashMap<>();
HashMap<String, String> contact = new HashMap<>();
// adding each child node to HashMap key => value
contact.put("namn", namn);
contact.put("avdelning", avdelning);
contact.put("mobil", mobil);
contact.put("telnr", telnr);
//contact.put("phone", phone);
//contact.put("namn", namn);
//contact.put("avdelning", avdelning);
//contact.put("telnr", telnr);
// adding contact to contact list
contactList.add(contact);
}
} catch (final JSONException e) {
Log.e(TAG, "Json parsing error: " + e.getMessage());
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Json parsing error: " + e.getMessage(),
Toast.LENGTH_LONG).show();
}
});
}
} else {
Log.e(TAG, "Couldn't get json from server.");
runOnUiThread(new Runnable() {
#Override
public void run() {
Toast.makeText(getApplicationContext(),
"Couldn't get json from server. Check LogCat for possible errors!",
Toast.LENGTH_LONG).show();
}
});
}
return null;
}
}
}
which part you got an error ?
with your Api ? or while receive you phone number from service ?
put your error to clarify the situation

ANDROID :Retrieving image from parse to an android activity

I have a ListView created . and when I click a single item of the ListView, I'm calling an activity to show the single item View. TextView data is parsing. but when I'm trying to call an image from parse its not loading (the image is hosted in a separate location online). if any one can please tell how to load image here ??
my file url
url = new URL("file location " + statusObject.getString("image"));
edited code
URL url = null;
try {
url = new URL("https://www.gravatar.com/avatar/db5bfe41c9d21d3a5b4e5b5f6a2d776d?s=32&d=identicon&r=PG&f=1");
} catch (MalformedURLException e1) {
e1.printStackTrace();
}
Bitmap bmp = null;
try {
bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream());
} catch (IOException e1) {
e1.printStackTrace();
}
txtv2.setImageBitmap(bmp);
////////////////
single item view
import android.content.*;
import android.net.*;
import android.os.Bundle;
import android.support.design.widget.FloatingActionButton;
import android.support.design.widget.Snackbar;
import android.support.v7.app.AppCompatActivity;
import android.support.v7.widget.Toolbar;
import android.util.*;
import android.view.View;
import android.widget.*;
import com.parse.*;
import com.parse.ParseException;
public class SingleItemView extends AppCompatActivity {
String objectId;
protected TextView txtv;
protected TextView txtv1;
protected ImageView txtv2;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_single_item_view);
txtv =(TextView)findViewById(R.id.txt123);
txtv1 =(TextView)findViewById(R.id.txt1234);
txtv2 =(ImageView)findViewById(R.id.txt12345);
Intent i =getIntent();
objectId = i.getStringExtra("objectId");
ParseQuery<ParseObject> query = ParseQuery.getQuery("_User");
query.getInBackground(objectId, new GetCallback<ParseObject>() {
public void done(ParseObject object, ParseException e) {
if (e == null) {
String username = object.getString("firstname");
txtv.setText(username);
String position = object.getString("position");
txtv1.setText(position);
String img_ = object.getString("image");
txtv2.setImageURI(Uri.parse(img_));
} else {
// something went wrong
}
}
});
}
}
fragment file
import android.content.*;
import android.os.Bundle;
import android.support.v4.app.*;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.*;
import com.parse.FindCallback;
import com.parse.ParseException;
import com.parse.ParseObject;
import com.parse.ParseQuery;
import java.util.ArrayList;
import java.util.List;
public class Individuals extends android.support.v4.app.ListFragment
implements FindCallback<ParseObject> {
private List<ParseObject> mOrganization = new ArrayList<ParseObject>();
SearchView sv;
IndividualsAdaptor adaptor;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
return inflater.inflate(R.layout.individuals, container, false);
}
#Override
public void onViewCreated(View view, Bundle b) {
super.onViewCreated(view, b);
sv = (SearchView) view.findViewById(R.id.ser1);
adaptor = new IndividualsAdaptor(getActivity(), mOrganization);
setListAdapter(adaptor);
ParseQuery.getQuery("_User").findInBackground(this);
sv.setOnQueryTextListener(new SearchView.OnQueryTextListener() {
#Override
public boolean onQueryTextSubmit(String text) {
return false;
}
#Override
public boolean onQueryTextChange(String text) {
adaptor.getFilter().filter(text);
return true;
}
});
}
#Override
public void done(List<ParseObject> scoreList, ParseException e) {
if (e == null) {
Log.d("score", "Retrieved " + scoreList.size() + " _User");
mOrganization.clear();
mOrganization.addAll(scoreList);
((IndividualsAdaptor) getListAdapter()).updateBackupList(mOrganization);
((IndividualsAdaptor) getListAdapter()).notifyDataSetChanged();
} else {
Log.d("score", "Error: " + e.getMessage());
}
}
#Override
public void onListItemClick(android.widget.ListView l, android.view.View v, int position, long id) {
super.onListItemClick(l, v, position, id);
ParseObject prs = mOrganization.get(position);
String objectId = prs.getObjectId();
Intent i = new Intent(getActivity(), SingleItemView.class);
i.putExtra("objectId", objectId);
startActivity(i);
}
}
Define <uses-permission android:name="android.permission.INTERNET" /> in Manifest.xml.
Then use Picasso or Gilde and parse images from their respective instances and pass image URL that you are querying from parsing. These libraries will parse URL and return image in the ImageView.
Other similar questions:
Load image from url
How to load an ImageView by URL in Android?
finally this code is working after editing some codes form the link in the answer . by this code you can
call images dynamically for each of the Object id.
URL url = null;
try {
url = new URL("image url" + object.getString("image"));
} catch (MalformedURLException e1) {
e1.printStackTrace();
}
Bitmap bmp = null;
try {
bmp = BitmapFactory.decodeStream(url.openConnection().getInputStream());
} catch (IOException e1) {
e1.printStackTrace();
}
txtv2.setImageBitmap(bmp);
// something went wrong

Getting json response in log.d but not inside app (code included)

I am trying to use the ProductHunt API to display a list of new posts in a ListView and further expand the list item on click.
On opening the app, the Progress bar appears but after that the app screen stays blank. I think there might be some error in my OnPostExecute method, because when I added a textview to display a string, its getting displayed but my listView is not getting displayed.
I used the standard Apache HttpClient for handling api requests.
I have 4 classes,
MainActivity.java
package com.emoji.apisoup;
/**
* Created by mdhalim on 16/05/16.
*/
import java.io.IOException;
import java.util.ArrayList;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Intent;
import android.os.AsyncTask;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.AdapterView;
import android.widget.ListView;
import org.apache.http.HttpClientConnection;
import org.apache.http.HttpResponse;
import org.apache.http.auth.AuthScope;
import org.apache.http.auth.UsernamePasswordCredentials;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.HttpClient;
import org.apache.http.client.ResponseHandler;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.BasicResponseHandler;
import org.apache.http.impl.client.DefaultHttpClient;
import org.apache.http.message.BasicHttpResponse;
import org.apache.http.protocol.HTTP;
public class MainActivity extends Activity {
private ListView lvPosts;
private ProductHuntAdapter adapterPosts;
public static final String POST_DETAIL_KEY = "posts";
private ProgressDialog pDialog;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.phunt_main);
String serverURL = "https://api.producthunt.com/v1/posts/";
ArrayList<ProductHuntList> aPosts = new ArrayList<ProductHuntList>();
adapterPosts = new ProductHuntAdapter(MainActivity.this, aPosts);
lvPosts = (ListView) findViewById(R.id.lvPosts);
lvPosts.setOnItemClickListener(new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
{
Intent i = new Intent(MainActivity.this, ProductHuntDetail.class);
i.putExtra(POST_DETAIL_KEY, adapterPosts.getItem(position));
startActivity(i);
}
}
});
new LongOperation().execute(serverURL);
}
private class LongOperation extends AsyncTask<String, Void, Void> {
private final HttpClient Content = new DefaultHttpClient();
private String Error = null;
#Override
protected void onPreExecute() {
super.onPreExecute();
// Showing progress dialog
pDialog = new ProgressDialog(MainActivity.this);
pDialog.setMessage("Please wait...");
pDialog.setCancelable(false);
pDialog.show();
}
protected Void doInBackground(String... urls){
JSONArray items = null;
try {
HttpGet httpget = new HttpGet(urls[0]);
httpget.setHeader("Accept","application/json");
httpget.setHeader("Content-Type","application/json");
httpget.setHeader("Authorization","Bearer 2587aa878d7334e3c89794a6b73ebffb59a06c23b82cd0f789d2ab72d2417739");
ResponseHandler<String> responseHandler = new BasicResponseHandler();
String jsonStr = Content.execute(httpget, responseHandler);
Log.d("Response: ", "> " + jsonStr);
JSONObject jsonObj = new JSONObject(jsonStr);
items = jsonObj.getJSONArray("posts");
// Parse json array into array of model objects
ArrayList<ProductHuntList> posts = ProductHuntList.fromJson(items);
// Load model objects into the adapter
for (ProductHuntList post : posts) {
adapterPosts.add(post);
}
} catch (JSONException e) {
e.printStackTrace();
} catch (IOException e) {
Error = e.getMessage();
cancel(true);
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
ArrayList<ProductHuntList> aPosts = new ArrayList<ProductHuntList>();
adapterPosts = new ProductHuntAdapter(MainActivity.this, aPosts);
lvPosts.setAdapter(adapterPosts);
}
}
}
ProductHuntList.java containing the JSON Data model and deserializer and a static method for parsing an array of JSON
package com.emoji.apisoup;
import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;
import java.util.ArrayList;
import java.io.Serializable;
/**
* Created by mdhalim on 18/05/16.
*/
public class ProductHuntList implements Serializable {
private static final long serialVersionUID = -8959832007991513854L;
private String name;
private String tagline;
private String screenshot_url;
private String largePosterUrl;
private String discussion_Url;
private String created_at;
private int votes_count;
public String getNames() {
return name;
}
public String getCreated_at() {
return created_at;
}
public String getScreenshot_url() {
return screenshot_url;
}
public String getDiscussion_Url() {
return discussion_Url;
}
public int getVotes_count() {
return votes_count;
}
public String getLargePosterUrl() {
return largePosterUrl;
}
public String getTagline(){
return tagline;
}
public static ProductHuntList fromJson(JSONObject jsonObject) {
ProductHuntList b = new ProductHuntList();
try {
// Deserialize json into object fields
b.name = jsonObject.getString("name");
b.created_at = jsonObject.getString("created_at");
b.tagline = jsonObject.getString("tagline");
b.screenshot_url = jsonObject.getJSONObject("screenshot_url").getString("300px");
b.largePosterUrl = jsonObject.getJSONObject("screenshot_url").getString("850px");
b.votes_count = jsonObject.getInt("votes_count");
b.discussion_Url = jsonObject.getString("discussion_url");
} catch (JSONException e) {
e.printStackTrace();
return null;
}
// Return new object
return b;
}
public static ArrayList<ProductHuntList> fromJson(JSONArray jsonArray) {
ArrayList<ProductHuntList> posts = new ArrayList<ProductHuntList>(jsonArray.length());
for (int i = 0; i < jsonArray.length(); i++) {
JSONObject productJson = null;
try {
productJson = jsonArray.getJSONObject(i);
} catch (Exception e) {
e.printStackTrace();
continue;
}
ProductHuntList post = ProductHuntList.fromJson(productJson);
if (post != null)
{
posts.add(post);
}
}
return posts;
}
}
ProductHuntAdapter.java this implements the ArrayAdapter
package com.emoji.apisoup;
/**
* Created by mdhalim on 18/05/16.
*/
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import com.squareup.picasso.Picasso;
import java.util.ArrayList;
/**
* Created by mdhalim on 18/05/16.
*/
public class ProductHuntAdapter extends ArrayAdapter<ProductHuntList> {
public ProductHuntAdapter(Context context, ArrayList<ProductHuntList> aPosts) {
super(context, 0, aPosts);
}
#Override
public View getView(int position, View convertView, ViewGroup parent) {
// Get the data item for this position
ProductHuntList posts = getItem(position);
// Check if an existing view is being reused, otherwise inflate the view
if (convertView == null) {
LayoutInflater inflater = LayoutInflater.from(getContext());
convertView = inflater.inflate(R.layout.item_product_hunt, null);
}
// Lookup view for data population
TextView name = (TextView) convertView.findViewById(R.id.name);
TextView created = (TextView) convertView.findViewById(R.id.created);
TextView tagline = (TextView) convertView.findViewById(R.id.tagline);
ImageView ivPosterImage = (ImageView) convertView.findViewById(R.id.ivPosterImage);
// Populate the data into the template view using the data object
name.setText(posts.getNames());
created.setText("Created On: " + posts.getCreated_at() + "%");
tagline.setText(posts.getTagline());
Picasso.with(getContext()).load(posts.getScreenshot_url()).into(ivPosterImage);
// Return the completed view to render on screen
return convertView;
}
}
and finally, a class implementing the activity for Item Details when a user clicks on any item on the list.
ProductHuntDetail
package com.emoji.apisoup;
/**
* Created by mdhalim on 18/05/16.
*/
import android.annotation.SuppressLint;
import android.app.Activity;
import android.os.Bundle;
import android.text.Html;
import android.widget.ImageView;
import android.widget.TextView;
import com.squareup.picasso.Picasso;
public class ProductHuntDetail extends Activity {
private ImageView ivPosterImage;
private TextView name;
private TextView discusUrl;
private TextView upvotes;
private TextView tagline;
private TextView created;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.product_hunt_detail);
// Fetch views
ivPosterImage = (ImageView) findViewById(R.id.ivPosterImage);
name = (TextView) findViewById(R.id.name);
discusUrl = (TextView) findViewById(R.id.discusUrl);
created = (TextView) findViewById(R.id.created);
upvotes = (TextView) findViewById(R.id.upvotes);
tagline = (TextView) findViewById(R.id.tagline);
// Load movie data
ProductHuntList posts = (ProductHuntList) getIntent().getSerializableExtra(MainActivity.POST_DETAIL_KEY);
loadMovie(posts);
}
// Populate the data for the movie
#SuppressLint("NewApi")
public void loadMovie(ProductHuntList posts) {
// Populate data
name.setText(posts.getNames());
upvotes.setText(Html.fromHtml("<b>Upvotes:</b> " + posts.getVotes_count() + "%"));
created.setText(posts.getCreated_at());
tagline.setText(posts.getTagline());
discusUrl.setText(Html.fromHtml("<b>Discussion Url:</b> " + posts.getDiscussion_Url()));
// R.drawable.large_movie_poster from
// http://content8.flixster.com/movie/11/15/86/11158674_pro.jpg -->
Picasso.with(this).load(posts.getLargePosterUrl()).
placeholder(R.drawable.large_movie_poster).
into(ivPosterImage);
}
}
I have been trying to debug this for hours :/
Your Async task is returning a void.
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
ArrayList<ProductHuntList> aPosts = new ArrayList<ProductHuntList>();
adapterPosts = new ProductHuntAdapter(MainActivity.this, aPosts);
lvPosts.setAdapter(adapterPosts);
}
As far as I can tell from the code, aPosts is empty.
I think your Async task should be -
AsyncTask<String, Void, ProductHuntAdapter>
and remove -
adapterPosts = new ProductHuntAdapter(MainActivity.this, aPosts);
You are creating and updating this in your doInBackground() method already.
I got it!
I didnt need to declare these lines again in my onPostExecute() method
ArrayList<ProductHuntList> aPosts = new ArrayList<ProductHuntList>();
adapterPosts = new ProductHuntAdapter(MainActivity.this, aPosts);
So bascially, my new onPostExecute() method goes like this
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
lvPosts.setAdapter(adapterPosts);
}
I had been trying to find this error for last 2 hours, it was harder since, I wasn't even getting any errors. As soon as I posted it on StackOverFlow, seems like I had a divine intervention.

why replace words to question mark in send data to server

I try send data to server but when I send Persian words it sends question marks, for example if I send "سلام" it sends "????"
How can I fix this ?
This is my FragmentForm.class :
package com.skyline.jimmy;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLDecoder;
import java.net.URLEncoder;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.util.EntityUtils;
import com.skyline.jimmy.R;
import android.app.Activity;
import android.app.ProgressDialog;
import android.content.Context;
import android.content.Intent;
import android.database.Cursor;
import android.database.sqlite.SQLiteDatabase;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.provider.Settings.Secure;
import android.support.v4.app.Fragment;
import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.EditText;
import android.widget.ImageButton;
import android.widget.RatingBar;
import android.widget.TextView;
import android.widget.Toast;
public class FragmentForm extends Fragment {
// An interface to display or dismiss of ProgressBar
public interface OnSendingRequestToServer {
public void DisplayLoding(boolean setVisibility);
}
private final String TAG = "FragmentForm";
private OnSendingRequestToServer onRequestToServer;
private Context context;
private EditText etName;
private EditText etComment;
private RatingBar ratingBar;
private ImageButton ibSubmit;
#Override
public void onAttach(Activity activity) {
super.onAttach(activity);
try {
onRequestToServer = (OnSendingRequestToServer) activity;
} catch (ClassCastException e) {
throw new ClassCastException(activity.toString() + " must implement OnConnectingToServer interface.");
}
context = activity.getApplicationContext();
Log.d(TAG, "Fragment attached to activity.");
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
View view = inflater.inflate(R.layout.fragment_form, container, false);
etName = (EditText) view.findViewById(R.id.etName);
etComment = (EditText) view.findViewById(R.id.etComment);
ratingBar = (RatingBar) view.findViewById(R.id.ratingBar);
ibSubmit = (ImageButton) view.findViewById(R.id.ibSubmit);
//TextView tvcm = (TextView) view.findViewById(R.id.tvComment);
Log.d(TAG, "Fragment created.");
return view;
}
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
ibSubmit.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
String strName = etName.getText().toString().trim();
if(strName.length() <= 0) {
Toast.makeText(context, "نام خود را وارد کنید", Toast.LENGTH_LONG).show();
return;
}
String strComment = etComment.getText().toString().trim();
if(strComment.length() <= 0) {
Toast.makeText(context, "متن جک را وارد کنید", Toast.LENGTH_LONG).show();
return;
}
int rate = (int) ratingBar.getRating();
if(rate <= 0) {
Toast.makeText(context, "امتیاز جکتان را وارد کنید", Toast.LENGTH_LONG).show();
return;
}
String deviceId = getDeviceId();
new SendFormTask(deviceId, strName, rate, strComment).execute();
}
private TextView findViewById(int tvcomment) {
// TODO Auto-generated method stub
return null;
}
});
}
private String getDeviceId() {
return Secure.getString(context.getContentResolver(), Secure.ANDROID_ID);
}
/*----------------------------------------------------------------------------
* This method is responsible for creating another thread in parallel with
* main UI thread in order to send a request to server and get data (if any).
* ---------------------------------------------------------------------------*/
public class SendFormTask extends AsyncTask<Void, Void, Boolean> {
String deviceId, name, comment;
int rate;
SendFormTask(String deviceId, String strName, int rate, String strComment) {
this.deviceId = deviceId;
this.name = strName;
this.rate = rate;
this.comment = strComment;
}
#Override
protected void onPreExecute() {
Log.d(TAG, "SendFormTask is about to start....");
onRequestToServer.DisplayLoding(true);
}
#Override
protected Boolean doInBackground(Void... params) {
boolean status = false;
HttpURLConnection urlConnection = null;
try {
//URL url = new URL(LinkManager.getFormAPI(deviceId, name, rate, comment));
//URL url = new URL(LinkManager.getFormAPI(deviceId, name, rate, comment));
String url1 = LinkManager.getFormAPI(deviceId, name, rate, comment) ;
//String stUrl = URLEncoder.encode(url1, "UTF-8");
URL url = new URL(url1);
Log.d(TAG, "Try to open: " + url.toString());
urlConnection = (HttpURLConnection) url.openConnection();
int responseCode = urlConnection.getResponseCode();
Log.d(TAG, "Response code is: " + responseCode);
if (responseCode == HttpURLConnection.HTTP_OK) {
BufferedReader in = new BufferedReader(
new InputStreamReader(urlConnection.getInputStream())
);
if (in != null) {
StringBuilder strBuilder = new StringBuilder();
// Read character by character
int ch = 0;
while ((ch = in.read()) != -1)
strBuilder.append((char) ch);
// get returned message and show it
String response = strBuilder.toString();
Log.d("Server response:", response);
if(response.equalsIgnoreCase("1"))
status = true;
}
in.close();
}
}
catch(MalformedURLException e){
e.printStackTrace();
}
catch (IOException e) {
e.printStackTrace();
}
finally {
urlConnection.disconnect();
}
return status;
}
#Override
protected void onPostExecute(Boolean result) {
Log.d(TAG, "SendFormTask finished its task.");
onRequestToServer.DisplayLoding(false);
if(result)
Toast.makeText(context, "جک شما ارسال شد, منتظر تایید آن باشید", Toast.LENGTH_LONG).show();
else
Toast.makeText(context, "جک شما ارسال شد , منتظر تایید آن باشید", Toast.LENGTH_LONG).show();
}
}
}
and my LinkManager.class :
package com.skyline.jimmy;
public class LinkManager {
private final static String API_FORM = "http://jimmy.ir/jimmy/sendjoke.php?p1=###&p2=####&p3=#####&p4=######";
private final static String API_Comment = "http://jimmy.ir/jimmy/index.php?p1=###";
public static String getFormAPI(String deviceId, String name, int rate, String comment) {
String url = API_FORM;
url = url.replaceAll("###", deviceId);
url = url.replaceAll("####", name);
url = url.replaceAll("#####", Integer.toString(rate));
url = url.replaceAll("######", comment);
return url;
}
public static String getCommentAPI(String deviceId) {
String url = API_Comment;
url = url.replaceAll("###", deviceId);
return url;
}
}
See this link for accepted characters in URL. Persian characters are not supported as get parameters in a url. You can use http post for sending the data to the server.
first make sure that you are sending right word (persian ) from android side , maybe your java code not sending text in UTF-8 , then make sure that your server, database , and table collection are utf8_persian_ci
and change this
BufferedReader in = new BufferedReader(
new InputStreamReader(urlConnection.getInputStream()));
to this:
BufferedReader in = new BufferedReader(
new InputStreamReader(urlConnection.getInputStream(), "utf-8"),8);

Categories

Resources