Advertisement
Guest User

Untitled

a guest
May 22nd, 2015
231
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
  1. -- Variable definitions
  2. local valve, monitor, screenw, screenh
  3. local serverID = nil
  4. local clients = {}
  5. local args = {...}
  6. local redlimit, redside, on
  7. local sides = {"left", "right", "top", "bottom", "front", "back"};
  8.  
  9. ----------------------------------------------------
  10. -- Function definitions
  11. ----------------------------------------------------
  12. local liquidColors = {{"Water", colors.blue },
  13.                                         {"tile.oilStill", colors.gray, "Oil"},
  14.                                         {"Creosote Oil", colors.brown},
  15.                                         {"Essence", colors.lime},
  16.                                         {"Steam", colors.lightGray},
  17.                                         {"Honey", colors.yellow},
  18.                                         {"Ethanol", colors.orange},
  19.                                         {"Lava", colors.orange},
  20.                                         {"item.fuel", colors.yellow, "Fuel"},
  21.                                         {"Biomass", colors.green},
  22.                                         {"Fortron", colors.lightBlue},
  23.                                         {"Sludge", colors.black},
  24.                                         {"Liquid DNA", colors.magenta},
  25.                                         {"Fruit Juice", colors.green},
  26.                                         {"Seed Oil", colors.yellow},
  27.                                         {"Liquid Force", colors.yellow},
  28.                                         {"Oil", colors.black, "Oil"},
  29.                                         {"Fuel", colors.yellow, "Fuel"},
  30.                                         {"uumatter", colors.purple, "UUMatter"},
  31.                                         {"vegetable", colors.magenta, "Veg"},
  32.                                         {"deuterium", colors.lightBlue, "Deuterium"},
  33. --liquid names for OpenPeripherals 0.2.1 by AmigaLink
  34.                                         {"creosote", colors.brown, "Creosote Oil"},
  35.                                         {"essence", colors.lime, "Essence"},
  36.                                         {"steam", colors.lightGray, "Steam"},
  37.                                         {"honey", colors.yellow, "Honey"},
  38.                                         {"bioethanol", colors.orange, "Ethanol"},
  39.                                         {"lava", colors.orange, "Lava"},
  40.                                         {"biomass", colors.green, "Biomass"},
  41.                                         {"fortron", colors.lightBlue, "Fortron"},
  42.                                         {"sludge", colors.black, "Sludge"},
  43.                                         {"liquiddna", colors.magenta, "Liquid DNA"},
  44.                                         {"fruitjuice", colors.green, "Fruit Juice"},
  45.                                         {"seedoil", colors.yellow, "Seed Oil"},
  46.                                         {"xpjuice", colors.lime, "XP Juice"},
  47.                                         {"liquidforce", colors.yellow, "Liquid Force"},
  48.                                         {"oil", colors.gray, "Oil"},
  49.                                         {"fuel", colors.yellow, "Fuel"},
  50.                                         {"milk", colors.white, "Milk"},
  51. -- Life Essence suggested by Fyrhtu
  52.                                         {"life essence", colors.red, "Life Essence"},
  53. -- My liquids
  54.                                         {"nitrofuel", colors.green, "Nitrofuel"}
  55.                                 }
  56.  
  57. local function getLiquidColor(liquid)
  58.     for c, color in pairs (liquidColors) do
  59.         if (liquid == color[1]) then
  60.                 return color[2],color[3] or liquid
  61.         end
  62.     end
  63.     return colors.white, liquid;
  64. end
  65.  
  66. local function getDeviceSide(deviceType)
  67.         for i,side in pairs(sides) do
  68.                 if (peripheral.isPresent(side)) then
  69.                         if (peripheral.getType(side)) == string.lower(deviceType) then
  70.                                         return side;
  71.                         end
  72.                 end
  73.         end
  74. end
  75.  
  76. local function showLevel(count,max,filled,color,label, amt, threshold, signal)
  77.         local screenw, screenh = monitor.getSize() / 4
  78.         max = max + 1
  79.         if (not screenw) then
  80.                 return nil;
  81.                 -- monitor has been broken
  82.         end
  83.        
  84.       local starty = screenh -  math.floor((screenh * filled))
  85.       local width  = math.ceil(screenw / max + .5)
  86.       local offset = math.ceil(width * (count - 1))
  87.         local amtw = string.len(amt)
  88.         local thresholdy = (threshold and ( screenh - ((threshold / 100) * screenh)))
  89.        
  90.         if (count == max) then
  91.         --  the final column should use up the remaining space.  A hack!
  92.                 width = screenw - offset
  93.         end
  94.         --truncate the label to the width of the bar.
  95.         label = string.sub(label, 1, math.max((width - 1), 0))
  96.  
  97.         if (thresholdy and thresholdy < 1) then
  98.                 thresholdy = 1
  99.         else
  100.                 if (thresholdy and thresholdy > screenh) then
  101.                         thresholdy = screenh
  102.                 end
  103.         end
  104.  
  105.       term.redirect(monitor)
  106.       for c=starty, screenh + 1, 1 do
  107.             for line=0, width, 1 do
  108.                         paintutils.drawPixel(line + offset, c, color)
  109.             end
  110.       end
  111.         if (thresholdy) then
  112.                 local thresholdColor = color
  113.                 for line=0, width, 1 do
  114.                         thresholdColor = color
  115.                         if (signal) then
  116.                                         thresholdColor = colors.red
  117.                         else
  118.                                         -- makes a dotted line when there is no redstone signal
  119.                                         if (line % 2 == 0) then
  120.                                                 thresholdColor = colors.red
  121.                                         end
  122.                         end
  123.                         paintutils.drawPixel(line + offset, thresholdy, thresholdColor)
  124.             end
  125.         end
  126.  
  127.         monitor.setBackgroundColor(color)
  128.         if (color == colors.white) then
  129.                 monitor.setTextColor(colors.black)
  130.         end
  131.        
  132.         labely = math.min((starty + 1), screenh - 1)
  133.         monitor.setCursorPos(offset + 1, labely)
  134.         write(label)
  135.        
  136.         if (amtw <= width) then
  137.                 amty = math.min(labely + 1, screenh)
  138.                 monitor.setCursorPos(offset + 1, amty)
  139.                 write(amt)
  140.         end
  141.         monitor.setTextColor(colors.white)
  142.   --    term.restore()
  143. end
  144.  
  145. local function tankStats(tank)
  146.         if(tank) then
  147.                 local amt = tank["amount"]
  148.                 local size = tank["capacity"]
  149.                 local filled = (amt and 1 / (size / amt)) or 0
  150.                 return amt, size, filled
  151.         else
  152.                 return nil;
  153.         end
  154. end
  155.  
  156. local function tableCount(t)
  157.         local total=0
  158.         for k,v in pairs (t) do
  159.                 total = total + 1
  160.         end
  161.         return total
  162. end
  163.  
  164. local function updateDisplay()
  165.         local total = tableCount(clients)
  166.         local count = 1
  167.  
  168.         monitor.setBackgroundColor(colors.black)
  169.         monitor.setTextScale(.5)
  170.         monitor.clear()
  171.    
  172.         for ix,client in pairs (clients) do
  173.                 local tank = client[1]
  174.                 local threshold = client[2]
  175.                 local signalOn = client[3]
  176.                 local amt,size,filled = tankStats(tank)
  177.                 local kind = tank["name"]
  178.                 local color,name = getLiquidColor(kind)
  179.                 local unit = ""
  180.                 local amount = math.max(amt or 0, 0)
  181.    
  182.                 if (amount > 1000000) then
  183.                         unit="M"
  184.                         amount=string.format("%.2f", math.floor(amt / 1000) / 1000)
  185.                 else
  186.                         if(amount > 0) then
  187.                           unit="K"
  188.                           amount=string.format("%.2f", amt / 1000)
  189.                         else
  190.                           amount = ""
  191.                         end
  192.                 end
  193.                 amount = amount..unit
  194.                 showLevel(count, total, filled, color, name or "Empty", amount, threshold, signalOn)
  195.                 count = count + 1    
  196.         end
  197.         return nil;
  198. end
  199.  
  200. local function broadcast ()
  201.         term.clear()
  202.         term.setCursorPos(1,1)
  203.         print("_____________ tankmon Server started __________")
  204.         print("Broadcasting that tank display is available...")
  205.         print("Hold Ctrl+T to Terminate.")
  206.         while true do
  207.                 rednet.broadcast(os.getComputerID())
  208.                 -- term.setCursorPos(1, 5)
  209.                 -- term.clearLine()
  210.                 -- write("Connected tankmon clients: " .. tostring(tableCount(clients)))
  211.                 sleep(7)
  212.         end
  213. end
  214.  
  215. local function receive()
  216.     while true do
  217.       local senderID, message, distance = rednet.receive()
  218.       if (message) then
  219.                 local data = textutils.unserialize(message)
  220.                 clients[senderID] = data
  221.     end
  222.   end
  223. end
  224.  
  225. local function display()
  226.         while true do
  227.                 updateDisplay()
  228.                 sleep(1.5)
  229.         end
  230. end
  231.  
  232. local function connect()
  233.         print("Looking for a tankmon server in wireless Rednet range...")
  234.         while true do
  235.                 local senderID, message, distance = rednet.receive()
  236.                 serverID = senderID
  237.                 print("Connected to server " .. tostring(serverID))
  238.                 sleep(3)
  239.   end  
  240. end
  241.  
  242. local function publishTank()
  243.       while true do
  244.             if serverID then
  245.                         term.clear()
  246.                         term.setCursorPos(1,1)
  247.                 print("** Sending out tank information **")
  248.                 local tank = valve.getTankInfo("unknown")[1]
  249.                         -- establish whether redstone signal should be sent
  250.                         local amt,size,pctFilled = tankStats(tank)
  251.                         on = false
  252.                         local filled = pctFilled * 100
  253.                         if (filled and redlimit and redlimit==0 and filled==0) then
  254.                                 on = true
  255.                         else
  256.                                 if(filled and redlimit and filled <= redlimit) then
  257.                                         on=true
  258.                                 end
  259.                         end
  260.                         if(redside) then
  261.                                 rs.setOutput(redside, on)
  262.                         end
  263.                         -- use rednet to update the server with this tank's info.
  264.                         local info = {tank, redlimit, on}
  265.                         if (redlimit and redside) then
  266.                                 print("Redstone threshold: " .. tostring(redlimit))
  267.                                 print("Redstone output side: " .. redside)
  268.                                 print("Redstone signal on: " .. tostring(on))
  269.                                 print("")
  270.                         end
  271.                         term.clearLine()
  272.                         write("** Tank contains: " .. tostring(amt))
  273.             rednet.send(serverID, textutils.serialize(info), false)            
  274.                 end
  275.                 sleep(math.random(1,5))
  276.     end
  277. end
  278.  
  279. ---------------------------------------
  280. --the Main
  281. ---------------------------------------
  282. local modemSide = getDeviceSide("modem");
  283.  
  284. if (modemSide) then
  285.       local modem = peripheral.wrap(modemSide)
  286. else
  287.       error("A wireless modem must be attached to this computer.")
  288. end
  289.  
  290. local tankSide = getDeviceSide("iron_tank_valve");
  291. local tankSide2 = getDeviceSide("steel_tank_valve");
  292. local tankSide3 = getDeviceSide("rcsteeltankvalvetile");
  293. local tankSide4 = getDeviceSide("rcirontankvalvetile");
  294. local finalside = tankSide or tankSide2 or tankSide3 or tankSide4
  295. local screenSide = getDeviceSide("monitor");
  296.  
  297. if (finalside and screenSide) then
  298.       error("Either a screen or a tank valve can be connected, not both.")
  299. end
  300.  
  301. if finalside  then
  302.       valve = peripheral.wrap(finalside )
  303. end
  304.  
  305. if (screenSide) then
  306.       monitor = peripheral.wrap(screenSide)
  307.         if(not monitor.isColor()) then
  308.                 error("The attached monitor must be Advanced.  Get some gold!")
  309.         end
  310.     screenw, screenh = monitor.getSize()
  311.     monitor.clear()
  312. end
  313.  
  314. rednet.open(modemSide)
  315. if (valve) then
  316.       -- client mode
  317.         redlimit = args[1]
  318.         redside = args[2]
  319.         if (redlimit and not redside) then
  320.                 print("A threshold and redstone side must both be present.")
  321.                 print("e.g. tankmon 100 top")
  322.                 error()
  323.         end
  324.         if (redlimit) then
  325.                 redlimit = tonumber(redlimit)
  326.                 print("")
  327.                 print("Tank will send redstone signal at or below " .. tostring(redlimit) .. "% on side " .. redside)
  328.         end
  329.         -- clear outstanding redstone signals.
  330.         for i,side in pairs(sides) do
  331.                 rs.setOutput(side, false)
  332.         end
  333.     parallel.waitForAll(connect, publishTank)
  334. else
  335.       -- server mode
  336.       parallel.waitForAll(broadcast, receive, display)
  337. end
  338. rednet.close(modemSide)
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement