Show fragment inside viewpager from another fragment - android

Hello I'm developing an android app using 3 Fragments (Fragment A, B, C) inside viewpager and tabs, the viewpager works fine. The fragment A contains a List View, when the user clicks a item, the app open a Fragment Dialog with information about the item selected. This dialog has a button called "Add to favorites". Now I want to do this when user press button:
close the fragment dialog
show the fragment B inside the view pager
send the information from dialog fragment to fragment B
How can I do this?
This is part of my code:
* MainFragmentActivity * (This works fine)
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_tube);
// Set up the action bar.
final ActionBar actionBar = getSupportActionBar();
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
// Create the adapter that will return a fragment for each of the three
// primary sections of the activity.
mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());
// Set up the ViewPager with the sections adapter.
mViewPager = (ViewPager) findViewById(R.id.pager);
mViewPager.setAdapter(mSectionsPagerAdapter);
// When swiping between different sections, select the corresponding
// tab. We can also use ActionBar.Tab#select() to do this if we have
// a reference to the Tab.
mViewPager
.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
#Override
public void onPageSelected(int position) {
actionBar.setSelectedNavigationItem(position);
}
});
for (int i = 0; i < mSectionsPagerAdapter.getCount(); i++) {
actionBar.addTab(actionBar.newTab()
.setText(mSectionsPagerAdapter.getPageTitle(i))
.setTabListener(this));
}
}
#Override
public void onTabSelected(ActionBar.Tab tab,
FragmentTransaction fragmentTransaction) {
// When the given tab is selected, switch to the corresponding page in
// the ViewPager.
mViewPager.setCurrentItem(tab.getPosition());
}
#Override
public void onTabUnselected(ActionBar.Tab tab,
FragmentTransaction fragmentTransaction) {
}
#Override
public void onTabReselected(ActionBar.Tab tab,
FragmentTransaction fragmentTransaction) {
}
public class SectionsPagerAdapter extends FragmentPagerAdapter {
public SectionsPagerAdapter(FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int position) {
switch (position) {
case 0:
FragmentA a = new FragmentA();
Bundle args1 = new Bundle();
args1.putInt(FragmentA.ARG_SECTION_NAME , position + 1);
a.setArguments(args1);
return a;
case 1:
FragmentB b= new FragmentB();
Bundle args2 = new Bundle();
args2.putInt(FragmentB.ARG_SECTION_NAME , position + 2);
b.setArguments(args2);
return b;
case 2:
FragmentC c= new FragmentC();
Bundle args3 = new Bundle();
args3.putInt(FragmentC.ARG_SECTION_NAME , position + 3);
c.setArguments(args3);
return c;
default:
return null;
}
}
This is the Fragment Dialog
* FragmentDialogView *
public class FragmentDialogView extends DialogFragment implements OnClickListener {
private static final int REAUTH_ACTIVITY_CODE = 0;
private String videoId;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
Bundle mArgs = getArguments();
View view = (View) inflater.inflate(R.layout.fragment_dialog_view, container, false);
//Buttons
Button button = (Button) view.findViewById(R.id.button_one);
button.setOnClickListener(this);
buttonDownload.setOnClickListener(this);
return view;
}
#Override
public void onSaveInstanceState(Bundle bundle) {
super.onSaveInstanceState(bundle);
}
#Override
public void onResume() {
super.onResume();
}
#Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == REAUTH_ACTIVITY_CODE) {
}
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.button_one:
//Here it should show the fragment B inside the viewpager
break;
default:
break;
}
}
}

