I'm trying to improve the app performance downloading thumbnails to populate the listview and then, if the user selects an item, show a bigger resolution image.
The idea is to write the image url on the listview and pass the value to the detail activity, and manage the download there.
Using only one image the app works fine, but I don't like the result obtained by using a single image.
In the following piece of code, the added lines are preceded by a comment:
ListView showing all items with thumbnails
public class ListViewCategory extends Activity {
private static final String TAG = "ListViewCategory: ";
ListView mListView;
String strUrl;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.listview_category_layout);
// URL to the JSON data
Intent iN = getIntent();
Bundle b = iN.getExtras();
if (b!=null){
strUrl=(String)b.get("urlJSON");
}
// Creating a new non-ui thread task to download json data
DownloadTask downloadTask = new DownloadTask();
// Starting the download process
downloadTask.execute(strUrl);
// Getting a reference to ListView of activity_main
mListView = (ListView) findViewById(R.id.list);
mListView.setOnItemClickListener(new OnItemClickListener(){
public void onItemClick(AdapterView<?> parent, View view, int position, long id){
//get brand from listview
TextView marcaDetail = (TextView) view.findViewById(R.id.marcas);
String marcaToDetail = marcaDetail.getText().toString();
//get model from listview
TextView modeloDetail = (TextView) view.findViewById(R.id.modelos);
String modeloToDetail = modeloDetail.getText().toString();
//get photoUrl from listview
TextView urlDetail = (TextView) view.findViewById(R.id.tvUrl);
String urlToDetail = urlDetail.getText().toString();
//get price from listview
TextView priceDetail = (TextView) view.findViewById(R.id.precios);
String priceToDetail = priceDetail.getText().toString();
Intent iPosition = new Intent(view.getContext(),DetailViewItem.class);
iPosition.putExtra("marca", marcaToDetail);
iPosition.putExtra("photoDetail", urlToDetail);
iPosition.putExtra("modelo", modeloToDetail);
iPosition.putExtra("precio", priceToDetail);
startActivity(iPosition);
Toast.makeText(ListViewCategory.this,urlToDetail.toString() , Toast.LENGTH_LONG).show();
}
});
}
/** A method to download json data from url */
private String downloadUrl(String strUrl) throws IOException{
String data = "";
InputStream iStream = null;
try{
URL url = new URL(strUrl);
// Creating an http connection to communicate with url
HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
BufferedReader br = new BufferedReader(new InputStreamReader(iStream));
StringBuffer sb = new StringBuffer();
String line = "";
while( ( line = br.readLine()) != null){
sb.append(line);
}
data = sb.toString();
br.close();
}catch(Exception e){
Log.d("Exception while downloading url", e.toString());
}finally{
iStream.close();
}
return data;
}
/** AsyncTask to download json data */
private class DownloadTask extends AsyncTask<String, Integer, String>{
String data = null;
#Override
protected String doInBackground(String... url) {
try{
data = downloadUrl(url[0]);
}catch(Exception e){
Log.d("Background Task",e.toString());
}
return data;
}
#Override
protected void onPostExecute(String result) {
// The parsing of the xml data is done in a non-ui thread
ListViewLoaderTask listViewLoaderTask = new ListViewLoaderTask();
// Start parsing xml data
listViewLoaderTask.execute(result);
}
}
/** AsyncTask to parse json data and load ListView */
private class ListViewLoaderTask extends AsyncTask<String, Void, SimpleAdapter>{
JSONObject jObject;
// Doing the parsing of xml data in a non-ui thread
#Override
protected SimpleAdapter doInBackground(String... strJson) {
try{
jObject = new JSONObject(strJson[0]);
JSONParser jsonParser = new JSONParser();
jsonParser.parse(jObject);
}catch(Exception e){
Log.d("JSON Exception1",e.toString());
}
// Instantiating json parser class
JSONParser jsonParser = new JSONParser();
// A list object to store the parsed items list
List<HashMap<String, Object>> brands = null;
try{
// Getting the parsed data as a List construct
brands = jsonParser.parse(jObject);
}catch(Exception e){
Log.d("Exception",e.toString());
}
// Keys used in Hashmap
//added
String[] from = { "foto","marca","modelo","precio","detail"};
// Ids of views in list_v layout
int[] to = { R.id.fotos,R.id.marcas,R.id.modelos,R.id.precios,R.id.tvUrl};
// Instantiating an adapter to store each items
// R.layout.list_v defines the layout of each item
SimpleAdapter adapter = new SimpleAdapter(getBaseContext(), brands, R.layout.list_v, from, to);
return adapter;
}
/** Invoked by the Android on "doInBackground" is executed */
#Override
protected void onPostExecute(SimpleAdapter adapter) {
// Setting adapter for the listview
mListView.setAdapter(adapter);
for(int i=0;i<adapter.getCount();i++){
HashMap<String, Object> hm = (HashMap<String, Object>) adapter.getItem(i);
String imgUrl = (String) hm.get("photoUrl");
Log.i(TAG, imgUrl);
ImageLoaderTask imageLoaderTask = new ImageLoaderTask();
HashMap<String, Object> hmDownload = new HashMap<String, Object>();
hm.put("photoUrl",imgUrl);
hm.put("position", i);
// Starting ImageLoaderTask to download and populate image in the listview
imageLoaderTask.execute(hm);
}
}
}
/** AsyncTask to download and load an image in ListView */
private class ImageLoaderTask extends AsyncTask<HashMap<String, Object>, Void, HashMap<String, Object>>{
#Override
protected HashMap<String, Object> doInBackground(HashMap<String, Object>... hm) {
InputStream iStream=null;
String imgUrl = (String) hm[0].get("photoUrl");
int position = (Integer) hm[0].get("position");
URL url;
try {
url = new URL(imgUrl);
// Creating an http connection to communicate with url
HttpURLConnection urlConnection = (HttpURLConnection) url.openConnection();
// Connecting to url
urlConnection.connect();
// Reading data from url
iStream = urlConnection.getInputStream();
// Getting Caching directory
File cacheDirectory = getBaseContext().getCacheDir();
// Temporary file to store the downloaded image
File tmpFile = new File(cacheDirectory.getPath() + "/lakari_"+position+".png");
// The FileOutputStream to the temporary file
FileOutputStream fOutStream = new FileOutputStream(tmpFile);
// Creating a bitmap from the downloaded inputstream
Bitmap b = BitmapFactory.decodeStream(iStream);
// Writing the bitmap to the temporary file as png file
b.compress(Bitmap.CompressFormat.PNG,100, fOutStream);
// Flush the FileOutputStream
fOutStream.flush();
//Close the FileOutputStream
fOutStream.close();
// Create a hashmap object to store image path and its position in the listview
HashMap<String, Object> hmBitmap = new HashMap<String, Object>();
// Storing the path to the temporary image file
hmBitmap.put("foto",tmpFile.getPath());
// Storing the position of the image in the listview
hmBitmap.put("position",position);
// Returning the HashMap object containing the image path and position
return hmBitmap;
}catch (Exception e) {
e.printStackTrace();
}
return null;
}
#Override
protected void onPostExecute(HashMap<String, Object> result) {
// Getting the path to the downloaded image
String path = (String) result.get("foto");
// Getting the position of the downloaded image
int position = (Integer) result.get("position");
// Getting adapter of the listview
SimpleAdapter adapter = (SimpleAdapter ) mListView.getAdapter();
// Getting the hashmap object at the specified position of the listview
HashMap<String, Object> hm = (HashMap<String, Object>) adapter.getItem(position);
// Overwriting the existing path in the adapter
hm.put("foto",path);
// Noticing listview about the dataset changes
adapter.notifyDataSetChanged();
}
}
}
ListViewCategory layout:
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="#dimen/activity_vertical_margin"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
tools:context=".ListViewCategory"
android:background="#000000">
<TextView
android:id="#+id/textview"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center">
</TextView>
<ListView
android:id="#+id/list"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:divider="#e600e6"
android:dividerHeight="0.2sp"/>
</RelativeLayout>
ListView Cell:
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_weight="1"
android:orientation="vertical"
android:background="#a8a8a8" >
<ImageView
android:id="#+id/fotos"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:contentDescription="#string/description"
android:src="#drawable/ic_launcher" />
<!--
<TextView
android:id="#+id/tvUrl"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textColor="#aaaaaa"
android:textSize="6sp"/>
-->
</LinearLayout>
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight="2" >
<TextView
android:id="#+id/tvUrl"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textColor="#aaaaaa"
android:textSize="12sp"/>
<TextView
android:id="#+id/marcas"
android:textSize="14sp"
android:textColor="#aaaaaa"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="left"
/>
<TextView
android:id="#+id/modelos"
android:textSize="22sp"
android:textColor="#e600e6"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center"
/>
<TextView
android:id="#+id/precios"
android:textSize="16sp"
android:textColor="#aaaaab"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="right"
/>
</LinearLayout>
</LinearLayout>
JSON parser:
/** A class to parse json data */
public class JSONParser {
// Receives a JSONObject and returns a list
public List<HashMap<String,Object>> parse(JSONObject jObject){
JSONArray jItems = null;
try {
// Retrieves all the elements in the "items" array
jItems = jObject.getJSONArray("items");
} catch (JSONException e) {
e.printStackTrace();
}
return getItems(jItems);
}
private List<HashMap<String, Object>> getItems(JSONArray jItems){
int itemCount = jItems.length();
List<HashMap<String, Object>> itemList = new ArrayList<HashMap<String,Object>>();
HashMap<String, Object> item = null;
// Taking each item, parses and adds to list object
for(int i=0; i<itemCount;i++){
try {
// Call getItem with item JSON object to parse the item
item = getItem((JSONObject)jItems.get(i));
itemList.add(item);
} catch (JSONException e) {
e.printStackTrace();
}
}
return itemList;
}
// Parsing the JSON object
private HashMap<String, Object> getItem(JSONObject jItem){
HashMap<String, Object> item = new HashMap<String, Object>();
String marca = "";
String foto = "";
String modelo = "";
String precio = "";
//añadido
String detail = "";
try {
marca = jItem.getString("marca");
foto = jItem.getString("photoUrl");
modelo = jItem.getString("modelo");
precio = jItem.getString("precio");
//added
detail = jItem.getString("photoDetail");
item.put("marca", marca);
item.put("foto", R.drawable.ic_launcher);
item.put("modelo", modelo);
item.put("photoUrl", foto);
item.put("precio", precio);
//added
item.put("photoDetail", detail);
} catch (JSONException e) {
e.printStackTrace();
}
return item;
}
}
And finally, the detail activity where I an error, no image but the app does not crash:
public class DetailViewItem extends Activity{
//added
ImageView imageView;
private String photoCacheUri = "";
private String detailMarca = "";
private String detailModelo = "";
private String detailPrecio = "";
private String mailBody = "";
private String mailSubject = "";
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.detail_view_item_layout);
Intent intentDetail = getIntent();
Bundle bDetail = intentDetail.getExtras();
if (bDetail != null){
detailMarca = (String)bDetail.get("marca");
photoCacheUri = (String)bDetail.get("photoDetail");
detailModelo = (String)bDetail.getString("modelo");
detailPrecio = (String)bDetail.getString("precio");
}
//set brand
TextView textviewMarca = (TextView) findViewById(R.id.tvMarca);
textviewMarca.setText(detailMarca);
//set image
/*ImageView imageView = (ImageView) findViewById(R.id.photoDetail);
Bitmap bmImg = BitmapFactory.decodeFile(photoCacheUri);
imageView.setImageBitmap(bmImg);*/
//added
imageView= (ImageView) findViewById(R.id.photoDetail);
// Create an object for subclass of AsyncTask
GetXMLTask task = new GetXMLTask();
// Execute the task
task.execute(new String[] { photoCacheUri });
//set model
TextView textviewModelo = (TextView) findViewById(R.id.tvModelo);
textviewModelo.setText(detailModelo);
//set price
TextView textviewPrecio = (TextView) findViewById(R.id.tvPrecio);
textviewPrecio.setText(detailPrecio);
}
//added
private class GetXMLTask extends AsyncTask<String, Void, Bitmap> {
#Override
protected Bitmap doInBackground(String... urls) {
Bitmap map = null;
for (String url : urls) {
map = downloadImage(url);
}
return map;
}
// Sets the Bitmap returned by doInBackground
#Override
protected void onPostExecute(Bitmap result) {
imageView.setImageBitmap(result);
}
// Creates Bitmap from InputStream and returns it
private Bitmap downloadImage(String url) {
Bitmap bitmap = null;
InputStream stream = null;
BitmapFactory.Options bmOptions = new BitmapFactory.Options();
bmOptions.inSampleSize = 1;
try {
stream = getHttpConnection(url);
bitmap = BitmapFactory.
decodeStream(stream, null, bmOptions);
stream.close();
} catch (IOException e1) {
e1.printStackTrace();
}
return bitmap;
}
// Makes HttpURLConnection and returns InputStream
private InputStream getHttpConnection(String urlString)
throws IOException {
InputStream stream = null;
URL url = new URL(urlString);
URLConnection connection = url.openConnection();
try {
HttpURLConnection httpConnection = (HttpURLConnection) connection;
httpConnection.setRequestMethod("GET");
httpConnection.connect();
if (httpConnection.getResponseCode() == HttpURLConnection.HTTP_OK) {
stream = httpConnection.getInputStream();
}
} catch (Exception ex) {
ex.printStackTrace();
}
return stream;
}
}
}
LogCat:
12-03 04:33:12.256: W/System.err(2420): java.net.MalformedURLException: Protocol not found:
12-03 04:33:12.256: W/System.err(2420): at java.net.URL.<init>(URL.java:178)
12-03 04:33:12.266: W/System.err(2420): at java.net.URL.<init>(URL.java:127)
12-03 04:33:12.276: W/System.err(2420): at com.lupradoa.lakari.fragmenttabstudy.tabB.DetailViewItem$GetXMLTask.getHttpConnection(DetailViewItem.java:131)
12-03 04:33:12.276: W/System.err(2420): at com.lupradoa.lakari.fragmenttabstudy.tabB.DetailViewItem$GetXMLTask.downloadImage(DetailViewItem.java:117)
12-03 04:33:12.276: W/System.err(2420): at com.lupradoa.lakari.fragmenttabstudy.tabB.DetailViewItem$GetXMLTask.doInBackground(DetailViewItem.java:98)
12-03 04:33:12.276: W/System.err(2420): at com.lupradoa.lakari.fragmenttabstudy.tabB.DetailViewItem$GetXMLTask.doInBackground(DetailViewItem.java:1)
12-03 04:33:12.276: W/System.err(2420): at android.os.AsyncTask$2.call(AsyncTask.java:287)
12-03 04:33:12.276: W/System.err(2420): at java.util.concurrent.FutureTask.run(FutureTask.java:234)
12-03 04:33:12.326: W/System.err(2420): at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:230)
12-03 04:33:12.326: W/System.err(2420): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1080)
12-03 04:33:12.326: W/System.err(2420): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:573)
12-03 04:33:12.346: W/System.err(2420): at java.lang.Thread.run(Thread.java:841)
12-03 04:33:12.496: W/EGL_emulation(2420): eglSurfaceAttrib not implemented
I have revised the code a lot of times, but I can't find the mistake. Can any of you point it out?
Related
NetworkUtilities.java
public class NetworkUtilities {
private static final String TAG = NetworkUtilities.class.getSimpleName();
public static URL createUrl(String stringUrl){
URL url = null;
try{
url = new URL(stringUrl);
}catch (MalformedURLException e){
Log.v(TAG, "Problem building the Url");
}
return url;
}
public static String httpRequest(URL url) throws IOException{
String jsonResponse = "";
if(url ==null){
Log.v(TAG, "Url is null");
return jsonResponse;
}
HttpURLConnection httpURLConnection = null;
InputStream inputStream = null;
try{
httpURLConnection = (HttpURLConnection) url.openConnection();
httpURLConnection.setReadTimeout(10000);
httpURLConnection.setConnectTimeout(15000);
httpURLConnection.setRequestMethod("GET");
httpURLConnection.connect();
if(httpURLConnection.getResponseCode() == 200){
inputStream = httpURLConnection.getInputStream();
jsonResponse = readFromStream(inputStream);
}
else{
Log.e(TAG, "Error response code" + httpURLConnection.getResponseCode());
}
}catch (IOException e){
Log.v(TAG, "Problem retrieving the json result", e);
}finally {
if(httpURLConnection != null){
httpURLConnection.disconnect();
}
if(inputStream != null){
inputStream.close();
}
}
return jsonResponse;
}
private static String readFromStream(InputStream inputStream) throws IOException{
StringBuilder output = new StringBuilder();
if(inputStream != null){
InputStreamReader in = new InputStreamReader(inputStream, Charset.forName("UTF-8"));
BufferedReader bf = new BufferedReader(in);
String line = bf.readLine();
while(line != null){
output.append(line);
line = bf.readLine();
}
}
return output.toString();
}
public static List<String> extractFromJson(String jsonResponse){
if(TextUtils.isEmpty(jsonResponse)){
return null;
}
List<String> newsStories = new ArrayList<>();
try{
JSONObject baseObj = new JSONObject(jsonResponse);
JSONArray articlesArray = baseObj.getJSONArray("data");
for(int i=0;i<articlesArray.length();i++){
JSONObject currentArticle = articlesArray.getJSONObject(i);
JSONObject source = currentArticle.getJSONObject("source");
String sourceName = source.getString("name");
String title = currentArticle.getString("title");
String description = currentArticle.getString("description");
String newsStory = "Source" + sourceName + "/n" + title + "/n" + description;
newsStories.add(newsStory);
}
}catch (JSONException e){
Log.e(TAG, " Problem parsing the json string", e);
}
return newsStories;
}
NewsAdapter.java
public class NewsAdapter extends RecyclerView.Adapter<NewsAdapter.NewsViewHolder> {
private Context mContext;
private List<String> mNewsArticles;
NewsAdapter(Context context){
mContext = context;
}
#NonNull
#Override
public NewsViewHolder onCreateViewHolder(#NonNull ViewGroup parent, int viewType) {
View view = LayoutInflater
.from(mContext)
.inflate(R.layout.news_list_item,parent, false);
view.setFocusable(true);
return new NewsViewHolder(view);
}
#Override
public void onBindViewHolder( NewsViewHolder holder, int position) {
String currentArticle = mNewsArticles.get(position);
holder.mTextView.setText(currentArticle);
}
#Override
public int getItemCount() {
if(mNewsArticles != null){
return mNewsArticles.size();
}
return 0;
}
public class NewsViewHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
final TextView mTextView;
public NewsViewHolder(#NonNull View itemView) {
super(itemView);
mTextView = (TextView) itemView.findViewById(R.id.textView);
itemView.setOnClickListener(this);
}
#Override
public void onClick(View v) {
Toast.makeText(v.getContext(), "position :" + getLayoutPosition(), Toast.LENGTH_SHORT).show();
}
}
public void setNewsData(List<String> newsData){
mNewsArticles = newsData;
notifyDataSetChanged();
}
MainActivity.java
public class MainActivity extends AppCompatActivity {
private static final String TAG = MainActivity.class.getSimpleName();
private RecyclerView mRecyclerView;
private NewsAdapter mNewsAdapter;
private static final String BASE_URL = "https://newsapi.org/v2/top-headlines?country=us&apiKey=13f428d687714c33a24f34ad6c5***87";
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);
mRecyclerView.setLayoutManager(
new LinearLayoutManager(this,LinearLayoutManager.VERTICAL,false));
mRecyclerView.setHasFixedSize(true);
mNewsAdapter = new NewsAdapter(this);
mRecyclerView.setAdapter(mNewsAdapter);
new FetchNewsArticle().execute(BASE_URL);
}
public class FetchNewsArticle extends AsyncTask<String, Void, List<String>>{
#Override
protected List<String> doInBackground(String... strings) {
String stringUrl = strings[0];
URL url = NetworkUtilities.createUrl(stringUrl);
String json = "";
try{
json = NetworkUtilities.httpRequest(url);
List<String> articles = NetworkUtilities.extractFromJson(json);
return articles;
}catch (Exception e){
e.printStackTrace();
Log.v(TAG, "Problem retrieving data");
return null;
}
}
#Override
protected void onPostExecute(List<String> strings) {
if(strings != null){
mNewsAdapter.setNewsData(strings);
}
}
}
Error
W/Zygote: Unable to open libbeluga.so: dlopen failed: library "libbeluga.so" not found.
D/NetworkSecurityConfig: No Network Security Config specified, using platform default
D/NetworkSecurityConfig: No Network Security Config specified, using platform default
W/xample.newsfee: Accessing hidden method Landroid/view/View; >computeFitSystemWindows(Landroid/graphics/Rect;Landroid/graphics/Rect;)Z (greylist, reflection, allowed)
W/xample.newsfee: Accessing hidden method Landroid/view/ViewGroup;->makeOptionalFitsSystemWindows()V (greylist, reflection, allowed)
com.example.newsfeed V/NetworkUtilities: Problem retrieving the json result
java.io.IOException: Cleartext HTTP traffic to api.mediastack.com not permitted
at com.android.okhttp.HttpHandler$CleartextURLFilter.checkURLPermitted(HttpHandler.java:127)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.execute(HttpURLConnectionImpl.java:462)
at com.android.okhttp.internal.huc.HttpURLConnectionImpl.connect(HttpURLConnectionImpl.java:131)
at com.example.newsfeed.Utils.NetworkUtilities.httpRequest(NetworkUtilities.java:49)
at com.example.newsfeed.MainActivity$FetchNewsArticle.doInBackground(MainActivity.java:46)
at com.example.newsfeed.MainActivity$FetchNewsArticle.doInBackground(MainActivity.java:38)
at android.os.AsyncTask$3.call(AsyncTask.java:394)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at android.os.AsyncTask$SerialExecutor$1.run(AsyncTask.java:305)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1167)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:641)
at java.lang.Thread.run(Thread.java:923)
2021-03-11 22:53:28.124 9391-9391/com.example.newsfeed W/Looper: PerfMonitor looperActivity : package=com.example.newsfeed/.MainActivity time=1ms latency=447ms running=2ms procState=2 ClientTransaction{ callbacks=[android.app.servertransaction.TopResumedActivityChangeItem] } historyMsgCount=4 (msgIndex=3 wall=87ms seq=3 running=50ms runnable=28ms io=2ms late=6ms h=android.app.ActivityThread$H w=110) (msgIndex=4 wall=356ms seq=4 running=212ms runnable=80ms io=11ms late=91ms h=android.app.ActivityThread$H w=159)
2021-03-11 22:53:28.199 9391-9429/com.example.newsfeed I/AdrenoGLES-0: QUALCOMM build : 979eaa0, I11632bc865
Build Date : 11/18/20
OpenGL ES Shader Compiler Version: EV031.32.02.00
Local Branch :
Remote Branch : refs/tags/AU_LINUX_ANDROID_LA.UM.9.1.R1.11.00.00.604.067
Remote Branch : NONE
Reconstruct Branch : NOTHING
2021-03-11 22:53:28.199 9391-9429/com.example.newsfeed I/AdrenoGLES-0: Build Config : S P 10.0.6 AArch64
2021-03-11 22:53:28.199 9391-9429/com.example.newsfeed I/AdrenoGLES-0: Driver Path : /vendor/lib64/egl/libGLESv2_adreno.so
2021-03-11 22:53:28.213 9391-9429/com.example.newsfeed I/AdrenoGLES-0: PFP: 0x016ee190, ME: 0x00000000
2021-03-11 22:53:28.253 9391-9429/com.example.newsfeed E/LB: fail to open file: No such file or directory
The error seems to be: java.io.IOException: Cleartext HTTP traffic to api.mediastack.com not permitted.
Starting from Android 9, clear text http communication is disabled by default.
Check out the official Android documentation for this and also this question for further information.
I would like to work on moving the json data from libgdx to my web server, but I am not sure how to do it. The method below was created by referring to libgdx's documentation.
private void httpPostJson(){
final Json json = new Json();
final String requestJson = json.toJson(requestObject);
Net.HttpRequest request = new Net.HttpRequest("POST");
final String url = "http://localhost:8080/data";
request.setUrl(url);
request.setContent(requestJson);
request.setHeader("Content-Type", "application/json");
Gdx.net.sendHttpRequest(request, new Net.HttpResponseListener() {
#Override
public void handleHttpResponse(Net.HttpResponse httpResponse) {
String responseJson = httpResponse.getResultAsString();
Gson gson = new Gson();
data = gson.fromJson(responseJson, Person.class);
//'Person' is just sample class. data is class Person's object.
data.StoreData("",1);//successed to receive json data from web server.
//StoreData is just getter method.
}
#Override
public void failed(Throwable t) {
Gdx.app.log("failed!");
}
#Override
public void cancelled() {
Gdx.app.log("cancelled!");
}
});
}
It is possible to receive data transmitted from a web server.
But, this method can't send data to web server.
Can you tell me how to move data from libgdx project to web server?
This is the data transmitted to the web server:
final String requestJson = json.toJson(requestObject);
We are using the following Code (as you have more control over the request as opposed to using gdx.net), works like a charm, just don't execute on the main thread - body is your JSON as String
URL url = new URL(<your url>);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("POST");
conn.setDoInput(true);
conn.setDoOutput(true);
conn.setRequestProperty("Accept", "application/json");
conn.setRequestProperty("Content-Type",
"application/json; charset=utf-8");
if (body != null) {
OutputStream os = conn.getOutputStream();
BufferedWriter writer = new BufferedWriter(new OutputStreamWriter(
os, "UTF-8"));
writer.write(body);
writer.close();
os.close();
}
conn.connect();
String s = stringFromStream(conn.getInputStream(), 4096);
Method stringFromStream:
public static String stringFromStream(final InputStream is,
final int bufferSize) {
final char[] buffer = new char[bufferSize];
final StringBuilder out = new StringBuilder();
try {
final Reader in = new InputStreamReader(is, "UTF-8");
try {
for (; ; ) {
int rsz = in.read(buffer, 0, buffer.length);
if (rsz < 0)
break;
out.append(buffer, 0, rsz);
}
} finally {
in.close();
}
} catch (Exception ex) {
}
return out.toString();
}
I have a listview in a fragment that I am populating with information from a JSON call.
I am having an issue wetting up the listview in my fragment. My fragment only extends Fragment and I am assuming this may be where my issue is. the sample code I was working from to assist me with importing the json data was not using fragments so Im a little confused.
My error is:
java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.ListView.setAdapter(android.widget.ListAdapter)' on a null object reference
at com.peekatu.Fcc4me.watchFragment$GetContacts.onPostExecute(watchFragment.java:192)
at com.peekatu.Fcc4me.watchFragment$GetContacts.onPostExecute(watchFragment.java:119)
at android.os.AsyncTask.finish(AsyncTask.java:632)
at android.os.AsyncTask.access$600(AsyncTask.java:177)
at android.os.AsyncTask$InternalHandler.handleMessage(AsyncTask.java:645)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:135)
at android.app.ActivityThread.main(ActivityThread.java:5221)
at java.lang.reflect.Method.invoke(Native Method)
at java.lang.reflect.Method.invoke(Method.java:372)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:899)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:694)
Fragment
public class watchFragment extends Fragment {
private static final String TAG_DATA = "data";
private static final String TAG_TITLE = "title";
private static final String TAG_URL = "video_url";
private static final String TAG_IMAGE = "image";
public ListView lv;
private ProgressDialog pDialog;
// URL to get contacts JSON
private static String url = "/load.php";
// contacts JSONArray
JSONArray data = null;
// Hashmap for ListView
ArrayList<HashMap<String, String>> dataList;
private WebView web_v;
// TODO: Rename parameter arguments, choose names that match
// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER
private static final String ARG_PARAM1 = "param1";
private static final String ARG_PARAM2 = "param2";
// TODO: Rename and change types of parameters
private String mParam1;
private String mParam2;
/**
* Use this factory method to create a new instance of
* this fragment using the provided parameters.
*
* #param param1 Parameter 1.
* #param param2 Parameter 2.
* #return A new instance of fragment watchFragment.
*/
// TODO: Rename and change types and number of parameters
public static watchFragment newInstance(String param1, String param2) {
watchFragment fragment = new watchFragment();
Bundle args = new Bundle();
args.putString(ARG_PARAM1, param1);
args.putString(ARG_PARAM2, param2);
fragment.setArguments(args);
return fragment;
}
public watchFragment() {
// Required empty public constructor
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
if (getArguments() != null) {
mParam1 = getArguments().getString(ARG_PARAM1);
mParam2 = getArguments().getString(ARG_PARAM2);
}
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
View v= inflater.inflate(R.layout.fragment_watch, container, false);
//btn = (Button) v.findViewById(R.id.button1);
dataList = new ArrayList<HashMap<String, String>>();
ListView lv = (ListView) v.findViewById(R.id.listView1);
// Calling async task to get json
new GetVideos().execute();
return v;
}
private class GetVideos extends AsyncTask<Void, Void, Void> {
#Override
protected void onPreExecute() {
super.onPreExecute();
// Showing progress dialog
pDialog = new ProgressDialog(getActivity());
pDialog.setMessage("Please wait...");
pDialog.setCancelable(false);
pDialog.show();
}
#Override
protected Void doInBackground(Void... arg0) {
// Creating service handler class instance
ServiceHandler sh = new ServiceHandler();
// Making a request to url and getting response
String jsonStr = sh.makeServiceCall(url, ServiceHandler.GET);
Log.d("Response: ", "> " + jsonStr);
if (jsonStr != null) {
try {
JSONObject jsonObj = new JSONObject(jsonStr);
// Getting JSON Array node
data = jsonObj.getJSONArray(TAG_DATA);
// looping through All Contacts
for (int i = 0; i < data.length(); i++) {
JSONObject d = data.getJSONObject(i);
String title = d.getString(TAG_TITLE);
String image = d.getString(TAG_IMAGE);
String url = d.getString(TAG_URL);
// tmp hashmap for single contact
HashMap<String, String> data = new HashMap<String, String>();
// adding each child node to HashMap key => value
data.put(TAG_TITLE, title);
data.put(TAG_IMAGE, image);
data.put(TAG_URL, url);
// adding contact to contact list
dataList.add(data);
}
} catch (JSONException e) {
e.printStackTrace();
}
} else {
Log.e("ServiceHandler", "Couldn't get any data from the url");
}
return null;
}
#Override
protected void onPostExecute(Void result) {
super.onPostExecute(result);
// Dismiss the progress dialog
if (pDialog.isShowing())
pDialog.dismiss();
/**
* Updating parsed JSON data into ListView
* */
ListAdapter adapter = new SimpleAdapter(
getActivity(), dataList,
R.layout.list_item, new String[] { TAG_TITLE, TAG_IMAGE
}, new int[] { R.id.title,
R.id.image});
lv.setAdapter(adapter);
}
}
}
XML Layout
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context="com.peekatu.Fcc4me.watchFragment">
<!-- TODO: Update blank fragment layout -->
<VideoView
android:layout_width="wrap_content"
android:layout_height="225dp"
android:id="#+id/videoView"
android:layout_gravity="center_horizontal|top" />
<ListView
android:id="#+id/listView1"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:layout_below="#+id/videoView" />
</RelativeLayout>
Line 192 is lv.setAdapter(adapter);
The ListView lv is not initialized (you commented out that line in onCreateView):
//ListView lv = (ListView) v.findViewById(R.id.listView1);
you should uncomment it:
ListView lv = (ListView) v.findViewById(R.id.listView1);
EDIT: Ok, ok, I am sorry, you need to assign to the global lv variable instead of the local one, try this:
lv = (ListView) v.findViewById(R.id.listView1);
This should get you the correct view and make null exception dissapear...
You should do
lv = (ListView) v.findViewById(R.id.listView1);
instead of
ListView lv = (ListView) v.findViewById(R.id.listView1);
Doing this you are defining another lv variable just visible inside that method, but what you really want is assign a value to your lv class variable.
I'm making an App that implements this slide-out Menu and i'm pretty much satisfied about the implementation.
I divided my app in multiple Fragment for one Activity so for each section of the menu there is a Fragment.
The point is that i have an OnItemClickListener that allow me to switch beetween Fragments, so I'd tried two methods :
replace() : it works fine for all fragment except for one of them that load a XML which contains a map (code below). On first load there's no problem but when I switch to another fragment and came back to the one with the map, the app crash.
<fragment
android:id="#+id/map"
android:layout_width="match_parent"
android:layout_height="match_parent"
class="com.google.android.gms.maps.SupportMapFragment" />
<RelativeLayout
android:id="#+id/RelativeLayout1"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<ImageButton
android:id="#+id/refreshButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentRight="true"
android:layout_alignParentTop="true"
android:layout_marginTop="63dp"
android:src="#drawable/refresh"
android:text="Rafraichir" />
</RelativeLayout>
public class MapFragment extends Fragment implements
OnInfoWindowClickListener, LocationListener {
private GoogleMap gMap;
Geocoder geocoder;
private LocationManager locationManager;
private Location userLocation;
private String provider;
private ImageButton refreshButton;
ArrayList<Parking> Parkings;
Context context;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
final View view = inflater.inflate(R.layout.fragmen_map,
container, false);
gMap = ((SupportMapFragment) getFragmentManager().findFragmentById(
R.id.map)).getMap();
gMap.setOnInfoWindowClickListener(this);
context = getActivity();
geocoder = new Geocoder(context);
refreshButton = (ImageButton) view.findViewById(R.id.refreshButton);
refreshButton.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
getParkingsConnection = new GetParkingsConnection(context);
getParkingsConnection.execute(null, null, null);
myParkings = new ArrayList<Parking>();
}
});
// Geolocaliation
LocationManager service = (LocationManager) getActivity()
.getSystemService(getActivity().LOCATION_SERVICE);
boolean enabled = service
.isProviderEnabled(LocationManager.GPS_PROVIDER);
// Check if enabled and if not send user to the GSP settings
// Better solution would be to display a dialog and suggesting to
// go to the settings
if (!enabled) {
Intent intent = new Intent(Settings.ACTION_LOCATION_SOURCE_SETTINGS);
startActivity(intent);
}
// Get the location manager
locationManager = (LocationManager) getActivity().getSystemService(
getActivity().LOCATION_SERVICE);
// Define the criteria how to select the locatioin provider -> use
// default
Criteria criteria = new Criteria();
provider = locationManager.getBestProvider(criteria, false);
Location location = locationManager.getLastKnownLocation(provider);
return view;
}
private Double[] getLatAndLong(String addresse) {
List<Address> addresses = null;
Double latALng[] = new Double[2];
try {
addresses = geocoder.getFromLocationName(addresse, 1);
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
if (addresses.size() > 0) {
double latitude = addresses.get(0).getLatitude();
double longitude = addresses.get(0).getLongitude();
latALng[0] = latitude;
latALng[1] = longitude;
}
return latALng;
}
private GetParkingsConnection getParkingsConnection;
JSONObject json;
// Non-Statice inner class : connection au serveur
private class GetParkingsConnection extends AsyncTask<String, Void, String> {
Context mContext;
private ProgressDialog mDialog;
GetParkingsConnection(Context context) {
mContext = context;
}
#Override
protected void onPreExecute() {
super.onPreExecute();
mDialog = new ProgressDialog(mContext);
mDialog.setMessage("Mise à jour de la carte...");
mDialog.show();
}
#Override
protected String doInBackground(String... urls) {
String resultat;
resultat = getParkings();
return resultat;
}
#Override
protected void onPostExecute(String result) {
super.onPostExecute(result);
Log.d("JSON", result);
JSONArray jArray;
try {
json = new JSONObject(result);
jArray = json.getJSONArray("parking");
System.out.println("*****Parkings*****" + jArray.length());
for (int i = 0; i < jArray.length(); i++) {
JSONObject json_data = jArray.getJSONObject(i);
Log.d("adresse :",
json_data.getString("adresse") + ", nom :"
+ json_data.getString("nom")
+ ", latitude :"
+ json_data.getDouble("latitude")
+ ", longitude :"
+ json_data.getDouble("longitude"));
String adresse = json_data.getString("adresse");
Double latALng[] = getLatAndLong(adresse);
Double lat = latALng[0]; // json_data.getDouble("latitude");
Double lng = latALng[1]; // json_data.getDouble("longitude");
String nom = json_data.getString("nom");
LatLng parkingLocation = new LatLng(lat, lng);
Marker parking = gMap.addMarker(new MarkerOptions()
.position(parkingLocation)
.title(nom)
.snippet(adresse)
.icon(BitmapDescriptorFactory
.fromResource(R.drawable.my_marker)));
Parking park = new Parking(parking.getId(), adresse, nom,
"", lat, lng);
myParkings.add(park);
}
} catch (JSONException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
mDialog.dismiss();
}
// Fonction effectuant uenrequête de type GET sur le fichier
// getParking.php
protected String getParkings() {
HttpResponse response = null;
String res = "";
try {
HttpClient client = new DefaultHttpClient();
HttpGet request = new HttpGet();
// request.setURI(new
// URI("http://pkdom.1x.biz/getParkings.php"));
request.setURI(new URI(
"http://glennsonna.fr/webService/getParkings"));
response = client.execute(request);
HttpEntity entity = response.getEntity();
// JSONObject json = new JSONObject();
res = EntityUtils.toString(entity);
} catch (URISyntaxException e) {
e.printStackTrace();
} catch (ClientProtocolException e) {
// TODO Auto-generated catch block
e.printStackTrace();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return res;
}
}
#Override
public void onInfoWindowClick(Marker marker) {
// TODO Auto-generated method stub
Parking parkingToSend = null;
// TOAST
/*
* int p = 0;
*
* while(myParkings.get(p).idMarker != marker.getId() && p <
* myParkings.size()){ Log.d("Marker :" + marker.getId(),
* myParkings.get(p).idMarker);
*
* if(myParkings.get(p).idMarker.equals(marker.getId()) ){
* parkingToSend = myParkings.get(p); Context context =
* getApplicationContext(); CharSequence text = "Match" +
* parkingToSend.adresse; int duration = Toast.LENGTH_SHORT; Toast toast
* = Toast.makeText(context, text, duration); toast.show(); }
*
* p++; }
*/
for (int p = 0; p < myParkings.size(); p++) {
Log.d("Marker :" + marker.getId(), myParkings.get(p).idMarker);
if (myParkings.get(p).idMarker.equals(marker.getId())) {
parkingToSend = myParkings.get(p);
}
}
if (parkingToSend != null) {
Intent i = new Intent(context.getApplicationContext(),
ParkingDetail.class);
i.putExtra("id", parkingToSend.idMarker);
i.putExtra("adresse", parkingToSend.adresse);
i.putExtra("nom", parkingToSend.nom);
i.putExtra("descri", parkingToSend.description);
i.putExtra("latitude", parkingToSend.lat);
i.putExtra("longitude", parkingToSend.lng);
startActivity(i);
}
}
#Override
public void onLocationChanged(Location user) {
// TODO Auto-generated method stub
Log.d("Latitude", ":" + user.getLatitude());
Log.d("Longitude", ":" + user.getLongitude());
this.gMap.setMyLocationEnabled(true);
}
#Override
public void onProviderDisabled(String provider) {
// TODO Auto-generated method stub
}
#Override
public void onProviderEnabled(String provider) {
// TODO Auto-generated method stub
}
#Override
public void onStatusChanged(String provider, int status, Bundle extras) {
// TODO Auto-generated method stub
}
}
hide() & show() : I can switch beetween fragment but excepted for the first screen (the map) all the other show a blank screen without content.
private MenuDrawer mMenuDrawer;
private MenuAdapter mAdapter;
private ListView mList;
private GoogleMap gMap;
private int mActivePosition = -1;
List<Object> mmyFragment;
Fragment currentFragment;
myMapFragment mmyMapFragment;
myMonCompteFragment mmyMonCompteFragment;
myPaiementFragment mmyPaiementFragment;
myReservationsFragment mmyReservationsFragment;
myFavorisFragment mmyFavorisFragment;
myCodePromoFragment mmyCodePromoFragment;
myAboutFragment mmyAboutFragment;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// setContentView(R.layout.activity_my_map);
ActionBar actionBar = this.getActionBar();
actionBar.setSubtitle("Trouvez votre parking");
actionBar.setTitle("my");
actionBar.setDisplayHomeAsUpEnabled(true);
setupMenu();
setupFragments();
}
private void setupMenu() {
mMenuDrawer = MenuDrawer.attach(this, Position.LEFT);
mMenuDrawer.setContentView(R.layout.activity_my_map);
List<Object> items = new ArrayList<Object>();
items.add(new Item("Carte", R.drawable.ic_action_refresh_dark));
items.add(new Item("Mon Compte", R.drawable.ic_action_refresh_dark));
items.add(new Item("Paiement", R.drawable.ic_action_select_all_dark));
items.add(new Item("Mes Réservations",
R.drawable.ic_action_select_all_dark));
items.add(new Item("Mes favoris", R.drawable.ic_action_refresh_dark));
// items.add(new Category(" "));
items.add(new Item("Code Promo", R.drawable.ic_action_refresh_dark));
items.add(new Item("A propos", R.drawable.ic_action_select_all_dark));
// A custom ListView is needed so the drawer can be notified when it's
// scrolled. This is to update the position
// of the arrow indicator.
mList = new ListView(this);
mAdapter = new MenuAdapter(items);
mList.setAdapter(mAdapter);
mList.setOnItemClickListener(mItemClickListener);
mMenuDrawer.setMenuView(mList);
}
private void setupFragments() {
mmyMapFragment = new myMapFragment();
mmyMonCompteFragment = new myMonCompteFragment();
mmyPaiementFragment = new myPaiementFragment();
mmyReservationsFragment = new myReservationsFragment();
mmyFavorisFragment = new myFavorisFragment();
mmyCodePromoFragment = new myCodePromoFragment();
mmyAboutFragment = new myAboutFragment();
mmyFragment = new ArrayList<Object>();
mmyFragment.add(mmyMapFragment);
mmyFragment.add(mmyMonCompteFragment);
mmyFragment.add(mmyPaiementFragment);
mmyFragment.add(mmyReservationsFragment);
mmyFragment.add(mmyFavorisFragment);
mmyFragment.add(mmyCodePromoFragment);
mmyFragment.add(mmyAboutFragment);
FragmentManager fragmentManager = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager
.beginTransaction();
fragmentTransaction.replace(R.id.myContenu, mmyMapFragment);
fragmentTransaction.commit();
currentFragment = mmyMapFragment;
}
private AdapterView.OnItemClickListener mItemClickListener = new AdapterView.OnItemClickListener() {
#Override
public void onItemClick(AdapterView<?> parent, View view, int position,
long id) {
mActivePosition = position;
mMenuDrawer.setActiveView(view, position);
mMenuDrawer.closeMenu();
if ((mmyFragment.get(position) != null)
/*&& (mmyFragment.get(position).getClass() != currentFragment
.getClass())*/) {
Fragment nexFragment = (Fragment) mmyFragment
.get(position);
FragmentManager fragmentManager = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager
.beginTransaction();
fragmentTransaction.setCustomAnimations(android.R.anim.fade_in,
android.R.anim.fade_out);
fragmentTransaction.hide(currentFragment);
if (!nexFragment.isHidden()) {
//fragmentTransaction.add(nexFragment, nexFragment.getTag());
Toast.makeText(
getApplicationContext(),
""
+ nexFragment.getClass().toString()
+ " : "
+ mmyFragment.indexOf(mmyFragment
.get(position)), Toast.LENGTH_SHORT).show();
}
//fragmentTransaction.addToBackStack(nexFragment.getTag());
fragmentTransaction.attach(nexFragment);
fragmentTransaction.replace(R.id.myContenu, nexFragment);
//fragmentTransaction.show(nexFragment);
currentFragment = nexFragment;
fragmentTransaction.commit();...}
After one day i finaly found the answer here
So i just implemented the code below. But I have to use replace(); so I'll find a way to save my map state.
public void onDestroyView ()
{
try{
SupportMapFragment fragment = ((SupportMapFragment) getFragmentManager().findFragmentById(R.id.map));
FragmentTransaction ft = getActivity().getSupportFragmentManager().beginTransaction();
ft.remove(fragment);
ft.commit();
}catch(Exception e){
}
super.onDestroyView();
}
I'm working on an application that needs to get the source of a web page from a link, and then parse the html from that page.
Could you give me some examples, or starting points where to look to start writing such an app?
You can use HttpClient to perform an HTTP GET and retrieve the HTML response, something like this:
HttpClient client = new DefaultHttpClient();
HttpGet request = new HttpGet(url);
HttpResponse response = client.execute(request);
String html = "";
InputStream in = response.getEntity().getContent();
BufferedReader reader = new BufferedReader(new InputStreamReader(in));
StringBuilder str = new StringBuilder();
String line = null;
while((line = reader.readLine()) != null)
{
str.append(line);
}
in.close();
html = str.toString();
I would suggest jsoup.
According to their website:
Fetch the Wikipedia homepage, parse it to a DOM, and select the headlines from the In the news section into a list of Elements (online sample):
Document doc = Jsoup.connect("http://en.wikipedia.org/").get();
Elements newsHeadlines = doc.select("#mp-itn b a");
Getting started:
Download the jsoup jar core library
Read the cookbook introduction
This question is a bit old, but I figured I should post my answer now that DefaultHttpClient, HttpGet, etc. are deprecated. This function should get and return HTML, given a URL.
public static String getHtml(String url) throws IOException {
// Build and set timeout values for the request.
URLConnection connection = (new URL(url)).openConnection();
connection.setConnectTimeout(5000);
connection.setReadTimeout(5000);
connection.connect();
// Read and store the result line by line then return the entire string.
InputStream in = connection.getInputStream();
BufferedReader reader = new BufferedReader(new InputStreamReader(in));
StringBuilder html = new StringBuilder();
for (String line; (line = reader.readLine()) != null; ) {
html.append(line);
}
in.close();
return html.toString();
}
public class RetrieveSiteData extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... urls) {
StringBuilder builder = new StringBuilder(100000);
for (String url : urls) {
DefaultHttpClient client = new DefaultHttpClient();
HttpGet httpGet = new HttpGet(url);
try {
HttpResponse execute = client.execute(httpGet);
InputStream content = execute.getEntity().getContent();
BufferedReader buffer = new BufferedReader(new InputStreamReader(content));
String s = "";
while ((s = buffer.readLine()) != null) {
builder.append(s);
}
} catch (Exception e) {
e.printStackTrace();
}
}
return builder.toString();
}
#Override
protected void onPostExecute(String result) {
}
}
Call it like
new RetrieveFeedTask(new OnTaskFinished()
{
#Override
public void onFeedRetrieved(String feeds)
{
//do whatever you want to do with the feeds
}
}).execute("http://enterurlhere.com");
RetrieveFeedTask.class
class RetrieveFeedTask extends AsyncTask<String, Void, String>
{
String HTML_response= "";
OnTaskFinished onOurTaskFinished;
public RetrieveFeedTask(OnTaskFinished onTaskFinished)
{
onOurTaskFinished = onTaskFinished;
}
#Override
protected void onPreExecute()
{
super.onPreExecute();
}
#Override
protected String doInBackground(String... urls)
{
try
{
URL url = new URL(urls[0]); // enter your url here which to download
URLConnection conn = url.openConnection();
// open the stream and put it into BufferedReader
BufferedReader br = new BufferedReader(new InputStreamReader(conn.getInputStream()));
String inputLine;
while ((inputLine = br.readLine()) != null)
{
// System.out.println(inputLine);
HTML_response += inputLine;
}
br.close();
System.out.println("Done");
}
catch (MalformedURLException e)
{
e.printStackTrace();
}
catch (IOException e)
{
e.printStackTrace();
}
return HTML_response;
}
#Override
protected void onPostExecute(String feed)
{
onOurTaskFinished.onFeedRetrieved(feed);
}
}
OnTaskFinished.java
public interface OnTaskFinished
{
public void onFeedRetrieved(String feeds);
}
If you have a look here or here, you will see that you can't do that directly with android API, you need an external librairy...
You can choose between the 2 here's hereabove if you need an external librairy.
One of the other SO post answer helped me. This doesn't read line by line; supposingly the html file had a line null in between. As preRequisite add this dependancy from project settings "com.koushikdutta.ion:ion:2.2.1" implement this code in AsyncTASK. If you want the returned -something- to be in UI thread, pass it to a mutual interface.
Ion.with(getApplicationContext()).
load("https://google.com/hashbrowns")
.asString()
.setCallback(new FutureCallback<String>()
{
#Override
public void onCompleted(Exception e, String result) {
//int s = result.lastIndexOf("user_id")+9;
// String st = result.substring(s,s+5);
// Log.e("USERID",st); //something
}
});
public class DownloadTask extends AsyncTask<String, Void, String> {
#Override
protected String doInBackground(String... urls) {
String result = "";
URL url;
HttpsURLConnection urlConnection = null;
try {
url = new URL(urls[0]);
urlConnection = (HttpsURLConnection) url.openConnection();
BufferedReader br = new BufferedReader(new InputStreamReader(urlConnection.getInputStream()));
String inputLine;
while ((inputLine = br.readLine()) != null)
{
// System.out.println(inputLine);
result += inputLine;
}
br.close();
return result;
} catch (Exception e) {
e.printStackTrace();
return "failed";
}
}
}
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DownloadTask task = new DownloadTask();
String result = null;
try {
result = task.execute("https://www.example.com").get();
}catch (Exception e){
e.printStackTrace();
}
Log.i("Result", result);
}