defmodule LabelmakerWeb.Tools do # for the ~p sigil use Phoenix.VerifiedRoutes, endpoint: LabelmakerWeb.Endpoint, router: LabelmakerWeb.Router, statics: LabelmakerWeb.static_paths() alias LabelmakerWeb.Constants def process_parameters(parameters) do parameters = Constants.defaults() |> Map.new(fn {k, v} -> {Atom.to_string(k), v} end) |> Map.merge(parameters) |> Enum.map(fn {"label", label} -> {"label", process_label(label)} pair -> pair end) |> Map.new() parameters = Constants.defaults() |> Map.new(fn {k, v} -> {Atom.to_string(k), v} end) |> Map.merge(parameters) |> Map.take(Constants.permitted_keys()) |> Map.new(fn {k, v} -> {String.to_atom(k), v} end) |> Enum.map(fn {:align, align} -> {:align, align |> String.downcase()} {:font, font} -> {:font, Constants.font_map()[String.downcase(font)]} {:height, height} -> {:height, process_height(height, parameters)} {:label_too_long, _} -> {:label_too_long, String.length(parameters["label"]) > Constants.max_label_length()} {:preview_height, _} -> {:preview_height, calculate_preview_height(parameters)} {:preview_text, _} -> {:preview_text, generate_preview_text(parameters["label"])} {:rows, _} -> {:rows, process_rows(parameters["label"])} {:sizing, _} -> {:sizing, process_sizing(parameters)} {:width, width} -> {:width, process_width(width, parameters)} pair -> pair end) |> Enum.filter(fn {:align, align} -> align in Constants.permitted_alignments() {:color, color} -> color in Constants.colors() {:font, font} -> font in Map.values(Constants.font_map()) {:outline, outline} -> outline in Constants.outlines() {:size, size} -> size in Constants.sizes() _ -> true end) |> Map.new() parameters = Map.merge(Constants.defaults(), parameters) Map.put(parameters, :link, generate_link(parameters)) end def process_gravity("left"), do: "west" def process_gravity("middle"), do: "center" def process_gravity("right"), do: "east" def process_gravity(alignment), do: alignment |> String.downcase() defp process_height("", _parameters), do: "" # defp process_height("", parameters) do # parameters["width"] |> String.to_integer() |> max(0) |> min(Constants.max_height()) # end defp process_height(height, _parameters) do height |> String.to_integer() |> max(0) |> min(Constants.max_height()) end defp process_label(label) do label |> String.replace("\\n", "\n") |> String.slice(0, Constants.max_label_length()) end defp generate_link(%{height: "", label: label, width: ""} = parameters) do ~p"/#{label}?#{Map.take(parameters, [:color, :font, :outline, :size])}" end defp generate_link(%{label: label} = parameters) do ~p"/#{label}?#{Map.take(parameters, [:align, :color, :font, :height, :outline, :width])}" end defp generate_preview_text(label) do label |> String.replace("\n", "
") end def process_preview_background(bg) do case bg do "r" -> "bg-[linear-gradient(to_right,_black_33%,_white_67%)]" "b" -> "bg-[linear-gradient(to_bottom,_black_33%,_white_67%)]" "c" -> "" _ -> "bg-[linear-gradient(to_right,_black_33%,_white_67%)]" end end defp process_width("", _parameters), do: "" # defp process_width("", parameters) do # parameters["height"] |> String.to_integer() |> max(0) |> min(Constants.max_width()) # end defp process_width(width, _parameters) do width |> String.to_integer() |> max(0) |> min(Constants.max_width()) end defp calculate_preview_height(parameters) do size = parameters["size"] |> String.to_integer() rows = calculate_rows(parameters["label"]) size + size * rows end defp calculate_rows(label) do Regex.scan(~r/#{Regex.escape("\n")}/, label) |> length() end defp process_rows(label) do calculate_rows(label) |> max(Constants.rows_min()) |> min(Constants.rows_max()) end defp process_sizing(%{"_target" => [target | _tail]}) when target in ["width", "height", "radio_option"], do: "wxh" defp process_sizing(%{"_target" => ["size" | _tail]}), do: "font" defp process_sizing(%{"sizing" => sizing}), do: sizing def outline(_, error: true), do: outline(Constants.danger(), false) def outline("none", _error), do: "" def outline(color, _error), do: "text-shadow: -1px -1px 0 #{color}, 1px -1px 0 #{color}, -1px 1px 0 #{color}, 1px 1px 0 #{color};" end