mirror of
https://github.com/BlackMATov/evolved.lua.git
synced 2026-01-11 02:39:42 +07:00
Compare commits
4 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
c29092c3e1 | ||
|
|
a0a4a20c35 | ||
|
|
2f8b0b0ef3 | ||
|
|
5e0170b4e8 |
@@ -1,6 +1,6 @@
|
||||
MIT License
|
||||
|
||||
Copyright (C) 2024-2025, by Matvey Cherevko (blackmatov@gmail.com)
|
||||
Copyright (C) 2024-2026, by Matvey Cherevko (blackmatov@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
|
||||
64
README.md
64
README.md
@@ -43,6 +43,7 @@
|
||||
- [Deferred Operations](#deferred-operations)
|
||||
- [Batch Operations](#batch-operations)
|
||||
- [Systems](#systems)
|
||||
- [Processing Payloads](#processing-payloads)
|
||||
- [Predefined Traits](#predefined-traits)
|
||||
- [Fragment Tags](#fragment-tags)
|
||||
- [Fragment Hooks](#fragment-hooks)
|
||||
@@ -60,6 +61,7 @@
|
||||
- [Chunk](#chunk)
|
||||
- [Builder](#builder)
|
||||
- [Changelog](#changelog)
|
||||
- [vX.Y.Z](#vxyz)
|
||||
- [v1.6.0](#v160)
|
||||
- [v1.5.0](#v150)
|
||||
- [v1.4.0](#v140)
|
||||
@@ -880,6 +882,43 @@ The prologue and epilogue fragments do not require an explicit query. They will
|
||||
> [!NOTE]
|
||||
> And one more thing about systems. Execution callbacks are called in the [deferred scope](#deferred-operations), which means that all modifying operations inside the callback will be queued and applied after the system has processed all chunks. But prologue and epilogue callbacks are not called in the deferred scope, so all modifying operations inside them will be applied immediately. This is done to avoid confusion and to make it clear that prologue and epilogue callbacks are not part of the chunk processing.
|
||||
|
||||
#### Processing Payloads
|
||||
|
||||
Additionally, systems can have a payload that will be passed to the execution, prologue, and epilogue callbacks. This is useful for passing additional data to the system without using global variables or closures.
|
||||
|
||||
```lua
|
||||
---@param system evolved.system
|
||||
---@param ... any processing payload
|
||||
function evolved.process_with(system, ...) end
|
||||
```
|
||||
|
||||
The [`evolved.process_with`](#evolvedprocess_with) function is similar to the [`evolved.process`](#evolvedprocess) function, but it takes a processing payload as additional arguments. These arguments will be passed to the system's callbacks.
|
||||
|
||||
```lua
|
||||
local evolved = require 'evolved'
|
||||
|
||||
local position_x, position_y = evolved.id(2)
|
||||
local velocity_x, velocity_y = evolved.id(2)
|
||||
|
||||
local physics_system = evolved.builder()
|
||||
:include(position_x, position_y)
|
||||
:include(velocity_x, velocity_y)
|
||||
:execute(function(chunk, entity_list, entity_count, delta_time)
|
||||
local px, py = chunk:components(position_x, position_y)
|
||||
local vx, vy = chunk:components(velocity_x, velocity_y)
|
||||
|
||||
for i = 1, entity_count do
|
||||
px[i] = px[i] + vx[i] * delta_time
|
||||
py[i] = py[i] + vy[i] * delta_time
|
||||
end
|
||||
end):build()
|
||||
|
||||
local delta_time = 0.016
|
||||
evolved.process_with(physics_system, delta_time)
|
||||
```
|
||||
|
||||
`delta_time` in this example is passed as a processing payload to the system's execution callback. Payloads can be of any type and can be multiple values. Also, payloads are passed to prologue and epilogue callbacks if they are defined. Every subsystem in a group will receive the same payload when the group is processed with [`evolved.process_with`](#evolvedprocess_with).
|
||||
|
||||
### Predefined Traits
|
||||
|
||||
#### Fragment Tags
|
||||
@@ -1125,9 +1164,9 @@ storage :: component[]
|
||||
default :: component
|
||||
duplicate :: {component -> component}
|
||||
|
||||
execute :: {chunk, entity[], integer}
|
||||
prologue :: {}
|
||||
epilogue :: {}
|
||||
execute :: {chunk, entity[], integer, any...}
|
||||
prologue :: {any...}
|
||||
epilogue :: {any...}
|
||||
|
||||
set_hook :: {entity, fragment, component, component}
|
||||
assign_hook :: {entity, fragment, component, component}
|
||||
@@ -1229,6 +1268,7 @@ execute :: query -> {execute_state? -> chunk?, entity[]?, integer?}, execute_sta
|
||||
locate :: entity -> chunk?, integer
|
||||
|
||||
process :: system... -> ()
|
||||
process_with :: system, ... -> ()
|
||||
|
||||
debug_mode :: boolean -> ()
|
||||
collect_garbage :: ()
|
||||
@@ -1302,16 +1342,20 @@ builder_mt:on_remove :: {entity, fragment} -> builder
|
||||
builder_mt:group :: system -> builder
|
||||
|
||||
builder_mt:query :: query -> builder
|
||||
builder_mt:execute :: {chunk, entity[], integer} -> builder
|
||||
builder_mt:execute :: {chunk, entity[], integer, any...} -> builder
|
||||
|
||||
builder_mt:prologue :: {} -> builder
|
||||
builder_mt:epilogue :: {} -> builder
|
||||
builder_mt:prologue :: {any...} -> builder
|
||||
builder_mt:epilogue :: {any...} -> builder
|
||||
|
||||
builder_mt:destruction_policy :: id -> builder
|
||||
```
|
||||
|
||||
## Changelog
|
||||
|
||||
### vX.Y.Z
|
||||
|
||||
- Added the new [`evolved.process_with`](#evolvedprocess_with) function that allows passing payloads to processing systems
|
||||
|
||||
### v1.6.0
|
||||
|
||||
- Significant performance improvements of the [`evolved.REQUIRES`](#evolvedrequires) fragment trait
|
||||
@@ -1710,6 +1754,14 @@ function evolved.locate(entity) end
|
||||
function evolved.process(...) end
|
||||
```
|
||||
|
||||
### `evolved.process_with`
|
||||
|
||||
```lua
|
||||
---@param system evolved.system
|
||||
---@param ... any processing payload
|
||||
function evolved.process_with(system, ...) end
|
||||
```
|
||||
|
||||
### `evolved.debug_mode`
|
||||
|
||||
```lua
|
||||
|
||||
@@ -7,6 +7,7 @@ require 'develop.testing.locate_tests'
|
||||
require 'develop.testing.main_tests'
|
||||
require 'develop.testing.multi_spawn_tests'
|
||||
require 'develop.testing.name_tests'
|
||||
require 'develop.testing.process_with_tests'
|
||||
require 'develop.testing.requires_fragment_tests'
|
||||
require 'develop.testing.spawn_tests'
|
||||
require 'develop.testing.system_as_query_tests'
|
||||
|
||||
107
develop/testing/process_with_tests.lua
Normal file
107
develop/testing/process_with_tests.lua
Normal file
@@ -0,0 +1,107 @@
|
||||
local evo = require 'evolved'
|
||||
|
||||
do
|
||||
local f = evo.id()
|
||||
local e = evo.builder():set(f, 42):spawn()
|
||||
|
||||
local s = evo.builder()
|
||||
:include(f)
|
||||
:prologue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == 11 and payload2 == 22 and payload3 == 33)
|
||||
end)
|
||||
:execute(function(chunk, entity_list, entity_count, payload1, payload2, payload3)
|
||||
assert(payload1 == 11 and payload2 == 22 and payload3 == 33)
|
||||
assert(chunk == evo.chunk(f) and entity_count == 1 and entity_list[1] == e)
|
||||
end)
|
||||
:epilogue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == 11 and payload2 == 22 and payload3 == 33)
|
||||
end)
|
||||
:spawn()
|
||||
|
||||
evo.process_with(s, 11, 22, 33)
|
||||
end
|
||||
|
||||
do
|
||||
local f = evo.id()
|
||||
local e = evo.builder():set(f, 42):spawn()
|
||||
|
||||
local s = evo.builder()
|
||||
:include(f)
|
||||
:prologue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == 42 and payload3 == nil)
|
||||
end)
|
||||
:execute(function(chunk, entity_list, entity_count, payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == 42 and payload3 == nil)
|
||||
assert(chunk == evo.chunk(f) and entity_count == 1 and entity_list[1] == e)
|
||||
end)
|
||||
:epilogue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == 42 and payload3 == nil)
|
||||
end)
|
||||
:spawn()
|
||||
|
||||
evo.process_with(s, nil, 42)
|
||||
end
|
||||
|
||||
do
|
||||
local f = evo.id()
|
||||
local e = evo.builder():set(f, 42):spawn()
|
||||
|
||||
local s = evo.builder()
|
||||
:include(f)
|
||||
:prologue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == nil and payload3 == nil)
|
||||
end)
|
||||
:execute(function(chunk, entity_list, entity_count, payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == nil and payload3 == nil)
|
||||
assert(chunk == evo.chunk(f) and entity_count == 1 and entity_list[1] == e)
|
||||
end)
|
||||
:epilogue(function(payload1, payload2, payload3)
|
||||
assert(payload1 == nil and payload2 == nil and payload3 == nil)
|
||||
end)
|
||||
:spawn()
|
||||
|
||||
evo.process_with(s)
|
||||
end
|
||||
|
||||
do
|
||||
local f = evo.id()
|
||||
local e = evo.builder():set(f, 42):spawn()
|
||||
|
||||
local prologue_sum, execute_sum, epilogue_sum = 0, 0, 0
|
||||
|
||||
local function sum(...)
|
||||
local s = 0
|
||||
for i = 1, select('#', ...) do
|
||||
s = s + select(i, ...)
|
||||
end
|
||||
return s
|
||||
end
|
||||
|
||||
local function iota(n)
|
||||
if n == 0 then return end
|
||||
return n, iota(n - 1)
|
||||
end
|
||||
|
||||
local s = evo.builder()
|
||||
:include(f)
|
||||
:prologue(function(...)
|
||||
prologue_sum = prologue_sum + sum(...)
|
||||
end)
|
||||
:execute(function(chunk, entity_list, entity_count, ...)
|
||||
execute_sum = execute_sum + sum(...)
|
||||
assert(chunk == evo.chunk(f) and entity_count == 1 and entity_list[1] == e)
|
||||
end)
|
||||
:epilogue(function(...)
|
||||
epilogue_sum = epilogue_sum + sum(...)
|
||||
end)
|
||||
:spawn()
|
||||
|
||||
for n = 0, 50 do
|
||||
prologue_sum, execute_sum, epilogue_sum = 0, 0, 0
|
||||
evo.process_with(s, iota(n))
|
||||
local expect_sum = (n * (n + 1)) / 2
|
||||
assert(prologue_sum == expect_sum)
|
||||
assert(execute_sum == expect_sum)
|
||||
assert(epilogue_sum == expect_sum)
|
||||
end
|
||||
end
|
||||
@@ -79,10 +79,10 @@
|
||||
group: function(self: Builder, group: System): Builder
|
||||
|
||||
query: function(self: Builder, query: Query): Builder
|
||||
execute: function(self: Builder, execute: function(Chunk, {Entity}, integer)): Builder
|
||||
execute: function(self: Builder, execute: function(Chunk, {Entity}, integer, ...: any)): Builder
|
||||
|
||||
prologue: function(self: Builder, prologue: function()): Builder
|
||||
epilogue: function(self: Builder, epilogue: function()): Builder
|
||||
prologue: function(self: Builder, prologue: function(...: any)): Builder
|
||||
epilogue: function(self: Builder, epilogue: function(...: any)): Builder
|
||||
|
||||
destruction_policy: function(self: Builder, destruction_policy: Id): Builder
|
||||
end
|
||||
@@ -171,6 +171,7 @@
|
||||
locate: function(entity: Entity): Chunk | nil, integer
|
||||
|
||||
process: function(...: System)
|
||||
process_with: function(system: System, ...: any)
|
||||
|
||||
debug_mode: function(yesno: boolean)
|
||||
collect_garbage: function()
|
||||
|
||||
296
evolved.lua
296
evolved.lua
@@ -5,7 +5,7 @@ local evolved = {
|
||||
__LICENSE = [[
|
||||
MIT License
|
||||
|
||||
Copyright (C) 2024-2025, by Matvey Cherevko (blackmatov@gmail.com)
|
||||
Copyright (C) 2024-2026, by Matvey Cherevko (blackmatov@gmail.com)
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
@@ -43,10 +43,11 @@ local evolved = {
|
||||
---@alias evolved.execute fun(
|
||||
--- chunk: evolved.chunk,
|
||||
--- entity_list: evolved.entity[],
|
||||
--- entity_count: integer)
|
||||
--- entity_count: integer,
|
||||
--- ...: any)
|
||||
|
||||
---@alias evolved.prologue fun()
|
||||
---@alias evolved.epilogue fun()
|
||||
---@alias evolved.prologue fun(...: any)
|
||||
---@alias evolved.epilogue fun(...: any)
|
||||
|
||||
---@alias evolved.set_hook fun(
|
||||
--- entity: evolved.entity,
|
||||
@@ -207,7 +208,6 @@ local __lua_string_format = string.format
|
||||
local __lua_table_concat = table.concat
|
||||
local __lua_table_sort = table.sort
|
||||
local __lua_tostring = tostring
|
||||
local __lua_xpcall = xpcall
|
||||
|
||||
---@type fun(nseq?: integer): table
|
||||
local __lua_table_new = (function()
|
||||
@@ -338,6 +338,244 @@ local __lua_debug_traceback = (function()
|
||||
end
|
||||
end)()
|
||||
|
||||
---@type fun(f: function, e: function, ...): boolean, ...
|
||||
local __lua_xpcall = (function()
|
||||
-- https://github.com/BlackMATov/xpcall.lua/tree/v1.0.1
|
||||
|
||||
local __lua_xpcall = xpcall
|
||||
|
||||
---@diagnostic disable-next-line: redundant-parameter
|
||||
if __lua_select(2, __lua_xpcall(function(a) return a end, function() end, 42)) == 42 then
|
||||
-- use built-in xpcall if it works correctly with extra arguments
|
||||
return __lua_xpcall
|
||||
end
|
||||
|
||||
local __xpcall_function
|
||||
|
||||
local __xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4
|
||||
local __xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8
|
||||
|
||||
local __xpcall_argument_tail_list = __lua_setmetatable({}, { __mode = 'v' })
|
||||
local __xpcall_argument_tail_count = 0
|
||||
|
||||
local function ret_xpcall_function_1(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1 = nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_2(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2 = nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_3(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3 = nil, nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_4(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = nil, nil, nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_5(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = nil, nil, nil, nil
|
||||
__xpcall_argument_5 = nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_6(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = nil, nil, nil, nil
|
||||
__xpcall_argument_5, __xpcall_argument_6 = nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_7(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = nil, nil, nil, nil
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7 = nil, nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function ret_xpcall_function_8(...)
|
||||
__xpcall_function = nil
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = nil, nil, nil, nil
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8 = nil, nil, nil, nil
|
||||
return ...
|
||||
end
|
||||
|
||||
local function call_xpcall_function_1()
|
||||
return ret_xpcall_function_1(__xpcall_function(
|
||||
__xpcall_argument_1))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_2()
|
||||
return ret_xpcall_function_2(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_3()
|
||||
return ret_xpcall_function_3(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_4()
|
||||
return ret_xpcall_function_4(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_5()
|
||||
return ret_xpcall_function_5(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_6()
|
||||
return ret_xpcall_function_6(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_7()
|
||||
return ret_xpcall_function_7(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_8()
|
||||
return ret_xpcall_function_8(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8))
|
||||
end
|
||||
|
||||
local function call_xpcall_function_N()
|
||||
return ret_xpcall_function_8(__xpcall_function(
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8,
|
||||
__lua_table_unpack(__xpcall_argument_tail_list, 1, __xpcall_argument_tail_count)))
|
||||
end
|
||||
|
||||
---@param f function
|
||||
---@param e function
|
||||
---@param ... any
|
||||
---@return boolean success
|
||||
---@return any ... results
|
||||
return function(f, e, ...)
|
||||
local argument_count = __lua_select('#', ...)
|
||||
|
||||
if argument_count == 0 then
|
||||
-- no extra arguments, just use built-in xpcall
|
||||
return __lua_xpcall(f, e)
|
||||
end
|
||||
|
||||
__xpcall_function = f
|
||||
|
||||
if argument_count <= 8 then
|
||||
if argument_count <= 4 then
|
||||
if argument_count <= 2 then
|
||||
if argument_count <= 1 then
|
||||
__xpcall_argument_1 = ...
|
||||
return __lua_xpcall(call_xpcall_function_1, e)
|
||||
else
|
||||
__xpcall_argument_1, __xpcall_argument_2 = ...
|
||||
return __lua_xpcall(call_xpcall_function_2, e)
|
||||
end
|
||||
else
|
||||
if argument_count <= 3 then
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3 = ...
|
||||
return __lua_xpcall(call_xpcall_function_3, e)
|
||||
else
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4 = ...
|
||||
return __lua_xpcall(call_xpcall_function_4, e)
|
||||
end
|
||||
end
|
||||
else
|
||||
if argument_count <= 6 then
|
||||
if argument_count <= 5 then
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5 = ...
|
||||
return __lua_xpcall(call_xpcall_function_5, e)
|
||||
else
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6 = ...
|
||||
return __lua_xpcall(call_xpcall_function_6, e)
|
||||
end
|
||||
else
|
||||
if argument_count <= 7 then
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7 = ...
|
||||
return __lua_xpcall(call_xpcall_function_7, e)
|
||||
else
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8 = ...
|
||||
return __lua_xpcall(call_xpcall_function_8, e)
|
||||
end
|
||||
end
|
||||
end
|
||||
else
|
||||
__xpcall_argument_1, __xpcall_argument_2, __xpcall_argument_3, __xpcall_argument_4,
|
||||
__xpcall_argument_5, __xpcall_argument_6, __xpcall_argument_7, __xpcall_argument_8 = ...
|
||||
end
|
||||
|
||||
local argument_tail_list = __xpcall_argument_tail_list
|
||||
__xpcall_argument_tail_count = argument_count - 8
|
||||
|
||||
for i = 1, argument_count - 8, 8 do
|
||||
local argument_remaining = argument_count - 8 - i + 1
|
||||
|
||||
if argument_remaining <= 4 then
|
||||
if argument_remaining <= 2 then
|
||||
if argument_remaining <= 1 then
|
||||
argument_tail_list[i] = __lua_select(i + 8, ...)
|
||||
else
|
||||
argument_tail_list[i], argument_tail_list[i + 1] = __lua_select(i + 8, ...)
|
||||
end
|
||||
else
|
||||
if argument_remaining <= 3 then
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2] = __lua_select(i + 8, ...)
|
||||
else
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2], argument_tail_list[i + 3] = __lua_select(i + 8, ...)
|
||||
end
|
||||
end
|
||||
else
|
||||
if argument_remaining <= 6 then
|
||||
if argument_remaining <= 5 then
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2], argument_tail_list[i + 3],
|
||||
argument_tail_list[i + 4] = __lua_select(i + 8, ...)
|
||||
else
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2], argument_tail_list[i + 3],
|
||||
argument_tail_list[i + 4], argument_tail_list[i + 5] = __lua_select(i + 8, ...)
|
||||
end
|
||||
else
|
||||
if argument_remaining <= 7 then
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2], argument_tail_list[i + 3],
|
||||
argument_tail_list[i + 4], argument_tail_list[i + 5],
|
||||
argument_tail_list[i + 6] = __lua_select(i + 8, ...)
|
||||
else
|
||||
argument_tail_list[i], argument_tail_list[i + 1],
|
||||
argument_tail_list[i + 2], argument_tail_list[i + 3],
|
||||
argument_tail_list[i + 4], argument_tail_list[i + 5],
|
||||
argument_tail_list[i + 6], argument_tail_list[i + 7] = __lua_select(i + 8, ...)
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return __lua_xpcall(call_xpcall_function_N, e)
|
||||
end
|
||||
end)()
|
||||
|
||||
---
|
||||
---
|
||||
---
|
||||
@@ -840,6 +1078,7 @@ local __evolved_execute
|
||||
local __evolved_locate
|
||||
|
||||
local __evolved_process
|
||||
local __evolved_process_with
|
||||
|
||||
local __evolved_debug_mode
|
||||
local __evolved_collect_garbage
|
||||
@@ -3665,32 +3904,24 @@ function __iterator_fns.__execute_iterator(execute_state)
|
||||
__release_table(__table_pool_tag.execute_state, execute_state, true)
|
||||
end
|
||||
|
||||
---@type { [1]: evolved.query, [2]: evolved.execute }
|
||||
local __query_execute_external_arguments = {}
|
||||
|
||||
---@param query? evolved.query
|
||||
---@param execute? evolved.execute
|
||||
local function __query_execute(query, execute)
|
||||
-- we use the external arguments here to support lua 5.1 xpcall (which does not support argument passing)
|
||||
-- also, we can not use upvalues directly, because the function may be called recursively in that case
|
||||
-- storing the arguments in local variables makes them invulnerable to changes during recursive calls
|
||||
|
||||
query = query or __query_execute_external_arguments[1]
|
||||
execute = execute or __query_execute_external_arguments[2]
|
||||
|
||||
---@param query evolved.query
|
||||
---@param execute evolved.execute
|
||||
---@param ... any processing payload
|
||||
local function __query_execute(query, execute, ...)
|
||||
for chunk, entity_list, entity_count in __evolved_execute(query) do
|
||||
execute(chunk, entity_list, entity_count)
|
||||
execute(chunk, entity_list, entity_count, ...)
|
||||
end
|
||||
end
|
||||
|
||||
---@param system evolved.system
|
||||
local function __system_process(system)
|
||||
---@param ... any processing payload
|
||||
local function __system_process(system, ...)
|
||||
---@type evolved.query?, evolved.execute?, evolved.prologue?, evolved.epilogue?
|
||||
local query, execute, prologue, epilogue = __evolved_get(system,
|
||||
__QUERY, __EXECUTE, __PROLOGUE, __EPILOGUE)
|
||||
|
||||
if prologue then
|
||||
local success, result = __lua_xpcall(prologue, __lua_debug_traceback)
|
||||
local success, result = __lua_xpcall(prologue, __lua_debug_traceback, ...)
|
||||
|
||||
if not success then
|
||||
__error_fmt('system prologue failed: %s', result)
|
||||
@@ -3700,8 +3931,7 @@ local function __system_process(system)
|
||||
if execute then
|
||||
__evolved_defer()
|
||||
do
|
||||
__query_execute_external_arguments[1], __query_execute_external_arguments[2] = query or system, execute
|
||||
local success, result = __lua_xpcall(__query_execute, __lua_debug_traceback, query or system, execute)
|
||||
local success, result = __lua_xpcall(__query_execute, __lua_debug_traceback, query or system, execute, ...)
|
||||
|
||||
if not success then
|
||||
__evolved_cancel()
|
||||
@@ -3727,7 +3957,7 @@ local function __system_process(system)
|
||||
for subsystem_index = 1, group_subsystem_count do
|
||||
local subsystem = subsystem_list[subsystem_index]
|
||||
if not __evolved_has(subsystem, __DISABLED) then
|
||||
__system_process(subsystem)
|
||||
__system_process(subsystem, ...)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -3736,7 +3966,7 @@ local function __system_process(system)
|
||||
end
|
||||
|
||||
if epilogue then
|
||||
local success, result = __lua_xpcall(epilogue, __lua_debug_traceback)
|
||||
local success, result = __lua_xpcall(epilogue, __lua_debug_traceback, ...)
|
||||
|
||||
if not success then
|
||||
__error_fmt('system epilogue failed: %s', result)
|
||||
@@ -5092,14 +5322,25 @@ function __evolved_process(...)
|
||||
if __freelist_ids[system_primary] ~= system then
|
||||
__warning_fmt('the system (%s) is not alive and cannot be processed',
|
||||
__id_name(system))
|
||||
elseif __evolved_has(system, __DISABLED) then
|
||||
-- the system is disabled, nothing to process
|
||||
else
|
||||
__system_process(system)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
---@param system evolved.system
|
||||
---@param ... any processing payload
|
||||
function __evolved_process_with(system, ...)
|
||||
local system_primary = system % 2 ^ 20
|
||||
|
||||
if __freelist_ids[system_primary] ~= system then
|
||||
__error_fmt('the system (%s) is not alive and cannot be processed',
|
||||
__id_name(system))
|
||||
end
|
||||
|
||||
__system_process(system, ...)
|
||||
end
|
||||
|
||||
---@param yesno boolean
|
||||
function __evolved_debug_mode(yesno)
|
||||
__debug_mode = yesno
|
||||
@@ -6337,6 +6578,7 @@ evolved.execute = __evolved_execute
|
||||
evolved.locate = __evolved_locate
|
||||
|
||||
evolved.process = __evolved_process
|
||||
evolved.process_with = __evolved_process_with
|
||||
|
||||
evolved.debug_mode = __evolved_debug_mode
|
||||
evolved.collect_garbage = __evolved_collect_garbage
|
||||
|
||||
@@ -12,10 +12,6 @@ local STAGES = {
|
||||
:build(),
|
||||
}
|
||||
|
||||
local UNIFORMS = {
|
||||
DELTA_TIME = 1.0 / 60.0,
|
||||
}
|
||||
|
||||
local FRAGMENTS = {
|
||||
POSITION_X = evolved.builder()
|
||||
:name('FRAGMENTS.POSITION_X')
|
||||
@@ -82,8 +78,7 @@ evolved.builder()
|
||||
:group(STAGES.ON_UPDATE)
|
||||
:include(FRAGMENTS.POSITION_X, FRAGMENTS.POSITION_Y)
|
||||
:include(FRAGMENTS.VELOCITY_X, FRAGMENTS.VELOCITY_Y)
|
||||
:execute(function(chunk, _, entity_count)
|
||||
local delta_time = UNIFORMS.DELTA_TIME
|
||||
:execute(function(chunk, _, entity_count, delta_time)
|
||||
local screen_width, screen_height = love.graphics.getDimensions()
|
||||
|
||||
---@type number[], number[]
|
||||
@@ -156,8 +151,7 @@ end
|
||||
|
||||
---@type love.update
|
||||
function love.update(dt)
|
||||
UNIFORMS.DELTA_TIME = dt
|
||||
evolved.process(STAGES.ON_UPDATE)
|
||||
evolved.process_with(STAGES.ON_UPDATE, dt)
|
||||
end
|
||||
|
||||
---@type love.draw
|
||||
|
||||
Reference in New Issue
Block a user