Option Strict On
Option Explicit On

Imports System
Imports System.Collections.Generic
Imports System.Globalization
Imports System.Windows.Forms
Imports Nexamas.UI.Architecture
Imports Nexamas.UI.Composition
Imports Nexamas.UI.Controls
Imports Nexamas.UI.General
Imports Nexamas.UI.Layout
Imports Nexamas.UI.Rendering
Imports Nexamas.UI.TextRendering
Imports Nexamas.UI.Theming
Imports Nexamas.UI.Values
Imports SkiaSharp

Namespace Nexamas.UI.Components

    Partial Public NotInheritable Class MASDataForm

#Region "Helpers"

        Private Function HitFieldIndex(ptPx As SKPoint) As Integer
            If _lastFieldRects Is Nothing Then Return -1
            For i As Integer = 0 To _lastFieldRects.Length - 1
                If _lastFieldRects(i).Contains(ptPx.X, ptPx.Y) Then Return i
            Next
            Return -1
        End Function

        Private Sub MoveFocusedField(delta As Integer)
            If _fields.Count <= 0 Then Return
            Dim current As Integer = If(_focusedFieldIndex < 0, If(delta >= 0, -1, _fields.Count), _focusedFieldIndex)
            SetFocusedFieldInternal(current + delta, True)
        End Sub

        Private Sub SetFocusedFieldInternal(value As Integer,
                                            refreshVisual As Boolean)
            Dim normalized As Integer = NormalizeFieldIndex(value)
            If _focusedFieldIndex = normalized Then Return
            _focusedFieldIndex = normalized
            If refreshVisual Then InvalidateVisual()
        End Sub

        Private Function NormalizeFieldIndex(value As Integer) As Integer
            If _fields.Count <= 0 Then Return -1
            If value < 0 Then Return -1
            If value >= _fields.Count Then Return _fields.Count - 1
            Return value
        End Function

        Private Sub NormalizeFocusedFieldAfterCollectionChange()
            _focusedFieldIndex = NormalizeFieldIndex(_focusedFieldIndex)
            If _fields.Count = 0 Then _lastFieldRects = Array.Empty(Of SKRect)()
        End Sub

        Private Function BuildFormSummaryText() As String
            If _fields.Count = 0 Then Return DataFormTokens.EmptyText

            Dim requiredCount As Integer = 0
            Dim issueCount As Integer = 0
            For Each field As FieldEntry In _fields
                If field.Required OrElse field.State = MASDataFormFieldState.Required Then requiredCount += 1
                If MASFormBuilderFieldPolicy.IsIssueState(field.State) Then issueCount += 1
            Next

            Return String.Format(CultureInfo.CurrentCulture, "{0} fields · {1} required · {2} issues", _fields.Count, requiredCount, issueCount)
        End Function

        Private Sub RaiseFieldsChangedSafe()
            Try
                RaiseEvent FieldsChanged(Me, EventArgs.Empty)
            Catch masCaughtException1 As Exception
                Nexamas.UI.Diagnostics.MASExceptionSilencer.SwallowInputBoundary(masCaughtException1, "MASDataForm.FieldsChanged")
            End Try
        End Sub

        Private Shared Function ResolveRightToLeft() As Boolean
            Return Nexamas.UI.Localization.MASLocalization.IsCurrentRightToLeft()
        End Function

        Private Shared Function ResolveKindEmptyText(kind As MASDataFormFieldKind) As String
            Return MASFormBuilderFieldPolicy.ResolveEmptyValuePlaceholder(kind)
        End Function

        Private Shared Function ResolveSurfaceColor(ctx As MASThemeContext) As SKColor
            If ctx IsNot Nothing AndAlso ctx.SurfaceTheme IsNot Nothing Then Return ctx.SurfaceTheme.SurfaceMid
            Return New SKColor(255, 255, 255)
        End Function

        Private Shared Function ResolvePrimaryTextColor(ctx As MASThemeContext) As SKColor
            If ctx IsNot Nothing AndAlso ctx.TextColorTheme IsNot Nothing Then Return ctx.TextColorTheme.PrimaryText
            Return Nexamas.UI.Values.Color.Text.Primary
        End Function

        Private Shared Function ResolveMutedTextColor(ctx As MASThemeContext) As SKColor
            If ctx IsNot Nothing AndAlso ctx.TextColorTheme IsNot Nothing Then Return ctx.TextColorTheme.MutedText
            Return SKColors.Gray
        End Function

        Private Shared Function ResolveAccentColor(ctx As MASThemeContext) As SKColor
            If ctx IsNot Nothing AndAlso ctx.BrandTheme IsNot Nothing Then Return ctx.BrandTheme.BrandPrimary
            If ctx IsNot Nothing AndAlso ctx.SemanticTheme IsNot Nothing Then Return ctx.SemanticTheme.Info
            Return SKColors.DodgerBlue
        End Function

        Private Shared Function ResolveStateColor(ctx As MASThemeContext,
                                                  state As MASDataFormFieldState) As SKColor
            If ctx IsNot Nothing AndAlso ctx.SemanticTheme IsNot Nothing Then
                Select Case state
                    Case MASDataFormFieldState.Success
                        Return ctx.SemanticTheme.Success
                    Case MASDataFormFieldState.Warning
                        Return ctx.SemanticTheme.Warning
                    Case MASDataFormFieldState.[Error]
                        Return ctx.SemanticTheme.Danger
                    Case MASDataFormFieldState.Disabled
                        Return ResolveMutedTextColor(ctx)
                    Case MASDataFormFieldState.Required
                        Return ResolveAccentColor(ctx)
                    Case Else
                        Return ResolveAccentColor(ctx)
                End Select
            End If

            Select Case state
                Case MASDataFormFieldState.Success
                    Return SKColors.SeaGreen
                Case MASDataFormFieldState.Warning
                    Return SKColors.Goldenrod
                Case MASDataFormFieldState.[Error]
                    Return SKColors.IndianRed
                Case Else
                    Return ResolveAccentColor(ctx)
            End Select
        End Function

        Private Shared Function ResolveValueColor(ctx As MASThemeContext,
                                                  state As MASDataFormFieldState) As SKColor
            If state = MASDataFormFieldState.Disabled Then Return ResolveMutedTextColor(ctx).WithAlpha(DataFormTokens.DisabledTextAlpha)
            Return ResolvePrimaryTextColor(ctx).WithAlpha(DataFormTokens.TextAlpha)
        End Function

#End Region

    End Class

End Namespace
