I have a problem. I am trying to change a fragment when a user clicks on it, but it does not work. I do not see the mistake but It works for another fragment. Here is my code :
**Fragment where I try to switch: **
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view = inflater.inflate(R.layout.fragment_profil, container, false);
TextView textViewNom = view.findViewById(R.id.labelNom);
textViewNom.setText(((Main)getActivity()).getNomComplet());
linearScore = (LinearLayout)view.findViewById(R.id.linearScore);
linearScore.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
fragment_score frag_score= new fragment_score();
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.add(R.id.fragment_container, frag_score,"scorefrag");
transaction.addToBackStack("scorefrag");
transaction.commit();
}
});
linearReglage = (LinearLayout)view.findViewById(R.id.linearReglage);
linearReglage.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
fragment_reglage frag_reglage= new fragment_reglage();
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.add(R.id.fragment_container, frag_reglage,"reglagefrag");
transaction.addToBackStack("reglagefrag");
transaction.commit();
}
});
To explain you I do not have problem when I click on linearScore in the view but my application restarts when I try to click on linearReglage.
linearReglage (XML) :
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#color/white"
tools:context="layout.fragment_reglage">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="oui"
android:textSize="30dp"/>
</ScrollView>
fragment_reglage (java):
public class fragment_reglage extends Fragment {
private View view;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view=inflater.inflate(R.layout.fragment_reglage, container, false);
return view;
}
public void onResume(){
super.onResume();
}
}
I do not see an error I just have a Failed exception ( because of non-0 exit status). But the application restart like if it was basic.
I do know what is this error and if it is link
as #Eselfar in the comment recommended you to see this answer
using the dex solution and trying it on a real device this cache error would be long gone probably! but to me everything seems fine in the code except the cache mechanism you are trying using the backStack along add option
see this for back stack management
I think this code will solve the problem of yours
just change the fragmentTransaction.add to fragmentTransaction.replace because from your code you are trying to navigate between two fragments replacing will keep the cache maintained
do that and test on real device..
here how your code will look like after the change
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
view = inflater.inflate(R.layout.fragment_profil, container, false);
TextView textViewNom = view.findViewById(R.id.labelNom);
textViewNom.setText(((Main)getActivity()).getNomComplet());
linearScore = (LinearLayout)view.findViewById(R.id.linearScore);
linearScore.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
fragment_score frag_score= new fragment_score();
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.replace(R.id.fragment_container, frag_score,"scorefrag");
transaction.addToBackStack("scorefrag");
transaction.commit();
}
});
linearReglage = (LinearLayout)view.findViewById(R.id.linearReglage);
linearReglage.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
fragment_reglage frag_reglage= new fragment_reglage();
FragmentTransaction transaction = getFragmentManager().beginTransaction();
transaction.replace(R.id.fragment_container, frag_reglage,"reglagefrag");
transaction.addToBackStack("reglagefrag");
transaction.commit();
}
});
Related
I've been developing an android app which I included the default Navigation-Drawer from Android Studio and so on. In my home fragment, I've implemented CarViews, and then set those cardview(s) OnClickListener to replace the fragment with traditional procedure.
After the fragment replacement and new page comes, I wanted to change the Actionbar title.
So in the onCreateView(...) method, I tried,
((AppCompatActivity)getActivity()).getSupportActionBar().setTitle("B");
It worked. But after pressing the hardware back button to go back to the stacked fragment, the title remains changed & it doesn't change to "Home" again. I've tried other ways. Here's my following codes. Thanks in advance.
public class HomeFragment extends Fragment implements View.OnClickListener {
public View onCreateView(#NonNull LayoutInflater inflater,
ViewGroup container, Bundle savedInstanceState) {
View root = inflater.inflate(R.layout.fragment_home, container, false);
Objects.requireNonNull(((AppCompatActivity) Objects.requireNonNull(getActivity())).getSupportActionBar()).setTitle("Home");
CardView cardView1 = root.findViewById(R.id.doctor_on);
CardView cardView2 = root.findViewById(R.id.ambulance_e);
CardView cardView3 = root.findViewById(R.id.maintainance_s);
cardView1.setOnClickListener(this);
cardView2.setOnClickListener(this);
cardView3.setOnClickListener(this);
return root;
}
#Override
public void onClick(View v) {
int id = v.getId();
switch (id) {
case R.id.doctor_on:
FragmentTransaction fragmentTransaction = Objects.requireNonNull(getActivity()).getSupportFragmentManager().beginTransaction();
Fragment fragment1 = new doctors();
fragmentTransaction.replace(R.id.container1, fragment1).addToBackStack(getString(R.string.menu_home)).commit();
return;
case R.id.ambulance_e:
//Put Actions
FragmentTransaction fragmentTransaction2 = Objects.requireNonNull(getActivity()).getSupportFragmentManager().beginTransaction();
Fragment fragment2 = new ambulance();
fragmentTransaction2.replace(R.id.container1, fragment2).addToBackStack(getString(R.string.menu_home)).commit();
return;
case R.id.maintainance_s:
//Put Actions
FragmentTransaction fragmentTransaction3 = Objects.requireNonNull(getActivity()).getSupportFragmentManager().beginTransaction();
Fragment fragment3 = new maintanance();
fragmentTransaction3.replace(R.id.container1, fragment3).addToBackStack(getString(R.string.menu_home)).commit();
return;
}
}
#Override
public void onResume() {
super.onResume();
((AppCompatActivity) getActivity()).getSupportActionBar().setTitle("Home");
}
}
To the next fragment(where I change the titlebar and pressed back button):
public class doctors extend Fragment{
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout for this fragment
((AppCompatActivity)getActivity()).getSupportActionBar().setTitle("B");
View root = inflater.inflate(R.layout.fragment_doctors, container, false);
return root;
}
}
And in the doctors Fragment... Should fix the title error.
#Override
public void onDestroyView() {
super.onDestroyView();
Objects.requireNonNull(((AppCompatActivity) Objects.requireNonNull(getActivity()))
.getSupportActionBar())
.setTitle(getString(R.string.your_title_here));
}
You have to override the method onBackPressed() and write the code:
#Override
public View onBackPressed(){
//Here goes the code that head back to your main fragment
FragmentTransaction fragmentTransaction3 = Objects.requireNonNull(getActivity()).getSupportFragmentManager().beginTransaction();
Fragment fragment3 = new maintanance();
fragmentTransaction3.replace(R.id.container1, fragment3).addToBackStack(getString(R.string.menu_home)).commit();
}
}`
Add below code in Home Fragment...
#Override
public void onHiddenChanged(Boolean hidden) {
super.onHiddenChanged(hidden);
((AppCompatActivity) getActivity()).getSupportActionBar().setTitle("Home");
}
I have Index.class as the Activity, when the user choose Profile, it will call fragment Profile
if (id == R.id.nav_profile){
FragmentTransaction transaction = getSupportFragmentManager()
.beginTransaction();
transaction.setCustomAnimations(R.anim.enter,R.anim.exit,R.anim.enter,R.anim.exit);
transaction.replace(R.id.flContent, new Profile(), "ProfileFragment");
transaction.addToBackStack(null);
viewPager.getAdapter().notifyDataSetChanged();
transaction.commit();
}
Now in Profile Fragment, when the user clicks a button it will call DevRegistration Activity
case 1:
btnBeDeveloper.setText("Developer Console");
btnBeDeveloper.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
Intent index = new Intent(getActivity(), DevRegistration.class);
startActivity(index);
}
});
break;
Then in DevRegistration class, after I click the register button, it will display a dialog fragment class.
What I want to do is when I click the button inside the dialog fragment, how can I refresh the profile fragment?
Dialog Fragment Class:
public class df_SuccessDevRegistration extends DialogFragment {
Button btnDevGoProfile;
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
View rootView = inflater.inflate(R.layout.fragment_success_developer_registration, container, false);
btnDevGoProfile = (Button) rootView.findViewById(R.id.btnDevGoProfile);
btnDevGoProfile.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
dismiss();
getFragmentManager().popBackStack();
getActivity().finish();
Profile fragment = (Profile)
getSupportFragmentManager().findFragmentByTag("ProfileFragment");
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction()
transaction.detach(fragment);
transaction.attach(fragment);
transaction.commit();
}
});
return rootView;
}
}
By the way, I dont know why getSupportFragmentManager isnt working. It shows an error cannot resolve method... when I used getFragmentManager() it crashes.
You could also try this to refresh the current fragment
FragmentTransaction ftran = getActivity().getFragmentManager().beginTransaction();
ftran .detach(this).attach(this).commit();
In your dev registration activity , get your fragment :
Profile profileFragment = getSupportFragmentManager().findFragmentByTag("ProfileFragment");
To refresh it you can try :
FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
transaction.detach(profileFragment);
transaction.attach(profileFragment);
transaction.commit();
EDIT:
Can you try this ?
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
getDialog().getWindow().requestFeature(Window.FEATURE_NO_TITLE);
View rootView = inflater.inflate(R.layout.fragment_success_developer_registration, container, false);
btnDevGoProfile = (Button) rootView.findViewById(R.id.btnDevGoProfile);
return rootView;
}
#Override
public Dialog onCreateDialog(Bundle savedInstanceState) {
btnDevGoProfile.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View v) {
getActivity().getSupportFragmentManager().popBackStack();
Profile fragment = (Profile)
getActivity().getSupportFragmentManager().findFragmentByTag("ProfileFragment");
FragmentTransaction transaction = getActivity().getSupportFragmentManager().beginTransaction()
transaction.detach(fragment);
transaction.attach(fragment);
transaction.commit();
getActivity().finish();
dismiss();
}
});
}
Hope this helps.
I have a series of fragments. And I use "previous" and "next" buttons for navigation within this fragments. There are many edit texts and radio buttons in this fragments.
I want to save and and restore the user input in these edit texts and radio buttons when a previous fragment is loaded by clicking on "previous" button.
Screeshots:
Fragment 1
Fragment 2
Fragment 1:
public class Register_Page6 extends Fragment {
public Register_Page6() {}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_register_page6, container, false);
Button Previous = (Button) view.findViewById(R.id.Previous6);
Button Next = (Button) view.findViewById(R.id.Next6);
Next.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
android.support.v4.app.FragmentTransaction FT;
FT = getActivity().getSupportFragmentManager().beginTransaction();
FT.replace(R.id.main_container,new Register_Page7());
FT.commit();
}
});
Previous.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
android.support.v4.app.FragmentTransaction FT;
FT = getActivity().getSupportFragmentManager().beginTransaction();
FT.replace(R.id.main_container,new Register_Page5());
FT.commit();
}
});
return view;
}
}
Fragment 2:
public class Register_Page7 extends Fragment {
public Register_Page7(){
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {
View view = inflater.inflate(R.layout.fragment_register_page7, container, false);
Button Previous = (Button) view.findViewById(R.id.Previous7);
Button Regiter = (Button) view.findViewById(R.id.Submit);
Regiter.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
android.support.v4.app.FragmentTransaction FT;
FT = getActivity().getSupportFragmentManager().beginTransaction();
FT.replace(R.id.main_container,new Register_Page6());
FT.commit();
}
});
Previous.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
android.support.v4.app.FragmentTransaction FT;
FT = getActivity().getSupportFragmentManager().beginTransaction();
FT.replace(R.id.main_container,new Register_Page6());
FT.commit();
}
});
return view;
}
}
Add Your fragment to back stack using addToBackStack("YOUTAG") like this in all your fragments :
android.support.v4.app.FragmentTransaction FT;
FT = getActivity().getSupportFragmentManager().beginTransaction();
FT.replace(R.id.main_container, new Register_Page6()).addToBackStack("FragmentName");
FT.commit();
When you have a series of fragments if you add them to the backstack it would be memory wastage.
For this kind of action android provides something called ViewPager, which will always store 2 fragments at a time and create the rest of fragments dynamically when needed.
So if you still decided you don't want to use ViewPager, you can store the Fragment's data in activity's bundle and you can retrieve data when creating the fragment again
This is the code II implemented by googling and reading another stack overflow answers. but any answer is not working for me.
Following code this error - "No view found for id 0x7f09009e
Please help me to implement this
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
//////more code here //////
OnClickListener listner = new OnClickListener() {
#Override
public void onClick(View v) {
Fragment fragment=null;
if(v==rootView.findViewById(R.id.Button)){
fragment = new SortListFragment();
}
FragmentManager manager =getFragmentManager();
FragmentTransaction transaction = manager.beginTransaction();
transaction.replace(R.id.fragment_sort, fragment);
transaction.commit();
}
};
ImageButton btn = (ImageButton)rootView.findViewById(R.id.button);
btn.setOnClickListener(listner);
return rootView;
}
ButtonOnClickInterface interface;
public void onCreateView(//parameters){
View view=//inflate the view;
Button button =(Button)view.findViewById(R.id.buttonId);
button.setOnClickListener(new View.OnclickListener{
#Override
public void onClick(View v){
try{
interface.onClick();
}catch(Throwable e){
//may be null
}
}
});
}
#Override
public void onAttach(Context c){
super.onAttach(c);
try{
interface=(ButtonOnClickInterface)c;
}catch(Throwable e){
//not implemented
}
}
And your interface
interface ButtonOnClickInteface{
void onClick();
}
Implement this interface in your activity.
Add this line above on click listner:
rootview = inflater.inflate(R.layout.<your layout xml>, container,
false);
I think you forgot to provide layout file in which you have put buttons and all.
So please provide below line in your code after "super.OnCreateView()"
rootView = inflater.inflate(R.layout.your_layout_file, container, false);
And then check it is working or not, hope this will work
On click of Button I am trying to open second fragment(YourResultFragment.java),
I had a lots but don't know why it is not working , here is my code which I am using
public class KnowYourBodyFragment extends Fragment {
public KnowYourBodyFragment() {
// Required empty public constructor
}
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
}
#Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_know_your_body, container, false);
Button button = (Button)rootView.findViewById(R.id.button2);
button.setOnClickListener(new OnClickListener()
{
#Override
public void onClick(View v)
{
Fragment mFragment = new YourResultFragment();
getActivity().getSupportFragmentManager().beginTransaction()
.replace(R.id.know_your_body_container, mFragment ).commit();
}
});
// Inflate the layout for this fragment
return rootView;
}
Use this Try to replace it with Default Container android.R.id.content.
Button button = (Button)rootView.findViewById(R.id.button2);
button.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
Fragment newFragment = new YourResultFragment();
FragmentTransaction transaction = getFragmentManager()
.beginTransaction();
// Replace whatever is in the fragment_container view with this
// fragment,
// and add the transaction to the back stack
transaction.replace(android.R.id.content, newFragment);
transaction.addToBackStack("tag");
// Commit the transaction
transaction.commitAllowingStateLoss();
}
});
What is transaction.addToBackStack("tag") ?
Add this transaction to the back stack. This means that the transaction will be remembered after it is committed, and will reverse its operation when later popped off the stack.