-- TurbineMonitor -- Made By: MrKMG -- -- This program will keep your turbines up to speed -- and turn the coil on and off as needed. -- -- To Use: -- -- Attach as many Turbines and Monitors as you -- would like via wired modems. Monitors will all -- display the same information for each turbine: -- Current Speed -- Current Power Generation, -- Coil On/Off -- Flow On/Off -- -- Monitors can be of any size -- --Edit these to fit your turbines -- Speed to keep rotors between. Recommend putting -- just above the best your turbine can do. minSpeed = 1800 maxSpeed = 1820 -- Range of RF to keep in turbine. Recommend to -- keep low to avoid waste. minEnergy = 1 maxEnergy = 200000 -- Colors for the monitor uiColors = {} uiColors["background"] = colors.gray uiColors["border"] = colors.black uiColors["headerBackground"] = colors.blue uiColors["headerText"] = colors.black uiColors["currentSpeedBackground"] = colors.black uiColors["currentSpeedText"] = colors.white uiColors["currentPowerGenBackground"] = colors.black uiColors["currentPowerGenText"] = colors.white uiColors["coilOnBackground"] = colors.green uiColors["coilOnText"] = colors.white uiColors["coilOffBackground"] = colors.red uiColors["coilOffText"] = colors.white uiColors["flowOnBackground"] = colors.green uiColors["flowOnText"] = colors.white uiColors["flowOffBackground"] = colors.red uiColors["flowOffText"] = colors.white -- Text for the monitor. uiText = {} uiText["name"] = "Turbine " uiText["rpm"] = " rpm" uiText["rft"] = " RF/t" uiText["rfs"] = " RF/s" uiText["/"] = " / " uiText["flowOn"] = "Flow: On" uiText["flowOff"] = "Flow: Off" uiText["coilsOn"] = "Coils: On" uiText["coilsOff"] = "Coils: Off" uiText["title"] = "Turbine Monitor" -- Edit below at your your own risk -- !#!#!#!#!#!#!#!#!#!#!#!#!#!#!#!# function drawPixel(x, y, col) mon.setTextColor(uiColors["coilOnText"]) mon.setCursorPos(x, y) mon.setBackgroundColor(col) mon.write(" ") end function drawLine(x, y, length, col) for i = 0, length - 1 do drawPixel(x + i, y, col) end end -- Center Text local function printCenter(mon, y, txt) local w, h = mon.getSize() local x = math.floor((w / 2) - (#txt / 2)) mon.setBackgroundColor(uiColors["flowOffBackground"]) mon.setTextColor(uiColors["coilOnText"]) mon.setCursorPos(x, y) mon.write(txt) end -- Global Variables mon = peripheral.wrap("right") t = {} -- Holds turbines m = {} -- Holds monitor w = {} -- Holds windows -- Other Functions function round(num) return math.floor(num + 0.5) end -- Program Functions -- Finds all devices. Puts turbines in `t` table -- and monitors in `m` table function getDevices() for _, name in pairs(peripheral.getNames()) do if peripheral.getType(name) == "BigReactors-Turbine" then table.insert(t, peripheral.wrap(name)) end if peripheral.getType(name) == "monitor" then table.insert(m, peripheral.wrap(name)) end end end -- Determines if the coil should be turned on function needCoilOn(i) if t[i].getEnergyStored() < minEnergy then return true else return false end end -- Determines if the coil should be turned off function needCoilOff(i) if t[i].getEnergyStored() > maxEnergy then return true else return false end end -- Turns coil on function coilOn(i) t[i].setInductorEngaged(true) end -- Tuns coil off function coilOff(i) t[i].setInductorEngaged(false) end -- Checks if coil in on or off function isCoilOn(i) return t[i].getInductorEngaged() end -- Determines if flow should turn on function needFlowOn(i) if t[i].getRotorSpeed() < minSpeed then return true else return false end end -- Determines if flow should turn off function needFlowOff(i) if t[i].getRotorSpeed() > maxSpeed then return true else return false end end -- Turns flow on -- (Sets flow to MAX) function flowOn(i) t[i].setFluidFlowRateMax(t[i].getFluidFlowRateMaxMax()) end -- Turns flow off -- (Sets flow to 0) function flowOff(i) t[i].setFluidFlowRateMax(0) end -- Checks if flow is on or off -- (Assumes MAX is on, other is off) function isFlowOn(i) return t[i].getFluidFlowRateMax() == t[i].getFluidFlowRateMaxMax() end -- Get Rotor Speed function getRotorSpeed(i) return math.floor(t[i].getRotorSpeed()) end -- Get Power Generation function getPowerGeneration(i) return math.floor(t[i].getEnergyProducedLastTick()) end -- Get Sum Power Generation function getSumPowerGeneration() local sum = 0 for i = 1, #t ,1 do sum = sum + getPowerGeneration(i) end return sum end function getSumPowerGeneration20() local sum = 0 for i = 1, #t ,1 do sum = getSumPowerGeneration() * 20 end return sum end -- Returns text scale for best fit -- TODO Figure out if there is a better way than -- brute forcing function getScaleForBox(baseWidth, baseHeight, fitWidth, fitHeight, count) local best = 0.5 for i = best, 5, 0.5 do local cWidth = baseWidth / i local cHeight = baseHeight / i local cPerRow = math.floor(cWidth / fitWidth) local cPerCol = math.floor(cHeight / fitHeight) if cPerRow * cPerCol >= count then best = i else break end end return best end -- Determins offset to center the windows in the -- monitor. function getOffsetForWindow(monitorWidth, monitorHeight, desiredWidth, desiredHeight, count) local columnsNeeded = math.min(math.floor(monitorWidth / desiredWidth), count) local rowsNeeded = math.ceil(count / columnsNeeded) local widthUsed = desiredWidth * columnsNeeded local heightUsed = desiredHeight * rowsNeeded local offsetLeft = math.ceil((monitorWidth - widthUsed) / 2) local offsetRight = math.ceil((monitorHeight - heightUsed) / 2) return offsetLeft, offsetRight end -- Clears each connected monitor function clearMonitors() for i = 1, #m do m[i].setBackgroundColor(uiColors["border"]) m[i].clear() end end -- Setup each monitor -- (Put a window in each monitor for each turbine) function setupMonitors() if #t > 0 then local monitorWidth local monitorHeight local desiredW = 14 local desiredH = 8 local currentX local currentY for i = 1, #m do print("Setting Up " .. i) table.insert(w, {}) m[i].setTextScale(1) monitorWidth, monitorHeight = m[i].getSize() print("Initial Size: " .. monitorWidth .. " " .. monitorHeight) scale = getScaleForBox(monitorWidth, monitorHeight, desiredW, desiredH, #t) print("Scale: " .. scale) m[i].setTextScale(scale) monitorWidth, monitorHeight = m[i].getSize() offsetX, offsetY = getOffsetForWindow(monitorWidth, monitorHeight, desiredW, desiredH, #t) print("Offset: " .. offsetX .. " " .. offsetY) currentX = offsetX currentY = offsetY for ii = 1, #t do print(currentX .. " " .. currentY .. " " .. desiredW .. " " .. desiredH) table.insert(w[i], window.create(m[i], currentX, currentY, desiredW, desiredH)) currentX = currentX + desiredW if (currentX + desiredW > monitorWidth) then currentX = offsetX currentY = currentY + desiredH end end end end end -- Write status of turn to window function writeStatus(turbine, screen) screen.setBackgroundColor(uiColors["border"]) screen.clear() -- Write Title screen.setBackgroundColor(uiColors["headerBackground"]) screen.setTextColor(uiColors["headerText"]) screen.setCursorPos(2, 2) screen.clearLine() screen.write(uiText["name"] .. turbine) --Filler screen.setBackgroundColor(uiColors["background"]) screen.setCursorPos(1, 3) screen.clearLine() -- Write Rotor Speed screen.setBackgroundColor(uiColors["currentSpeedBackground"]) screen.setTextColor(uiColors["currentSpeedText"]) screen.setCursorPos(2, 4) screen.clearLine() screen.write(getRotorSpeed(turbine) .. uiText["rpm"]) -- Write Power Generation screen.setBackgroundColor(uiColors["currentPowerGenBackground"]) screen.setTextColor(uiColors["currentPowerGenText"]) screen.setCursorPos(2, 5) screen.clearLine() screen.write(getPowerGeneration(turbine) .. uiText["rft"]) --Filler screen.setBackgroundColor(uiColors["background"]) screen.setCursorPos(1, 6) screen.clearLine() -- Write Coil Status if isCoilOn(turbine) then screen.setBackgroundColor(uiColors["coilOnBackground"]) screen.setTextColor(uiColors["coilOnText"]) screen.setCursorPos(2, 7) screen.clearLine() screen.write(uiText["coilsOn"]) else screen.setBackgroundColor(uiColors["coilOffBackground"]) screen.setTextColor(uiColors["coilOffText"]) screen.setCursorPos(2, 7) screen.clearLine() screen.write(uiText["coilsOff"]) end -- Write Flow Status if isFlowOn(turbine) then screen.setBackgroundColor(uiColors["flowOnBackground"]) screen.setTextColor(uiColors["flowOnText"]) screen.setCursorPos(2, 8) screen.clearLine() screen.write(uiText["flowOn"]) else screen.setBackgroundColor(uiColors["flowOffBackground"]) screen.setTextColor(uiColors["flowOffText"]) screen.setCursorPos(2, 8) screen.clearLine() screen.write(uiText["flowOff"]) end -- Draw Right Border screen.setBackgroundColor(uiColors["border"]) for i = 1, 8 do screen.setCursorPos(14, i) screen.write(" ") end end -- Write status of each turbine to appropiate windows function writeStatuses() for i = 1, #m do for ii = 1, #t do writeStatus(ii, w[i][ii]) end end end -- Setup function setup() w = {} m = {} t = {} getDevices() if (#t == 0) then error("No Turbines. You did something wrong") end if (#m > 0) then clearMonitors() setupMonitors() end end -- Main Loop function main() for i = 1, #t do if isCoilOn(i) then if needCoilOff(i) then print("turning off " .. i) coilOff(i) end else if needCoilOn(i) then print("turning on " .. i) coilOn(i) end end if isFlowOn(i) then if needFlowOff(i) then print("stopping flow " .. i) flowOff(i) end else if needFlowOn(i) then print("starting flow " .. i) flowOn(i) end end end writeStatuses() end -- Program Run setup() while true do main() drawLine(1, 2, 4, colors.black) drawLine(5, 2, 69, colors.red) drawLine(74, 2, 6, colors.black) drawLine(1, 3, 4, colors.black) drawLine(5, 3, 69, colors.red) printCenter(mon, 3, uiText["title"]) drawLine(74, 3, 6, colors.black) drawLine(1, 4, 4, colors.black) drawLine(5, 4, 69, colors.red) drawLine(74, 4, 6, colors.black) drawLine(1, 48, 4, colors.black) drawLine(5, 48, 69, colors.red) drawLine(74, 48, 6, colors.black) drawLine(1, 49, 4, colors.black) drawLine(5, 49, 69, colors.red) printCenter(mon, 49, getSumPowerGeneration() .. uiText["rft"] .. uiText["/"] .. getSumPowerGeneration20() .. uiText["rfs"]) drawLine(74, 49, 6, colors.black) drawLine(1, 50, 4, colors.black) drawLine(5, 50, 69, colors.red) drawLine(74, 50, 6, colors.black) os.sleep(1) end