package it.danieleverducci.openweddingapp.ui.gallery

import android.Manifest
import android.app.Activity
import android.app.DownloadManager
import android.app.Service
import android.content.Context
import android.content.Context.DOWNLOAD_SERVICE
import android.content.pm.PackageManager
import android.net.Uri
import android.os.Environment
import android.os.Handler
import android.os.Looper
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.view.animation.Animation
import android.view.animation.AnimationUtils
import android.widget.*
import androidx.appcompat.widget.AppCompatImageView
import androidx.core.app.ActivityCompat
import androidx.core.content.ContextCompat
import androidx.core.content.ContextCompat.getSystemService
import androidx.recyclerview.widget.RecyclerView
import com.squareup.picasso.Picasso
import it.danieleverducci.openweddingapp.Config
import it.danieleverducci.openweddingapp.MainActivity
import it.danieleverducci.openweddingapp.R
import it.danieleverducci.openweddingapp.entities.GalleryItem
import it.danieleverducci.openweddingapp.utils.ImageUtils
import it.danieleverducci.openweddingapp.utils.ViewUtils


class GalleryRecyclerAdapter(private val activityContext: Activity, private val dataset: ArrayList<GalleryItem>):
    RecyclerView.Adapter<GalleryRecyclerAdapter.ViewHolder>() {
    companion object {
        val TAG = "GalleryRecyclerAdapter"
    }

    public var onGalleryItemListener: GalleryItemListener? = null
    public var moreItemsAvailable = true
    private lateinit var likeButtonAnimation: Animation
    private var sharing = false



    override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder {
        if (!this::likeButtonAnimation.isInitialized)
            likeButtonAnimation = AnimationUtils.loadAnimation(parent.context, R.anim.like_button)

        val view = LayoutInflater.from(parent.context).inflate(R.layout.listitem_gallery, parent, false) as LinearLayout
        view.setOnClickListener(object: View.OnClickListener{
            override fun onClick(v: View?) {
                if (v != null) {
                    onGalleryItemListener?.OnGalleryItemClickedListener(v.getTag() as GalleryItem)
                }
            }
        })
        val likeButton = view.findViewById<ImageView>(R.id.gallery_listitem_like_button)
        likeButton.setOnClickListener(object: View.OnClickListener{
            override fun onClick(v: View?) {
                if (v != null) {
                    // Play animation
                    likeButtonAnimation.setAnimationListener(object : Animation.AnimationListener {
                        override fun onAnimationStart(p0: Animation?) {}

                        override fun onAnimationEnd(p0: Animation?) {
                            // Notify listener
                            val rootLayout = v.parent.parent.parent as View
                            onGalleryItemListener?.OnGalleryItemLikedListener(rootLayout.getTag() as GalleryItem)
                        }

                        override fun onAnimationRepeat(p0: Animation?) {}

                    })
                    likeButton.startAnimation(likeButtonAnimation)
                }
            }
        })

        // Download button
        val downloadButton = view.findViewById<ImageView>(R.id.gallery_listitem_download_button)
        downloadButton.setOnClickListener(object: View.OnClickListener{
            override fun onClick(v: View?) {
                if (v != null) {
                    // Request storage permission
                    if (ContextCompat.checkSelfPermission(v.context,
                            Manifest.permission.WRITE_EXTERNAL_STORAGE)
                        != PackageManager.PERMISSION_GRANTED) {
                        // Request permission
                        ActivityCompat.requestPermissions(activityContext,
                            arrayOf(Manifest.permission.WRITE_EXTERNAL_STORAGE),
                            MainActivity.MY_PERMISSIONS_REQUEST
                        )
                    } else {
                        val rootLayout = v.parent.parent.parent as View
                        val uri =
                            Uri.parse("${Config.MEDIA_BASE_URL}${(rootLayout.getTag() as GalleryItem).imageUrl}")
                        val r = DownloadManager.Request(uri)
                        r.setDestinationInExternalPublicDir(
                            Environment.DIRECTORY_PICTURES,
                            "${Config.SAVED_FILES_BASE_NAME}-${System.currentTimeMillis()}.jpg"
                        )
                        r.setNotificationVisibility(DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED)
                        val dm = v.context.getSystemService(DOWNLOAD_SERVICE) as DownloadManager?
                        dm!!.enqueue(r)

                        val progressBar = rootLayout.findViewById<ProgressBar>(R.id.gallery_listitem_share_progressbar)
                        // Replace button with spinning indicator
                        progressBar.visibility = View.VISIBLE
                        v.visibility = View.GONE
                        // After 1 sec, back to previous
                        val h = Handler(Looper.getMainLooper())
                        h.postDelayed({
                            // Replace button with spinning indicator
                            progressBar.visibility = View.GONE
                            v.visibility = View.VISIBLE
                            Toast.makeText(v.context, R.string.image_download_started, Toast.LENGTH_SHORT).show()
                        }, 1000)
                    }
                }
            }
        })

        // Share button
        val shareButton = view.findViewById<ImageView>(R.id.gallery_listitem_share_button)
        shareButton.setOnClickListener(object: View.OnClickListener{
            override fun onClick(v: View?) {
                if (v != null) {
                    if (sharing) {
                        Toast.makeText(v.context, R.string.image_share_already_sharing, Toast.LENGTH_SHORT).show()
                        return
                    }

                    sharing = true
                    val rootLayout = v.parent.parent.parent as View
                    val progressBar = rootLayout.findViewById<ProgressBar>(R.id.gallery_listitem_share_progressbar)
                    // Replace button with spinning indicator
                    progressBar.visibility = View.VISIBLE
                    v.visibility = View.GONE
                    ImageUtils.shareImage(v.context, "${Config.MEDIA_BASE_URL}${(rootLayout.getTag() as GalleryItem).imageUrl}",
                        object: ImageUtils.Companion.OnImageSharedListener {
                            override fun onImageShared() {
                                // Replace spinning indicator with button
                                progressBar.visibility = View.GONE
                                v.visibility = View.VISIBLE
                                sharing = false
                            }

                            override fun onImageShareFailed() {
                                progressBar.visibility = View.GONE
                                Toast.makeText(v.context, R.string.image_share_fail, Toast.LENGTH_SHORT).show()
                                sharing = false
                            }
                        })
                }
            }
        })
        return ViewHolder(view)
    }

    override fun getItemCount(): Int {
        return dataset.size
    }

    override fun onBindViewHolder(holder: ViewHolder, position: Int) {
        if (position == itemCount - 1) {
           onGalleryItemListener?.OnGalleryLastItemScrolledListener()
        }
        holder.setItem(dataset.get(position), position == itemCount-1, moreItemsAvailable)
    }

    class ViewHolder(val view: LinearLayout): RecyclerView.ViewHolder(view) {
        val userImageBadge: AppCompatImageView
        val userTextBadge: TextView
        val userName: TextView
        val image: ImageView
        val description: TextView
        val likes: TextView
        val likeButton: ImageView
        val progress: View
        init {
            userImageBadge = view.findViewById(R.id.gallery_listitem_user_badge)
            userTextBadge = view.findViewById(R.id.gallery_listitem_user_text_badge)
            userName = view.findViewById(R.id.gallery_listitem_user_name)
            image = view.findViewById(R.id.gallery_listitem_image)
            description = view.findViewById(R.id.gallery_listitem_description)
            likes = view.findViewById(R.id.gallery_listitem_likes)
            likeButton = view.findViewById(R.id.gallery_listitem_like_button)
            progress = view.findViewById(R.id.gallery_listitem_progress)
        }

        public fun setItem(item: GalleryItem, isLast: Boolean, more: Boolean) {
            view.setTag(item)

            // Post image
            Picasso.get()
                .load(item.thumbUrl)
                .placeholder(R.drawable.placeholder)
                .error(R.drawable.placeholder)
                .into(image)

            // User image
            if (item.author.picture != null && item.author.picture.isNotEmpty()) {
                userImageBadge.visibility = View.VISIBLE
                userTextBadge.visibility = View.GONE
                Picasso.get()
                    .load(item.author.pictureUrl)
                    .placeholder(R.drawable.placeholder)
                    .error(R.drawable.placeholder)
                    .into(userImageBadge)
            } else {
                userImageBadge.visibility = View.GONE
                userTextBadge.visibility = View.VISIBLE
                userTextBadge.text = item.author.name.substring(0,1)
                ViewUtils.colorizeUserBadge(userTextBadge, item.author)
            }

            userName.setText("${item.author.name} ${item.author.surname}")
            if (item.description.isNotEmpty()) {
                description.visibility = View.VISIBLE
                description.text = item.description
            } else {
                description.visibility = View.GONE
            }

            // Set likes text
            if (item.likes == 0)
                likes.setText("")
            else if (item.likes == 1)
                likes.setText(likes.context.getString(R.string.gallery_liked_single).format(item.firstUserLiked?.name))
            else
                likes.setText(likes.context.getString(R.string.gallery_liked_by).format(item.firstUserLiked?.name, item.likes - 1))

            // Set icon color
            likeButton.background = ContextCompat.getDrawable(likeButton.context,
                if (item.currentUserLike != null) R.drawable.gallery_like_button_background_active else R.drawable.gallery_like_button_background_inactive
            )

            progress.visibility = if (isLast && more) View.VISIBLE else View.GONE
        }
    }

    interface GalleryItemListener {
        fun OnGalleryItemClickedListener(item: GalleryItem)
        fun OnGalleryItemLikedListener(item: GalleryItem)
        fun OnGalleryLastItemScrolledListener()
    }
}