To dismiss the Dialog include the following in your DialogFragment's class
private Dialog dialog;
#Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
dialog = new Dialog(getActivity());
return dialog;
}
#Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.button_one:
dismiss();
break;
default:
break;
}
}
And create a interface
Create the following Communicator.java
public interface Communicator {
public void respond(int i);
}
Implement this Communicator in your MainAcitvity
And create a instance of this Communicator in your fragment like this
public class FragmentDialogView extends DialogFragment implements OnClickListener {
private Communicator com;
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
com = (Communicator) getActivity();
btn.setOnClickListener(this);
}
#Override
public void onClick(View view) {
switch (view.getId()) {
case R.id.btn:
com.respond(1);
break;
}
}
Whenever you click that button it sends the int to the method which is residing inside the MainActivity
which will look like following
#Override
public void respond(int i) {
// Receive a bundle here
// and pass the corresponding information to the FragmentB
// here i'm receving an int and pass it to the FragmentB as a String
FragmentManager fm = getFragmentManager();
FragmentB fragment = (FragmentB) fm.findFragmentByTag("FragmentB");
fragment.fromMainActivity(""+i);
// If the above the one doesn't work keep the instance as Static and then try
viewPager.invalidate();
pagerAdapter.notifyDataSetChanged();
viewPager.setCurrentItem(1, true);
// Inside the setCuttentItem() method 0 first tab
// 1 second tab
// 2 third tab and so on
}
Here I'm receiving an int . You can use a bundle to pass the corresponding information. This will change the viewPager to show the next tab as well
and keep any simple method insdie the FragmentB like the following
public void fromMainActivity(String sample) {
Toast.makeText(getActivity(), sample, duration).show();
}
I hope this would help :) Happy coding

1.Try this : getDialog().dismiss();
2.As I understood correctly, create a method like this in your fragment ,
public static FirstFragment newInstance(String text){
FirstFragment f= new FirstFragment();
return f;
}
Call it in your button onClick() such as FirstFragment.newInstance("Fragment, Instance 1");
3.Create Interface with the method in your DialogFragment can call to pass any data you want back to Fragment that created said DialogFragment. Also set your Fragment as target such as myFragmentDialog.setTargetFragment(this, 0). Then in dialog, get your target fragment object with getTargetFragment() and cast to interface you created. Now you can pass the data using ((MyInterface)getTargetFragment()).methodToPassData(data).
For more info : link

Related

Android refresh a fragment list from its parent activity

