Implicit Intent is not working due to context issue - android

Here is my code :-
Favourite Activity
import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.ImageView
import android.widget.TextView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.widget.Toolbar
import androidx.core.content.ContextCompat.startActivity
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import java.security.AccessController.getContext
//this is my calling activity
class FavouriteActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.favourite_activity)
val mToolbar: Toolbar = findViewById(R.id.toolbar_favourite)
setSupportActionBar(mToolbar)
getSupportActionBar()?.setDisplayHomeAsUpEnabled(true);
getSupportActionBar()?.setDisplayShowHomeEnabled(true);
setTitle("Favourite Activity");
//getting recyclerview from xml
val recyclerView = findViewById(R.id.recyclerView) as RecyclerView
//adding a layoutmanager
recyclerView.layoutManager = LinearLayoutManager(this, RecyclerView.VERTICAL, false)
//it can be staggered and grid
//creating our adapter
val adapter = CustomAdapter(star) //here I am calling the adapter activity
//now adding the adapter to recyclerview
recyclerView.adapter = adapter
}
override fun onSupportNavigateUp(): Boolean {
onBackPressed()
return true
}
}
CustomAdapter class
class CustomAdapter(val userList: ArrayList<User>) : RecyclerView.Adapter<CustomAdapter.ViewHolder>() {
//this method is returning the view for each item in the list
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): CustomAdapter.ViewHolder {
val v = LayoutInflater.from(parent.context).inflate(R.layout.list_layout_favourite, parent, false)
return ViewHolder(v)
}
//this method is binding the data on the list
override fun onBindViewHolder(holder: CustomAdapter.ViewHolder, position: Int) {
holder.bindItems(userList[position])
holder.imgCopy.setOnClickListener(View.OnClickListener {
holder.shareString(userList[position])
Toast.makeText(holder.itemView.getContext(),"Copy Button Clicked", Toast.LENGTH_SHORT).show()
})
}
//this method is giving the size of the list
override fun getItemCount(): Int {
return userList.size
}
//the class is holding the list view
class ViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
val imgCopy: ImageView = itemView.findViewById(R.id.img_copy) as ImageView
val textViewName = itemView.findViewById(R.id.tvTitle) as TextView
fun bindItems(user: User) {
textViewName.text = user.name
}
fun shareString(user: User)
{
val message : String = user.name
val intent = Intent()
intent.action = Intent.ACTION_SEND
intent.putExtra(Intent.EXTRA_TEXT,message)
intent.type = "text/plain"
startActivity(Intent.createChooser(intent,"Share to :")) ///Issue occur right here
}}}
Getting error : Required context , found Intent.
it is working fine in other FragmentActivity.
I have tried various methods to called the context. but anything is not working.
I have also passed the context from Fragment activity, but that also not worked.
Please let me know is there any way to start Intent.
As I am always getting error and stuck due to this.

The startActivity available in the ViewHolder class is different from the one available in activites. So in this method (available in viewholder), the first parameter should be a context. So pass the context as follows:
startActivity(itemView.context, Intent.createChooser(intent,"Share to :"))

Related

Firebase remove child recyclerview Kotlin

I need to remove child from Firebase after onClick from RecyclerView Adapter.
I have something like this:
Firebase database is
recyclerview is
My biggest problem is not sure how to get the "key" of the child node from the recyclerview.
I have been stuck on this supposedly simple thing for about 3 days so hopefully any help is appreciated.
package com.cpg12.findingfresh.adapters
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.Button
import android.widget.TextView
import androidx.recyclerview.widget.RecyclerView
import com.cpg12.findingfresh.R
import com.cpg12.findingfresh.database.ShoppingList
import com.google.firebase.database.FirebaseDatabase
class ShoppingListAdapter : RecyclerView.Adapter<ShoppingListAdapter.ShoppingListViewHolder>() {
private val shoppingList = ArrayList<ShoppingList>()
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ShoppingListViewHolder {
val itemView = LayoutInflater.from(parent.context)
.inflate(R.layout.shopping_list_item, parent, false)
/** References the node to which market data is stored**/
val databaseReference = FirebaseDatabase.getInstance().getReference("Users")
return ShoppingListViewHolder(itemView)
}
override fun onBindViewHolder(holder: ShoppingListAdapter.ShoppingListViewHolder, position: Int) {
val currentItem = shoppingList[position]
holder.sListItem.text = currentItem.shoppingItem
}
override fun getItemCount(): Int {
return shoppingList.size
}
fun updateShoppinglist(shoppingList: List<ShoppingList>){
this.shoppingList.clear()
this.shoppingList.addAll(shoppingList)
notifyDataSetChanged()
}
class ShoppingListViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView), View.OnClickListener {
val sListItem : TextView = itemView.findViewById(R.id.ShoppingItemTV)
override fun onClick(v: View?) {
databaseReference.child(marketName).setValue(markets).child(key).setValue("")
}
}
}

