commit
a6a7310a38
|
@ -14,7 +14,7 @@ dependencies {
|
|||
compile "com.android.support:gridlayout-v7:$supportVersion"
|
||||
compile "com.android.support:cardview-v7:$supportVersion"
|
||||
compile "com.android.support:design:$supportVersion"
|
||||
compile "com.android.support:recyclerview-v7:22.2.+"
|
||||
compile "com.android.support:recyclerview-v7:$supportVersion"
|
||||
compile "org.apache.commons:commons-lang3:$commonslangVersion"
|
||||
compile("org.shredzone.flattr4j:flattr4j-core:$flattr4jVersion") {
|
||||
exclude group: "org.json", module: "json"
|
||||
|
@ -31,9 +31,12 @@ dependencies {
|
|||
compile "io.reactivex:rxjava:$rxJavaVersion"
|
||||
// And ProGuard rules for RxJava!
|
||||
compile "com.artemzin.rxjava:proguard-rules:$rxJavaRulesVersion"
|
||||
compile "com.joanzapata.iconify:android-iconify-fontawesome:2.1.0"
|
||||
compile "com.afollestad:material-dialogs:0.7.8.1"
|
||||
compile "com.yqritc:recyclerview-flexibledivider:1.2.6"
|
||||
compile "com.joanzapata.iconify:android-iconify-fontawesome:$iconifyFontawesomeVersion"
|
||||
compile "com.joanzapata.iconify:android-iconify-material:$iconifyFontawesomeVersion"
|
||||
compile("com.github.afollestad.material-dialogs:commons:$materialDialogsVersion") {
|
||||
transitive = true
|
||||
}
|
||||
compile "com.yqritc:recyclerview-flexibledivider:$recyclerviewFlexibledividerVersion"
|
||||
|
||||
compile "com.github.AntennaPod:AntennaPod-AudioPlayer:$audioPlayerVersion"
|
||||
|
||||
|
|
|
@ -51,6 +51,7 @@ public class MainActivityTest extends ActivityInstrumentationTestCase2<MainActiv
|
|||
adapter.close();
|
||||
|
||||
// override first launch preference
|
||||
// do this BEFORE calling getActivity()!
|
||||
prefs = getInstrumentation().getTargetContext().getSharedPreferences(MainActivity.PREF_NAME, Context.MODE_PRIVATE);
|
||||
prefs.edit().putBoolean(MainActivity.PREF_IS_FIRST_LAUNCH, false).commit();
|
||||
|
||||
|
@ -71,7 +72,8 @@ public class MainActivityTest extends ActivityInstrumentationTestCase2<MainActiv
|
|||
}
|
||||
|
||||
private void openNavDrawer() {
|
||||
solo.clickOnScreen(50, 50);
|
||||
solo.clickOnImageButton(0);
|
||||
getInstrumentation().waitForIdleSync();
|
||||
}
|
||||
|
||||
public void testAddFeed() throws Exception {
|
||||
|
@ -125,7 +127,7 @@ public class MainActivityTest extends ActivityInstrumentationTestCase2<MainActiv
|
|||
assertEquals(solo.getString(R.string.add_feed_label), getActionbarTitle());
|
||||
|
||||
// podcasts
|
||||
ListView list = (ListView)solo.getView(R.id.nav_list);
|
||||
ListView list = (ListView) solo.getView(R.id.nav_list);
|
||||
for (int i = 0; i < uiTestUtils.hostedFeeds.size(); i++) {
|
||||
Feed f = uiTestUtils.hostedFeeds.get(i);
|
||||
solo.clickOnScreen(50, 50); // open nav drawer
|
||||
|
@ -137,7 +139,7 @@ public class MainActivityTest extends ActivityInstrumentationTestCase2<MainActiv
|
|||
}
|
||||
|
||||
private String getActionbarTitle() {
|
||||
return ((MainActivity)solo.getCurrentActivity()).getMainActivtyActionBar().getTitle().toString();
|
||||
return ((MainActivity) solo.getCurrentActivity()).getSupportActionBar().getTitle().toString();
|
||||
}
|
||||
|
||||
@FlakyTest(tolerance = 3)
|
||||
|
@ -185,14 +187,14 @@ public class MainActivityTest extends ActivityInstrumentationTestCase2<MainActiv
|
|||
openNavDrawer();
|
||||
solo.clickLongOnText(solo.getString(R.string.queue_label));
|
||||
solo.waitForDialogToOpen();
|
||||
for(String title : titles) {
|
||||
for (String title : titles) {
|
||||
solo.clickOnText(title);
|
||||
}
|
||||
solo.clickOnText(solo.getString(R.string.confirm_label));
|
||||
solo.waitForDialogToClose();
|
||||
List<String> hidden = UserPreferences.getHiddenDrawerItems();
|
||||
assertEquals(titles.length, hidden.size());
|
||||
for(String tag : MainActivity.NAV_DRAWER_TAGS) {
|
||||
for (String tag : MainActivity.NAV_DRAWER_TAGS) {
|
||||
assertTrue(hidden.contains(tag));
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
package de.test.antennapod.ui;
|
||||
|
||||
import android.annotation.TargetApi;
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.SharedPreferences;
|
||||
|
@ -10,7 +9,6 @@ import android.preference.PreferenceManager;
|
|||
import android.test.ActivityInstrumentationTestCase2;
|
||||
import android.test.FlakyTest;
|
||||
import android.view.View;
|
||||
import android.widget.ImageButton;
|
||||
import android.widget.ListView;
|
||||
|
||||
import com.robotium.solo.Solo;
|
||||
|
@ -21,15 +19,12 @@ import java.util.List;
|
|||
import de.danoeh.antennapod.R;
|
||||
import de.danoeh.antennapod.activity.MainActivity;
|
||||
import de.danoeh.antennapod.core.feed.FeedItem;
|
||||
import de.danoeh.antennapod.core.feed.FeedMedia;
|
||||
import de.danoeh.antennapod.core.preferences.UserPreferences;
|
||||
import de.danoeh.antennapod.core.service.playback.PlaybackService;
|
||||
import de.danoeh.antennapod.core.service.playback.PlayerStatus;
|
||||
import de.danoeh.antennapod.core.storage.DBReader;
|
||||
import de.danoeh.antennapod.core.storage.DBWriter;
|
||||
import de.danoeh.antennapod.core.storage.PodDBAdapter;
|
||||
import de.danoeh.antennapod.core.util.playback.Playable;
|
||||
import de.danoeh.antennapod.core.util.playback.PlaybackController;
|
||||
|
||||
/**
|
||||
* test cases for starting and ending playback from the MainActivity and AudioPlayerActivity
|
||||
|
@ -90,7 +85,7 @@ public class PlaybackSonicTest extends ActivityInstrumentationTestCase2<MainActi
|
|||
}
|
||||
|
||||
private void openNavDrawer() {
|
||||
solo.clickOnScreen(50, 50);
|
||||
solo.clickOnImageButton(0);
|
||||
getInstrumentation().waitForIdleSync();
|
||||
}
|
||||
|
||||
|
|
|
@ -79,9 +79,9 @@ public class PlaybackTest extends ActivityInstrumentationTestCase2<MainActivity>
|
|||
|
||||
super.tearDown();
|
||||
}
|
||||
|
||||
private void openNavDrawer() {
|
||||
solo.clickOnScreen(50, 50);
|
||||
solo.clickOnImageButton(0);
|
||||
getInstrumentation().waitForIdleSync();
|
||||
}
|
||||
|
||||
private void setContinuousPlaybackPreference(boolean value) {
|
||||
|
|
|
@ -1,15 +1,15 @@
|
|||
package de.test.antennapod.ui;
|
||||
|
||||
import android.test.InstrumentationTestCase;
|
||||
import de.danoeh.antennapod.core.feed.Feed;
|
||||
import de.danoeh.antennapod.core.feed.FeedItem;
|
||||
import org.apache.http.HttpStatus;
|
||||
|
||||
import java.io.File;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.URL;
|
||||
import java.util.List;
|
||||
|
||||
import de.danoeh.antennapod.core.feed.Feed;
|
||||
import de.danoeh.antennapod.core.feed.FeedItem;
|
||||
|
||||
/**
|
||||
* Test for the UITestUtils. Makes sure that all URLs are reachable and that the class does not cause any crashes.
|
||||
*/
|
||||
|
@ -55,7 +55,7 @@ public class UITestUtilsTest extends InstrumentationTestCase {
|
|||
conn.setRequestMethod("GET");
|
||||
conn.connect();
|
||||
int rc = conn.getResponseCode();
|
||||
assertEquals(HttpStatus.SC_OK, rc);
|
||||
assertEquals(HttpURLConnection.HTTP_OK, rc);
|
||||
conn.disconnect();
|
||||
}
|
||||
|
||||
|
|
|
@ -1,6 +1,21 @@
|
|||
package de.test.antennapod.util.service.download;
|
||||
|
||||
import java.io.*;
|
||||
import android.support.v4.util.ArrayMap;
|
||||
|
||||
import java.io.BufferedReader;
|
||||
import java.io.ByteArrayInputStream;
|
||||
import java.io.Closeable;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.InputStreamReader;
|
||||
import java.io.OutputStream;
|
||||
import java.io.PrintWriter;
|
||||
import java.io.PushbackInputStream;
|
||||
import java.io.RandomAccessFile;
|
||||
import java.io.UnsupportedEncodingException;
|
||||
import java.net.InetAddress;
|
||||
import java.net.InetSocketAddress;
|
||||
import java.net.ServerSocket;
|
||||
|
@ -14,7 +29,6 @@ import java.text.SimpleDateFormat;
|
|||
import java.util.ArrayList;
|
||||
import java.util.Calendar;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.HashSet;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
|
@ -281,7 +295,7 @@ public abstract class NanoHTTPD {
|
|||
* @return HTTP response, see class Response for details
|
||||
*/
|
||||
public Response serve(IHTTPSession session) {
|
||||
Map<String, String> files = new HashMap<String, String>();
|
||||
Map<String, String> files = new ArrayMap<>();
|
||||
Method method = session.getMethod();
|
||||
if (Method.PUT.equals(method) || Method.POST.equals(method)) {
|
||||
try {
|
||||
|
@ -334,7 +348,7 @@ public abstract class NanoHTTPD {
|
|||
* @return a map of <code>String</code> (parameter name) to <code>List<String></code> (a list of the values supplied).
|
||||
*/
|
||||
protected Map<String, List<String>> decodeParameters(String queryString) {
|
||||
Map<String, List<String>> parms = new HashMap<String, List<String>>();
|
||||
Map<String, List<String>> parms = new ArrayMap<String, List<String>>();
|
||||
if (queryString != null) {
|
||||
StringTokenizer st = new StringTokenizer(queryString, "&");
|
||||
while (st.hasMoreTokens()) {
|
||||
|
@ -549,7 +563,7 @@ public abstract class NanoHTTPD {
|
|||
/**
|
||||
* Headers for the HTTP response. Use addHeader() to add lines.
|
||||
*/
|
||||
private Map<String, String> header = new HashMap<String, String>();
|
||||
private Map<String, String> header = new ArrayMap<String, String>();
|
||||
/**
|
||||
* The request method that spawned this response.
|
||||
*/
|
||||
|
@ -851,7 +865,7 @@ public abstract class NanoHTTPD {
|
|||
this.inputStream = new PushbackInputStream(inputStream, BUFSIZE);
|
||||
this.outputStream = outputStream;
|
||||
String remoteIp = inetAddress.isLoopbackAddress() || inetAddress.isAnyLocalAddress() ? "127.0.0.1" : inetAddress.getHostAddress().toString();
|
||||
headers = new HashMap<String, String>();
|
||||
headers = new ArrayMap<String, String>();
|
||||
|
||||
headers.put("remote-addr", remoteIp);
|
||||
headers.put("http-client-ip", remoteIp);
|
||||
|
@ -895,16 +909,16 @@ public abstract class NanoHTTPD {
|
|||
inputStream.unread(buf, splitbyte, rlen - splitbyte);
|
||||
}
|
||||
|
||||
parms = new HashMap<String, String>();
|
||||
parms = new ArrayMap<String, String>();
|
||||
if(null == headers) {
|
||||
headers = new HashMap<String, String>();
|
||||
headers = new ArrayMap<String, String>();
|
||||
}
|
||||
|
||||
// Create a BufferedReader for parsing the header.
|
||||
BufferedReader hin = new BufferedReader(new InputStreamReader(new ByteArrayInputStream(buf, 0, rlen)));
|
||||
|
||||
// Decode the header into parms and header java properties
|
||||
Map<String, String> pre = new HashMap<String, String>();
|
||||
Map<String, String> pre = new ArrayMap<String, String>();
|
||||
decodeHeader(hin, pre, parms, headers);
|
||||
|
||||
method = Method.lookup(pre.get("method"));
|
||||
|
@ -1102,7 +1116,7 @@ public abstract class NanoHTTPD {
|
|||
throw new ResponseException(Response.Status.BAD_REQUEST, "BAD REQUEST: Content type is multipart/form-data but next chunk does not start with boundary. Usage: GET /example/file.html");
|
||||
}
|
||||
boundarycount++;
|
||||
Map<String, String> item = new HashMap<String, String>();
|
||||
Map<String, String> item = new ArrayMap<String, String>();
|
||||
mpline = in.readLine();
|
||||
while (mpline != null && mpline.trim().length() > 0) {
|
||||
int p = mpline.indexOf(':');
|
||||
|
@ -1117,7 +1131,7 @@ public abstract class NanoHTTPD {
|
|||
throw new ResponseException(Response.Status.BAD_REQUEST, "BAD REQUEST: Content type is multipart/form-data but no content-disposition info found. Usage: GET /example/file.html");
|
||||
}
|
||||
StringTokenizer st = new StringTokenizer(contentDisposition, ";");
|
||||
Map<String, String> disposition = new HashMap<String, String>();
|
||||
Map<String, String> disposition = new ArrayMap<String, String>();
|
||||
while (st.hasMoreTokens()) {
|
||||
String token = st.nextToken().trim();
|
||||
int p = token.indexOf('=');
|
||||
|
@ -1352,7 +1366,7 @@ public abstract class NanoHTTPD {
|
|||
* @author LordFokas
|
||||
*/
|
||||
public class CookieHandler implements Iterable<String> {
|
||||
private HashMap<String, String> cookies = new HashMap<String, String>();
|
||||
private ArrayMap<String, String> cookies = new ArrayMap<String, String>();
|
||||
private ArrayList<Cookie> queue = new ArrayList<Cookie>();
|
||||
|
||||
public CookieHandler(Map<String, String> httpHeaders) {
|
||||
|
|
|
@ -6,6 +6,7 @@ import android.os.StrictMode;
|
|||
|
||||
import com.joanzapata.iconify.Iconify;
|
||||
import com.joanzapata.iconify.fonts.FontAwesomeModule;
|
||||
import com.joanzapata.iconify.fonts.MaterialModule;
|
||||
|
||||
import de.danoeh.antennapod.core.feed.EventDistributor;
|
||||
import de.danoeh.antennapod.core.preferences.PlaybackPreferences;
|
||||
|
@ -62,6 +63,7 @@ public class PodcastApp extends Application {
|
|||
NetworkUtils.init(this);
|
||||
EventDistributor.getInstance();
|
||||
Iconify.with(new FontAwesomeModule());
|
||||
Iconify.with(new MaterialModule());
|
||||
|
||||
SPAUtil.sendSPAppsQueryFeedsIntent(this);
|
||||
}
|
||||
|
|
|
@ -15,12 +15,12 @@ import android.support.v4.app.Fragment;
|
|||
import android.support.v4.app.FragmentManager;
|
||||
import android.support.v4.app.FragmentTransaction;
|
||||
import android.support.v4.widget.DrawerLayout;
|
||||
import android.support.v7.app.ActionBar;
|
||||
import android.support.v7.app.ActionBarActivity;
|
||||
import android.support.v7.app.ActionBarDrawerToggle;
|
||||
import android.support.v7.app.AlertDialog;
|
||||
import android.support.v7.app.AppCompatActivity;
|
||||
import android.support.v7.widget.Toolbar;
|
||||
import android.util.Log;
|
||||
import android.util.TypedValue;
|
||||
import android.view.ContextMenu;
|
||||
import android.view.MenuInflater;
|
||||
import android.view.MenuItem;
|
||||
|
@ -71,7 +71,7 @@ import rx.schedulers.Schedulers;
|
|||
/**
|
||||
* The activity that is shown when the user launches the app.
|
||||
*/
|
||||
public class MainActivity extends ActionBarActivity implements NavDrawerActivity {
|
||||
public class MainActivity extends AppCompatActivity implements NavDrawerActivity {
|
||||
|
||||
private static final String TAG = "MainActivity";
|
||||
|
||||
|
@ -125,7 +125,13 @@ public class MainActivity extends ActionBarActivity implements NavDrawerActivity
|
|||
|
||||
toolbar = (Toolbar) findViewById(R.id.toolbar);
|
||||
setSupportActionBar(toolbar);
|
||||
getSupportActionBar().setElevation(3.0f);
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
|
||||
findViewById(R.id.shadow).setVisibility(View.GONE);
|
||||
int elevation = (int) TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, 4,
|
||||
getResources().getDisplayMetrics());
|
||||
getSupportActionBar().setElevation(elevation);
|
||||
}
|
||||
|
||||
currentTitle = getTitle();
|
||||
|
||||
|
@ -252,10 +258,6 @@ public class MainActivity extends ActionBarActivity implements NavDrawerActivity
|
|||
builder.create().show();
|
||||
}
|
||||
|
||||
public ActionBar getMainActivtyActionBar() {
|
||||
return getSupportActionBar();
|
||||
}
|
||||
|
||||
public boolean isDrawerOpen() {
|
||||
return drawerLayout != null && navDrawer != null && drawerLayout.isDrawerOpen(navDrawer);
|
||||
}
|
||||
|
@ -363,10 +365,6 @@ public class MainActivity extends ActionBarActivity implements NavDrawerActivity
|
|||
getSupportFragmentManager().popBackStack();
|
||||
}
|
||||
|
||||
public Toolbar getToolbar() {
|
||||
return toolbar;
|
||||
}
|
||||
|
||||
private int getSelectedNavListIndex() {
|
||||
String currentFragment = getLastNavFragment();
|
||||
if(currentFragment == null) {
|
||||
|
|
|
@ -39,7 +39,7 @@ public class StorageErrorActivity extends ActionBarActivity {
|
|||
@Override
|
||||
protected void onResume() {
|
||||
super.onResume();
|
||||
if (StorageUtils.storageAvailable(this)) {
|
||||
if (StorageUtils.storageAvailable()) {
|
||||
leaveErrorState();
|
||||
} else {
|
||||
registerReceiver(mediaUpdate, new IntentFilter(
|
||||
|
|
|
@ -5,6 +5,7 @@ import android.graphics.Color;
|
|||
import android.os.Bundle;
|
||||
import android.support.v4.app.ActivityCompat;
|
||||
import android.support.v4.app.Fragment;
|
||||
import android.support.v4.util.ArrayMap;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.Menu;
|
||||
import android.view.MenuInflater;
|
||||
|
@ -22,7 +23,6 @@ import com.joanzapata.iconify.fonts.FontAwesomeIcons;
|
|||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
|
@ -58,7 +58,7 @@ public class EpisodesApplyActionFragment extends Fragment {
|
|||
|
||||
public EpisodesApplyActionFragment() {
|
||||
this.episodes = new ArrayList<>();
|
||||
this.idMap = new HashMap<>();
|
||||
this.idMap = new ArrayMap<>();
|
||||
}
|
||||
|
||||
public void setEpisodes(List<FeedItem> episodes) {
|
||||
|
|
|
@ -45,7 +45,7 @@ public class AddFeedFragment extends Fragment {
|
|||
Button butSearchITunes = (Button) root.findViewById(R.id.butSearchItunes);
|
||||
|
||||
final MainActivity activity = (MainActivity) getActivity();
|
||||
activity.getMainActivtyActionBar().setTitle(R.string.add_feed_label);
|
||||
activity.getSupportActionBar().setTitle(R.string.add_feed_label);
|
||||
|
||||
butSearchITunes.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
|
|
|
@ -10,6 +10,7 @@ import android.support.v4.view.MenuItemCompat;
|
|||
import android.support.v7.widget.LinearLayoutManager;
|
||||
import android.support.v7.widget.RecyclerView;
|
||||
import android.support.v7.widget.SearchView;
|
||||
import android.support.v7.widget.SimpleItemAnimator;
|
||||
import android.util.Log;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.Menu;
|
||||
|
@ -303,7 +304,10 @@ public class AllEpisodesFragment extends Fragment {
|
|||
View root = inflater.inflate(fragmentResource, container, false);
|
||||
|
||||
recyclerView = (RecyclerView) root.findViewById(android.R.id.list);
|
||||
recyclerView.getItemAnimator().setSupportsChangeAnimations(false);
|
||||
RecyclerView.ItemAnimator animator = recyclerView.getItemAnimator();
|
||||
if (animator instanceof SimpleItemAnimator) {
|
||||
((SimpleItemAnimator) animator).setSupportsChangeAnimations(false);
|
||||
}
|
||||
layoutManager = new LinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.setHasFixedSize(true);
|
||||
|
|
|
@ -4,35 +4,33 @@ import android.annotation.TargetApi;
|
|||
import android.content.ClipData;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.res.TypedArray;
|
||||
import android.net.Uri;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.support.annotation.Nullable;
|
||||
import android.support.v4.app.Fragment;
|
||||
import android.support.v4.util.Pair;
|
||||
import android.support.v7.widget.PopupMenu;
|
||||
import android.support.v7.widget.Toolbar;
|
||||
import android.text.TextUtils;
|
||||
import android.text.format.DateUtils;
|
||||
import android.util.Log;
|
||||
import android.view.ContextMenu;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.Menu;
|
||||
import android.view.MenuInflater;
|
||||
import android.view.MenuItem;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.webkit.WebSettings;
|
||||
import android.webkit.WebView;
|
||||
import android.webkit.WebViewClient;
|
||||
import android.widget.Button;
|
||||
import android.widget.ImageButton;
|
||||
import android.widget.ImageView;
|
||||
import android.widget.ProgressBar;
|
||||
import android.widget.TextView;
|
||||
import android.widget.Toast;
|
||||
|
||||
import com.bumptech.glide.Glide;
|
||||
import com.joanzapata.iconify.Iconify;
|
||||
import com.joanzapata.iconify.widget.IconButton;
|
||||
|
||||
import org.apache.commons.lang3.ArrayUtils;
|
||||
|
||||
|
@ -101,7 +99,6 @@ public class ItemFragment extends Fragment {
|
|||
private List<Downloader> downloaderList;
|
||||
|
||||
private ViewGroup root;
|
||||
private View header;
|
||||
private WebView webvDescription;
|
||||
private TextView txtvTitle;
|
||||
private TextView txtvDuration;
|
||||
|
@ -109,10 +106,9 @@ public class ItemFragment extends Fragment {
|
|||
private ImageView imgvCover;
|
||||
private ProgressBar progbarDownload;
|
||||
private ProgressBar progbarLoading;
|
||||
private Button butAction1;
|
||||
private Button butAction2;
|
||||
private ImageButton butMore;
|
||||
private PopupMenu popupMenu;
|
||||
private IconButton butAction1;
|
||||
private IconButton butAction2;
|
||||
private Menu popupMenu;
|
||||
|
||||
private Subscription subscription;
|
||||
|
||||
|
@ -125,7 +121,7 @@ public class ItemFragment extends Fragment {
|
|||
public void onCreate(Bundle savedInstanceState) {
|
||||
super.onCreate(savedInstanceState);
|
||||
setRetainInstance(true);
|
||||
setHasOptionsMenu(false);
|
||||
setHasOptionsMenu(true);
|
||||
|
||||
itemID = getArguments().getLong(ARG_FEEDITEM, -1);
|
||||
}
|
||||
|
@ -134,15 +130,12 @@ public class ItemFragment extends Fragment {
|
|||
@Override
|
||||
public View onCreateView(LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
|
||||
super.onCreateView(inflater, container, savedInstanceState);
|
||||
((MainActivity) getActivity()).getSupportActionBar().setTitle("");
|
||||
Toolbar toolbar = ((MainActivity) getActivity()).getToolbar();
|
||||
View layout = inflater.inflate(R.layout.feeditem_fragment, container, false);
|
||||
|
||||
header = inflater.inflate(R.layout.feeditem_fragment_header, toolbar, false);
|
||||
root = (ViewGroup) layout.findViewById(R.id.content_root);
|
||||
txtvTitle = (TextView) header.findViewById(R.id.txtvTitle);
|
||||
txtvDuration = (TextView) header.findViewById(R.id.txtvDuration);
|
||||
txtvPublished = (TextView) header.findViewById(R.id.txtvPublished);
|
||||
txtvTitle = (TextView) layout.findViewById(R.id.txtvTitle);
|
||||
txtvDuration = (TextView) layout.findViewById(R.id.txtvDuration);
|
||||
txtvPublished = (TextView) layout.findViewById(R.id.txtvPublished);
|
||||
if (Build.VERSION.SDK_INT >= 14) { // ellipsize is causing problems on old versions, see #448
|
||||
txtvTitle.setEllipsize(TextUtils.TruncateAt.END);
|
||||
}
|
||||
|
@ -172,81 +165,43 @@ public class ItemFragment extends Fragment {
|
|||
});
|
||||
registerForContextMenu(webvDescription);
|
||||
|
||||
imgvCover = (ImageView) header.findViewById(R.id.imgvCover);
|
||||
progbarDownload = (ProgressBar) header.findViewById(R.id.progbarDownload);
|
||||
imgvCover = (ImageView) layout.findViewById(R.id.imgvCover);
|
||||
progbarDownload = (ProgressBar) layout.findViewById(R.id.progbarDownload);
|
||||
progbarLoading = (ProgressBar) layout.findViewById(R.id.progbarLoading);
|
||||
butAction1 = (Button) header.findViewById(R.id.butAction1);
|
||||
butAction2 = (Button) header.findViewById(R.id.butAction2);
|
||||
butMore = (ImageButton) header.findViewById(R.id.butMoreActions);
|
||||
popupMenu = new PopupMenu(getActivity(), butMore);
|
||||
butAction1 = (IconButton) layout.findViewById(R.id.butAction1);
|
||||
butAction2 = (IconButton) layout.findViewById(R.id.butAction2);
|
||||
|
||||
butAction1.setOnClickListener(new View.OnClickListener() {
|
||||
DefaultActionButtonCallback actionButtonCallback = new DefaultActionButtonCallback(getActivity());
|
||||
|
||||
@Override
|
||||
|
||||
public void onClick(View v) {
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
actionButtonCallback.onActionButtonPressed(item);
|
||||
FeedMedia media = item.getMedia();
|
||||
if (media != null && media.isDownloaded()) {
|
||||
// playback was started, dialog should close itself
|
||||
((MainActivity) getActivity()).dismissChildFragment();
|
||||
}
|
||||
}
|
||||
}
|
||||
);
|
||||
butAction1.setOnClickListener(v -> {
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
DefaultActionButtonCallback actionButtonCallback = new DefaultActionButtonCallback(getActivity());
|
||||
actionButtonCallback.onActionButtonPressed(item);
|
||||
FeedMedia media = item.getMedia();
|
||||
if (media != null && media.isDownloaded()) {
|
||||
// playback was started, dialog should close itself
|
||||
((MainActivity) getActivity()).dismissChildFragment();
|
||||
}
|
||||
});
|
||||
|
||||
butAction2.setOnClickListener(v -> {
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (item.hasMedia()) {
|
||||
FeedMedia media = item.getMedia();
|
||||
if (!media.isDownloaded()) {
|
||||
DBTasks.playMedia(getActivity(), media, true, true, true);
|
||||
((MainActivity) getActivity()).dismissChildFragment();
|
||||
} else {
|
||||
DBWriter.deleteFeedMediaOfItem(getActivity(), media.getId());
|
||||
}
|
||||
} else if (item.getLink() != null) {
|
||||
Uri uri = Uri.parse(item.getLink());
|
||||
getActivity().startActivity(new Intent(Intent.ACTION_VIEW, uri));
|
||||
}
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
);
|
||||
|
||||
butMore.setOnClickListener(v -> {
|
||||
if (item == null) {
|
||||
return;
|
||||
}
|
||||
popupMenu.getMenu().clear();
|
||||
popupMenu.inflate(R.menu.feeditem_options);
|
||||
if (item.hasMedia()) {
|
||||
FeedItemMenuHandler.onPrepareMenu(getActivity(), popupMenuInterface, item, true, queue);
|
||||
if (item.hasMedia()) {
|
||||
FeedMedia media = item.getMedia();
|
||||
if (!media.isDownloaded()) {
|
||||
DBTasks.playMedia(getActivity(), media, true, true, true);
|
||||
((MainActivity) getActivity()).dismissChildFragment();
|
||||
} else {
|
||||
// these are already available via button1 and button2
|
||||
FeedItemMenuHandler.onPrepareMenu(getActivity(), popupMenuInterface, item, true, queue,
|
||||
R.id.mark_read_item, R.id.visit_website_item);
|
||||
DBWriter.deleteFeedMediaOfItem(getActivity(), media.getId());
|
||||
}
|
||||
popupMenu.show();
|
||||
} else if (item.getLink() != null) {
|
||||
Uri uri = Uri.parse(item.getLink());
|
||||
getActivity().startActivity(new Intent(Intent.ACTION_VIEW, uri));
|
||||
}
|
||||
);
|
||||
|
||||
popupMenu.setOnMenuItemClickListener(menuItem -> {
|
||||
|
||||
try {
|
||||
return FeedItemMenuHandler.onMenuItemClicked(getActivity(), menuItem.getItemId(), item);
|
||||
} catch (DownloadRequestException e) {
|
||||
e.printStackTrace();
|
||||
Toast.makeText(getActivity(), e.getMessage(), Toast.LENGTH_LONG).show();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
return layout;
|
||||
}
|
||||
|
@ -254,8 +209,6 @@ public class ItemFragment extends Fragment {
|
|||
@Override
|
||||
public void onActivityCreated(@Nullable Bundle savedInstanceState) {
|
||||
super.onActivityCreated(savedInstanceState);
|
||||
Toolbar toolbar = ((MainActivity) getActivity()).getToolbar();
|
||||
toolbar.addView(header);
|
||||
load();
|
||||
}
|
||||
|
||||
|
@ -279,7 +232,6 @@ public class ItemFragment extends Fragment {
|
|||
@Override
|
||||
public void onDestroyView() {
|
||||
super.onDestroyView();
|
||||
resetViewState();
|
||||
if(subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
|
@ -289,15 +241,37 @@ public class ItemFragment extends Fragment {
|
|||
}
|
||||
}
|
||||
|
||||
private void resetViewState() {
|
||||
Toolbar toolbar = ((MainActivity) getActivity()).getToolbar();
|
||||
toolbar.removeView(header);
|
||||
@Override
|
||||
public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
|
||||
if(item == null) {
|
||||
return;
|
||||
}
|
||||
inflater.inflate(R.menu.feeditem_options, menu);
|
||||
popupMenu = menu;
|
||||
if (item.hasMedia()) {
|
||||
FeedItemMenuHandler.onPrepareMenu(getActivity(), popupMenuInterface, item, true, queue);
|
||||
} else {
|
||||
// these are already available via button1 and button2
|
||||
FeedItemMenuHandler.onPrepareMenu(getActivity(), popupMenuInterface, item, true, queue,
|
||||
R.id.mark_read_item, R.id.visit_website_item);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean onOptionsItemSelected(MenuItem menuItem) {
|
||||
try {
|
||||
return FeedItemMenuHandler.onMenuItemClicked(getActivity(), menuItem.getItemId(), item);
|
||||
} catch (DownloadRequestException e) {
|
||||
e.printStackTrace();
|
||||
Toast.makeText(getActivity(), e.getMessage(), Toast.LENGTH_LONG).show();
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
private final FeedItemMenuHandler.MenuInterface popupMenuInterface = new FeedItemMenuHandler.MenuInterface() {
|
||||
@Override
|
||||
public void setItemVisibility(int id, boolean visible) {
|
||||
MenuItem item = popupMenu.getMenu().findItem(id);
|
||||
MenuItem item = popupMenu.findItem(id);
|
||||
if (item != null) {
|
||||
item.setVisible(visible);
|
||||
}
|
||||
|
@ -319,7 +293,7 @@ public class ItemFragment extends Fragment {
|
|||
Log.d(TAG, "updateAppearance item is null");
|
||||
return;
|
||||
}
|
||||
|
||||
getActivity().supportInvalidateOptionsMenu();
|
||||
txtvTitle.setText(item.getTitle());
|
||||
|
||||
if (item.getPubDate() != null) {
|
||||
|
@ -347,54 +321,55 @@ public class ItemFragment extends Fragment {
|
|||
}
|
||||
|
||||
FeedMedia media = item.getMedia();
|
||||
String butAction1Icon = null;
|
||||
int butAction1Text = 0;
|
||||
String butAction2Icon = null;
|
||||
int butAction2Text = 0;
|
||||
if (media == null) {
|
||||
TypedArray drawables = getActivity().obtainStyledAttributes(new int[]{R.attr.navigation_accept,
|
||||
R.attr.location_web_site});
|
||||
|
||||
if (!item.isPlayed()) {
|
||||
butAction1.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(0), null, null, null);
|
||||
butAction1.setText(getActivity().getString(R.string.mark_read_label));
|
||||
butAction1.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
butAction1.setVisibility(View.INVISIBLE);
|
||||
butAction1Icon = "{fa-check 24sp}";
|
||||
butAction1Text = R.string.mark_read_label;
|
||||
}
|
||||
|
||||
if (item.getLink() != null) {
|
||||
butAction2.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(1), null, null, null);
|
||||
butAction2.setText(getActivity().getString(R.string.visit_website_label));
|
||||
} else {
|
||||
butAction2.setEnabled(false);
|
||||
butAction2Icon = "{ma-web 24sp}";
|
||||
butAction2Text = R.string.visit_website_label;
|
||||
}
|
||||
|
||||
drawables.recycle();
|
||||
} else {if(media.getDuration() > 0) {
|
||||
} else {
|
||||
if(media.getDuration() > 0) {
|
||||
txtvDuration.setText(Converter.getDurationStringLong(media.getDuration()));
|
||||
}
|
||||
|
||||
boolean isDownloading = DownloadRequester.getInstance().isDownloadingFile(media);
|
||||
TypedArray drawables = getActivity().obtainStyledAttributes(new int[]{R.attr.av_play,
|
||||
R.attr.av_download, R.attr.action_stream, R.attr.content_discard, R.attr.navigation_cancel});
|
||||
|
||||
if (!media.isDownloaded()) {
|
||||
butAction2.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(2), null, null, null);
|
||||
butAction2.setText(getActivity().getString(R.string.stream_label));
|
||||
butAction2Icon = "{md-settings-input-antenna 24sp}";
|
||||
butAction2Text = R.string.stream_label;
|
||||
} else {
|
||||
butAction2.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(3), null, null, null);
|
||||
butAction2.setText(getActivity().getString(R.string.remove_episode_lable));
|
||||
butAction2Icon = "{md-delete 24sp}";
|
||||
butAction2Text = R.string.remove_label;
|
||||
}
|
||||
|
||||
if (isDownloading) {
|
||||
butAction1.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(4), null, null, null);
|
||||
butAction1.setText(getActivity().getString(R.string.cancel_download_label));
|
||||
butAction1Icon = "{md-cancel 24sp}";
|
||||
butAction1Text = R.string.cancel_label;
|
||||
} else if (media.isDownloaded()) {
|
||||
butAction1.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(0), null, null, null);
|
||||
butAction1.setText(getActivity().getString(R.string.play_label));
|
||||
butAction1Icon = "{md-play-arrow 24sp}";
|
||||
butAction1Text = R.string.play_label;
|
||||
} else {
|
||||
butAction1.setCompoundDrawablesWithIntrinsicBounds(drawables.getDrawable(1), null, null, null);
|
||||
butAction1.setText(getActivity().getString(R.string.download_label));
|
||||
butAction1Icon = "{md-file-download 24sp}";
|
||||
butAction1Text = R.string.download_label;
|
||||
}
|
||||
|
||||
drawables.recycle();
|
||||
}
|
||||
if(butAction1Icon != null && butAction1Text != 0) {
|
||||
butAction1.setText(butAction1Icon +"\u0020\u0020" + getActivity().getString(butAction1Text));
|
||||
Iconify.addIcons(butAction1);
|
||||
butAction1.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
butAction1.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
if(butAction2Icon != null && butAction2Text != 0) {
|
||||
butAction2.setText(butAction2Icon +"\u0020\u0020" + getActivity().getString(butAction2Text));
|
||||
Iconify.addIcons(butAction2);
|
||||
butAction2.setVisibility(View.VISIBLE);
|
||||
} else {
|
||||
butAction2.setVisibility(View.INVISIBLE);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -12,7 +12,6 @@ import android.os.Bundle;
|
|||
import android.support.v4.app.ListFragment;
|
||||
import android.support.v4.util.Pair;
|
||||
import android.support.v4.view.MenuItemCompat;
|
||||
import android.support.v7.app.ActionBarActivity;
|
||||
import android.support.v7.widget.SearchView;
|
||||
import android.util.Log;
|
||||
import android.view.ContextMenu;
|
||||
|
@ -145,34 +144,26 @@ public class ItemlistFragment extends ListFragment {
|
|||
@Override
|
||||
public void onStart() {
|
||||
super.onStart();
|
||||
EventDistributor.getInstance().register(contentUpdate);
|
||||
EventBus.getDefault().registerSticky(this);
|
||||
if (viewsCreated && itemsLoaded) {
|
||||
onFragmentLoaded();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStop() {
|
||||
super.onStop();
|
||||
EventDistributor.getInstance().unregister(contentUpdate);
|
||||
EventBus.getDefault().unregister(this);
|
||||
if(subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
Log.d(TAG, "onResume()");
|
||||
EventDistributor.getInstance().register(contentUpdate);
|
||||
EventBus.getDefault().registerSticky(this);
|
||||
((MainActivity)getActivity()).getSupportActionBar().setTitle("");
|
||||
updateProgressBarVisibility();
|
||||
loadItems();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDetach() {
|
||||
super.onDetach();
|
||||
public void onPause() {
|
||||
super.onPause();
|
||||
EventDistributor.getInstance().unregister(contentUpdate);
|
||||
EventBus.getDefault().unregister(this);
|
||||
if(subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
|
@ -368,7 +359,6 @@ public class ItemlistFragment extends ListFragment {
|
|||
@Override
|
||||
public void onViewCreated(View view, Bundle savedInstanceState) {
|
||||
super.onViewCreated(view, savedInstanceState);
|
||||
((ActionBarActivity) getActivity()).getSupportActionBar().setTitle("");
|
||||
|
||||
registerForContextMenu(getListView());
|
||||
|
||||
|
@ -382,7 +372,9 @@ public class ItemlistFragment extends ListFragment {
|
|||
public void onListItemClick(ListView l, View v, int position, long id) {
|
||||
FeedItem selection = adapter.getItem(position - l.getHeaderViewsCount());
|
||||
if (selection != null) {
|
||||
((MainActivity) getActivity()).loadChildFragment(ItemFragment.newInstance(selection.getId()));
|
||||
MainActivity activity = (MainActivity) getActivity();
|
||||
activity.loadChildFragment(ItemFragment.newInstance(selection.getId()));
|
||||
activity.getSupportActionBar().setTitle(feed.getTitle());
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -547,15 +539,12 @@ public class ItemlistFragment extends ListFragment {
|
|||
.dontAnimate()
|
||||
.into(imgvCover);
|
||||
|
||||
butShowInfo.setOnClickListener(new View.OnClickListener() {
|
||||
@Override
|
||||
public void onClick(View v) {
|
||||
if (viewsCreated && itemsLoaded) {
|
||||
Intent startIntent = new Intent(getActivity(), FeedInfoActivity.class);
|
||||
startIntent.putExtra(FeedInfoActivity.EXTRA_FEED_ID,
|
||||
feed.getId());
|
||||
startActivity(startIntent);
|
||||
}
|
||||
butShowInfo.setOnClickListener(v -> {
|
||||
if (viewsCreated && itemsLoaded) {
|
||||
Intent startIntent = new Intent(getActivity(), FeedInfoActivity.class);
|
||||
startIntent.putExtra(FeedInfoActivity.EXTRA_FEED_ID,
|
||||
feed.getId());
|
||||
startActivity(startIntent);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
@ -573,16 +562,13 @@ public class ItemlistFragment extends ListFragment {
|
|||
View header = inflater.inflate(R.layout.more_content_list_footer, lv, false);
|
||||
lv.addFooterView(header);
|
||||
listFooter = new MoreContentListFooterUtil(header);
|
||||
listFooter.setClickListener(new MoreContentListFooterUtil.Listener() {
|
||||
@Override
|
||||
public void onClick() {
|
||||
if (feed != null) {
|
||||
try {
|
||||
DBTasks.loadNextPageOfFeed(getActivity(), feed, false);
|
||||
} catch (DownloadRequestException e) {
|
||||
e.printStackTrace();
|
||||
DownloadRequestErrorDialogCreator.newRequestErrorDialog(getActivity(), e.getMessage());
|
||||
}
|
||||
listFooter.setClickListener(() -> {
|
||||
if (feed != null) {
|
||||
try {
|
||||
DBTasks.loadNextPageOfFeed(getActivity(), feed, false);
|
||||
} catch (DownloadRequestException e) {
|
||||
e.printStackTrace();
|
||||
DownloadRequestErrorDialogCreator.newRequestErrorDialog(getActivity(), e.getMessage());
|
||||
}
|
||||
}
|
||||
});
|
||||
|
@ -629,7 +615,6 @@ public class ItemlistFragment extends ListFragment {
|
|||
if(subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
|
||||
subscription = Observable.fromCallable(() -> loadData())
|
||||
.subscribeOn(Schedulers.newThread())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
|
|
|
@ -2,21 +2,20 @@ package de.danoeh.antennapod.fragment;
|
|||
|
||||
import android.content.Intent;
|
||||
import android.content.res.Resources;
|
||||
import android.os.AsyncTask;
|
||||
import android.os.Bundle;
|
||||
import android.support.v4.app.Fragment;
|
||||
import android.support.v7.widget.SearchView;
|
||||
import android.util.Log;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.AdapterView;
|
||||
import android.widget.GridView;
|
||||
|
||||
import org.apache.http.HttpResponse;
|
||||
import org.apache.http.client.HttpClient;
|
||||
import org.apache.http.client.methods.HttpGet;
|
||||
import org.apache.http.impl.client.DefaultHttpClient;
|
||||
import org.apache.http.util.EntityUtils;
|
||||
import com.squareup.okhttp.OkHttpClient;
|
||||
import com.squareup.okhttp.Request;
|
||||
import com.squareup.okhttp.Response;
|
||||
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
@ -30,13 +29,23 @@ import java.util.List;
|
|||
import de.danoeh.antennapod.R;
|
||||
import de.danoeh.antennapod.activity.OnlineFeedViewActivity;
|
||||
import de.danoeh.antennapod.adapter.itunes.ItunesAdapter;
|
||||
import de.danoeh.antennapod.core.ClientConfig;
|
||||
import de.danoeh.antennapod.core.preferences.UserPreferences;
|
||||
import de.danoeh.antennapod.core.service.download.AntennapodHttpClient;
|
||||
import rx.Observable;
|
||||
import rx.Subscription;
|
||||
import rx.android.schedulers.AndroidSchedulers;
|
||||
import rx.schedulers.Schedulers;
|
||||
|
||||
import static de.danoeh.antennapod.adapter.itunes.ItunesAdapter.Podcast;
|
||||
|
||||
//Searches iTunes store for given string and displays results in a list
|
||||
public class ItunesSearchFragment extends Fragment {
|
||||
final String TAG = "ItunesSearchFragment";
|
||||
|
||||
private static final String TAG = "ItunesSearchFragment";
|
||||
|
||||
private static final String API_URL = "https://itunes.apple.com/search?media=podcast&term=%s";
|
||||
|
||||
/**
|
||||
* Search input field
|
||||
*/
|
||||
|
@ -52,6 +61,8 @@ public class ItunesSearchFragment extends Fragment {
|
|||
*/
|
||||
private List<Podcast> searchResults;
|
||||
|
||||
private Subscription subscription;
|
||||
|
||||
/**
|
||||
* Replace adapter data with provided search results from SearchTask.
|
||||
* @param result List of Podcast objects containing search results
|
||||
|
@ -117,7 +128,7 @@ public class ItunesSearchFragment extends Fragment {
|
|||
//This prevents onQueryTextSubmit() from being called twice when keyboard is used
|
||||
//to submit the query.
|
||||
searchView.clearFocus();
|
||||
new SearchTask(s).execute();
|
||||
search(s);
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -137,77 +148,59 @@ public class ItunesSearchFragment extends Fragment {
|
|||
return view;
|
||||
}
|
||||
|
||||
/**
|
||||
* Search the iTunes store for podcasts using the given query
|
||||
*/
|
||||
class SearchTask extends AsyncTask<Void,Void,Void> {
|
||||
/**
|
||||
* Incomplete iTunes API search URL
|
||||
*/
|
||||
final String apiUrl = "https://itunes.apple.com/search?media=podcast&term=%s";
|
||||
|
||||
/**
|
||||
* Search terms
|
||||
*/
|
||||
final String query;
|
||||
|
||||
/**
|
||||
* Search result
|
||||
*/
|
||||
final List<Podcast> taskData = new ArrayList<>();
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param query Search string
|
||||
*/
|
||||
public SearchTask(String query) {
|
||||
String encodedQuery = null;
|
||||
try {
|
||||
encodedQuery = URLEncoder.encode(query, "UTF-8");
|
||||
} catch(UnsupportedEncodingException e) {
|
||||
// this won't ever be thrown
|
||||
}
|
||||
if(encodedQuery != null) {
|
||||
this.query = encodedQuery;
|
||||
} else {
|
||||
this.query = query; // failsafe
|
||||
}
|
||||
private void search(String query) {
|
||||
if (subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
subscription = rx.Observable.create((Observable.OnSubscribe<List<Podcast>>) subscriber -> {
|
||||
String encodedQuery = null;
|
||||
try {
|
||||
encodedQuery = URLEncoder.encode(query, "UTF-8");
|
||||
} catch (UnsupportedEncodingException e) {
|
||||
// this won't ever be thrown
|
||||
}
|
||||
if (encodedQuery == null) {
|
||||
encodedQuery = query; // failsafe
|
||||
}
|
||||
|
||||
//Get the podcast data
|
||||
@Override
|
||||
protected Void doInBackground(Void... params) {
|
||||
//Spaces in the query need to be replaced with '+' character.
|
||||
String formattedUrl = String.format(API_URL, query).replace(' ', '+');
|
||||
|
||||
//Spaces in the query need to be replaced with '+' character.
|
||||
String formattedUrl = String.format(apiUrl, query).replace(' ', '+');
|
||||
OkHttpClient client = AntennapodHttpClient.getHttpClient();
|
||||
Request.Builder httpReq = new Request.Builder()
|
||||
.url(formattedUrl)
|
||||
.header("User-Agent", ClientConfig.USER_AGENT);
|
||||
List<Podcast> podcasts = new ArrayList<>();
|
||||
try {
|
||||
Response response = client.newCall(httpReq.build()).execute();
|
||||
|
||||
HttpClient client = new DefaultHttpClient();
|
||||
HttpGet get = new HttpGet(formattedUrl);
|
||||
if(response.isSuccessful()) {
|
||||
String resultString = response.body().string();
|
||||
JSONObject result = new JSONObject(resultString);
|
||||
JSONArray j = result.getJSONArray("results");
|
||||
|
||||
try {
|
||||
HttpResponse response = client.execute(get);
|
||||
String resultString = EntityUtils.toString(response.getEntity());
|
||||
JSONObject result = new JSONObject(resultString);
|
||||
JSONArray j = result.getJSONArray("results");
|
||||
|
||||
for (int i = 0; i < j.length(); i++){
|
||||
JSONObject podcastJson = j.getJSONObject(i);
|
||||
Podcast podcast = new Podcast(podcastJson);
|
||||
taskData.add(podcast);
|
||||
}
|
||||
|
||||
} catch (IOException | JSONException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
//Save the data and update the list
|
||||
@Override
|
||||
protected void onPostExecute(Void aVoid) {
|
||||
super.onPostExecute(aVoid);
|
||||
updateData(taskData);
|
||||
}
|
||||
for (int i = 0; i < j.length(); i++) {
|
||||
JSONObject podcastJson = j.getJSONObject(i);
|
||||
Podcast podcast = new Podcast(podcastJson);
|
||||
podcasts.add(podcast);
|
||||
}
|
||||
}
|
||||
else {
|
||||
subscriber.onError(new IOException("Unexpected error: " + response));
|
||||
}
|
||||
} catch (IOException | JSONException e) {
|
||||
Log.e(TAG, Log.getStackTraceString(e));
|
||||
}
|
||||
subscriber.onNext(podcasts);
|
||||
subscriber.onCompleted();
|
||||
})
|
||||
.subscribeOn(Schedulers.newThread())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
.subscribe(podcasts -> {
|
||||
updateData(podcasts);
|
||||
}, error -> {
|
||||
Log.e(TAG, Log.getStackTraceString(error));
|
||||
});
|
||||
}
|
||||
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
package de.danoeh.antennapod.fragment;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.content.res.TypedArray;
|
||||
import android.os.Bundle;
|
||||
import android.support.v4.app.ListFragment;
|
||||
|
@ -14,7 +14,6 @@ import android.view.View;
|
|||
import android.widget.ListView;
|
||||
|
||||
import java.util.List;
|
||||
import java.util.concurrent.atomic.AtomicReference;
|
||||
|
||||
import de.danoeh.antennapod.R;
|
||||
import de.danoeh.antennapod.activity.MainActivity;
|
||||
|
@ -50,16 +49,13 @@ public class PlaybackHistoryFragment extends ListFragment {
|
|||
private boolean itemsLoaded = false;
|
||||
private boolean viewsCreated = false;
|
||||
|
||||
private AtomicReference<Activity> activity = new AtomicReference<Activity>();
|
||||
|
||||
private List<Downloader> downloaderList;
|
||||
|
||||
private Subscription subscription;
|
||||
|
||||
@Override
|
||||
public void onAttach(Activity activity) {
|
||||
super.onAttach(activity);
|
||||
this.activity.set(activity);
|
||||
public void onAttach(Context context) {
|
||||
super.onAttach(context);
|
||||
if (viewsCreated && itemsLoaded) {
|
||||
onFragmentLoaded();
|
||||
}
|
||||
|
@ -123,7 +119,6 @@ public class PlaybackHistoryFragment extends ListFragment {
|
|||
if(subscription != null) {
|
||||
subscription.unsubscribe();
|
||||
}
|
||||
activity.set(null);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -138,7 +133,7 @@ public class PlaybackHistoryFragment extends ListFragment {
|
|||
DownloaderUpdate update = event.update;
|
||||
downloaderList = update.downloaders;
|
||||
if (adapter != null) {
|
||||
adapter.notifyDataSetChanged();
|
||||
adapter.notifyDataSetChanged();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -210,7 +205,8 @@ public class PlaybackHistoryFragment extends ListFragment {
|
|||
// played items shoudln't be transparent for this fragment since, *all* items
|
||||
// in this fragment will, by definition, be played. So it serves no purpose and can make
|
||||
// it harder to read.
|
||||
adapter = new FeedItemlistAdapter(getActivity(), itemAccess, new DefaultActionButtonCallback(activity.get()), true, false);
|
||||
adapter = new FeedItemlistAdapter(getActivity(), itemAccess,
|
||||
new DefaultActionButtonCallback(getActivity()), true, false);
|
||||
setListAdapter(adapter);
|
||||
}
|
||||
setListShown(true);
|
||||
|
|
|
@ -10,6 +10,7 @@ import android.support.v4.view.MenuItemCompat;
|
|||
import android.support.v7.widget.LinearLayoutManager;
|
||||
import android.support.v7.widget.RecyclerView;
|
||||
import android.support.v7.widget.SearchView;
|
||||
import android.support.v7.widget.SimpleItemAnimator;
|
||||
import android.support.v7.widget.helper.ItemTouchHelper;
|
||||
import android.util.Log;
|
||||
import android.view.LayoutInflater;
|
||||
|
@ -365,7 +366,10 @@ public class QueueFragment extends Fragment {
|
|||
View root = inflater.inflate(R.layout.queue_fragment, container, false);
|
||||
infoBar = (TextView) root.findViewById(R.id.info_bar);
|
||||
recyclerView = (RecyclerView) root.findViewById(R.id.recyclerView);
|
||||
recyclerView.getItemAnimator().setSupportsChangeAnimations(false);
|
||||
RecyclerView.ItemAnimator animator = recyclerView.getItemAnimator();
|
||||
if (animator instanceof SimpleItemAnimator) {
|
||||
((SimpleItemAnimator) animator).setSupportsChangeAnimations(false);
|
||||
}
|
||||
layoutManager = new LinearLayoutManager(getActivity());
|
||||
recyclerView.setLayoutManager(layoutManager);
|
||||
recyclerView.addItemDecoration(new HorizontalDividerItemDecoration.Builder(getActivity()).build());
|
||||
|
|
|
@ -45,7 +45,7 @@ public class TagFragment extends PodcastListFragment {
|
|||
@Override
|
||||
public void onActivityCreated(@Nullable Bundle savedInstanceState) {
|
||||
super.onActivityCreated(savedInstanceState);
|
||||
((MainActivity) getActivity()).getMainActivtyActionBar().setTitle(tag.getTitle());
|
||||
((MainActivity) getActivity()).getSupportActionBar().setTitle(tag.getTitle());
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -80,7 +80,7 @@ public class TagListFragment extends ListFragment {
|
|||
@Override
|
||||
public void onResume() {
|
||||
super.onResume();
|
||||
((MainActivity) getActivity()).getMainActivtyActionBar().setTitle(R.string.add_feed_label);
|
||||
((MainActivity) getActivity()).getSupportActionBar().setTitle(R.string.add_feed_label);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -0,0 +1,37 @@
|
|||
package de.danoeh.antennapod.preferences;
|
||||
|
||||
import android.annotation.TargetApi;
|
||||
import android.content.Context;
|
||||
import android.os.Build;
|
||||
import android.preference.CheckBoxPreference;
|
||||
import android.util.AttributeSet;
|
||||
|
||||
import de.danoeh.antennapod.R;
|
||||
|
||||
public class SwitchCompatPreference extends CheckBoxPreference {
|
||||
|
||||
public SwitchCompatPreference(Context context, AttributeSet attrs, int defStyleAttr) {
|
||||
super(context, attrs, defStyleAttr);
|
||||
init();
|
||||
}
|
||||
|
||||
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
|
||||
public SwitchCompatPreference(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
|
||||
super(context, attrs, defStyleAttr, defStyleRes);
|
||||
init();
|
||||
}
|
||||
|
||||
public SwitchCompatPreference(Context context, AttributeSet attrs) {
|
||||
super(context, attrs);
|
||||
init();
|
||||
}
|
||||
|
||||
public SwitchCompatPreference(Context context) {
|
||||
super(context);
|
||||
init();
|
||||
}
|
||||
|
||||
private void init() {
|
||||
setWidgetLayoutResource(R.layout.preference_switch_layout);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,7 @@
|
|||
<shape xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:shape="rectangle">
|
||||
<gradient
|
||||
android:startColor="@android:color/transparent"
|
||||
android:endColor="#40000000"
|
||||
android:angle="90" />
|
||||
</shape>
|
|
@ -1,13 +1,141 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<RelativeLayout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/content_root"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/header"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_horizontal"
|
||||
android:background="?attr/colorPrimary"
|
||||
android:gravity="center_horizontal"
|
||||
android:orientation="vertical"
|
||||
tools:background="@android:color/darker_gray">
|
||||
|
||||
<RelativeLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_horizontal"
|
||||
android:orientation="horizontal"
|
||||
android:layout_marginTop="16dp"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_marginRight="16dp">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/imgvCover"
|
||||
android:layout_width="50dp"
|
||||
android:layout_height="50dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:contentDescription="@string/cover_label"
|
||||
android:gravity="center_vertical"
|
||||
tools:src="@drawable/ic_stat_antenna_default"
|
||||
tools:background="@android:color/holo_green_dark" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvPublished"
|
||||
style="@style/AntennaPod.TextView.ListItemSecondaryTitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_alignParentTop="true"
|
||||
android:layout_alignParentRight="true"
|
||||
android:layout_marginLeft="8dp"
|
||||
tools:text="Jan\n23"
|
||||
tools:background="@android:color/holo_green_dark"
|
||||
android:layout_below="@+id/txtvTitle"/>
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvTitle"
|
||||
style="@style/TextAppearance.AppCompat.Widget.ActionBar.Title"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_alignTop="@id/imgvCover"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_toLeftOf="@id/txtvPublished"
|
||||
android:layout_toRightOf="@id/imgvCover"
|
||||
android:includeFontPadding="false"
|
||||
android:maxLines="5"
|
||||
tools:text="Podcast title"
|
||||
tools:background="@android:color/holo_green_dark" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvDuration"
|
||||
style="@style/AntennaPod.TextView.ListItemSecondaryTitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_toRightOf="@id/imgvCover"
|
||||
android:layout_below="@id/txtvTitle"
|
||||
android:layout_marginLeft="16dp"
|
||||
tools:text="00:42:23"
|
||||
tools:background="@android:color/holo_green_dark"/>
|
||||
|
||||
</RelativeLayout>
|
||||
|
||||
<ProgressBar
|
||||
android:id="@+id/progbarDownload"
|
||||
style="?android:attr/progressBarStyleHorizontal"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginTop="8dp"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_marginRight="16dp"
|
||||
android:visibility="gone" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_marginRight="16dp"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:orientation="horizontal"
|
||||
tools:background="@android:color/holo_blue_bright">
|
||||
|
||||
<com.joanzapata.iconify.widget.IconButton
|
||||
android:id="@+id/butAction1"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginRight="8dp"
|
||||
android:layout_weight="1"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:ellipsize="end"
|
||||
android:gravity="center"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/text_size_small"
|
||||
tools:text="Button 1"
|
||||
tools:background="@android:color/holo_red_light" />
|
||||
|
||||
<com.joanzapata.iconify.widget.IconButton
|
||||
android:id="@+id/butAction2"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginLeft="8dp"
|
||||
android:layout_weight="1"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:ellipsize="end"
|
||||
android:gravity="center"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/text_size_small"
|
||||
tools:text="Button 2"
|
||||
tools:background="@android:color/holo_orange_dark" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<View
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="2dp"
|
||||
android:background="@color/light_gray"/>
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
<WebView
|
||||
android:id="@+id/webvDescription"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_below="@id/header"
|
||||
android:layout_height="match_parent"
|
||||
android:foreground="?android:windowContentOverlay" />
|
||||
|
||||
|
@ -22,4 +150,4 @@
|
|||
android:layout_gravity="center"
|
||||
android:indeterminate="true" />
|
||||
</FrameLayout>
|
||||
</FrameLayout>
|
||||
</RelativeLayout>
|
|
@ -1,136 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/header"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_horizontal"
|
||||
android:background="?attr/colorPrimary"
|
||||
android:gravity="center_horizontal"
|
||||
android:orientation="vertical"
|
||||
tools:background="@android:color/darker_gray">
|
||||
|
||||
|
||||
<RelativeLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center_horizontal"
|
||||
android:orientation="horizontal"
|
||||
android:paddingBottom="0dp">
|
||||
|
||||
<ImageView
|
||||
android:id="@+id/imgvCover"
|
||||
android:layout_width="50dp"
|
||||
android:layout_height="50dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:layout_marginTop="16dp"
|
||||
android:contentDescription="@string/cover_label"
|
||||
android:gravity="center_vertical"
|
||||
tools:src="@drawable/ic_stat_antenna_default"
|
||||
tools:background="@android:color/holo_green_dark" />
|
||||
|
||||
|
||||
<ImageButton
|
||||
android:id="@+id/butMoreActions"
|
||||
android:layout_width="48dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_alignParentRight="true"
|
||||
android:layout_alignParentTop="true"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:contentDescription="@string/butAction_label"
|
||||
android:paddingTop="4dp"
|
||||
android:src="?attr/ic_action_overflow"
|
||||
tools:src="@drawable/ic_info_white_24dp"
|
||||
tools:background="@android:color/holo_green_dark" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvTitle"
|
||||
style="@style/TextAppearance.AppCompat.Widget.ActionBar.Title"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_centerVertical="true"
|
||||
android:layout_marginBottom="8dp"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_marginRight="8dp"
|
||||
android:layout_marginTop="16dp"
|
||||
android:layout_toLeftOf="@id/butMoreActions"
|
||||
android:layout_toRightOf="@id/imgvCover"
|
||||
android:maxLines="5"
|
||||
tools:text="Podcast title"
|
||||
tools:background="@android:color/holo_green_dark" />
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvDuration"
|
||||
style="@style/AntennaPod.TextView.ListItemSecondaryTitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_toRightOf="@id/imgvCover"
|
||||
android:layout_below="@id/txtvTitle"
|
||||
android:layout_marginLeft="16dp"
|
||||
tools:text="00:42:23"
|
||||
tools:background="@android:color/holo_green_dark"/>
|
||||
|
||||
<TextView
|
||||
android:id="@+id/txtvPublished"
|
||||
style="@style/AntennaPod.TextView.ListItemSecondaryTitle"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_toLeftOf="@id/butMoreActions"
|
||||
android:layout_marginRight="8dp"
|
||||
tools:text="Jan 23"
|
||||
tools:background="@android:color/holo_green_dark"
|
||||
android:layout_below="@+id/txtvTitle"/>
|
||||
|
||||
</RelativeLayout>
|
||||
|
||||
<ProgressBar
|
||||
android:id="@+id/progbarDownload"
|
||||
style="?android:attr/progressBarStyleHorizontal"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_marginLeft="16dp"
|
||||
android:layout_marginRight="16dp"
|
||||
android:visibility="invisible" />
|
||||
|
||||
<LinearLayout
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="?attr/actionBarSize"
|
||||
android:layout_marginRight="8dp"
|
||||
android:orientation="horizontal"
|
||||
tools:background="@android:color/holo_blue_bright">
|
||||
|
||||
<Button
|
||||
android:id="@+id/butAction1"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginRight="8dp"
|
||||
android:layout_weight="1"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:ellipsize="end"
|
||||
android:paddingTop="4dp"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/text_size_small"
|
||||
tools:text="Button 1"
|
||||
tools:background="@android:color/holo_red_light" />
|
||||
|
||||
<Button
|
||||
android:id="@+id/butAction2"
|
||||
android:layout_width="0dp"
|
||||
android:layout_height="48dp"
|
||||
android:layout_gravity="center_vertical"
|
||||
android:layout_marginLeft="8dp"
|
||||
android:layout_weight="1"
|
||||
android:background="?attr/selectableItemBackground"
|
||||
android:ellipsize="end"
|
||||
android:paddingTop="4dp"
|
||||
android:textColor="?android:attr/textColorPrimary"
|
||||
android:textSize="@dimen/text_size_small"
|
||||
tools:text="Button 2"
|
||||
tools:background="@android:color/holo_orange_dark" />
|
||||
|
||||
</LinearLayout>
|
||||
|
||||
|
||||
</LinearLayout>
|
|
@ -1,5 +1,6 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<android.support.v4.widget.DrawerLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
<android.support.v4.widget.DrawerLayout
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:id="@+id/drawer_layout"
|
||||
android:layout_width="match_parent"
|
||||
|
@ -10,7 +11,6 @@
|
|||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent">
|
||||
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/playerFragment"
|
||||
android:layout_width="match_parent"
|
||||
|
@ -27,6 +27,14 @@
|
|||
android:background="?attr/colorPrimary"
|
||||
android:minHeight="?attr/actionBarSize"
|
||||
tools:background="@android:color/holo_blue_dark" />
|
||||
|
||||
<View
|
||||
android:id="@+id/shadow"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="4dp"
|
||||
android:layout_below="@id/toolbar"
|
||||
android:background="@drawable/shadow" />
|
||||
|
||||
<FrameLayout
|
||||
android:id="@+id/main_view"
|
||||
android:layout_width="match_parent"
|
||||
|
|
|
@ -0,0 +1,9 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<android.support.v7.widget.SwitchCompat
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
android:id="@android:id/checkbox"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@null"
|
||||
android:clickable="false"
|
||||
android:focusable="false" />
|
|
@ -1,5 +1,7 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
|
||||
<PreferenceScreen
|
||||
xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto">
|
||||
|
||||
<PreferenceCategory android:title="@string/user_interface_label">
|
||||
<com.afollestad.materialdialogs.prefs.MaterialListPreference
|
||||
|
@ -8,7 +10,8 @@
|
|||
android:title="@string/pref_set_theme_title"
|
||||
android:key="prefTheme"
|
||||
android:summary="@string/pref_set_theme_sum"
|
||||
android:defaultValue="0"/>
|
||||
android:defaultValue="0"
|
||||
app:useStockLayout="true"/>
|
||||
<PreferenceScreen
|
||||
android:key="prefDrawerSettings"
|
||||
android:summary="@string/pref_nav_drawer_sum"
|
||||
|
@ -23,34 +26,36 @@
|
|||
android:title="@string/pref_nav_drawer_feed_order_title"
|
||||
android:key="prefDrawerFeedOrder"
|
||||
android:summary="@string/pref_nav_drawer_feed_order_sum"
|
||||
android:defaultValue="0"/>
|
||||
android:defaultValue="0"
|
||||
app:useStockLayout="true"/>
|
||||
<com.afollestad.materialdialogs.prefs.MaterialListPreference
|
||||
android:entryValues="@array/nav_drawer_feed_counter_values"
|
||||
android:entries="@array/nav_drawer_feed_counter_options"
|
||||
android:title="@string/pref_nav_drawer_feed_counter_title"
|
||||
android:key="prefDrawerFeedIndicator"
|
||||
android:summary="@string/pref_nav_drawer_feed_counter_sum"
|
||||
android:defaultValue="0"/>
|
||||
android:defaultValue="0"
|
||||
app:useStockLayout="true"/>
|
||||
</PreferenceScreen>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefExpandNotify"
|
||||
android:summary="@string/pref_expandNotify_sum"
|
||||
android:title="@string/pref_expandNotify_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefPersistNotify"
|
||||
android:summary="@string/pref_persistNotify_sum"
|
||||
android:title="@string/pref_persistNotify_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefLockscreenBackground"
|
||||
android:summary="@string/pref_lockscreen_background_sum"
|
||||
android:title="@string/pref_lockscreen_background_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefShowDownloadReport"
|
||||
|
@ -59,7 +64,7 @@
|
|||
</PreferenceCategory>
|
||||
|
||||
<PreferenceCategory android:title="@string/queue_label">
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefQueueAddToFront"
|
||||
|
@ -69,45 +74,45 @@
|
|||
</PreferenceCategory>
|
||||
|
||||
<PreferenceCategory android:title="@string/playback_pref">
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefPauseOnHeadsetDisconnect"
|
||||
android:summary="@string/pref_pauseOnDisconnect_sum"
|
||||
android:title="@string/pref_pauseOnHeadsetDisconnect_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:dependency="prefPauseOnHeadsetDisconnect"
|
||||
android:key="prefUnpauseOnHeadsetReconnect"
|
||||
android:summary="@string/pref_unpauseOnHeadsetReconnect_sum"
|
||||
android:title="@string/pref_unpauseOnHeadsetReconnect_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:dependency="prefPauseOnHeadsetDisconnect"
|
||||
android:key="prefUnpauseOnBluetoothReconnect"
|
||||
android:summary="@string/pref_unpauseOnBluetoothReconnect_sum"
|
||||
android:title="@string/pref_unpauseOnBluetoothReconnect_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefHardwareForwardButtonSkips"
|
||||
android:summary="@string/pref_hardwareForwardButtonSkips_sum"
|
||||
android:title="@string/pref_hardwareForwardButtonSkips_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefFollowQueue"
|
||||
android:summary="@string/pref_followQueue_sum"
|
||||
android:title="@string/pref_followQueue_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefSkipKeepsEpisode"
|
||||
android:summary="@string/pref_skip_keeps_episodes_sum"
|
||||
android:title="@string/pref_skip_keeps_episodes_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefAutoDelete"
|
||||
|
@ -119,19 +124,20 @@
|
|||
android:entryValues="@array/smart_mark_as_played_values"
|
||||
android:key="prefSmartMarkAsPlayedSecs"
|
||||
android:summary="@string/pref_smart_mark_as_played_sum"
|
||||
android:title="@string/pref_smart_mark_as_played_title"/>
|
||||
android:title="@string/pref_smart_mark_as_played_title"
|
||||
app:useStockLayout="true"/>
|
||||
<Preference
|
||||
android:key="prefPlaybackSpeedLauncher"
|
||||
android:summary="@string/pref_playback_speed_sum"
|
||||
android:title="@string/pref_playback_speed_title" />
|
||||
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefPauseForFocusLoss"
|
||||
android:summary="@string/pref_pausePlaybackForFocusLoss_sum"
|
||||
android:title="@string/pref_pausePlaybackForFocusLoss_title" />
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="true"
|
||||
android:enabled="true"
|
||||
android:key="prefResumeAfterCall"
|
||||
|
@ -144,46 +150,47 @@
|
|||
android:key="prefAutoUpdateIntervall"
|
||||
android:summary="@string/pref_autoUpdateIntervallOrTime_sum"
|
||||
android:title="@string/pref_autoUpdateIntervallOrTime_title"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="true"
|
||||
android:key="prefMobileUpdate"
|
||||
android:summary="@string/pref_mobileUpdate_sum"
|
||||
android:title="@string/pref_mobileUpdate_title"/>
|
||||
|
||||
<com.afollestad.materialdialogs.prefs.MaterialListPreference
|
||||
android:defaultValue="-1"
|
||||
android:entries="@array/episode_cleanup_entries"
|
||||
android:key="prefEpisodeCleanup"
|
||||
android:title="@string/pref_episode_cleanup_title"
|
||||
android:summary="@string/pref_episode_cleanup_summary"
|
||||
android:entryValues="@array/episode_cleanup_values"/>
|
||||
|
||||
android:entryValues="@array/episode_cleanup_values"
|
||||
app:useStockLayout="true"/>
|
||||
<com.afollestad.materialdialogs.prefs.MaterialEditTextPreference
|
||||
android:defaultValue="4"
|
||||
android:inputType="number"
|
||||
android:key="prefParallelDownloads"
|
||||
android:title="@string/pref_parallel_downloads_title"/>
|
||||
android:title="@string/pref_parallel_downloads_title"
|
||||
app:useStockLayout="true"/>
|
||||
<com.afollestad.materialdialogs.prefs.MaterialListPreference
|
||||
android:defaultValue="20"
|
||||
android:entries="@array/episode_cache_size_entries"
|
||||
android:key="prefEpisodeCacheSize"
|
||||
android:title="@string/pref_episode_cache_title"
|
||||
android:entryValues="@array/episode_cache_size_values"/>
|
||||
android:entryValues="@array/episode_cache_size_values"
|
||||
app:useStockLayout="true"/>
|
||||
<PreferenceScreen
|
||||
android:summary="@string/pref_automatic_download_sum"
|
||||
android:key="prefAutoDownloadSettings"
|
||||
android:title="@string/pref_automatic_download_title">
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:key="prefEnableAutoDl"
|
||||
android:title="@string/pref_automatic_download_title"
|
||||
android:defaultValue="false"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:key="prefEnableAutoDownloadOnBattery"
|
||||
android:title="@string/pref_automatic_download_on_battery_title"
|
||||
android:summary="@string/pref_automatic_download_on_battery_sum"
|
||||
android:defaultValue="true"/>
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:key="prefEnableAutoDownloadWifiFilter"
|
||||
android:title="@string/pref_autodl_wifi_filter_title"
|
||||
android:summary="@string/pref_autodl_wifi_filter_sum"/>
|
||||
|
@ -258,7 +265,7 @@
|
|||
</PreferenceCategory>
|
||||
|
||||
<PreferenceCategory android:title="@string/experimental_pref">
|
||||
<CheckBoxPreference
|
||||
<de.danoeh.antennapod.preferences.SwitchCompatPreference
|
||||
android:defaultValue="false"
|
||||
android:enabled="false"
|
||||
android:key="prefSonic"
|
||||
|
|
25
build.gradle
25
build.gradle
|
@ -6,7 +6,7 @@ buildscript {
|
|||
}
|
||||
dependencies {
|
||||
classpath "com.android.tools.build:gradle:1.5.0"
|
||||
classpath "me.tatarka:gradle-retrolambda:3.2.3"
|
||||
classpath "me.tatarka:gradle-retrolambda:3.2.4"
|
||||
classpath "me.tatarka.retrolambda.projectlombok:lombok.ast:0.2.3.a2"
|
||||
|
||||
// Exclude the version that the android plugin depends on.
|
||||
|
@ -36,27 +36,30 @@ subprojects {
|
|||
}
|
||||
|
||||
project.ext {
|
||||
compileSdkVersion = 22
|
||||
buildToolsVersion = "22.0.1"
|
||||
compileSdkVersion = 23
|
||||
buildToolsVersion = "23.0.2"
|
||||
minSdkVersion = 10
|
||||
targetSdkVersion = 22
|
||||
targetSdkVersion = 23
|
||||
|
||||
supportVersion = "22.2.1"
|
||||
supportVersion = "23.1.1"
|
||||
commonsioVersion = "2.4"
|
||||
commonslangVersion = "3.4"
|
||||
eventbusVersion = "2.4.0"
|
||||
flattr4jVersion = "2.12"
|
||||
glideVersion = "3.6.1"
|
||||
jsoupVersion = "1.7.3"
|
||||
rxAndroidVersion = "1.0.1"
|
||||
rxJavaVersion = "1.0.16"
|
||||
rxJavaRulesVersion = "1.0.16.1"
|
||||
okhttpVersion = "2.5.0"
|
||||
iconifyFontawesomeVersion = "2.1.1"
|
||||
materialDialogsVersion = "0.8.5.3@aar"
|
||||
recyclerviewFlexibledividerVersion = "1.2.6"
|
||||
rxAndroidVersion = "1.1.0"
|
||||
rxJavaVersion = "1.1.0"
|
||||
rxJavaRulesVersion = "1.1.0.0"
|
||||
okhttpVersion = "2.7.0"
|
||||
okioVersion = "1.6.0"
|
||||
|
||||
audioPlayerVersion = "v1.0.7"
|
||||
audioPlayerVersion = "v1.0.8"
|
||||
}
|
||||
|
||||
task wrapper(type: Wrapper) {
|
||||
gradleVersion = "2.4"
|
||||
gradleVersion = "2.10"
|
||||
}
|
||||
|
|
|
@ -4,6 +4,10 @@ general:
|
|||
machine:
|
||||
java:
|
||||
version: oraclejdk8
|
||||
dependencies:
|
||||
pre:
|
||||
- echo y | android update sdk --no-ui --all --filter "tools,platform-tools,android-23"
|
||||
- echo y | android update sdk --no-ui --all --filter "build-tools-23.0.2"
|
||||
test:
|
||||
override:
|
||||
- ./gradlew assembleDebug -PdisablePreDex
|
|
@ -46,7 +46,7 @@ dependencies {
|
|||
exclude group: "org.json", module: "json"
|
||||
}
|
||||
compile "commons-io:commons-io:$commonsioVersion"
|
||||
compile "com.jayway.android.robotium:robotium-solo:5.5.2"
|
||||
compile "com.jayway.android.robotium:robotium-solo:5.5.3"
|
||||
compile "org.jsoup:jsoup:$jsoupVersion"
|
||||
compile "com.github.bumptech.glide:glide:$glideVersion"
|
||||
compile "com.github.bumptech.glide:okhttp-integration:1.3.1"
|
||||
|
|
|
@ -10,8 +10,6 @@ import com.squareup.okhttp.RequestBody;
|
|||
import com.squareup.okhttp.Response;
|
||||
import com.squareup.okhttp.ResponseBody;
|
||||
|
||||
import org.apache.http.HttpStatus;
|
||||
import org.apache.http.client.ClientProtocolException;
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
@ -19,6 +17,7 @@ import org.json.JSONObject;
|
|||
import java.io.ByteArrayOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.net.HttpURLConnection;
|
||||
import java.net.MalformedURLException;
|
||||
import java.net.URI;
|
||||
import java.net.URISyntaxException;
|
||||
|
@ -602,10 +601,7 @@ public class GpodnetService {
|
|||
checkStatusCode(response);
|
||||
body = response.body();
|
||||
result = getStringFromResponseBody(body);
|
||||
} catch (ClientProtocolException e) {
|
||||
e.printStackTrace();
|
||||
throw new GpodnetServiceException(e);
|
||||
} catch (IOException e) {
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
throw new GpodnetServiceException(e);
|
||||
} finally {
|
||||
|
@ -652,12 +648,12 @@ public class GpodnetService {
|
|||
private void checkStatusCode(@NonNull Response response)
|
||||
throws GpodnetServiceException {
|
||||
int responseCode = response.code();
|
||||
if (responseCode != HttpStatus.SC_OK) {
|
||||
if (responseCode == HttpStatus.SC_UNAUTHORIZED) {
|
||||
if (responseCode != HttpURLConnection.HTTP_OK) {
|
||||
if (responseCode == HttpURLConnection.HTTP_UNAUTHORIZED) {
|
||||
throw new GpodnetServiceAuthenticationException("Wrong username or password");
|
||||
} else {
|
||||
throw new GpodnetServiceBadStatusCodeException(
|
||||
"Bad response code: " + responseCode, responseCode);
|
||||
throw new GpodnetServiceBadStatusCodeException("Bad response code: "
|
||||
+ responseCode, responseCode);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,12 +1,13 @@
|
|||
package de.danoeh.antennapod.core.gpoddernet.model;
|
||||
|
||||
import android.support.v4.util.ArrayMap;
|
||||
|
||||
import org.apache.commons.lang3.builder.ToStringBuilder;
|
||||
import org.apache.commons.lang3.builder.ToStringStyle;
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
public class GpodnetEpisodeActionPostResponse {
|
||||
|
@ -36,8 +37,8 @@ public class GpodnetEpisodeActionPostResponse {
|
|||
public static GpodnetEpisodeActionPostResponse fromJSONObject(String objectString) throws JSONException {
|
||||
final JSONObject object = new JSONObject(objectString);
|
||||
final long timestamp = object.getLong("timestamp");
|
||||
Map<String, String> updatedUrls = new HashMap<String, String>();
|
||||
JSONArray urls = object.getJSONArray("update_urls");
|
||||
Map<String, String> updatedUrls = new ArrayMap<String, String>(urls.length());
|
||||
for (int i = 0; i < urls.length(); i++) {
|
||||
JSONArray urlPair = urls.getJSONArray(i);
|
||||
updatedUrls.put(urlPair.getString(0), urlPair.getString(1));
|
||||
|
|
|
@ -1,10 +1,11 @@
|
|||
package de.danoeh.antennapod.core.gpoddernet.model;
|
||||
|
||||
import android.support.v4.util.ArrayMap;
|
||||
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
|
@ -37,7 +38,7 @@ public class GpodnetUploadChangesResponse {
|
|||
public static GpodnetUploadChangesResponse fromJSONObject(String objectString) throws JSONException {
|
||||
final JSONObject object = new JSONObject(objectString);
|
||||
final long timestamp = object.getLong("timestamp");
|
||||
Map<String, String> updatedUrls = new HashMap<String, String>();
|
||||
Map<String, String> updatedUrls = new ArrayMap<>();
|
||||
JSONArray urls = object.getJSONArray("update_urls");
|
||||
for (int i = 0; i < urls.length(); i++) {
|
||||
JSONArray urlPair = urls.getJSONArray(i);
|
||||
|
|
|
@ -8,12 +8,12 @@ import android.content.Context;
|
|||
import android.content.Intent;
|
||||
import android.os.IBinder;
|
||||
import android.support.v4.app.NotificationCompat;
|
||||
import android.support.v4.util.ArrayMap;
|
||||
import android.util.Log;
|
||||
import android.util.Pair;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
|
@ -226,7 +226,7 @@ public class GpodnetSyncService extends Service {
|
|||
if(remoteActions.size() == 0) {
|
||||
return;
|
||||
}
|
||||
Map<Pair<String, String>, GpodnetEpisodeAction> localMostRecentPlayAction = new HashMap<Pair<String, String>, GpodnetEpisodeAction>();
|
||||
Map<Pair<String, String>, GpodnetEpisodeAction> localMostRecentPlayAction = new ArrayMap<>();
|
||||
for(GpodnetEpisodeAction action : localActions) {
|
||||
Pair key = new Pair(action.getPodcast(), action.getEpisode());
|
||||
GpodnetEpisodeAction mostRecent = localMostRecentPlayAction.get(key);
|
||||
|
@ -238,7 +238,7 @@ public class GpodnetSyncService extends Service {
|
|||
}
|
||||
|
||||
// make sure more recent local actions are not overwritten by older remote actions
|
||||
Map<Pair<String, String>, GpodnetEpisodeAction> mostRecentPlayAction = new HashMap<Pair<String, String>, GpodnetEpisodeAction>();
|
||||
Map<Pair<String, String>, GpodnetEpisodeAction> mostRecentPlayAction = new ArrayMap<>();
|
||||
for (GpodnetEpisodeAction action : remoteActions) {
|
||||
switch (action.getAction()) {
|
||||
case NEW:
|
||||
|
|
|
@ -1,54 +0,0 @@
|
|||
package de.danoeh.antennapod.core.service.download;
|
||||
|
||||
import android.util.Log;
|
||||
import de.danoeh.antennapod.core.BuildConfig;
|
||||
import org.apache.http.Header;
|
||||
import org.apache.http.HttpResponse;
|
||||
import org.apache.http.impl.client.DefaultRedirectHandler;
|
||||
import org.apache.http.protocol.HttpContext;
|
||||
|
||||
import java.net.URI;
|
||||
|
||||
public class APRedirectHandler extends DefaultRedirectHandler {
|
||||
// Identifier for logger
|
||||
private static final String TAG = "APRedirectHandler";
|
||||
// Header field, which has to be potentially fixed
|
||||
private static final String LOC = "Location";
|
||||
// Regular expressions for character strings, which should not appear in URLs
|
||||
private static final String CHi[] = { "\\{", "\\}", "\\|", "\\\\", "\\^", "~", "\\[", "\\]", "\\`"};
|
||||
private static final String CHo[] = { "%7B", "%7D", "%7C", "%5C", "%5E", "%7E", "%5B", "%5D", "%60"};
|
||||
|
||||
/**
|
||||
* Workaround for broken URLs in redirection.
|
||||
* Proper solution involves LaxRedirectStrategy() which is not available in
|
||||
* current API yet.
|
||||
*/
|
||||
@Override
|
||||
public URI getLocationURI(HttpResponse response, HttpContext context)
|
||||
throws org.apache.http.ProtocolException {
|
||||
|
||||
Header h[] = response.getHeaders(LOC);
|
||||
if (h.length>0) {
|
||||
String s = h[0].getValue();
|
||||
|
||||
// Fix broken URL
|
||||
for(int i=0; i<CHi.length;i++)
|
||||
s = s.replaceAll(CHi[i], CHo[i]);
|
||||
|
||||
// If anything had to be fixed, then replace the header
|
||||
if (!s.equals(h[0].getValue()))
|
||||
{
|
||||
if (BuildConfig.DEBUG)
|
||||
Log.d(TAG, "Original URL: " + h[0].getValue());
|
||||
|
||||
response.setHeader(LOC, s);
|
||||
|
||||
if (BuildConfig.DEBUG)
|
||||
Log.d(TAG, "Fixed URL: " + s);
|
||||
}
|
||||
}
|
||||
|
||||
// call DefaultRedirectHandler with fixed URL
|
||||
return super.getLocationURI(response, context);
|
||||
}
|
||||
}
|
|
@ -22,7 +22,6 @@ import android.util.Log;
|
|||
import android.webkit.URLUtil;
|
||||
|
||||
import org.apache.commons.io.FileUtils;
|
||||
import org.apache.http.HttpStatus;
|
||||
import org.xml.sax.SAXException;
|
||||
|
||||
import java.io.File;
|
||||
|
@ -187,7 +186,7 @@ public class DownloadService extends Service {
|
|||
if (status.getReason() == DownloadError.ERROR_UNAUTHORIZED) {
|
||||
postAuthenticationNotification(downloader.getDownloadRequest());
|
||||
} else if (status.getReason() == DownloadError.ERROR_HTTP_DATA_ERROR
|
||||
&& Integer.valueOf(status.getReasonDetailed()) == HttpStatus.SC_REQUESTED_RANGE_NOT_SATISFIABLE) {
|
||||
&& Integer.valueOf(status.getReasonDetailed()) == 416) {
|
||||
|
||||
Log.d(TAG, "Requested invalid range, restarting download from the beginning");
|
||||
FileUtils.deleteQuietly(new File(downloader.getDownloadRequest().getDestination()));
|
||||
|
|
|
@ -11,7 +11,6 @@ import com.squareup.okhttp.ResponseBody;
|
|||
import com.squareup.okhttp.internal.http.HttpDate;
|
||||
|
||||
import org.apache.commons.io.IOUtils;
|
||||
import org.apache.http.HttpStatus;
|
||||
|
||||
import java.io.BufferedInputStream;
|
||||
import java.io.File;
|
||||
|
@ -162,7 +161,7 @@ public class HttpDownloader extends Downloader {
|
|||
return;
|
||||
}
|
||||
|
||||
if (!StorageUtils.storageAvailable(ClientConfig.applicationCallbacks.getApplicationInstance())) {
|
||||
if (!StorageUtils.storageAvailable()) {
|
||||
onFail(DownloadError.ERROR_DEVICE_NOT_FOUND, null);
|
||||
return;
|
||||
}
|
||||
|
@ -171,7 +170,7 @@ public class HttpDownloader extends Downloader {
|
|||
|
||||
String contentRangeHeader = (fileExists) ? response.header("Content-Range") : null;
|
||||
|
||||
if (fileExists && response.code() == HttpStatus.SC_PARTIAL_CONTENT
|
||||
if (fileExists && response.code() == HttpURLConnection.HTTP_PARTIAL
|
||||
&& !TextUtils.isEmpty(contentRangeHeader)) {
|
||||
String start = contentRangeHeader.substring("bytes ".length(),
|
||||
contentRangeHeader.indexOf("-"));
|
||||
|
|
|
@ -5,7 +5,6 @@ import android.hardware.Sensor;
|
|||
import android.hardware.SensorEvent;
|
||||
import android.hardware.SensorEventListener;
|
||||
import android.hardware.SensorManager;
|
||||
import android.util.FloatMath;
|
||||
import android.util.Log;
|
||||
|
||||
public class ShakeListener implements SensorEventListener
|
||||
|
@ -50,8 +49,8 @@ public class ShakeListener implements SensorEventListener
|
|||
float gY = event.values[1] / SensorManager.GRAVITY_EARTH;
|
||||
float gZ = event.values[2] / SensorManager.GRAVITY_EARTH;
|
||||
|
||||
float gForce = FloatMath.sqrt(gX*gX + gY*gY + gZ*gZ);
|
||||
if (gForce > 2.25f) {
|
||||
double gForce = Math.sqrt(gX*gX + gY*gY + gZ*gZ);
|
||||
if (gForce > 2.25) {
|
||||
Log.d(TAG, "Detected shake " + gForce);
|
||||
mSleepTimer.onShake();
|
||||
}
|
||||
|
|
|
@ -1,13 +1,13 @@
|
|||
package de.danoeh.antennapod.core.storage;
|
||||
|
||||
import android.database.Cursor;
|
||||
import android.support.v4.util.ArrayMap;
|
||||
import android.util.Log;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collections;
|
||||
import java.util.Comparator;
|
||||
import java.util.Date;
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
|
||||
|
@ -229,7 +229,7 @@ public final class DBReader {
|
|||
for(int i=0, len=itemIds.length; i < len; i++) {
|
||||
ids[i] = String.valueOf(itemIds[i]);
|
||||
}
|
||||
Map<Long,FeedMedia> result = new HashMap<>(itemIds.length);
|
||||
Map<Long,FeedMedia> result = new ArrayMap<>(itemIds.length);
|
||||
Cursor cursor = adapter.getFeedMediaCursor(ids);
|
||||
try {
|
||||
if (cursor.moveToFirst()) {
|
||||
|
@ -871,7 +871,7 @@ public final class DBReader {
|
|||
ids[i] = String.valueOf(imageIds[i]);
|
||||
}
|
||||
Cursor cursor = adapter.getImageCursor(ids);
|
||||
Map<Long, FeedImage> result = new HashMap<>(cursor.getCount());
|
||||
Map<Long, FeedImage> result = new ArrayMap<>(cursor.getCount());
|
||||
try {
|
||||
if ((cursor.getCount() == 0) || !cursor.moveToFirst()) {
|
||||
return Collections.emptyMap();
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
package de.danoeh.antennapod.core.syndication.handler;
|
||||
|
||||
import android.support.v4.util.ArrayMap;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.Map;
|
||||
import java.util.Stack;
|
||||
|
||||
|
@ -32,7 +32,7 @@ public class HandlerState {
|
|||
/**
|
||||
* Namespaces that have been defined so far.
|
||||
*/
|
||||
protected HashMap<String, Namespace> namespaces;
|
||||
protected Map<String, Namespace> namespaces;
|
||||
protected Stack<Namespace> defaultNamespaces;
|
||||
/**
|
||||
* Buffer for saving characters.
|
||||
|
@ -42,16 +42,16 @@ public class HandlerState {
|
|||
/**
|
||||
* Temporarily saved objects.
|
||||
*/
|
||||
protected HashMap<String, Object> tempObjects;
|
||||
protected Map<String, Object> tempObjects;
|
||||
|
||||
public HandlerState(Feed feed) {
|
||||
this.feed = feed;
|
||||
alternateUrls = new LinkedHashMap<String, String>();
|
||||
alternateUrls = new ArrayMap<>();
|
||||
items = new ArrayList<FeedItem>();
|
||||
tagstack = new Stack<SyndElement>();
|
||||
namespaces = new HashMap<String, Namespace>();
|
||||
namespaces = new ArrayMap<>();
|
||||
defaultNamespaces = new Stack<Namespace>();
|
||||
tempObjects = new HashMap<String, Object>();
|
||||
tempObjects = new ArrayMap<>();
|
||||
}
|
||||
|
||||
public Feed getFeed() {
|
||||
|
@ -105,7 +105,7 @@ public class HandlerState {
|
|||
alternateUrls.put(url, title);
|
||||
}
|
||||
|
||||
public HashMap<String, Object> getTempObjects() {
|
||||
public Map<String, Object> getTempObjects() {
|
||||
return tempObjects;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,14 +1,15 @@
|
|||
package de.danoeh.antennapod.core.util;
|
||||
|
||||
import android.support.v4.util.ArrayMap;
|
||||
|
||||
import java.nio.charset.Charset;
|
||||
import java.util.HashMap;
|
||||
|
||||
public class LangUtils {
|
||||
public static final Charset UTF_8 = Charset.forName("UTF-8");
|
||||
|
||||
private static HashMap<String, String> languages;
|
||||
private static ArrayMap<String, String> languages;
|
||||
static {
|
||||
languages = new HashMap<String, String>();
|
||||
languages = new ArrayMap<>();
|
||||
languages.put("af", "Afrikaans");
|
||||
languages.put("sq", "Albanian");
|
||||
languages.put("sq", "Albanian");
|
||||
|
|
|
@ -1,14 +1,12 @@
|
|||
package de.danoeh.antennapod.core.util;
|
||||
|
||||
import android.app.Activity;
|
||||
import android.content.Context;
|
||||
import android.os.Build;
|
||||
import android.os.StatFs;
|
||||
import android.util.Log;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
import de.danoeh.antennapod.core.BuildConfig;
|
||||
import de.danoeh.antennapod.core.ClientConfig;
|
||||
import de.danoeh.antennapod.core.preferences.UserPreferences;
|
||||
|
||||
|
@ -18,13 +16,12 @@ import de.danoeh.antennapod.core.preferences.UserPreferences;
|
|||
public class StorageUtils {
|
||||
private static final String TAG = "StorageUtils";
|
||||
|
||||
public static boolean storageAvailable(Context context) {
|
||||
public static boolean storageAvailable() {
|
||||
File dir = UserPreferences.getDataFolder(null);
|
||||
if (dir != null) {
|
||||
return dir.exists() && dir.canRead() && dir.canWrite();
|
||||
} else {
|
||||
if (BuildConfig.DEBUG)
|
||||
Log.d(TAG, "Storage not available: data folder is null");
|
||||
Log.d(TAG, "Storage not available: data folder is null");
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -39,7 +36,7 @@ public class StorageUtils {
|
|||
* @return true if external storage is available
|
||||
*/
|
||||
public static boolean checkStorageAvailability(Activity activity) {
|
||||
boolean storageAvailable = storageAvailable(activity);
|
||||
boolean storageAvailable = storageAvailable();
|
||||
if (!storageAvailable) {
|
||||
activity.finish();
|
||||
activity.startActivity(ClientConfig.applicationCallbacks.getStorageErrorActivity(activity));
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
package de.danoeh.antennapod.core.util.syndication;
|
||||
|
||||
import android.net.Uri;
|
||||
import android.support.v4.util.ArrayMap;
|
||||
import android.text.TextUtils;
|
||||
|
||||
import org.jsoup.Jsoup;
|
||||
|
@ -10,7 +11,6 @@ import org.jsoup.select.Elements;
|
|||
|
||||
import java.io.File;
|
||||
import java.io.IOException;
|
||||
import java.util.LinkedHashMap;
|
||||
import java.util.Map;
|
||||
|
||||
/**
|
||||
|
@ -46,7 +46,7 @@ public class FeedDiscoverer {
|
|||
}
|
||||
|
||||
private Map<String, String> findLinks(Document document, String baseUrl) {
|
||||
Map<String, String> res = new LinkedHashMap<String, String>();
|
||||
Map<String, String> res = new ArrayMap<>();
|
||||
Elements links = document.head().getElementsByTag("link");
|
||||
for (Element link : links) {
|
||||
String rel = link.attr("rel");
|
||||
|
|
Loading…
Reference in New Issue