diff --git a/predator_prey_generic.jl b/predator_prey_generic.jl index 95c6072..9b135c1 100644 --- a/predator_prey_generic.jl +++ b/predator_prey_generic.jl @@ -107,6 +107,7 @@ function eat!(a::Animal, model) end if "Grass" ∈ a.def.food && model.fully_grown[a.pos...] model.fully_grown[a.pos...] = false + model.growth[a.pos...] = 0 a.energy += model.Δenergy_grass end return @@ -194,7 +195,7 @@ function initialize_model(; model_properties = Dict( :events => events, :fully_grown => falses(dims), - :countdown => zeros(Int, dims), + :growth => zeros(Int, dims), :regrowth_time => regrowth_time, :Δenergy_grass => Δenergy_grass, ) @@ -212,8 +213,8 @@ function initialize_model(; ## Add grass with random initial growth for p in positions(model) fully_grown = rand(abmrng(model), Bool) - countdown = fully_grown ? regrowth_time : rand(abmrng(model), 1:regrowth_time) - 1 - model.countdown[p...] = countdown + growth = fully_grown ? regrowth_time : rand(abmrng(model), 1:regrowth_time) - 1 + model.growth[p...] = growth model.fully_grown[p...] = fully_grown end return model @@ -245,7 +246,7 @@ function animal_step!(a::Animal, model) end function model_step!(model) - event_handler!(model) + handle_event!(model) grass_step!(model) end @@ -264,25 +265,26 @@ function grass_step!(model) end @inbounds for p in positions(model) # we don't have to enable bound checking if !(model.fully_grown[p...]) - if model.countdown[p...] ≤ 0 + if model.growth[p...] ≥ model.regrowth_time#≤ 0 model.fully_grown[p...] = true - model.countdown[p...] = model.regrowth_time + #model.growth[p...] = model.regrowth_time else - model.countdown[p...] -= 1 + model.growth[p...] += 1 end end end end -# Check current step and start event at step t -function event_handler!(model) +function handle_event!(model) ids = collect(allids(model)) for event in model.events if event.timer == event.t_start # start event if event.name == "Drought" - model.regrowth_time = event.value - for id in ids - abmproperties(model)[Symbol(model[id].def.type*"_"*"perception")] += 1 + #model.regrowth_time = event.value + + predators = filter(id -> !("Grass" ∈ model[id].def.food), ids) + for id in predators + abmproperties(model)[Symbol(model[id].def.type*"_"*"perception")] = 2 end elseif event.name == "Flood" @@ -291,6 +293,7 @@ function event_handler!(model) abmproperties(model)[Symbol(model[id].def.type*"_"*"Δenergy")] -= 1 end + elseif event.name == "PreyReproduceSeasonal" prey = filter(id -> "Grass" ∈ model[id].def.food, ids) for id in prey @@ -306,11 +309,37 @@ function event_handler!(model) end end + if (event.timer ≥ event.t_start) && (event.timer < event.t_end) + if event.name == "Drought" + for p in positions(model) + dry_out_chance = 0.4 * (model.growth[p...] / model.regrowth_time) + if model.fully_grown[p...] && (dry_out_chance ≥ rand(abmrng(model))) + #model.growth[p...] = 0 + model.growth[p...] = rand(abmrng(model), 1:model.regrowth_time) - 1 + model.fully_grown[p...] = false + end + end + elseif event.name == "Winter" + block_field_every = 2 + i = 1 + for p in positions(model) + if i % block_field_every == 0 + model.growth[p...] = rand(abmrng(model), 1:(model.regrowth_time / 2)) + model.fully_grown[p...] = false + end + i += 1 + end + + end + end + + if event.timer == event.t_end # end event if event.name == "Drought" - model.regrowth_time = event.pre_value - for id in ids - abmproperties(model)[Symbol(model[id].def.type*"_"*"perception")] -= 1 + #model.regrowth_time = event.pre_value + predators = filter(id -> !("Grass" ∈ model[id].def.food), ids) + for id in predators + abmproperties(model)[Symbol(model[id].def.type*"_"*"perception")] = 1 end elseif event.name == "Flood" @@ -334,9 +363,9 @@ function event_handler!(model) end end - if event.timer == event.t_cycle # reset cycle - event.timer = 1 - else + if event.timer == event.t_cycle # reset timer + event.timer = 0 + else # continue timer event.timer += 1 end end diff --git a/test_predator_prey_generic.ipynb b/test_predator_prey_generic.ipynb index ce7b85c..9ff58e9 100644 --- a/test_predator_prey_generic.ipynb +++ b/test_predator_prey_generic.ipynb @@ -2,7 +2,7 @@ "cells": [ { "cell_type": "code", - "execution_count": 1, + "execution_count": 8, "metadata": {}, "outputs": [ { @@ -21,7 +21,7 @@ }, { "cell_type": "code", - "execution_count": 2, + "execution_count": 81, "metadata": {}, "outputs": [ { @@ -42,7 +42,7 @@ "acolor(a) = a.def.color\n", "\n", "# and instruct [`abmplot`](@ref) how to plot grass as a heatmap:\n", - "grasscolor(model) = model.countdown ./ model.regrowth_time\n", + "grasscolor(model) = model.growth ./ model.regrowth_time\n", "# and finally define a colormap for the grass:\n", "heatkwargs = (colormap = [:brown, :green], colorrange = (0, 1))\n", "\n", @@ -60,7 +60,7 @@ }, { "cell_type": "code", - "execution_count": 8, + "execution_count": 105, "metadata": {}, "outputs": [], "source": [ @@ -68,11 +68,13 @@ "#Pkg.status([\"Agents\",\"GLMakie\"]; mode = Pkg.Types.PKGMODE_MANIFEST, io=stdout)\n", "using GLMakie\n", "GLMakie.activate!()\n", - "events = RecurringEvent[]\n", - "#push!(events, RecurringEvent(\"Drought\", 80, 30, 30, 50, 120, 1))\n", - "#push!(events, RecurringEvent(\"Flood\", 50, 30, 70, 80, 120, 1))\n", - "#push!(events, RecurringEvent(\"PreyReproduceSeasonal\", 0.5, 0.1, 1, 4, 12, 1))\n", - "#push!(events, RecurringEvent(\"PredatorReproduceSeasonal\", 0.1, 0.07, 4, 6, 12, 1))\n", + "events = RecurringEvent[\n", + "#RecurringEvent(\"Drought\", 30, 30, 30, 60, 120, 0)\n", + "#RecurringEvent(\"Flood\", 50, 30, 70, 80, 120, 0)\n", + "RecurringEvent(\"Winter\", 0, 0, 18, 24, 24, 0)\n", + "RecurringEvent(\"PreyReproduceSeasonal\", 0.5, 0.05, 1, 6, 24, 0)\n", + "#RecurringEvent(\"PredatorReproduceSeasonal\", 0.1, 0.07, 4, 6, 12, 0)\n", + "]\n", "animal_defs = [\n", "AnimalDefinition(30,'●',RGBAf(1.0, 1.0, 1.0, 0.8),20, 0.3, 20, 3, \"Sheep\", [\"Wolf\",\"Bear\"], [\"Grass\"])\n", "AnimalDefinition(3,'▲',RGBAf(0.2, 0.2, 0.3, 0.8),20, 0.07, 20, 1, \"Wolf\", [], [\"Sheep\"])\n", @@ -110,17 +112,23 @@ " alabels = [\"Sheep\", \"Wolf\", \"Eaten\", \"Starved\"],\n", " mdata, mlabels = [\"Grass\"]\n", ")\n", - "#, step! = (model) -> begin event_handler!(model, \"Dürre\") model.wolf_reproduce = 0.1 Agents.step!() end\n", "#fig, ax, abmobs = abmplot(model; add_controls=true, plotkwargs...)\n", "\n", "fig\n", "#run!(model, 2)" ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] } ], "metadata": { "kernelspec": { - "display_name": "Julia 1.10.3", + "display_name": "Julia 1.10.2", "language": "julia", "name": "julia-1.10" }, @@ -128,7 +136,7 @@ "file_extension": ".jl", "mimetype": "application/julia", "name": "julia", - "version": "1.10.3" + "version": "1.10.2" } }, "nbformat": 4,