I have a main activity which contains the action bar with 3 menu buttons in it.
I then have a fragment within this main activity which has a list.
I would like to be able to refresh the list in the fragment from the main activity, when one of the menu buttons is clicked, or preferably just removed all the rows from the list.
Any help is appreciated.
Thanks.
public class Favourite extends SherlockFragmentActivity {
ActionBar actionBar;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.favourite);
actionBar = getSupportActionBar();
actionBar.setDisplayShowTitleEnabled(false);
BitmapDrawable bg = (BitmapDrawable)getResources().getDrawable(R.drawable.actionbar_bg);
bg.setTileModeX(TileMode.REPEAT);
getSupportActionBar().setBackgroundDrawable(bg);
getSupportActionBar().setIcon(R.drawable.favourite_title);
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
ActionBar.Tab tabAll = actionBar.newTab();
ActionBar.Tab tabfavs = actionBar.newTab();
ActionBar.Tab tabhist = actionBar.newTab();
tabAll.setText("all");
tabfavs.setText("favs");
tabhist.setText("hist");
tabAll.setTabListener(new MyTabListener());
tabfavs.setTabListener(new MyTabListener());
tabhist.setTabListener(new MyTabListener());
actionBar.addTab(tabAll);
actionBar.addTab(tabfavs);
actionBar.addTab(tabhist);
try{
}
catch(Exception e)
{
}
}
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getSupportMenuInflater();
inflater.inflate(R.menu.actionbar_itemlist_favourite, menu);
return true;
}
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch(item.getItemId()) {
case R.id.history:
break;
case R.id.favourite:
Intent favAct = new Intent(this, Favourite.class);
startActivity(favAct);
break;
case R.id.delete:
///I WANT TO BE ABLE TO REFRESH FRAGMENTLIST FROM HERE
}
return true;
}
}
class MyTabListener implements ActionBar.TabListener {
public void onTabSelected(Tab tab, FragmentTransaction ft) {
if(tab.getPosition()==0)
{
FavouriteAllWords frag = new FavouriteAllWords();
ft.replace(android.R.id.content, frag);
}
else if(tab.getPosition()==1)
{
FavouriteFavWords frag = new FavouriteFavWords();
ft.replace(android.R.id.content, frag);
}
else if(tab.getPosition()==2)
{
FavouriteHistWords frag = new FavouriteHistWords();
ft.replace(android.R.id.content, frag);
}
}
public void onTabUnselected(Tab tab, FragmentTransaction ft) {
// TODO Auto-generated method stub
}
public void onTabReselected(Tab tab, FragmentTransaction ft) {
// TODO Auto-generated method stub
}
}
////////////////////MY LIST FRAGMENT CLASS
public class FavouriteAllWords extends ListFragment {
ArrayAdapter<String> adapter;
List<String> stringOfFavWords;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup group, Bundle saved)
{
adapter = new ArrayAdapter<String>(
inflater.getContext(), R.layout.row, stringOfFavWords);
setListAdapter(adapter);
return super.onCreateView(inflater, group, saved);
}
#Override
public void onActivityCreated (Bundle savedInstanceState)
{
super.onActivityCreated(savedInstanceState);
}
}
You can easily achieve this using INTERFACE
MainActivity.java
public class MainActivity extends Activity {
public FragmentRefreshListener getFragmentRefreshListener() {
return fragmentRefreshListener;
}
public void setFragmentRefreshListener(FragmentRefreshListener fragmentRefreshListener) {
this.fragmentRefreshListener = fragmentRefreshListener;
}
private FragmentRefreshListener fragmentRefreshListener;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
Button b = (Button)findViewById(R.id.btnRefreshFragment);
b.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
if(getFragmentRefreshListener()!=null){
getFragmentRefreshListener().onRefresh();
}
}
});
}
public interface FragmentRefreshListener{
void onRefresh();
}
}
MyFragment.java
public class MyFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = null; // some view
/// Your Code
((MainActivity)getActivity()).setFragmentRefreshListener(new MainActivity.FragmentRefreshListener() {
#Override
public void onRefresh() {
// Refresh Your Fragment
}
});
return v;
}
}
Just make your update/refresh method public and call it from your Activity.
OR
Use LocalBroadcastManager or EventBus to send event from your Activity, and by subscribing to this event in a Fragment - react to it and call refresh/update method.
Your activity can call methods in the fragment by acquiring a reference to the Fragment.
(1) Provide a tag when you add your fragment.
transaction.add(R.id.fragment_container, myFragment, "myfragmentTag");
(2) In your hosting activity you can find the fragment and have access to it's methods.
FragmentManager fm = getSupportFragmentManager();
myFragment f = (myFragment) fm.findFragmentByTag("myfragmentTag");
f.refreshAdapter()
(3) refreshAdapter() could now call adapter.notifyDataSetChanged().
This is one of the recommended ways to communicate up to a fragment.
The interface implementation is mainly for communicating back to the activity.
Biraj Zalavadia's answer is 100% right, you will call nay fragment methods from using interface....
this interface methods is running without error...
use this in MainActivity above oncreate
private FragmentRefreshListener fragmentRefreshListener;
public FragmentRefreshListener getFragmentRefreshListener() {
return fragmentRefreshListener;
}
public void setFragmentRefreshListener(
FragmentRefreshListener fragmentRefreshListener) {
this.fragmentRefreshListener = fragmentRefreshListener;
}
inside of Activity
private void refreshcall(String result2) {
// TODO Auto-generated method stub
if (getFragmentRefreshListener() != null) {
getFragmentRefreshListener().onRefresh(result2);
}
}
and put this in needed Fragment
private FragmentRefreshListener fragmentRefreshListener;
public FragmentRefreshListener getFragmentRefreshListener() {
return fragmentRefreshListener;
}
public void setFragmentRefreshListener(
FragmentRefreshListener fragmentRefreshListener) {
this.fragmentRefreshListener = fragmentRefreshListener;
}
Communicating with Other Fragments
http://developer.android.com/training/basics/fragments/communicating.html
This can also be used to communicate between an Activity and a Fragment.
When you click on ActionBar any Button then call interface to refresh the ListFragment. Because in java interface is used for inter-communication.
In Kotlin
Get the list of Support Fragment from the activity and check Instance and then call fragment function
val fragments = supportFragmentManager.fragments
for (fragment in fragments) {
if (fragment is HomeCategoriesFragment) {
fragment.updateAdapter() // Define function in Fragment
}
}

