Advertisement
neuroticfox

Draconic Control v15.0b2 [xAID] [Lua 5.3 / 5.2]

Apr 3rd, 2025 (edited)
402
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Lua 31.70 KB | None | 0 0
  1. -- Dear Programmer:
  2. -- When we wrote this code, only god and
  3. -- us understood how it worked. And now
  4. -- only god knows.
  5. --
  6. -- Therefore, if you are trying to optimize
  7. -- this script and it fails (Very likely),
  8. -- please increase this counter for the next
  9. -- person.
  10. --
  11. -- wastedHours = 541
  12.  
  13.  :: start ::
  14.  -- Locals & Requirements
  15.     local component = require("component")
  16.     local event = require("event")
  17.     local term = require("term")
  18.     local gpu = component.gpu
  19.     local screen = component.screen
  20.     local unicode= require("unicode")
  21.     local reactorOutputMultiplier = 1
  22.     local cutoffTemp = 9005
  23.     local chaosMode = 0
  24.     local tempDrop = 0
  25.     local devMode = 0
  26.     local fieldAdj = 0
  27.     local deviation = 0
  28.     local cVar = "DEV RELEASE: Use at your own risk."
  29.     local tArgs = {...}
  30.     local Arg0 = tonumber(tArgs[1])
  31.     local Arg1 = tonumber(tArgs[2])
  32.     local Arg2 = tonumber(tArgs[3])
  33.     local Arg3 = tonumber(tArgs[4])
  34.     local Arg4 = tostring(tArgs[5])
  35.     local Arg5 = tostring(tArgs[6])
  36.     local ratioX, ratioY = screen.getAspectRatio()
  37.     local maxX, maxY = gpu.maxResolution()
  38.     gpu.setResolution(math.min(ratioX*55, maxX), math.min(ratioY*25,maxY))
  39. term.clear()
  40. term.setCursor(0, 0)
  41. os.sleep(0.5)
  42.  -- pArgs
  43. if not Arg0 then
  44. os.execute(cls)
  45. print("Draconic Control 14")
  46. print("1.12 - 1.16 Compatible-ish")
  47. print()
  48. print("dc14 [Mult] [Temp] [Field] [Mode]")
  49. print()
  50. print("Arguments")
  51. print()
  52. print("[Mult]           -   Reactor Output Multiplier")
  53. print("1.16 [10]            1.12 [1]")
  54. print()
  55. print("[Temp]           -   Desired Reactor Temperature")
  56. print("Default [8000]           Range [2500-8000]")
  57. print()
  58. print("[Field]          -   Desired Field Strength")
  59. print("Default [15]         Range [0.5-99]")
  60. print()
  61. print("[Mode]           -   Set Desired Program Mode")
  62. print("Default [1]          Range [1-3]")
  63. print("[1-3]            -   Simple, Dev, noGUI")
  64. print()
  65. print("       Compiled by BrokenSynapse & AwesomeAlec1")
  66. print()
  67. print("Thanks to Maurdekye for creating the base of this program:")
  68. print("             https://youtu.be/iLvkk41K84E")
  69. print()
  70. print(" Thanks to AwesomeAlec1 for creating the control script:")
  71. print("             https://youtu.be/CLku1ckXpeU")
  72. print()
  73. print("  Thanks to MightyPirates for being so gracious as to")
  74. print("   let me fix what they broke by never using Lua 5.3")
  75. print()
  76. print("   And a very special thanks to ZanBorg for breaking")
  77. print("      this script until it doesn't break anymore.")
  78. goto fin
  79. end
  80.  -- sArgs
  81. local reactorOutputMultiplier = Arg0
  82. local idealTemp = Arg1 or 8000
  83. local idealField = Arg2 or 15
  84. local Mode = Arg3 or 1
  85.  -- Components
  86.     if not component.isAvailable("draconic_reactor") then
  87.         print("Reactor not connected. Please connect computer to reactor with an Adapter block.")
  88.         os.exit()
  89.     end
  90.     local reactor = component.draconic_reactor
  91.     local info = reactor.getReactorInfo()
  92.     local fluxGates = {}
  93.     for x,y in pairs(component.list("flux_gate")) do
  94.         fluxGates[#fluxGates+1] = x
  95.     end
  96.     if #fluxGates < 2 then
  97.         print("Not enough flux gates connected; please connect inflow and outflow flux gates with Adapter blocks.")
  98.         os.exit()
  99.     end
  100.     local inputFlux = component.proxy(fluxGates[1])
  101.     local outputFlux = component.proxy(fluxGates[2])
  102.     outputFlux.setOverrideEnabled(true)
  103.     inputFlux.setOverrideEnabled(true)
  104.     if not inputFlux or not outputFlux then
  105.         print("Not enough flux gates connected; please connect inflow and outflow flux gates with Adapter blocks.")
  106.         os.exit()
  107.     end
  108.  -- AutoSet Gates
  109.         reactor.chargeReactor()
  110.         satOne = info.energySaturation
  111.         fieldOne = info.fieldStrength
  112.         inputFlux.setFlowOverride(1.0)
  113.         os.sleep(0.5)
  114.         satTwo = info.energySaturation
  115.         fieldTwo = info.fieldStrength
  116.         inputFlux.setFlowOverride(0.0)
  117.         reactor.stopReactor()
  118.     if satTwo <= satOne or fieldTwo <= fieldOne then
  119.     local oldAddr = inputFlux.address
  120.       inputFlux = component.proxy(outputFlux.address)
  121.       outputFlux = component.proxy(oldAddr)
  122.     end
  123.  
  124.  -- Functions
  125.  
  126. function exit_msg(msg)
  127.     term.clear()
  128.     print(msg)
  129.     os.exit()
  130. end
  131. function modifyTemp(offset)
  132.     local newTemp = idealTemp + offset
  133.     if newTemp > 8000 and Mode == 1 then
  134.         newTemp = 8000
  135.     elseif newTemp > 8000 and Mode == 2 and chaosmode == 0 then
  136.         newTemp = 8000
  137.     elseif newTemp > 18000 and chaosmode == 1 then
  138.         newTemp = 18000
  139.     elseif newTemp < 2000 then
  140.         newTemp = 2000
  141.     end
  142.         idealTemp = newTemp
  143.     end
  144. function modifyField(offset)
  145.     local newField = idealField + offset
  146.     if newField > 99 then
  147.         newField = 99
  148.     elseif newField < 100 and chaosMode == 1 then
  149.         newField = 100
  150.     elseif newField < 0.5 and Mode == 1 or Mode == 3 then
  151.         newField = 0.5
  152.     elseif newField < 0.125 and Mode == 2 then
  153.         newField = 0.125
  154.     end
  155.         idealField = newField
  156.     end
  157.    
  158.  -- Buttons
  159.     local adj_button_width = 19
  160.     local tempOffsetX = 62
  161.     local tempOffsetY = 2
  162.     local fieldOffsetX = tempOffsetX + adj_button_width + 2
  163.     local fieldOffsetY = 2
  164.     local cutoffField = 0.75
  165.     highest_use = 0.1
  166.     local buttons = {
  167.     startButton={
  168.     x=2,
  169.     y=20,
  170.     width=18,
  171.     height=1,
  172.     text="Start",
  173.     textcolor = 0x0000AA,
  174.     action=function()
  175.       if info.status == "cooling" or info.status == "cold" then
  176.             chaosMode = 0
  177.             idealField = Arg2
  178.             cutoffField = 0.4
  179.             idealTemp = Arg1
  180.             startingVar = 1
  181.             cVar = "Do not use Chaos Mode with less than one block of fuel"
  182.         reactor.chargeReactor()
  183.       elseif info.status == "stopping" then
  184.             chaosMode = 0
  185.             idealField = Arg2
  186.             cutoffField = 0.4
  187.             idealTemp = Arg1
  188.             startingVar = 0
  189.             cVar = "Do not use Chaos Mode with less than one block of fuel"
  190.         reactor.activateReactor()
  191.       end
  192.     end,
  193.     condition=function() return info.status ~= "running" and info.status ~= "warming_up" end
  194.   },
  195.   shutdownButton={
  196.     x=2,
  197.     y=20,
  198.     width=18,
  199.     height=1,
  200.     text="Shutdown",
  201.     textcolor = 0xAA0000,
  202.     action=function()
  203.     cutoffTemp = 9000
  204.     idealTemp = Arg1
  205.     cutoffField = 0.4
  206.     cVar = "Do not use Chaos Mode with less than one block of fuel"
  207.       state = "MASD"
  208.       reactor.stopReactor()
  209.     end,
  210.     condition=function() return info.status == "running" or info.status == "warming_up" end
  211.   },
  212.   chaosMode={
  213.     x=2,
  214.     y=22,
  215.     width=18,
  216.     height=1,
  217.     text=" Chaos Mode",
  218.     textcolor = 0x800080,
  219.     action=function()
  220.         if chaosMode == 0 then
  221.             chaosMode = 1
  222.             cutoffTemp = 18000
  223.             idealTemp = 18000
  224.             idealField = 100
  225.             cutoffField = 5
  226.             idealTemp = 8000
  227.         elseif chaosMode == 1 then
  228.             chaosMode = 0
  229.             idealField = Arg2
  230.             cutoffField = 0.4
  231.             idealTemp = Arg1
  232.         end
  233.     end,
  234.     condition=function() return Mode == 2 and info.status == "running" end
  235.   },
  236.   forceExit={
  237.     x=158,
  238.     y=1,
  239.     width=3,
  240.     height=1,
  241.     text=" X ",
  242.     textcolor = 0xB00000,
  243.     action=function()
  244.         inputFlux.setFlowOverride(250000.0)
  245.         chaosMode = 0
  246.         idealField = 99
  247.         cutoffField = 0.4
  248.         idealTemp = Arg1
  249.       reactor.stopReactor()
  250.       gpu.setResolution(gpu.maxResolution())
  251.       event_loop = false
  252.       os.execute("cls")
  253.     end,
  254. --    condition=function() return running or shutting_down end
  255.   },
  256.   Update={
  257.     x=22,
  258.     y=22,
  259.     width=18,
  260.     height=1,
  261.     text="Update",
  262.     action=function()
  263.         reactor.stopReactor()
  264.         os.execute("cd /home; pastebin get -f YZK9hTBU dc14; cls; dc14")
  265.     end,
  266.     condition=function() return info.status ~= "running" and info.status ~= "warming_up" end
  267.   },
  268.   switchGates={
  269.     x=2,
  270.     y=22,
  271.     width=18,
  272.     height=1,
  273.     text="Swap Flux Gates",
  274.     action=function()
  275.       cutoffTemp = 10500
  276.       local old_addr = inputFlux.address
  277.       inputFlux = component.proxy(outputFlux.address)
  278.       outputFlux = component.proxy(old_addr)
  279.     end,
  280.     condition=function() return info.status == "cooling" or info.status == "cold" or info.status == "stopping" end
  281.   },
  282.   tempMax={
  283.     x=tempOffsetX,
  284.     y=tempOffsetY,
  285.     width=adj_button_width,
  286.     height=1,
  287.     text="Maximum",
  288.     textcolor = 0x552222,
  289.     action=function()
  290.     idealTemp = 8000 end
  291.   },
  292.   tempPThousand={
  293.     x=tempOffsetX,
  294.     y=tempOffsetY+2,
  295.     width=adj_button_width,
  296.     height=1,
  297.     text="+1000",
  298.     textcolor = 0x552222,
  299.     action=function() modifyTemp(1000) end
  300.   },
  301.   tempPHundred={
  302.     x=tempOffsetX,
  303.     y=tempOffsetY+4,
  304.     width=adj_button_width,
  305.     height=1,
  306.     text="+100",
  307.     textcolor = 0x552222,
  308.     action=function() modifyTemp(100) end
  309.   },
  310.   tempPTen={
  311.     x=tempOffsetX,
  312.     y=tempOffsetY+6,
  313.     width=adj_button_width,
  314.     height=1,
  315.     text="+10",
  316.     textcolor = 0x552222,
  317.     action=function() modifyTemp(10) end
  318.   },
  319.   tempPOne={
  320.     x=tempOffsetX,
  321.     y=tempOffsetY+8,
  322.     width=adj_button_width,
  323.     height=1,
  324.     text="+1",
  325.     textcolor = 0x552222,
  326.     action=function() modifyTemp(1) end
  327.   },
  328.   tempMin={
  329.     x=tempOffsetX,
  330.     y=tempOffsetY+20,
  331.     width=adj_button_width,
  332.     height=1,
  333.     text="Minimum",
  334.     textcolor = 0x552222,
  335.     action=function() modifyTemp(-20000) end
  336.   },
  337.   tempMThousand={
  338.     x=tempOffsetX,
  339.     y=tempOffsetY+18,
  340.     width=adj_button_width,
  341.     height=1,
  342.     text="-1000",
  343.     textcolor = 0x552222,
  344.     action=function() modifyTemp(-1000) end
  345.   },
  346.   tempMHundred={
  347.     x=tempOffsetX,
  348.     y=tempOffsetY+16,
  349.     width=adj_button_width,
  350.     height=1,
  351.     text="-100",
  352.     textcolor = 0x552222,
  353.     action=function() modifyTemp(-100) end
  354.   },
  355.   tempMTen={
  356.     x=tempOffsetX,
  357.     y=tempOffsetY+14,
  358.     width=adj_button_width,
  359.     height=1,
  360.     text="-10",
  361.     textcolor = 0x552222,
  362.     action=function() modifyTemp(-10) end
  363.   },
  364.   tempMOne={
  365.     x=tempOffsetX,
  366.     y=tempOffsetY+12,
  367.     width=adj_button_width,
  368.     height=1,
  369.     text="-1",
  370.     textcolor = 0x552222,
  371.     action=function() modifyTemp(-1) end
  372.   },
  373.   fieldPTen={
  374.     x=fieldOffsetX,
  375.     y=fieldOffsetY+1,
  376.     width=adj_button_width,
  377.     height=1,
  378.     text="+10",
  379.     textcolor = 0x222299,
  380.     action=function() modifyField(10) end
  381.   },
  382.     fieldPOne={
  383.     x=fieldOffsetX,
  384.     y=fieldOffsetY+3,
  385.     width=adj_button_width,
  386.     height=1,
  387.     text="+1",
  388.     textcolor = 0x222299,
  389.     action=function() modifyField(1) end
  390.   },
  391.   fieldPTenth={
  392.     x=fieldOffsetX,
  393.     y=fieldOffsetY+5,
  394.     width=adj_button_width,
  395.     height=1,
  396.     text="+0.1",
  397.     textcolor = 0x222299,
  398.     action=function() modifyField(0.1) end
  399.   },
  400.     fieldPThou={
  401.     x=fieldOffsetX,
  402.     y=fieldOffsetY+7,
  403.     width=adj_button_width,
  404.     height=1,
  405.     text="+0.005",
  406.     textcolor = 0x222299,
  407.     action=function() modifyField(0.005) end
  408.   },
  409.   fieldMTen={
  410.     x=fieldOffsetX,
  411.     y=fieldOffsetY+19,
  412.     width=adj_button_width,
  413.     height=1,
  414.     text="-10",
  415.     textcolor = 0x222299,
  416.     action=function() modifyField(-10) end
  417.   },
  418.     fieldMOne={
  419.     x=fieldOffsetX,
  420.     y=fieldOffsetY+17,
  421.     width=adj_button_width,
  422.     height=1,
  423.     text="-1",
  424.     textcolor = 0x222299,
  425.     action=function() modifyField(-1) end
  426.   },
  427.   fieldMTenth={
  428.     x=fieldOffsetX,
  429.     y=fieldOffsetY+15,
  430.     width=adj_button_width,
  431.     height=1,
  432.     text="-0.1",
  433.     textcolor = 0x222299,
  434.     action=function() modifyField(-0.1) end
  435.    },
  436.      fieldMThou={
  437.     x=fieldOffsetX,
  438.     y=fieldOffsetY+13,
  439.     width=adj_button_width,
  440.     height=1,
  441.     text="-0.005",
  442.     textcolor = 0x222299,
  443.     action=function() modifyField(-0.005) end
  444.    }
  445. }
  446.  -- Control Loop
  447. event_loop = true
  448. while event_loop do
  449. :: loopstart ::
  450.         info = reactor.getReactorInfo()
  451.     if not info or info.maxFuelConversion < 0.001 then
  452.     cutoffTemp = 9000
  453.     idealTemp = Arg1
  454.     chaosMode = 0
  455.     gpu.setBackground(0x000000)
  456.     gpu.setForeground(0xFF0000)
  457.     term.setCursor(55, 1)
  458.     print "Please verify that your reactor is refueled."
  459.     term.setCursor(55, 2)
  460.     print "Please verify the integrity of your reactor."
  461.     goto start
  462.     gpu.setForeground(0x000000)
  463.     end
  464.     if info.temperature >= 2000 and info.status ~= "stopping"  then
  465.         reactor.activateReactor()
  466.     end
  467.    
  468.  -- Chaos Mode Safe Shutdown
  469.     if info.temperature > 18000 and chaosMode == 1 and tempDrop == 0 then
  470.         idealTemp = 16000
  471.         tempDrop = 1
  472.         cVar = "Cooling For Shutdown"
  473.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) < 8 and chaosMode == 1  and tempDrop == 1 then
  474.         idealTemp = 14000
  475.         tempDrop = 2
  476.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) < 12.5 and chaosMode == 1  and info.maxFuelConversion < 1297 then
  477.         idealTemp = 8000
  478.         idealField = 99
  479.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) < 1.3 and chaosMode == 1  and tempDrop == 2 and info.maxFuelConversion < 5185 then
  480.         idealTemp = 8000
  481.         idealField = 25
  482.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) < 1 and chaosMode == 1  and tempDrop == 2 then
  483.         idealTemp = 8000
  484.         idealField = 25
  485.     end
  486.  
  487.  -- Auto Adjust Offset
  488.  
  489.     if info.temperature == idealTemp and ((info.fieldStrength / info.maxFieldStrength) * 100) < idealField and chaosMode ~= 1 then
  490.         fieldAdj = (idealField - ((info.fieldStrength / info.maxFieldStrength) * 100))
  491.     end
  492.  
  493.     local targetShieldPercent = idealField or 15 -- Desired shield strength
  494.     local targetShield = (targetShieldPercent / 100)
  495.    
  496.  -- Reactor equation variables
  497.  
  498.     local targetTemp50  = math.min((tonumber(idealTemp) / 10000.0) * 50.0, 99.0)
  499.     local coreSat       = tonumber(info.energySaturation) / tonumber(info.maxEnergySaturation)
  500.     local convLVL       = (tonumber(info.fuelConversion) / tonumber(info.maxFuelConversion) * 1.3) - 0.3
  501.    
  502.     -- Calculate hybrid temperature adjustment
  503.     local tempAdjustment = 0.0
  504.     local tempBoostFactor = 1.0
  505.     if tonumber(idealTemp) > 8000.0 then
  506.         local tempDiff = tonumber(idealTemp) - 8000.0
  507.         -- Small additive adjustment
  508.         tempAdjustment = tempDiff * 0.00005
  509.         -- Very small multiplicative boost that scales down with temperature
  510.         local scaleFactor = 1.0 - (tempDiff * 0.00002)
  511.         tempBoostFactor = 1.0 + (tempDiff * 0.00003 * scaleFactor)
  512.     end
  513.    
  514.     -- Apply both adjustments to conversion level
  515.     convLVL = (convLVL + tempAdjustment) * tempBoostFactor
  516.    
  517.  -- Calculate the temperature rise resistance for the reactor at the desired temperature.
  518.  
  519.     local targetTempResist = ((targetTemp50^4.0) / (100.0 - targetTemp50))
  520.    
  521.  -- Calculate the temperature rise exponential needed to reach the desired temperature
  522.  
  523.     local targetTempExpo = -(targetTempResist*convLVL) - 1000.0*convLVL + targetTempResist
  524.    
  525.     -- Hybrid adjustment for temperature exponential
  526.     if tonumber(info.temperature) < tonumber(idealTemp) then
  527.         local tempDiff = tonumber(idealTemp) - tonumber(info.temperature)
  528.         -- Additive adjustment
  529.         local addAdjust = tempDiff * 0.00003
  530.         -- Multiplicative adjustment that scales with difference
  531.         local scaleFactor = 1.0 - (tempDiff * 0.00001)
  532.         local multAdjust = 1.0 + (tempDiff * 0.00002 * scaleFactor)
  533.         targetTempExpo = (targetTempExpo + addAdjust) * multAdjust
  534.     end
  535.    
  536.  -- Calculate the saturation level needed to produce the required tempRiseExpo
  537.  
  538.     local term1 = 1334.1-(3.0*targetTempExpo)
  539.     local term2 = (1200690.0-(2700.0*targetTempExpo))^2.0
  540.     local term3 = ((-1350.0*targetTempExpo)+(((-4.0*term1^3.0+term2)^(1.0/2.0))/2.0)+600345.0)^(1.0/3.0)
  541.     local targetNegCSat = -(term1/(3.0*term3))-(term3/3.0)
  542.    
  543.  -- Saturation received from above equation needs to be reformatted to a more useful form
  544.  
  545.     local targetCoreSat = 1.0 - (targetNegCSat/99.0)
  546.     local targetSat = targetCoreSat * tonumber(info.maxEnergySaturation)
  547.    
  548.  -- Calculate the difference between where saturation is and where it needs to be
  549.  
  550.     local saturationError = tonumber(info.energySaturation) - targetSat
  551.    
  552.     -- Hybrid adjustment for saturation error
  553.     if tonumber(info.temperature) < tonumber(idealTemp) then
  554.         local tempDiff = tonumber(idealTemp) - tonumber(info.temperature)
  555.         -- Additive adjustment
  556.         local addAdjust = tempDiff * 0.00004
  557.         -- Multiplicative adjustment that scales with difference
  558.         local scaleFactor = 1.0 - (tempDiff * 0.00001)
  559.         local multAdjust = 1.0 + (tempDiff * 0.000025 * scaleFactor)
  560.         saturationError = (saturationError + addAdjust) * multAdjust
  561.     end
  562.    
  563.  -- Calculate field drain
  564.  
  565.     local tempDrainFactor = 0.0
  566.     if tonumber(info.temperature) > 8000.0 then
  567.         tempDrainFactor = 1.0 + ((tonumber(info.temperature)-8000.0)^2.0 * 0.0000025)
  568.     elseif tonumber(info.temperature) > 2000.0 then
  569.         tempDrainFactor = 1.0
  570.     elseif tonumber(info.temperature) > 1000.0 then
  571.         tempDrainFactor = (tonumber(info.temperature)-1000.0)/1000.0
  572.     end
  573.     local baseMaxRFt = (tonumber(info.maxEnergySaturation) / 1000.0) * tonumber(reactorOutputMultiplier) * 1.5
  574.     local fieldDrain = math.min(tempDrainFactor * math.max(0.01, (1.0-coreSat)) * (baseMaxRFt / 10.923556), 2147000000.0)
  575.     local fieldNegPercent = 1.0 - targetShield
  576.    
  577.  --local fieldInputRate = fieldDrain / fieldNegPercent
  578.  
  579.     local fieldStrengthError = (tonumber(info.maxFieldStrength) * targetShield) - tonumber(info.fieldStrength)
  580.     local requiredInput = math.min((tonumber(info.maxFieldStrength) * tonumber(info.fieldDrainRate)) / (tonumber(info.maxFieldStrength) - tonumber(info.fieldStrength)), tonumber(info.maxFieldStrength) - tonumber(info.fieldStrength))
  581.    
  582.  --Automations
  583.  
  584.     if info.status == "running" then
  585.     local outputNeeded = math.min(saturationError, (tonumber(info.maxEnergySaturation)/40))-- + info.generationRate
  586.         outputFlux.setFlowOverride(outputNeeded)
  587.         inputFlux.setFlowOverride(math.min(fieldStrengthError + requiredInput, tonumber(info.maxFieldStrength)) - tonumber(info.fieldDrainRate) + 1)
  588.     elseif info.status == "warming_up" then
  589.         outputFlux.setFlowOverride(0.0)
  590.         inputFlux.setFlowOverride(550000000.0)
  591.     elseif info.status == "stopping" then
  592.         outputFlux.setFlowOverride(0.0)
  593.         inputFlux.setFlowOverride(requiredInput)
  594.     if info.temperature > cutoffTemp then
  595.         print("Reactor Too Hot, shutting down")
  596.         reactor.stopReactor()
  597.     end
  598.     if ((info.fieldStrength / info.maxFieldStrength) * 100) < cutoffField then
  599.         print("Reactor Field Has Failed, Failsafe Activated, Shutting Down")
  600.         reactor.stopReactor()
  601.     end
  602.     if ((1 - info.fuelConversion / info.maxFuelConversion) * 100) < 0.2 then
  603.         print("Reactor Fuel Low, Shutting Down")
  604.         reactor.stopReactor()
  605.     end
  606.    end
  607.  
  608.     -- Get Temp Rise
  609.         oldTemp = currentTemp or info.temperature
  610.         currentTemp = info.temperature
  611.         oldTempRate = tempChangeRate or currentTemp - oldTemp
  612.         tempChangeRate = currentTemp - oldTemp
  613.         tempAccel = tempChangeRate - oldTempRate
  614.     if tempAccel == 0 then
  615.         tempAccel = 0.001
  616.     end
  617.     -- Get Fuel Use Rate
  618.         oldFuel = currentFuel or (info.maxFuelConversion - info.fuelConversion)
  619.         currentFuel = (info.maxFuelConversion - info.fuelConversion)
  620.         oldUseRate = fuelUseRate or math.max(info.fuelConversionRate*20, 0.1)
  621.         fuelUseRate = math.max(info.fuelConversionRate*20, 0.1)
  622.         fuelAccel = math.max(fuelUseRate - oldUseRate, 0.1)
  623.  -- Fuel Conversion Rate
  624.     if info.fuelConversionRate > 249999 then
  625.         fuelConversionRate = ((info.fuelConversionRate / (info.maxFuelConversion * 1000000)) * 2000)
  626.         fuelMeasure = "  %%/s"
  627.     elseif info.fuelConversionRate > 999 then
  628.         fuelConversionRate = (info.fuelConversionRate / 1000)
  629.         fuelMeasure = " "..(unicode.char(956)).."b/t"
  630.     elseif info.fuelConversionRate > 999999 then
  631.         fuelConversionRate = (info.fuelConversionRate / 1000000)
  632.         fuelMeasure = " mb/t"
  633.     else
  634.         fuelConversionRate = info.fuelConversionRate
  635.         fuelMeasure = " nb/t"
  636.     end
  637.  -- Get Time Until Cool
  638.     if info.fuelConversionRate < 1 then
  639.         tempDrain = ((info.temperature - 2000) / 0.4)
  640.     else
  641.         tempDrain = 1
  642.     end
  643.  -- Get Temp Rise
  644.    
  645.    
  646.  --Burn Stage
  647.     if ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 20 then burnStage = "H"
  648.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 15 then burnStage = "He"
  649.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 10 then burnStage = "C"
  650.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 8 then burnStage = "Ne"
  651.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 5.5 then burnStage = "O"
  652.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 2.5 then burnStage = "Si"
  653.     elseif ((1 - info.fuelConversion / info.maxFuelConversion) * 100) > 1 then burnStage = "Fe"
  654.     end
  655.  -- Accuracy
  656.     if ((info.fieldStrength / info.maxFieldStrength) * 100) > idealField then
  657.      deviation = (((info.fieldStrength / info.maxFieldStrength) * 100) + fieldAdj) - idealField
  658.     elseif ((info.fieldStrength / info.maxFieldStrength) * 100) < idealField then
  659.      deviation = idealField - (((info.fieldStrength / info.maxFieldStrength) * 100) + fieldAdj)
  660.     end
  661.  -- DrawData
  662.     local secondsToExpire = (info.maxFuelConversion - info.fuelConversion) / math.max(info.fuelConversionRate*0.00002, 0.00001)
  663.  -- GUI
  664.     if term.isAvailable() and Mode ~= 3 then
  665.         function modify_eff(offset)
  666.             local eff = ((outputFlux / inputFlux) * 100)
  667.             if eff > 100000 then
  668.             eff = 1
  669.         end
  670.     end
  671.     local left_margin = 2
  672.     local spacing = 1
  673.     local values = {
  674.                 "Draconic Control™  [v14.0 sMAT | YZK9hTBU]",
  675.                 " ",
  676.                 "┌──────────────────Reactor Statistics────────────────────┐",
  677. string.format("│Time Until Refuel:         │  %5.0fd, %2.0fh, %2.0fm, %2.0fs     │", secondsToExpire/86400, secondsToExpire   /3600 % 24, secondsToExpire/60 % 60, secondsToExpire % 60),
  678. string.format("│Time Until Cool:           │  %5.0fd, %2.0fh, %2.0fm, %2.0fs     │", tempDrain/86400, tempDrain   /3600 % 24, tempDrain/60 % 60, tempDrain % 60),
  679. string.format("│Ideal Field:               │           %8.3f%%        │", idealField),
  680. string.format("│Current Field:             │           %7.3f%%         │", ((info.fieldStrength / info.maxFieldStrength) * 100) + fieldAdj),
  681.                 "├───────────────────────────┼────────────────────────────┤",
  682. string.format("│Fuel Remaining:            │           %7.3f%%         │", ((1 - info.fuelConversion / info.maxFuelConversion) * 100)),
  683. string.format("│Fuel Use Rate:             │           %7.3f" .. fuelMeasure .. "     │", fuelConversionRate),
  684.                 "├───────────────────────────┼────────────────────────────┤",
  685. string.format("│Temperature                │   %7.1f°c [%8.1f°f]   │", info.temperature, ((info.temperature * 1.8) + 32)),
  686. string.format("│Ideal Temperature:         │   %7.1f°c [%8.1f°f]   │", idealTemp, ((idealTemp * 1.8) + 32)),
  687.                 "├───────────────────────────┼────────────────────────────┤",
  688. string.format("│Energy Input:              │   %12.1f RF/t        │", requiredInput),
  689. string.format("│Energy Output:             │   %12.1f RF/t        │", outputFlux.getFlow()),
  690.                 "└───────────────────────────┴────────────────────────────┘",
  691.                 " " .. cVar,
  692.                 " "
  693. }
  694.     local values2 = {
  695. " ",
  696. " ",
  697. " ",
  698. "                                                                                                                          [Reference Table]",
  699. "                                                                                                             ┌─────────────┬─────────────┬─────────────┐",
  700. "                                                                                                             │ Temperature │  Remaining  │ Consumption │",
  701. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  702. "                                                                                                             │    14000    │    93.27    │    91.90    │",
  703. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  704. "                                                                                                             │    15000    │    59.00    │    123.5    │",
  705. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  706. "                                                                                                             │    16000    │    36.45    │     161     │",
  707. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  708. "                                                                                                             │    17000    │    21.40    │     204     │",
  709. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  710. "                                                                                                             │    18000    │    11.80    │     251     │",
  711. "                                                                                                             ├─────────────┼─────────────┼─────────────┤",
  712. "                                                                                                             │    19000    │    03.89    │     303     │",
  713. "                                                                                                             └─────────────┴─────────────┴─────────────┘",
  714. " ",
  715. " ",
  716. " ",
  717. " ",
  718. " ",
  719. " ",
  720. " ",
  721. " ",
  722. " ",
  723. " ",
  724. " ",
  725. " ",
  726. " ",
  727.               "Eq. Fusion Stage     " .. burnStage,
  728. string.format("Max Fuel [nb]:       %4.3f", (info.maxFuelConversion * 1000000)),
  729. string.format("Fuel Remaining [nb]: %4.3f", ((info.maxFuelConversion - info.fuelConversion) * 1000000)),
  730. string.format("Temperature Rise: %4.3f", tempAccel),
  731. string.format("Temp Resist for target temp %g (%g): %.2f", idealTemp, targetTemp50, targetTempResist),
  732. string.format("Temp expo for convLVL %.2f: %.2f", convLVL, targetTempExpo),
  733. string.format("Saturation needed for zero rise: %g (%3.2f%%)", targetSat, targetCoreSat*100),
  734. string.format("Error between current saturation and target saturation: %g\n", saturationError),
  735. string.format("Current field drain is %g RF/t", info.fieldDrainRate),
  736. string.format("Current temp drain factor for temp %g is %1.2f", info.temperature, tempDrainFactor),
  737. string.format("fieldNegPercent is %g", fieldNegPercent),
  738. string.format("Required input to counter field drain: %g RF/t\n", requiredInput),
  739. string.format("Field Deviation: " .. unicode.char(8776) .. deviation .. "%%"),
  740. string.format("Field #:       %9.3f", info.fieldStrength),
  741. string.format("Field Per:     %9.3f", ((info.fieldStrength / info.maxFieldStrength) * 100)),
  742. string.format("Input Flux Gate:  [" .. inputFlux.address .. "] Set To: " .. inputFlux.getFlow()),
  743. string.format("Output Flux Gate: [" .. outputFlux.address .. "] Set To: " .. outputFlux.getFlow())
  744. }
  745. term.clear()
  746.     if Mode == 2 and Mode ~= 3 then
  747.     for i, v in ipairs(values2) do
  748.         term.setCursor(left_margin, i * spacing)
  749.         term.write(v)
  750.         end
  751.     end
  752.     if Mode ~= 3 then
  753.     for i, v in ipairs(values) do
  754.         term.setCursor(left_margin, i * spacing)
  755.         term.write(v)
  756.         end
  757.     end
  758.  -- Draw Buttons
  759.  
  760.         term.setCursor(tempOffsetX, tempOffsetY+10)
  761.         term.write("Reactor Temperature")
  762.         term.setCursor(fieldOffsetX+1, fieldOffsetY+10)
  763.         term.write("  Field Strength")
  764.         gpu.setForeground(0xFFFFFF)
  765.     for bname, button in pairs(buttons) do
  766.         gpu.setForeground(0x000000)
  767.         if button.depressed then
  768.             button.depressed = button.depressed - 1
  769.             if button.depressed == 0 then
  770.                 button.depressed = nil
  771.             end
  772.         end
  773.     if button.condition == nil or button.condition() then
  774.         local centerColor = 0xBBBBBB
  775.         local highlightColor = 0xCCCCCC
  776.         local lowlightColor = 0x808080
  777.     if button.depressed then
  778.         centerColor = 0xAAAAAA
  779.         highlightColor = 0x707070
  780.         lowlightColor = 0xBBBBBB
  781.     end
  782.         gpu.setBackground(centerColor)
  783.         gpu.fill(button.x, button.y, button.width, button.height, " ")
  784.     if button.width > 1 and button.height > 1 then
  785.         gpu.setBackground(lowlightColor)
  786.         gpu.fill(button.x+1, button.y+button.height-1, button.width-1, 1, " ")
  787.         gpu.fill(button.x+button.width-1, button.y, 1, button.height, " ")
  788.         gpu.setBackground(highlightColor)
  789.         gpu.fill(button.x, button.y, 1, button.height, " ")
  790.         gpu.fill(button.x, button.y, button.width, 1, " ")
  791.     end
  792.         gpu.setBackground(centerColor)
  793.     if button.textcolor then gpu.setForeground(button.textcolor) end
  794.         term.setCursor(button.x + math.floor(button.width / 2 - #button.text / 2), button.y + math.floor(button.height / 2))
  795.         term.write(button.text)
  796.     end
  797.     end
  798.     gpu.setBackground(0x676767)
  799.     gpu.setForeground(0x220000)
  800.     end
  801.     if term.isAvailable() and Mode == 3 then
  802.     local left_margin = 2
  803.     local spacing = 1
  804.     local values3 = {
  805. "Eq. Fusion Stage     " .. burnStage,
  806. string.format("Max Fuel [nb]:       %4.3f", (info.maxFuelConversion * 1000000)),
  807. string.format("Fuel Remaining [nb]: %4.3f", ((info.maxFuelConversion - info.fuelConversion) * 1000000)),
  808. string.format("Temperature Rise: %4.3f", tempAccel),
  809. string.format("Temp Resist for target temp %g (%g): %.2f", idealTemp, targetTemp50, targetTempResist),
  810. string.format("Temp expo for convLVL %.2f: %.2f", convLVL, targetTempExpo),
  811. string.format("Saturation needed for zero rise: %g (%3.2f%%)", targetSat, targetCoreSat*100),
  812. string.format("Error between current saturation and target saturation: %g\n", saturationError),
  813. string.format("Current field drain is %g RF/t", info.fieldDrainRate),
  814. string.format("Current temp drain factor for temp %g is %1.2f", info.temperature, tempDrainFactor),
  815. string.format("fieldNegPercent is %g", fieldNegPercent),
  816. string.format("Required input to counter field drain: %g RF/t\n", requiredInput),
  817. string.format("Field Deviation: " .. unicode.char(8776) .. deviation .. "%%"),
  818. string.format("Input Flux Gate:  [" .. inputFlux.address .. "] Set To: " .. inputFlux.getFlow()),
  819. string.format("Output Flux Gate: [" .. outputFlux.address .. "] Set To: " .. outputFlux.getFlow())
  820. }
  821.  for i, v in ipairs(values3) do
  822.  term.setCursor(left_margin, i * spacing)
  823.  term.write(v)
  824.  end
  825. end
  826.  -- Wait for next tick, or manual shutdown
  827.     local event, id, op1, op2 = event.pull(0.05)
  828.     if event == "interrupted" then
  829.         if safe then
  830.         break
  831.         end
  832.     elseif event == "touch" then
  833.  -- Handle Button Presses
  834.         local x = op1
  835.         local y = op2
  836.         for bname, button in pairs(buttons) do
  837.             if (button.condition == nil or button.condition()) and x >= button.x and x <= button.x + button.width and y >= button.y and y <= button.y + button.height then
  838.                 button.action()
  839.                 button.depressed = 3
  840.             end
  841.         end
  842.     end
  843.     os.sleep()
  844.         if info.fuelConversionRate == 0 and chaosMode == 1 then
  845.         reactor.stopReactor()
  846.         cutoffTemp = 9001
  847.         idealTemp = 8000
  848.         chaosMode = 0
  849.     end
  850. end
  851. :: fin ::
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement