Segarkan Fragmen saat memuat ulang


110

Dalam aplikasi android saya memuat data dari Db ke TableViewdalam a Fragment. Tapi ketika saya reload Fragmentitu menampilkan data sebelumnya. Dapatkah saya mengisi kembali Fragmentdengan data saat ini daripada data sebelumnya?


tolong tunjukkan kami beberapa kode. Di mana Anda memuat data Anda, di mana Anda memulai fragmen Anda, di mana Anda menyimpan nilai-nilai Anda?
SEBAGAI

Ini akan menyelesaikan masalah yang dijelaskan secara kasar: stackoverflow.com/questions/6503189/…
Benjamin W.

berikan potongan kode info lebih lanjut
nikvs

Coba gunakan Gesek untuk Menyegarkan Aplikasi Anda, lihat stackoverflow.com/questions/41469040/fragment-refresh/…
Imtiaz Mamun

Jawaban:


207

Saya rasa Anda ingin menyegarkan konten fragmen setelah pembaruan db

Jika demikian, lepaskan pecahannya dan pasang kembali

// Reload current fragment
Fragment frg = null;
frg = getSupportFragmentManager().findFragmentByTag("Your_Fragment_TAG");
final FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.detach(frg);
ft.attach(frg);
ft.commit();

Your_Fragment_TAG adalah nama yang Anda berikan pada fragmen Anda saat membuatnya

Kode ini untuk pustaka dukungan.

Jika Anda tidak mendukung perangkat lama, cukup gunakan getFragmentManager, bukan getSupportFragmentManager

[EDIT]

Metode ini membutuhkan Fragmen untuk memiliki tag.
Jika Anda tidak memilikinya, maka metode @ Hammer adalah yang Anda butuhkan.


3
Ini memberikan kesalahan berikut - java.lang.RuntimeException: Kegagalan mengirimkan hasil ResultInfo {who = null, request = 2, result = 3, data = null} ke aktivitas {xont.virtusel.v4.controller / xont.virtusel.v4.controller .sale.InvocieBrandActivity}: java.lang.IllegalStateException: Tidak dapat melakukan tindakan ini setelah onSaveInstanceState
Samantha Withanage

1
@Elizabeth memastikan Fragmen Anda memiliki tag yang disetel dengan benar
Phantômaxx

1
@Rotwang Terima kasih atas balasan Anda Saya hanya mengambil jalan pintas daripada melakukan kode panjang tetapi itu membantu membuka jalan :)
Si8

1
Solusi ini tidak berfungsi lagi di versi baru support-v4-library (25.1.0). Penjelasannya di sini: stackoverflow.com/questions/41270858/…
Brahim Bouaboud

1
Peringatan: trik ini hanya berfungsi di Oreo jika Anda menggunakan Support Fragment!
balapan

146

Ini akan menyegarkan fragmen saat ini:

FragmentTransaction ft = getFragmentManager().beginTransaction();
if (Build.VERSION.SDK_INT >= 26) {
   ft.setReorderingAllowed(false);
}
ft.detach(this).attach(this).commit();

1
di mana meletakkan kode ini? di dalam aktivitas atau fragmen itu sendiri?
Narendra Singh

2
Anda memasukkannya ke dalam fragmen yang perlu di-refresh.
Mbengue Assane

1
@ SagarChavada di mana Anda meletakkan kode? Anda harus meletakkannya di acara satu kali seperti saat data di-refresh.
Mbengue Assane

5
Rekursi, rekursi, panggilan tak berujung
zulkarnain shah

2
Menggunakan ini membuat dalam onResume di fragmen membuat loop, bagaimana cara menghindarinya?
Soul

32

Jika Anda tidak memiliki tag fragmen, kode berikut berfungsi dengan baik untuk saya.

Fragment currentFragment = getActivity().getFragmentManager().findFragmentById(R.id.fragment_container);
if (currentFragment instanceof "NAME OF YOUR FRAGMENT CLASS") {
 FragmentTransaction fragTransaction =   (getActivity()).getFragmentManager().beginTransaction();
 fragTransaction.detach(currentFragment);
 fragTransaction.attach(currentFragment);
 fragTransaction.commit();}
}