How to retain CheckedTextView Checked status after Orientation changes

I've created an application that uses recyclerView and adapter. I want to use onSaveInstanceState to save the state of my checkedtextview upon orientation it was refreshed. How can I retain the state of it? I want to use onSave and onRestore Instances.
import android.net.wifi.rtt.CivicLocationKeys
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.os.PersistableBundle
import android.util.Log
import androidx.recyclerview.widget.RecyclerView
import androidx.recyclerview.widget.LinearLayoutManager
import android.os.Parcelable
import android.widget.CheckedTextView
import android.net.wifi.rtt.CivicLocationKeys.STATE
import androidx.annotation.NonNull
class MainActivity : AppCompatActivity() {
//TODO declare the grocery list as an ArrayList?
val grocerList: ArrayList<String> = arrayListOf("Cilantro", "Beans", "Cheese",
"Oil","Tomato", "Salt", "Pepper", "Flour", "Garlic",
"Lime", "Onion", "Rice", "Cabbage", "Avocado")
//TODO implement the recyclerview
//TODO implement the adapter for the recyclerview IN A SEPARATE CLASS
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
val rc : RecyclerView = findViewById(R.id.recyclerViewGroceryList)
rc.layoutManager = LinearLayoutManager(this)
val rcAdapter = GroceryAdapter(grocerList)
rc.adapter = rcAdapter
Log.d("MainActivity","onCreate()") //onCreate()
}
//TODO override all the activity callbacks, don't forget to call super!
//onStart()
override fun onStart() {
super.onStart()
Log.d("MainActivity","onStart()")
}
//onResume()
override fun onResume() {
super.onResume()
Log.d("MainActivity","onResume()")
}
//onPause()
override fun onPause(){
super.onPause()
Log.d("MainActivity","onPause()")
}
//onStop()
override fun onStop() {
super.onStop()
Log.d("MainActivity","onStop()")
}
//onDestroy()
override fun onDestroy() {
super.onDestroy()
Log.d("MainActivity","onDestroy()")
}
override fun onSaveInstanceState(outState: Bundle) {
super.onSaveInstanceState(outState)
}
override fun onRestoreInstanceState(savedInstanceState: Bundle) {
super.onRestoreInstanceState(savedInstanceState)
}
}
This is the adapter that I use to take in the string array. I want to save the state of my recyclerView so when it orientates my checkedTextView tick did not remove.
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.CheckedTextView
import androidx.recyclerview.widget.RecyclerView
import android.os.PersistableBundle
import android.os.Bundle
class GroceryAdapter(private val gList: ArrayList<String>) : RecyclerView.Adapter<GroceryAdapter.GroceryViewHolder>() {
// create new views
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): GroceryViewHolder {
// inflates the card_view_design view
// that is used to hold list item
val view = LayoutInflater.from(parent.context)
.inflate(R.layout.grocery_list, parent, false)
return GroceryViewHolder(view)
}
// binds the list items to a view
override fun onBindViewHolder(holder: GroceryViewHolder, position: Int) {
// sets the text to the textview from our itemHolder class
holder.gItem.text = gList[position]
holder.gItem.setOnClickListener {
if (holder.gItem.isChecked) {
holder.gItem.isChecked = false
} else holder.gItem.isChecked = !holder.gItem.isChecked
}
}
/* return the number of the items in the list */
override fun getItemCount(): Int {
return gList.size
}
// Holds the views for adding it to text
class GroceryViewHolder(ItemView: View) : RecyclerView.ViewHolder(ItemView) {
val gItem: CheckedTextView = itemView.findViewById(R.id.groceryCTV)
}
}
Have a boolean array/list of the form
val checkedState=mutableArrayOf<Boolean>(false,false,false,false)
considering there are 4 checkboxes.
Now use the checked listener to manipulate the checkedState variable.
(if the 2nd and fourth are checked the value would be false,true,false,true)
On reorientation simply use the values in the checkedState to assign the value as checked or not

