1
1
require " config"
2
2
3
- local mod_version = " 0.12 .0"
4
- local mod_data_version = " 0.12 .0"
3
+ local mod_version = " 0.13 .0"
4
+ local mod_data_version = " 0.13 .0"
5
5
6
6
local termbelts = {}
7
7
local curvebelts = {}
@@ -13,7 +13,7 @@ local polling_cycles = math.floor(60/belt_polling_rate)
13
13
local polling_remainder = math.random (polling_cycles )- 1
14
14
15
15
-- local function debug(...)
16
- -- if game.players[1] then
16
+ -- if game and game .players[1] then
17
17
-- game.players[1].print(...)
18
18
-- end
19
19
-- end
@@ -60,20 +60,11 @@ local function rotate_pos(x,y,rotation)
60
60
return rotate_posd ({x ,y ,0 },rotation )
61
61
end
62
62
63
- local belt_speeds = {basic = 1 ,fast = 2 ,express = 3 ,faster = 4 ,purple = 5 }
64
-
65
- local function beltspeedword (name )
66
- local m = string.match (name ," ^(.*)%-transport%-belt" )
67
- if not m then m = string.match (name ," ^(.*)%-transport%-belt%-to%-ground" ) end
68
- if not m then m = string.match (name ," ^(.*)%-splitter" ) end
69
- return m
70
- end
71
-
72
63
local function terminal_belt_lines (args )
73
64
local entity = args .entity
74
65
local entity_to_ignore = args .entity_to_ignore
75
66
if entity == entity_to_ignore then return {} end
76
- if entity .type == " transport -belt-to-ground " and
67
+ if entity .type == " underground -belt" and
77
68
entity .belt_to_ground_type == " input" then
78
69
if # entity .neighbours > 0 and entity .neighbours [1 ] ~= entity_to_ignore then
79
70
return {}
@@ -92,7 +83,7 @@ local function terminal_belt_lines(args)
92
83
{pos = {pos .x + dx ,pos .y + dy },lines = {5 ,6 }},
93
84
{pos = {pos .x - dx ,pos .y - dy },lines = {7 ,8 }}
94
85
}
95
- elseif entity .type == " transport -belt-to-ground " and
86
+ elseif entity .type == " underground -belt" and
96
87
entity .belt_to_ground_type == " input" then
97
88
to_check = {{pos = pos ,lines = {3 ,4 }}}
98
89
else
@@ -111,12 +102,12 @@ local function terminal_belt_lines(args)
111
102
local dx ,dy = rotate_pos (0 ,- 1 ,dir )
112
103
local tpos = {check .pos [1 ]+ dx ,check .pos [2 ]+ dy }
113
104
-- debug("tpos "..pos2s(tpos))
114
- local entities = game . get_surface ( entity .surface . index ) .find_entities ({tpos ,tpos })
105
+ local candidates = entity .surface .find_entities ({tpos ,tpos })
115
106
local target = nil
116
- for _ ,candidate in pairs (entities ) do
107
+ for _ ,candidate in pairs (candidates ) do
117
108
if candidate ~= entity_to_ignore then
118
109
if candidate .type == " transport-belt" or
119
- candidate .type == " transport -belt-to-ground " or
110
+ candidate .type == " underground -belt" or
120
111
candidate .type == " splitter" then
121
112
target = candidate
122
113
break
@@ -125,19 +116,14 @@ local function terminal_belt_lines(args)
125
116
end
126
117
if target then
127
118
-- debug("target found "..target.type)
128
- -- any feed into a slower belt can be terminal
129
- local bsw1 = beltspeedword (entity .name )
130
- local bsw2 = beltspeedword (target .name )
131
- if bsw1 ~= bsw2 then -- different speeds
132
- if (not belt_speeds [bsw1 ]) or (not belt_speeds [bsw2 ]) or -- unknown speed(s)
133
- belt_speeds [bsw1 ]> belt_speeds [bsw2 ] then -- slower
134
- result (check .lines )
135
- end
119
+ -- fast belts can overflow onto slow belts
120
+ if entity .prototype .belt_speed > target .prototype .belt_speed then
121
+ result (check .lines )
136
122
-- nothing accepts connections from the front
137
123
elseif math.abs (target .direction - dir )== 4 then
138
124
result (check .lines )
139
125
-- underground belt outputs don't accept connections from behind
140
- elseif target .type == " transport -belt-to-ground " and
126
+ elseif target .type == " underground -belt" and
141
127
target .belt_to_ground_type == " output" and
142
128
target .direction == dir then
143
129
result (check .lines )
@@ -160,12 +146,12 @@ local function terminal_belt_lines(args)
160
146
}
161
147
for _ ,bpos in pairs (bpd ) do
162
148
-- debug("checking for belt-behind at "..pos2s(bpos.pos).." dir="..bpos.dir)
163
- local entities = game . get_surface ( entity .surface . index ) .find_entities ({bpos .pos ,bpos .pos })
164
- for _ ,candidate in pairs (entities ) do
149
+ local candidates = entity .surface .find_entities ({bpos .pos ,bpos .pos })
150
+ for _ ,candidate in pairs (candidates ) do
165
151
if candidate ~= entity_to_ignore then
166
152
-- debug("candidate "..candidate.type.." ".."dir="..candidate.direction)
167
153
if candidate .type == " transport-belt" or
168
- candidate .type == " transport -belt-to-ground " or
154
+ candidate .type == " underground -belt" or
169
155
candidate .type == " splitter" then
170
156
if candidate .direction == bpos .dir then
171
157
belt_behind_target = true
@@ -191,16 +177,18 @@ local function terminal_belt_lines(args)
191
177
result (check .lines )
192
178
end
193
179
end
194
- -- splitters can't be half-terminal
195
- if entity .type == " splitter" and # result_lines < 4 then return {} end
180
+ -- splitters can't be just half-terminal
181
+ if entity .type == " splitter" and # result_lines > 0 then return {5 , 6 , 7 , 8 } end
196
182
return result_lines
197
183
end
198
184
return {}
199
185
end
200
186
201
187
local function cleartermbelt (x ,y )
188
+ -- debug("clearing "..x..","..y)
202
189
if termbelts [y ] and termbelts [y ][x ] then
203
190
if termbelts [y ][x ].indicator then
191
+ -- debug("and your little dog, too")
204
192
termbelts [y ][x ].indicator .destroy ()
205
193
end
206
194
termbelts [y ][x ] = nil
@@ -213,7 +201,7 @@ local function onTick(event)
213
201
if event .tick % polling_cycles == polling_remainder then
214
202
for y ,row in pairs (termbelts ) do
215
203
for x ,belt in pairs (row ) do
216
- -- debug(x..','..y)
204
+ -- -- debug(x..','..y)
217
205
if not belt .entity or not belt .entity .valid then
218
206
cleartermbelt (x ,y )
219
207
else
@@ -228,28 +216,28 @@ local function onTick(event)
228
216
else
229
217
caps = line_caps .straight
230
218
end
231
- elseif e .type == " transport -belt-to-ground " then
219
+ elseif e .type == " underground -belt" then
232
220
caps = line_caps .ground
233
221
elseif e .type == " splitter" then
234
222
caps = line_caps .splitter
235
223
end
236
224
local ground_prefill = {}
237
225
for i = 1 ,# belt .lines do
238
226
local line = belt .lines [i ]
239
- -- debug(pos2s(pos)..' line '..line..':')
227
+ -- -- debug(pos2s(pos)..' line '..line..':')
240
228
local tl = e .get_transport_line (line )
241
229
local item_name
242
230
if tl .get_item_count ()>= caps [line ] then
243
231
for name ,count in pairs (tl .get_contents ()) do
244
232
-- debug(line..' '..name..' '..count)
245
233
item_name = name
246
234
end
247
- if e .type == " transport -belt-to-ground " and
235
+ if e .type == " underground -belt" and
248
236
e .belt_to_ground_type == " input" and
249
237
line < 3 then
250
238
-- track this for future reference, but don't overflow here
251
239
ground_prefill [line ]= true
252
- elseif e .type == " transport -belt-to-ground " and
240
+ elseif e .type == " underground -belt" and
253
241
e .belt_to_ground_type == " input" and
254
242
line > 2 and not ground_prefill [line - 2 ] then
255
243
-- do nothing, this won't overflow until the prior line overflows
@@ -260,7 +248,7 @@ local function onTick(event)
260
248
local x ,y = pos .x ,pos .y
261
249
local dir = e .direction
262
250
local dx ,dy = 0 ,0
263
- if e .type == " transport -belt-to-ground " and e .belt_to_ground_type == " input" then
251
+ if e .type == " underground -belt" and e .belt_to_ground_type == " input" then
264
252
-- spill beside the underground input
265
253
dy = dy + 0.25
266
254
if (line % 2 )== 0 then
@@ -351,14 +339,16 @@ end
351
339
352
340
local function check_and_update_posd (posd ,surface ,entity_to_ignore )
353
341
local box = {{posd [1 ]- 0.5 ,posd [2 ]- 0.5 },{posd [1 ]+ 0.5 ,posd [2 ]+ 0.5 }}
354
- local entities = surface .find_entities (box )
355
- for _ ,candidate in pairs (entities ) do
356
- if candidate .type == " transport-belt" or
357
- candidate .type == " transport-belt-to-ground" or
358
- candidate .type == " splitter" then
359
- if candidate .direction == posd [3 ] then
360
- if candidate ~= entity_to_ignore then
361
- check_and_update_entity {entity = candidate ,entity_to_ignore = entity_to_ignore }
342
+ local candidates = surface .find_entities (box )
343
+ for _ ,candidate in pairs (candidates ) do
344
+ if candidate .valid then
345
+ if candidate .type == " transport-belt" or
346
+ candidate .type == " underground-belt" or
347
+ candidate .type == " splitter" then
348
+ if candidate .direction == posd [3 ] then
349
+ if candidate ~= entity_to_ignore then
350
+ check_and_update_entity {entity = candidate ,entity_to_ignore = entity_to_ignore }
351
+ end
362
352
end
363
353
end
364
354
end
@@ -377,7 +367,7 @@ local function check_and_update_neighborhood(args)
377
367
{- 1 ,- 1 ,2 },{1 ,- 1 ,6 }, -- ahead and left/right can change if they point at the same belt as this does
378
368
{0 ,- 2 ,4 } -- and so can two-ahead
379
369
}
380
- elseif entity .type == " transport -belt-to-ground " then
370
+ elseif entity .type == " underground -belt" then
381
371
if entity .belt_to_ground_type == " input" then
382
372
hood = {{0 ,0 ,0 }} -- no neighbors can change for an underground input
383
373
else
@@ -406,13 +396,14 @@ local function check_and_update_neighborhood(args)
406
396
check_and_update_posd ({entity .position .x + posd [1 ],entity .position .y + posd [2 ],posd [3 ]},entity .surface ,removal and entity or nil )
407
397
end
408
398
end
399
+ if removal then cleartermbelt (entity .position .x ,entity .position .y ) end
409
400
end
410
401
411
402
local function onModifyEntity (args )
412
403
local entity = args .entity
413
404
local removal = args .removal
414
405
if entity .type == " transport-belt" or
415
- entity .type == " transport -belt-to-ground " or
406
+ entity .type == " underground -belt" or
416
407
entity .type == " splitter" then
417
408
check_and_update_neighborhood {entity = entity ,removal = removal }
418
409
end
@@ -444,19 +435,26 @@ local function find_all_entities(args)
444
435
end
445
436
446
437
local function refreshData ()
438
+ -- forget all previously found terminal belts
447
439
if global .terminal_belts then
448
440
for y ,row in pairs (global .terminal_belts ) do
449
441
for x ,belt in pairs (row ) do
450
- -- debug('refreshData clear '..x..','..y)
451
442
cleartermbelt (x ,y )
452
443
end
453
444
end
454
445
end
446
+ -- destroy any remaining indicators
447
+ for _ ,name in pairs ({" belt-overflow-indicator" ," belt-overflow-indicator-wide" ," belt-overflow-indicator-tall" }) do
448
+ for _ ,e in pairs (find_all_entities {name = name }) do
449
+ e .destroy ()
450
+ end
451
+ end
455
452
global .terminal_belts = {}
456
453
global .curve_belts = {}
457
454
curvebelts = global .curve_belts
458
455
termbelts = global .terminal_belts
459
- for _ ,type in pairs ({" transport-belt" ," transport-belt-to-ground" ," splitter" }) do
456
+ -- find all terminal belts
457
+ for _ ,type in pairs ({" transport-belt" ," underground-belt" ," splitter" }) do
460
458
for _ ,e in pairs (find_all_entities {type = type }) do
461
459
check_and_update_entity {entity = e }
462
460
end
@@ -478,16 +476,19 @@ local function updateIndicators(old_draw_terminal_indicator, new_draw_terminal_i
478
476
if global .terminal_belts then
479
477
if old_draw_terminal_indicator ~= new_draw_terminal_indicator then
480
478
if new_draw_terminal_indicator then
481
- -- add indicators to existing termbelts
479
+ -- add indicators to existing termbelts without them
482
480
for y ,row in pairs (global .terminal_belts ) do
483
481
for x ,belt in pairs (row ) do
484
- belt .indicator = create_indicator (belt .entity )
482
+ if (belt .indicator and not belt .indicator .valid ) or not belt .indicator then
483
+ belt .indicator = create_indicator (belt .entity )
484
+ end
485
485
end
486
486
end
487
487
else
488
488
-- remove existing indicators
489
489
for y ,row in pairs (global .terminal_belts ) do
490
490
for x ,belt in pairs (row ) do
491
+ if belt .indicator .valid then belt .indicator .destroy () end
491
492
belt .indicator = nil
492
493
end
493
494
end
@@ -496,32 +497,27 @@ local function updateIndicators(old_draw_terminal_indicator, new_draw_terminal_i
496
497
end
497
498
end
498
499
499
- local function onLoad ()
500
- -- The only reason to have version/data_version is to trigger migrations, so do that here.
501
- checkForMigration (global .version , mod_version )
502
- checkForDataMigration (global .data_version , mod_data_version )
503
- updateIndicators (global .draw_terminal_indicator , draw_terminal_indicator )
504
-
505
- -- After these lines, we can no longer check for migration.
500
+ local function onInit ()
506
501
global .version = mod_version
507
502
global .data_version = mod_data_version
508
503
global .draw_terminal_indicator = draw_terminal_indicator
509
504
510
505
if global .terminal_belts == nil then
511
506
refreshData ()
512
507
end
508
+ end
513
509
514
- -- for y,row in pairs(termbelts) do
515
- -- for x,belt in pairs(row) do
516
- -- -- debug(x..','..y )
517
- -- end
518
- -- end
510
+ local function onConfigurationChanged ()
511
+ -- The only reason to have version/data_version is to trigger migrations, so do that here.
512
+ checkForMigration ( global . version , mod_version )
513
+ checkForDataMigration ( global . data_version , mod_data_version )
514
+ updateIndicators ( global . draw_terminal_indicator , draw_terminal_indicator )
519
515
516
+ onInit ()
520
517
end
521
518
522
- script .on_init (onLoad )
523
- script .on_configuration_changed (onLoad )
524
- -- script.on_load(onLoad)
519
+ script .on_init (onInit )
520
+ script .on_configuration_changed (onConfigurationChanged )
525
521
526
522
script .on_event (defines .events .on_built_entity , onPlaceEntity )
527
523
script .on_event (defines .events .on_robot_built_entity , onPlaceEntity )
@@ -533,3 +529,7 @@ script.on_event(defines.events.on_robot_pre_mined, onRemoveEntity)
533
529
script .on_event (defines .events .on_entity_died , onRemoveEntity )
534
530
535
531
script .on_event (defines .events .on_tick , onTick )
532
+
533
+ remote .add_interface (" belt-overflow" ,
534
+ {refreshData = refreshData }
535
+ )
0 commit comments