How do a simple timer with proccess?
This timer should have to GenServer to take away the management of the timer, In this timer we will have a counter to know how many seconds we want during the timer.
defmodule ExTyperacer.TimerServer do
use GenServer
require Kernel
alias ExTyperacer.Logic.{Game, Player}
def start_link() do
GenServer.start_link(__MODULE__, %{})
end
def init(state) do
IO.puts "Init timer"
#timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:ok, state}
end
def handle_call({:reset_timer, counter, uuid}, _from, %{timer: timer}) do
:timer.cancel(timer)
timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:reply, :ok, %{timer: timer}}
end
def handle_info({:work, 0, uuid}, state) do
IO.puts "Finished proccess"
{:noreply, state}
end
def handle_info({:work, counter, uuid}, state) do
IO.puts "Counting..."
IO.inspect counter
counter = counter - 1
timer = Process.send_after(self(), {:work, counter, uuid},1_000)
{:noreply, %{timer: timer}}
end
def handle_info({:start_timer, counter, uuid}, state) do
timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:noreply, %{timer: timer}}
end
# So that unhanded messages don't error
def handle_info(_, state) do
{:ok, state}
end
end
Demo
If you want to add one communicate for broadcast to channel, you should have to like this:
- Subscribe timer server to channel
ExTyperacerWeb.Endpoint.subscribe "timer:start", []
- Created a private function to use broadcast
defp broadcast(time, response) do
IO.inspect response
ExTyperacerWeb.Endpoint.broadcast! "timer:update", "new_time_#{response.uuid}", %{ response: response.message, time: time}
end
For example:
defmodule ExTyperacer.TimerServer do
use GenServer
require Kernel
alias ExTyperacer.Logic.{Game, Player}
def start_link() do
GenServer.start_link(__MODULE__, %{})
end
def init(state) do
IO.puts "Init timer"
ExTyperacerWeb.Endpoint.subscribe "timer:start", []
#timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:ok, state}
end
def handle_call({:reset_timer, counter, uuid}, _from, %{timer: timer}) do
:timer.cancel(timer)
timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:reply, :ok, %{timer: timer}}
end
def handle_info({:work, 0, uuid}, state) do
IO.puts "Finished proccess"
broadcast 0, %{message: "Counting", uuid: uuid}
{:noreply, state}
end
def handle_info({:work, counter, uuid}, state) do
IO.puts "Counting..."
IO.inspect uuid
IO.inspect counter
broadcast counter, %{message: "Counting", uuid: uuid}
counter = counter - 1
timer = Process.send_after(self(), {:work, counter, uuid},1_000)
{:noreply, %{timer: timer}}
end
def handle_info({:start_timer, counter, uuid}, state) do
timer = Process.send_after(self(), {:work, counter, uuid}, 1_000)
{:noreply, %{timer: timer}}
end
# So that unhanded messages don't error
def handle_info(_, state) do
{:ok, state}
end
defp broadcast(time, response) do
IO.inspect response
ExTyperacerWeb.Endpoint.broadcast! "timer:update","new_time", %{ time: time, response: response.message}
end
end