Merge branch 'MihailRis:main' into main

This commit is contained in:
Xertis
2025-01-09 14:37:15 +03:00
committed by GitHub
250 changed files with 7152 additions and 2904 deletions
+2 -1
View File
@@ -1,4 +1,5 @@
{
"texture": "bazalt",
"breakable": false
"breakable": false,
"base:durability": 1e9
}
+2 -1
View File
@@ -9,5 +9,6 @@
"grounded": true,
"model": "X",
"hitbox": [0.15, 0.0, 0.15, 0.7, 0.7, 0.7],
"base:durability": 0.0
"base:durability": 0.0,
"base:loot": []
}
+4 -1
View File
@@ -8,5 +8,8 @@
"grass_side",
"grass_side"
],
"base:durability": 1.3
"base:durability": 1.3,
"base:loot": [
{"item": "base:dirt.item"}
]
}
+1
View File
@@ -1 +1,2 @@
"base:durability" = {}
"base:loot" = {}
+30
View File
@@ -11,4 +11,34 @@ function util.drop(ppos, itemid, count, pickup_delay)
}})
end
local function calc_loot(loot_table)
local results = {}
for _, loot in ipairs(loot_table) do
local chance = loot.chance or 1
local count = loot.count or 1
local roll = math.random()
if roll < chance then
if loot.min and loot.max then
count = math.random(loot.min, loot.max)
end
if count == 0 then
goto continue
end
table.insert(results, {item=item.index(loot.item), count=count})
end
::continue::
end
return results
end
function util.block_loot(blockid)
local lootscheme = block.properties[blockid]["base:loot"]
if lootscheme then
return calc_loot(lootscheme)
end
return {{item=block.get_picking_item(blockid), count=1}}
end
return util
@@ -3,17 +3,32 @@ local body = entity.rigidbody
local rig = entity.skeleton
local blockid = ARGS.block
local blockstates = ARGS.states or 0
if SAVED_DATA.block then
blockid = SAVED_DATA.block
blockstates = SAVED_DATA.states or 0
else
SAVED_DATA.block = blockid
SAVED_DATA.states = blockstates
end
do -- setup visuals
local textures = block.get_textures(block.index(blockid))
local id = block.index(blockid)
local rotation = block.decompose_state(blockstates)[1]
local textures = block.get_textures(id)
for i,t in ipairs(textures) do
rig:set_texture("$"..tostring(i-1), "blocks:"..textures[i])
end
local axisX = {block.get_X(id, rotation)}
local axisY = {block.get_Y(id, rotation)}
local axisZ = {block.get_Z(id, rotation)}
local matrix = {
axisX[1], axisX[2], axisX[3], 0,
axisY[1], axisY[2], axisY[3], 0,
axisZ[1], axisZ[2], axisZ[3], 0,
0, 0, 0, 1
}
rig:set_matrix(0, matrix)
end
function on_grounded()
@@ -22,7 +37,7 @@ function on_grounded()
local iy = math.floor(pos[2])
local iz = math.floor(pos[3])
if block.is_replaceable_at(ix, iy, iz) then
block.place(ix, iy, iz, block.index(blockid), 0)
block.place(ix, iy, iz, block.index(blockid), blockstates)
else
local picking_item = block.get_picking_item(block.index(blockid))
local drop = entities.spawn("base:drop", pos, {base__drop={id=picking_item, count=1}})
+14 -10
View File
@@ -1,12 +1,16 @@
function on_block_broken(id, x, y, z, playerid)
gfx.particles.emit({x+0.5, y+0.5, z+0.5}, 64, {
lifetime=1.0,
spawn_interval=0.0001,
explosion={4, 4, 4},
texture="blocks:"..block.get_textures(id)[1],
random_sub_uv=0.1,
size={0.1, 0.1, 0.1},
spawn_shape="box",
spawn_spread={0.4, 0.4, 0.4}
})
if gfx then
gfx.particles.emit({x+0.5, y+0.5, z+0.5}, 64, {
lifetime=1.0,
spawn_interval=0.0001,
explosion={4, 4, 4},
texture="blocks:"..block.get_textures(id)[1],
random_sub_uv=0.1,
size={0.1, 0.1, 0.1},
spawn_shape="box",
spawn_spread={0.4, 0.4, 0.4}
})
end
rules.create("do-loot-non-player", true)
end
+26
View File
@@ -0,0 +1,26 @@
bazalt breaker=bazalt sindiruvchi
bazalt=bazalt
blue lamp=kok lampa
brick=g'isht
dirt=yer
flower=gul
glass=shisha
grass block=o'tli blok
green lamp=yashil lampa
ice=muz
lamp=lampa
leaves=barglar
light bulb=chiroq
metal=metal
pane=panel
pipe=quvur
planks=yog'och
red lamp=qizil lampa
rust=zang
sand=qum
stone=tosh
tall grass=Baland o't
torch=fakel
water=suv
wood=yog'och
wooden door=yog'och eshik
+8 -2
View File
@@ -185,8 +185,14 @@ function refresh()
end
end
local packids = {unpack(packs_installed)}
for i,k in ipairs(packs_available) do
table.insert(packids, k)
end
local packinfos = pack.get_info(packids)
for i,id in ipairs(packs_installed) do
local packinfo = pack.get_info(id)
local packinfo = packinfos[id]
packinfo.index = i
callback = not table.has(base_packs, id) and string.format('move_pack("%s")', id) or nil
packinfo.error = check_dependencies(packinfo)
@@ -194,7 +200,7 @@ function refresh()
end
for i,id in ipairs(packs_available) do
local packinfo = pack.get_info(id)
local packinfo = packinfos[id]
packinfo.index = i
callback = string.format('move_pack("%s")', id)
packinfo.error = check_dependencies(packinfo)
+2 -1
View File
@@ -247,8 +247,9 @@ function refresh()
local contents = document.contents
contents:clear()
local packinfos = pack.get_info(packs_installed)
for i, id in ipairs(packs_installed) do
local packinfo = pack.get_info(id)
local packinfo = packinfos[id]
packinfo.id = id
packs_installed[i] = {packinfo.id, packinfo.title}
+1
View File
@@ -1,5 +1,6 @@
<panel size='400' color='0' interval='1' context='menu'>
<button onclick='menu.page="worlds"'>@Worlds</button>
<button onclick='menu.page="scripts"'>@Scripts</button>
<button onclick='menu.page="settings"'>@Settings</button>
<button onclick='menu.page="content_menu"'>@Contents Menu</button>
<button onclick='core.quit()'>@Quit</button>
+12
View File
@@ -0,0 +1,12 @@
<panel size='400' color='#00000030' context='menu'>
<container size='400,32'>
<label pos='2,10'>@Scripts</label>
<image onclick='refresh()' interactive='true' src='gui/refresh'
size='32' gravity='top-right'
color='#FFFFFF80' hover-color='#FFFFFF10'/>
</container>
<panel id="list" size='400' interval='1' color='0' max-length='300'>
<!-- content is generated in script -->
</panel>
<button onclick='menu:back()'>@Back</button>
</panel>
+40
View File
@@ -0,0 +1,40 @@
function run_script(path)
debug.log("starting application script "..path)
local code = file.read(path)
local chunk, err = loadstring(code, path)
if chunk == nil then
error(err)
end
setfenv(chunk, setmetatable({app=__vc_app}, {__index=_G}))
start_coroutine(chunk, path)
end
function refresh()
document.list:clear()
local available = pack.get_available()
local infos = pack.get_info(available)
for _, name in ipairs(available) do
local info = infos[name]
local scripts_dir = info.path.."/scripts/app"
if not file.exists(scripts_dir) then
goto continue
end
local files = file.list(scripts_dir)
for _, filename in ipairs(files) do
if file.ext(filename) == "lua" then
document.list:add(gui.template("script", {
pack=name,
name=file.stem(filename),
path=filename
}))
end
end
::continue::
end
end
function on_open()
refresh()
end
+3
View File
@@ -0,0 +1,3 @@
<button color='#10305080' hover-color='#10305040' onclick='run_script("%{path}")'>
%{name} [%{pack}]
</button>
+134 -133
View File
@@ -13,15 +13,15 @@ local MAX_INT64 = 9223372036854775807
local MIN_INT64 = -9223372036854775808
local function maskHighBytes(num)
return bit.band(num, 0xFF)
return bit.band(num, 0xFF)
end
local function reverse(tbl)
for i=1, math.floor(#tbl / 2) do
local tmp = tbl[i]
tbl[i] = tbl[#tbl - i + 1]
tbl[#tbl - i + 1] = tmp
end
for i=1, math.floor(#tbl / 2) do
local tmp = tbl[i]
tbl[i] = tbl[#tbl - i + 1]
tbl[#tbl - i + 1] = tmp
end
return tbl
end
@@ -29,60 +29,60 @@ local orders = { "LE", "BE" }
local fromLEConvertors =
{
LE = function(bytes) return bytes end,
BE = function(bytes) return reverse(bytes) end
LE = function(bytes) return bytes end,
BE = function(bytes) return reverse(bytes) end
}
local toLEConvertors =
{
LE = function(bytes) return bytes end,
BE = function(bytes) return reverse(bytes) end
LE = function(bytes) return bytes end,
BE = function(bytes) return reverse(bytes) end
}
bit_converter.default_order = "LE"
bit_converter.default_order = "BE"
local function fromLE(bytes, orderTo)
if orderTo then
bit_converter.validate_order(orderTo)
return fromLEConvertors[orderTo](bytes)
else return bytes end
if orderTo then
bit_converter.validate_order(orderTo)
return fromLEConvertors[orderTo](bytes)
else return bytes end
end
local function toLE(bytes, orderFrom)
if orderFrom then
bit_converter.validate_order(orderFrom)
return toLEConvertors[orderFrom](bytes)
else return bytes end
if orderFrom then
bit_converter.validate_order(orderFrom)
return toLEConvertors[orderFrom](bytes)
else return bytes end
end
function bit_converter.validate_order(order)
if not bit_converter.is_valid_order(order) then
error("invalid order: "..order)
end
if not bit_converter.is_valid_order(order) then
error("invalid order: "..order)
end
end
function bit_converter.is_valid_order(order) return table.has(orders, order) end
function bit_converter.string_to_bytes(str)
local bytes = { }
local bytes = { }
local len = string.len(str)
local len = string.len(str)
local lenBytes = bit_converter.uint16_to_bytes(len)
local lenBytes = bit_converter.uint16_to_bytes(len)
for i = 1, #lenBytes do
bytes[i] = lenBytes[i]
end
for i = 1, #lenBytes do
bytes[i] = lenBytes[i]
end
for i = 1, len do
bytes[#bytes + 1] = string.byte(string.sub(str, i, i))
end
for i = 1, len do
bytes[#bytes + 1] = string.byte(string.sub(str, i, i))
end
return bytes
return bytes
end
function bit_converter.bool_to_byte(bool)
return bool and 1 or 0
return bool and 1 or 0
end
-- Credits to Iryont <https://github.com/iryont/lua-struct>
@@ -151,177 +151,178 @@ end
--
function bit_converter.float32_to_bytes(float, order)
return fromLE(floatOrDoubleToBytes(float, 'f'), order)
return fromLE(floatOrDoubleToBytes(float, 'f'), order)
end
function bit_converter.float64_to_bytes(float, order)
return fromLE(floatOrDoubleToBytes(float, 'd'), order)
return fromLE(floatOrDoubleToBytes(float, 'd'), order)
end
function bit_converter.single_to_bytes(float, order)
on_deprecated_call("bit_converter.float_to_bytes", "bit_converter.float32_to_bytes")
return bit_converter.float32_to_bytes(bytes, order)
on_deprecated_call("bit_converter.float_to_bytes", "bit_converter.float32_to_bytes")
return bit_converter.float32_to_bytes(bytes, order)
end
function bit_converter.double_to_bytes(double, order)
on_deprecated_call("bit_converter.double_to_bytes", "bit_converter.float64_to_bytes")
return bit_converter.float64_to_bytes(bytes, order)
on_deprecated_call("bit_converter.double_to_bytes", "bit_converter.float64_to_bytes")
return bit_converter.float64_to_bytes(bytes, order)
end
local function uint32ToBytes(int, order)
return fromLE({
maskHighBytes(bit.rshift(int, 24)),
maskHighBytes(bit.rshift(int, 16)),
maskHighBytes(bit.rshift(int, 8)),
maskHighBytes(int)
}, order)
return fromLE({
maskHighBytes(int),
maskHighBytes(bit.rshift(int, 8)),
maskHighBytes(bit.rshift(int, 16)),
maskHighBytes(bit.rshift(int, 24))
}, order)
end
local function uint16ToBytes(int, order)
return fromLE({
maskHighBytes(bit.rshift(int, 8)),
maskHighBytes(int)
}, order)
return fromLE({
maskHighBytes(int),
maskHighBytes(bit.rshift(int, 8))
}, order)
end
function bit_converter.uint32_to_bytes(int, order)
if int > MAX_UINT32 or int < MIN_UINT32 then
error("invalid uint32")
end
if int > MAX_UINT32 or int < MIN_UINT32 then
error("invalid uint32")
end
return uint32ToBytes(int, order)
return uint32ToBytes(int, order)
end
function bit_converter.uint16_to_bytes(int, order)
if int > MAX_UINT16 or int < MIN_UINT16 then
error("invalid uint16")
end
if int > MAX_UINT16 or int < MIN_UINT16 then
error("invalid uint16")
end
return uint16ToBytes(int, order)
return uint16ToBytes(int, order)
end
function bit_converter.int64_to_bytes(int, order)
if int > MAX_INT64 or int < MIN_INT64 then
error("invalid int64")
end
if int > MAX_INT64 or int < MIN_INT64 then
error("invalid int64")
end
return fromLE({
maskHighBytes(bit.rshift(int, 56)),
maskHighBytes(bit.rshift(int, 48)),
maskHighBytes(bit.rshift(int, 40)),
maskHighBytes(bit.rshift(int, 32)),
maskHighBytes(bit.rshift(int, 24)),
maskHighBytes(bit.rshift(int, 16)),
maskHighBytes(bit.rshift(int, 8)),
maskHighBytes(int)
}, order)
return fromLE({
maskHighBytes(int),
maskHighBytes(bit.rshift(int, 8)),
maskHighBytes(bit.rshift(int, 16)),
maskHighBytes(bit.rshift(int, 24)),
maskHighBytes(bit.rshift(int, 32)),
maskHighBytes(bit.rshift(int, 40)),
maskHighBytes(bit.rshift(int, 48)),
maskHighBytes(bit.rshift(int, 56))
}, order)
end
function bit_converter.int32_to_bytes(int, order)
on_deprecated_call("bit_converter.int32_to_bytes", "bit_converter.sint32_to_bytes")
on_deprecated_call("bit_converter.int32_to_bytes", "bit_converter.sint32_to_bytes")
if int > MAX_INT32 or int < MIN_INT32 then
error("invalid int32")
end
if int > MAX_INT32 or int < MIN_INT32 then
error("invalid int32")
end
return uint32ToBytes(int + MAX_INT32, order)
return uint32ToBytes(int + MAX_INT32, order)
end
function bit_converter.int16_to_bytes(int, order)
on_deprecated_call("bit_converter.int32_to_bytes", "bit_converter.sint16_to_bytes")
on_deprecated_call("bit_converter.int32_to_bytes", "bit_converter.sint16_to_bytes")
if int > MAX_INT16 or int < MIN_INT16 then
error("invalid int16")
end
if int > MAX_INT16 or int < MIN_INT16 then
error("invalid int16")
end
return uint16ToBytes(int + MAX_INT16, order)
return uint16ToBytes(int + MAX_INT16, order)
end
function bit_converter.sint32_to_bytes(int, order)
if int > MAX_INT32 or int < MIN_INT32 then
error("invalid sint32")
end
if int > MAX_INT32 or int < MIN_INT32 then
error("invalid sint32")
end
return uint32ToBytes(int + MAX_UINT32 + 1, order)
return uint32ToBytes(int + MAX_UINT32 + 1, order)
end
function bit_converter.sint16_to_bytes(int, order)
if int > MAX_INT16 or int < MIN_INT16 then
error("invalid sint16")
end
if int > MAX_INT16 or int < MIN_INT16 then
error("invalid sint16")
end
return uint16ToBytes(int + MAX_UINT16 + 1, order)
return uint16ToBytes(int + MAX_UINT16 + 1, order)
end
function bit_converter.bytes_to_float32(bytes, order)
return bytesToFloatOrDouble(toLE(bytes, order), 'f')
return bytesToFloatOrDouble(toLE(bytes, order), 'f')
end
function bit_converter.bytes_to_float64(bytes, order)
return bytesToFloatOrDouble(toLE(bytes, order), 'd')
return bytesToFloatOrDouble(toLE(bytes, order), 'd')
end
function bit_converter.bytes_to_single(bytes, order)
on_deprecated_call("bit_converter.bytes_to_single", "bit_converter.bytes_to_float32")
return bit_converter.bytes_to_float32(bytes, order)
on_deprecated_call("bit_converter.bytes_to_single", "bit_converter.bytes_to_float32")
return bit_converter.bytes_to_float32(bytes, order)
end
function bit_converter.bytes_to_double(bytes, order)
on_deprecated_call("bit_converter.bytes_to_double", "bit_converter.bytes_to_float64")
return bit_converter.bytes_to_float64(bytes, order)
on_deprecated_call("bit_converter.bytes_to_double", "bit_converter.bytes_to_float64")
return bit_converter.bytes_to_float64(bytes, order)
end
function bit_converter.bytes_to_string(bytes, order)
local len = bit_converter.bytes_to_uint16({ bytes[1], bytes[2] })
local len = bit_converter.bytes_to_uint16({ bytes[1], bytes[2] })
local str = ""
local str = ""
for i = 1, len do
str = str..string.char(bytes[i + 2])
end
for i = 1, len do
str = str..string.char(bytes[i + 2])
end
return str
return str
end
function bit_converter.byte_to_bool(byte)
return byte ~= 0
return byte ~= 0
end
function bit_converter.bytes_to_uint32(bytes, order)
if #bytes < 4 then
error("eof")
end
if #bytes < 4 then
error("eof")
end
bytes = toLE(bytes, order)
bytes = toLE(bytes, order)
return
bit.bor(
bit.bor(
bit.bor(
bit.lshift(bytes[1], 24),
bit.lshift(bytes[2], 16)),
bit.lshift(bytes[3], 8)),bytes[4])
bytes[1],
bit.lshift(bytes[2], 8)),
bit.lshift(bytes[3], 16)),
bit.lshift(bytes[4], 24))
end
function bit_converter.bytes_to_uint16(bytes, order)
if #bytes < 2 then
error("eof")
end
if #bytes < 2 then
error("eof")
end
bytes = toLE(bytes, order)
bytes = toLE(bytes, order)
return
bit.bor(
bit.lshift(bytes[1], 8),
bytes[2], 0)
bit.lshift(bytes[2], 8),
bytes[1], 0)
end
function bit_converter.bytes_to_int64(bytes, order)
if #bytes < 8 then
error("eof")
end
if #bytes < 8 then
error("eof")
end
bytes = toLE(bytes, order)
bytes = toLE(bytes, order)
return
bit.bor(
@@ -331,35 +332,35 @@ function bit_converter.bytes_to_int64(bytes, order)
bit.bor(
bit.bor(
bit.bor(
bit.lshift(bytes[1], 56),
bit.lshift(bytes[2], 48)),
bit.lshift(bytes[3], 40)),
bit.lshift(bytes[4], 32)),
bit.lshift(bytes[5], 24)),
bit.lshift(bit.band(bytes[6], 0xFF), 16)),
bit.lshift(bit.band(bytes[7], 0xFF), 8)),bit.band(bytes[8], 0xFF))
bit.lshift(bytes[8], 56),
bit.lshift(bytes[7], 48)),
bit.lshift(bytes[6], 40)),
bit.lshift(bytes[5], 32)),
bit.lshift(bytes[4], 24)),
bit.lshift(bit.band(bytes[3], 0xFF), 16)),
bit.lshift(bit.band(bytes[2], 0xFF), 8)),bit.band(bytes[1], 0xFF))
end
function bit_converter.bytes_to_int32(bytes, order)
on_deprecated_call("bit_converter.bytes_to_int32", "bit_converter.bytes_to_sint32")
return bit_converter.bytes_to_uint32(bytes, order) - MAX_INT32
on_deprecated_call("bit_converter.bytes_to_int32", "bit_converter.bytes_to_sint32")
return bit_converter.bytes_to_uint32(bytes, order) - MAX_INT32
end
function bit_converter.bytes_to_int16(bytes, order)
on_deprecated_call("bit_converter.bytes_to_int16", "bit_converter.bytes_to_sint16")
return bit_converter.bytes_to_uint16(bytes, order) - MAX_INT16
on_deprecated_call("bit_converter.bytes_to_int16", "bit_converter.bytes_to_sint16")
return bit_converter.bytes_to_uint16(bytes, order) - MAX_INT16
end
function bit_converter.bytes_to_sint32(bytes, order)
local num = bit_converter.bytes_to_uint32(bytes, order)
local num = bit_converter.bytes_to_uint32(bytes, order)
return MIN_INT32 * (bit.band(MAX_INT32 + 1, num) ~= 0 and 1 or 0) + bit.band(MAX_INT32, num)
return MIN_INT32 * (bit.band(MAX_INT32 + 1, num) ~= 0 and 1 or 0) + bit.band(MAX_INT32, num)
end
function bit_converter.bytes_to_sint16(bytes, order)
local num = bit_converter.bytes_to_uint16(bytes, order)
local num = bit_converter.bytes_to_uint16(bytes, order)
return MIN_INT16 * (bit.band(MAX_INT16 + 1, num) ~= 0 and 1 or 0) + bit.band(MAX_INT16, num)
return MIN_INT16 * (bit.band(MAX_INT16 + 1, num) ~= 0 and 1 or 0) + bit.band(MAX_INT16, num)
end
return bit_converter
+36
View File
@@ -0,0 +1,36 @@
local gui_util = {}
--- Parse `pagename?arg1=value1&arg2=value2` queries
--- @param query page query string
--- @return page_name, args_table
function gui_util.parse_query(query)
local args = {}
local name
local index = string.find(query, '?')
if index then
local argstr = string.sub(query, index + 1)
name = string.sub(query, 1, index - 1)
for key, value in string.gmatch(argstr, "([^=&]*)=([^&]*)") do
args[key] = value
end
else
name = query
end
return name, args
end
--- @param query page query string
--- @return document_id
function gui_util.load_page(query)
local name, args = gui_util.parse_query(query)
local filename = file.find(string.format("layouts/pages/%s.xml", name))
if filename then
name = file.prefix(filename)..":pages/"..name
gui.load_document(filename, name, args)
return name
end
end
return gui_util
+8
View File
@@ -0,0 +1,8 @@
local util = {}
function util.create_demo_world(generator)
app.config_packs({"base"})
app.new_world("demo", "2019", generator or "core:default")
end
return util
+3
View File
@@ -34,5 +34,8 @@
"blocks",
"items",
"particles"
],
"models": [
"block"
]
}
+1
View File
@@ -40,6 +40,7 @@ local Socket = {__index={
send=function(self, ...) return network.__send(self.id, ...) end,
recv=function(self, ...) return network.__recv(self.id, ...) end,
close=function(self) return network.__close(self.id) end,
available=function(self) return network.__available(self.id) or 0 end,
is_alive=function(self) return network.__is_alive(self.id) end,
is_connected=function(self) return network.__is_connected(self.id) end,
get_address=function(self) return network.__get_address(self.id) end,
+58
View File
@@ -0,0 +1,58 @@
function on_hud_open()
input.add_callback("player.pick", function ()
if hud.is_paused() or hud.is_inventory_open() then
return
end
local pid = hud.get_player()
local x, y, z = player.get_selected_block(pid)
if x == nil then
return
end
local id = block.get_picking_item(block.get(x, y, z))
local inv, cur_slot = player.get_inventory(pid)
local slot = inventory.find_by_item(inv, id, 0, 9)
if slot then
player.set_selected_slot(pid, slot)
return
end
if not rules.get("allow-content-access") then
return
end
slot = inventory.find_by_item(inv, 0, 0, 9)
if slot then
cur_slot = slot
end
player.set_selected_slot(pid, cur_slot)
inventory.set(inv, cur_slot, id, 1)
end)
input.add_callback("player.noclip", function ()
if hud.is_paused() or hud.is_inventory_open() then
return
end
local pid = hud.get_player()
if player.is_noclip(pid) then
player.set_flight(pid, false)
player.set_noclip(pid, false)
else
player.set_flight(pid, true)
player.set_noclip(pid, true)
end
end)
input.add_callback("player.flight", function ()
if hud.is_paused() or hud.is_inventory_open() then
return
end
local pid = hud.get_player()
if player.is_noclip(pid) then
return
end
if player.is_flight(pid) then
player.set_flight(pid, false)
else
player.set_flight(pid, true)
player.set_vel(pid, 0, 1, 0)
end
end)
end
+22 -1
View File
@@ -7,7 +7,7 @@ local names = {
"hidden", "draw-group", "picking-item", "surface-replacement", "script-name",
"ui-layout", "inventory-size", "tick-interval", "overlay-texture",
"translucent", "fields", "particles", "icon-type", "icon", "placing-block",
"stack-size"
"stack-size", "name"
}
for name, _ in pairs(user_props) do
table.insert(names, name)
@@ -40,3 +40,24 @@ make_read_only(block.properties)
for k,v in pairs(block.properties) do
make_read_only(v)
end
local function cache_names(library)
local indices = {}
local names = {}
for id=0,library.defs_count()-1 do
local name = library.properties[id].name
indices[name] = id
names[id] = name
end
function library.name(id)
return names[id]
end
function library.index(name)
return indices[name]
end
end
cache_names(block)
cache_names(item)
+171 -18
View File
@@ -9,6 +9,87 @@ function sleep(timesec)
end
end
function tb_frame_tostring(frame)
local s = frame.short_src
if frame.what ~= "C" then
s = s .. ":" .. tostring(frame.currentline)
end
if frame.what == "main" then
s = s .. ": in main chunk"
elseif frame.name then
s = s .. ": in function " .. utf8.escape(frame.name)
end
return s
end
local function complete_app_lib(app)
app.sleep = sleep
app.script = __VC_SCRIPT_NAME
app.new_world = core.new_world
app.open_world = core.open_world
app.save_world = core.save_world
app.close_world = core.close_world
app.reopen_world = core.reopen_world
app.delete_world = core.delete_world
app.reconfig_packs = core.reconfig_packs
app.get_setting = core.get_setting
app.set_setting = core.set_setting
app.tick = coroutine.yield
app.get_version = core.get_version
app.get_setting_info = core.get_setting_info
app.load_content = core.load_content
app.reset_content = core.reset_content
function app.config_packs(packs_list)
-- Check if packs are valid and add dependencies to the configuration
packs_list = pack.assemble(packs_list)
local installed = pack.get_installed()
local toremove = {}
for _, packid in ipairs(installed) do
if not table.has(packs_list, packid) then
table.insert(toremove, packid)
end
end
local toadd = {}
for _, packid in ipairs(packs_list) do
if not table.has(installed, packid) then
table.insert(toadd, packid)
end
end
app.reconfig_packs(toadd, toremove)
end
function app.quit()
local tb = debug.get_traceback(1)
local s = "app.quit() traceback:"
for i, frame in ipairs(tb) do
s = s .. "\n\t"..tb_frame_tostring(frame)
end
debug.log(s)
core.quit()
coroutine.yield()
end
function app.sleep_until(predicate, max_ticks)
max_ticks = max_ticks or 1e9
local ticks = 0
while ticks < max_ticks and not predicate() do
app.tick()
ticks = ticks + 1
end
if ticks == max_ticks then
error("max ticks exceed")
end
end
end
if app then
complete_app_lib(app)
elseif __vc_app then
complete_app_lib(__vc_app)
end
------------------------------------------------
------------------- Events ---------------------
------------------------------------------------
@@ -54,7 +135,12 @@ function events.emit(event, ...)
return nil
end
for _, func in ipairs(handlers) do
result = result or func(...)
local status, newres = xpcall(func, __vc__error, ...)
if not status then
debug.error("error in event ("..event..") handler: "..newres)
else
result = result or newres
end
end
return result
end
@@ -85,7 +171,7 @@ function Document.new(docname)
end
local _RadioGroup = {}
function _RadioGroup.set(self, key)
function _RadioGroup:set(key)
if type(self) ~= 'table' then
error("called as non-OOP via '.', use radiogroup:set")
end
@@ -98,7 +184,7 @@ function _RadioGroup.set(self, key)
self.callback(key)
end
end
function _RadioGroup.__call(self, elements, onset, default)
function _RadioGroup:__call(elements, onset, default)
local group = setmetatable({
elements=elements,
callback=onset,
@@ -114,20 +200,8 @@ _GUI_ROOT = Document.new("core:root")
_MENU = _GUI_ROOT.menu
menu = _MENU
local __post_runnables = {}
function __process_post_runnables()
if #__post_runnables then
for _, func in ipairs(__post_runnables) do
func()
end
__post_runnables = {}
end
end
function time.post_runnable(runnable)
table.insert(__post_runnables, runnable)
end
local gui_util = require "core:gui_util"
__vc_page_loader = gui_util.load_page
--- Console library extension ---
console.cheats = {}
@@ -272,7 +346,6 @@ function __vc_on_hud_open()
_rules.create("allow-content-access", hud._is_content_access(), function(value)
hud._set_content_access(value)
input.set_enabled("player.pick", value)
end)
_rules.create("allow-flight", true, function(value)
input.set_enabled("player.flight", value)
@@ -328,6 +401,86 @@ function __vc_on_world_quit()
_rules.clear()
end
local __vc_coroutines = {}
local __vc_named_coroutines = {}
local __vc_next_coroutine = 1
local __vc_coroutine_error = nil
function __vc_start_coroutine(chunk)
local co = coroutine.create(function()
local status, err = pcall(chunk)
if not status then
__vc_coroutine_error = err
end
end)
local id = __vc_next_coroutine
__vc_next_coroutine = __vc_next_coroutine + 1
__vc_coroutines[id] = co
return id
end
function __vc_resume_coroutine(id)
local co = __vc_coroutines[id]
if co then
coroutine.resume(co)
if __vc_coroutine_error then
debug.error(__vc_coroutine_error)
error(__vc_coroutine_error)
end
return coroutine.status(co) ~= "dead"
end
return false
end
function __vc_stop_coroutine(id)
local co = __vc_coroutines[id]
if co then
if coroutine.close then
coroutine.close(co)
end
__vc_coroutines[id] = nil
end
end
function start_coroutine(chunk, name)
local co = coroutine.create(function()
local status, error = xpcall(chunk, __vc__error)
if not status then
debug.error(error)
end
end)
__vc_named_coroutines[name] = co
end
local __post_runnables = {}
function __process_post_runnables()
if #__post_runnables then
for _, func in ipairs(__post_runnables) do
local status, result = xpcall(func, __vc__error)
if not status then
debug.error("error in post_runnable: "..result)
end
end
__post_runnables = {}
end
local dead = {}
for name, co in pairs(__vc_named_coroutines) do
coroutine.resume(co)
if coroutine.status(co) == "dead" then
table.insert(dead, name)
end
end
for _, name in ipairs(dead) do
__vc_named_coroutines[name] = nil
end
end
function time.post_runnable(runnable)
table.insert(__post_runnables, runnable)
end
assets = {}
assets.load_texture = core.__load_texture
+19 -2
View File
@@ -34,11 +34,11 @@ end
function timeit(iters, func, ...)
local tm = time.uptime()
local tm = os.clock()
for i=1,iters do
func(...)
end
print("[time mcs]", (time.uptime()-tm) * 1000000)
print("[time mcs]", (os.clock()-tm) * 1000000)
end
----------------------------------------------
@@ -361,3 +361,20 @@ function __vc_warning(msg, detail, n)
"core:warning", msg, detail, debug.get_traceback(1 + (n or 0)))
end
end
function file.name(path)
return path:match("([^:/\\]+)$")
end
function file.stem(path)
local name = file.name(path)
return name:match("(.+)%.[^%.]+$") or name
end
function file.ext(path)
return path:match("%.([^:/\\]+)$")
end
function file.prefix(path)
return path:match("^([^:]+)")
end
+1
View File
@@ -34,6 +34,7 @@ graphics.dense-render.tooltip=Включает прозрачность блок
menu.Apply=Применить
menu.Audio=Звук
menu.Back to Main Menu=Вернуться в Меню
menu.Scripts=Сценарии
menu.Content Error=Ошибка Контента
menu.Content=Контент
menu.Continue=Продолжить
+2 -2
View File
@@ -17,10 +17,10 @@ Console=Konsol
Log=log
Problems=Muammolar
Monitor=Monitoring
Debug=Xatolarni tuzatish (Debug)
Debug=Debug
File=Fayl
devtools.traceback=Chaqiruvlar steki (songgisidan boshlab)
devtools.traceback=Chaqiruvlar steki (so`nggisidan boshlab)
error.pack-not-found=Paketni topib bo'lmadi
error.dependency-not-found=Amaldagi qaramliklar topilmadi
pack.remove-confirm=Paketlar bilan taqdim etilgan barcha contentni dunyodan olib tashlash (qaytarib bo'lmaydi)?