local rate,bits = 44100,16 local chunk = 1/4 local look = 1/4 local chunkc = 2 local sour,pos local emsnd = require("soundgen") .silence(0) :clamp(0,chunk) :compile(rate,bits) local chunkd = {} local function samplify(snd) local chunk = {} for i=0,snd:getSampleCount()-1 do chunk[i] = snd:getSample(i,1) end chunkd[#chunkd+1] = chunk return snd end local sndc = love.thread.getChannel("snd") local ctrl = love.thread.getChannel("ctrl") local function push(c,v) ctrl:supply(c) ctrl:push(v) end local offset = 0 local function init() sour = love.audio.newQueueableSource(rate,bits,1,chunkc) pos = 0 chunkd={} for n=1,chunkc*2 do samplify(emsnd) end push("chunk",chunk) push("emsnd",emsnd) push("pos",pos) push("look",look) push("rate",rate) push("bits",bits) while offset>0 do local c = sndc:demand() local v = sndc:demand() if c == "snd" then offset=offset-1 end end end local playing=false function love.load() love.thread.newThread("thread.lua"):start() init() sour:play() end function love.keypressed(key) if key == "r" then sour:pause() sour:stop() init() elseif key == "space" then playing = not playing if playing then sour:play() else sour:pause() end end end local lastc = love.timer.getTime() local waitingc = false function love.update(dt) local tt = love.timer.getTime() for n=1,sour:getFreeBufferCount()-offset do push("snd",true) offset=offset+1 table.remove(chunkd,1) end local tt1 = love.timer.getTime() if tt1-lastc >= chunk*1.2 and not waitingc then waitingc = true push("slook",true) end local tt2 = love.timer.getTime() while sndc:getCount()>0 do local c = sndc:demand() local v = sndc:demand() if c == "snd" then sour:queue(samplify(v)) if playing then sour:play() end offset=offset-1 elseif c == "pos" then pos = v elseif c == "look" then look = v lastc = love.timer.getTime() waitingc = false else error("unkc: "..tostring(c)) end end local tt3 = love.timer.getTime() if tt3-tt > 0.01 then print("EE",tt3-tt) print(" 1",tt1-tt) print(" 2",tt2-tt1) print(" 3",tt3-tt2) end end function love.draw() local w,h = love.graphics.getDimensions() local line = {} local sx = math.floor(((chunkc+sour:getFreeBufferCount()-offset)*chunk+sour:tell())*rate) local rr = emsnd:getSampleCount() for t=0,w do local x = t/w x=x*2-1 x=x*rate*look x=sx+x line[#line+1]=t x=math.floor(x+.5) local si,ii = math.floor(x/rr)+1,x%rr line[#line+1]=(((chunkd[si]or{})[ii]or 0)*0.5+0.5)*h end love.graphics.setColor(1,1,1,0.1) love.graphics.line(w/2,0,w/2,h) love.graphics.setColor(1,1,1) love.graphics.line(line) end