context as a parameter takes this in android and allow us to implement method of interface. Why so?

My Main Activity Class
This is implemented to learn recycler view and to handle clicks. The below code works fine but while implementing listener I got confused. All the doubts are listed below. Do help.
package com.suasnom.pizzarecyclerview
import androidx.appcompat.app.AppCompatActivity
import android.os.Bundle
import android.widget.Toast
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.RecyclerView
import kotlinx.android.synthetic.main.activity_main.*
class MainActivity : AppCompatActivity(), isClickedInterface {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
//implementing recycler view
recycler_view.layoutManager= LinearLayoutManager(this)
val data = fetchData()
val adapter = CustomAdapter(data, this)
recycler_view.adapter = adapter
}
fun fetchData(): ArrayList<String> {
val list_Strings = ArrayList<String>()
var str = ""
for(i in 1..100){
str = "${i} line"
list_Strings.add(str)
}
return list_Strings
}
override fun onItemClicked(item: String) {
Toast.makeText(this, "$item", Toast.LENGTH_LONG).show()
}
}
In this statement I passed
val adapter = CustomAdapter(data, this)
and it allows me to override the below method:
override fun onItemClicked(item: String) {
Toast.makeText(this, "$item", Toast.LENGTH_LONG).show()
}
The below code is for recycler view adapter where I write that interface:
package com.suasnom.pizzarecyclerview
import android.view.LayoutInflater
import android.view.ViewGroup
import android.widget.TextView
import android.view.View
import androidx.recyclerview.widget.RecyclerView
class CustomAdapter(val list_strings: ArrayList<String>, private val listner: isClickedInterface): RecyclerView.Adapter<PizzaViewHolder>() {
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PizzaViewHolder {
val view = LayoutInflater.from(parent.context).inflate(R.layout.row, parent, false)
val pizzaObject = PizzaViewHolder(view)
view.setOnClickListener {
listner.onItemClicked(list_strings[pizzaObject.adapterPosition])
}
return pizzaObject
}
override fun onBindViewHolder(holder: PizzaViewHolder, position: Int) {
val data_incoming = list_strings[position]
holder.text_message.text = data_incoming
}
override fun getItemCount(): Int {
return list_strings.size
}
}
class PizzaViewHolder(private val view: View): RecyclerView.ViewHolder(view){
val text_message = view.findViewById<TextView>(R.id.textrow)
}
interface isClickedInterface{
fun onItemClicked(item: String){}
}
Any idea how this is working. Please Help ...
inside CustomAdapter on the bottom you have declared isClickedInterface (it might be declared anywhere else or as separated file). it is implemented by your MainActivity (after :), so you have to set this interface methods inside implementing class - so in Activity appears onItemClicked(item: String) method
now your CustomAdapter have constructor param to pass this interface (second one). for initiating new instance of adapter you have pass implemented interface, in here you may pass whole Activity as it implements desired interface (val adapter = CustomAdapter(data, this) - this points on Activity, which is also an isClickedInterface interface instance)
now inside onCreateViewHolder you are setting setOnClickListener and inside of it you are calling method from passed interface in constructor

Fragment to Fragment transaction in Adapter Class Android

