diff --git a/README.md b/README.md index 3fba36c..8eee2fd 100644 --- a/README.md +++ b/README.md @@ -22,5 +22,7 @@ Based on Immersive Sounds .36 mod by Neuromancer and optimized to run on servers - 1.7 - Music will play every 20-30 minutes if found, use '/mvol 0' to stop playing music or disable in-game. - 1.8 - Players can set induvidual volume for sound and music which is saved. - 1.9 - Tidy code, refactor music playing, add biome name to sound_check. +- 2.0 - Add Mineclone support, add ethereal leaf check, remove minetest.after for custom timer, add Polish translation, tweak & tidy code. +- 2.1 - Add ambience.group_total() function for easy counting of group: nodes inside a set. Code license: MIT diff --git a/api.txt b/api.txt index 3233a02..d682f47 100644 --- a/api.txt +++ b/api.txt @@ -43,14 +43,22 @@ ambience.add_set("windy", { {name = "crow", length = 3, ephemeral = true}, }, sound_check = function(def) - local number = totals["default:sand"] or 0 -- yep, can also be nil + local number = def.totals["default:sand"] or 0 -- yep, can also be nil if number > 20 then return "windy", 0.2 -- return set to play and optional gain volume end - end, + end }) +Counting group: nodes +--------------------- + +Instead of counting each node total for things like leaves within the sound_check function, you could use the following helper function to return their total instead e.g. + +local number = ambience.group_totals(def.totals, "leaves") -- count all group:leaves + + Getting Sound Set ----------------- diff --git a/init.lua b/init.lua index c3470fc..059d0bb 100644 --- a/init.lua +++ b/init.lua @@ -10,7 +10,7 @@ local MUSICVOLUME = 0.6 local MUSICINTERVAL = 60 * 20 local play_music = minetest.settings:get_bool("ambience_music") ~= false local radius = 6 -local playing = {} +local playing = {} -- user settings, timers and current set playing local sound_sets = {} -- all the sounds and their settings local sound_set_order = {} -- needed because pairs loops randomly through tables local set_nodes = {} -- all the nodes needed for sets @@ -21,7 +21,7 @@ local S = minetest.get_translator("ambience") -- add set to list -ambience.add_set = function(set_name, def) +function ambience.add_set(set_name, def) if not set_name or not def then return end @@ -61,13 +61,13 @@ end -- return set from list using name -ambience.get_set = function(set_name) +function ambience.get_set(set_name) return sound_sets[set_name] end -- remove set from list -ambience.del_set = function(set_name) +function ambience.del_set(set_name) sound_sets[set_name] = nil @@ -81,6 +81,26 @@ ambience.del_set = function(set_name) if can_del then table.remove(sound_set_order, can_del) end end +-- return node total belonging to a specific group: + +function ambience.group_total(ntab, ngrp) + + local tot = 0 + local def, grp + + for _,n in pairs(ntab) do + + def = minetest.registered_nodes[_] + grp = def and def.groups and def.groups[ngrp] + + if grp and grp > 0 then + tot = tot + n + end + end + + return tot +end + -- setup table when player joins minetest.register_on_joinplayer(function(player) @@ -93,9 +113,9 @@ minetest.register_on_joinplayer(function(player) playing[name] = { mvol = tonumber(meta:get_string("ambience.mvol")) or MUSICVOLUME, svol = tonumber(meta:get_string("ambience.svol")) or SOUNDVOLUME, + timer = 0, music = 0, - music_handler = nil, - timer = 0 + music_handler = nil } end end) @@ -109,7 +129,7 @@ end) -- plays music and selects sound set -local get_ambience = function(player, tod, name) +local function get_ambience(player, tod, name) -- if enabled and not already playing, play local/server music on interval check if play_music and playing[name] and playing[name].mvol > 0 then @@ -161,7 +181,7 @@ local get_ambience = function(player, tod, name) local bdata = minetest.get_biome_data(pos) local biome = bdata and minetest.get_biome_name(bdata.biome) or "" - -- pass settings to function for condition check + -- pass settings to set function for condition check local set_name, gain = set.sound_check({ player = player, pos = pos, @@ -188,10 +208,11 @@ local random = math.random minetest.register_globalstep(function(dtime) + local players = minetest.get_connected_players() local pname -- reduce sound timer for each player and stop/reset when needed - for _, player in pairs(minetest.get_connected_players()) do + for _, player in pairs(players) do pname = player:get_player_name() @@ -219,7 +240,7 @@ minetest.register_globalstep(function(dtime) local tod = minetest.get_timeofday() -- loop through players - for _, player in pairs(minetest.get_connected_players()) do + for _, player in pairs(players) do pname = player:get_player_name() @@ -266,12 +287,9 @@ minetest.register_globalstep(function(dtime) --print ("playing... " .. ambience.name .. " (" .. chance .. " < " -- .. sound_sets[set_name].frequency .. ") @ ", MORE_GAIN, handler) - -- only continue if sound playing returns handler if handler then ---print("-- current handler", handler) - - -- set what player is currently listening to + -- set what player is currently listening to if handler found playing[pname].set = set_name playing[pname].gain = MORE_GAIN playing[pname].handler = handler diff --git a/soundsets.lua b/soundsets.lua index 3d7d32c..1262ba2 100644 --- a/soundsets.lua +++ b/soundsets.lua @@ -76,75 +76,74 @@ end -- check for env_sounds mod, if not found enable water flowing and lava sounds if not minetest.get_modpath("env_sounds") then --- Water sound plays when near flowing water + -- Water sound plays when near flowing water -ambience.add_set("flowing_water", { + ambience.add_set("flowing_water", { - frequency = 1000, + frequency = 1000, - sounds = { - {name = "waterfall", length = 6} - }, + sounds = { + {name = "waterfall", length = 6} + }, - nodes = {"group:water"}, + nodes = {"group:water"}, - sound_check = function(def) + sound_check = function(def) - local c = (def.totals["default:water_flowing"] or 0) - + (def.totals["mcl_core:water_flowing"] or 0) + local c = (def.totals["default:water_flowing"] or 0) + + (def.totals["mcl_core:water_flowing"] or 0) - if c > 40 then return "flowing_water", 0.5 + if c > 40 then return "flowing_water", 0.5 - elseif c > 5 then return "flowing_water" end - end -}) + elseif c > 5 then return "flowing_water" end + end + }) --- River sound plays when near flowing river + -- River sound plays when near flowing river -ambience.add_set("river", { + ambience.add_set("river", { - frequency = 1000, + frequency = 1000, - sounds = { - {name = "river", length = 4, gain = 0.1} - }, + sounds = { + {name = "river", length = 4, gain = 0.1} + }, - sound_check = function(def) + sound_check = function(def) - local c = (def.totals["default:river_water_flowing"] or 0) - + (def.totals["mclx_core:river_water_flowing"] or 0) + local c = (def.totals["default:river_water_flowing"] or 0) + + (def.totals["mclx_core:river_water_flowing"] or 0) - if c > 20 then return "river", 0.5 + if c > 20 then return "river", 0.5 - elseif c > 5 then return "river" end - end -}) + elseif c > 5 then return "river" end + end + }) --- Lava sound plays when near lava + -- Lava sound plays when near lava -ambience.add_set("lava", { + ambience.add_set("lava", { - frequency = 1000, + frequency = 1000, - sounds = { - {name = "lava", length = 7} - }, + sounds = { + {name = "lava", length = 7} + }, - nodes = {"group:lava"}, + nodes = {"group:lava"}, - sound_check = function(def) + sound_check = function(def) - local c = (def.totals["default:lava_source"] or 0) - + (def.totals["default:lava_flowing"] or 0) - + (def.totals["mcl_core:lava_source"] or 0) - + (def.totals["mcl_core:lava_flowing"] or 0) + local c = (def.totals["default:lava_source"] or 0) + + (def.totals["default:lava_flowing"] or 0) + + (def.totals["mcl_core:lava_source"] or 0) + + (def.totals["mcl_core:lava_flowing"] or 0) - if c > 20 then return "lava", 0.5 - - elseif c > 5 then return "lava" end - end -}) + if c > 20 then return "lava", 0.5 + elseif c > 5 then return "lava" end + end + }) else print ("[MOD] Ambience - found env_sounds, using for water and lava sounds.") end @@ -324,22 +323,8 @@ ambience.add_set("day", { sound_check = function(def) - -- we used group:leaves but still need to specify actual nodes for total - local c = (def.totals["default:leaves"] or 0) - + (def.totals["default:bush_leaves"] or 0) - + (def.totals["default:pine_needles"] or 0) - + (def.totals["default:aspen_leaves"] or 0) - + (def.totals["mcl_trees:leaves_spruce"] or 0) - + (def.totals["mcl_trees:leaves_oak"] or 0) - + (def.totals["mcl_trees:leaves_mangrove"] or 0) - + (def.totals["mcl_trees:leaves_birch"] or 0) - + (def.totals["mcl_trees:leaves_acacia"] or 0) - + (def.totals["ethereal:birch_leaves"] or 0) - + (def.totals["ethereal:lemon_leaves"] or 0) - + (def.totals["ethereal:olive_leaves"] or 0) - + (def.totals["ethereal:redwood_leaves"] or 0) - + (def.totals["ethereal:sakura_leaves"] or 0) - + (def.totals["ethereal:sakura_leaves2"] or 0) + -- use handy function to count all nodes in group:leaves + local c = ambience.group_total(def.totals, "leaves") if (def.tod > 0.2 and def.tod < 0.8) and def.pos.y > -10 and c > 5 then return "day" @@ -365,22 +350,8 @@ ambience.add_set("night", { sound_check = function(def) - -- leaves were added in last set, so don't need to be added to this one - local c = (def.totals["default:leaves"] or 0) - + (def.totals["default:bush_leaves"] or 0) - + (def.totals["default:pine_needles"] or 0) - + (def.totals["default:aspen_leaves"] or 0) - + (def.totals["mcl_trees:leaves_spruce"] or 0) - + (def.totals["mcl_trees:leaves_oak"] or 0) - + (def.totals["mcl_trees:leaves_mangrove"] or 0) - + (def.totals["mcl_trees:leaves_birch"] or 0) - + (def.totals["mcl_trees:leaves_acacia"] or 0) - + (def.totals["ethereal:birch_leaves"] or 0) - + (def.totals["ethereal:lemon_leaves"] or 0) - + (def.totals["ethereal:olive_leaves"] or 0) - + (def.totals["ethereal:redwood_leaves"] or 0) - + (def.totals["ethereal:sakura_leaves"] or 0) - + (def.totals["ethereal:sakura_leaves2"] or 0) + -- use handy function to count all nodes in group:leaves + local c = ambience.group_total(def.totals, "leaves") if (def.tod < 0.2 or def.tod > 0.8) and def.pos.y > -10 and c > 5 then return "night"