It works like this, but it looks like I have some other mod that also adds radiation damage, since I took a full stack of uranium, and it instantly killed me, maybe I should reduce the modifiers a little, although on the other hand, it is logical that the more items with radiation, the faster the damage occurs. But I didn't even try to throw it out of my inventory :)
-- = Radiation Settings =
local RADIATION_RADIUS = 4
local INVENTORY_DAMAGE_PER_ITEM = 0.5
local EXTERIOR_DAMAGE = 0.1
Radioactive_Items = {
["uranium-235"] = 0.5,
["uranium-238"] = 0.3,
["uranium-fuel-cell"] = 1,
["depleted-uranium-fuel-cell"] = 0.4,
["uranium-ore"] = 0.1,
["uranium-concentrate"] = 0.2,
}
-- = End Radiation Settings =
remote.add_interface("TibsRadiationMod", {
insert_radioactive_item = function(item, value)
Radioactive_Items[item] = value
end,
remove_radioactive_item = function(item)
Radioactive_Items[item] = nil
end
})
last_radiation_sound_tick = last_radiation_sound_tick or {}
function play_radiation_sound(player)
local now = game.tick
local cooldown = 60 * 5
local last_tick = last_radiation_sound_tick[player.index] or 0
if now - last_tick >= cooldown then
game.play_sound{
path = "Radiation",
volume_modifier = 1.0,
position = player.position
}
last_radiation_sound_tick[player.index] = now
end
end
script.on_event(defines.events.on_tick, function(event)
for _, player in pairs(game.connected_players) do
if not (player.character and player.valid and player.surface) then goto continue end
local surface = player.surface
local pos = player.position
local inventory = player.get_main_inventory()
-- 1. Inventory Radiation
local InventoryDamage = 0
if inventory then
for name, dmg_per_unit in pairs(Radioactive_Items) do
if prototypes and prototypes.item and prototypes.item[name] then
local count = inventory.get_item_count(name)
InventoryDamage = InventoryDamage + (count * dmg_per_unit * INVENTORY_DAMAGE_PER_ITEM)
end
end
end
-- 2. Radiation from Uranium ore patches!
local ResourceDamage = 0
local resource_entities = surface.find_entities_filtered{
area = {
{pos.x - RADIATION_RADIUS, pos.y - RADIATION_RADIUS},
{pos.x + RADIATION_RADIUS, pos.y + RADIATION_RADIUS}
},
type = "resource"
}
for _, resource in pairs(resource_entities) do
local item_name = resource.name
local intensity = Radioactive_Items[item_name]
if intensity then
local distance = math.sqrt((resource.position.x - pos.x)^2 + (resource.position.y - pos.y)^2)
if distance <= RADIATION_RADIUS then
ResourceDamage = ResourceDamage + intensity * EXTERIOR_DAMAGE * (1 - (distance / RADIATION_RADIUS))
end
end
end
-- 3. Radiation from items on nearby belts
local BeltDamage = 0
local belt_entities = surface.find_entities_filtered{
area = {
{pos.x - RADIATION_RADIUS, pos.y - RADIATION_RADIUS},
{pos.x + RADIATION_RADIUS, pos.y + RADIATION_RADIUS}
},
type = {
"transport-belt", "fast-transport-belt", "express-transport-belt",
"express-splitter", "fast-splitter", "splitter"
}
}
for _, belt in pairs(belt_entities) do
for i = 1, belt.get_max_transport_line_index() do
local line = belt.get_transport_line(i)
local contents = line.get_contents()
for item_name, count in pairs(contents) do
local intensity = Radioactive_Items[item_name]
if intensity and count > 0 then
local distance = math.sqrt((belt.position.x - pos.x)^2 + (belt.position.y - pos.y)^2)
if distance <= RADIATION_RADIUS then
BeltDamage = BeltDamage + intensity * EXTERIOR_DAMAGE * count * (1 - (distance / RADIATION_RADIUS))
end
end
end
end
end
-- 4. Radiation from dropped items on the ground
local GroundDamage = 0
local ground_items = surface.find_entities_filtered{
area = {
{pos.x - RADIATION_RADIUS, pos.y - RADIATION_RADIUS},
{pos.x + RADIATION_RADIUS, pos.y + RADIATION_RADIUS}
},
type = "item-entity"
}
for _, entity in pairs(ground_items) do
if entity.valid and entity.stack and entity.stack.valid_for_read then
local item_name = entity.stack.name
local count = entity.stack.count
local intensity = Radioactive_Items[item_name]
if intensity then
local distance = math.sqrt((entity.position.x - pos.x)^2 + (entity.position.y - pos.y)^2)
if distance <= RADIATION_RADIUS then
GroundDamage = GroundDamage + intensity * EXTERIOR_DAMAGE * count * (1 - (distance / RADIATION_RADIUS))
end
end
end
end
local total_damage = InventoryDamage + BeltDamage + GroundDamage + ResourceDamage
if total_damage > 0 and player.character then
player.character.damage(total_damage, "neutral", "poison")
play_radiation_sound(player)
end
::continue::
end
end)