MainActivity has 2 buttons and when I click the buttons I want 2 fragments to appear in the same page.But when I click on itsMeContact button, it comes up, but when I click on the PhoneContact button, I overwrite the other one.
MainActivity.java
public class MainActivity extends AppCompatActivity {
Button itsMeContact,phoneContact;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
itsMeContact= (Button) findViewById(R.id.its_me_contact);
phoneContact= (Button) findViewById(R.id.phone_contact);
itsMeContact.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
FragmentManager manager = getFragmentManager();
UserFragment userFragment = new UserFragment();
FragmentTransaction transaction = manager.beginTransaction();
transaction.add(R.id.frame_layout, userFragment, "userFragment");
transaction.commit();
}
});
phoneContact.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
FragmentManager manager = getFragmentManager();
FragmentB fragmentB = new FragmentB();
FragmentTransaction transaction = manager.beginTransaction();
transaction.add(R.id.frame_layout, fragmentB, "fragg");
transaction.commit();
}
});
}
}
UserFragment.java
public class UserFragment extends Fragment {
RecyclerView recyclerView ;
UserAdapter userAdapter ;
ArrayList<Person> arrayList ;
private LinearLayoutManager layoutManager;
Button itsMeContact,phoneContact;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, Bundle savedInstanceState) {
View view=inflater.inflate(R.layout.fragment_user,container,false);
recyclerView = view.findViewById(R.id.recycler_view);
itsMeContact= view.findViewById(R.id.its_me_contact);
layoutManager = new LinearLayoutManager(getActivity());
layoutManager.scrollToPosition(0);
layoutManager.setOrientation(LinearLayoutManager.VERTICAL);
recyclerView.setLayoutManager(layoutManager);
arrayList=new ArrayList<Person>();
initial();
return view;
}
private void initial() {
Factory.getInstance().user().enqueue(new Callback<List<User>>() {
#Override
public void onResponse(Call<List<User>> call, Response<List<User>> response) {
// textView.setText(response.body().get(0).name);
userAdapter= new UserAdapter(response.body(), getActivity());
recyclerView.setAdapter(userAdapter);
}
#Override
public void onFailure(Call<List<User>> call, Throwable t) {
}
});
}
}
FragmentB.java
public class FragmentB extends Fragment {
TextView textView;
#Nullable
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, Bundle savedInstanceState) {
View view=inflater.inflate(R.layout.fragment_fragment_b,container,false);
textView=view.findViewById(R.id.textView);
textView.setText("naber");
return view;
}
}
Your advice important for me !
Thank you very much
My app:
enter image description here
Each Fragment transaction you did use the same framelayout : "R.id.frame_layout".
So this is normal if "it looks overhead". If you want 2 fragments displayed in a same layout, you should use 2 differents framelayout.
Related
I am facing a problem where I am opening a dialog (Dialog 1) from fragment1 and there is a button (change) on Dialog1 on which if I click then: Dialog1 should be dismissed and on the same fragment1 should be replaced by fragment2(Another fragment)
public class PedigreeAnalysis extends Fragment //My Fragment1
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {
showDialog();
}
// SHOW DIALOG FUNCTION IS SHOWN BELOW `
void showDialog() { //Function to show the dialog starts...
Dialog dialog= new Dialog(getActivity());
Button btn = dialog.findViewById(R.id.button);
btn.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
//Code for opening new fragment and dismissing the dialog.
getActivity().getSupportFragmentManager().beginTransaction()
.replace(R.id.fragment1, new Fragment2()).commit();
dialog.dismiss();
}
});
}//Function Ends Here....
I have even tried the reverse logic of (dismissing the dialog first and then replacing it with the function but it also doesn't works) as :
dialog.dismiss();//First dismissing the dialog
getActivity().getSupportFragmentManager().beginTransaction()
.replace(R.id.fragment1, new Fragment2()).commit();//Replacing the fragment
Follow this...
Fragment1:
public class Fragment1 extends Fragment {
private ItemClickListener itemClickListener;
private Button addButton;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// all the views are initialized here...
}
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
addButton.setOnClickListener(v -> {
if (itemClickListener != null) onItemClicked.onClicked(new Plan());
});
}
public Fragment1 setItemClickListener(ItemClickListener itemClickListener) {
this.itemClickListener = itemClickListener;
return this;
}
public interface ItemClickListener {
void onItemClicked(Plan plan);
}
}
In parent Activity Class
public class PlanActivity extends AppCompatActivity {
private Fragment1 fragment1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_plan);
fragment1 = new Fragment1()
.setOnAddButtonClicked(this::openFragmentEditPlan);
openFragment1();
}
private void openFragment1() {
getSupportFragmentManager().beginTransaction()
//frameLayout_PlanActivity is the container of both fragments
.add(R.id.frameLayout_PlanActivity, fragment1)
.commit();
}
public void openFragmentEditPlan(Plan plan) {
getSupportFragmentManager().beginTransaction()
.replace(R.id.frameLayout_PlanActivity, FragmentEditPlan.newInstance(plan))
.addToBackStack("Fragment Edit Plan")
.commit();
}
}
I have two different classes that i will show
public class Iniziale extends AppCompatActivity {
Button credits,gioca,giocamyquiz,newquestion;
TextView testo;
public boolean whatgame;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_iniziale);
gioca = findViewById(R.id.gioca);
giocamyquiz = findViewById(R.id.giocamyquiz);
newquestion= findViewById(R.id.newquestions);
whatgame=true;
FragmentManager fragmentManager = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();
gioca.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
whatgame=true;
Intent homeIntent = new Intent(Iniziale.this, MainActivity.class);
startActivity(homeIntent);
finish();
}
});
giocamyquiz.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
whatgame=false;
Intent homeIntent = new Intent(Iniziale.this, MainActivity.class);
startActivity(homeIntent);
finish();
}
});
}
public boolean FragmentMethod() {
return whatgame;
}
}
and a fragment
public class MainActivityFragment extends Fragment {
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
super.onCreateView(inflater, container, savedInstanceState);
View view = inflater.inflate(R.layout.fragment_main_activity, container, false);
what=true; //sceglie a quale quiz giocare
what=((Iniziale) getActivity()).FragmentMethod();
I want use method FragmentMethod() in my Fragment class because I need the value of the whatgame variable.
How the code is write it doesn't work.
In Iniziale class I have 2 buttons and based of what button i click I will modify my whatgame variable and modify some parameters in fragment class
Problem: Having a SwipeView inside a Fragment (So when the Fragment is active you can cycle through some other fargments)
What I tried: I tried implementing it the same way you would implement it normally but in the fragment:
NORMAL WAY:
public class MainActivity extends FragmentActivity {
ViewPager viewPager;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
viewPager = (ViewPager) findViewById(R.id.viewPager);
SwipeAdapter swipeAdapter = new SwipeAdapter(getSupportFragmentManager());
viewPager.setAdapter(swipeAdapter);
}
}
THE WAY I TRIED IT WITH A FRAGMENT:
public class SecondFragment extends Fragment {
ViewPager viewPager;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_first, container, false);
return view;
}
#Override
public void onViewCreated(#NonNull View view, #Nullable Bundle savedInstanceState) {
super.onViewCreated(view, savedInstanceState);
viewPager = view.findViewById(R.id.VIEWPAGER);
SwipeAdapter swipeAdapter = new SwipeAdapter(getChildFragmentManager());
viewPager.setAdapter(swipeAdapter);
}
}
THE ERROR: It returns a "null object reference" when I try to set the adapter (I'm guessing it has problems with the FragmentManager)
ADAPTER FOR BOTH EXAMPLES:
public class SwipeAdapter extends FragmentStatePagerAdapter {
public SwipeAdapter(FragmentManager fm) {
super(fm);
}
#Override
public Fragment getItem(int position) {
Fragment fragment = new PageFragment();
Bundle bundle = new Bundle();
bundle.putInt("count", position+1);
fragment.setArguments(bundle);
return fragment;
}
#Override
public int getCount() {
return 5;
}
}
In the Main Activity I set up so you can switch fragments with buttons, and what I'm trying to implement in the second fragment is to be able to swipe through fragments with SwipeView
MAIN ACTIVITY CODE:
public class MainActivity extends AppCompatActivity {
Button firstFragment, secondFragment;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
firstFragment = (Button) findViewById(R.id.firstFragment);
secondFragment = findViewById(R.id.secondFragment);
firstFragment.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
loadFragment(new FirstFragment());
}
});
secondFragment.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
loadFragment(new SecondFragment());
}
});
}
private void loadFragment(Fragment fragment) {
FragmentManager fm = getSupportFragmentManager();
FragmentTransaction fragmentTransaction = fm.beginTransaction();
fragmentTransaction.replace(R.id.frameLayout, fragment);
fragmentTransaction.commit();
}
}
I don't know if this is the right way to do it, but if anyone has a way to make this work any help would be appreciated, thanks!
You cannot set the adapter because your view has not been created yet.
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?,
savedInstanceState: Bundle?
): View? = inflater.inflate(R.layout.fragment_first, container, false)
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
viewPager = view.findViewById(R.id.viewPager) as ViewPager
swipeAdapter = SwipeAdapter(childFragmentManager)
...
}
I'm trying to update my WebView in a Fragment when RecyclerView Item is clicked. In the debug console it's printing my hard-coded URL, but it's not updating the View - it is staying on "Google" webpage without any changes, but seems like onClickListener is working.
MainActivity.java
public class MainActivity extends AppCompatActivity {
private RecyclerView mRecyclerView;
private RecyclerView.Adapter mAdapter;
private RecyclerView.LayoutManager mLayoutManager;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Add Websites
ArrayList<Website> websitesList = new ArrayList<>();
websitesList.add(new Website(R.drawable.ic_launcher_background, "Line 1", "https://google.com/"));
websitesList.add(new Website(R.drawable.ic_launcher_background, "Line 2", "https://yahoo.com/"));
websitesList.add(new Website(R.drawable.ic_launcher_background, "Line 3", "https://abv.bg/"));
mRecyclerView = findViewById(R.id.recyclerView);
mLayoutManager = new LinearLayoutManager(this);
mAdapter = new WebsiteAdapter(websitesList);
mRecyclerView.setLayoutManager(mLayoutManager);
mRecyclerView.setAdapter(mAdapter);
}
public void switchContent(int id, Fragment fragment) {
FragmentTransaction ft = getSupportFragmentManager().beginTransaction();
ft.add(id, fragment);
ft.commit();
}
}
RecyclerView Adapter
#Override
public void onBindViewHolder(#NonNull ExampleViewHolder holder, int position) {
final Website currentItem = mWebsiteList.get(position);
holder.mImageView.setImageResource(currentItem.getImage());
holder.mTitle.setText(currentItem.getTitle());
holder.mTitle.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
fragmentJump(currentItem);
}
});
}
#Override
public int getItemCount() {
return mWebsiteList.size();
}
private void fragmentJump(Website mItemSelected) {
Fragment mFragment = new WebsiteView();
Bundle mBundle = new Bundle();
mBundle.putString("url", "http://facebook.com/");
mFragment.setArguments(mBundle);
switchContent(R.id.fragment, mFragment);
}
public void switchContent(int id, Fragment fragment) {
if (mContext == null)
return;
if (mContext instanceof MainActivity) {
MainActivity mainActivity = (MainActivity) mContext;
mainActivity.switchContent(id, fragment);
}
}
WebView Fragment
private WebView webView;
String mUrl;
public WebsiteView() {}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_website_view, container, false);
try {
mUrl = getArguments().getString("url");
} catch(Exception ex) {
System.out.println(ex.toString());
mUrl = "http://google.com/";
}
System.out.println(mUrl);
webView = v.findViewById(R.id.webView);
webView.setWebViewClient(new WebViewClient());
webView.loadUrl(mUrl);
return v;
}
Okay, it appeared that I'm actually trying to update the Fragment data, and when I replace another fragment with my desired one it works. Any ideas how to update the WebView in the fragment?
There are lot of (duplicate) questions and answers are available, I went through almost all of them and failed. On reference of this question, I made some changes recently.
Brief : In my app, MainActivity holds Fragment View Pager and FrangmentA,B and C. FrangmentA Shows a DialogFragment CDialog onClik. After dismissing CDialog I need to Call FragmentA's doReload() which is not happening here.
MainActivity
protected void onCreate(Bundle savedInstanceState){
...
mSectionsPageAdapter = new FragmentAdapter(getSupportFragmentManager());
mViewPager = (ViewPager) findViewById(R.id.container);
setupViewPager(mViewPager);
TabLayout tabLayout = (TabLayout) findViewById(R.id.tabs);
tabLayout.setupWithViewPager(mViewPager);
int defaultValue = 0;
int page = getIntent().getIntExtra("One", defaultValue);
mViewPager.setCurrentItem(page);
}
private void setupViewPager(ViewPager viewPager)
{
FragmentAdapter adapter = new
FragmentAdapter(getSupportFragmentManager());
adapter.addFragment(new FragmentA(), "FragA");
adapter.addFragment(new FragmentB(), "FragB");
adapter.addFragment(new FragmentC(), "FragC");
viewPager.setAdapter(adapter);
}
FragmentA
public class FragmentA extends Fragment implements CDialog.Dismissed{
#Override
public View onCreateView(LayoutInflater inflater, #Nullable ViewGroup container, #Nullable Bundle savedInstanceState) {
...
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
FragmentManager fm = getActivity().getFragmentManager();
DialogFragment f = new CDialog();
f.show(fm, "CDialog");
}
});
#Override
public void dialogDismissed() {
Log.e(DFD_1, "dialogDismiss Called" );// <-- This is not working*
doReload();
}
}
And CDialogue
public class CDialog extends DialogFragment{
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
....
return v;
}
#Override
public void onViewCreated(View view, #Nullable Bundle savedInstanceState) {
...
dfd_1.setOnClickListener(
new View.OnClickListener() {
public void onClick(View v) {
getDialog().dismiss(); //<--when this happens*
}
});
}
#Override
public void onDismiss(DialogInterface dialog) {
if (getActivity() != null && getActivity() instanceof Dismissed) {
((Dismissed) getActivity()).dialogDismissed();
}
super.onDismiss(dialog);
}
public interface Dismissed {
public void dialogDismissed(); //<-- FragmentA implements this
}
}
You can always have direct callback to your Fragment itself.
First step, is to set targetFragment using setTargetFragment():
DialogFragment#setTargetFragment(Fragment fragment, int requestCode);
I do it this way:
public void showDialogFragment(Fragment targetFragment, AppCompatDialogFragment appCompatDialogFragment, int requestCode) {
FragmentTransaction fragmentTransaction = getSupportFragmentManager().beginTransaction();
fragmentTransaction.setCustomAnimations(android.R.anim.fade_in, android.R.anim.fade_out);
appCompatDialogFragment.setTargetFragment(targetFragment, requestCode);
fragmentTransaction.add(appCompatDialogFragment, appCompatDialogFragment.getClass().getSimpleName());
fragmentTransaction.commitAllowingStateLoss();
}
and then call to this method to open dialog fragment as:
public static final int RC_CDIALOG = 111;
button.setOnClickListener(new View.OnClickListener() {
public void onClick(View view) {
showDialogFragment(FragmentA.this, new CDialog(), RC_CDIALOG);
}
});
Then, in your DialogFragment's onDismissListener(), have some code like below:
#Override
public void onDismiss(DialogInterface dialog) {
super.onDismiss(dialog);
if (getTargetFragment() instanceof FragmentA)
((FragmentA) getTargetFragment()).doReload();
}
What you did this way is:
Show Dialog Fragment "CDialog" along with telling it that your target fragment is "FragmentA" whose reference you can use incase you have something to do with it. In your case you had to call doReload();