androidandroid-toolbardevice-orientation

toolbar items have no dimensions (width, height, left, right, ...) after a configuration change


I am developing a tutorial that needs to display a pointer at the various items of the toolbar. The toolbar is owned by the activity. In the fragment running the tutorial, I have the following code:

    @Override
    public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) {
        ...
        tutorialViewModel.getTutoData().observe(getViewLifecycleOwner(), tutoData -> {
            ...
            scToolbar = getActivity().findViewById(R.id.toolbar);
            ...
            androidx.appcompat.widget.AppCompatImageButton navigationButton = null;
            try {
                navigationButton = (androidx.appcompat.widget.AppCompatImageButton) scToolbar.getChildAt(scToolbar.getChildCount() - 1);
            } catch (Exception ClassCastException) {
                for (int i = 0; i < scToolbar.getChildCount(); i++) {
                    if (scToolbar.getChildAt(i) instanceof androidx.appcompat.widget.AppCompatImageButton) {
                        navigationButton = (androidx.appcompat.widget.AppCompatImageButton) scToolbar.getChildAt(i);
                        break;
                    }
                 }
             }

             androidx.appcompat.widget.AppCompatImageButton finalNavigationButton = navigationButton;
             navigationButton.post(new Tutorial(tutoMsg, (int) (finalNavigationButton.getLeft() + 0.5f* finalNavigationButton.getWidth()), 0, finalNavigationButton.getHeight(), tutoData.isTutoOutOfSequence()));
             ...
        });

This code works fine when the activity and this fragment are launched for the first time.

As soon as a configuration change (orientation change, actually) occurs the width/height/left/top/right/bottom fields of the toolbar itself and each of its items are equal to zero, ruining my effort to point at any particular item.

Why? What should I change in this code?


Solution

  • The following code is a workaround (I indeed think it is not the solution; however it fixes my issue):

    helpFrameLayout.post(() -> tutorialViewModel.getTutoData().observe(getViewLifecycleOwner(), tutoData -> {.post(() -> tutorialViewModel.getTutoData().observe(getViewLifecycleOwner(), tutorialData -> { ... }
    

    intead of

    tutorialViewModel.getTutoData().observe(getViewLifecycleOwner(), tutoData -> { ... }
    

    where tutorialViewModel is the ConstraintLayout in which the tutorial messages are displayed.