bottom navigation bar doesn't work at all after I change fragment with supportFragmentManager.
binding.addBookSelectBackBtn.setOnClickListener {
(context as MainActivity).supportFragmentManager.beginTransaction().replace(
R.id.nav_host_fragment_container,
AddBookFragment()
).commitAllowingStateLoss()
}
How can I solve it?
Related
I am trying to scroll to the bottom of my scrollView after a view becomes visible with button click. The problem is the scrollTo function is applied before the view is actually visible. I know this because when the button is pressed twice, it scrolls to the bottom on the second click.
So, is there a way to scroll after the view becomes visible?
button.setOnClickListener(v -> {
constraintLayout.setVisibility(View.VISIBLE);
scrollView.smoothScrollTo(0, constraintLayout.getBottom());
}
button.setOnClickListener(v -> {
constraintLayout.setVisibility(View.VISIBLE);
Handler handler = new Handler();
handler.postDelayed(() -> {
scrollView.smoothScrollTo(0, constraintLayout.getBottom());
}, 100);
}
I just figured out this works, but I was hoping to not use a delay.
Another option is to use a listener.
ViewTreeObserver.OnPreDrawListener viewVisibilityChanged = new ViewTreeObserver.OnPreDrawListener() {
#Override
public boolean onPreDraw() {
if (my_view.getVisibility() == View.VISIBLE) {
scroll_view.smoothScrollTo(0, scroll_view.getHeight());
}
return true;
}
};
You can add it to your view this way :
my_view.getViewTreeObserver().addOnPreDrawListener(viewVisibilityChanged);
I'm using the Navigation component for my two DialogFragments and when I press a button on the first DialogFragment it is dismissed and then the second one is shown. I need to test that clicking this button will take me to the second dialog. I have a simple home fragment that is overlayed by the first DialogFragment at the start of the app. The following code is from the first DialogFragment.
/**
* Redirects users to another dialog after pressing button
*/
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState)
button.setOnClickListener {
if (findNavController().currentDestination?.id == R.id.firstDialogFragment) {
findNavController().navigateUp()
val action = HomeFragmentDirections.actionHomeFragmentToSecondDialogFragment()
findNavController().navigate(action)
}
}
}
This next bit of code comes from the developer's guide and only checks for the behavior of dismissing a DialogFragment back to the previous Fragment.
#RunWith(AndroidJUnit4::class)
class MyTestSuite {
#Test fun testDismissDialogFragment() {
// Assumes that "MyDialogFragment" extends the DialogFragment class.
with(launchFragment<MyDialogFragment>()) {
onFragment { fragment ->
assertThat(fragment.dialog).isNotNull()
assertThat(fragment.requireDialog().isShowing).isTrue()
fragment.dismiss()
fragment.requireFragmentManager().executePendingTransactions()
assertThat(fragment.dialog).isNull()
}
// Assumes that the dialog had a button
// containing the text "Cancel".
onView(withText("Cancel")).check(doesNotExist())
}
}
}
I need some way to test the behavior of a DialogFragment's button and see that it dismisses itself and starts the second DialogFragment.
When I test for the button being clicked, the first DialogFragment is correctly dismissed, but the second DialogFragment is not launched. I've used both Espresso and UiAutomator and the click does occur, but reading the code snippet's explanation for testing DialogFragments it says,
"Even though dialogs are instances of graphical fragments, you use the launchFragment() method so that the dialog's elements are populated in the dialog itself, rather than in the activity that launches the dialog".
Is the reason that I am unable to check if the second DialogFragment exists or not, because it is an instance of a graphical fragment and my click listener for the button on the first DialogFragment cannot implement launchFragment() for the second DialogFragment?
I have an app with a bottom navigation and a toolbar.
The bottom navigation opens different fragments and the toolbar is suppose to change depending on the fragment (not implemented yet).
The toolbar is initialized in the main activity and depending on which fragment will be opened the menu of the toolbar will be inflated differently. There are different methods in the main activity which inflate the menu and set up the onClickListeners.
Inside OnCreate in MainActivity
if (savedInstanceState == null) {
supportFragmentManager
.beginTransaction()
.replace(R.id.main_container, QuickNPangFragment.QuickNPangFragment.newInstance(), "activitySelection")
.addToBackStack("navigation_quick")
.commit()
supportFragmentManager.executePendingTransactions()
}
[...]
val toolbar: Toolbar = findViewById(R.id.toolbarNew)
when (supportFragmentManager.getBackStackEntryAt(supportFragmentManager.backStackEntryCount-1).name) {
"navigation_quick" -> setQuickMenu(toolbar)
"navigation_location" -> setLocationMenu(toolbar)
"navigation_friends" -> setFriendsMenu(toolbar)
}
[...]
private fun setQuickMenu(toolbar: Toolbar) {
toolbar.inflateMenu(R.menu.menu_main)
toolbar.setOnMenuItemClickListener {
QuickNPangFragment.QuickNPangFragment.newInstance().setQuickMenuItemClickListener(it.itemId)
true
}
}
Inside QuickNPangFragment
object QuickNPangFragment {
fun newInstance() = QuickNPangFragment()
}
There is something wrong in my understanding of this concept of the singleton: I think that only ONE instance of this fragment will be created, so whenever I call the newInstance() method of the fragment, it will return the same instance.
When running the debugger though it shows that the reference to the QuickNPangFragment object that is added when calling onCreate (this = {QuickNPangFragment#10915}... << this is the address, correct?) is different from the one when setting up the onClickListener in the setQuickMenu method (this = {QuickNPangFragment#11154}).
1) What am making wrong? and/or Where is the misunderstanding of that concept?
2) Is it ok to change the toolbar menu depending on the fragment?
I have a SurfaceView with a LinearLayout which hides or shows if you click on the SurfaceView.
The problem is that the SurfaceView is not refreshed so if the setVisibility(View.VISIBLE) actually doesn't work.
This is the code I'm using:
sv.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v)
{
Log.d("MainActivity-onCreate-onClick-buttons",
buttonsVisibility.toString());
if (buttonsVisibility)
{
linearLayoutButtons.setVisibility(View.INVISIBLE);
buttonsVisibility = false;
} else
{
linearLayoutButtons.setVisibility(View.VISIBLE);
buttonsVisibility = true;
}
}
});
By default buttonVisibility is set to false and the first time I click the view it actually is so so the logic is consistent, the only problem is that the setVisibility seems to have no effect. Only if I turn on/off the screen I can see the layout displayed correctly and then working properly. Why I need to turn the screen off to refresh the UI? Shouldn't it refresh automatically after the setVisibility?
Thank you very much
I don't know why but if I change my Buttons to be ImageButtons it works but buttons appear with a wrong "z-index" wherever I put them. I need to click once on them to fix the "z-index". If I change setVisibility(View.INVISIBLE) with setVisibility(View.GONE) all works fine.
Hope this might be helpful for someone with the same problem.
I want to show the last item added in the table view when appears a scroll bar. Is there any way for the same and it will be grateful if can.
I have checked scroll pane with horizontal and vertical setValue() property. Is there any similar way for the table view scroll bar?
Check the TableView.scrollTo() out.
Here is a full generic solution:
public static <S> void addAutoScroll(final TableView<S> view) {
if (view == null) {
throw new NullPointerException();
}
view.getItems().addListener((ListChangeListener<S>) (c -> {
c.next();
final int size = view.getItems().size();
if (size > 0) {
view.scrollTo(size - 1);
}
}));
}