tweaks and shatter

This commit is contained in:
kepler155c
2018-11-03 04:47:52 -04:00
parent 047c2cdddb
commit aa66b1c663
6 changed files with 573 additions and 18 deletions

482
apis/shatter.lua Normal file
View File

@@ -0,0 +1,482 @@
local os = _G.os
local parallel = _G.parallel
local peripheral = _G.peripheral
local mods = peripheral.wrap("back")
--ensure glasses are present
if not mods.canvas then
error("Shatter requires Overlay Glasses", 2)
end
--###TERMINAL API CODE###--
--colors, for reference use
local colors = {
white = 0xf0f0f000,
orange = 0xf2b23300,
magenta = 0xe57fd800,
lightBlue = 0x99b2f200,
yellow = 0xdede6c00,
lime = 0x7fcc1900,
pink = 0xf2b2cc00,
gray = 0x4c4c4c00,
lightGray = 0x99999900,
cyan = 0x4c99b200,
purple = 0xb266e500,
blue = 0x3366cc00,
brown = 0x7f664c00,
green = 0x57a64e00,
red = 0xcc4c4c00,
black = 0x19191900
}
--colors by number
--colors by number
local cbn = {
colors.white,
colors.orange,
colors.magenta,
colors.lightBlue,
colors.yellow,
colors.lime,
colors.pink,
colors.gray,
colors.lightGray,
colors.cyan,
colors.purple,
colors.blue,
colors.brown,
colors.green,
colors.red,
colors.black
}
--scaled character factor
local ox, oy = 6, 9
-- character size
local sx, sy = 6, 9
--term bg and fg colors and alpha values
local bg, fg, bgbn, fgbn, fga, bga, fgabn, bgabn = colors.black, colors.white, 2^(#cbn-1), 2^0, 255, 255, 1, 1
--cursor, pos, and blink
local csr, cx, cy, cb = nil, 1, 1, true
local textScale = 1
local can = mods.canvas()
--term size
local tx, ty = can.getSize()
tx, ty = math.floor(tx/ox), math.floor(ty/oy)
--screen rendering in a table
local screen = {}
--populate that table
local function tPop()
local x, y = can.getSize()
for i = 1, math.floor(x/ox) do
screen[i] = {}
for j = 1, math.floor(y/oy) do
screen[i][j] = {bg = {}, fg = {}}
end
end
end
tPop()
--write text in grid fashion and add to table
local function write(x, y, char, color)
x, y = math.floor(x), math.floor(y)
if x > 0 and y > 0 and x <= tx and y <= ty then
if not screen[x][y].fg.getColor then
screen[x][y].fg = can.addText({((x-1)*ox)+1, ((y-1)*oy)+1}, char, color, ox/sx)
else
screen[x][y].fg.setColor(color)
screen[x][y].fg.setText(char)
end
end
end
--draw pixel in grid fashion and add to table
local function draw(x, y, color)
x, y = math.floor(x), math.floor(y)
if x > 0 and y > 0 and x <= tx and y <= ty then
if not screen[x][y].bg.getColor then
screen[x][y].bg = can.addRectangle((x-1)*ox, (y-1)*oy, ox, oy, color)
else
screen[x][y].bg.setColor(color)
end
end
end
--get the data of a particular pixel
local function getData(pixel)
if pixel then
return {bgc = bit32.band(pixel.bg.getColor(), 2^32-1), -- Credit to MC:Anavrins for bit32 ingenuity
fgc = bit32.band(pixel.fg.getColor(), 2^32-1),
txt = pixel.fg.getText()}
end
end
--set the data of a particular pixel
local function setData(pixel, data)
if pixel and data then
if pixel.bg.getPosition then
local x, y = pixel.bg.getPosition()
draw(math.floor(x/ox)+1, math.floor(y/oy)+1, data.bgc)
write(math.floor(x/ox)+1, math.floor(y/oy)+1, data.txt, data.fgc)
end
end
end
--move a row to an entirely different line
local function move(line, to)
if line > 0 and line <= ty and to > 0 and to <= ty then
for i = 1, tx do
setData(screen[i][to], getData(screen[i][line]))
end
end
end
--populate term with default bg and fg colors.
local function repopulate()
local x, y = can.getSize()
for i = 1, math.floor(x/ox) do
for j = 1, math.floor(y/oy) do
draw(i, j, bg)
end
end
for i = 1, math.floor(x/ox) do
for j = 1, math.floor(y/oy) do
write(i, j, "", fg)
end
end
end
local function resize(x, y)
ox, oy = math.ceil(textScale*sx), math.ceil(textScale*sy)
tx, ty = x, y
csr.remove()
local oldscr = screen -- replicate the screen
screen = {} -- remove it for repopulation of table w/ new scale
tPop() -- repopulate table
repopulate() -- add objects
csr = can.addText({cx*ox, (cy*oy)+1}, "", 0xffffffff, textScale) --recreate cursor
for i = 1, #oldscr do --rerender screen in new scale
for j = 1, #oldscr[i] do
if oldscr[i][j].bg.getColor ~= nil then
--if screen[i] and screen[i][j] then
-- setData(screen[i][j], getData(oldscr[i][j]))
--end
oldscr[i][j].bg.remove()
oldscr[i][j].fg.remove()
end
end
os.sleep(0)
end
os.queueEvent("monitor_resize", "glasses")
end
local out = {}
out.write = function(str)
--term.write
str = tostring(str)
for i = 1, #str do
write(cx+i-1, cy, str:sub(i, i), fg+fga)
draw(cx+i-1, cy, bg+bga)
end
cx = cx+#str
end
out.blit = function(str, tfg, tbg)
--term.blit
if type(str) ~= "string" then
error("bad argument #1 (expected string, got "..type(str)..")", 2)
elseif type(tfg) ~= "string" then
error("bad argument #2 (expected string, got "..type(tfg)..")", 2)
elseif type(tbg) ~= "string" then
error("bad argument #3 (expected string, got "..type(tbg)..")", 2)
end
for i = 1, #str do
local nfg = cbn[tonumber(tfg:sub(i,i), 16)+1]
local nbg = cbn[tonumber(tbg:sub(i,i), 16)+1]
draw(cx+i-1, cy, nbg+bga)
write(cx+i-1, cy, str:sub(i,i), nfg+fga)
end
cx = cx+#str
end
out.clear = function()
--term.clear
for i = 1, tx do
for j = 1, ty do
write(i, j, "", fg+fga)
draw(i, j, bg+bga)
end
end
end
out.clearLine = function()
--term.clearLine
if cy > 0 and cy <= ty then
for i = 1, tx do
draw(i, cy, bg+bga)
write(i, cy, "", fg+fga)
end
end
end
out.getCursorPos = function()
--term.getCursorPos
return cx, cy
end
out.setCursorPos = function(x, y)
--term.setCursorPos
if type(x) ~= "number" then
error("bad argument #1 (expected number, got "..type(x)..")", 2)
elseif type(y) ~= "number" then
error("bad argument #2 (expected number, got "..type(y)..")", 2)
end
csr.setPosition((x-1)*ox, ((y-1)*oy)+1)
cx, cy = x, y
end
out.setCursorBlink = function(b)
if type(b) ~= "boolean" then
error("bad argument #1 (expected boolean, got "..type(b)..")", 2)
end
cb = b
end
out.isColor = function()
return true, "now with more alpha!"
end
out.isColour = out.isColor
out.getSize = function()
return tx, ty
end
out.setSize = function(x, y)
resize(x, y)
end
out.scroll = function(amount)
local _, tcy = out.getCursorPos()
if type(amount) ~= "number" then
error("bad argument #1 (expected number, got "..type(amount)..")", 2)
end
if amount > 0 then
for i = 1, tx do
move(i, i-amount)
end
elseif amount < 0 then
for i = tx, 1, -1 do
move(i, i-amount)
end
end
out.setCursorPos(1, tcy-amount-1)
end
local function invCol(col)
--A simple error message I am too lazy to type twice
--used in the following few functions
error("invalid color (got "..col..")", 2)
end
local function lb2(num)
--very basic implementation of base 2 logarithm
return math.log(num)/math.log(2)
end
out.setTextColor = function(col)
--term.setTextColor
if type(col) ~= "number" then
error("bad argument #1 (number expected, got "..type(col)..")", 2)
end
if lb2(col) > #cbn or lb2(col) ~= math.ceil(lb2(col)) then
invCol(col)
else
fg = cbn[lb2(col)+1]
fgbn = col
end
end
out.setBackgroundColor = function(col)
--term.setBackgroundColor
if type(col) ~= "number" then
error("bad argument #1 (expected number, got "..type(col)..")", 2)
end
if lb2(col) > #cbn or lb2(col) ~= math.ceil(lb2(col)) then
invCol(col)
else
bg = cbn[lb2(col)+1]
bgbn = col
end
end
-- Text & BG Alpha innovated by MC:Ale32bit
out.setTextAlpha = function(val)
-- set the alpha value of the text
if type(val) ~= "number" then
error("bad argument #1 (expected number, got "..type(val)..")", 2)
end
if val > 1 then val = 1 elseif val < 0 then val = 0 end
fga = math.floor(val*255)
fgabn = val
end
out.setBackgroundAlpha = function(val)
-- set the alpha value of the background
if type(val) ~= "number" then
error("bad argument #1 (expected number, got "..type(val)..")", 2)
end
if val > 1 then val = 1 elseif val < 0 then val = 0 end
bga = math.floor(val*255)
bgabn = val
end
out.setTextHex = function(hex)
-- set the hex color value of the text
if type(tonumber(hex, 16)) ~= "number" then
error("bad argument #1 (expected number, got "..type(hex)..")", 2)
end
fg = hex
fgbn = 1
end
out.setBackgroundHex = function(hex)
-- set the hex color value of the background
if type(tonumber(hex, 16)) ~= "number" then
error("bad argument #1 (expected number, got "..type(hex)..")", 2)
end
bg = hex
bgbn = 1
end
out.getTextColor = function()
--term.getTextColor
return fgbn
end
out.getBackgroundColor = function()
--term.getBackgroundColor
return bgbn
end
out.getTextAlpha = function()
-- get the alpha value of the text
return fgabn
end
out.getBackgroundAlpha = function()
--get the alpha value of the background
return bgabn
end
out.getTextHex = function()
-- get the hex color value of the text
return fg
end
out.getBackgroundHex = function()
-- get the hex color value of the background
return bg
end
local function torgba(hex)
-- Converts a hex value into 3 seperate r, g, and b values
-- Technically also gets a value, but it thrown out due to what this is needed for
-- Credit to MC:valithor2 for this algorithm
local vals = {}
for i = 1, 4 do
vals[i] = hex%256
hex = (hex-vals[i])/256
end
return vals[4]/255, vals[3]/255, vals[2]/255
end
local function refreshColor(oc, nc)
-- refreshes terminal when palette values are manipulated
for i = 1, #screen do
for j = 1, #screen[i] do
local op, changed = getData(screen[i][j]), false
if op.bgc == oc then
op.bgc = nc
changed = true
end
if op.fgc == oc then
op.fgc = nc
changed = true
end
if changed then
setData(screen[i][j], op)
end
end
end
end
out.getPaletteColor = function(col)
--term.getPaletteColor
if type(col) ~= "number" then
error("bad argument #1 (number expected, got "..type(col)..")", 2)
end
if lb2(col) > #cbn or lb2(col) ~= math.ceil(lb2(col)) then
invCol(col)
end
return torgba(cbn[lb2(col)+1])
end
out.setPaletteColor = function(cnum, r, g, b)
--term.setPaletteColor
local oc = cbn[lb2(cnum)+1]
if type(cnum) ~= "number" then
error("bad argument #1 (number expected, got "..type(cnum)..")", 2)
end
if type(r) ~= "number" then
error("bad argument #2 (number expected, got "..type(r)..")", 2)
end
if g then
if type(g) ~= "number" then
error("bad argument #3 (number expected, got "..type(g)..")", 2)
elseif type(b) ~= "number" then
error("bad argument #4 (number expected, got "..type(b)..")", 2)
end
if r > 1 then r = 1 elseif r < 0 then r = 0 end
if g > 1 then g = 1 elseif g < 0 then g = 0 end
if b > 1 then b = 1 elseif b < 0 then b = 0 end
cbn[lb2(cnum)+1] = (((r*255)*(16^6))+((g*255)*(16^4))+((b*255)*(16^2)))
else
cbn[lb2(cnum)+1] = (r*256)
end
if bgbn == cnum then
out.setBackgroundColor(bgbn)
end
if fgbn == cnum then
out.setTextColor(fgbn)
end
--refreshColor(oc, cbn[lb2(cnum)+1]) -- errors
end
--compat for all those UK'ers
out.setTextColour = out.setTextColor
out.setBackgroundColour = out.setBackgroundColor
out.setPaletteColour = out.setPaletteColor
out.getTextColour = out.getTextColor
out.getBackgroundColour = out.getBackgroundColor
out.getPaletteColour = out.getPaletteColor
out.getTextScale = function() return textScale end
out.setTextScale = function(scale)
if type(scale) ~= "number" then
error("bad argument #1 (number expected, got "..type(scale)..")", 2)
end
if 0.4 >= scale or scale > 10 then
error("Expected number in range 0.5-10", 2)
end
if textScale ~= scale then
local factor = textScale/scale
debug({ scale, textScale, factor, tx*factor, ty*factor })
textScale = scale
resize(tx*factor, ty*factor)
end
end
--###TERMINAL CREATION CODE###--
csr = can.addText({cx*ox, (cy*oy)+1}, "", 0xffffffff, ox/sx)
repopulate()
out.cursorRoutine = function()
parallel.waitForAll(function()
--cursor flicker
while true do
if not cb then
csr.setText(" ")
os.sleep()
else
csr.setText("_")
os.sleep(.4)
csr.setText(" ")
os.sleep(.4)
end
end
end,
function()
--glasses event handler conversion
while true do
local e = {os.pullEvent()}
if e[1]:find("glasses") then
local _, b = e[1]:find("glasses")
e[1] = "mouse"..e[1]:sub(b+1, -1)
if e[1] ~= "mouse_scroll" then
e[3], e[4] = math.ceil(e[3]/ox), math.ceil(e[4]/oy)
end
os.queueEvent(unpack(e))
end
end
end)
end
return out

View File

@@ -2,6 +2,7 @@ _G.requireInjector(_ENV)
local Config = require('config')
local Util = require('util')
local InventoryAdapter = require('chestAdapter18')
local device = _G.device
local os = _G.os
@@ -16,23 +17,51 @@ local sensor = device['plethora:sensor'] or
turtle.equip('right', 'plethora:module:3') and device['plethora:sensor'] or
error('Plethora sensor required')
local dispenser = device['minecraft:dispenser_89'] or
error('Dispenser not found')
local integrator = device['redstone_integrator_131'] or
error('Integrator not found')
local function pulse()
integrator.setOutput('north', true)
os.sleep(.25)
integrator.setOutput('north', false)
end
local function turnOffWater()
local list = dispenser.list()
if list[1].name == 'minecraft:bucket' then
pulse()
os.sleep(2)
end
end
local function turnOnWater()
if dispenser.list()[1].name == 'minecraft:water_bucket' then
pulse()
end
end
local function getCowCount()
local blocks = sensor.sense()
local grown = 0
local babies = 0
local xpCount = 0
Util.filterInplace(blocks, function(v)
if v.name == 'Cow' then
if v.y > -.5 then grown = grown + 1 end
if v.y < -.5 then babies = babies + 1 end
return v.y > -.5
elseif v.name == 'XPOrb' then
xpCount = xpCount + 1
end
end)
Util.print('%d grown, %d babies', grown, babies)
Util.print('%d grown, %d babies, %d xp', grown, babies, xpCount)
return #blocks
return #blocks, xpCount
end
local function butcher()
@@ -60,17 +89,30 @@ local function breed()
end
end
local chest = InventoryAdapter({ side = 'top', direction = 'down' }) or
error('missing chest above')
turtle.run(function()
turnOffWater()
repeat
if getCowCount() > config.max_cows then
local cowCount, xpCount = getCowCount()
if cowCount > config.max_cows then
turtle.setStatus('Butchering')
butcher()
elseif turtle.getItemCount('minecraft:wheat') == 0 then
turtle.setStatus('Out of wheat')
if chest:provide({ name = 'minecraft:wheat' }, 64) == 0 then
turtle.setStatus('Out of wheat')
end
else
turtle.setStatus('Breeding')
breed()
end
if xpCount > 2 then
turnOnWater()
os.sleep(8)
turnOffWater()
end
os.sleep(5)
until turtle.isAborted()
end)

31
apps/glassesDriver.lua Normal file
View File

@@ -0,0 +1,31 @@
_G.requireInjector(_ENV)
local device = _G.device
local kernel = _G.kernel
local os = _G.os
local glasses = require('shatter')
glasses.name = 'glasses'
glasses.type = 'rayban'
glasses.size = 'face'
device.glasses = glasses
glasses.setTextScale(.5)
glasses.setSize(100, 40)
kernel.hook({ 'glasses_click', 'glasses_up', 'glasses_drag' }, function(event, eventData)
local sx, sy = 6, 9
local scale = glasses.getTextScale()
local ox, oy = math.ceil(scale*sx), math.ceil(scale*sy)
local lookup = {
glasses_click = 'monitor_touch',
glasses_up = 'monitor_up',
glasses_drag = 'monitor_drag',
}
local x, y = math.floor(eventData[2]/ox) + 1, math.floor(eventData[3]/oy) + 1
os.queueEvent(lookup[event], 'glasses', x, y)
glasses.setCursorPos(x, y)
glasses.write('X ' .. eventData[3])
end)

View File

@@ -28,8 +28,9 @@ local monitor
local defaultEnv = Util.shallowCopy(_ENV)
defaultEnv.multishell = multishell
if args[2] then
if args[3] then
monitor = _G.device[args[3]]
elseif args[2] then
monitor = peripheral.wrap(args[2]) or syntax()
else
monitor = peripheral.find('monitor') or syntax()

View File

@@ -12,10 +12,6 @@ local peripheral = _G.peripheral
local printError = _G.printError
local turtle = _G.turtle
if not device.wireless_modem then
error('Modem is required')
end
if not turtle then
error('Can only be run on a turtle')
end
@@ -236,16 +232,18 @@ local function pickupHost(socket)
end
end
Event.addRoutine(function()
while true do
print('waiting for connection on port 5222')
local socket = Socket.server(5222)
if device.wireless_modem then
Event.addRoutine(function()
while true do
print('waiting for connection on port 5222')
local socket = Socket.server(5222)
print('pickup: connection from ' .. socket.dhost)
print('pickup: connection from ' .. socket.dhost)
Event.addRoutine(function() pickupHost(socket) end)
end
end)
Event.addRoutine(function() pickupHost(socket) end)
end
end)
end
local function eachEntry(t, fn)

View File

@@ -94,6 +94,7 @@ local function getPoint()
if not gpt then
mainPage.statusBar:timedStatus('Unable to get location', 3)
end
gpt.y = gpt.y - 1
return gpt
end