diff --git a/app/src/androidTest/java/de/test/antennapod/ui/FeedSettingsTest.java b/app/src/androidTest/java/de/test/antennapod/ui/FeedSettingsTest.java index f3cd99b2c..861c62f1b 100644 --- a/app/src/androidTest/java/de/test/antennapod/ui/FeedSettingsTest.java +++ b/app/src/androidTest/java/de/test/antennapod/ui/FeedSettingsTest.java @@ -2,13 +2,11 @@ package de.test.antennapod.ui; import android.content.Intent; import androidx.test.espresso.intent.rule.IntentsTestRule; -import androidx.test.platform.app.InstrumentationRegistry; import androidx.test.ext.junit.runners.AndroidJUnit4; +import androidx.test.platform.app.InstrumentationRegistry; import de.danoeh.antennapod.R; import de.danoeh.antennapod.activity.MainActivity; -import de.danoeh.antennapod.core.storage.DBReader; import de.danoeh.antennapod.model.feed.Feed; -import de.danoeh.antennapod.model.feed.FeedPreferences; import de.test.antennapod.EspressoTestUtils; import org.junit.After; import org.junit.Before; @@ -18,8 +16,6 @@ import org.junit.runner.RunWith; import static androidx.test.espresso.Espresso.onView; import static androidx.test.espresso.action.ViewActions.click; -import static androidx.test.espresso.action.ViewActions.pressBack; -import static androidx.test.espresso.action.ViewActions.typeText; import static androidx.test.espresso.matcher.ViewMatchers.isDescendantOfA; import static androidx.test.espresso.matcher.ViewMatchers.isDisplayed; import static androidx.test.espresso.matcher.ViewMatchers.isRoot; @@ -28,10 +24,6 @@ import static androidx.test.espresso.matcher.ViewMatchers.withText; import static de.test.antennapod.EspressoTestUtils.clickPreference; import static de.test.antennapod.EspressoTestUtils.waitForView; import static org.hamcrest.Matchers.allOf; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertNotNull; - -import java.io.IOException; @RunWith(AndroidJUnit4.class) public class FeedSettingsTest { @@ -84,52 +76,4 @@ public class FeedSettingsTest { clickPreference(R.string.feed_volume_reduction); onView(withText(R.string.cancel_label)).perform(click()); } - - /** - * Test that modifying a feed's authentication settings results in proper behavior. - * Expect: - * - Feed is refreshed automatically - * - Database has updated username and password - */ - @Test - public void testAuthenticationSettingsUpdate() throws IOException { - onView(isRoot()).perform(waitForView(allOf(isDescendantOfA(withId(R.id.appBar)), - withText(feed.getTitle()), isDisplayed()), 1000)); - - String updatedTitle = "modified episode title"; - String username = "username"; - String password = "password"; - - // update feed hosted on server - feed.getItems().get(0).setTitle(updatedTitle); - uiTestUtils.hostFeed(feed); - - // interact with UI to update authentication settings - updateAuthenticationSettings(username, password); - - // expect feed to have refreshed and be showing new episode title - onView(isRoot()).perform(waitForView(withText(updatedTitle), 5000)); - - // expect database to be updated with correct username and password - Feed updatedFeed = DBReader.getFeed(feed.getId()); - assertNotNull(updatedFeed); - - FeedPreferences updatedFeedPreferences = updatedFeed.getPreferences(); - assertNotNull(updatedFeedPreferences); - - assertEquals("database updated with username", username, updatedFeedPreferences.getUsername()); - assertEquals("database updated with password", password, updatedFeedPreferences.getPassword()); - } - - private void updateAuthenticationSettings(String username, String password) { - onView(withId(R.id.butShowSettings)).perform(click()); - - clickPreference(R.string.authentication_label); - onView(withId(R.id.usernameEditText)).perform(typeText(username)); - onView(withId(R.id.passwordEditText)).perform(typeText(password)); - onView(withText(R.string.confirm_label)).perform(click()); - - onView(isRoot()).perform(pressBack()); - } - } diff --git a/app/src/androidTest/java/de/test/antennapod/ui/PreferencesTest.java b/app/src/androidTest/java/de/test/antennapod/ui/PreferencesTest.java index b790bc005..1b8100392 100644 --- a/app/src/androidTest/java/de/test/antennapod/ui/PreferencesTest.java +++ b/app/src/androidTest/java/de/test/antennapod/ui/PreferencesTest.java @@ -5,7 +5,6 @@ import android.content.SharedPreferences; import android.content.res.Resources; import androidx.annotation.StringRes; import androidx.preference.PreferenceManager; -import androidx.test.espresso.matcher.RootMatchers; import androidx.test.filters.LargeTest; import androidx.test.rule.ActivityTestRule; import de.danoeh.antennapod.R; @@ -25,9 +24,7 @@ import org.junit.Rule; import org.junit.Test; import java.util.Arrays; -import java.util.concurrent.TimeUnit; -import static androidx.test.espresso.Espresso.onData; import static androidx.test.espresso.Espresso.onView; import static androidx.test.espresso.action.ViewActions.click; import static androidx.test.espresso.action.ViewActions.closeSoftKeyboard; @@ -46,7 +43,6 @@ import static androidx.test.espresso.matcher.ViewMatchers.withText; import static de.test.antennapod.EspressoTestUtils.clickPreference; import static de.test.antennapod.EspressoTestUtils.waitForView; import static java.util.concurrent.TimeUnit.MILLISECONDS; -import static org.hamcrest.Matchers.anything; import static org.hamcrest.Matchers.endsWith; import static org.hamcrest.Matchers.not; import static org.junit.Assert.assertTrue; @@ -226,30 +222,6 @@ public class PreferencesTest { .until(() -> pauseForFocusLoss == UserPreferences.shouldPauseForFocusLoss()); } - @Test - public void testDisableUpdateInterval() { - clickPreference(R.string.network_pref); - clickPreference(R.string.feed_refresh_title); - onView(withText(R.string.feed_refresh_never)).perform(click()); - onView(withId(R.id.disableRadioButton)).perform(click()); - onView(withText(R.string.confirm_label)).perform(click()); - Awaitility.await().atMost(1000, MILLISECONDS) - .until(() -> UserPreferences.getUpdateInterval() == 0); - } - - @Test - public void testSetUpdateInterval() { - clickPreference(R.string.network_pref); - clickPreference(R.string.feed_refresh_title); - onView(withId(R.id.intervalRadioButton)).perform(click()); - onView(withId(R.id.spinner)).perform(click()); - int position = 1; // an arbitrary position - onData(anything()).inRoot(RootMatchers.isPlatformPopup()).atPosition(position).perform(click()); - onView(withText(R.string.confirm_label)).perform(click()); - Awaitility.await().atMost(1000, MILLISECONDS) - .until(() -> UserPreferences.getUpdateInterval() == TimeUnit.HOURS.toMillis(2)); - } - @Test public void testSetSequentialDownload() { clickPreference(R.string.network_pref); diff --git a/app/src/main/java/de/danoeh/antennapod/activity/MainActivity.java b/app/src/main/java/de/danoeh/antennapod/activity/MainActivity.java index 9c771f161..7851e5b9a 100644 --- a/app/src/main/java/de/danoeh/antennapod/activity/MainActivity.java +++ b/app/src/main/java/de/danoeh/antennapod/activity/MainActivity.java @@ -22,36 +22,31 @@ import androidx.core.graphics.Insets; import androidx.core.view.ViewCompat; import androidx.core.view.WindowCompat; import androidx.core.view.WindowInsetsCompat; -import com.google.android.material.appbar.MaterialToolbar; import androidx.drawerlayout.widget.DrawerLayout; import androidx.fragment.app.Fragment; import androidx.fragment.app.FragmentContainerView; import androidx.fragment.app.FragmentManager; import androidx.fragment.app.FragmentTransaction; import androidx.recyclerview.widget.RecyclerView; +import androidx.work.WorkInfo; +import androidx.work.WorkManager; import com.bumptech.glide.Glide; +import com.google.android.material.appbar.MaterialToolbar; import com.google.android.material.bottomsheet.BottomSheetBehavior; import com.google.android.material.snackbar.Snackbar; - -import de.danoeh.antennapod.core.preferences.ThemeSwitcher; -import de.danoeh.antennapod.fragment.AllEpisodesFragment; -import org.apache.commons.lang3.ArrayUtils; -import org.apache.commons.lang3.Validate; -import org.greenrobot.eventbus.EventBus; -import org.greenrobot.eventbus.Subscribe; -import org.greenrobot.eventbus.ThreadMode; - import de.danoeh.antennapod.R; -import de.danoeh.antennapod.storage.preferences.UserPreferences; +import de.danoeh.antennapod.core.preferences.ThemeSwitcher; import de.danoeh.antennapod.core.receiver.MediaButtonReceiver; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.dialog.RatingDialog; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; import de.danoeh.antennapod.event.MessageEvent; import de.danoeh.antennapod.fragment.AddFeedFragment; +import de.danoeh.antennapod.fragment.AllEpisodesFragment; import de.danoeh.antennapod.fragment.AudioPlayerFragment; import de.danoeh.antennapod.fragment.CompletedDownloadsFragment; -import de.danoeh.antennapod.fragment.InboxFragment; import de.danoeh.antennapod.fragment.FeedItemlistFragment; +import de.danoeh.antennapod.fragment.InboxFragment; import de.danoeh.antennapod.fragment.NavDrawerFragment; import de.danoeh.antennapod.fragment.PlaybackHistoryFragment; import de.danoeh.antennapod.fragment.QueueFragment; @@ -60,10 +55,16 @@ import de.danoeh.antennapod.fragment.SubscriptionFragment; import de.danoeh.antennapod.fragment.TransitionEffect; import de.danoeh.antennapod.playback.cast.CastEnabledActivity; import de.danoeh.antennapod.preferences.PreferenceUpgrader; +import de.danoeh.antennapod.storage.preferences.UserPreferences; import de.danoeh.antennapod.ui.appstartintent.MainActivityStarter; import de.danoeh.antennapod.ui.common.ThemeUtils; import de.danoeh.antennapod.ui.home.HomeFragment; import de.danoeh.antennapod.view.LockableBottomSheetBehavior; +import org.apache.commons.lang3.ArrayUtils; +import org.apache.commons.lang3.Validate; +import org.greenrobot.eventbus.EventBus; +import org.greenrobot.eventbus.Subscribe; +import org.greenrobot.eventbus.ThreadMode; /** * The activity that is shown when the user launches the app. @@ -157,6 +158,21 @@ public class MainActivity extends CastEnabledActivity { sheetBehavior = (LockableBottomSheetBehavior) BottomSheetBehavior.from(bottomSheet); sheetBehavior.setHideable(false); sheetBehavior.setBottomSheetCallback(bottomSheetCallback); + + FeedUpdateManager.restartUpdateAlarm(this, false); + WorkManager.getInstance(this) + .getWorkInfosByTagLiveData(FeedUpdateManager.WORK_TAG_FEED_UPDATE) + .observe(this, workInfos -> { + boolean isRefreshingFeeds = false; + for (WorkInfo workInfo : workInfos) { + if (workInfo.getState() == WorkInfo.State.RUNNING) { + isRefreshingFeeds = true; + } else if (workInfo.getState() == WorkInfo.State.ENQUEUED) { + isRefreshingFeeds = true; + } + } + EventBus.getDefault().postSticky(new FeedUpdateRunningEvent(isRefreshingFeeds)); + }); } @Override @@ -241,9 +257,7 @@ public class MainActivity extends CastEnabledActivity { private void checkFirstLaunch() { SharedPreferences prefs = getSharedPreferences(PREF_NAME, MODE_PRIVATE); if (prefs.getBoolean(PREF_IS_FIRST_LAUNCH, true)) { - // for backward compatibility, we only change defaults for fresh installs - UserPreferences.setUpdateInterval(12); - AutoUpdateManager.restartUpdateAlarm(this); + FeedUpdateManager.restartUpdateAlarm(this, true); SharedPreferences.Editor edit = prefs.edit(); edit.putBoolean(PREF_IS_FIRST_LAUNCH, false); @@ -553,7 +567,7 @@ public class MainActivity extends CastEnabledActivity { drawerLayout.open(); } if (intent.getBooleanExtra(EXTRA_REFRESH_ON_START, false)) { - AutoUpdateManager.runImmediate(this); + FeedUpdateManager.runOnceOrAsk(this); } // to avoid handling the intent twice when the configuration changes setIntent(new Intent(MainActivity.this, MainActivity.class)); diff --git a/app/src/main/java/de/danoeh/antennapod/activity/OnlineFeedViewActivity.java b/app/src/main/java/de/danoeh/antennapod/activity/OnlineFeedViewActivity.java index 50aabbd01..f5f3d28f6 100644 --- a/app/src/main/java/de/danoeh/antennapod/activity/OnlineFeedViewActivity.java +++ b/app/src/main/java/de/danoeh/antennapod/activity/OnlineFeedViewActivity.java @@ -36,7 +36,7 @@ import de.danoeh.antennapod.core.preferences.ThemeSwitcher; import de.danoeh.antennapod.core.service.download.DownloadService; import de.danoeh.antennapod.core.service.download.DownloadRequestCreator; import de.danoeh.antennapod.core.feed.FeedUrlNotFoundException; -import de.danoeh.antennapod.net.download.serviceinterface.DownloadServiceInterface; +import de.danoeh.antennapod.core.storage.DBTasks; import de.danoeh.antennapod.core.service.playback.PlaybackServiceInterface; import de.danoeh.antennapod.core.util.DownloadErrorLabel; import de.danoeh.antennapod.event.FeedListUpdateEvent; @@ -455,10 +455,7 @@ public class OnlineFeedViewActivity extends AppCompatActivity { if (feedInFeedlist()) { openFeed(); } else { - Feed f = new Feed(selectedDownloadUrl, null, feed.getTitle()); - DownloadServiceInterface.get().download(this, false, DownloadRequestCreator.create(f) - .withAuthentication(username, password) - .build()); + DBTasks.updateFeed(this, feed, false); didPressSubscribe = true; handleUpdatedFeedStatus(); } diff --git a/app/src/main/java/de/danoeh/antennapod/activity/OpmlImportActivity.java b/app/src/main/java/de/danoeh/antennapod/activity/OpmlImportActivity.java index 64a6b6632..10a41057c 100644 --- a/app/src/main/java/de/danoeh/antennapod/activity/OpmlImportActivity.java +++ b/app/src/main/java/de/danoeh/antennapod/activity/OpmlImportActivity.java @@ -29,7 +29,7 @@ import de.danoeh.antennapod.core.export.opml.OpmlReader; import de.danoeh.antennapod.core.preferences.ThemeSwitcher; import de.danoeh.antennapod.core.storage.DBTasks; -import de.danoeh.antennapod.net.download.serviceinterface.DownloadServiceInterface; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.databinding.OpmlSelectionBinding; import de.danoeh.antennapod.model.feed.Feed; import io.reactivex.Completable; @@ -101,7 +101,7 @@ public class OpmlImportActivity extends AppCompatActivity { feed.setItems(Collections.emptyList()); DBTasks.updateFeed(this, feed, false); } - DownloadServiceInterface.get().refreshAllFeeds(this, true); + FeedUpdateManager.runOnce(this); }) .subscribeOn(Schedulers.io()) .observeOn(AndroidSchedulers.mainThread()) diff --git a/app/src/main/java/de/danoeh/antennapod/dialog/FeedRefreshIntervalDialog.java b/app/src/main/java/de/danoeh/antennapod/dialog/FeedRefreshIntervalDialog.java deleted file mode 100644 index 3d92fd979..000000000 --- a/app/src/main/java/de/danoeh/antennapod/dialog/FeedRefreshIntervalDialog.java +++ /dev/null @@ -1,117 +0,0 @@ -package de.danoeh.antennapod.dialog; - -import android.content.Context; -import android.content.res.Resources; -import android.os.Build; -import android.text.format.DateFormat; -import android.view.LayoutInflater; -import android.view.View; -import android.widget.ArrayAdapter; -import androidx.appcompat.app.AlertDialog; -import com.google.android.material.dialog.MaterialAlertDialogBuilder; -import de.danoeh.antennapod.R; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; -import de.danoeh.antennapod.databinding.FeedRefreshDialogBinding; -import de.danoeh.antennapod.databinding.ScrollableDialogBinding; -import de.danoeh.antennapod.storage.preferences.UserPreferences; -import java.util.concurrent.TimeUnit; -import org.apache.commons.lang3.ArrayUtils; - -public class FeedRefreshIntervalDialog { - private static final int[] INTERVAL_VALUES_HOURS = {1, 2, 4, 8, 12, 24, 72}; - private final Context context; - private FeedRefreshDialogBinding viewBinding; - - public FeedRefreshIntervalDialog(Context context) { - this.context = context; - } - - public void show() { - MaterialAlertDialogBuilder builder = new MaterialAlertDialogBuilder(context); - builder.setTitle(R.string.feed_refresh_title); - builder.setMessage(R.string.feed_refresh_sum); - ScrollableDialogBinding scrollableDialogBinding = ScrollableDialogBinding.inflate(LayoutInflater.from(context)); - builder.setView(scrollableDialogBinding.getRoot()); - viewBinding = FeedRefreshDialogBinding.inflate(LayoutInflater.from(context)); - scrollableDialogBinding.content.addView(viewBinding.getRoot()); - - ArrayAdapter spinnerArrayAdapter = new ArrayAdapter<>(context, - android.R.layout.simple_spinner_item, buildSpinnerEntries()); - spinnerArrayAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item); - viewBinding.spinner.setAdapter(spinnerArrayAdapter); - viewBinding.timePicker.setIs24HourView(DateFormat.is24HourFormat(context)); - viewBinding.spinner.setSelection(ArrayUtils.indexOf(INTERVAL_VALUES_HOURS, 24)); - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { - viewBinding.timePicker.setHour(8); - viewBinding.timePicker.setMinute(0); - } else { - viewBinding.timePicker.setCurrentHour(8); - viewBinding.timePicker.setCurrentMinute(0); - } - - long currInterval = UserPreferences.getUpdateInterval(); - int[] updateTime = UserPreferences.getUpdateTimeOfDay(); - if (currInterval > 0) { - viewBinding.spinner.setSelection(ArrayUtils.indexOf(INTERVAL_VALUES_HOURS, - (int) TimeUnit.MILLISECONDS.toHours(currInterval))); - viewBinding.intervalRadioButton.setChecked(true); - } else if (updateTime.length == 2 && updateTime[0] >= 0) { - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { - viewBinding.timePicker.setHour(updateTime[0]); - viewBinding.timePicker.setMinute(updateTime[1]); - } else { - viewBinding.timePicker.setCurrentHour(updateTime[0]); - viewBinding.timePicker.setCurrentMinute(updateTime[1]); - } - viewBinding.timeRadioButton.setChecked(true); - } else { - viewBinding.disableRadioButton.setChecked(true); - } - updateVisibility(); - - viewBinding.radioGroup.setOnCheckedChangeListener((radioGroup, i) -> updateVisibility()); - - AlertDialog dialog = builder.show(); - - scrollableDialogBinding.positiveButton.setText(R.string.confirm_label); - scrollableDialogBinding.positiveButton.setOnClickListener(v -> { - dialog.dismiss(); - if (viewBinding.intervalRadioButton.isChecked()) { - UserPreferences.setUpdateInterval(INTERVAL_VALUES_HOURS[viewBinding.spinner.getSelectedItemPosition()]); - AutoUpdateManager.restartUpdateAlarm(context); - } else if (viewBinding.timeRadioButton.isChecked()) { - if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { - UserPreferences.setUpdateTimeOfDay(viewBinding.timePicker.getHour(), - viewBinding.timePicker.getMinute()); - } else { - UserPreferences.setUpdateTimeOfDay(viewBinding.timePicker.getCurrentHour(), - viewBinding.timePicker.getCurrentMinute()); - } - AutoUpdateManager.restartUpdateAlarm(context); - } else if (viewBinding.disableRadioButton.isChecked()) { - UserPreferences.disableAutoUpdate(); - AutoUpdateManager.disableAutoUpdate(context); - } else { - throw new IllegalStateException("Unexpected error."); - } - }); - - scrollableDialogBinding.negativeButton.setText(R.string.cancel_label); - scrollableDialogBinding.negativeButton.setOnClickListener((v) -> dialog.dismiss()); - } - - private String[] buildSpinnerEntries() { - final Resources res = context.getResources(); - String[] entries = new String[INTERVAL_VALUES_HOURS.length]; - for (int i = 0; i < INTERVAL_VALUES_HOURS.length; i++) { - int hours = INTERVAL_VALUES_HOURS[i]; - entries[i] = res.getQuantityString(R.plurals.feed_refresh_every_x_hours, hours, hours); - } - return entries; - } - - private void updateVisibility() { - viewBinding.spinner.setVisibility(viewBinding.intervalRadioButton.isChecked() ? View.VISIBLE : View.GONE); - viewBinding.timePicker.setVisibility(viewBinding.timeRadioButton.isChecked() ? View.VISIBLE : View.GONE); - } -} diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/CompletedDownloadsFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/CompletedDownloadsFragment.java index dbc453301..737975389 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/CompletedDownloadsFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/CompletedDownloadsFragment.java @@ -25,7 +25,7 @@ import de.danoeh.antennapod.core.event.DownloadLogEvent; import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; import de.danoeh.antennapod.core.storage.DBReader; import de.danoeh.antennapod.core.util.FeedItemUtil; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.event.FeedItemEvent; import de.danoeh.antennapod.event.PlayerStatusEvent; import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; @@ -193,7 +193,7 @@ public class CompletedDownloadsFragment extends Fragment @Override public boolean onMenuItemClick(MenuItem item) { if (item.getItemId() == R.id.refresh_item) { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); return true; } else if (item.getItemId() == R.id.action_download_logs) { new DownloadLogFragment().show(getChildFragmentManager(), null); diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/EpisodesListFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/EpisodesListFragment.java index 5ba323372..18bec12ca 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/EpisodesListFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/EpisodesListFragment.java @@ -30,11 +30,11 @@ import de.danoeh.antennapod.core.dialog.ConfirmationDialog; import de.danoeh.antennapod.core.event.DownloadEvent; import de.danoeh.antennapod.core.event.DownloaderUpdate; import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; -import de.danoeh.antennapod.core.service.download.DownloadService; import de.danoeh.antennapod.core.util.FeedItemUtil; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.event.FeedItemEvent; import de.danoeh.antennapod.event.FeedListUpdateEvent; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; import de.danoeh.antennapod.event.PlayerStatusEvent; import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; import de.danoeh.antennapod.event.playback.PlaybackPositionEvent; @@ -123,7 +123,7 @@ public abstract class EpisodesListFragment extends Fragment } final int itemId = item.getItemId(); if (itemId == R.id.refresh_item) { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); return true; } else if (itemId == R.id.action_search) { ((MainActivity) getActivity()).loadChildFragment(SearchFragment.newInstance()); @@ -184,7 +184,7 @@ public abstract class EpisodesListFragment extends Fragment SwipeRefreshLayout swipeRefreshLayout = root.findViewById(R.id.swipeRefresh); swipeRefreshLayout.setDistanceToTriggerSync(getResources().getInteger(R.integer.swipe_refresh_distance)); swipeRefreshLayout.setOnRefreshListener(() -> { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); new Handler(Looper.getMainLooper()).postDelayed(() -> swipeRefreshLayout.setRefreshing(false), getResources().getInteger(R.integer.swipe_to_refresh_duration_in_ms)); }); @@ -455,9 +455,12 @@ public abstract class EpisodesListFragment extends Fragment protected abstract String getPrefName(); protected void updateToolbar() { + } + + @Subscribe(sticky = true, threadMode = ThreadMode.MAIN) + public void onEventMainThread(FeedUpdateRunningEvent event) { if (toolbar.getMenu().findItem(R.id.refresh_item) != null) { - MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), R.id.refresh_item, - DownloadService.isRunning && DownloadService.isDownloadingFeeds()); + MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), R.id.refresh_item, event.isFeedUpdateRunning); } } diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/FeedItemlistFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/FeedItemlistFragment.java index 0b264b5a3..ecc60c411 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/FeedItemlistFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/FeedItemlistFragment.java @@ -33,11 +33,11 @@ import de.danoeh.antennapod.core.event.DownloadEvent; import de.danoeh.antennapod.core.event.DownloaderUpdate; import de.danoeh.antennapod.core.feed.FeedEvent; import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; -import de.danoeh.antennapod.core.service.download.DownloadService; import de.danoeh.antennapod.core.storage.DBReader; import de.danoeh.antennapod.core.storage.DBTasks; import de.danoeh.antennapod.core.util.FeedItemPermutors; import de.danoeh.antennapod.core.util.FeedItemUtil; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.core.util.gui.MoreContentListFooterUtil; import de.danoeh.antennapod.databinding.FeedItemListFragmentBinding; import de.danoeh.antennapod.databinding.MultiSelectSpeedDialBinding; @@ -48,6 +48,7 @@ import de.danoeh.antennapod.dialog.RenameItemDialog; import de.danoeh.antennapod.event.FavoritesEvent; import de.danoeh.antennapod.event.FeedItemEvent; import de.danoeh.antennapod.event.FeedListUpdateEvent; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; import de.danoeh.antennapod.event.PlayerStatusEvent; import de.danoeh.antennapod.event.QueueEvent; import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; @@ -164,7 +165,7 @@ public class FeedItemlistFragment extends Fragment implements AdapterView.OnItem nextPageLoader = new MoreContentListFooterUtil(viewBinding.moreContent.moreContentListFooter); nextPageLoader.setClickListener(() -> { if (feed != null) { - DBTasks.loadNextPageOfFeed(getActivity(), feed, false); + FeedUpdateManager.runOnce(getContext(), feed, true); } }); viewBinding.recyclerView.addOnScrollListener(new RecyclerView.OnScrollListener() { @@ -241,8 +242,6 @@ public class FeedItemlistFragment extends Fragment implements AdapterView.OnItem } viewBinding.toolbar.getMenu().findItem(R.id.visit_website_item).setVisible(feed.getLink() != null); - MenuItemUtils.updateRefreshMenuItem(viewBinding.toolbar.getMenu(), R.id.refresh_item, - DownloadService.isRunning && DownloadService.isDownloadingFile(feed.getDownload_url())); FeedMenuHandler.onPrepareOptionsMenu(viewBinding.toolbar.getMenu(), feed); } @@ -384,7 +383,6 @@ public class FeedItemlistFragment extends Fragment implements AdapterView.OnItem private void updateUi() { loadItems(); - updateSyncProgressBarVisibility(); } @Subscribe(threadMode = ThreadMode.MAIN) @@ -404,12 +402,14 @@ public class FeedItemlistFragment extends Fragment implements AdapterView.OnItem } } - private void updateSyncProgressBarVisibility() { - updateToolbar(); - if (!DownloadService.isDownloadingFeeds()) { + @Subscribe(sticky = true, threadMode = ThreadMode.MAIN) + public void onEventMainThread(FeedUpdateRunningEvent event) { + nextPageLoader.setLoadingState(event.isFeedUpdateRunning); + if (!event.isFeedUpdateRunning) { nextPageLoader.getRoot().setVisibility(View.GONE); } - nextPageLoader.setLoadingState(DownloadService.isDownloadingFeeds()); + MenuItemUtils.updateRefreshMenuItem(viewBinding.toolbar.getMenu(), + R.id.refresh_item, event.isFeedUpdateRunning); } private void refreshHeaderView() { @@ -534,14 +534,12 @@ public class FeedItemlistFragment extends Fragment implements AdapterView.OnItem adapter.setDummyViews(0); adapter.updateItems(feed.getItems()); updateToolbar(); - updateSyncProgressBarVisibility(); }, error -> { feed = null; refreshHeaderView(); adapter.setDummyViews(0); adapter.updateItems(Collections.emptyList()); updateToolbar(); - updateSyncProgressBarVisibility(); Log.e(TAG, Log.getStackTraceString(error)); }); } diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/FeedSettingsFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/FeedSettingsFragment.java index b4195ba01..ae9e003d5 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/FeedSettingsFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/FeedSettingsFragment.java @@ -16,7 +16,7 @@ import androidx.preference.PreferenceFragmentCompat; import androidx.preference.SwitchPreferenceCompat; import androidx.recyclerview.widget.RecyclerView; import de.danoeh.antennapod.R; -import de.danoeh.antennapod.core.storage.DBTasks; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.event.settings.SkipIntroEndingChangedEvent; import de.danoeh.antennapod.event.settings.SpeedPresetChangedEvent; import de.danoeh.antennapod.event.settings.VolumeAdaptionChangedEvent; @@ -270,8 +270,7 @@ public class FeedSettingsFragment extends Fragment { } catch (InterruptedException | ExecutionException e) { e.printStackTrace(); } - - DBTasks.forceRefreshFeed(requireContext(), feed, true); + FeedUpdateManager.runOnce(getContext(), feed); }, "RefreshAfterCredentialChange").start(); } }.show(); diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/QueueFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/QueueFragment.java index bb22c5652..6681df4c1 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/QueueFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/QueueFragment.java @@ -18,13 +18,13 @@ import android.widget.CheckBox; import android.widget.ProgressBar; import android.widget.TextView; import androidx.annotation.NonNull; -import com.google.android.material.dialog.MaterialAlertDialogBuilder; -import com.google.android.material.appbar.MaterialToolbar; import androidx.fragment.app.Fragment; import androidx.recyclerview.widget.ItemTouchHelper; import androidx.recyclerview.widget.RecyclerView; import androidx.recyclerview.widget.SimpleItemAnimator; import androidx.swiperefreshlayout.widget.SwipeRefreshLayout; +import com.google.android.material.appbar.MaterialToolbar; +import com.google.android.material.dialog.MaterialAlertDialogBuilder; import com.google.android.material.snackbar.Snackbar; import com.leinardi.android.speeddial.SpeedDialView; import de.danoeh.antennapod.R; @@ -36,14 +36,13 @@ import de.danoeh.antennapod.core.event.DownloadEvent; import de.danoeh.antennapod.core.event.DownloaderUpdate; import de.danoeh.antennapod.core.feed.util.PlaybackSpeedUtils; import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; -import de.danoeh.antennapod.storage.preferences.UserPreferences; -import de.danoeh.antennapod.core.service.download.DownloadService; import de.danoeh.antennapod.core.storage.DBReader; import de.danoeh.antennapod.core.storage.DBWriter; import de.danoeh.antennapod.core.util.Converter; import de.danoeh.antennapod.core.util.FeedItemUtil; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.event.FeedItemEvent; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; import de.danoeh.antennapod.event.PlayerStatusEvent; import de.danoeh.antennapod.event.QueueEvent; import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; @@ -54,6 +53,7 @@ import de.danoeh.antennapod.menuhandler.FeedItemMenuHandler; import de.danoeh.antennapod.model.feed.FeedItem; import de.danoeh.antennapod.model.feed.FeedItemFilter; import de.danoeh.antennapod.model.feed.SortOrder; +import de.danoeh.antennapod.storage.preferences.UserPreferences; import de.danoeh.antennapod.view.EmptyViewHandler; import de.danoeh.antennapod.view.EpisodeItemListRecyclerView; import de.danoeh.antennapod.view.LiftOnScrollListener; @@ -263,8 +263,11 @@ public class QueueFragment extends Fragment implements MaterialToolbar.OnMenuIte toolbar.getMenu().findItem(R.id.queue_lock).setVisible(!keepSorted); toolbar.getMenu().findItem(R.id.sort_random).setVisible(!keepSorted); toolbar.getMenu().findItem(R.id.keep_sorted).setChecked(keepSorted); - MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), - R.id.refresh_item, DownloadService.isRunning && DownloadService.isDownloadingFeeds()); + } + + @Subscribe(sticky = true, threadMode = ThreadMode.MAIN) + public void onEventMainThread(FeedUpdateRunningEvent event) { + MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), R.id.refresh_item, event.isFeedUpdateRunning); } @Override @@ -274,7 +277,7 @@ public class QueueFragment extends Fragment implements MaterialToolbar.OnMenuIte toggleQueueLock(); return true; } else if (itemId == R.id.refresh_item) { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); return true; } else if (itemId == R.id.clear_queue) { // make sure the user really wants to clear the queue @@ -457,7 +460,7 @@ public class QueueFragment extends Fragment implements MaterialToolbar.OnMenuIte SwipeRefreshLayout swipeRefreshLayout = root.findViewById(R.id.swipeRefresh); swipeRefreshLayout.setDistanceToTriggerSync(getResources().getInteger(R.integer.swipe_refresh_distance)); swipeRefreshLayout.setOnRefreshListener(() -> { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); new Handler(Looper.getMainLooper()).postDelayed(() -> swipeRefreshLayout.setRefreshing(false), getResources().getInteger(R.integer.swipe_to_refresh_duration_in_ms)); }); diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/SubscriptionFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/SubscriptionFragment.java index cc13f4ce3..a0698229a 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/SubscriptionFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/SubscriptionFragment.java @@ -13,20 +13,40 @@ import android.view.View; import android.view.ViewGroup; import android.widget.ProgressBar; import android.widget.TextView; - import androidx.annotation.NonNull; -import com.google.android.material.appbar.MaterialToolbar; import androidx.fragment.app.Fragment; import androidx.recyclerview.widget.GridLayoutManager; import androidx.recyclerview.widget.RecyclerView; import androidx.swiperefreshlayout.widget.SwipeRefreshLayout; - +import com.google.android.material.appbar.MaterialToolbar; import com.google.android.material.floatingactionbutton.FloatingActionButton; import com.joanzapata.iconify.Iconify; import com.leinardi.android.speeddial.SpeedDialView; - +import de.danoeh.antennapod.R; +import de.danoeh.antennapod.activity.MainActivity; +import de.danoeh.antennapod.adapter.SubscriptionsRecyclerAdapter; +import de.danoeh.antennapod.core.event.DownloadEvent; +import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; +import de.danoeh.antennapod.core.storage.DBReader; +import de.danoeh.antennapod.core.storage.NavDrawerData; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; +import de.danoeh.antennapod.dialog.FeedSortDialog; +import de.danoeh.antennapod.dialog.RenameItemDialog; +import de.danoeh.antennapod.dialog.SubscriptionsFilterDialog; +import de.danoeh.antennapod.event.FeedListUpdateEvent; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; +import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; +import de.danoeh.antennapod.fragment.actions.FeedMultiSelectActionHandler; +import de.danoeh.antennapod.menuhandler.FeedMenuHandler; +import de.danoeh.antennapod.model.feed.Feed; +import de.danoeh.antennapod.storage.preferences.UserPreferences; import de.danoeh.antennapod.ui.statistics.StatisticsFragment; +import de.danoeh.antennapod.view.EmptyViewHandler; import de.danoeh.antennapod.view.LiftOnScrollListener; +import io.reactivex.Observable; +import io.reactivex.android.schedulers.AndroidSchedulers; +import io.reactivex.disposables.Disposable; +import io.reactivex.schedulers.Schedulers; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; import org.greenrobot.eventbus.ThreadMode; @@ -35,30 +55,6 @@ import java.util.ArrayList; import java.util.List; import java.util.Locale; -import de.danoeh.antennapod.R; -import de.danoeh.antennapod.activity.MainActivity; -import de.danoeh.antennapod.adapter.SubscriptionsRecyclerAdapter; -import de.danoeh.antennapod.core.event.DownloadEvent; -import de.danoeh.antennapod.event.FeedListUpdateEvent; -import de.danoeh.antennapod.event.UnreadItemsUpdateEvent; -import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; -import de.danoeh.antennapod.storage.preferences.UserPreferences; -import de.danoeh.antennapod.core.service.download.DownloadService; -import de.danoeh.antennapod.core.storage.DBReader; -import de.danoeh.antennapod.core.storage.NavDrawerData; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; -import de.danoeh.antennapod.dialog.FeedSortDialog; -import de.danoeh.antennapod.dialog.RenameItemDialog; -import de.danoeh.antennapod.dialog.SubscriptionsFilterDialog; -import de.danoeh.antennapod.fragment.actions.FeedMultiSelectActionHandler; -import de.danoeh.antennapod.model.feed.Feed; -import de.danoeh.antennapod.view.EmptyViewHandler; -import de.danoeh.antennapod.menuhandler.FeedMenuHandler; -import io.reactivex.Observable; -import io.reactivex.android.schedulers.AndroidSchedulers; -import io.reactivex.disposables.Disposable; -import io.reactivex.schedulers.Schedulers; - /** * Fragment for displaying feed subscriptions */ @@ -173,7 +169,7 @@ public class SubscriptionFragment extends Fragment SwipeRefreshLayout swipeRefreshLayout = root.findViewById(R.id.swipeRefresh); swipeRefreshLayout.setDistanceToTriggerSync(getResources().getInteger(R.integer.swipe_refresh_distance)); swipeRefreshLayout.setOnRefreshListener(() -> { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); new Handler(Looper.getMainLooper()).postDelayed(() -> swipeRefreshLayout.setRefreshing(false), getResources().getInteger(R.integer.swipe_to_refresh_duration_in_ms)); }); @@ -209,16 +205,18 @@ public class SubscriptionFragment extends Fragment private void refreshToolbarState() { int columns = prefs.getInt(PREF_NUM_COLUMNS, getDefaultNumOfColumns()); toolbar.getMenu().findItem(COLUMN_CHECKBOX_IDS[columns - MIN_NUM_COLUMNS]).setChecked(true); + } - MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), R.id.refresh_item, - DownloadService.isRunning && DownloadService.isDownloadingFeeds()); + @Subscribe(sticky = true, threadMode = ThreadMode.MAIN) + public void onEventMainThread(FeedUpdateRunningEvent event) { + MenuItemUtils.updateRefreshMenuItem(toolbar.getMenu(), R.id.refresh_item, event.isFeedUpdateRunning); } @Override public boolean onMenuItemClick(MenuItem item) { final int itemId = item.getItemId(); if (itemId == R.id.refresh_item) { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); return true; } else if (itemId == R.id.subscriptions_filter) { SubscriptionsFilterDialog.showDialog(requireContext()); diff --git a/app/src/main/java/de/danoeh/antennapod/fragment/preferences/NetworkPreferencesFragment.java b/app/src/main/java/de/danoeh/antennapod/fragment/preferences/NetworkPreferencesFragment.java index 50de1e3c4..94c85abfe 100644 --- a/app/src/main/java/de/danoeh/antennapod/fragment/preferences/NetworkPreferencesFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/fragment/preferences/NetworkPreferencesFragment.java @@ -1,21 +1,15 @@ package de.danoeh.antennapod.fragment.preferences; -import android.content.Context; import android.content.SharedPreferences; import android.content.res.Resources; import android.os.Bundle; -import android.text.format.DateFormat; import androidx.preference.PreferenceFragmentCompat; import androidx.preference.PreferenceManager; import de.danoeh.antennapod.R; import de.danoeh.antennapod.activity.PreferenceActivity; -import de.danoeh.antennapod.storage.preferences.UserPreferences; -import de.danoeh.antennapod.dialog.FeedRefreshIntervalDialog; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.dialog.ProxyDialog; - -import java.util.Calendar; -import java.util.GregorianCalendar; -import java.util.concurrent.TimeUnit; +import de.danoeh.antennapod.storage.preferences.UserPreferences; public class NetworkPreferencesFragment extends PreferenceFragmentCompat @@ -45,7 +39,6 @@ public class NetworkPreferencesFragment extends PreferenceFragmentCompat @Override public void onResume() { super.onResume(); - setUpdateIntervalText(); setParallelDownloadsText(UserPreferences.getParallelDownloads()); } @@ -54,21 +47,12 @@ public class NetworkPreferencesFragment extends PreferenceFragmentCompat ((PreferenceActivity) getActivity()).openScreen(R.xml.preferences_autodownload); return true; }); - findPreference(UserPreferences.PREF_UPDATE_INTERVAL) - .setOnPreferenceClickListener(preference -> { - new FeedRefreshIntervalDialog(getContext()).show(); - return true; - }); - - findPreference(UserPreferences.PREF_PARALLEL_DOWNLOADS) - .setOnPreferenceChangeListener( - (preference, o) -> { - if (o instanceof Integer) { - setParallelDownloadsText((Integer) o); - } - return true; - } - ); + findPreference(UserPreferences.PREF_PARALLEL_DOWNLOADS).setOnPreferenceChangeListener((preference, o) -> { + if (o instanceof Integer) { + setParallelDownloadsText((Integer) o); + } + return true; + }); // validate and set correct value: number of downloads between 1 and 50 (inclusive) findPreference(PREF_PROXY).setOnPreferenceClickListener(preference -> { ProxyDialog dialog = new ProxyDialog(getActivity()); @@ -77,35 +61,6 @@ public class NetworkPreferencesFragment extends PreferenceFragmentCompat }); } - /** - * Used to init and handle changes to view - */ - private void setUpdateIntervalText() { - Context context = getActivity().getApplicationContext(); - String val; - long interval = UserPreferences.getUpdateInterval(); - if (interval > 0) { - int hours = (int) TimeUnit.MILLISECONDS.toHours(interval); - val = context.getResources().getQuantityString( - R.plurals.feed_refresh_every_x_hours, hours, hours); - } else { - int[] timeOfDay = UserPreferences.getUpdateTimeOfDay(); - if (timeOfDay.length == 2) { - Calendar cal = new GregorianCalendar(); - cal.set(Calendar.HOUR_OF_DAY, timeOfDay[0]); - cal.set(Calendar.MINUTE, timeOfDay[1]); - String timeOfDayStr = DateFormat.getTimeFormat(context).format(cal.getTime()); - val = String.format(context.getString(R.string.feed_refresh_interval_at), - timeOfDayStr); - } else { - val = context.getString(R.string.feed_refresh_never); - } - } - String summary = context.getString(R.string.feed_refresh_sum) + "\n" - + String.format(context.getString(R.string.pref_current_value), val); - findPreference(UserPreferences.PREF_UPDATE_INTERVAL).setSummary(summary); - } - private void setParallelDownloadsText(int downloads) { final Resources res = getActivity().getResources(); String s = res.getString(R.string.parallel_downloads, downloads); @@ -115,9 +70,7 @@ public class NetworkPreferencesFragment extends PreferenceFragmentCompat @Override public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) { if (UserPreferences.PREF_UPDATE_INTERVAL.equals(key)) { - setUpdateIntervalText(); + FeedUpdateManager.restartUpdateAlarm(getContext(), true); } } } - - diff --git a/app/src/main/java/de/danoeh/antennapod/menuhandler/FeedMenuHandler.java b/app/src/main/java/de/danoeh/antennapod/menuhandler/FeedMenuHandler.java index 7aee499da..e9b0c0b19 100644 --- a/app/src/main/java/de/danoeh/antennapod/menuhandler/FeedMenuHandler.java +++ b/app/src/main/java/de/danoeh/antennapod/menuhandler/FeedMenuHandler.java @@ -10,6 +10,7 @@ import de.danoeh.antennapod.core.storage.DBTasks; import de.danoeh.antennapod.core.storage.DBWriter; import de.danoeh.antennapod.core.util.IntentUtils; import de.danoeh.antennapod.core.util.ShareUtils; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.dialog.IntraFeedSortDialog; import de.danoeh.antennapod.model.feed.Feed; import de.danoeh.antennapod.model.feed.SortOrder; @@ -26,6 +27,7 @@ import io.reactivex.android.schedulers.AndroidSchedulers; import io.reactivex.schedulers.Schedulers; import java.util.Collections; import java.util.concurrent.Callable; +import java.util.concurrent.ExecutionException; import java.util.concurrent.Future; /** @@ -64,7 +66,16 @@ public class FeedMenuHandler { if (itemId == R.id.refresh_item) { DBTasks.forceRefreshFeed(context, selectedFeed, true); } else if (itemId == R.id.refresh_complete_item) { - DBTasks.forceRefreshCompleteFeed(context, selectedFeed); + new Thread(() -> { + selectedFeed.setNextPageLink(selectedFeed.getDownload_url()); + selectedFeed.setPageNr(0); + try { + DBWriter.resetPagedFeedPage(selectedFeed).get(); + FeedUpdateManager.runOnce(context, selectedFeed); + } catch (ExecutionException | InterruptedException e) { + throw new RuntimeException(e); + } + }).start(); } else if (itemId == R.id.sort_items) { showSortDialog(context, selectedFeed); } else if (itemId == R.id.visit_website_item) { diff --git a/app/src/main/java/de/danoeh/antennapod/preferences/PreferenceUpgrader.java b/app/src/main/java/de/danoeh/antennapod/preferences/PreferenceUpgrader.java index 875ed347e..80e7fdb1e 100644 --- a/app/src/main/java/de/danoeh/antennapod/preferences/PreferenceUpgrader.java +++ b/app/src/main/java/de/danoeh/antennapod/preferences/PreferenceUpgrader.java @@ -13,7 +13,7 @@ import de.danoeh.antennapod.core.preferences.SleepTimerPreferences; import de.danoeh.antennapod.error.CrashReportWriter; import de.danoeh.antennapod.storage.preferences.UserPreferences; import de.danoeh.antennapod.storage.preferences.UserPreferences.EnqueueLocation; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.fragment.QueueFragment; import de.danoeh.antennapod.fragment.swipeactions.SwipeAction; import de.danoeh.antennapod.fragment.swipeactions.SwipeActions; @@ -31,7 +31,7 @@ public class PreferenceUpgrader { int newVersion = BuildConfig.VERSION_CODE; if (oldVersion != newVersion) { - AutoUpdateManager.restartUpdateAlarm(context); + FeedUpdateManager.restartUpdateAlarm(context, true); CrashReportWriter.getFile().delete(); upgrade(oldVersion, context); @@ -138,6 +138,9 @@ public class PreferenceUpgrader { .apply(); } UserPreferences.setAllowMobileSync(true); + if (prefs.getString(UserPreferences.PREF_UPDATE_INTERVAL, ":").contains(":")) { // Unset or "time of day" + prefs.edit().putString(UserPreferences.PREF_UPDATE_INTERVAL, "12").apply(); + } } } } diff --git a/app/src/main/java/de/danoeh/antennapod/receiver/SPAReceiver.java b/app/src/main/java/de/danoeh/antennapod/receiver/SPAReceiver.java index c566a1fd2..788359a4e 100644 --- a/app/src/main/java/de/danoeh/antennapod/receiver/SPAReceiver.java +++ b/app/src/main/java/de/danoeh/antennapod/receiver/SPAReceiver.java @@ -8,11 +8,12 @@ import android.util.Log; import android.widget.Toast; import java.util.Arrays; +import java.util.Collections; import de.danoeh.antennapod.R; import de.danoeh.antennapod.core.ClientConfigurator; -import de.danoeh.antennapod.core.service.download.DownloadRequestCreator; -import de.danoeh.antennapod.net.download.serviceinterface.DownloadServiceInterface; +import de.danoeh.antennapod.core.storage.DBTasks; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.model.feed.Feed; /** @@ -43,9 +44,11 @@ public class SPAReceiver extends BroadcastReceiver{ Log.d(TAG, "Received feeds list: " + Arrays.toString(feedUrls)); ClientConfigurator.initialize(context); for (String url : feedUrls) { - Feed f = new Feed(url, null); - DownloadServiceInterface.get().download(context, false, DownloadRequestCreator.create(f).build()); + Feed feed = new Feed(url, null, "Unknown podcast"); + feed.setItems(Collections.emptyList()); + DBTasks.updateFeed(context, feed, false); } Toast.makeText(context, R.string.sp_apps_importing_feeds_msg, Toast.LENGTH_LONG).show(); + FeedUpdateManager.runOnce(context); } } diff --git a/app/src/main/java/de/danoeh/antennapod/ui/home/HomeFragment.java b/app/src/main/java/de/danoeh/antennapod/ui/home/HomeFragment.java index da3fd7b05..778b57c8c 100644 --- a/app/src/main/java/de/danoeh/antennapod/ui/home/HomeFragment.java +++ b/app/src/main/java/de/danoeh/antennapod/ui/home/HomeFragment.java @@ -17,13 +17,12 @@ import androidx.fragment.app.Fragment; import androidx.fragment.app.FragmentContainerView; import de.danoeh.antennapod.R; import de.danoeh.antennapod.activity.MainActivity; -import de.danoeh.antennapod.core.event.DownloadEvent; import de.danoeh.antennapod.core.menuhandler.MenuItemUtils; -import de.danoeh.antennapod.core.service.download.DownloadService; import de.danoeh.antennapod.core.storage.DBReader; -import de.danoeh.antennapod.core.util.download.AutoUpdateManager; +import de.danoeh.antennapod.core.util.download.FeedUpdateManager; import de.danoeh.antennapod.databinding.HomeFragmentBinding; import de.danoeh.antennapod.event.FeedListUpdateEvent; +import de.danoeh.antennapod.event.FeedUpdateRunningEvent; import de.danoeh.antennapod.fragment.SearchFragment; import de.danoeh.antennapod.ui.home.sections.DownloadsSection; import de.danoeh.antennapod.ui.home.sections.EpisodesSurpriseSection; @@ -69,13 +68,12 @@ public class HomeFragment extends Fragment implements Toolbar.OnMenuItemClickLis } viewBinding.homeScrollView.setOnScrollChangeListener(new LiftOnScrollListener(viewBinding.appbar)); ((MainActivity) requireActivity()).setupToolbarToggle(viewBinding.toolbar, displayUpArrow); - refreshToolbarState(); populateSectionList(); updateWelcomeScreenVisibility(); viewBinding.swipeRefresh.setDistanceToTriggerSync(getResources().getInteger(R.integer.swipe_refresh_distance)); viewBinding.swipeRefresh.setOnRefreshListener(() -> { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); new Handler(Looper.getMainLooper()).postDelayed(() -> viewBinding.swipeRefresh.setRefreshing(false), getResources().getInteger(R.integer.swipe_to_refresh_duration_in_ms)); }); @@ -126,14 +124,10 @@ public class HomeFragment extends Fragment implements Toolbar.OnMenuItemClickLis return new ArrayList<>(Arrays.asList(TextUtils.split(hiddenSectionsString, ","))); } - private void refreshToolbarState() { - MenuItemUtils.updateRefreshMenuItem(viewBinding.toolbar.getMenu(), - R.id.refresh_item, DownloadService.isRunning && DownloadService.isDownloadingFeeds()); - } - @Subscribe(sticky = true, threadMode = ThreadMode.MAIN) - public void onEventMainThread(DownloadEvent event) { - refreshToolbarState(); + public void onEventMainThread(FeedUpdateRunningEvent event) { + MenuItemUtils.updateRefreshMenuItem(viewBinding.toolbar.getMenu(), + R.id.refresh_item, event.isFeedUpdateRunning); } @Override @@ -142,7 +136,7 @@ public class HomeFragment extends Fragment implements Toolbar.OnMenuItemClickLis HomeSectionsSettingsDialog.open(getContext(), (dialogInterface, i) -> populateSectionList()); return true; } else if (item.getItemId() == R.id.refresh_item) { - AutoUpdateManager.runImmediate(requireContext()); + FeedUpdateManager.runOnceOrAsk(requireContext()); return true; } else if (item.getItemId() == R.id.action_search) { ((MainActivity) getActivity()).loadChildFragment(SearchFragment.newInstance()); diff --git a/app/src/main/java/de/danoeh/antennapod/view/TimePicker.java b/app/src/main/java/de/danoeh/antennapod/view/TimePicker.java deleted file mode 100644 index 191f72d2e..000000000 --- a/app/src/main/java/de/danoeh/antennapod/view/TimePicker.java +++ /dev/null @@ -1,31 +0,0 @@ -package de.danoeh.antennapod.view; - -import android.content.Context; -import android.util.AttributeSet; - -/** - * Samsung's Android 6.0.1 has a bug that crashes the app when inflating a time picker. - * This class serves as a workaround for affected devices. - */ -public class TimePicker extends android.widget.TimePicker { - public TimePicker(Context context) { - super(context); - } - - public TimePicker(Context context, AttributeSet attrs) { - super(context, attrs); - } - - public TimePicker(Context context, AttributeSet attrs, int defStyleAttr) { - super(context, attrs, defStyleAttr); - } - - @Override - public void onRtlPropertiesChanged(int layoutDirection) { - try { - super.onRtlPropertiesChanged(layoutDirection); - } catch (Exception e) { - e.printStackTrace(); - } - } -} diff --git a/app/src/main/res/layout/feed_refresh_dialog.xml b/app/src/main/res/layout/feed_refresh_dialog.xml deleted file mode 100644 index 5a6770a80..000000000 --- a/app/src/main/res/layout/feed_refresh_dialog.xml +++ /dev/null @@ -1,40 +0,0 @@ - - - - - - - - - - - - - - diff --git a/app/src/main/res/layout/scrollable_dialog.xml b/app/src/main/res/layout/scrollable_dialog.xml deleted file mode 100644 index 29b84ee4b..000000000 --- a/app/src/main/res/layout/scrollable_dialog.xml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - - - -