118 lines
3 KiB
Elixir
118 lines
3 KiB
Elixir
|
defmodule Scenic.Driver.Renderling.Window do
|
||
|
@moduledoc """
|
||
|
The Scenic for windowed applications.
|
||
|
"""
|
||
|
|
||
|
alias Scenic.ViewPort
|
||
|
alias Scenic.Driver.Renderling.Window.{Config, Nif}
|
||
|
|
||
|
use Scenic.Driver
|
||
|
require Logger
|
||
|
|
||
|
@default_limit 29
|
||
|
@default_layer 0
|
||
|
@default_opacity 255
|
||
|
|
||
|
@position_schema [
|
||
|
scaled: [type: :boolean, default: false],
|
||
|
centered: [type: :boolean, default: false],
|
||
|
orientation: [type: {:in, [:normal, :left, :right, :upside_down]}, default: :normal]
|
||
|
]
|
||
|
|
||
|
@window_schema [
|
||
|
title: [type: :string, default: "Scenic Window"],
|
||
|
resizeable: [type: :boolean, default: false]
|
||
|
]
|
||
|
|
||
|
@opts_schema [
|
||
|
name: [type: {:or, [:atom, :string]}],
|
||
|
limit_ms: [type: :non_neg_integer, default: @default_limit],
|
||
|
layer: [type: :integer, default: @default_layer],
|
||
|
opacity: [type: :integer, default: @default_opacity],
|
||
|
debug: [type: :boolean, default: false],
|
||
|
debugger: [type: :string, default: ""],
|
||
|
debug_fps: [type: :integer, default: 0],
|
||
|
antialias: [type: :boolean, default: true],
|
||
|
position: [type: :keyword_list, keys: @position_schema, default: []],
|
||
|
window: [type: :keyword_list, keys: @window_schema, default: []],
|
||
|
cursor: [type: :boolean, default: false],
|
||
|
key_map: [type: :atom, default: Scenic.KeyMap.USEnglish],
|
||
|
on_close: [
|
||
|
type:
|
||
|
{:or, [:mfa, {:in, [:restart, :stop_driver, :stop_viewport, :stop_system, :halt_system]}]},
|
||
|
default: :restart
|
||
|
],
|
||
|
input_blacklist: [type: {:list, :string}, default: []]
|
||
|
]
|
||
|
|
||
|
@doc false
|
||
|
@impl Scenic.Driver
|
||
|
def validate_opts(opts), do: NimbleOptions.validate(opts, @opts_schema)
|
||
|
|
||
|
@doc false
|
||
|
@impl true
|
||
|
def init(driver, opts) do
|
||
|
{width, height} = driver.viewport.size
|
||
|
|
||
|
config =
|
||
|
opts
|
||
|
|> Keyword.update(
|
||
|
:window,
|
||
|
[width: width, height: height],
|
||
|
&Keyword.merge(&1, width: width, height: height)
|
||
|
)
|
||
|
|> Config.init()
|
||
|
|
||
|
driver = assign(driver, config: config, server: Nif.init(config))
|
||
|
|
||
|
Process.flag(:trap_exit, true)
|
||
|
|
||
|
Logger.info("#{inspect(__MODULE__)}: start #{inspect(opts)}, pid: #{inspect(self())}")
|
||
|
|
||
|
{:ok, driver}
|
||
|
end
|
||
|
|
||
|
@doc false
|
||
|
@impl true
|
||
|
def update_scene(ids, driver) do
|
||
|
Enum.reduce_while(ids, {:ok, driver}, fn id, {:ok, driver} ->
|
||
|
case ViewPort.get_script(driver.viewport, id) do
|
||
|
{:ok, script} ->
|
||
|
Nif.update_scene(script, id, driver.assigns.server)
|
||
|
|
||
|
{:cont, {:ok, driver}}
|
||
|
|
||
|
{:error, reason} ->
|
||
|
{:halt, {:error, reason}}
|
||
|
end
|
||
|
end)
|
||
|
end
|
||
|
|
||
|
@doc false
|
||
|
@impl true
|
||
|
def reset_scene(driver) do
|
||
|
Nif.reset_scene(driver.assigns.server)
|
||
|
{:ok, driver}
|
||
|
end
|
||
|
|
||
|
@doc false
|
||
|
@impl true
|
||
|
def del_scripts(ids, driver) do
|
||
|
Nif.del_scripts(ids, driver.assigns.server)
|
||
|
{:ok, driver}
|
||
|
end
|
||
|
|
||
|
@doc false
|
||
|
@impl true
|
||
|
def clear_color(color, driver) do
|
||
|
Nif.clear_color(color, driver.assigns.server)
|
||
|
{:ok, driver}
|
||
|
end
|
||
|
|
||
|
@doc false
|
||
|
@impl GenServer
|
||
|
def terminate(_, driver) do
|
||
|
Nif.terminate(driver.assigns.server)
|
||
|
end
|
||
|
end
|