Hello I'm new in Android Developing and I'm creating a family Application in Android Studio. Whenever I want to go to another fragment in Adapter class the fragment is overlapping old fragment.
I want to go to Another fragment name SubFamilyFragment() from the adapter class.
I tried many ways from internet but I'm not getting success.
Here is my Adapter class code
import android.content.Context
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.CheckBox
import android.widget.TextView
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.fragment.app.Fragment
import androidx.recyclerview.widget.RecyclerView
import com.example.mks.Fragments.SubFamilyFragment
import com.example.mks.Models.Family
import com.example.mks.R
class FamilyRecyclerAdapter(val context: Context, val familyList: ArrayList<Family>) : RecyclerView.Adapter<FamilyRecyclerAdapter.viewHolder>() {
class viewHolder(view: View) : RecyclerView.ViewHolder(view) {
val familyName : TextView = view.findViewById(R.id.familyName)
val familyMember : TextView = view.findViewById(R.id.familyMemberCount)
val subFamily : CheckBox = view.findViewById(R.id.chkSubFamily)
}
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): viewHolder {
val view = LayoutInflater.from(parent.context).inflate(R.layout.family_recycler_single_row,parent,false)
return viewHolder(view)
}
override fun getItemCount(): Int {
return familyList.size
}
override fun onBindViewHolder(holder: viewHolder, position: Int) {
val number = familyList[position]
holder.familyName.text = number.familyName
holder.familyMember.text = number.familyMember.toString()
holder.subFamily.text = number.subFamily.toString()
holder.itemView.setOnClickListener {
val activity : AppCompatActivity = it.context as AppCompatActivity
if (number.subFamily){
// val fragment2 = SubFamilyFragment()
// val fragmentTransaction: FragmentTransaction = activity.supportFragmentManager.beginTransaction()
// fragmentTransaction.replace(R.id.nav_host_fragment, fragment2)
// fragmentTransaction.commit()
val myFragment: Fragment = SubFamilyFragment()
(it.getContext() as AppCompatActivity).supportFragmentManager.beginTransaction()
.replace(R.id.nav_host_fragment, myFragment).addToBackStack(null)
.commit()
}
else{
Toast.makeText(context,"No Sub Family",Toast.LENGTH_SHORT).show()
}
}
}
}```
This code is working but the fragment is overlapping.
Please tell me what to do.

Unresolved reference for applicationContext recycleview element (kotlin app for android)

I'm developing an android app in kotlin, and I want to have a button in every recyclerView element, which will launch an intent - the same in whole recycle view, but with different parameters(for now it's just position for testing, in final form that will be some value from database).
I write the following code for that(inside my adapter class):
override fun onBindViewHolder(holder: ProjectViewHolder, position: Int) {
val Edit: Button = holder.view.EditButton
Edit.setOnClickListener()
{
var projekt: Intent = Intent(applicationContext, Project::class.java)
projekt.putExtra("id", position)
startActivity(projekt)
}
But I get "unresolved refference" error for applicationContext. I used buttons with intent like that before and that worked perfectly fine, though this is the first time I'm trying to do it inside recyclerView element.
How to make it work? Maybe I just take the wrong approach and it should be done in different way?
Edit: Complete adapter class file:
package com.example.legoapp127260
import android.content.Intent
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.Button
import android.widget.TextView
import androidx.recyclerview.widget.RecyclerView
import kotlinx.android.synthetic.main.project_item_layout.view.*
class ProjectAdapter : RecyclerView.Adapter<ProjectViewHolder>()
{
override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): ProjectViewHolder {
val layoutInflater = LayoutInflater.from(viewGroup.context)
val projectRow = layoutInflater.inflate(R.layout.project_item_layout, viewGroup, false)
return ProjectViewHolder(projectRow)
}
override fun getItemCount(): Int {
return 2;
}
override fun onBindViewHolder(holder: ProjectViewHolder, position: Int) {
val projectName: TextView = holder.view.projectName
val projectNames: Array<String> = arrayOf("Set 1", "Set 2")
val Edit: Button = holder.view.EditButton
projectName.setText(projectNames[position])
Edit.setOnClickListener()
{
var projekt: Intent = Intent(Edit.context, Project::class.java)
projekt.putExtra("id", position)
Edit.context.startActivity(projekt)
}
}
}
class ProjectViewHolder(val view: View) : RecyclerView.ViewHolder(view)
{
}
You can get context from your button:
var projekt: Intent = Intent(Edit.context, Project::class.java)
projekt.putExtra("id", position)
Edit.context.startActivity(projekt)

Categories

Resources