How to handle AsyncTask's in ActionBarActivity Fragments when ViewPager is used?

I'm using ActionBarActivity to create 5 tabs. I have used ViewPager to swipe between the 5 tabs using SectionsPagerAdapter which extends FragmentPagerAdapter. Each tab has a fragment with an asynctask called in oncreateview method. When I'm in one fragment, asynctask in other fragment is being called.
I tried using toast messages in oncreateview method is each fragment instead of asynctask. But wrong toast messages are being fired in wrong fragment.
Oncreate method code:
mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());
mViewPager = (ViewPager) findViewById(R.id.pager_exp);
mViewPager.setAdapter(mSectionsPagerAdapter);
mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
#Override
public void onPageSelected(int position)
{
actionBar.setSelectedNavigationItem(position);
actionBar.setTitle(getHomePageTitle(position));
}
});
for (int i = 0; i < mSectionsPagerAdapter.getCount(); i++)
{
// Create a tab with text corresponding to the page title defined by
// the adapter. Also specify this Activity object, which implements
// the TabListener interface, as the callback (listener) for when
// this tab is selected.
actionBar.addTab(actionBar.newTab()
.setIcon(getPagedrawable(i))
.setTabListener(this));
}
// Adapter class code:
public class SectionsPagerAdapter extends FragmentPagerAdapter {
public SectionsPagerAdapter(FragmentManager fm)
{
super(fm);
}
#Override
public Fragment getItem(int position) {
switch (position)
{
case 0:
Fragment1 f1 = new Fragment1();
return f1;
case 1:
Fragment2 f2 = new Fragment2();
return f2;
case 2:
Fragment3 f3 = new Fragment3();
return f3;
case 3:
Fragment4 f4 = new Fragment4();
return f4;
case 4:
Fragment5 f5 = new Fragment5();
return f5;
}
return null;
}
#Override
public int getCount() {
// Show 5 total pages.
return 5;
}
}
Fragemnt class code :
public class F1 extends Fragment
{
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
}
#SuppressLint("NewApi")
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState)
{
View view = inflater.inflate(R.layout.f1,container, false);
Toast.makeText(getActivity(), "F1", Toast.LENGTH_SHORT).show();
return view;
}
}
The FragmentPagerAdapter keeps additional fragments, besides the one shown, in resumed state. The solution is to implement a custom OnPageChangeListener and create a new method for when the fragment is shown.
1) Create LifecycleManager Interface
The interface will have two methods and each ViewPager’s Fragment will implement it. These methods Are as follows:
public interface FragmentLifecycle {
public void onPauseFragment();
public void onResumeFragment();
}
2) Let each Fragment implement the interface
Add iplements statement for each class declaration:
public class FragmentBlue extends Fragment implements FragmentLifecycle
public class FragmentGreen extends Fragment implements FragmentLifecycle
public class FragmentPink extends Fragment implements FragmentLifecycle
3) Implement interface methods in each fragment
In order to check that it really works as expected, I will just log the method call and show Toast:
#Override
public void onPauseFragment() {
Log.i(TAG, "onPauseFragment()");
Toast.makeText(getActivity(), "onPauseFragment():" + TAG, Toast.LENGTH_SHORT).show();
}
#Override
public void onResumeFragment() {
Log.i(TAG, "onResumeFragment()");
Toast.makeText(getActivity(), "onResumeFragment():" + TAG, Toast.LENGTH_SHORT).show();
}
4) Call interface methods on ViewPager page change
You can set OnPageChangeListener on ViewPager and get callback each time when ViewPager shows another page:
pager.setOnPageChangeListener(pageChangeListener);
5) Implement OnPageChangeListener to call your custom Lifecycle methods
Listener knows the new position and can call the interface method on new Fragment with the help of PagerAdapter. I can here call onResumeFragment() for new fragment and onPauseFragment() on the current one.
I need to store also the current fragment’s position (initially the current position is equal to 0), since I don’t know whether the user scrolled from left to right or from right to left. See what I mean in code:
private OnPageChangeListener pageChangeListener = new OnPageChangeListener() {
int currentPosition = 0;
#Override
public void onPageSelected(int newPosition) {
FragmentLifecycle fragmentToShow = (FragmentLifecycle)pageAdapter.getItem(newPosition);
fragmentToShow.onResumeFragment();
FragmentLifecycle fragmentToHide = (FragmentLifecycle)pageAdapter.getItem(currentPosition);
fragmentToHide.onPauseFragment();
currentPosition = newPosition;
}
#Override
public void onPageScrolled(int arg0, float arg1, int arg2) { }
public void onPageScrollStateChanged(int arg0) { }
};
I didn't write the code. Full tutorial here: http://looksok.wordpress.com/2013/11/02/viewpager-with-detailed-fragment-lifecycle-onresumefragment-including-source-code/
Use this
viewPager.setOffscreenPageLimit(1); // the number of pages you want to load in background
and also a ProgressDialogue.
ViewPager creates views for fragments adjacent to your current page. This also gives you an opportunity to load any data required for the adjacent fragments. If you are using AsyncTasks to load data, using this feature will result in a better user experience. But if you need an event when a particular page is opened by the viewpager, LordRaydenMK's solution will work.
See my post on the following thread for using AsyncTasks in a ViewPager:
AsyncTask runs on each page of the ViewPager
Hi You can try by using tag of each fragment and call method of each fragment on Page Changed
mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
#Override
public void onPageSelected(int position) {
actionBar.setSelectedNavigationItem(position);
actionBar.setTitle(getHomePageTitle(position));
Fragment f = getFragrmentManager().findFragmentByTag(
"" + position);
if (f != null)
f.refresh();
}
});
and on
#Override
public Fragment getItem(int position) {
Fragment f=null;
switch (position)
{
case 0:
f = new Fragment1();
break;
case 1:
f = new Fragment2();
break;
case 2:
f = new Fragment3();
break;
case 3:
f = new Fragment4();
break;
case 4:
f = new Fragment5();
break;
}
f.setTag(""+position);
return f;
}

