it-swarm.com.ru

Задержка навигационного ящика на Android

У меня проблема с Navigation Drawer, он слишком медленный, решение, которое я ищу, - сначала закрыть ящик, а затем показать действие, но оно не работает, конечно, я что-то упустил. 

private class DrawerItemClickListener implements ListView.OnItemClickListener {
        @Override
        public void onItemClick(AdapterView<?> parent, View view, int posicao, long id) {
            setLastPosition(posicao);
            setFragmentList(lastPosition);
            layoutDrawer.closeDrawer(linearDrawer);
        }
    }

    private OnClickListener userOnClick = new OnClickListener() {
        @Override
        public void onClick(View v) {
            layoutDrawer.closeDrawer(linearDrawer);
        }
    };

    private void setFragmentList(int posicao) {

        FragmentManager fragmentManager = getSupportFragmentManager();
        Fragment fragment = new FragmentViagens();

        switch (posicao) {

            case 0:
                fragmentManager.beginTransaction().replace(R.id.content_frame, fragment).commit();
                break;
            case 1:
                fragmentManager.beginTransaction().replace(R.id.content_frame, new FragmentPedidos()).commit();
                break;
            case 2:
                fragmentManager.beginTransaction().replace(R.id.content_frame, new FragmentClientes()).commit();
                break;

        }

        navigationAdapter.setChecked(posicao, true);
        setTitleFragments(lastPosition);
        navigationAdapter.resetarCheck();
        layoutDrawer.closeDrawer(linearDrawer);

    }
13
AND4011002849

Вы можете сделать это таким образом, чтобы избежать задержки, измените onItemClick:

layoutDrawer.closeDrawer(linearDrawer);
setLastPosition(posicao);
new Handler().postDelayed(new Runnable() {
        @Override
        public void run() {
            setFragmentList(lastPosition);
        }
    }, 200);

Edit: предпочтительным способом должна быть установка DrawerListener на DrawerLayout и установка вашего фрагмента в onDrawerClosed Следующим образом:

Fragment mFragmentToSet = null;

@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
    // Handle navigation view item clicks here.
    switch (item.getItemId()) {
        case R.id.nav_home:
            mFragmentToSet = HomeFragment.newInstance(); 
            break;
    }

    mDrawerLayout.closeDrawer(GravityCompat.START);
    return true;
}

mDrawerLayout.addDrawerListener(new DrawerLayout.DrawerListener() {
        @Override public void onDrawerSlide(View drawerView, float slideOffset) {}
        @Override public void onDrawerOpened(View drawerView) {}
        @Override public void onDrawerStateChanged(int newState) {}

        @Override
        public void onDrawerClosed(View drawerView) {
          //Set your new fragment here
          if (mFragmentToSet != null) {
            getSupportFragmentManager()
                  .beginTransaction()
                  .replace(FRAGMENT_CONTAINER_ID, mFragmentToSet)
                  .commit();
            mFragmentToSet = null;
          }
        }
    });
30
Yuraj

Вместо того, чтобы делать транзакции в onClick, почему бы не сделать это в onDrawerClosed из DrawerLayout.DrawerListener?

18
uDevel

Я думаю, что нашел лучшее решение для этого! 

Сначала сделайте вашу транзакцию фрагмента так:

new Handler().post(new Runnable() {
                @Override
                public void run() {
                    getSupportFragmentManager()
                            .beginTransaction()
                            .setCustomAnimations(Android.R.anim.fade_in, Android.R.anim.fade_out)
                            .replace(R.id.container, finalMenuFragment)
                            .commit();
                }
            });

Я знаю, что публиковать Runnable выглядит бесполезно, но этот хак позволяет избежать задержки анимации щелчков в ящике, особенно когда вы используете Android:background="?attr/selectableItemBackground" для кликабельного элемента.

И затем вы закрываете секцию AT функции КОНЕЦ onResume () вашего фрагмента (в данном примере это «finalMenuFragment») следующим образом:

 new Handler().post(new Runnable() {
        public void run() {

            mDrawerLayout.closeDrawer(mFragmentContainerView);
        }
    });

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

Таким образом, ящик будет закрываться настолько быстро, насколько это возможно, если вы хотите сгладить анимацию, и если у вашего фрагмента мало просмотров, он закроется быстрее и без задержки.

Я хотел бы получить некоторые отзывы об этом, если кто-нибудь протестировал это решение, надеюсь, оно поможет!

7
Quentin G.

Я только что решил эту проблему просто One-Line

перейдите в файл Manifest В своем ящике Activity просто поместите HardwareAccelerated true , чтобы предотвратить задержку открытия ящика

<activity
        Android:name=".activity.YourDrawerActivity"
        Android:configChanges="keyboardHidden|orientation"
        Android:screenOrientation="portrait"
        Android:hardwareAccelerated="true"  //important 
        Android:theme="@style/AppTheme.NoActionBar"
        Android:windowSoftInputMode="stateHidden" />
5
Darshan

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

 Android:hardwareAccelerated="true"

если ваш метод oncreate добавить этот код

getWindow().setFlags(
    WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED,
    WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED);

теперь у вас есть аппаратное ускорение в вашей деятельности . источник: https://developer.Android.com/guide/topics/graphics/hardware-accel.html

2
sajad abbasi

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

Внутри MainActivity

private BroadcastReceiver xBroadcastReceiver = new BroadcastReceiver() {
    @Override
    public void onReceive(Context context, Intent intent) {
        if (Drawer.isDrawerOpen(GravityCompat.START)){
            Drawer.closeDrawers();
        }
    }
};

@Override
protected void onStart() {
    super.onStart();
    IntentFilter filter = new IntentFilter();
    filter.addAction("my.drawer.listener");
    this.registerReceiver(xBroadcastReceiver, filter);
}

@Override
public void onDestroy() {
    super.onDestroy();
    this.unregisterReceiver(xBroadcastReceiver);
}

Внутренняя деятельность или фрагмент

@Override
public void onStart() {
    super.onStart();
    Intent intent = new Intent();
    intent.setAction("my.drawer.listener");
    getActivity().sendBroadcast(intent);
}

вы можете изменить его на более ранний процесс с onCreate или onAttach, но это зависит от вашего приложения.

1
Azizi Musa

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

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

Я предпочитаю выполнять транзакцию сразу после щелчка по навигации, после чего закройте ящик с помощью postDelayed 200 мс (при проверке работоспособности на случай, если она не равна нулю) . Фрагмент открывается непосредственно перед тем, как ящик начинает закрываться.

Не только задержка от нажатия до тех пор, пока закрытие выдвижного ящика не короче, чем закрытие выдвижного ящика и появление следующего фрагмента, это лучше UX, поскольку пользователь убирает палец с экрана - задержка менее заметна.

0
Deividas Strioga