I have an application where I'm using a ViewPager to slide between two Fragments. I can slide between two Fragments perfectly; but now I need to slide only half of the fragment. How to do that? Here is what I've tried:
This my MainActivity
public class MainActivity extends FragmentActivity
{
MyPageAdapter pageAdapter;
Context c;
int[] pics = {R.drawable.ic_launcher};
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
c = MainActivity.this;
pageAdapter = new MyPageAdapter(getSupportFragmentManager(), c, pics);
ViewPager pager = (ViewPager)findViewById(R.id.viewpager);
pager.setAdapter(pageAdapter);
}
}
PageAdapter.java
class MyPageAdapter extends FragmentPagerAdapter {
Context c;
int[] pics;
Fragment fragment;
public MyPageAdapter(android.support.v4.app.FragmentManager fm, Context c, int[] pics) {
super(fm);
this.c =c;
this.pics = pics;
}
#Override
public Fragment getItem(int position) {
switch(position){
case 0:return new MyFragment();
case 1: return new NewFragment();
default: return new MyFragment();
}
}
#Override
public int getCount() {
return 2;
}
}
MyFragment.java
public class MyFragment extends Fragment {
public static final String EXTRA_MESSAGE = "EXTRA_MESSAGE";
public static final MyFragment newInstance(String message,int a)
{
MyFragment f = new MyFragment();
return f;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.myfragment_layout, container, false);
TextView messageTextView = (TextView)v.findViewById(R.id.textView);
messageTextView.setText("hi");
v.setBackgroundColor(Color.parseColor("#ff0000"));
return v;
}
}
NewFragment.java
public class NewFragment extends Fragment {
public static final MyFragment newInstance(String message,int a)
{
MyFragment f = new MyFragment();
return f;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.new_fragment, container, false);
Button b1 = (Button) v.findViewById(R.id.b1);
v.setBackgroundColor(Color.parseColor("#0000ff"));
return v;
}
}
Override the getPageWidth method of PagerAdapter and make it return 0.5f;
Related
I'm a beginner who learning Android basic course
I want to make 6 fragments that have same structure (only title, image, texts will be different) by using single fragment.
I tried this code but I can see only one fragment.
MainActivity.java
public class MainActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
viewPager = (ViewPager) findViewById(R.id.fragment_container);
MoviePagerAdapter adapter = new MoviePagerAdapter(getSupportFragmentManager());
mainfragment = new MainFragment();
adapter.addItem(mainfragment);
viewPager.setAdapter(adapter);
viewPager.setOffscreenPageLimit(6);
}
ViewPager Adapter (in MainActivity)
class MoviePagerAdapter extends FragmentStatePagerAdapter {
public ArrayList<Fragment> items = new ArrayList<Fragment>();
#Override
public Fragment getItem(int position) {
return items.get(position);
}
public MoviePagerAdapter(#NonNull FragmentManager fm) {
super(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT);
}
public void addItem(Fragment item) {
items.add(item);
}
#Override
public int getCount() {
return items.size();
}
}
MainFragment.java
public class MainFragment extends androidx.fragment.app.Fragment {
#Nullable
#Override
public View onCreateView(#NonNull LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.main_frargment, container,
false);
//...
'i want to make 6fragments with datas below '
movieData = new MovieData("title1", "rate1", "grade1");
addData(movieData);
movieData = new MovieData("title2", "rate2", "grade2");
addData(movieData);
movieData = new MovieData("title3", "rate3", "grade3");
addData(movieData);
movieData = new MovieData("title4", "rate4", "grade4");
addData(movieData);
movieData = new MovieData("title5", "rate5", "grade5");
addData(movieData);
movieData = new MovieData("title6", "rate6", "grade6");
addData(movieData);
return rootView;
}
public void addData(MovieData movieData){
Bundle bundle = new Bundle();
bundle.putParcelable("data", movieData);
MainFragment mainFragment = new MainFragment();
mainFragment.setArguments(bundle);
title.setText(movieData.title);
reservation_rate.setText(movieData.getReservation_rate());
grade.setText(movieData.getGrade());
image.setImageResource(R.drawable.image6);
}
}
change your code like this:
public class MainActivity extends AppCompatActivity {
private MoviePagerAdapter adapter;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
viewPager = (ViewPager) findViewById(R.id.fragment_container);
adapter = new MoviePagerAdapter(getSupportFragmentManager());
viewPager.setAdapter(adapter);
viewPager.setOffscreenPageLimit(6);
for(int i =0;i<6;i++){
createFrag(i);
}
}
}
private void createFrag(int number) {
MainFragment fragment = new MainFragment();
Bundle args = new Bundle();
args.putInt("NUMBER",number);
fragment.setArguments(args);
adapter.addItem(fragment);
adapter.notifyDataSetChanged();
}
class MoviePagerAdapter extends FragmentStatePagerAdapter {
public ArrayList<Fragment> items = new ArrayList<Fragment>();
#Override
public Fragment getItem(int position) {
return items.get(position);
}
public MoviePagerAdapter(#NonNull FragmentManager fm) {
super(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT);
}
public void addItem(Fragment item) {
items.add(item);
}
#Override
public int getCount() {
return items.size();
}
}
and change your Fragment like this:
public class MainFragment extends androidx.fragment.app.Fragment {
//1st
private int number;
#Nullable
//this is variant 1 - with static Movie data
#Override
public View onCreateView(#NonNull LayoutInflater inflater, #Nullable
ViewGroup container, #Nullable Bundle savedInstanceState) {
ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.main_frargment,
container,
false);
//...
//2d
assert getArguments() != null;
number = getArguments().getInt("NUMBER");
switch (number) {
case 0:
MmovieData movieData1 = new MovieData("title1", "rate1",
"grade1");
addData(movieData1);
break;
case 1:
MmovieData movieData2 = new MovieData("title2", "rate2",
"grade2");
addData(movieData2);
break;
//...
}
return rootView;
}
public void addData(MovieData movieData){
title.setText(movieData.title);
reservation_rate.setText(movieData.getReservation_rate());
grade.setText(movieData.getGrade());
image.setImageResource(R.drawable.image6);
}
}
and this is variant 2 ( with dynamic data and listener)
public class MainFragment extends androidx.fragment.app.Fragment {
//1st
private int number;
#Nullable
#Override
public View onCreateView(#NonNull LayoutInflater inflater, #Nullable
ViewGroup container, #Nullable Bundle savedInstanceState) {
ViewGroup rootView = (ViewGroup) inflater.inflate(R.layout.main_frargment,
container,
false);
//...
//2d
assert getArguments() != null;
number = getArguments().getInt("NUMBER");
return rootView;
}
//some method of listener changed
public void dataChanged(MovieData movieData, int position){
if(number==position){
title.setText(movieData.title);
reservation_rate.setText(movieData.getReservation_rate());
grade.setText(movieData.getGrade());
image.setImageResource(R.drawable.image6);
}
}
I want to change the Fragment when i click the button. The fragments are in the same adapter/viewpager.
FROM THIS FRAGMENT:
public class LoginFragment extends Fragment {
TextView linkToRegister;
public static final LoginFragment newInstance()
{
LoginFragment mf = new LoginFragment();
Bundle bd = new Bundle(1);
mf.setArguments(bd);
return mf;
}
public View onCreateView(LayoutInflater inflater, final ViewGroup container, Bundle savedInstanceState )
{
View v = inflater.inflate(R.layout.fragment_login, container, false);
linkToRegister = (TextView) v.findViewById(R.id.link_to_register);
linkToRegister.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
// Change Fragment
}
});
return v;
}
}
TO THIS FRAGMENT:
public class RegisterFragment extends Fragment {
public static final String EXTRA_MESSAGE = "EXTRA_MESSAGE";
public static final RegisterFragment newInstance()
{
RegisterFragment mf = new RegisterFragment();
Bundle bd = new Bundle(1);
mf.setArguments(bd);
return mf;
}
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState )
{
View v = inflater.inflate(R.layout.fragment_register, container, false);
return v;
}
}
PagerAdapter:
public class WelcomePagerAdapter extends FragmentStatePagerAdapter {
private final List<Fragment> Welcomefragments;
public WelcomePagerAdapter(FragmentManager fm, List<Fragment> Welcomefragments) {
super(fm);
this.Welcomefragments = Welcomefragments;
}
#Override
public Fragment getItem(int position) {
return this.Welcomefragments.get(position);
}
#Override
public int getCount() {
return this.Welcomefragments.size();
}
}
Activity:
public class WelcomeActivity extends AppCompatActivity {
ViewPager welcomeViewPager;
WelcomePagerAdapter welcomePagerAdapter;
List<Fragment> welcomeFragments;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_welcome);
welcomeViewPager = (ViewPager) findViewById(R.id.viewPagerWelcome);
welcomeFragments = getWelcomeFragments();
welcomePagerAdapter = new WelcomePagerAdapter(getSupportFragmentManager(), welcomeFragments);
welcomeViewPager.setAdapter(welcomePagerAdapter);
}
public List<Fragment> getWelcomeFragments() {
List<Fragment> newFragment = new ArrayList<Fragment>();
newFragment.add(LoginFragment.newInstance());
newFragment.add(RegisterFragment.newInstance());
return newFragment;
}
}
Step 1: Define a callback interface in the Fragment and hook in the Activity when the Fragment attaches to it.
public class MyFragment extends Fragment {
public interface OnInteractionListener {
void doAction(); // Can include parameters here if needed
}
private OnInteractionListener listener;
#Override
public void onAttach(Context context) {
if (context instanceof OnInteractionListener) {
listener = (OnInteractionListener) context;
} else {
throw new ClassCastException(context + "must implement " + OnInteractionListener.class.getSimpleName());
}
super.onAttach(context);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_layout, container, false);
// ...
return v;
}
}
Step 2: Make sure your Activity implements that Interface
public class MyActivity extends AppCompatActivity implements MyFragment.OnInteractionListener {
#Override
public void doAction() {
// TODO: Implement this... e.g. switch fragments
}
...
}
Step 3: Inside the Fragment, you can invoke the callback whenever you want to perform some action
if (listener != null) {
listener.doAction();
}
From MainActivity(), get the navController and then use the navigate() function:
NavController navController = Navigation.findNavController(this,R.id.nav_host_fragment);
navController.navigate(R.id.nav_grid);
I am able to get DFragment on top of AFragment and on press back of DFragment I am getting AFragment. But the problem that I am facing is when AFragment is shown,BFragment and CFragment show their respective layouts. But when I traverse from A to D, then B and C show D's layouts only.
I have tried notifyDataSetChanged on the Adapter but still doesn't work properly. Please help
My MainActivity
public class MainActivity extends FragmentActivity {
ViewPager pager;
ViewPagerAdapter adapter;
SlidingTabLayout tabs;
CharSequence tabTitles[] = {"A", "B", "C"};
int numTabs = 3;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
adapter = new ViewPagerAdapter(getSupportFragmentManager(), tabTitles, numTabs);
pager = (ViewPager) findViewById(R.id.pager);
pager.setAdapter(adapter);
tabs = (SlidingTabLayout) findViewById(R.id.tabs);
tabs.setDistributeEvenly(true);
tabs.setCustomTabColorizer(new SlidingTabLayout.TabColorizer() {
#Override
public int getIndicatorColor(int position) {
return getResources().getColor(R.color.tabsScrollColor);
}
});
tabs.setViewPager(pager);
}
}
This is my ViewPagerAdapter
public class ViewPagerAdapter extends FragmentStatePagerAdapter {
CharSequence tabTitles[];
int numTabs;
public ViewPagerAdapter(FragmentManager fm,CharSequence tabTitles[], int numTabs) {
super(fm);
this.tabTitles = tabTitles;
this.numTabs = numTabs;
}
#Override
public Fragment getItem(int position) {
if(position==0)
return new AFragment();
else
if(position==1)
return new BFragment();
else
return new CFragment();
}
#Override
public int getCount() {
return numTabs;
}
#Override
public CharSequence getPageTitle(int position) {
return tabTitles[position];
}
}
This is my 0th fragment
public class AFragment extends Fragment{
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState){
View rootView =inflater.inflate(R.layout.a,container,false);
Button b = (Button)rootView.findViewById(R.id.b);
b.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
((MainActivity) context).getSupportFragmentManager().beginTransaction().add(R.id.container, new DFragment())
.addToBackStack("").commit();
}
});
return rootView;
}
}
This is the new fragment that comes on top of my 0th fragment
public class DFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_d,null);
return rootView;
}
}
I am trying to swipe item(from listview) in my detail activity using viewpager.
I have 20 items in my listview (data parsed from json) Instead of swiping the next/previous item , It's only the same item that I swipe (20 times).
here is my DetailActivity.
public class DetailsActivity extends FragmentActivity {
Article feed;
int pos;
private DescAdapter adapter;
private ViewPager pager;
...
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.item_details);
pos = getIntent().getExtras().getInt("pos");
adapter = new DescAdapter(getSupportFragmentManager());
pager = (ViewPager) findViewById(R.id.pager);
pager.setAdapter(adapter);
pager.setCurrentItem(pos);
}
public class DescAdapter extends FragmentStatePagerAdapter {
public DescAdapter(FragmentManager fm) {
super(fm);
}
#Override
public int getCount() {
return 20;
}
public Fragment getItem(int position) {
return DetailFragment.newInstance(position);
}
}
And my detailFragment
public class DetailFragment extends Fragment {
static DetailFragment newInstance(int position) {
DetailFragment f = new DetailFragment();
return f;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.detail_fragment, container, false);
String displaytitle= getActivity().getIntent().getStringExtra("title");
TextView titleF = (TextView)view.findViewById(R.id.title);
titleF.setText(displaytitle);
...
return view;
}
What am I doing wrong?
You are not using the correct argument:
You send the argument "pos2" but you retrieve the argument "title".
#Override
public Fragment getItem(int position) {
DetailFragment frag = new DetailFragment();
Bundle bundle = new Bundle();
bundle.putInt("fPos",position);
frag.setArguments(bundle);
return frag;
}
How i can update data in my case
public class SpaFragment extends Fragment {
public SpaFragment(){}
private SpaList mSpa;
private TabHost tabs;
private View rootView;
private ViewPager pager;
private PagerAdapter pagerAdapter;
public void setSpa(SpaList s)
{
mSpa=s;
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
rootView = inflater.inflate(R.layout.spa_tab_fragment, container, false);
FragmentManager f = ((FragmentActivity) getActivity()).getSupportFragmentManager();
pagerAdapter = new MyPagerAdapter( f );
pager = (ViewPager) rootView.findViewById(R.id.pager);
pager.setAdapter(pagerAdapter);
pagerAdapter.notifyDataSetChanged();
Log.d(""+mSpa.getSpaName(),"");
return rootView;
}
private class MyPagerAdapter extends FragmentStatePagerAdapter {
public MyPagerAdapter(FragmentManager fm) {
super(fm);
}
#Override
public int getItemPosition(Object object) {
return POSITION_NONE;
}
#Override
public CharSequence getPageTitle(int position) {
Resources res = getResources();
String[] title = res.getStringArray(R.array.title_spa_viewpager_array);
return title[position];
}
#Override
public android.support.v4.app.Fragment getItem(int pos) {
switch(pos) {
case 0: return FirstFragment.newInstance(mSpa.getSpaName());
case 1: return SecondFragment.newInstance(mSpa.getSpaAddr());
case 2: return SecondFragment.newInstance(mSpa.getCityEngName());
default: return FirstFragment.newInstance(mSpa.getSpaPhone());
}
}
#Override
public int getCount() {
return 3;
}
}
}
and fragment code
public class FirstFragment extends Fragment {
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.viewpager_tab_text, container, false);
TextView tv = (TextView) v.findViewById(R.id.tvFragFirst);
tv.setText(getArguments().getString("msg"));
return v;
}
public static FirstFragment newInstance(String text) {
FirstFragment f = new FirstFragment();
Bundle b = new Bundle();
b.putString("msg", text);
f.setArguments(b);
return f;
}
}