Как вызвать onCreateView только тогда, когда фрагмент виден? - PullRequest
0 голосов
/ 28 января 2019

Я использую ViewPager с 5 фрагментами, и моя проблема в том, что когда первый фрагмент виден, он уже загружает второй.

Я прочитал что-то о viewPager.setOffscreenPageLimit();но значением по умолчанию для этого является '1' и не может быть установлено в '0', потому что ViewPager нуждается в этом для анимации смахивания.

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

Но моя проблема в том, что у меня есть глобальный Arraylist в обоих фрагментах с разными значениями, загруженными в каждый фрагмент, и когда я нахожусь на фрагменте один, значения перезаписываются, потому что второй фрагмент вызывается.

Как вызвать onCreateView для каждого фрагмента, только когда этот фрагмент видим для пользователя?

Ответы [ 3 ]

0 голосов
/ 07 февраля 2019

С помощью этого вы можете попробовать,

@Override
    public void setUserVisibleHint(boolean isVisibleToUser) {
}
0 голосов
/ 09 мая 2019

Просмотр пейджера будет загружать соседние фрагменты, даже если вы установите setOffscreenPageLimit равным 0. Так как, если значение меньше 1, они установят его как 1.

Так onCreate, onCreateView ... onResumeближайшие фрагменты будут вызваны до того, как они станут видимыми.

Так что просто загрузите ваши данные в setUserVisibleHint .

@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
    super.setUserVisibleHint(isVisibleToUser);
    if(getView() != null && isVisibleToUser){
        loadData();
    }
}

Но существует проблема.Этот метод (setUserVisibleHint) будет вызываться перед onCreate нашего фрагмента.

Если вы получаете данные из аргументов. Мы получим эти данные из onCreate или onCreateView фрагмента.Таким образом, первый видимый фрагмент setUserVisibleHint будет вызван без данных для загрузки ( getView ()! = Null из вышеописанного метода).Для этого мы можем использовать

 public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View view = super.onCreateView(inflater,container,savedInstanceState);

    // This is because for the first fragment to loadData, since the 
    // setUserVisibleHint is called before the onCreateView of the fragment.

    if(getUserVisibleHint()){
        loadData();
    }

    return view;
}

loadData - метод, который будет выполнять связывание данных с частью моего фрагмента.

Делая это, для первого видимого фрагмента loadDataбудет вызываться из onCreateView, а рядом с фрагментом будет вызываться из setUserVisibleHint.

0 голосов
/ 28 января 2019

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

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

Наконец, рассмотрите возможность переместить логику в onResume, если только у вас нет веских причин не делать этого.Если это не работает для вас, то следите за событием смены страницы и вызывайте общий метод «load», который вы создаете для каждого baseFragment, который вы можете просто вызывать и обрабатывать там свой код.

...