Open fragment from a fragment in android

I have a Activity extending to FragmentActivity which has 4 fragments. I now want to open fragment2 on button click which is present in fragment1.
In short I want to switch from fragment1 to fragment 2 on button click.
My code is:
public class SampleActivity extends FragmentActivity{
static ViewPager mViewPager;
PagingAdapter TabAdapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
TabAdapter = new PagingAdapter(getSupportFragmentManager(), this);
mViewPager = (ViewPager) findViewById(R.id.pager);
mViewPager.setAdapter(TabAdapter);
}
public class PagingAdapter extends FragmentPagerAdapter {
private Context context;
public PagingAdapter(FragmentManager fm, Context context) {
super(fm);
this.context = context;
}
#Override
public Fragment getItem(int i) {
switch(i){
case 0:
return new Fragment1();
case 1:
return new Fragment2();
case 2:
return new Fragment3();
case 3:
return new Fragment4();
}
return null;
}
#Override
public int getCount() {
return 4;
}
#Override
public CharSequence getPageTitle(int position) {
switch(position){
case 0:
return context.getString(R.string.page_tab_1);
case 1:
return context.getString(R.string.page_tab_2);
case 2:
return context.getString(R.string.page_tab_3);
case 3:
return context.getString(R.string.page_tab_4);
}
return "Fragment " + (position + 1);
}
}
public class Fragment1 extends Fragment{
Button btn_close = (Button) mydeals.findViewById(R.id.btn_close);
btn_all.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
//Needs to open fragment2 here.
});
}
I have tried shifting using id but fragment4 is opening by the below code
ViewPager viewpager = DealsActivity.mViewPager;
viewpager.setCurrentItem(getId());
In your Fragment1 layout, add the attribute android:onClick="buttonClickMethod" in your Button definition. Then in your activity, add the following method :
public void buttonClickMethod(View v) {
// some code to execute after button click
// ....
// You can open fragment 2 here, like this :
FragmentManager fm = getSupportFragmentManager();
FragmentTransaction ft = fm.beginTransaction();
ft.replace(R.id.LAYOUT_ID_FOR_FRAGMENT2, FRAGMENT2);
ft.commit();
}
Note that the name of that method is the same one defined in android:onClick attribute.

