From 9e0ed0c2563587aca928ed1634eb569be9d3bc48 Mon Sep 17 00:00:00 2001 From: Till Affeldt Date: Sun, 26 Apr 2020 18:11:38 +0200 Subject: [PATCH] Tweak world cycle, add documentation --- ca_effects/hud_overlay.lua | 9 ++++++++ ca_effects/particles.lua | 20 +++++++++++++++++- ca_effects/skybox.lua | 12 +++++++++++ ca_effects/sound.lua | 9 ++++++++ init.lua | 18 ++++++++++++---- lib/api.lua | 42 ++++++++++++++++++++++++++++++++------ lib/commands.lua | 12 +++++++++++ lib/datastorage.lua | 2 +- lib/main.lua | 4 ++-- lib/trigger.lua | 1 - 10 files changed, 114 insertions(+), 15 deletions(-) diff --git a/ca_effects/hud_overlay.lua b/ca_effects/hud_overlay.lua index f2cd2cf..e816854 100644 --- a/ca_effects/hud_overlay.lua +++ b/ca_effects/hud_overlay.lua @@ -1,3 +1,12 @@ +--[[ +# HUD Overlay Effect +Use this effect to display a fullscreen image as part of a player's HUD. +Expects a table as the parameter containing the following values: +- ``file ``: The name (including file ending) if the image to be displayed +- ``z_index `` (optional): The z_index to forward to player.hud_add. Defaults to 1 +- ``color_correction `` (optional): Whether the image should automatically darken based on current light. Defaults to false. +]] + if not climate_mod.settings.hud_overlay then return end local EFFECT_NAME = "climate_api:hud_overlay" diff --git a/ca_effects/particles.lua b/ca_effects/particles.lua index f0e7898..2f592d9 100644 --- a/ca_effects/particles.lua +++ b/ca_effects/particles.lua @@ -1,3 +1,21 @@ +--[[ +# Particle Effect +Use this effect to render downfall using particles. +Expects a table as the parameter containing the following values: +- amount : The quantity of spawned particles per cycle +- EITHER texture : The image file name +- OR textures : A list of possible texture variants +- falling_speed : The downwards speed +- min_pos : Bottom-left corner of spawn position (automatically adjusted by wind) +- max_pos : Top-right corner of spawn position (automatically adjusted by wind) +- acceleration (optional): Particle acceleration in any direction +- exptime : Time of life of particles +- time (optional): The time of life of particle spawners (defaults to 0.5) +- EITHER size : Size of the particles +- OR min_size and max_size : Minimum and maximum size +- vertical (optional): Whether particles should rotate in 2D space only (default depends on falling vector) +]] + if not climate_mod.settings.particles then return end local EFFECT_NAME = "climate_api:particles" @@ -10,7 +28,7 @@ local function get_particle_texture(particles) end local function spawn_particles(player, particles) - local ppos = player:getpos() + local ppos = player:get_pos() local wind = climate_api.environment.get_wind() local amount = particles.amount * climate_mod.settings.particle_count diff --git a/ca_effects/skybox.lua b/ca_effects/skybox.lua index bce8b78..3110270 100644 --- a/ca_effects/skybox.lua +++ b/ca_effects/skybox.lua @@ -1,3 +1,15 @@ +--[[ +# Skybox Effect +Use this effect to modify a player's sky, clouds, sun, moon, or stars +Expects a table as the parameter containing the following values: +- ``sky_data
`` (optional): Sky paramaters to be applied using player.set_sky +- ``cloud_data
`` (optional): Cloud paramaters to be applied using player.set_clouds +- ``sun_data
`` (optional): Sun paramaters to be applied using player.set_sun +- ``moon_data
`` (optional): Sky paramaters to be applied using player.set_moon +- ``star_data
`` (optional): Sky paramaters to be applied using player.set_stars +- ``priority `` (optional): A skybox with higher priority will override lower rated ones (defaults to 1) +]] + if not climate_mod.settings.skybox then return end local EFFECT_NAME = "climate_api:skybox" diff --git a/ca_effects/sound.lua b/ca_effects/sound.lua index 04a42c1..6da671d 100644 --- a/ca_effects/sound.lua +++ b/ca_effects/sound.lua @@ -1,3 +1,12 @@ +--[[ +# Sound Loop Effect +Use this effect to loop an ambient sound effect +Expects a table as the parameter containing the following values: +- ``name ``: Name of the played sound effect (without .ogg file ending) +- ``gain `` (optional): Volume of the sound (defaults to 1.0) +- ``pitch `` (optional): Pitch of the sound (defaults to 1.0) +]] + if not climate_mod.settings.sound then return end local EFFECT_NAME = "climate_api:sound" diff --git a/init.lua b/init.lua index e89c198..756c59d 100644 --- a/init.lua +++ b/init.lua @@ -1,17 +1,22 @@ +-- warn about outdated Minetest versions assert(minetest.add_particlespawner, "[Climate API] This mod requires a more current version of Minetest") +-- initialize global API interfaces climate_api = {} climate_mod = {} +-- set mod path for file imports local modname = minetest.get_current_modname() local modpath = minetest.get_modpath(modname) +-- retrieve boolean value from mod config local function get_setting_bool(name, default) local value = minetest.settings:get_bool("climate_api_" .. name) if type(value) == "nil" then value = default end return minetest.is_yes(value) end +-- retrive numeric value from mod config local function get_setting_number(name, default) local value = minetest.settings:get("climate_api_" .. name) if type(value) == "nil" then value = default end @@ -36,7 +41,7 @@ climate_mod.settings = { volume = get_setting_number("volume", 1) } --- initiate empty registers +-- initialize empty registers climate_mod.weathers = {} climate_mod.effects = {} climate_mod.cycles = {} @@ -48,19 +53,24 @@ climate_mod.current_effects = {} climate_mod.forced_weather = {} climate_mod.forced_wind = nil --- import core API +-- handle persistent mod storage climate_mod.state = dofile(modpath .. "/lib/datastorage.lua") + +-- import core API climate_api = dofile(modpath .. "/lib/api.lua") climate_api.utility = dofile(modpath .. "/lib/api_utility.lua") climate_api.skybox = dofile(modpath .. "/lib/skybox_merger.lua") -dofile(modpath .. "/lib/influences.lua") climate_api.environment = dofile(modpath .. "/lib/environment.lua") ---climate_api = dofile(modpath .. "/lib/influences.lua") climate_mod.world = dofile(modpath .. "/lib/world.lua") climate_mod.trigger = dofile(modpath .. "/lib/trigger.lua") + +-- start event loop and register chat commands dofile(modpath.."/lib/main.lua") dofile(modpath.."/lib/commands.lua") +-- register environment influences +dofile(modpath .. "/lib/influences.lua") + -- import predefined environment effects dofile(modpath .. "/ca_effects/hud_overlay.lua") dofile(modpath .. "/ca_effects/particles.lua") diff --git a/lib/api.lua b/lib/api.lua index 0ba901a..4cb6b8c 100644 --- a/lib/api.lua +++ b/lib/api.lua @@ -1,12 +1,17 @@ +-- initialize API interface local api = {} -api.SHORT_CYCLE = 0.03 -- for particles and fast animations -api.DEFAULT_CYCLE = 0.1 -- for most effect types -api.MEDIUM_CYCLE = 2.0 -- for ressource intensive tasks -api.LONG_CYCLE = 5.0 -- for write operations and skybox changes +-- define various standard effect cycle lengths +api.SHORT_CYCLE = 0 -- for particles and fast animations (use GSCYCLE) +api.DEFAULT_CYCLE = 0.1 -- for most effect types +api.MEDIUM_CYCLE = 2.0 -- for ressource intensive tasks +api.LONG_CYCLE = 5.0 -- for write operations and skybox changes +-- register new weather presets (like rain) +-- @param name Unique preset name, ideally prefixed +-- @param conditions
A collection of required influences +-- @param effects
A
containing all applied effects as keys and parameters as values function api.register_weather(name, conditions, effects) - -- TODO: check and sanitize climate_mod.weathers[name] = { conditions = conditions, effects = effects, @@ -14,6 +19,10 @@ function api.register_weather(name, conditions, effects) } end +-- register new weather effects (like particles) +-- @param name Unique effect name, ideally prefixed +-- @param handler A function to be called when the effect is active +-- @param htype Determines when the function is called function api.register_effect(name, handler, htype) -- check for valid handler types if htype ~= "start" and htype ~= "tick" and htype ~= "stop" then @@ -29,18 +38,32 @@ function api.register_effect(name, handler, htype) table.insert(climate_mod.effects[name][htype], handler) end +-- set cycle length of given effect +-- @param name Name of the affected effect +-- @param cycle Duration between function calls function api.set_effect_cycle(name, cycle) climate_mod.cycles[name].timespan = cycle end +-- register new environment influence that is independent of position +-- @param name Unique influence name +-- @param func Returns current influence value for entire world function api.register_global_influence(name, func) climate_mod.global_influences[name] = func end +-- register new environment influence based on position +-- @param name Unique influence name +-- @param func Returns current influence value for given position function api.register_influence(name, func) climate_mod.influences[name] = func end +-- register new Active Block Modifier dependent on weather status +-- Uses same config as Minetest.register_abm() but also adds +-- conditions similiar to weather presets and provides local environment +-- to action event handler as third parameter. +-- @param config
ABM configuration with additional information function api.register_abm(config) if not climate_mod.settings.block_updates then return end @@ -48,16 +71,21 @@ function api.register_abm(config) local action = config.action local pos_override = config.pos_override + -- override action handler to inject weather status local override = function(pos, node) - local env = climate_mod.trigger.get_position_environment(pos) if type(pos_override) == "function" then pos = pos_override(pos) + node = minetest.get_node(pos) end + -- get environment influences for current position + local env = climate_mod.trigger.get_position_environment(pos) + if conditions == nil then return action(pos, node, env) end + -- check if all conditions are met for condition, goal in pairs(conditions) do local is_applicable = climate_mod.trigger.test_condition(condition, env, goal) if not is_applicable then return end @@ -65,9 +93,11 @@ function api.register_abm(config) return action(pos, node, env) end + -- register overridden abm setup config.conditions = nil config.action = override minetest.register_abm(config) end +-- return supplied API endpoint return api diff --git a/lib/commands.lua b/lib/commands.lua index c8f80ad..c832944 100644 --- a/lib/commands.lua +++ b/lib/commands.lua @@ -1,3 +1,5 @@ +-- parse heat values into readable format +-- also convert to Celsius if configured local function parse_heat(heat) local indicator = "°F" if not climate_mod.settings.fahrenheit then @@ -8,11 +10,14 @@ local function parse_heat(heat) return heat .. indicator end + +-- register weather privilege in order to modify the weather status minetest.register_privilege("weather", { description = "Make changes to the current weather", give_to_singleplayer = false }) +-- display general information on current weather minetest.register_chatcommand("weather", { description ="Display weather information", func = function(playername) @@ -49,6 +54,7 @@ minetest.register_chatcommand("weather", { end }) +-- set base heat to increase or decrease global climate temperatures minetest.register_chatcommand("set_heat", { params = "", description = "Override the weather algorithm's base heat", @@ -63,6 +69,7 @@ minetest.register_chatcommand("set_heat", { end }) +-- set base heat to increase or decrease global climate humidity minetest.register_chatcommand("set_humidity", { params = "", description = "Override the weather algorithm's base humidity", @@ -77,6 +84,7 @@ minetest.register_chatcommand("set_humidity", { end }) +-- override wind direction and speed with given values minetest.register_chatcommand("set_wind", { params = "", description = "Override the weather algorithm's windspeed", @@ -103,6 +111,7 @@ minetest.register_chatcommand("set_wind", { end }) +-- display current mod config minetest.register_chatcommand("weather_settings", { description = "Print the active Climate API configuration", func = function(playername) @@ -113,6 +122,7 @@ minetest.register_chatcommand("weather_settings", { end }) +-- force a weather preset or disable it minetest.register_chatcommand("set_weather", { params =" ", description ="Turn the specified weather preset on or off for all players or reset it to automatic", @@ -141,6 +151,7 @@ minetest.register_chatcommand("set_weather", { end }) +-- list all weather presets and whether they have been forced or disabled minetest.register_chatcommand("weather_status", { description = "Prints which weather presets are enforced or disabled", func = function(playername) @@ -157,6 +168,7 @@ minetest.register_chatcommand("weather_status", { end }) +-- show all environment influences and their values for the executing player minetest.register_chatcommand("weather_influences", { description = "Prints which weather influences cause your current weather", func = function(playername) diff --git a/lib/datastorage.lua b/lib/datastorage.lua index 9571b48..6d5fdd1 100644 --- a/lib/datastorage.lua +++ b/lib/datastorage.lua @@ -7,7 +7,7 @@ if not state:contains("noise_timer") then humidity_base = 50, wind_x = 0.5, wind_z = 0.5, - noise_timer = math.random(0, 300000) + noise_timer = 0 }) end diff --git a/lib/main.lua b/lib/main.lua index a2cf65c..2cc834a 100644 --- a/lib/main.lua +++ b/lib/main.lua @@ -1,5 +1,5 @@ -local GSCYCLE = 0.03 * climate_mod.settings.tick_speed -local WORLD_CYCLE = 2 * climate_mod.settings.tick_speed +local GSCYCLE = 0.03 * climate_mod.settings.tick_speed -- only process event loop after this time amount +local WORLD_CYCLE = 15.00 * climate_mod.settings.tick_speed -- only update global environment influences after this time amount local gs_timer = 0 local world_timer = 0 diff --git a/lib/trigger.lua b/lib/trigger.lua index 31cd6a5..67eca59 100644 --- a/lib/trigger.lua +++ b/lib/trigger.lua @@ -122,7 +122,6 @@ function trigger.call_handlers(name, effect, prev_effect) has_ticks = true ticks.current[player] = sources ticks.prev[player] = prev_effect[player] - --prev_effect[player] = nil -- remove any found entries else has_starts = true starts[player] = sources