From 08dfb6e30aa09356a86860556ea9144ca0cfec99 Mon Sep 17 00:00:00 2001 From: Igor Timofeev Date: Thu, 14 Jun 2018 21:46:00 +0300 Subject: [PATCH] aefaefaef --- Applications/Robot/VRScanComputer.lua | 112 +++++++++++++++++++------- Applications/Robot/VRScanRobot.lua | 78 +++++++++++++----- Applications/Robot/advancedRobot.lua | 16 +++- Applications/Robot/commander.lua | 2 + 4 files changed, 154 insertions(+), 54 deletions(-) diff --git a/Applications/Robot/VRScanComputer.lua b/Applications/Robot/VRScanComputer.lua index b8b59375..9a12bc87 100644 --- a/Applications/Robot/VRScanComputer.lua +++ b/Applications/Robot/VRScanComputer.lua @@ -12,12 +12,21 @@ local modem = component.modem local port = 512 config = { - offsetX = 0, - offsetY = 0, - offsetZ = 0, + glassesX = 0, + glassesY = 0, + glassesZ = 0, + robotX = 0, + robotY = 0, + robotZ = 0, + width = 3, + height = 1, + length = 3, + radius = 16, + minDensity = 0.2, + maxDensity = 10, } -local configPath = MineOSPaths.applicationData .. "VRScan.cfg" +local configPath = MineOSPaths.applicationData .. "VRScan4.cfg" if filesystem.exists(configPath) then config = table.fromFile(configPath) end @@ -33,57 +42,100 @@ mainContainer:addChild(GUI.panel(1, 1, mainContainer.width, mainContainer.height local layout = mainContainer:addChild(GUI.layout(1, 1, mainContainer.width, mainContainer.height, 1, 1)) -local offsetXInput = layout:addChild(GUI.input(1, 1, 36, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, tostring(config.offsetX), "Robot offset by X")) +local width = 39 -local offsetYInput = layout:addChild(GUI.input(1, 1, 36, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, tostring(config.offsetY), "Robot offset by Y")) +local function addCoords(v1, v2, v3, t1, t2, t3) + local subLayout = layout:addChild(GUI.layout(1, 1, width, 3, 1, 1)) + subLayout:setDirection(1, 1, GUI.DIRECTION_HORIZONTAL) + subLayout:setAlignment(1, 1, GUI.ALIGNMENT_HORIZONTAL_LEFT, GUI.ALIGNMENT_VERTICAL_TOP) -local offsetZInput = layout:addChild(GUI.input(1, 1, 36, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, tostring(config.offsetZ), "Robot offset by Z")) + local width = math.floor((width - 2) / 3) + return + subLayout:addChild(GUI.input(1, 1, width, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, v1, t1)), + subLayout:addChild(GUI.input(1, 1, width, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, v2, t2)), + subLayout:addChild(GUI.input(1, 1, width, 3, 0xE1E1E1, 0x787878, 0xB4B4B4, 0xE1E1E1, 0x2D2D2D, v3, t3)) +end -local widthSlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, 3, false, "Width: ", "")) +local glassesXInput, glassesYInput, glassesZInput = addCoords(tostring(config.glassesX), tostring(config.glassesY), tostring(config.glassesZ), "Glasses X", "Glasses Y", "Glasses Z") + +local robotXInput, robotYInput, robotZInput = addCoords(tostring(config.robotX), tostring(config.robotY), tostring(config.robotZ), "Robot X", "Robot Y", "Robot Z") + +local widthSlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, config.width, false, "Width: ", "")) widthSlider.height = 2 widthSlider.roundValues = true -local heightSlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, 3, false, "Height: ", "")) +local heightSlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, config.height, false, "Height: ", "")) heightSlider.height = 2 heightSlider.roundValues = true -local lengthSlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, 3, false, "Length: ", "")) +local lengthSlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, config.length, false, "Length: ", "")) lengthSlider.height = 2 -heightSlider.roundValues = true +lengthSlider.roundValues = true -local radiusSlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 10, 3, false, "Radius: ", "")) +local radiusSlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 1, 24, config.radius, false, "Radius: ", "")) radiusSlider.height = 2 radiusSlider.roundValues = true -local minDensitySlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 0, 10, 0.5, false, "Min density: ", "")) +local minDensitySlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 0, 10, config.minDensity, false, "Min density: ", "")) minDensitySlider.height = 2 -local maxDensitySlider = layout:addChild(GUI.slider(1, 1, 36, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 0, 10, 0.5, false, "Max density: ", "")) +local maxDensitySlider = layout:addChild(GUI.slider(1, 1, width, 0x66DB80, 0xE1E1E1, 0xFFFFFF, 0xB4B4B4, 0, 10, config.maxDensity, false, "Max density: ", "")) maxDensitySlider.height = 2 -layout:addChild(GUI.button(1, 1, 36, 3, 0xC3C3C3, 0xFFFFFF, 0x969696, 0xFFFFFF, "Scan")).onTouch = function() - config.offsetX, config.offsetY, config.offsetZ = tonumber(offsetXInput.text), tonumber(offsetYInput.text), tonumber(offsetZInput.text) +local function saveConfig() + config.glassesX = tonumber(glassesXInput.text) + config.glassesY = tonumber(glassesYInput.text) + config.glassesZ = tonumber(glassesZInput.text) + config.robotX = tonumber(robotXInput.text) + config.robotY = tonumber(robotYInput.text) + config.robotZ = tonumber(robotZInput.text) + config.width = math.floor(widthSlider.value) + config.height = math.floor(heightSlider.value) + config.length = math.floor(lengthSlider.value) + config.radius = math.floor(radiusSlider.value) + config.minDensity = minDensitySlider.value + config.maxDensity = maxDensitySlider.value + table.toFile(configPath, config) +end + +layout:addChild(GUI.button(1, 1, width, 3, 0xC3C3C3, 0xFFFFFF, 0x969696, 0xFFFFFF, "Scan")).onTouch = function() + saveConfig() - broadcast( - "scan", - config.offsetX, - config.offsetY, - config.offsetZ, - math.floor(widthSlider.value), - math.floor(heightSlider.value), - math.floor(lengthSlider.value), - math.floor(radiusSlider.value), - minDensitySlider.value, - maxDensitySlider.value - ) + broadcast("scan", table.toString({ + width = config.width, + height = config.height, + length = config.length, + radius = config.radius, + minDensity = config.minDensity, + maxDensity = config.maxDensity + })) + + glasses.removeAll() end layout.eventHandler = function(mainContainer, layout, e1, e2, e3, e4, e5, e6, e7, e8, e9, e10, e11, e12) if e1 == "modem_message" and e6 == "VRScan" then if e7 == "result" then - local robotX, robotY, robotZ, result = e[8], e[9], e[10], serialization.unserialize(e[11]) - GUI.alert("Got result from " .. robotX .. "x" .. robotY .. robotZ .. " with size " .. #result) + local result = table.fromString(e8) + + for x in pairs(result.blocks) do + for y in pairs(result.blocks[x]) do + for z in pairs(result.blocks[x][y]) do + for i = 1, #result.blocks[x][y][z] do + local cube = glasses.addCube3D() + cube.setVisibleThroughObjects(true) + cube.setColor(0, 0.6, 1) + cube.setAlpha(0.5) + cube.set3DPos( + config.robotX - config.glassesX + result.x + x, + config.robotY - config.glassesY + result.y + y, + config.robotZ - config.glassesZ + result.z + z + ) + end + end + end + end end end end diff --git a/Applications/Robot/VRScanRobot.lua b/Applications/Robot/VRScanRobot.lua index 20ba8fdc..af0e3195 100644 --- a/Applications/Robot/VRScanRobot.lua +++ b/Applications/Robot/VRScanRobot.lua @@ -9,52 +9,86 @@ AR.proxies.modem.open(port) -------------------------------------------------------------------------------- local function broadcast(...) - modem.broadcast(port, "VRScan", ...) + AR.proxies.modem.broadcast(port, "VRScan", ...) +end + +local function round(num, decimalPlaces) + local mult = 10 ^ (decimalPlaces or 0) + return math.floor(num * mult + 0.5) / mult end local function move(x, y, z) print("Moving to next chunk with offset " .. x .. "x" .. y .. "x" .. z) - AR.moveToPosition(AR.robotPositionX + x, AR.robotPositionY + y, AR.robotPositionZ + z) + AR.moveToPosition(AR.positionX + x, AR.positionY + y, AR.positionZ + z) end +print("Waiting for modem commands...") + while true do local e = {event.pull()} if e[1] == "modem_message" and e[6] == "VRScan" then if e[7] == "scan" then - print("Scanning started") - - local width, height, length, radius, minDensity, maxDensity = e[8], e[9], e[10], e[11], e[12], e[13] + local settings = serialization.unserialize(e[8]) - for h = 1, height do - for w = 1, width do - for l = 1, length do + print("Scanning with paramerers: " .. e[8]) + + local h, w, l, startX, startY, startZ = 0, 0, 0, AR.positionX, AR.positionY, AR.positionZ + + local function move() + local distance = settings.radius * 2 + 1 + local moveX, moveZ = AR.getRotatedPosition(w * distance, l * distance) + + AR.moveToPosition( + startX + moveX, + startY + h * distance, + startZ + moveZ + ) + end + + while h < settings.height do + while w < settings.width do + while l < settings.length do print("Scanning chunk " .. w .. " x " .. h .. " x " .. l) - local result, column = {} - for z = -radius, radius do - for x = -radius, radius do + local result, column = { + x = AR.positionX, + y = AR.positionY, + z = AR.positionZ, + blocks = {} + } + + local blockCount = 0 + for z = -settings.radius, settings.radius do + for x = -settings.radius, settings.radius do column = AR.proxies.geolyzer.scan(x, z) - for i = 1, #column do - if column[i] >= minDensity and column[i] <= maxDensity then - table.insert(result, AR.robotPositionX) - table.insert(result, AR.robotPositionY) - table.insert(result, AR.robotPositionZ) - table.insert(result, column[i]) + + for i = 32 - settings.radius, 32 + settings.radius do + if column[i] >= settings.minDensity and column[i] <= settings.maxDensity then + local y = i - 33 + result.blocks[x] = result.blocks[x] or {} + result.blocks[x][y] = result.blocks[x][y] or {} + result.blocks[x][y][z] = result.blocks[x][y][z] or {} + table.insert(result.blocks[x][y][z], round(column[i], 2)) + + blockCount = blockCount + 1 end end end end - print("Scanning finished. Sending result with size: " .. #result) - broadcast("result", AR.robotPositionX, AR.robotPositionY, AR.robotPositionZ, serialization.serialize(result)) + print("Scanning finished. Sending result with blocks size: " .. blockCount) + broadcast("result", serialization.serialize(result)) - move(0, 0, radius + 1) + l = l + 1 + move() end - move(radius + 1, 0, 0) + w = w + 1 + move() end - move(0, radius + 1, 0) + h = h + 1 + move() end end end diff --git a/Applications/Robot/advancedRobot.lua b/Applications/Robot/advancedRobot.lua index bae294f2..34f3c15d 100644 --- a/Applications/Robot/advancedRobot.lua +++ b/Applications/Robot/advancedRobot.lua @@ -58,6 +58,18 @@ AR.rotation = 0 -------------------------------------------------------------------------------- +function AR.getRotatedPosition(x, z) + if AR.rotation == 0 then + return x, z + elseif AR.rotation == 1 then + return -z, x + elseif AR.rotation == 2 then + return -x, -z + else + return z, -x + end +end + function AR.updateProxies() local name for name in pairs(AR.requiredProxies) do @@ -342,7 +354,7 @@ function AR.checkEnergyStatus() if computer.energy() / computer.maxEnergy() < AR.zeroPositionReturnEnergy then print("Low energy level detected") -- Запоминаем старую позицию, шобы суда вернуться - local oldPosition = AR.getRobotPosition() + local x, y, z = AR.positionX, AR.positionY, AR.positionZ -- Пиздуем на базу за зарядкой AR.moveToZeroPosition() -- Заряжаемся, пока энергия не достигнет более-менее максимума @@ -351,7 +363,7 @@ function AR.checkEnergyStatus() os.sleep(1) end -- Пиздуем обратно - AR.moveToPosition(oldPosition.x, oldPosition.y, oldPosition.z) + AR.moveToPosition(x, y, z) AR.turnToRotation(oldPosition.rotation) end end diff --git a/Applications/Robot/commander.lua b/Applications/Robot/commander.lua index fc69b148..a96efd61 100644 --- a/Applications/Robot/commander.lua +++ b/Applications/Robot/commander.lua @@ -28,6 +28,8 @@ local function execute(symbol) print("Swinging:", AR.swingForward()) elseif symbol == "e" then print("Swinging:", AR.useForward()) + elseif symbol == "." then + print("Returning to start:", AR.moveToZeroPosition()) end end