Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

Проматывать рекомендации к элементу, открытому из публичного экрана плейлиста через контекстное меню "играть в плейлисте" #172

Closed
sadr0b0t opened this issue Feb 23, 2023 · 4 comments
Labels
enhancement New feature or request

Comments

@sadr0b0t
Copy link
Owner

Переходим в экран плейлиста, выставляем настройки фильтра/сортировки, кликаем на ролике в списке и выбираем меню "играть в плейлисте".

На экране плеера:

  • открытый ролик должен быть не в начале списка, а в исходной позициив сотрированном/фильтрованном списке
  • список рекомендации следует промотать к этому ролику
  • кнопка "следующее видео" должна открывать ролик, следующий за открытым, а не первый в списке рекомендаций

Таким обрзом появится возможность, к примеру, продолжить просмотр плейлиста начиная с нужного ролика, который выбран на экране плейлиста, а не после откртия на экране плеера.

Связанный тикет (там этот случай следует исключить): #170

Где не желательно: Меню "играть в плейлисте" на выбранном ролике в отсортированном/фильтрованном, т.к. в таком случае нарушится порядок сортировки. Для этого меню хороший вариант - загружать рекомендации с настройками сортировки/фильтра, а к выбранному ролику прокручивать список. Проблема здесь в том, что у него заранее неизвестен индекс в поисковой выдаче, но это решается ручным перебором. Мало вероятно, что ролик окажется в конце длинного списка, т.к. в таком случае пользователь должен был перемотать его вручную в гуе.

@sadr0b0t sadr0b0t added the enhancement New feature or request label Feb 23, 2023
@sadr0b0t
Copy link
Owner Author

Реализовал прокрутку через ручной перебор элементов в адаптере (коммита пока нет). Режим включен при открытии ролика через контекстное меню "играть в плейлисте" в публичном экарне плейлиста и при клике на ролик в экране плейлиста в настройках.

Если элемент плюс-минус в начале списка, работает. Если промотать плейлист дальше, то не работает, т.к. PagedListAdapter загружает ролики из базы данных не сразу, а порциями по мере прокрутки списка, и в адаптере после некоторого индекса по порядковому номеру можно получить только null.

Пока оставлю как есть. Возможные варианты сделать идеально:

  • программно прокручивать список дальше и дальше, чтобы нужные элементы появлялись в адаптере, пока не будет найден нужный элемент (довольно муторно, т.к. подгрузка будет происходить в фоне).
  • попробовать посмотреть, есть ли запрос SQL, который даст порядковый номер исхомого элемента в выдаче запроса - тогда адаптер не будет нужен
  • можно этот же номер взять в исходном списке на экране плейлиста
  • попробовать сразу прогружать все элементы в список до необходимого - настройка PagedList.Config.Builder().setPageSize при создании PagedListAdapter. Можно выставить размер страницы так, чтобы он заведомо включал элемент, до которого нужно прокрутить. Вопрос где брать размер страницы - можно тоже на странице со списком до того, как откроем плеер. Техника примерно та же, что и с предыдущим пунктом. Может быть не очень эффективно с точки зрения экономии памяти, но для фильтрованных плейлистов и при условии, что пользователь изначально не будет мотать слишком глубоко вниз, можно быть приемлемо.

@sadr0b0t
Copy link
Owner Author

Реализовал прокрутку через ручной перебор элементов в адаптере (коммита пока нет)

оставлю этот код здесь:

if (videoId != VideoItem.ID_NONE) {
                        playerService.playVideoItem(videoId, false);

                        if (WatchVideoActivity.this.getIntent().getBooleanExtra(PARAM_SCROLL_TO_IN_RECOMMENDATIONS, false)) {
                            recommendationsListener = new RecommendationsListener() {
                                @Override
                                public void onFirstItemLoaded(final VideoItem firstItem) {
                                    // попробуем промотать список рекомендаций до выбранного видео
                                    int pos = -1;

                                    // сейчас сюда попадаем только в одном случае - если ролик выбран в
                                    // публичном экране плейлиста через меню "играть в плейлисте" -
                                    // в этом случае у нас для рекомендаций будет создан VideoItemPagedListAdapter
                                    final VideoItemPagedListAdapter adapterAsPaged = (VideoItemPagedListAdapter) videoList.getAdapter();
                                    for (int i = 0; i < adapterAsPaged.getItemCount(); i++) {
                                        if (adapterAsPaged.getItem(i) == null) {
                                            // если в качестве элементов пошли null, значит
                                            // адаптер в этот заход не загрузил ролики до нужного;
                                            // найти индекс ролика в незагруженном списке будет
                                            // довольно проблематично, поэтому в этой ситуации сейчас
                                            // просто ничего не делаем
                                            break;
                                        } else if (adapterAsPaged.getItem(i).getId() == videoId) {
                                            pos = i;
                                            break;
                                        }
                                    }

                                    if (pos != -1) {
                                        playerService.getVideoListPosMap().put(videoId, pos);
                                        playerService.setVideoListCurrentPosition(pos);
                                        videoList.scrollToPosition(pos);
                                    }
                                }
                            };
                        } else {
                            recommendationsListener = new RecommendationsListener() {
                                @Override
                                public void onFirstItemLoaded(final VideoItem firstItem) {
                                    // проверим, совпадает ли первый элемент в рекомендациях с роликом,
                                    // который загружен; если совпадает, то установим индекс текущего ролика
                                    // нулём, чтобы плеер понимал, что загруженное видео - первое в списке
                                    // рекомендаций
                                    if (videoId == firstItem.getId()) {
                                        playerService.getVideoListPosMap().put(videoId, 0);
                                        playerService.setVideoListCurrentPosition(0);
                                    }
                                }
                            };
                        }
                    }

и реализую по этой схеме:

можно этот же номер взять в исходном списке на экране плейлиста

@sadr0b0t
Copy link
Owner Author

sadr0b0t commented Feb 23, 2023

можно этот же номер взять в исходном списке на экране плейлиста

Вот так получилось норм. Ограничения на расстояние от начала списка теперь нет. Один раз, правда, показалось, что поймал глюк с неправильным элементом, но, может, что-то неправильно увидел из-за тормозов эмулятора.

Заодно получилось этим способом применить промотку к выбранному элементу при открытии ролика по адресу в списках "новое для всех плейлистов", "новое для плейлиста", "добавить плейлист", т.е. там, где списки берут не из базы данных. Но срабатывает не всегда, если умотать далеко вниз список.

@sadr0b0t
Copy link
Owner Author

Исправлено здесь 3d024dd в этом тикете #7

# for free to join this conversation on GitHub. Already have an account? # to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

1 participant