Merge branch 'master' of git.fakecake.org:tt-rss-android
This commit is contained in:
commit
56a0993a90
@ -1,8 +1,8 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
package="org.fox.ttrss"
|
||||
android:versionCode="424"
|
||||
android:versionName="1.190" >
|
||||
android:versionCode="425"
|
||||
android:versionName="1.191" >
|
||||
|
||||
<uses-permission android:name="android.permission.INTERNET" />
|
||||
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
|
||||
|
125
org.fox.ttrss/src/main/java/org/fox/ttrss/ApiCommon.java
Normal file
125
org.fox.ttrss/src/main/java/org/fox/ttrss/ApiCommon.java
Normal file
@ -0,0 +1,125 @@
|
||||
package org.fox.ttrss;
|
||||
|
||||
import android.os.Build;
|
||||
import android.util.Log;
|
||||
|
||||
import java.security.cert.CertificateException;
|
||||
import java.security.cert.X509Certificate;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.HttpsURLConnection;
|
||||
import javax.net.ssl.SSLContext;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import javax.net.ssl.TrustManager;
|
||||
import javax.net.ssl.X509TrustManager;
|
||||
|
||||
public class ApiCommon {
|
||||
public static final String TAG = "ApiCommon";
|
||||
|
||||
public enum ApiError { NO_ERROR, HTTP_UNAUTHORIZED, HTTP_FORBIDDEN, HTTP_NOT_FOUND,
|
||||
HTTP_SERVER_ERROR, HTTP_OTHER_ERROR, SSL_REJECTED, SSL_HOSTNAME_REJECTED, PARSE_ERROR, IO_ERROR, OTHER_ERROR, API_DISABLED,
|
||||
API_UNKNOWN, LOGIN_FAILED, INVALID_URL, API_INCORRECT_USAGE, NETWORK_UNAVAILABLE, API_UNKNOWN_METHOD }
|
||||
|
||||
public static int getErrorMessage(ApiError error) {
|
||||
switch (error) {
|
||||
case NO_ERROR:
|
||||
return R.string.error_unknown;
|
||||
case HTTP_UNAUTHORIZED:
|
||||
return R.string.error_http_unauthorized;
|
||||
case HTTP_FORBIDDEN:
|
||||
return R.string.error_http_forbidden;
|
||||
case HTTP_NOT_FOUND:
|
||||
return R.string.error_http_not_found;
|
||||
case HTTP_SERVER_ERROR:
|
||||
return R.string.error_http_server_error;
|
||||
case HTTP_OTHER_ERROR:
|
||||
return R.string.error_http_other_error;
|
||||
case SSL_REJECTED:
|
||||
return R.string.error_ssl_rejected;
|
||||
case SSL_HOSTNAME_REJECTED:
|
||||
return R.string.error_ssl_hostname_rejected;
|
||||
case PARSE_ERROR:
|
||||
return R.string.error_parse_error;
|
||||
case IO_ERROR:
|
||||
return R.string.error_io_error;
|
||||
case OTHER_ERROR:
|
||||
return R.string.error_other_error;
|
||||
case API_DISABLED:
|
||||
return R.string.error_api_disabled;
|
||||
case API_UNKNOWN:
|
||||
return R.string.error_api_unknown;
|
||||
case API_UNKNOWN_METHOD:
|
||||
return R.string.error_api_unknown_method;
|
||||
case LOGIN_FAILED:
|
||||
return R.string.error_login_failed;
|
||||
case INVALID_URL:
|
||||
return R.string.error_invalid_api_url;
|
||||
case API_INCORRECT_USAGE:
|
||||
return R.string.error_api_incorrect_usage;
|
||||
case NETWORK_UNAVAILABLE:
|
||||
return R.string.error_network_unavailable;
|
||||
default:
|
||||
Log.d(TAG, "getErrorMessage: unknown error code=" + error);
|
||||
return R.string.error_unknown;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static void trustAllHosts(boolean trustAnyCert, boolean trustAnyHost) {
|
||||
try {
|
||||
if (trustAnyCert) {
|
||||
X509TrustManager easyTrustManager = new X509TrustManager() {
|
||||
|
||||
public void checkClientTrusted(
|
||||
X509Certificate[] chain,
|
||||
String authType) throws CertificateException {
|
||||
// Oh, I am easy!
|
||||
}
|
||||
|
||||
public void checkServerTrusted(
|
||||
X509Certificate[] chain,
|
||||
String authType) throws CertificateException {
|
||||
// Oh, I am easy!
|
||||
}
|
||||
|
||||
public X509Certificate[] getAcceptedIssuers() {
|
||||
return null;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// Create a trust manager that does not validate certificate chains
|
||||
TrustManager[] trustAllCerts = new TrustManager[] {easyTrustManager};
|
||||
|
||||
// Install the all-trusting trust manager
|
||||
|
||||
SSLContext sc = SSLContext.getInstance("TLS");
|
||||
|
||||
sc.init(null, trustAllCerts, new java.security.SecureRandom());
|
||||
|
||||
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
|
||||
}
|
||||
|
||||
if (trustAnyHost) {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
protected static void disableConnectionReuseIfNecessary() {
|
||||
// HTTP connection reuse which was buggy pre-froyo
|
||||
if (Integer.parseInt(Build.VERSION.SDK) < Build.VERSION_CODES.FROYO) {
|
||||
System.setProperty("http.keepAlive", "false");
|
||||
}
|
||||
}
|
||||
|
||||
}
|
261
org.fox.ttrss/src/main/java/org/fox/ttrss/ApiLoader.java
Normal file
261
org.fox.ttrss/src/main/java/org/fox/ttrss/ApiLoader.java
Normal file
@ -0,0 +1,261 @@
|
||||
package org.fox.ttrss;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.SharedPreferences;
|
||||
import android.net.ConnectivityManager;
|
||||
import android.net.NetworkInfo;
|
||||
import android.preference.PreferenceManager;
|
||||
import android.support.v4.content.AsyncTaskLoader;
|
||||
import android.util.Base64;
|
||||
import android.util.Log;
|
||||
|
||||
import com.google.gson.Gson;
|
||||
import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.JsonParser;
|
||||
|
||||
import org.fox.ttrss.ApiCommon.ApiError;
|
||||
|
||||
import java.io.IOException;
|
||||
import java.io.InputStreamReader;
|
||||
import java.io.OutputStream;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URL;
|
||||
import java.util.HashMap;
|
||||
|
||||
public class ApiLoader extends AsyncTaskLoader<JsonElement> {
|
||||
private final String TAG = this.getClass().getSimpleName();
|
||||
|
||||
|
||||
public static final int API_STATUS_OK = 0;
|
||||
public static final int API_STATUS_ERR = 1;
|
||||
|
||||
private String m_api;
|
||||
private boolean m_transportDebugging = false;
|
||||
protected int m_responseCode = 0;
|
||||
protected String m_responseMessage;
|
||||
protected int m_apiStatusCode = 0;
|
||||
protected boolean m_canUseProgress = false;
|
||||
protected Context m_context;
|
||||
private SharedPreferences m_prefs;
|
||||
protected String m_lastErrorMessage;
|
||||
protected ApiError m_lastError;
|
||||
protected HashMap<String,String> m_params;
|
||||
protected JsonElement m_data;
|
||||
|
||||
public ApiLoader(Context context, HashMap<String,String> params) {
|
||||
super(context);
|
||||
|
||||
m_context = context;
|
||||
|
||||
m_prefs = PreferenceManager.getDefaultSharedPreferences(m_context);
|
||||
|
||||
m_api = m_prefs.getString("ttrss_url", "").trim();
|
||||
m_transportDebugging = m_prefs.getBoolean("transport_debugging", false);
|
||||
m_lastError = ApiError.NO_ERROR;
|
||||
m_params = params;
|
||||
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onStartLoading() {
|
||||
if (m_data != null) {
|
||||
deliverResult(m_data);
|
||||
} else {
|
||||
forceLoad();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void deliverResult(JsonElement data) {
|
||||
m_data = data;
|
||||
|
||||
super.deliverResult(data);
|
||||
}
|
||||
|
||||
public int getErrorMessage() {
|
||||
return ApiCommon.getErrorMessage(m_lastError);
|
||||
}
|
||||
|
||||
public ApiError getLastError() {
|
||||
return m_lastError;
|
||||
}
|
||||
|
||||
public String getLastErrorMessage() {
|
||||
return m_lastErrorMessage;
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsonElement loadInBackground() {
|
||||
|
||||
if (!isNetworkAvailable()) {
|
||||
m_lastError = ApiError.NETWORK_UNAVAILABLE;
|
||||
return null;
|
||||
}
|
||||
|
||||
Gson gson = new Gson();
|
||||
|
||||
String requestStr = gson.toJson(new HashMap<>(m_params));
|
||||
byte[] postData = null;
|
||||
|
||||
try {
|
||||
postData = requestStr.getBytes("UTF-8");
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
m_lastError = ApiError.OTHER_ERROR;
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
|
||||
if (m_transportDebugging) Log.d(TAG, ">>> (" + requestStr + ") " + m_api);
|
||||
|
||||
URL url;
|
||||
|
||||
try {
|
||||
url = new URL(m_api + "/api/");
|
||||
} catch (Exception e) {
|
||||
m_lastError = ApiError.INVALID_URL;
|
||||
e.printStackTrace();
|
||||
return null;
|
||||
}
|
||||
|
||||
try {
|
||||
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
|
||||
|
||||
String httpLogin = m_prefs.getString("http_login", "").trim();
|
||||
String httpPassword = m_prefs.getString("http_password", "").trim();
|
||||
|
||||
if (httpLogin.length() > 0) {
|
||||
if (m_transportDebugging) Log.d(TAG, "Using HTTP Basic authentication.");
|
||||
|
||||
conn.setRequestProperty("Authorization", "Basic " +
|
||||
Base64.encodeToString((httpLogin + ":" + httpPassword).getBytes("UTF-8"), Base64.NO_WRAP));
|
||||
}
|
||||
|
||||
conn.setDoInput(true);
|
||||
conn.setDoOutput(true);
|
||||
conn.setUseCaches(false);
|
||||
conn.setRequestMethod("POST");
|
||||
conn.setRequestProperty("Content-Length", Integer.toString(postData.length));
|
||||
|
||||
OutputStream out = conn.getOutputStream();
|
||||
out.write(postData);
|
||||
out.close();
|
||||
|
||||
m_responseCode = conn.getResponseCode();
|
||||
m_responseMessage = conn.getResponseMessage();
|
||||
|
||||
switch (m_responseCode) {
|
||||
case HttpURLConnection.HTTP_OK:
|
||||
StringBuffer response = new StringBuffer();
|
||||
InputStreamReader in = new InputStreamReader(conn.getInputStream(), "UTF-8");
|
||||
char[] buf = new char[256];
|
||||
int read = 0;
|
||||
int total = 0;
|
||||
|
||||
int contentLength = conn.getHeaderFieldInt("Api-Content-Length", -1);
|
||||
|
||||
m_canUseProgress = (contentLength != -1);
|
||||
|
||||
while ((read = in.read(buf)) >= 0) {
|
||||
response.append(buf, 0, read);
|
||||
total += read;
|
||||
//publishProgress(Integer.valueOf(total), Integer.valueOf(contentLength));
|
||||
}
|
||||
|
||||
if (m_transportDebugging) Log.d(TAG, "<<< " + response);
|
||||
|
||||
JsonParser parser = new JsonParser();
|
||||
|
||||
JsonElement result = parser.parse(response.toString());
|
||||
JsonObject resultObj = result.getAsJsonObject();
|
||||
|
||||
m_apiStatusCode = resultObj.get("status").getAsInt();
|
||||
|
||||
conn.disconnect();
|
||||
|
||||
switch (m_apiStatusCode) {
|
||||
case API_STATUS_OK:
|
||||
return result.getAsJsonObject().get("content");
|
||||
case API_STATUS_ERR:
|
||||
JsonObject contentObj = resultObj.get("content").getAsJsonObject();
|
||||
String error = contentObj.get("error").getAsString();
|
||||
|
||||
if (error.equals("LOGIN_ERROR")) {
|
||||
m_lastError = ApiError.LOGIN_FAILED;
|
||||
} else if (error.equals("API_DISABLED")) {
|
||||
m_lastError = ApiError.API_DISABLED;
|
||||
} else if (error.equals("NOT_LOGGED_IN")) {
|
||||
m_lastError = ApiError.LOGIN_FAILED;
|
||||
} else if (error.equals("INCORRECT_USAGE")) {
|
||||
m_lastError = ApiError.API_INCORRECT_USAGE;
|
||||
} else if (error.equals("UNKNOWN_METHOD")) {
|
||||
m_lastError = ApiError.API_UNKNOWN_METHOD;
|
||||
} else {
|
||||
Log.d(TAG, "Unknown API error: " + error);
|
||||
m_lastError = ApiError.API_UNKNOWN;
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
case HttpURLConnection.HTTP_UNAUTHORIZED:
|
||||
m_lastError = ApiError.HTTP_UNAUTHORIZED;
|
||||
break;
|
||||
case HttpURLConnection.HTTP_FORBIDDEN:
|
||||
m_lastError = ApiError.HTTP_FORBIDDEN;
|
||||
break;
|
||||
case HttpURLConnection.HTTP_NOT_FOUND:
|
||||
m_lastError = ApiError.HTTP_NOT_FOUND;
|
||||
break;
|
||||
case HttpURLConnection.HTTP_INTERNAL_ERROR:
|
||||
m_lastError = ApiError.HTTP_SERVER_ERROR;
|
||||
break;
|
||||
default:
|
||||
Log.d(TAG, "HTTP response code: " + m_responseCode + "(" + m_responseMessage + ")");
|
||||
m_lastError = ApiError.HTTP_OTHER_ERROR;
|
||||
break;
|
||||
}
|
||||
|
||||
conn.disconnect();
|
||||
return null;
|
||||
} catch (javax.net.ssl.SSLPeerUnverifiedException e) {
|
||||
m_lastError = ApiError.SSL_REJECTED;
|
||||
m_lastErrorMessage = e.getMessage();
|
||||
e.printStackTrace();
|
||||
} catch (IOException e) {
|
||||
m_lastError = ApiError.IO_ERROR;
|
||||
m_lastErrorMessage = e.getMessage();
|
||||
|
||||
if (e.getMessage() != null) {
|
||||
if (e.getMessage().matches("Hostname [^ ]+ was not verified")) {
|
||||
m_lastError = ApiError.SSL_HOSTNAME_REJECTED;
|
||||
}
|
||||
}
|
||||
|
||||
e.printStackTrace();
|
||||
} catch (com.google.gson.JsonSyntaxException e) {
|
||||
m_lastError = ApiError.PARSE_ERROR;
|
||||
m_lastErrorMessage = e.getMessage();
|
||||
e.printStackTrace();
|
||||
} catch (Exception e) {
|
||||
m_lastError = ApiError.OTHER_ERROR;
|
||||
m_lastErrorMessage = e.getMessage();
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
protected boolean isNetworkAvailable() {
|
||||
ConnectivityManager cm = (ConnectivityManager)
|
||||
m_context.getSystemService(Context.CONNECTIVITY_SERVICE);
|
||||
NetworkInfo networkInfo = cm.getActiveNetworkInfo();
|
||||
|
||||
// if no network is available networkInfo will be null
|
||||
// otherwise check if we are connected
|
||||
if (networkInfo != null && networkInfo.isConnected()) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
@ -22,24 +22,13 @@ import java.io.OutputStream;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URL;
|
||||
import java.security.cert.CertificateException;
|
||||
import java.security.cert.X509Certificate;
|
||||
import java.util.HashMap;
|
||||
|
||||
import javax.net.ssl.HostnameVerifier;
|
||||
import javax.net.ssl.HttpsURLConnection;
|
||||
import javax.net.ssl.SSLContext;
|
||||
import javax.net.ssl.SSLSession;
|
||||
import javax.net.ssl.TrustManager;
|
||||
import javax.net.ssl.X509TrustManager;
|
||||
import static org.fox.ttrss.ApiCommon.ApiError;
|
||||
|
||||
public class ApiRequest extends AsyncTask<HashMap<String,String>, Integer, JsonElement> {
|
||||
private final String TAG = this.getClass().getSimpleName();
|
||||
|
||||
public enum ApiError { NO_ERROR, HTTP_UNAUTHORIZED, HTTP_FORBIDDEN, HTTP_NOT_FOUND,
|
||||
HTTP_SERVER_ERROR, HTTP_OTHER_ERROR, SSL_REJECTED, SSL_HOSTNAME_REJECTED, PARSE_ERROR, IO_ERROR, OTHER_ERROR, API_DISABLED,
|
||||
API_UNKNOWN, LOGIN_FAILED, INVALID_URL, API_INCORRECT_USAGE, NETWORK_UNAVAILABLE, API_UNKNOWN_METHOD }
|
||||
|
||||
public static final int API_STATUS_OK = 0;
|
||||
public static final int API_STATUS_ERR = 1;
|
||||
|
||||
@ -76,47 +65,7 @@ public class ApiRequest extends AsyncTask<HashMap<String,String>, Integer, JsonE
|
||||
}
|
||||
|
||||
public int getErrorMessage() {
|
||||
switch (m_lastError) {
|
||||
case NO_ERROR:
|
||||
return R.string.error_unknown;
|
||||
case HTTP_UNAUTHORIZED:
|
||||
return R.string.error_http_unauthorized;
|
||||
case HTTP_FORBIDDEN:
|
||||
return R.string.error_http_forbidden;
|
||||
case HTTP_NOT_FOUND:
|
||||
return R.string.error_http_not_found;
|
||||
case HTTP_SERVER_ERROR:
|
||||
return R.string.error_http_server_error;
|
||||
case HTTP_OTHER_ERROR:
|
||||
return R.string.error_http_other_error;
|
||||
case SSL_REJECTED:
|
||||
return R.string.error_ssl_rejected;
|
||||
case SSL_HOSTNAME_REJECTED:
|
||||
return R.string.error_ssl_hostname_rejected;
|
||||
case PARSE_ERROR:
|
||||
return R.string.error_parse_error;
|
||||
case IO_ERROR:
|
||||
return R.string.error_io_error;
|
||||
case OTHER_ERROR:
|
||||
return R.string.error_other_error;
|
||||
case API_DISABLED:
|
||||
return R.string.error_api_disabled;
|
||||
case API_UNKNOWN:
|
||||
return R.string.error_api_unknown;
|
||||
case API_UNKNOWN_METHOD:
|
||||
return R.string.error_api_unknown_method;
|
||||
case LOGIN_FAILED:
|
||||
return R.string.error_login_failed;
|
||||
case INVALID_URL:
|
||||
return R.string.error_invalid_api_url;
|
||||
case API_INCORRECT_USAGE:
|
||||
return R.string.error_api_incorrect_usage;
|
||||
case NETWORK_UNAVAILABLE:
|
||||
return R.string.error_network_unavailable;
|
||||
default:
|
||||
Log.d(TAG, "getErrorMessage: unknown error code=" + m_lastError);
|
||||
return R.string.error_unknown;
|
||||
}
|
||||
return ApiCommon.getErrorMessage(m_lastError);
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -140,13 +89,8 @@ public class ApiRequest extends AsyncTask<HashMap<String,String>, Integer, JsonE
|
||||
return null;
|
||||
}
|
||||
|
||||
/* disableConnectionReuseIfNecessary(); */
|
||||
|
||||
if (m_transportDebugging) Log.d(TAG, ">>> (" + requestStr + ") " + m_api);
|
||||
|
||||
/* ApiRequest.trustAllHosts(m_prefs.getBoolean("ssl_trust_any", false),
|
||||
m_prefs.getBoolean("ssl_trust_any_host", false)); */
|
||||
|
||||
URL url;
|
||||
|
||||
try {
|
||||
@ -283,64 +227,7 @@ public class ApiRequest extends AsyncTask<HashMap<String,String>, Integer, JsonE
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
public static void trustAllHosts(boolean trustAnyCert, boolean trustAnyHost) {
|
||||
try {
|
||||
if (trustAnyCert) {
|
||||
X509TrustManager easyTrustManager = new X509TrustManager() {
|
||||
|
||||
public void checkClientTrusted(
|
||||
X509Certificate[] chain,
|
||||
String authType) throws CertificateException {
|
||||
// Oh, I am easy!
|
||||
}
|
||||
|
||||
public void checkServerTrusted(
|
||||
X509Certificate[] chain,
|
||||
String authType) throws CertificateException {
|
||||
// Oh, I am easy!
|
||||
}
|
||||
|
||||
public X509Certificate[] getAcceptedIssuers() {
|
||||
return null;
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// Create a trust manager that does not validate certificate chains
|
||||
TrustManager[] trustAllCerts = new TrustManager[] {easyTrustManager};
|
||||
|
||||
// Install the all-trusting trust manager
|
||||
|
||||
SSLContext sc = SSLContext.getInstance("TLS");
|
||||
|
||||
sc.init(null, trustAllCerts, new java.security.SecureRandom());
|
||||
|
||||
HttpsURLConnection.setDefaultSSLSocketFactory(sc.getSocketFactory());
|
||||
}
|
||||
|
||||
if (trustAnyHost) {
|
||||
HttpsURLConnection.setDefaultHostnameVerifier(new HostnameVerifier() {
|
||||
@Override
|
||||
public boolean verify(String hostname, SSLSession session) {
|
||||
return true;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@SuppressWarnings("deprecation")
|
||||
protected static void disableConnectionReuseIfNecessary() {
|
||||
// HTTP connection reuse which was buggy pre-froyo
|
||||
if (Integer.parseInt(Build.VERSION.SDK) < Build.VERSION_CODES.FROYO) {
|
||||
System.setProperty("http.keepAlive", "false");
|
||||
}
|
||||
}
|
||||
|
||||
protected boolean isNetworkAvailable() {
|
||||
ConnectivityManager cm = (ConnectivityManager)
|
||||
m_context.getSystemService(Context.CONNECTIVITY_SERVICE);
|
||||
|
@ -3,7 +3,6 @@ package org.fox.ttrss;
|
||||
import android.annotation.SuppressLint;
|
||||
import android.app.Activity;
|
||||
import android.content.SharedPreferences;
|
||||
import android.net.Uri;
|
||||
import android.os.BadParcelableException;
|
||||
import android.os.Bundle;
|
||||
import android.os.Handler;
|
||||
@ -216,7 +215,7 @@ public class ArticlePager extends Fragment {
|
||||
}
|
||||
|
||||
} else {
|
||||
if (m_lastError == ApiError.LOGIN_FAILED) {
|
||||
if (m_lastError == ApiCommon.ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
m_activity.toast(getErrorMessage());
|
||||
|
@ -10,6 +10,8 @@ import android.content.SharedPreferences;
|
||||
import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
|
||||
import android.os.Bundle;
|
||||
import android.preference.PreferenceManager;
|
||||
import android.support.v4.app.LoaderManager;
|
||||
import android.support.v4.content.Loader;
|
||||
import android.support.v4.widget.SwipeRefreshLayout;
|
||||
import android.util.Log;
|
||||
import android.util.TypedValue;
|
||||
@ -43,7 +45,8 @@ import java.util.Comparator;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnItemClickListener, OnSharedPreferenceChangeListener {
|
||||
public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnItemClickListener, OnSharedPreferenceChangeListener,
|
||||
LoaderManager.LoaderCallbacks<JsonElement> {
|
||||
private final String TAG = this.getClass().getSimpleName();
|
||||
private FeedCategoryListAdapter m_adapter;
|
||||
private FeedCategoryList m_cats = new FeedCategoryList();
|
||||
@ -53,6 +56,131 @@ public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnIt
|
||||
private ListView m_list;
|
||||
protected SharedPreferences m_prefs;
|
||||
|
||||
@Override
|
||||
public Loader<JsonElement> onCreateLoader(int id, Bundle args) {
|
||||
final String sessionId = m_activity.getSessionId();
|
||||
final boolean unreadOnly = m_activity.getUnreadOnly();
|
||||
|
||||
@SuppressWarnings("serial")
|
||||
HashMap<String, String> params = new HashMap<String, String>() {
|
||||
{
|
||||
put("op", "getCategories");
|
||||
put("sid", sessionId);
|
||||
put("enable_nested", "true");
|
||||
if (unreadOnly) {
|
||||
put("unread_only", String.valueOf(unreadOnly));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
return new ApiLoader(getContext(), params);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onLoadFinished(Loader<JsonElement> loader, JsonElement result) {
|
||||
Log.d(TAG, "onLoadFinished: " + loader + " " + result);
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(false);
|
||||
|
||||
View loadingBar = getView().findViewById(R.id.feeds_loading_bar);
|
||||
|
||||
if (loadingBar != null) {
|
||||
loadingBar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
try {
|
||||
JsonArray content = result.getAsJsonArray();
|
||||
if (content != null) {
|
||||
Type listType = new TypeToken<List<FeedCategory>>() {}.getType();
|
||||
final List<FeedCategory> cats = new Gson().fromJson(content, listType);
|
||||
|
||||
m_cats.clear();
|
||||
|
||||
int apiLevel = m_activity.getApiLevel();
|
||||
|
||||
boolean specialCatFound = false;
|
||||
|
||||
// virtual cats implemented in getCategories since api level 1
|
||||
if (apiLevel == 0) {
|
||||
m_cats.add(new FeedCategory(-1, "Special", 0));
|
||||
m_cats.add(new FeedCategory(-2, "Labels", 0));
|
||||
m_cats.add(new FeedCategory(0, "Uncategorized", 0));
|
||||
|
||||
specialCatFound = true;
|
||||
}
|
||||
|
||||
for (FeedCategory c : cats) {
|
||||
if (c.id == -1) {
|
||||
specialCatFound = true;
|
||||
}
|
||||
}
|
||||
|
||||
m_cats.addAll(cats);
|
||||
|
||||
sortCats();
|
||||
|
||||
if (!specialCatFound) {
|
||||
m_cats.add(0, new FeedCategory(-1, "Special", 0));
|
||||
}
|
||||
|
||||
//m_adapter.notifyDataSetChanged(); (done by sortCats)
|
||||
//m_activity.setLoadingStatus(R.string.blank, false);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
ApiLoader al = (ApiLoader) loader;
|
||||
|
||||
if (al.getLastError() == ApiCommon.ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
if (al.getLastErrorMessage() != null) {
|
||||
m_activity.toast(getString(al.getErrorMessage()) + "\n" + al.getLastErrorMessage());
|
||||
} else {
|
||||
m_activity.toast(al.getErrorMessage());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void sortCats() {
|
||||
Comparator<FeedCategory> cmp;
|
||||
|
||||
if (m_prefs.getBoolean("sort_feeds_by_unread", false)) {
|
||||
cmp = new CatUnreadComparator();
|
||||
} else {
|
||||
if (m_activity.getApiLevel() >= 3) {
|
||||
cmp = new CatOrderComparator();
|
||||
} else {
|
||||
cmp = new CatTitleComparator();
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
Collections.sort(m_cats, cmp);
|
||||
} catch (IllegalArgumentException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
try {
|
||||
m_adapter.notifyDataSetChanged();
|
||||
} catch (NullPointerException e) {
|
||||
// adapter missing
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onLoaderReset(Loader<JsonElement> loader) {
|
||||
Log.d(TAG, "onLoaderReset: " + loader);
|
||||
|
||||
m_cats.clear();
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
@SuppressLint("DefaultLocale")
|
||||
class CatUnreadComparator implements Comparator<FeedCategory> {
|
||||
@Override
|
||||
@ -199,7 +327,7 @@ public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnIt
|
||||
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
|
||||
if (savedInstanceState != null) {
|
||||
m_selectedCat = savedInstanceState.getParcelable("selectedCat");
|
||||
m_cats = savedInstanceState.getParcelable("cats");
|
||||
//m_cats = savedInstanceState.getParcelable("cats");
|
||||
}
|
||||
|
||||
View view = inflater.inflate(R.layout.fragment_cats, container, false);
|
||||
@ -247,9 +375,9 @@ public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnIt
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
refresh(false);
|
||||
|
||||
|
||||
getLoaderManager().initLoader(0, null, this);
|
||||
|
||||
m_activity.invalidateOptionsMenu();
|
||||
}
|
||||
|
||||
@ -259,165 +387,15 @@ public class FeedCategoriesFragment extends BaseFeedlistFragment implements OnIt
|
||||
|
||||
out.setClassLoader(getClass().getClassLoader());
|
||||
out.putParcelable("selectedCat", m_selectedCat);
|
||||
out.putParcelable("cats", m_cats);
|
||||
//out.putParcelable("cats", m_cats);
|
||||
}
|
||||
|
||||
/* private void setLoadingStatus(int status, boolean showProgress) {
|
||||
if (getView() != null) {
|
||||
TextView tv = (TextView)getView().findViewById(R.id.loading_message);
|
||||
|
||||
if (tv != null) {
|
||||
tv.setText(status);
|
||||
}
|
||||
}
|
||||
|
||||
m_activity.setProgressBarIndeterminateVisibility(showProgress);
|
||||
} */
|
||||
|
||||
public void refresh(boolean background) {
|
||||
if (!isAdded()) return;
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(true);
|
||||
|
||||
CatsRequest req = new CatsRequest(getActivity().getApplicationContext());
|
||||
|
||||
final String sessionId = m_activity.getSessionId();
|
||||
final boolean unreadOnly = m_activity.getUnreadOnly();
|
||||
|
||||
if (sessionId != null) {
|
||||
//m_activity.setLoadingStatus(R.string.blank, true);
|
||||
//m_activity.setProgressBarVisibility(true);
|
||||
|
||||
@SuppressWarnings("serial")
|
||||
HashMap<String,String> map = new HashMap<String,String>() {
|
||||
{
|
||||
put("op", "getCategories");
|
||||
put("sid", sessionId);
|
||||
put("enable_nested", "true");
|
||||
if (unreadOnly) {
|
||||
put("unread_only", String.valueOf(unreadOnly));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
req.execute(map);
|
||||
}
|
||||
}
|
||||
|
||||
private class CatsRequest extends ApiRequest {
|
||||
|
||||
public CatsRequest(Context context) {
|
||||
super(context);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onProgressUpdate(Integer... progress) {
|
||||
m_activity.setProgress(Math.round((((float)progress[0] / (float)progress[1]) * 10000)));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
if (isDetached() || !isAdded()) return;
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(false);
|
||||
|
||||
if (getView() != null) {
|
||||
View loadingBar = getView().findViewById(R.id.feeds_loading_bar);
|
||||
|
||||
if (loadingBar != null) {
|
||||
loadingBar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
try {
|
||||
JsonArray content = result.getAsJsonArray();
|
||||
if (content != null) {
|
||||
Type listType = new TypeToken<List<FeedCategory>>() {}.getType();
|
||||
final List<FeedCategory> cats = new Gson().fromJson(content, listType);
|
||||
|
||||
m_cats.clear();
|
||||
|
||||
int apiLevel = m_activity.getApiLevel();
|
||||
|
||||
boolean specialCatFound = false;
|
||||
|
||||
// virtual cats implemented in getCategories since api level 1
|
||||
if (apiLevel == 0) {
|
||||
m_cats.add(new FeedCategory(-1, "Special", 0));
|
||||
m_cats.add(new FeedCategory(-2, "Labels", 0));
|
||||
m_cats.add(new FeedCategory(0, "Uncategorized", 0));
|
||||
|
||||
specialCatFound = true;
|
||||
}
|
||||
|
||||
for (FeedCategory c : cats) {
|
||||
if (c.id == -1) {
|
||||
specialCatFound = true;
|
||||
}
|
||||
|
||||
m_cats.add(c);
|
||||
}
|
||||
|
||||
sortCats();
|
||||
|
||||
if (!specialCatFound) {
|
||||
m_cats.add(0, new FeedCategory(-1, "Special", 0));
|
||||
}
|
||||
|
||||
/* if (m_cats.size() == 0)
|
||||
setLoadingStatus(R.string.no_feeds_to_display, false);
|
||||
else */
|
||||
|
||||
//m_adapter.notifyDataSetChanged(); (done by sortCats)
|
||||
//m_activity.setLoadingStatus(R.string.blank, false);
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
if (m_lastError == ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
|
||||
if (m_lastErrorMessage != null) {
|
||||
m_activity.toast(getString(getErrorMessage()) + "\n" + m_lastErrorMessage);
|
||||
} else {
|
||||
m_activity.toast(getErrorMessage());
|
||||
}
|
||||
|
||||
//m_activity.setLoadingStatus(getErrorMessage(), false);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public void sortCats() {
|
||||
Comparator<FeedCategory> cmp;
|
||||
|
||||
if (m_prefs.getBoolean("sort_feeds_by_unread", false)) {
|
||||
cmp = new CatUnreadComparator();
|
||||
} else {
|
||||
if (m_activity.getApiLevel() >= 3) {
|
||||
cmp = new CatOrderComparator();
|
||||
} else {
|
||||
cmp = new CatTitleComparator();
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
Collections.sort(m_cats, cmp);
|
||||
} catch (IllegalArgumentException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
try {
|
||||
m_adapter.notifyDataSetChanged();
|
||||
} catch (NullPointerException e) {
|
||||
// adapter missing
|
||||
}
|
||||
|
||||
getLoaderManager().restartLoader(0, null, this).forceLoad();
|
||||
}
|
||||
|
||||
private class FeedCategoryListAdapter extends ArrayAdapter<FeedCategory> {
|
||||
|
@ -11,6 +11,8 @@ import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
|
||||
import android.graphics.Typeface;
|
||||
import android.os.Bundle;
|
||||
import android.preference.PreferenceManager;
|
||||
import android.support.v4.app.LoaderManager;
|
||||
import android.support.v4.content.Loader;
|
||||
import android.support.v4.widget.SwipeRefreshLayout;
|
||||
import android.util.Log;
|
||||
import android.util.TypedValue;
|
||||
@ -45,7 +47,8 @@ import java.util.Comparator;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
|
||||
public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickListener, OnSharedPreferenceChangeListener {
|
||||
public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickListener, OnSharedPreferenceChangeListener,
|
||||
LoaderManager.LoaderCallbacks<JsonElement> {
|
||||
private final String TAG = this.getClass().getSimpleName();
|
||||
private SharedPreferences m_prefs;
|
||||
private FeedListAdapter m_adapter;
|
||||
@ -53,9 +56,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
private MasterActivity m_activity;
|
||||
private Feed m_selectedFeed;
|
||||
private FeedCategory m_activeCategory;
|
||||
private static final String ICON_PATH = "/icons/";
|
||||
//private boolean m_enableFeedIcons;
|
||||
private boolean m_feedIconsChecked = false;
|
||||
private SwipeRefreshLayout m_swipeLayout;
|
||||
private boolean m_enableParentBtn = false;
|
||||
private ListView m_list;
|
||||
@ -64,7 +64,114 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
m_activeCategory = cat;
|
||||
m_enableParentBtn = enableParentBtn;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public Loader<JsonElement> onCreateLoader(int id, Bundle args) {
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(true);
|
||||
|
||||
final int catId = (m_activeCategory != null) ? m_activeCategory.id : -4;
|
||||
|
||||
final String sessionId = m_activity.getSessionId();
|
||||
final boolean unreadOnly = m_activity.getUnreadOnly() && (m_activeCategory == null || m_activeCategory.id != -1);
|
||||
|
||||
HashMap<String,String> params = new HashMap<String,String>() {
|
||||
{
|
||||
put("op", "getFeeds");
|
||||
put("sid", sessionId);
|
||||
put("include_nested", "true");
|
||||
put("cat_id", String.valueOf(catId));
|
||||
if (unreadOnly) {
|
||||
put("unread_only", String.valueOf(unreadOnly));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
return new FeedsLoader(getActivity().getApplicationContext(), params, catId);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onLoadFinished(Loader<JsonElement> loader, JsonElement result) {
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(false);
|
||||
|
||||
View loadingBar = getView().findViewById(R.id.feeds_loading_bar);
|
||||
|
||||
if (loadingBar != null) {
|
||||
loadingBar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
|
||||
if (result != null) {
|
||||
try {
|
||||
JsonArray content = result.getAsJsonArray();
|
||||
if (content != null) {
|
||||
|
||||
Type listType = new TypeToken<List<Feed>>() {}.getType();
|
||||
final List<Feed> feeds = new Gson().fromJson(content, listType);
|
||||
|
||||
m_feeds.clear();
|
||||
|
||||
int catUnread = 0;
|
||||
|
||||
int catId = ((FeedsLoader) loader).getCatId();
|
||||
|
||||
for (Feed f : feeds)
|
||||
if (f.id > -10 || catId != -4) { // skip labels for flat feedlist for now
|
||||
if (m_activeCategory != null || f.id >= 0) {
|
||||
m_feeds.add(f);
|
||||
catUnread += f.unread;
|
||||
}
|
||||
}
|
||||
|
||||
sortFeeds();
|
||||
|
||||
if (m_activeCategory == null) {
|
||||
Feed feed = new Feed(-1, "Special", true);
|
||||
feed.unread = catUnread;
|
||||
|
||||
m_feeds.add(0, feed);
|
||||
m_adapter.notifyDataSetChanged();
|
||||
|
||||
}
|
||||
|
||||
if (m_enableParentBtn && m_activeCategory != null && m_activeCategory.id >= 0 && m_feeds.size() > 0) {
|
||||
Feed feed = new Feed(m_activeCategory.id, m_activeCategory.title, true);
|
||||
feed.unread = catUnread;
|
||||
feed.always_display_as_feed = true;
|
||||
feed.display_title = getString(R.string.feed_all_articles);
|
||||
|
||||
m_feeds.add(0, feed);
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
ApiLoader al = (ApiLoader) loader;
|
||||
|
||||
if (al.getLastError() == ApiCommon.ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
|
||||
if (al.getLastErrorMessage() != null) {
|
||||
m_activity.toast(getString(al.getErrorMessage()) + "\n" + al.getLastErrorMessage());
|
||||
} else {
|
||||
m_activity.toast(al.getErrorMessage());
|
||||
}
|
||||
|
||||
//m_activity.setLoadingStatus(getErrorMessage(), false);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onLoaderReset(Loader<JsonElement> loader) {
|
||||
m_feeds.clear();
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
@SuppressLint("DefaultLocale")
|
||||
class FeedUnreadComparator implements Comparator<Feed> {
|
||||
|
||||
@ -227,7 +334,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
|
||||
AdapterContextMenuInfo info = (AdapterContextMenuInfo) menuInfo;
|
||||
|
||||
//ListView list = (ListView) getView().findViewById(R.id.feeds);
|
||||
Feed feed = (Feed) m_list.getItemAtPosition(info.position);
|
||||
|
||||
menu.setHeaderTitle(feed.display_title != null ? feed.display_title : feed.title);
|
||||
@ -249,8 +355,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
|
||||
if (savedInstanceState != null) {
|
||||
m_selectedFeed = savedInstanceState.getParcelable("selectedFeed");
|
||||
m_feeds = savedInstanceState.getParcelable("feeds");
|
||||
m_feedIconsChecked = savedInstanceState.getBoolean("feedIconsChecked");
|
||||
m_activeCategory = savedInstanceState.getParcelable("activeCat");
|
||||
m_enableParentBtn = savedInstanceState.getBoolean("enableParentBtn");
|
||||
}
|
||||
@ -266,21 +370,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
}
|
||||
});
|
||||
|
||||
/* Button parentBtn = (Button) view.findViewById(R.id.open_parent);
|
||||
|
||||
if (parentBtn != null) {
|
||||
if (m_enableParentBtn) {
|
||||
parentBtn.setOnClickListener(new OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View view) {
|
||||
m_activity.getSupportFragmentManager().popBackStack();
|
||||
}
|
||||
});
|
||||
} else {
|
||||
parentBtn.setVisibility(View.GONE);
|
||||
}
|
||||
} */
|
||||
|
||||
m_list = (ListView)view.findViewById(R.id.feeds);
|
||||
|
||||
initDrawerHeader(inflater, view, m_list, m_activity, m_prefs, !m_enableParentBtn);
|
||||
@ -298,23 +387,18 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
m_list.addHeaderView(layout, null, false);
|
||||
}
|
||||
|
||||
m_adapter = new FeedListAdapter(getActivity(), R.layout.feeds_row, (ArrayList<Feed>)m_feeds);
|
||||
m_adapter = new FeedListAdapter(getActivity(), R.layout.feeds_row, m_feeds);
|
||||
m_list.setAdapter(m_adapter);
|
||||
m_list.setOnItemClickListener(this);
|
||||
|
||||
registerForContextMenu(m_list);
|
||||
|
||||
//m_enableFeedIcons = m_prefs.getBoolean("download_feed_icons", false);
|
||||
|
||||
View loadingBar = (View) view.findViewById(R.id.feeds_loading_bar);
|
||||
View loadingBar = view.findViewById(R.id.feeds_loading_bar);
|
||||
|
||||
if (loadingBar != null) {
|
||||
loadingBar.setVisibility(View.VISIBLE);
|
||||
}
|
||||
|
||||
//Log.d(TAG, "mpTRA=" + m_activity.m_pullToRefreshAttacher);
|
||||
//m_activity.m_pullToRefreshAttacher.addRefreshableView(list, this);
|
||||
|
||||
return view;
|
||||
}
|
||||
|
||||
@ -337,8 +421,8 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
refresh(false);
|
||||
|
||||
getLoaderManager().initLoader(0, null, this);
|
||||
|
||||
m_activity.invalidateOptionsMenu();
|
||||
}
|
||||
@ -349,8 +433,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
|
||||
out.setClassLoader(getClass().getClassLoader());
|
||||
out.putParcelable("selectedFeed", m_selectedFeed);
|
||||
out.putParcelable("feeds", m_feeds);
|
||||
out.putBoolean("feedIconsChecked", m_feedIconsChecked);
|
||||
out.putParcelable("activeCat", m_activeCategory);
|
||||
out.putBoolean("enableParentBtn", m_enableParentBtn);
|
||||
}
|
||||
@ -384,202 +466,11 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
|
||||
@SuppressWarnings({ "serial" })
|
||||
public void refresh(boolean background) {
|
||||
//FeedCategory cat = m_onlineServices.getActiveCategory();
|
||||
if (!isAdded()) return;
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(true);
|
||||
|
||||
final int catId = (m_activeCategory != null) ? m_activeCategory.id : -4;
|
||||
|
||||
final String sessionId = m_activity.getSessionId();
|
||||
final boolean unreadOnly = m_activity.getUnreadOnly() && (m_activeCategory == null || m_activeCategory.id != -1);
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(true);
|
||||
|
||||
FeedsRequest req = new FeedsRequest(getActivity().getApplicationContext(), catId);
|
||||
|
||||
if (sessionId != null) {
|
||||
//m_activity.setLoadingStatus(R.string.blank, true);
|
||||
//m_activity.setProgressBarVisibility(true);
|
||||
|
||||
HashMap<String,String> map = new HashMap<String,String>() {
|
||||
{
|
||||
put("op", "getFeeds");
|
||||
put("sid", sessionId);
|
||||
put("include_nested", "true");
|
||||
put("cat_id", String.valueOf(catId));
|
||||
if (unreadOnly) {
|
||||
put("unread_only", String.valueOf(unreadOnly));
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
req.execute(map);
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
/* private void setLoadingStatus(int status, boolean showProgress) {
|
||||
if (getView() != null) {
|
||||
TextView tv = (TextView)getView().findViewById(R.id.loading_message);
|
||||
|
||||
if (tv != null) {
|
||||
tv.setText(status);
|
||||
}
|
||||
}
|
||||
|
||||
if (getActivity() != null)
|
||||
getActivity().setProgressBarIndeterminateVisibility(showProgress);
|
||||
} */
|
||||
|
||||
@SuppressWarnings({ "serial" })
|
||||
/* public void getFeedIcons() {
|
||||
|
||||
ApiRequest req = new ApiRequest(getActivity().getApplicationContext()) {
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
if (isDetached()) return;
|
||||
|
||||
if (result != null) {
|
||||
|
||||
try {
|
||||
JsonElement iconsUrl = result.getAsJsonObject().get("icons_url");
|
||||
|
||||
if (iconsUrl != null) {
|
||||
String iconsStr = iconsUrl.getAsString();
|
||||
String baseUrl = "";
|
||||
|
||||
if (!iconsStr.contains("://")) {
|
||||
baseUrl = m_prefs.getString("ttrss_url", "").trim() + "/" + iconsStr;
|
||||
} else {
|
||||
baseUrl = iconsStr;
|
||||
}
|
||||
|
||||
GetIconsTask git = new GetIconsTask(baseUrl);
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.HONEYCOMB)
|
||||
git.executeOnExecutor(AsyncTask.THREAD_POOL_EXECUTOR, m_feeds);
|
||||
else
|
||||
git.execute(m_feeds);
|
||||
|
||||
m_feedIconsChecked = true;
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Log.d(TAG, "Error receiving icons configuration");
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
final String sessionId = m_activity.getSessionId();
|
||||
|
||||
HashMap<String,String> map = new HashMap<String,String>() {
|
||||
{
|
||||
put("sid", sessionId);
|
||||
put("op", "getConfig");
|
||||
}
|
||||
};
|
||||
|
||||
req.execute(map);
|
||||
} */
|
||||
|
||||
private class FeedsRequest extends ApiRequest {
|
||||
private int m_catId;
|
||||
|
||||
public FeedsRequest(Context context, int catId) {
|
||||
super(context);
|
||||
m_catId = catId;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onProgressUpdate(Integer... progress) {
|
||||
m_activity.setProgress(Math.round((((float)progress[0] / (float)progress[1]) * 10000)));
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
if (isDetached() || !isAdded()) return;
|
||||
|
||||
if (getView() != null) {
|
||||
View loadingBar = getView().findViewById(R.id.feeds_loading_bar);
|
||||
|
||||
if (loadingBar != null) {
|
||||
loadingBar.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(false);
|
||||
|
||||
if (result != null) {
|
||||
try {
|
||||
JsonArray content = result.getAsJsonArray();
|
||||
if (content != null) {
|
||||
|
||||
Type listType = new TypeToken<List<Feed>>() {}.getType();
|
||||
final List<Feed> feeds = new Gson().fromJson(content, listType);
|
||||
|
||||
m_feeds.clear();
|
||||
|
||||
int catUnread = 0;
|
||||
|
||||
for (Feed f : feeds)
|
||||
if (f.id > -10 || m_catId != -4) { // skip labels for flat feedlist for now
|
||||
if (m_activeCategory != null || f.id >= 0) {
|
||||
m_feeds.add(f);
|
||||
catUnread += f.unread;
|
||||
}
|
||||
}
|
||||
|
||||
sortFeeds();
|
||||
|
||||
if (m_activeCategory == null) {
|
||||
Feed feed = new Feed(-1, "Special", true);
|
||||
feed.unread = catUnread;
|
||||
|
||||
m_feeds.add(0, feed);
|
||||
m_adapter.notifyDataSetChanged();
|
||||
|
||||
}
|
||||
|
||||
if (m_enableParentBtn && m_activeCategory != null && m_activeCategory.id >= 0 && m_feeds.size() > 0) {
|
||||
Feed feed = new Feed(m_activeCategory.id, m_activeCategory.title, true);
|
||||
feed.unread = catUnread;
|
||||
feed.always_display_as_feed = true;
|
||||
feed.display_title = getString(R.string.feed_all_articles);
|
||||
|
||||
m_feeds.add(0, feed);
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
/*if (m_feeds.size() == 0)
|
||||
setLoadingStatus(R.string.no_feeds_to_display, false);
|
||||
else */
|
||||
|
||||
//m_activity.setLoadingStatus(R.string.blank, false);
|
||||
//m_adapter.notifyDataSetChanged(); (done by sortFeeds)
|
||||
|
||||
/* if (m_enableFeedIcons && !m_feedIconsChecked && Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState()))
|
||||
getFeedIcons(); */
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
if (m_lastError == ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
|
||||
if (m_lastErrorMessage != null) {
|
||||
m_activity.toast(getString(getErrorMessage()) + "\n" + m_lastErrorMessage);
|
||||
} else {
|
||||
m_activity.toast(getErrorMessage());
|
||||
}
|
||||
|
||||
//m_activity.setLoadingStatus(getErrorMessage(), false);
|
||||
}
|
||||
}
|
||||
getLoaderManager().restartLoader(0, null, this).forceLoad();
|
||||
}
|
||||
|
||||
private class FeedListAdapter extends ArrayAdapter<Feed> {
|
||||
@ -612,8 +503,8 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
if (!m_activity.isSmallScreen() && m_selectedFeed != null && feed.id == m_selectedFeed.id) {
|
||||
return VIEW_SELECTED;
|
||||
} else {
|
||||
return VIEW_NORMAL;
|
||||
}
|
||||
return VIEW_NORMAL;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
@ -624,13 +515,13 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
|
||||
if (v == null) {
|
||||
int layoutId = R.layout.feeds_row;
|
||||
|
||||
|
||||
switch (getItemViewType(position)) {
|
||||
case VIEW_SELECTED:
|
||||
layoutId = R.layout.feeds_row_selected;
|
||||
break;
|
||||
}
|
||||
|
||||
|
||||
LayoutInflater vi = (LayoutInflater)getActivity().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
|
||||
v = vi.inflate(layoutId, null);
|
||||
|
||||
@ -685,16 +576,16 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
tu.setText(String.valueOf(feed.unread));
|
||||
tu.setVisibility((feed.unread > 0) ? View.VISIBLE : View.INVISIBLE);
|
||||
}
|
||||
|
||||
|
||||
/*ImageButton ib = (ImageButton) v.findViewById(R.id.feed_menu_button);
|
||||
|
||||
|
||||
if (ib != null) {
|
||||
ib.setOnClickListener(new OnClickListener() {
|
||||
ib.setOnClickListener(new OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
getActivity().openContextMenu(v);
|
||||
}
|
||||
});
|
||||
});
|
||||
}*/
|
||||
|
||||
return v;
|
||||
@ -727,95 +618,6 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
// adapter missing
|
||||
}
|
||||
}
|
||||
|
||||
/* public class GetIconsTask extends AsyncTask<FeedList, Integer, Integer> {
|
||||
|
||||
private String m_baseUrl;
|
||||
|
||||
public GetIconsTask(String baseUrl) {
|
||||
m_baseUrl = baseUrl.trim();
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Integer doInBackground(FeedList... params) {
|
||||
|
||||
FeedList localList = new FeedList();
|
||||
|
||||
try {
|
||||
localList.addAll(params[0]);
|
||||
|
||||
File storage = m_activity.getExternalCacheDir();
|
||||
final File iconPath = new File(storage.getAbsolutePath() + ICON_PATH);
|
||||
if (!iconPath.exists()) iconPath.mkdirs();
|
||||
|
||||
if (iconPath.exists()) {
|
||||
for (Feed feed : localList) {
|
||||
if (feed.id > 0 && feed.has_icon && !feed.is_cat) {
|
||||
File outputFile = new File(iconPath.getAbsolutePath() + "/" + feed.id + ".ico");
|
||||
String fetchUrl = m_baseUrl + "/" + feed.id + ".ico";
|
||||
|
||||
if (!outputFile.exists()) {
|
||||
downloadFile(fetchUrl, outputFile.getAbsolutePath());
|
||||
Thread.sleep(2000);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (Exception e) {
|
||||
Log.d(TAG, "Error while downloading feed icons");
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
protected void downloadFile(String fetchUrl, String outputFile) {
|
||||
AndroidHttpClient client = AndroidHttpClient.newInstance("Tiny Tiny RSS");
|
||||
|
||||
try {
|
||||
URL url = new URL(fetchUrl);
|
||||
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
|
||||
|
||||
conn.setConnectTimeout(1000);
|
||||
conn.setReadTimeout(5000);
|
||||
|
||||
Log.d(TAG, "[downloadFile] " + url);
|
||||
|
||||
String httpLogin = m_prefs.getString("http_login", "");
|
||||
String httpPassword = m_prefs.getString("http_password", "");
|
||||
|
||||
if (httpLogin.length() > 0) {
|
||||
conn.setRequestProperty("Authorization", "Basic " +
|
||||
Base64.encodeToString((httpLogin + ":" + httpPassword).getBytes("UTF-8"), Base64.NO_WRAP));
|
||||
}
|
||||
|
||||
InputStream content = conn.getInputStream();
|
||||
|
||||
BufferedInputStream is = new BufferedInputStream(content, 1024);
|
||||
FileOutputStream fos = new FileOutputStream(outputFile);
|
||||
|
||||
byte[] buffer = new byte[1024];
|
||||
int len = 0;
|
||||
while ((len = is.read(buffer)) != -1) {
|
||||
fos.write(buffer, 0, len);
|
||||
}
|
||||
|
||||
fos.close();
|
||||
is.close();
|
||||
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
client.close();
|
||||
}
|
||||
|
||||
protected void onPostExecute(Integer result) {
|
||||
if (isDetached()) return;
|
||||
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
|
||||
} */
|
||||
|
||||
@Override
|
||||
public void onSharedPreferenceChanged(SharedPreferences sharedPreferences,
|
||||
@ -835,22 +637,4 @@ public class FeedsFragment extends BaseFeedlistFragment implements OnItemClickLi
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
/* public Feed getSelectedFeed() {
|
||||
return m_selectedFeed;
|
||||
}
|
||||
|
||||
public void setSelectedFeed(Feed feed) {
|
||||
m_selectedFeed = feed;
|
||||
|
||||
if (m_adapter != null) {
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
} */
|
||||
|
||||
/* @Override
|
||||
public void onRefreshStarted(View view) {
|
||||
refresh(false);
|
||||
} */
|
||||
|
||||
}
|
||||
|
19
org.fox.ttrss/src/main/java/org/fox/ttrss/FeedsLoader.java
Normal file
19
org.fox.ttrss/src/main/java/org/fox/ttrss/FeedsLoader.java
Normal file
@ -0,0 +1,19 @@
|
||||
package org.fox.ttrss;
|
||||
|
||||
import android.content.Context;
|
||||
|
||||
import java.util.HashMap;
|
||||
|
||||
class FeedsLoader extends ApiLoader {
|
||||
private int m_catId;
|
||||
|
||||
public FeedsLoader(Context context, HashMap<String, String> params, int catId) {
|
||||
super(context, params);
|
||||
|
||||
m_catId = catId;
|
||||
}
|
||||
|
||||
public int getCatId() {
|
||||
return m_catId;
|
||||
}
|
||||
}
|
@ -36,7 +36,6 @@ import android.view.Display;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.MenuInflater;
|
||||
import android.view.MenuItem;
|
||||
import android.view.MotionEvent;
|
||||
import android.view.View;
|
||||
import android.view.View.OnClickListener;
|
||||
import android.view.ViewGroup;
|
||||
@ -63,7 +62,6 @@ import com.nhaarman.listviewanimations.appearance.simple.SwingBottomInAnimationA
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.DynamicListView;
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.swipedismiss.DismissableManager;
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.swipedismiss.OnDismissCallback;
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.swipedismiss.undo.SimpleSwipeUndoAdapter;
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.swipedismiss.undo.TimedUndoAdapter;
|
||||
import com.nhaarman.listviewanimations.itemmanipulation.swipedismiss.undo.UndoAdapter;
|
||||
import com.nostra13.universalimageloader.core.DisplayImageOptions;
|
||||
@ -100,9 +98,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
public static final int HEADLINES_REQUEST_SIZE = 30;
|
||||
public static final int HEADLINES_BUFFER_MAX = 500;
|
||||
|
||||
//public static final int ARTICLE_SPECIAL_LOADMORE = -1;
|
||||
//public static final int ARTICLE_SPECIAL_TOP_CHANGED = -3;
|
||||
|
||||
private final String TAG = this.getClass().getSimpleName();
|
||||
|
||||
private Feed m_feed;
|
||||
@ -262,157 +257,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
return true;
|
||||
}
|
||||
|
||||
/*@Override
|
||||
public boolean onContextItemSelected(MenuItem item) {
|
||||
AdapterContextMenuInfo info = (AdapterContextMenuInfo) item
|
||||
.getMenuInfo();
|
||||
|
||||
switch (item.getItemId()) {
|
||||
case R.id.set_labels:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
|
||||
if (article != null) {
|
||||
if (m_activity.getApiLevel() != 7) {
|
||||
m_activity.editArticleLabels(article);
|
||||
} else {
|
||||
m_activity.toast(R.string.server_function_not_available);
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
case R.id.article_set_note:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
|
||||
if (article != null) {
|
||||
m_activity.editArticleNote(article);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
||||
case R.id.headlines_article_link_copy:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
|
||||
if (article != null) {
|
||||
m_activity.copyToClipboard(article.link);
|
||||
}
|
||||
}
|
||||
return true;
|
||||
case R.id.headlines_article_link_open:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
|
||||
if (article != null) {
|
||||
m_activity.openUri(Uri.parse(article.link));
|
||||
|
||||
if (article.unread) {
|
||||
article.unread = false;
|
||||
m_activity.saveArticleUnread(article);
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
case R.id.selection_toggle_marked:
|
||||
if (true) {
|
||||
ArticleList selected = getSelectedArticles();
|
||||
|
||||
if (selected.size() > 0) {
|
||||
for (Article a : selected)
|
||||
a.marked = !a.marked;
|
||||
|
||||
m_activity.toggleArticlesMarked(selected);
|
||||
//updateHeadlines();
|
||||
} else {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
if (article != null) {
|
||||
article.marked = !article.marked;
|
||||
m_activity.saveArticleMarked(article);
|
||||
//updateHeadlines();
|
||||
}
|
||||
}
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
return true;
|
||||
case R.id.selection_toggle_published:
|
||||
if (true) {
|
||||
ArticleList selected = getSelectedArticles();
|
||||
|
||||
if (selected.size() > 0) {
|
||||
for (Article a : selected)
|
||||
a.published = !a.published;
|
||||
|
||||
m_activity.toggleArticlesPublished(selected);
|
||||
//updateHeadlines();
|
||||
} else {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
if (article != null) {
|
||||
article.published = !article.published;
|
||||
m_activity.saveArticlePublished(article);
|
||||
//updateHeadlines();
|
||||
}
|
||||
}
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
return true;
|
||||
case R.id.selection_toggle_unread:
|
||||
if (true) {
|
||||
ArticleList selected = getSelectedArticles();
|
||||
|
||||
if (selected.size() > 0) {
|
||||
for (Article a : selected)
|
||||
a.unread = !a.unread;
|
||||
|
||||
m_activity.toggleArticlesUnread(selected);
|
||||
//updateHeadlines();
|
||||
} else {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
if (article != null) {
|
||||
article.unread = !article.unread;
|
||||
m_activity.saveArticleUnread(article);
|
||||
//updateHeadlines();
|
||||
}
|
||||
}
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
return true;
|
||||
case R.id.headlines_share_article:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
if (article != null)
|
||||
m_activity.shareArticle(article);
|
||||
}
|
||||
return true;
|
||||
case R.id.catchup_above:
|
||||
if (true) {
|
||||
Article article = getArticleAtPosition(info.position);
|
||||
if (article != null) {
|
||||
ArticleList articles = getAllArticles();
|
||||
ArticleList tmp = new ArticleList();
|
||||
for (Article a : articles) {
|
||||
if (article.id == a.id)
|
||||
break;
|
||||
|
||||
if (a.unread) {
|
||||
a.unread = false;
|
||||
tmp.add(a);
|
||||
}
|
||||
}
|
||||
if (tmp.size() > 0) {
|
||||
m_activity.toggleArticlesUnread(tmp);
|
||||
//updateHeadlines();
|
||||
}
|
||||
}
|
||||
m_adapter.notifyDataSetChanged();
|
||||
}
|
||||
return true;
|
||||
default:
|
||||
Log.d(TAG, "onContextItemSelected, unhandled id=" + item.getItemId());
|
||||
return super.onContextItemSelected(item);
|
||||
}
|
||||
} */
|
||||
|
||||
public HeadlinesFragment() {
|
||||
super();
|
||||
|
||||
@ -506,12 +350,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
}
|
||||
|
||||
m_listLoadingView = inflater.inflate(R.layout.headlines_row_loadmore, m_list, false);
|
||||
//m_list.addFooterView(m_listLoadingView, null, false);
|
||||
//m_listLoadingView.setVisibility(View.GONE);
|
||||
|
||||
m_topChangedView = inflater.inflate(R.layout.headlines_row_top_changed, m_list, false);
|
||||
//m_list.addFooterView(m_topChangedView, null, false);
|
||||
//m_topChangedView.setVisibility(View.GONE);*/
|
||||
|
||||
if (m_prefs.getBoolean("headlines_mark_read_scroll", false)) {
|
||||
WindowManager wm = (WindowManager) m_activity.getSystemService(Context.WINDOW_SERVICE);
|
||||
@ -539,7 +378,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
m_animationAdapter.setAbsListView(m_list);
|
||||
m_list.setAdapter(m_animationAdapter);
|
||||
|
||||
if (enableSwipeToDismiss) {
|
||||
if (enableSwipeToDismiss && !m_prefs.getBoolean("headlines_mark_read_scroll", false)) {
|
||||
|
||||
TimedUndoAdapter swipeUndoAdapter = new TimedUndoAdapter(m_adapter, m_activity,
|
||||
new OnDismissCallback() {
|
||||
@ -604,32 +443,14 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
|
||||
if (m_adapter != null) m_adapter.notifyDataSetChanged();
|
||||
|
||||
/* if (Application.getInstance().m_activeArticle != null) {
|
||||
m_activeArticle = Application.getInstance().m_activeArticle;
|
||||
Application.getInstance().m_activeArticle = null;
|
||||
} */
|
||||
|
||||
if (m_activeArticle != null) {
|
||||
setActiveArticle(m_activeArticle);
|
||||
}
|
||||
|
||||
/* if (!(m_activity instanceof DetailActivity)) {
|
||||
refresh(false);
|
||||
} */
|
||||
|
||||
if (m_articles.size() == 0) {
|
||||
refresh(false);
|
||||
}
|
||||
|
||||
/* if (m_articles.size() == 0 || !m_feed.equals(Application.getInstance().m_activeFeed)) {
|
||||
if (m_activity.getSupportFragmentManager().findFragmentByTag(CommonActivity.FRAG_ARTICLE) == null) {
|
||||
refresh(false);
|
||||
Application.getInstance().m_activeFeed = m_feed;
|
||||
}
|
||||
} else {
|
||||
notifyUpdated();
|
||||
} */
|
||||
|
||||
m_activity.invalidateOptionsMenu();
|
||||
}
|
||||
|
||||
@ -681,10 +502,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
|
||||
if (m_swipeLayout != null) m_swipeLayout.setRefreshing(true);
|
||||
|
||||
/* if (!m_feed.equals(Application.getInstance().m_activeFeed)) {
|
||||
append = false;
|
||||
} */
|
||||
|
||||
// new stuff may appear on top, scroll back to show it
|
||||
if (!append) {
|
||||
if (getView() != null) {
|
||||
@ -731,11 +548,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
if (m_firstIdChanged) {
|
||||
m_lazyLoadDisabled = true;
|
||||
|
||||
//m_activity.toast(R.string.headlines_row_top_changed);
|
||||
|
||||
//m_topChangedView.setVisibility(View.VISIBLE);
|
||||
//m_articles.add(new Article(ARTICLE_SPECIAL_TOP_CHANGED));
|
||||
|
||||
m_list.addFooterView(m_topChangedView, null, false);
|
||||
}
|
||||
|
||||
@ -758,7 +570,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
//m_listLoadingView.setVisibility(m_amountLoaded == HEADLINES_REQUEST_SIZE ? View.VISIBLE : View.GONE);
|
||||
|
||||
} else {
|
||||
if (m_lastError == ApiError.LOGIN_FAILED) {
|
||||
if (m_lastError == ApiCommon.ApiError.LOGIN_FAILED) {
|
||||
m_activity.login(true);
|
||||
} else {
|
||||
|
||||
@ -767,8 +579,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
} else {
|
||||
m_activity.toast(getErrorMessage());
|
||||
}
|
||||
|
||||
//m_activity.setLoadingStatus(getErrorMessage(), false);
|
||||
}
|
||||
}
|
||||
|
||||
@ -910,9 +720,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
public static final int VIEW_UNREAD = 1;
|
||||
public static final int VIEW_SELECTED = 2;
|
||||
public static final int VIEW_SELECTED_UNREAD = 3;
|
||||
//public static final int VIEW_LOADMORE = 4;
|
||||
//public static final int VIEW_TOP_CHANGED = 4;
|
||||
|
||||
|
||||
public static final int VIEW_COUNT = VIEW_SELECTED_UNREAD + 1;
|
||||
|
||||
private final Integer[] origTitleColors = new Integer[VIEW_COUNT];
|
||||
@ -966,11 +774,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
public int getItemViewType(int position) {
|
||||
Article a = items.get(position);
|
||||
|
||||
/*if (a.id == ARTICLE_SPECIAL_LOADMORE) {
|
||||
return VIEW_LOADMORE; */
|
||||
/*if (a.id == ARTICLE_SPECIAL_TOP_CHANGED) {
|
||||
return VIEW_TOP_CHANGED;
|
||||
} else */ if (m_activeArticle != null && a.id == m_activeArticle.id && a.unread) {
|
||||
if (m_activeArticle != null && a.id == m_activeArticle.id && a.unread) {
|
||||
return VIEW_SELECTED_UNREAD;
|
||||
} else if (m_activeArticle != null && a.id == m_activeArticle.id) {
|
||||
return VIEW_SELECTED;
|
||||
@ -1066,12 +870,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
int layoutId = m_compactLayoutMode ? R.layout.headlines_row_compact : R.layout.headlines_row;
|
||||
|
||||
switch (getItemViewType(position)) {
|
||||
/*case VIEW_LOADMORE:
|
||||
layoutId = R.layout.headlines_row_loadmore;
|
||||
break;
|
||||
case VIEW_TOP_CHANGED:
|
||||
layoutId = R.layout.headlines_row_top_changed;
|
||||
break;*/
|
||||
case VIEW_UNREAD:
|
||||
layoutId = m_compactLayoutMode ? R.layout.headlines_row_unread_compact : R.layout.headlines_row_unread;
|
||||
break;
|
||||
@ -1760,7 +1558,7 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
m_listPreviousVisibleItem = firstVisibleItem;
|
||||
}
|
||||
|
||||
if (!m_refreshInProgress && !m_lazyLoadDisabled && /*m_articles.findById(ARTICLE_SPECIAL_LOADMORE) != null &&*/ firstVisibleItem + visibleItemCount == m_articles.size()) {
|
||||
if (!m_refreshInProgress && !m_lazyLoadDisabled && firstVisibleItem + visibleItemCount == m_articles.size()) {
|
||||
refresh(true);
|
||||
}
|
||||
}
|
||||
@ -1796,14 +1594,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
return -1;
|
||||
}
|
||||
|
||||
/* public int getArticlePosition(Article article) {
|
||||
try {
|
||||
return m_adapter.getPosition(article);
|
||||
} catch (NullPointerException e) {
|
||||
return -1;
|
||||
}
|
||||
} */
|
||||
|
||||
public String getSearchQuery() {
|
||||
return m_searchQuery;
|
||||
}
|
||||
@ -1823,10 +1613,6 @@ public class HeadlinesFragment extends Fragment implements OnItemClickListener,
|
||||
return m_feed;
|
||||
}
|
||||
|
||||
/*public ArticleList getArticles() {
|
||||
return m_articles;
|
||||
}*/
|
||||
|
||||
public void setArticles(ArticleList articles) {
|
||||
m_articles.clear();
|
||||
m_articles.addAll(articles);
|
||||
|
@ -136,7 +136,7 @@ public class OnlineActivity extends CommonActivity {
|
||||
|
||||
@Override
|
||||
public void onCreate(Bundle savedInstanceState) {
|
||||
ApiRequest.disableConnectionReuseIfNecessary();
|
||||
ApiCommon.disableConnectionReuseIfNecessary();
|
||||
|
||||
// we use that before parent onCreate so let's init locally
|
||||
m_prefs = PreferenceManager
|
||||
@ -1184,7 +1184,7 @@ public class OnlineActivity extends CommonActivity {
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
|
||||
ApiRequest.trustAllHosts(m_prefs.getBoolean("ssl_trust_any", false),
|
||||
ApiCommon.trustAllHosts(m_prefs.getBoolean("ssl_trust_any", false),
|
||||
m_prefs.getBoolean("ssl_trust_any_host", false));
|
||||
|
||||
IntentFilter filter = new IntentFilter();
|
||||
@ -1581,7 +1581,7 @@ public class OnlineActivity extends CommonActivity {
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
} else if (m_lastError != ApiError.API_UNKNOWN_METHOD) {
|
||||
} else if (m_lastError != ApiCommon.ApiError.API_UNKNOWN_METHOD) {
|
||||
// Unknown method means old tt-rss, in that case we assume API 0 and continue
|
||||
|
||||
setLoadingStatus(getErrorMessage(), false);
|
||||
|
@ -9,6 +9,7 @@ import android.widget.EditText;
|
||||
|
||||
import com.google.gson.JsonElement;
|
||||
|
||||
import org.fox.ttrss.ApiCommon;
|
||||
import org.fox.ttrss.ApiRequest;
|
||||
import org.fox.ttrss.R;
|
||||
|
||||
@ -95,7 +96,7 @@ public class ShareActivity extends CommonShareActivity {
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
setProgressBarIndeterminateVisibility(false);
|
||||
|
||||
if (m_lastError != ApiError.NO_ERROR) {
|
||||
if (m_lastError != ApiCommon.ApiError.NO_ERROR) {
|
||||
toast(getErrorMessage());
|
||||
} else {
|
||||
toast(R.string.share_article_posted);
|
||||
|
@ -18,6 +18,7 @@ import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
|
||||
import org.fox.ttrss.ApiCommon;
|
||||
import org.fox.ttrss.ApiRequest;
|
||||
import org.fox.ttrss.R;
|
||||
import org.fox.ttrss.types.FeedCategory;
|
||||
@ -168,7 +169,7 @@ public class SubscribeActivity extends CommonShareActivity {
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
m_progressBar.setVisibility(View.INVISIBLE);
|
||||
|
||||
if (m_lastError != ApiError.NO_ERROR) {
|
||||
if (m_lastError != ApiCommon.ApiError.NO_ERROR) {
|
||||
toast(getErrorMessage());
|
||||
} else {
|
||||
try {
|
||||
@ -273,7 +274,7 @@ public class SubscribeActivity extends CommonShareActivity {
|
||||
protected void onPostExecute(JsonElement result) {
|
||||
m_progressBar.setVisibility(View.INVISIBLE);
|
||||
|
||||
if (m_lastError != ApiError.NO_ERROR) {
|
||||
if (m_lastError != ApiCommon.ApiError.NO_ERROR) {
|
||||
toast(getErrorMessage());
|
||||
} else {
|
||||
JsonArray content = result.getAsJsonArray();
|
||||
|
@ -1,5 +1,6 @@
|
||||
package org.fox.ttrss.tasker;
|
||||
|
||||
import org.fox.ttrss.ApiCommon;
|
||||
import org.fox.ttrss.ApiRequest;
|
||||
import org.fox.ttrss.CommonActivity;
|
||||
import org.fox.ttrss.OnlineActivity;
|
||||
@ -80,7 +81,7 @@ public class TaskerReceiver extends BroadcastReceiver {
|
||||
String login = prefs.getString("login", "").trim();
|
||||
String password = prefs.getString("password", "").trim();
|
||||
String ttrssUrl = prefs.getString("ttrss_url", "").trim();
|
||||
ApiRequest.trustAllHosts(prefs.getBoolean("ssl_trust_any", false), prefs.getBoolean("ssl_trust_any_host", false));
|
||||
ApiCommon.trustAllHosts(prefs.getBoolean("ssl_trust_any", false), prefs.getBoolean("ssl_trust_any_host", false));
|
||||
|
||||
if (ttrssUrl.equals("")) {
|
||||
Toast toast = Toast.makeText(fContext, "Could not download articles: not configured?", Toast.LENGTH_SHORT);
|
||||
|
@ -9,8 +9,8 @@ import com.google.gson.JsonElement;
|
||||
import com.google.gson.JsonObject;
|
||||
import com.google.gson.reflect.TypeToken;
|
||||
|
||||
import org.fox.ttrss.ApiCommon;
|
||||
import org.fox.ttrss.ApiRequest;
|
||||
import org.fox.ttrss.HeadlinesFragment;
|
||||
import org.fox.ttrss.OnlineActivity;
|
||||
import org.fox.ttrss.types.Article;
|
||||
import org.fox.ttrss.types.ArticleList;
|
||||
@ -121,7 +121,7 @@ public class HeadlinesRequest extends ApiRequest {
|
||||
}
|
||||
}
|
||||
|
||||
if (m_lastError == ApiError.LOGIN_FAILED) {
|
||||
if (m_lastError == ApiCommon.ApiError.LOGIN_FAILED) {
|
||||
m_activity.login();
|
||||
} else {
|
||||
|
||||
|
@ -86,6 +86,7 @@
|
||||
|
||||
<org.fox.ttrss.util.LessBrokenSwitchPreference
|
||||
android:defaultValue="true"
|
||||
android:dependency="headlines_mark_read_scroll"
|
||||
android:key="headlines_swipe_to_dismiss"
|
||||
android:summary="@string/pref_headlines_swipe_to_dismiss_long"
|
||||
android:title="@string/pref_headlines_swipe_to_dismiss" />
|
||||
@ -103,6 +104,7 @@
|
||||
|
||||
<org.fox.ttrss.util.LessBrokenSwitchPreference
|
||||
android:defaultValue="false"
|
||||
android:disableDependentsState="true"
|
||||
android:key="headlines_mark_read_scroll"
|
||||
android:summary="@string/pref_headlines_mark_read_scroll_long"
|
||||
android:title="@string/pref_headlines_mark_read_scroll" />
|
||||
|
Loading…
Reference in New Issue
Block a user