Strange onPause(), onResume() behaviour in fragments

The application has a main activity (MainActivity.java) with three tabs (fragments). I can navigate between them using the swipe left (riht) or clicking on a specific tab.
Upon starting the application, the 1st fragment is shown.
If I go to the 2nd fragment from the 1st fragment and then back to the 1st fragment, nothing happens (onResume() of the 1rd fragment isn't called), so it doesn't refresh it's content.
If I go to the 3rd fragment from the 1st fragment and then directly back to the 1st fragment, the onCreateView() of fragment1 is created and it's onResume() is called, which is correct.
If I go from the 3rd fragment to the 2nd fragment, the onCreateView() and onResume() of fragment1 are called, but not the onCreateView of fragment2.
I guess the logic in MainActivity isn't right, so I would kindly ask someone to take a look and tell me what could be wrong.
MainActivity.java:
public class MainActivity extends FragmentActivity implements ActionBar.TabListener {
CollectionPagerAdapter mCollectionPagerAdapter;
public TTSocket socket;
DBHandler db;
public String logged_user;
private LogedinPerson person;
ViewPager mViewPager;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
Bundle extras = getIntent().getExtras();
logged_user = extras.getString("logged_user");
socket = TTSocket.getInstance();
socket.currentRef = this;
db = new DBHandler(this);
person=db.getLogedInPerson();
socket.dbHandler=db;
socket.person=person;
if(!socket.isInit){
String typeInitStr = "{\"Type\":\"Init\", \"UserId\":\""+ person.getUserId() +"\"}";
socket.Send(typeInitStr);
}
mCollectionPagerAdapter = new CollectionPagerAdapter(getSupportFragmentManager());
// Set up action bar.
final ActionBar actionBar = getActionBar();
// Specify that we will be displaying tabs in the action bar.
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
// Set up the ViewPager, attaching the adapter and setting up a listener
// for when the
// user swipes between sections.
mViewPager = (ViewPager) findViewById(R.id.pager);
mViewPager.setAdapter(mCollectionPagerAdapter);
mViewPager.setOnPageChangeListener(new ViewPager.SimpleOnPageChangeListener() {
#Override
public void onPageSelected(int position) {
Log.d("TEST",position+"");
// the corresponding tab.
// We can also use ActionBar.Tab#select() to do this if
// we have a reference to the Tab
actionBar.setSelectedNavigationItem(position);
}
});
// For each of the sections in the app, add a tab to the action bar.
for (int i = 0; i < mCollectionPagerAdapter.getCount(); i++) {
// Create a tab with text corresponding to the page title defined by
// the adapter.
// Also specify this Activity object, which implements the
// TabListener interface, as the
// listener for when this tab is selected.
if(i == 0){
actionBar.addTab(actionBar.newTab()
.setIcon(R.drawable.messages)
.setTabListener(this));
}else if(i == 1){
actionBar.addTab(actionBar.newTab()
.setIcon(R.drawable.contacts)
.setTabListener(this));
}else{
actionBar.addTab(actionBar.newTab()
.setIcon(R.drawable.history)
.setTabListener(this));
}
}
}
#Override
protected void onResume() {
// TODO Auto-generated method stub
super.onResume();
socket.currentRef = this;
socket.dbHandler=db;
socket.person=person;
//mCollectionPagerAdapter.notifyDataSetChanged();
}
public void onTabUnselected(ActionBar.Tab tab, FragmentTransaction fragmentTransaction) {
}
public void onTabSelected(ActionBar.Tab tab, FragmentTransaction fragmentTransaction) {
// When the given tab is selected, switch to the corresponding page in
// the ViewPager.
mViewPager.setCurrentItem(tab.getPosition());
}
public void onTabReselected(ActionBar.Tab tab, FragmentTransaction fragmentTransaction) {
}
/**
* A {#link FragmentPagerAdapter} that returns a fragment corresponding to
* one of the primary sections of the app.
*/
public class CollectionPagerAdapter extends FragmentPagerAdapter {
final int NUM_ITEMS = 3; // number of tabs
public CollectionPagerAdapter(FragmentManager fm) {
super(fm);
}
/*
#Override
public Fragment getItem(int i) {
Fragment fragment = new TabFragment();
Bundle args = new Bundle();
args.putInt(TabFragment.ARG_OBJECT, i);
fragment.setArguments(args);
return fragment;
}
*/
#Override
public Fragment getItem(int position) {
Fragment fragment = new Fragment();
Bundle args = new Bundle();
args.putInt(TabFragment.ARG_OBJECT, position);
switch (position) {
case 0:
Log.i("Fragment", "0");
fragment = new Tab1Fragment();
fragment.setArguments(args);
return fragment;
case 1:
Log.i("Fragment", "1");
fragment = new Tab2Fragment();
fragment.setArguments(args);
return fragment;
case 2:
Log.i("Fragment", "2");
fragment = new Tab3Fragment();
fragment.setArguments(args);
return fragment;
default:
break;
}
return fragment;
}
#Override
public int getCount() {
return NUM_ITEMS;
}
#Override
public CharSequence getPageTitle(int position) {
String tabLabel = null;
switch (position) {
case 0:
tabLabel = getString(R.string.label1);
break;
case 1:
tabLabel = getString(R.string.label2);
break;
case 2:
tabLabel = getString(R.string.label3);
break;
}
return tabLabel;
}
}
/**
* A fragment that launches other parts of the demo application.
*/
public static class TabFragment extends Fragment {
public static final String ARG_OBJECT = "object";
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
Bundle args = getArguments();
int position = args.getInt(ARG_OBJECT);
int tabLayout = 0;
switch (position) {
case 0:
tabLayout = R.layout.tab1;
break;
case 1:
tabLayout = R.layout.tab2;
break;
case 2:
tabLayout = R.layout.tab3;
break;
}
View rootView = inflater.inflate(tabLayout, container, false);
return rootView;
}
}
}
Strange onPause(), onResume() behaviour() in fragments
It's not strange behaviour but native behaviour of ActionSherlock. This kind of behaviour is used for caching -> optimalisation for older devices with lower RAM this is reason why fragments are cached.
If you need to update content of fragment don't try to replace its layout or something similar. If you want to update fragment when scrolling between pages, you need to use method of FragmentPagerAdapter:
#Override
public int getItemPosition(Object object) {
// implementation
return super.getItemPosition(object);
}
This method is called when you will call
notifyDataSetChanged();
on your FragmentPagerAdapter. It's handy method for make updates of your fragments. There are more ways how to do it but here i'll show you how I'm doing it.
Let your fragments implement interface for example called Updateable:
interface Updateable {
public void update();
}
public class MyFragment extends SherlockFragment implements Updateable {
#Override
public void update() {
// perform Fragment updates
}
}
And in this method you will perform updates. Now back to getItemPosition() method. This method will be used for invoking update() method from Fragment i.e:
#Override
public int getItemPosition(Object object) {
Fragment f = (Fragment) object;
// determine which fragment
if (f instanceof MyFragment) {
((MyFragment) f).update(); // invokes update() method
}
return super.getItemPosition(object);
}
Now whenever you scroll page or tap on some tab (you need also call notifyDataSetChanged()) you are able to make Fragment updates. This way is more efficient against destroying and recreating fragment(s) each time you scrolling or clicking on tabs. But how i said this is not only solution there are more possible solutions.
Note: getItemPosition() can return two values: POSITION_NONE and UNCHANGED. Difference between both is that first indicates that Fragment will be always destroyed and recreated that is not very efficient and second indicates that Fragment won't be changed (is in on right place).
For more detailed explanation look here.
That is because ViewPager doesn't hide all fragments you switch.
You can control this behaviour by setOffscreenPageLimit

