Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to fix inflating error caused by destination is not a direct child of this NavGraph

I have a simple app with a main activity, a fragment frag_home, and a listfragment named ItemFragment. In frag_home I have a calendarview. If the user selects a date, the action frag_homeDirections.actionFragHomeToItemFragment(mytimeinmillis) opens the listfragment which shows the events of the selected day. The action uses the argument timeinmillis, which holds the selected date in milliseconds.

Everything works fine. But if I want to create a two panel view and implement the listfragment into the layout of the main fragment (just by using the xml editor, choosing activity_main.xml, drag a fragment component into activity_main and choose listItem) I get the following error if I try to run my application:

E/AndroidRuntime: FATAL EXCEPTION: main
    Process: com.example.myapplication, PID: 8401
    java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.myapplication/com.example.myapplication.MainActivity}: android.view.InflateException: Binary XML file line #29: Binary XML file line #29: Error inflating class fragment
        at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2756)
        at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2817)
        at android.app.ActivityThread.-wrap12(ActivityThread.java)
        at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1556)
        at android.os.Handler.dispatchMessage(Handler.java:102)
        at android.os.Looper.loop(Looper.java:163)
        at android.app.ActivityThread.main(ActivityThread.java:6388)
        at java.lang.reflect.Method.invoke(Native Method)
        at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:930)
        at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:820)
     Caused by: android.view.InflateException: Binary XML file line #29: Binary XML file line #29: Error inflating class fragment
     Caused by: android.view.InflateException: Binary XML file line #29: Error inflating class fragment
     Caused by: java.lang.IllegalArgumentException: navigation destination com.example.myapplication:id/destination_home is not a direct child of this NavGraph

this is my main activity in which I have implemented the fragment ItemFragment

?xml version="1.0" encoding="utf-8"?>
<androidx.drawerlayout.widget.DrawerLayout
        xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:app="http://schemas.android.com/apk/res-auto"
        xmlns:tools="http://schemas.android.com/tools"
        android:id="@+id/drawer_layout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        tools:context=".MainActivity">
<LinearLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:orientation="vertical"
        tools:context=".MainActivity" >


    <androidx.appcompat.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:background="?attr/colorPrimary"
            android:theme="?attr/actionBarTheme"

    />


    <com.google.android.material.bottomnavigation.BottomNavigationView
            android:id="@+id/bottom_nav"
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            app:menu="@menu/menu_navigation"/>
    <fragment
            android:name="androidx.navigation.fragment.NavHostFragment"
            android:layout_width="423dp"
            android:layout_height="320dp" app:navGraph="@navigation/nav_graph" app:defaultNavHost="true"
            android:id="@+id/nav_host_fragment"/>
    <fragment
            android:layout_width="match_parent"
            android:layout_height="301dp" android:name="com.example.myapplication.ItemFragment"
            android:id="@+id/fragment"/>


</LinearLayout>
<com.google.android.material.navigation.NavigationView
android:id="@+id/nav_view"
android:layout_width="wrap_content"
android:layout_height="match_parent"
android:layout_gravity="start"
app:menu="@menu/menu_navigation"/>
        </androidx.drawerlayout.widget.DrawerLayout >

this is my navigation graph

?xml version="1.0" encoding="utf-8"?>
<navigation xmlns:android="http://schemas.android.com/apk/res/android"
            xmlns:app="http://schemas.android.com/apk/res-auto"
            xmlns:tools="http://schemas.android.com/tools" android:id="@+id/nav_graph"
            app:startDestination="@+id/frag_home">

    <fragment android:id="@+id/itemFragment" android:name="com.example.myapplication.ItemFragment"
              android:label="ItemFragment" tools:layout="@layout/fragment_item">
        <argument android:name="timeinmillis" app:argType="long" />
    </fragment>
    <fragment android:id="@+id/frag_home" android:name="com.example.myapplication.frag_home"
              android:label="fragment_main" tools:layout="@layout/frag_home">
        <action android:id="@+id/action_frag_home_to_itemFragment" app:destination="@id/itemFragment"/>
        <action android:id="@+id/action_frag_home_to_create_Event" app:destination="@id/create_Event"/>
    </fragment>
    <fragment android:id="@+id/create_Event" android:name="com.example.myapplication.Create_Event"
              android:label="fragment_create__event" tools:layout="@layout/fragment_create__event"/>
