8

i want to insert menu gridview in tablayout with kotlin. i have been searching for many references in google but it wont help, still getting 1 error in adapter = FoodAdapter(this, foodsList). it says "Type missmatch : inferred type as fragmentHome but Context was expected". this is my code for fragmentHome.kt

package com.example.ako.nextbrilliantgeneration

import android.os.Bundle
import android.support.v4.app.Fragment
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.BaseAdapter
import android.content.Context
import android.support.v4.app.FragmentActivity
import kotlinx.android.synthetic.main.fragment_fragment_home.*
import kotlinx.android.synthetic.main.menu_entry.view.*

private const val ARG_PARAM1 = "param1"
private const val ARG_PARAM2 = "param2"

class fragmentHome : Fragment() {


var adapter: FoodAdapter? = null
var foodsList = ArrayList<Menu>()


override fun onCreateView(
    inflater: LayoutInflater, container: ViewGroup?,
    savedInstanceState: Bundle?


): View? {

    // Inflate the layout for this fragment
    return inflater.inflate(R.layout.fragment_fragment_home, container, false)

    foodsList.add(Menu("Coffee", R.drawable.profile))
    foodsList.add(Menu("Espersso", R.drawable.profile))
    foodsList.add(Menu("French Fires", R.drawable.profile))
    foodsList.add(Menu("Honey",R.drawable.profile))
    foodsList.add(Menu("Strawberry", R.drawable.profile))
    foodsList.add(Menu("Sugar cubes", R.drawable.profile))
    adapter = FoodAdapter(this, foodsList)

    gvFoods.adapter = adapter


}

class FoodAdapter : BaseAdapter {
    var foodsList = ArrayList<Menu>()
    var context: Context? = null


    constructor(context: Context, foodsList: ArrayList<Menu>) : super() {
        this.context = context
        this.foodsList = foodsList
    }

    override fun getCount(): Int {
        return foodsList.size
    }

    override fun getItem(position: Int): Any {
        return foodsList[position]
    }

    override fun getItemId(position: Int): Long {
        return position.toLong()
    }

    override fun getView(position: Int, convertView: View?, parent: ViewGroup?): View {
        val food = this.foodsList[position]

        var inflator = context!!.getSystemService(Context.LAYOUT_INFLATER_SERVICE) as LayoutInflater
        var foodView = inflator.inflate(R.layout.menu_entry, null)
        foodView.imgFood.setImageResource(food.image!!)
        foodView.tvName.text = food.name!!

        return foodView
    }
}

}

is there any solution?

thanks

Tri Ako Nugroho
  • 135
  • 1
  • 1
  • 7

4 Answers4

14

Your adapter takes in a non-null Context, but you're passing in a Fragment. You could try passing in your activity from your fragment, either:

adapter = FoodAdapter(activity!!, foodsList)

Or if you have the latest support library:

adapter = FoodAdapter(requireActivity(), foodsList)

You're getting unreachable error because you return from the method too early, simply move it to the bottom:

override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View {
    foodsList.add(Menu("Coffee", R.drawable.profile))
    foodsList.add(Menu("Espersso", R.drawable.profile))
    foodsList.add(Menu("French Fires", R.drawable.profile))
    foodsList.add(Menu("Honey",R.drawable.profile))
    foodsList.add(Menu("Strawberry", R.drawable.profile))
    foodsList.add(Menu("Sugar cubes", R.drawable.profile))
    adapter = FoodAdapter(this, foodsList)

    gvFoods.adapter = adapter

    // move this line to last
    return inflater.inflate(R.layout.fragment_fragment_home, container, false)
}
Aaron
  • 3,764
  • 2
  • 8
  • 25
  • this makes the error was gone, but another warning showed up it says unreachable code in : foodsList.add(Menu("Sugar cubes", R.drawable.profile)) adapter = FoodAdapter(this, foodsList) gvFoods.adapter = adapter – Tri Ako Nugroho Nov 09 '18 at 04:50
  • Yeah that will be your coding error. Just move that return after setting the adapter. – Aaron Nov 09 '18 at 06:18
  • 1
    Do not use requireActvity() unless you want an exception to be thrown in your code in the case that the activity is null. Better to use `?.let` to check for null before calling the method. – Mike Dec 06 '18 at 16:29
  • Well I guess I'm only trying to help with type mismatch error and not nullable issue. But if I had, I could argue that moving adapter creation to `onAcivityCreated` so that `requireActivity` would never return null, or to `onAttach` so that `requireContext` would never return null, instead showing a blank recycler view if somehow they are null, but then I again I decided to keep the answer as simple as possible. It may help others who are confused with mistype error to understand better. – Aaron Dec 06 '18 at 21:38
3

The error is clear enough you try to pass this which refer to Fragment object but your adapter needs Context then try to pass Activity that extends from Context.

Replace this line

adapter = FoodAdapter(this, foodsList)

With

adapter = FoodAdapter(getActivity(), foodsList)

Update

calls to Java get and set methods that can be replaced with the use of Kotlin synthetic properties.

getActivity()  --> activity
Khaled Lela
  • 7,831
  • 6
  • 45
  • 73
  • thank you for the answer, its really helpfull. but can you help me for the detail? now i know the problem, but i dont know what im going to do cause im newbie. i just replace `this` with `getActivity()` and still have type missmatch – Tri Ako Nugroho Nov 08 '18 at 19:35
  • `adapter = FoodAdapter(activity, foodsList)` shall fix mismatch error – Khaled Lela Nov 08 '18 at 19:39
  • still not fix the problem yet sir – Tri Ako Nugroho Nov 08 '18 at 20:13
  • Try `Clean & run` and feedback? – Khaled Lela Nov 08 '18 at 20:21
  • i try to clean and run but nothing change. the error was gone if i replace `adapter = FoodAdapter(this, foodsList)` With `adapter = FoodAdapter(activity!!, foodsList)`. but another warning showed up, it says "Unreachable code" in : `foodsList.add(Menu("Sugar cubes", R.drawable.profile)) adapter = FoodAdapter(activity!!, foodsList) gvFoods.adapter = adapter` – Tri Ako Nugroho Nov 09 '18 at 05:41
1

This is a great update to help developers who are writing in Kotlin. The getActivity method has been annotated with @Nullable to better support Kotlin null-safety. Before, this method could return null and would therefore cause an IllegalStateException in Kotlin code because a null object would be used where a non-null type was expected.

To best handle these cases for methods that have been annotated with @Nullable, use the let operator to unwrap the nullable into a non-null object.

getActivity()?.let { adapter = FoodAdapter(it, foodList) }

DO NOT use requireActivity() to "ensure" a non-null activity because this method will throw an exception if your activity does happen to be null.

Mike
  • 10,297
  • 2
  • 21
  • 21
0

In Fragment class you should use following way:

mFargmentSettingBinding.txtAppVersionCode.setText(Static.getAppVersion(activity!!))
Soumen Das
  • 1,292
  • 17
  • 12