How to show ListView in Tab?

I want to display ListView in Tab (after selecting this tab I want ListView to appear),so I have created Fragment class and placed ListView code in it.The main problem now is to pass fragment object to tabListener. Please, post here example, or even better show how to do that in my code. Anyway, any help will be appreciated.
public class MainActivity extends Activity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
ActionBar actionBar = getActionBar();
actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
ActionBar.Tab tabOne = actionBar.newTab().setText("One");
ActionBar.Tab tabTwo = actionBar.newTab().setText("Two");
tabOne.setTabListener(new tabListener());
tabTwo.setTabListener(new tabListener());
actionBar.addTab(tabOne);
actionBar.addTab(tabTwo);
}
protected class tabListener implements ActionBar.TabListener {
#Override
public void onTabUnselected(Tab tab, FragmentTransaction ft) {
}
#Override
public void onTabSelected(Tab tab, FragmentTransaction ft) {
}
#Override
public void onTabReselected(Tab tab, FragmentTransaction ft) {
}
};
public class FirstFragment extends ListFragment {
private ArrayList<Cinemas> cinema;
private CinemasAdapter cinemaAdapter;
private ListView list;
#Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
cinema = new Handler().handle();
cinemaAdapter = new CinemasAdapter(MainActivity.this, R.layout.movie_data_row, cinema);
setListAdapter(cinemaAdapter);
}
#Override
public void onListItemClick(ListView l, View v, int position, long id) {
Cinemas movie = cinemaAdapter.getItem(position);
Intent intent = new Intent (MainActivity.this, More.class);
intent.putExtra("Cinemas", movie);
intent.putExtra("data", movie.getBitmap());
Bundle translateBundle =
ActivityOptions.makeCustomAnimation(MainActivity.this,
R.anim.slide_in_left, R.anim.slide_out_left).toBundle();
startActivity (intent, translateBundle);
}
}
}
If you want to open up the list inside the tabTwo, you will need to create an instance of the FirstFragment class and add it to your view when you select the tab. Inside onTabSelected, create a new instance of FirstFragment if it isn't null, and add it to your view inside a container in your activity_main file. A container is a linear layout inside the view with the given amount of space that should be occupied by the fragment. In the case of a fullscreen fragment, the container is the root layout. You need only to specify an id to this layout. Once you create a new fragment, attach it by calling transaction.attach(); The final code block should be similar to this:
/** this example assumes that the fragment
* FirstFragment will be attached to tab 1
* which is at position = 0, and SecondFragment
* will be attached to tab 2, which is at
* position = 1. Also, the root layout of
* activity_main.xml has the id attribute of
* fragment_container
*/
FirstFragment firstFragment;
SecondFragment secondFragment;
#Override
public void onTabSelected(Tab tab, FragmentTransaction transaction) {
switch (tab.getPosition()) {
case 0:
if (firstFragment == null) {
firstFragment = new FirstFragment();
transaction.add(R.id.fragment_container,
firstFragment, "FIRST");
} else {
transaction.attach(firstFragment);
}
break;
case 1:
if (secondFragment == null) {
secondFragment = new SecondFragment();
transaction.add(R.id.fragment_container, secondFragment, "SECOND");
} else {
transaction.attach(secondFragment);
}
break;
}
}

Categories

Resources