1
apa yang akan menjadi ID fragmen, saya belum mendeklarasikan id fragmen di mana pun. Bagaimana dan di mana mendeklarasikannya?
Narendra Singh

Sepertinya tidak dapat digunakan getActivity()dalam Aktivitas saya. Haruskah saya gunakan Activity.this...?
Si8

@NarendraJi, hanya ID FrameLayout saja yang tempat Anda meletakkan fragmen di container.
Lokesh

Harap hapus penjepit ekstra itu. Itu menyebabkan banyak masalah bagi saya.
Abhishek

9

Anda dapat menyegarkan fragmen Anda saat terlihat oleh pengguna, cukup tambahkan kode ini ke dalam Fragmen Anda, ini akan menyegarkan fragmen Anda saat terlihat.

@Override
public void setUserVisibleHint(boolean isVisibleToUser) {
    super.setUserVisibleHint(isVisibleToUser);
    if (isVisibleToUser) {
        // Refresh your fragment here          
  getFragmentManager().beginTransaction().detach(this).attach(this).commit();
        Log.i("IsRefresh", "Yes");
    }
}

sangat lambat sehingga membutuhkan waktu 3 detik hingga dimuat ulang
Omar Boshra

Ini tampaknya bekerja dengan baik dengan adaptor viewpager
DragonFire

2
setUserVisibleHint tidak digunakan lagi
Sai Aditya

Bekerja untuk saya, terima kasih atas solusinya.
hetsgandhi

7

Untuk menyegarkan fragmen, jawaban yang diterima tidak akan berfungsi di Nougat dan versi di atasnya. Untuk membuatnya bekerja pada semua os yang dapat Anda lakukan berikut ini.

    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
        fragmentManager.beginTransaction().detach(this).commitNow();
        fragmentManager.beginTransaction().attach(this).commitNow();
    } else {
        fragmentManager.beginTransaction().detach(this).attach(this).commit();
    }

5

Anda tidak dapat memuat ulang fragmen saat itu dilampirkan ke suatu Kegiatan, di mana Anda mendapatkan Fragment Already Addedpengecualian " ".

Jadi, fragmen pertama-tama harus dilepaskan dari aktivitasnya, lalu dilampirkan. Semua bisa dilakukan dengan menggunakan api fasih dalam satu baris:

getFragmentManager().beginTransaction().detach(this).attach(this).commit();

Pembaruan: Ini untuk menggabungkan perubahan yang dilakukan pada API 26 dan di atasnya:

FragmentTransaction transaction = mActivity.getFragmentManager()
                        .beginTransaction();
                if (Build.VERSION.SDK_INT >= 26) {
                    transaction.setReorderingAllowed(false);
                }
                transaction.detach(this).attach
                        (this).commit();

Untuk penjelasan lebih lanjut tentang pembaruan, silakan lihat https://stackoverflow.com/a/51327440/4514796


2
Harap berikan jawaban Anda dengan deskripsi yang jelas. Jangan menulis kodenya, berikan penjelasan tentang kode yang telah anda bagikan, agar orang lain juga bisa mengerti dan akan sangat membantu. Saya meminta Anda untuk membaca Bagian FAQ untuk menggunakan Stack Overflow secara efektif.
Sankar Ganesh

3
   MyFragment fragment = (MyFragment) getSupportFragmentManager().findFragmentByTag(FRAGMENT_TAG);
        getSupportFragmentManager().beginTransaction().detach(fragment).attach(fragment).commit();

ini hanya akan berfungsi jika Anda menggunakan FragmentManageruntuk menginisialisasi fragmen. Jika Anda memilikinya sebagai <fragment ... />XML, itu tidak akan memanggil onCreateViewlagi. Membuang waktu 30 menit saya untuk memikirkan hal ini.


1

Di sini yang saya lakukan dan berhasil untuk saya, saya menggunakan firebase dan ketika pengguna masuk, saya ingin menyegarkan Fragmen saat ini terlebih dahulu, Anda perlu meminta konteks dari aktivitas karena fragmen tidak memiliki cara untuk mendapatkan konteks kecuali Anda menyetelnya dari Aktivitas atau konteks di sini adalah kode yang saya gunakan dan bekerja dalam bahasa kotlin saya pikir Anda bisa menggunakan yang sama di kelas java

   override fun setUserVisibleHint(isVisibleToUser: Boolean) {
    super.setUserVisibleHint(isVisibleToUser)
    val context = requireActivity()
    if (auth.currentUser != null) {
        if (isVisibleToUser){
            context.supportFragmentManager.beginTransaction().detach(this).attach(this).commit()
        }
    }

}

