feat: 50 игр на Lua + импорт Roblox для всех + поддержка Lua в плеере #39
Binary file not shown.
@ -113,18 +113,28 @@ class CFrame:
|
|||||||
matrix: tuple # (r00, r01, r02, r10, r11, r12, r20, r21, r22)
|
matrix: tuple # (r00, r01, r02, r10, r11, r12, r20, r21, r22)
|
||||||
|
|
||||||
def to_euler_xyz(self) -> tuple:
|
def to_euler_xyz(self) -> tuple:
|
||||||
"""Конверт 3x3 rotation matrix в Euler XYZ (radians).
|
"""Конверт 3x3 rotation matrix в Euler YXZ (Babylon convention).
|
||||||
|
|
||||||
Использует стандартную intrinsic XYZ rotation extraction:
|
Babylon mesh.rotation = Vector3(rx, ry, rz) применяется в порядке YXZ
|
||||||
Rx = atan2(r21, r22)
|
(rotate Y first, then X, then Z). Чтобы извлечь Euler из матрицы под
|
||||||
Ry = atan2(-r20, sqrt(r21² + r22²))
|
этот convention, используем формулу YXZ-extraction:
|
||||||
Rz = atan2(r10, r00)
|
Rx = asin(-r12)
|
||||||
|
Ry = atan2(r02, r22)
|
||||||
|
Rz = atan2(r10, r11)
|
||||||
|
(имя метода to_euler_xyz сохраняем для совместимости вызовов.)
|
||||||
"""
|
"""
|
||||||
import math
|
import math
|
||||||
r00, r01, r02, r10, r11, r12, r20, r21, r22 = self.matrix
|
r00, r01, r02, r10, r11, r12, r20, r21, r22 = self.matrix
|
||||||
rx = math.atan2(r21, r22)
|
# Edge case: r12 близко к ±1 (gimbal lock на X = ±90°)
|
||||||
ry = math.atan2(-r20, math.sqrt(r21*r21 + r22*r22))
|
clamped = max(-1.0, min(1.0, -r12))
|
||||||
rz = math.atan2(r10, r00)
|
rx = math.asin(clamped)
|
||||||
|
if abs(clamped) > 0.99999:
|
||||||
|
# Gimbal lock — z = 0, y = atan2(-r20, r00)
|
||||||
|
ry = math.atan2(-r20, r00)
|
||||||
|
rz = 0.0
|
||||||
|
else:
|
||||||
|
ry = math.atan2(r02, r22)
|
||||||
|
rz = math.atan2(r10, r11)
|
||||||
return (rx, ry, rz)
|
return (rx, ry, rz)
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
@ -183,6 +183,15 @@ export class LuaSharedSandbox {
|
|||||||
Source = nil,
|
Source = nil,
|
||||||
}
|
}
|
||||||
local co = coroutine.create(function()
|
local co = coroutine.create(function()
|
||||||
|
-- WATCHDOG: каждые 50000 инструкций — yield 1 кадр.
|
||||||
|
-- Защищает от tight-loop типа:
|
||||||
|
-- while not parent:FindFirstChild(name) do
|
||||||
|
-- parent.ChildAdded:wait()
|
||||||
|
-- end
|
||||||
|
-- где наш stub :wait() возвращает сразу.
|
||||||
|
debug.sethook(function()
|
||||||
|
coroutine.yield(0.016)
|
||||||
|
end, "", 50000)
|
||||||
-- pcall защищает от runtime-ошибок которые иначе крашат
|
-- pcall защищает от runtime-ошибок которые иначе крашат
|
||||||
-- coroutine и могут повредить WASM-стейт. Возвраты
|
-- coroutine и могут повредить WASM-стейт. Возвраты
|
||||||
-- handler'а намеренно поглощаются.
|
-- handler'а намеренно поглощаются.
|
||||||
|
|||||||
@ -58,7 +58,10 @@ function makeSignal() {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
sig.fire = sig.Fire;
|
sig.fire = sig.Fire;
|
||||||
sig.Wait = () => undefined;
|
// Wait() возвращает -1 как маркер "yield 1 кадр" — наш Lua-prelude
|
||||||
|
// оборачивает все Signal:Wait через __rbxl_signal_wait который при
|
||||||
|
// получении -1 делает rbx_wait(0.05) (yield в coroutine).
|
||||||
|
sig.Wait = () => -1;
|
||||||
sig.wait = sig.Wait;
|
sig.wait = sig.Wait;
|
||||||
return sig;
|
return sig;
|
||||||
}
|
}
|
||||||
@ -1385,6 +1388,12 @@ export function registerRobloxShim(lua, opts) {
|
|||||||
local ret = coroutine.yield(sec)
|
local ret = coroutine.yield(sec)
|
||||||
return ret or sec
|
return ret or sec
|
||||||
end
|
end
|
||||||
|
|
||||||
|
-- Глобальный безопасный yield для любых stub-сигналов / любых
|
||||||
|
-- "ждунов". Используется в Lua-обёртках вокруг WaitForChild и т.п.
|
||||||
|
function __rbxl_yield_frame()
|
||||||
|
coroutine.yield(0.05)
|
||||||
|
end
|
||||||
if type(task) == 'table' then
|
if type(task) == 'table' then
|
||||||
task.wait = rbx_wait
|
task.wait = rbx_wait
|
||||||
else
|
else
|
||||||
@ -1413,6 +1422,10 @@ export function registerRobloxShim(lua, opts) {
|
|||||||
-- что приводит к wasmoon promise-detection crash). pcall возвращает
|
-- что приводит к wasmoon promise-detection crash). pcall возвращает
|
||||||
-- (ok, ret1, ret2, ...) — мы их не используем.
|
-- (ok, ret1, ret2, ...) — мы их не используем.
|
||||||
local co = coroutine.create(function()
|
local co = coroutine.create(function()
|
||||||
|
-- Тот же watchdog что и в _startSingleScript
|
||||||
|
debug.sethook(function()
|
||||||
|
coroutine.yield(0.016)
|
||||||
|
end, "", 50000)
|
||||||
pcall(fn, a1, a2, a3, a4)
|
pcall(fn, a1, a2, a3, a4)
|
||||||
end)
|
end)
|
||||||
__rbxl_register_coroutine(handlerId, co)
|
__rbxl_register_coroutine(handlerId, co)
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user