Как проверить, виден ли фрагмент в ViewPager? - PullRequest
0 голосов
/ 19 февраля 2020

Во-первых, ни одно из решений не работало при условии stackoverflow из-за изменения либо Android, либо моей проблемы, которая была совершенно другой.

Чего я хочу достичь - Я хочу определить, когда мой вид (например, ThirdFragment) находится в фокусе и становится видимым для пользователя. Кроме того, он должен определять, когда пользователь перемещается от текущего представления к следующему или предыдущему.

Почему я хочу это сделать? - Что ж, я создаю медиаплеер в одном из представлений, как показано в примере фрагмента кода, и пользователь может воспроизводить любую музыку c, указанную в представлении, нажав на кнопку c в списке, но когда пользователь переходит к следующему экрану, он должен остановиться.

В чем проблема? - Проблема в том, что медиаплеер не останавливается сразу после переключения из вида, но [***], если я проведу два шага, он остановится, но не чисто, он дрожит на заднем плане.

То, что я пробовал раньше - Я пробовал это setUserVisibleHint , но оно не работало, потому что было удалено. onPause, onDetach, onStop никто не работает, как упомянуто здесь [***]

/*------Home ViewPager----- */

public class HomeFragment extends Fragment {

    private ViewPager viewPager; 

    private String[] titles = {"First","Second","Third","Fourth"};

    @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
    }

    public View onCreateView(@NonNull LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
        TextView subtitle = getActivity().findViewById(R.id.toolbar_right_subtitle);
        subtitle.setText(titles[0]);
        return inflater.inflate(R.layout.fragment_home, container, false);
    }

    @Override
    public void onViewCreated(@NonNull final View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState); 

        /* pages */
        viewPager = view.findViewById(R.id.interfaces);
        InterfaceAdapter interfacePagerAdapter = new InterfaceAdapter(getActivity().getSupportFragmentManager(),0);
        viewPager.setAdapter(interfacePagerAdapter);
        viewPager.setCurrentItem(0);
        viewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
            @Override
            public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
            }

            @Override
            public void onPageSelected(int position) {
                TextView subtitle = getActivity().findViewById(R.id.toolbar_right_subtitle);
                subtitle.setText(titles[position]); 
            }

            @Override
            public void onPageScrollStateChanged(int state) {

            }
        });
    } 
}

    /*---------- My Fragment Adapter --------- */

    public class InterfaceAdapter extends FragmentStatePagerAdapter {

        public InterfaceAdapter(@NonNull FragmentManager fm, int behavior) {
            super(fm, behavior);
        }

        @NonNull
        @Override
        public Fragment getItem(int position) {
            switch (position){
                case 0:
                    return new FirstFragment();
                case 1:
                    return new SecondFragment();
                case 2:
                    return new ThirdFragment();
                case 3:
                    return new FourthFragment();
                default:
                    return null;
            }
        }

        @Override
        public int getCount() {
            return 4;
        }
    }


/*---------- One of my Fragment --------- */

public class ThirdFragment extends Fragment {

    //------Media Player ----------
    private MusicAdapter musicAdapter;
    private List<SongData> songsList;
    private ListView listView;
    private static MediaPlayer mediaPlayer;
    private Handler handler = new Handler();
    private Runnable runnable;
    private ImageView playButton, prevButton, nextButton;
    private SeekBar seekbarPayer;
    private TextView playerTime,songTitle;
    private int pos = 0;