</navigation> 

my mainActivity

class MainActivity : AppCompatActivity() {
    private lateinit var linearLayoutManager: LinearLayoutManager
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)
       //linearLayoutManager = LinearLayoutManager(this)
        //list2_recycler_view.layoutManager = linearLayoutManager
        setSupportActionBar(toolbar)
        val navController = Navigation.findNavController(this,R.id.nav_host_fragment)


        setupBottomNavMenu(navController)

        setupActionBar(navController)
    setupSideNavigationMenu(navController)
    }

my home fragment:

class frag_home : Fragment() {

    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
        // Inflate the layout for this fragment
        return inflater.inflate(R.layout.frag_home, container, false)
    }

    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)

        btnCreateEvent.setOnClickListener{
           //val date = "heute"
            val action = frag_homeDirections.actionFragHomeToCreateEvent()
            val openHandler = My_Clients_OpenHandler()
            val selected_date = Calendar.getInstance().timeInMillis
           // action.setStrDatum("Bussi!")
          Navigation.findNavController(it).navigate(action)


        }
        btnListe.setOnClickListener{
            //val date = "heute"
            val caltmp = Calendar.getInstance()
            val mytimeinmillis = caltmp.timeInMillis
            val action = frag_homeDirections.actionFragHomeToItemFragment(mytimeinmillis)
            val openHandler = My_Clients_OpenHandler()
            // action.setStrDatum("Bussi!")

          Navigation.findNavController(it).navigate(action)


        }
        calendarView?.setOnDateChangeListener { view, year, month, dayOfMonth ->
            // Note that months are indexed from 0. So, 0 means January, 1 means february, 2 means march etc.

            val selected_date = "Selected date is " + dayOfMonth + "/" + (month + 1) + "/" + year
            val caltmp = Calendar.getInstance()
            //val newdatetime = DateTime(year,month, dayOfMonth)
            caltmp.set(year,month,dayOfMonth)
            val mytimeinmillis = caltmp.timeInMillis
            val sdf = SimpleDateFormat("dd.MM.yyyy HH:mm")
            val strSelectedDate = sdf.format(caltmp.getTime())
            val action = frag_homeDirections.actionFragHomeToItemFragment(mytimeinmillis)


              view.findNavController().navigate(action)
          //  actionCreateEvent.setStrDatum(msg)
          //  Navigation.findNavController(view).navigate(actionCreateEvent)
        }


    }

}

