package com.anytypeio.anytype.presentation.objects

import com.anytypeio.anytype.core_models.Hash
import com.anytypeio.anytype.core_models.ObjectWrapper
import com.anytypeio.anytype.core_models.Url
import com.anytypeio.anytype.domain.misc.UrlBuilder
import com.anytypeio.anytype.presentation.objects.ObjectIcon.TypeIcon.Default.Companion.DEFAULT_ICON_PREFIX
import com.anytypeio.anytype.presentation.objects.custom_icon.CustomIconColor

sealed class ObjectIcon {

    data object None : ObjectIcon()

    sealed class Basic : ObjectIcon() {
        data class Image(
            val hash: Hash,
            val fallback: TypeIcon.Fallback = TypeIcon.Fallback.DEFAULT
        ) : Basic()

        data class Emoji(
            val unicode: String,
            val fallback: TypeIcon.Fallback = TypeIcon.Fallback.DEFAULT
        ) : Basic()
    }

    sealed class Profile : ObjectIcon() {
        data class Avatar(val name: String) : Profile()
        data class Image(val hash: Hash, val name: String) : Profile()
    }

    data class Task(val isChecked: Boolean) : ObjectIcon()

    data class Bookmark(
        val image: Url,
        val fallback: TypeIcon
    ) : ObjectIcon()

    data class File(
        val mime: String?,
        val fileName: String?,
        val extensions: String? = null
    ) : ObjectIcon()

    data object Deleted : ObjectIcon()

    data class Checkbox(val isChecked: Boolean) : ObjectIcon()

    sealed class TypeIcon : ObjectIcon() {

        /**
         * Extension function that converts a kebab-case string to snake_case.
         *
         * Simply replaces all occurrences of '-' with '_'.
         *
         * @receiver String to be converted.
         * @return The snake_case version of the string.
         */
        internal fun String.toSnakeCase(): String = replace("-", "_")

        data object Deleted : TypeIcon() {
            const val DEFAULT_DELETED_ICON = "extension-puzzle"
        }

        data class Emoji(
            val unicode: String,
            val rawValue: String,
            val color: CustomIconColor,
        ) : TypeIcon()

        data class Default(
            val rawValue: String,
            val color: CustomIconColor,
        ) : TypeIcon() {

            /**
             * Returns the drawable resource name for this icon.
             *
             * The drawable name is generated by converting [rawValue] from kebab-case
             * (e.g., "battery-dead") to snake_case ("battery_dead") and prefixing it with "ci_".
             */
            val drawableResId: String
                get() = DEFAULT_ICON_PREFIX + rawValue.toSnakeCase()

            companion object {
                const val DEFAULT_ICON_PREFIX = "ci_"
                const val DEFAULT_CUSTOM_ICON = "extension-puzzle"

                val DEFAULT = Default(DEFAULT_CUSTOM_ICON, CustomIconColor.DEFAULT)
                val DATE = Default("calendar", CustomIconColor.DEFAULT)
            }
        }

        //we use this icon when we can't find the emoji for object or image icon can't be loaded
        data class Fallback(val rawValue: String) : TypeIcon() {

            val drawableResId: String
                get() = DEFAULT_ICON_PREFIX + rawValue.toSnakeCase()

            companion object {
                const val DEFAULT_FALLBACK_ICON = "extension-puzzle"

                val DEFAULT = Fallback(DEFAULT_FALLBACK_ICON)
            }
        }
    }
}

sealed class SpaceMemberIconView {
    data class Placeholder(val name: String) : SpaceMemberIconView()
    data class Image(val url: String, val name: String) : SpaceMemberIconView()

    companion object {
        fun icon(obj: ObjectWrapper.SpaceMember, urlBuilder: UrlBuilder) : SpaceMemberIconView {
            val icon = obj.iconImage
            return when {
                !icon.isNullOrEmpty() -> Image(
                    url = urlBuilder.thumbnail(icon),
                    name = obj.name.orEmpty()
                )
                else -> Placeholder(name = obj.name.orEmpty())
            }
        }
    }
}