    public ThirdFragment() {
        // Required empty public constructor
    }

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
    }

    @Override
    public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { 
        eventViewModels = new ViewModelProvider((FragmentActivity) getContext()).get(EventViewModels.class);
        mediaPlayer = new MediaPlayer();
        getAllSongs();
        return inflater.inflate(R.layout.fragment_focus, container, false);
    }

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        super.onViewCreated(view, savedInstanceState); 

        //--------Music Player---------------
        mediaPlayer = new MediaPlayer();
        playButton = view.findViewById(R.id.playpause_player);
        prevButton = view.findViewById(R.id.prev_player);
        nextButton = view.findViewById(R.id.next_player);
        seekbarPayer = view.findViewById(R.id.seekbar_player);
        playerTime = view.findViewById(R.id.playertime);
        songTitle = view.findViewById(R.id.songname);
        songTitle.setSelected(true);

        songsList = new ArrayList<>();
        musicAdapter = new MusicAdapter(getActivity(), songsList);
        listView = view.findViewById(R.id.songList);
        listView.setAdapter(musicAdapter);
        listView.setOnItemClickListener(new AdapterView.OnItemClickListener() {
            @Override
            public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
                pos = position;
                playMusicFile(songsList.get(position).getUri(),songsList.get(position).getTitle());
            }
        });

        //play or pause music
        playButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                playPause();
            }
        });

        //next music
        nextButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (pos < songsList.size() - 1) {
                    pos++;
                } else {
                    pos = 0;
                }
                playMusicFile(songsList.get(pos).getUri(),songsList.get(pos).getTitle());
            }
        });

        //next music
        prevButton.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                if (pos > 0) {
                    pos--;
                } else {
                    pos = songsList.size() - 1;
                }
                playMusicFile(songsList.get(pos).getUri(),songsList.get(pos).getTitle());
            }
        });
    } 

     @Override
    public void onActivityCreated(@Nullable Bundle savedInstanceState) {
        super.onActivityCreated(savedInstanceState);
        eventViewModels.getTrigger().observe((LifecycleOwner) getContext(), new Observer<Integer>() {
            @Override
            public void onChanged(@Nullable final Integer val) {
                assert val!=null;
                Log.d("ObserverValue",val+"");
            }
        });
    }




    @Override
    public void onStart() {
        super.onStart();
        getAllSongs();
        Log.d("SystemStatus","Start"); 
    } 

    @Override
    public void onResume() {
        super.onResume();
        getAllSongs();
        Log.d("SystemStatus","Resume"); 
    } 

    @Override
    public void onStop() {
        super.onStop();
        stopPlayer();
        Log.d("SystemStatus","Stop"); 
    }

    @Override
    public void onDetach() {
        super.onDetach();
        stopPlayer();
        Log.d("SystemStatus","Detach");
    }

    @Override
    public void onPause() {
        super.onPause();
        stopPlayer();
        Log.d("SystemStatus","Pause");   



    if (eventViewModels != null && eventViewModels.getTrigger().hasObservers()) {
     eventViewModels.getTrigger().removeObservers(this);
 } 
        }

    //---Media Player-----

    private void getAllSongs() {
       /*
        * get all songs and add it into songlist
        */
    }

    private void playMusicFile(String filePath,final String title){
        if(mediaPlayer!=null) {
            mediaPlayer.reset();
            try {
                mediaPlayer.setDataSource(filePath);
                mediaPlayer.prepareAsync();
                mediaPlayer.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
                    @Override
                    public void onPrepared(MediaPlayer mp) {
                        mp.start(); 
                    }
                });
                mediaPlayer.setOnCompletionListener(new MediaPlayer.OnCompletionListener() {
                    @Override
                    public void onCompletion(MediaPlayer mp) { 
                        stopPlayer();
                    }
                }); 
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    } 

    private void playPause() {
        if (!mediaPlayer.isPlaying()) {
            mediaPlayer.start(); 
        }else {
            mediaPlayer.pause(); 
        }
    }

    private void stopPlayer() {
        if(mediaPlayer.isPlaying()){
            mediaPlayer.stop();
            mediaPlayer.reset(); 
        }
    } 

}

Редактировать:

Спасибо @ianhanniballake за предоставляя решение.

Это решило мою проблему "частично". Я могу остановить медиаплеер, но не могу остановить наблюдателя, наблюдающего за событием во время паузы. обновление кода

1 Ответ

2 голосов
/ 19 февраля 2020

Вы передаете 0 как поведение, которое соответствует устаревшему BEHAVIOR_SET_USER_VISIBLE_HINT. Используя это поведение, setUserVisibleHint() будет вызываться с true, когда ваш фрагмент становится текущей страницей, и false, когда это не так.

Если вы переключитесь на не устаревшую BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT , тогда только текущая страница получит onResume(). Когда страница изменится, этот фрагмент получит обратный вызов на onPause(), а новый активный фрагмент получит вызов на onResume().

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...