export type MailListViewMode = "list-only" | "split-horizontal" | "split-vertical";
export type MailListSortOrder = "latest" | "oldest";

export type MailLayoutPreferences = {
  sidebarWidth: number;
  listWidth: number;
  listHeight: number;
  viewMode: MailListViewMode;
  sortOrder: MailListSortOrder;
};

export const DEFAULT_MAIL_LAYOUT_PREFERENCES: MailLayoutPreferences = {
  sidebarWidth: 270,
  listWidth: 540,
  listHeight: 420,
  viewMode: "list-only",
  sortOrder: "latest",
};

export const MAIL_LAYOUT_LIMITS = {
  sidebar: {
    min: 220,
    max: 420,
  },
  list: {
    min: 540,
    max: 760,
  },
  listHeight: {
    min: 220,
    max: 760,
  },
  detailMinWidth: 320,
  detailMinHeight: 220,
  contentMinWidth: 420,
} as const;

function clamp(value: number, min: number, max: number) {
  return Math.min(max, Math.max(min, value));
}

function normalizeNumber(value: unknown, fallback: number) {
  if (typeof value !== "number" || !Number.isFinite(value)) {
    return fallback;
  }

  return Math.round(value);
}

function normalizeViewMode(value: unknown, fallback: MailListViewMode) {
  return value === "split-horizontal" || value === "split-vertical" || value === "list-only"
    ? value
    : fallback;
}

function normalizeSortOrder(value: unknown, fallback: MailListSortOrder) {
  return value === "oldest" || value === "latest" ? value : fallback;
}

export function normalizeMailLayoutPreferences(input?: Partial<MailLayoutPreferences>) {
  return {
    sidebarWidth: clamp(
      normalizeNumber(input?.sidebarWidth, DEFAULT_MAIL_LAYOUT_PREFERENCES.sidebarWidth),
      MAIL_LAYOUT_LIMITS.sidebar.min,
      MAIL_LAYOUT_LIMITS.sidebar.max,
    ),
    listWidth: clamp(
      normalizeNumber(input?.listWidth, DEFAULT_MAIL_LAYOUT_PREFERENCES.listWidth),
      MAIL_LAYOUT_LIMITS.list.min,
      MAIL_LAYOUT_LIMITS.list.max,
    ),
    listHeight: clamp(
      normalizeNumber(input?.listHeight, DEFAULT_MAIL_LAYOUT_PREFERENCES.listHeight),
      MAIL_LAYOUT_LIMITS.listHeight.min,
      MAIL_LAYOUT_LIMITS.listHeight.max,
    ),
    viewMode: normalizeViewMode(
      input?.viewMode,
      DEFAULT_MAIL_LAYOUT_PREFERENCES.viewMode,
    ),
    sortOrder: normalizeSortOrder(
      input?.sortOrder,
      DEFAULT_MAIL_LAYOUT_PREFERENCES.sortOrder,
    ),
  } satisfies MailLayoutPreferences;
}