and if you need the important part of itemfragment

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        arguments?.let {
            columnCount = it.getInt(ARG_COLUMN_COUNT)
        }
    }

    override fun onCreateView(
        inflater: LayoutInflater, container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
        val view = inflater.inflate(
            R.layout.fragment_recyclerview,
            container,
            false
        )
        //val timeinmillis = arguments?.let { ItemFragmentArgs.fromBundle(it).timeinmillis }
        // val selecteddate = ItemFragmentArgs.fromBundle(arguments)
        //getActivity()?.setTitle(selecteddate);
        // Set the adapter
      var linearLayoutManager: LinearLayoutManager


        openCalendar = OpenCalendarHandler(activity)
        val caltemp = Calendar.getInstance();
        val longTimeinMillis = arguments?.let { ItemFragmentArgs.fromBundle(it).timeinmillis }

        caltemp.timeInMillis = longTimeinMillis!!


        val heute = caltemp.timeInMillis

        val intCalendarId = openCalendar.getCalendarIdbyCalendarName(view.context, "Klienten_Rolandcloud")
        val strCalendarId = intCalendarId!!.toString()
        // alle events vom aktuell im Kalendar_Monat ausgew�hlten Tag
        val selection = ("((" + CalendarContract.Events.DTSTART + " >= ?) AND ("
                + CalendarContract.Events.DTEND + " <= ?) AND ("
                + CalendarContract.Events.DELETED + " = ?) AND ("
                + CalendarContract.Events.CALENDAR_ID + " = ?))")

        val t = Time()
        t.set(caltemp.getTimeInMillis())

        // Ende des Tages indem ich die Uhrzeit auf 23:59 und 59 Sekunden
        // stelle..
        t.set(59, 59, 23, t.monthDay, t.month, t.year)
        val dtEnd = java.lang.Long.toString(t.toMillis(false))
        val strEnde = openCalendar.getStringTimeinMillis(
            t.toMillis(false),
            "yyyy-MM-dd HH:mm"
        )

        // Start des Tages bei 00:00
        t.set(0, 0, 0, t.monthDay, t.month, t.year)
        val strStart = openCalendar.getStringTimeinMillis(
            t.toMillis(false),
            "yyyy-MM-dd HH:mm"
        )
        val dtStart = java.lang.Long.toString(t.toMillis(false))


        val selectionArgs = arrayOf(dtStart, dtEnd, "0", intCalendarId.toString())

        //my_recyclerview  // Add this
        val activity = activity as Context
        val my_recycler_view = view.findViewById<RecyclerView>(R.id.my_recycler_view)
        val meinCursor = openCalendar.getEvents(view.context,selection,selectionArgs,null)
       //linearLayoutManager = LinearLayoutManager(activity)

        view.my_recycler_view.layoutManager = LinearLayoutManager(activity)
        // set the custom adapter to the RecyclerView
        view.my_recycler_view.adapter = MyCalendarAdapter_kotlin(view.context,meinCursor)



        return view
    }

    override fun onActivityCreated(savedInstanceState: Bundle?) {
        super.onActivityCreated(savedInstanceState)
        LoaderManager.getInstance(this).initLoader(EVENTLOADER_ID, null, this)
    }
    // populate the views now that the layout has been inflated
    override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
        super.onViewCreated(view, savedInstanceState)
        // RecyclerView node initialized here
        my_recycler_view.apply {
            // set a LinearLayoutManager to handle Android
            // RecyclerView behavior
            val caltmp = Calendar.getInstance()

        }
    }

/*

So how can I fix this error, if I want to implement the listfragment into the activity_main fragment. My goal: to see both fragments frag_home with calendarview and beyond that fragment the listfragment with the events of the day. All by using the navigation component and actions.

Or is it impossible to use the navigation component to navigate to a fragment, which is implemented in an other layout? Thanks!!

like image 977
Roland Avatar asked Jun 03 '19 07:06

Roland


People also ask

What is navigation component in android?

Android Jetpack's Navigation component helps you implement navigation, from simple button clicks to more complex patterns, such as app bars and the navigation drawer. The Navigation component also ensures a consistent and predictable user experience by adhering to an established set of principles.

Can we use navigation component for activity?

To take full advantage of the Navigation component, your app should use multiple fragments in a single activity. However, activities can still benefit from the Navigation component. Note, however, that your app's UI must be visually broken up across several navigation graphs.

What is Nav_host_fragment?

NavHostFragment provides an area within your layout for self-contained navigation to occur. NavHostFragment is intended to be used as the content area within a layout resource defining your app's chrome around it, e.g.: <androidx.drawerlayout.widget.DrawerLayout.


1 Answers

Make sure that you specify a starting fragment. For one reason or another I had no starting fragments and once fixed corrected the "not a direct child error".

Make sure you have that Start specified on a fragment

Make sure you have that Start specified on a fragment

like image 129
ashkan117 Avatar answered Oct 10 '22 10:10

ashkan117