0

Gunakan ContentProviderdan muat data Anda menggunakan 'CursorLoader'. Dengan arsitektur ini, data Anda akan dimuat ulang secara otomatis pada perubahan database. Gunakan kerangka kerja pihak ketiga untuk Anda ContentProvider- Anda tidak benar-benar ingin menerapkannya sendiri ...


0

Saya memiliki masalah yang sama tetapi tidak satu pun di atas yang berhasil untuk masalah saya. baik ada masalah backstack (setelah memuat ketika pengguna menekan kembali itu akan pergi ke fragmen yang sama lagi) atau tidak memanggilonCreaetView

akhirnya saya melakukan ini:

public void transactFragment(Fragment fragment, boolean reload) {
    FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
    transaction.setTransition(FragmentTransaction.TRANSIT_FRAGMENT_FADE);
    if (reload) {
        getSupportFragmentManager().popBackStack();
    }
    transaction.replace(R.id.main_activity_frame_layout, fragment);
    transaction.addToBackStack(null);
    transaction.commit();
}

Poin bagusnya adalah Anda juga tidak memerlukan tag atau id dari fragmen. jika Anda ingin memuat ulang


0

Manfaatkan metode onResume ... baik pada aktivitas fragmen maupun aktivitas yang menahan fragmen.


0
getActivity().getSupportFragmentManager().beginTransaction().replace(GeneralInfo.this.getId(), new GeneralInfo()).commit();

GeneralInfo ini kelas Fragmen saya GeneralInfo.java

Saya meletakkannya sebagai metode di kelas fragmen:

public void Reload(){
    getActivity().getSupportFragmentManager().beginTransaction().replace(LogActivity.this.getId(), new LogActivity()).commit();
}

0

Misalnya dengan TabLayout: cukup terapkan OnTabSelectedListener. Untuk memuat ulang halaman, Anda dapat menggunakan implementasi SwipeRefreshLayout.OnRefreshListener yaitupublic class YourFragment extends Fragment implements SwipeRefreshLayout.OnRefreshListener {

metode onRefresh () akan menjadi @Override dari antarmuka yaitu:

@Override
public void onRefresh() {
 loadData();
}

Berikut tata letaknya:

<com.google.android.material.tabs.TabLayout
    android:id="@+id/tablayout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:background="@color/colorPrimaryLighter"
    app:tabGravity="fill"
    app:tabIndicatorColor="@color/white"
    app:tabMode="fixed"
    app:tabSelectedTextColor="@color/colorTextPrimary"
    app:tabTextColor="@color/colorTextDisable" />

Kode dalam aktivitas Anda

TabLayout tabLayout = (TabLayout) findViewById (R.id.tablayout); tabLayout.setupWithViewPager (viewPager);

    tabLayout.addOnTabSelectedListener(new TabLayout.OnTabSelectedListener() {
        @Override
        public void onTabSelected(TabLayout.Tab tab) {
            if (tab.getPosition() == 0) {
                yourFragment1.onRefresh();
            } else if (tab.getPosition() == 1) {
                yourFragment2.onRefresh();
            }
        }

        @Override
        public void onTabUnselected(TabLayout.Tab tab) {

        }

        @Override
        public void onTabReselected(TabLayout.Tab tab) {

        }
    });

-2
protected void onResume() {
        super.onResume();
        viewPagerAdapter.notifyDataSetChanged();
    }

Lakukan tulis viewpagerAdapter.notifyDataSetChanged (); di onResume () di MainActivity. Semoga berhasil :)


-2

Cara termudah

buat metode statis publik yang berisi viewpager.setAdapter

membuat adaptor dan viewpager statis

public static void refreshFragments(){
        viewPager.setAdapter(adapter);
    }

panggil di mana saja, aktivitas apa pun, fragmen apa pun.

MainActivity.refreshFragments();
Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.