Vendor libs/hump, sfxrlua, json4lua, narrator as real files
These were committed as empty submodule gitlinks with no .gitmodules, so the folders were never populated and the game could not load (require of libs/hump/timer, libs/sfxrlua/sfxr, narrator.narrator). Checked out each at its pinned commit and vendored the files, matching the existing bundled-libs convention. Removed the junk libs/libs/ tree. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
e73f63b5d4
commit
03532d29e4
219 changed files with 20254 additions and 252 deletions
|
|
@ -1 +0,0 @@
|
|||
Subproject commit 949429d4618aee8b019899af101bd5f793d07a64
|
||||
40
libs/sfxrlua/.gitignore
vendored
Normal file
40
libs/sfxrlua/.gitignore
vendored
Normal file
|
|
@ -0,0 +1,40 @@
|
|||
# Compiled Lua sources
|
||||
luac.out
|
||||
|
||||
# luarocks build files
|
||||
*.src.rock
|
||||
*.zip
|
||||
*.tar.gz
|
||||
|
||||
# Object files
|
||||
*.o
|
||||
*.os
|
||||
*.ko
|
||||
*.obj
|
||||
*.elf
|
||||
|
||||
# Precompiled Headers
|
||||
*.gch
|
||||
*.pch
|
||||
|
||||
# Libraries
|
||||
*.lib
|
||||
*.a
|
||||
*.la
|
||||
*.lo
|
||||
*.def
|
||||
*.exp
|
||||
|
||||
# Shared objects (inc. Windows DLLs)
|
||||
*.dll
|
||||
*.so
|
||||
*.so.*
|
||||
*.dylib
|
||||
|
||||
# Executables
|
||||
*.exe
|
||||
*.out
|
||||
*.app
|
||||
*.i*86
|
||||
*.x86_64
|
||||
*.hex
|
||||
3
libs/sfxrlua/.gitmodules
vendored
Normal file
3
libs/sfxrlua/.gitmodules
vendored
Normal file
|
|
@ -0,0 +1,3 @@
|
|||
[submodule "loveframes"]
|
||||
path = demo/loveframes
|
||||
url = https://github.com/NikolaiResokav/LoveFrames
|
||||
21
libs/sfxrlua/LICENSE
Normal file
21
libs/sfxrlua/LICENSE
Normal file
|
|
@ -0,0 +1,21 @@
|
|||
The MIT License (MIT)
|
||||
|
||||
Copyright (c) 2014 nucular
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
61
libs/sfxrlua/README.md
Normal file
61
libs/sfxrlua/README.md
Normal file
|
|
@ -0,0 +1,61 @@
|
|||
sfxr.lua
|
||||
========
|
||||
|
||||
```
|
||||
luarocks install sfxr
|
||||
```
|
||||
|
||||
A port of the sfxr sound effect synthesizer to pure Lua, designed to be used
|
||||
together with the *awesome* [LÖVE](https://love2d.org) game framework.
|
||||
|
||||
Demo
|
||||
----
|
||||
|
||||
To run the demo application you first need to download
|
||||
[LoveFrames](https://github.com/NikolaiResokav/LoveFrames) as a submodule:
|
||||
```
|
||||
git submodule update --init
|
||||
love demo
|
||||
```
|
||||
Note: Due to LoveFrames only supporting LÖVE 0.9.x, this dependency is inherited
|
||||
by the demo. A move to a new GUI framework is pending.
|
||||
|
||||
Example usage
|
||||
-------------
|
||||
|
||||
The following code examples demonstrate how to play a randomly generated sound:
|
||||
|
||||
With [LÖVE](http://love2d.org):
|
||||
```lua
|
||||
local sfxr = require("sfxr")
|
||||
|
||||
function love.load()
|
||||
local sound = sfxr.newSound()
|
||||
sound:randomize()
|
||||
local sounddata = sound:generateSoundData()
|
||||
local source = love.audio.newSource(sounddata)
|
||||
source:play()
|
||||
end
|
||||
```
|
||||
|
||||
With [lao](https://github.com/TheLinx/lao):
|
||||
```lua
|
||||
require("ao")
|
||||
local sfxr = require("sfxr")
|
||||
|
||||
local driverId = ao.defaultDriverId()
|
||||
local device = ao.openLive(driverId, {bits = 16, rate = 44100, channels = 1})
|
||||
|
||||
local sound = sfxr.newSound()
|
||||
sound:randomize()
|
||||
|
||||
device:play(sound:generateString())
|
||||
```
|
||||
|
||||
Documentation
|
||||
-------------
|
||||
|
||||
[**The latest documentation build is available here**](http://nucular.github.io/sfxrlua/)
|
||||
|
||||
This project uses [LDoc](http://stevedonovan.github.io/ldoc/) for autogenerated
|
||||
API documentation.
|
||||
12
libs/sfxrlua/config.ld
Normal file
12
libs/sfxrlua/config.ld
Normal file
|
|
@ -0,0 +1,12 @@
|
|||
project = "sfxr.lua"
|
||||
description = "A port of the sfxr sound effect synthesizer to Lua"
|
||||
title = "sfxr.lua Documentation"
|
||||
format = "markdown"
|
||||
not_luadoc = true
|
||||
style = "!pale"
|
||||
kind_names = {topic = "Topics", module = "API"}
|
||||
dir = "./docs"
|
||||
|
||||
file = "sfxr.lua"
|
||||
topics = {
|
||||
}
|
||||
6
libs/sfxrlua/demo/conf.lua
Normal file
6
libs/sfxrlua/demo/conf.lua
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
function love.conf(t)
|
||||
t.version = love._version:match("0%.9%.%d+") or "0.9.x"
|
||||
t.window.width = 640
|
||||
t.window.height = 600
|
||||
t.window.title = "sfxr.lua Demo"
|
||||
end
|
||||
695
libs/sfxrlua/demo/main.lua
Normal file
695
libs/sfxrlua/demo/main.lua
Normal file
|
|
@ -0,0 +1,695 @@
|
|||
#/usr/bin/env love
|
||||
-- love .
|
||||
|
||||
local sfxr = require("sfxr")
|
||||
|
||||
-- Global stuff
|
||||
local source
|
||||
local sound
|
||||
local sounddata
|
||||
|
||||
local seed
|
||||
local playbutton
|
||||
local playing = false
|
||||
|
||||
local wavecanvas
|
||||
local statistics = {
|
||||
generation = 0,
|
||||
transfer = 0,
|
||||
waveview = 0,
|
||||
duration = 0
|
||||
}
|
||||
|
||||
-- This will hold all sliders and the wave form box
|
||||
local guiparams = {}
|
||||
-- The parameter list is built from this
|
||||
-- {{"Text", "table name", {{"Text", "table paramter", min, max}, ...}}, ...}
|
||||
local guicategories = {
|
||||
{
|
||||
"Envelope",
|
||||
"envelope",
|
||||
{
|
||||
{"Attack Time", "attack", 0, 1},
|
||||
{"Sustain Time", "sustain", 0, 1},
|
||||
{"Sustain Punch", "punch", 0, 1},
|
||||
{"Decay Time", "decay", 0, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Frequency",
|
||||
"frequency",
|
||||
{
|
||||
{"Start", "start", 0, 1},
|
||||
{"Minimum", "min", 0, 1},
|
||||
{"Slide", "slide", -1, 1},
|
||||
{"Delta Slide", "dslide", -1, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Vibrato",
|
||||
"vibrato",
|
||||
{
|
||||
{"Depth", "depth", 0, 1},
|
||||
{"Speed", "speed", 0, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Change",
|
||||
"change",
|
||||
{
|
||||
{"Amount", "amount", -1, 1},
|
||||
{"Speed", "speed", 0, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Square Duty",
|
||||
"duty",
|
||||
{
|
||||
{"Ratio", "ratio", 0, 1},
|
||||
{"Sweep", "sweep", -1, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Phaser",
|
||||
"phaser",
|
||||
{
|
||||
{"Offset", "offset", -1, 1},
|
||||
{"Sweep", "sweep", -1, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"Low Pass",
|
||||
"lowpass",
|
||||
{
|
||||
{"Cutoff", "cutoff", 0, 1},
|
||||
{"Sweep", "sweep", -1, 1},
|
||||
{"Resonance", "resonance", 0, 1}
|
||||
}
|
||||
},
|
||||
{
|
||||
"High Pass",
|
||||
"highpass",
|
||||
{
|
||||
{"Cutoff", "cutoff", 0, 1},
|
||||
{"Sweep", "sweep", -1, 1}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
-- Easy lookup of wave forms
|
||||
local waveFormList = {
|
||||
["Square"] = 0,
|
||||
["Sawtooth"] = 1,
|
||||
["Sine"] = 2,
|
||||
["Noise"] = 3,
|
||||
[0] = "Square",
|
||||
[1] = "Sawtooth",
|
||||
[2] = "Sine",
|
||||
[3] = "Noise"
|
||||
}
|
||||
|
||||
|
||||
function stopSound()
|
||||
playbutton:SetText("Play")
|
||||
if source then
|
||||
source:stop()
|
||||
end
|
||||
end
|
||||
|
||||
function playSound()
|
||||
-- Stop the currently playing source
|
||||
if source then
|
||||
source:stop()
|
||||
end
|
||||
|
||||
local t = love.timer.getTime()
|
||||
local tab = sound:generateTable(sfxr.FREQ_44100, sfxr.BITS_FLOAT)
|
||||
t = love.timer.getTime() - t
|
||||
statistics.generation = math.floor(t * 10000) / 10
|
||||
|
||||
if #tab == 0 then
|
||||
return nil
|
||||
end
|
||||
|
||||
sounddata = love.sound.newSoundData(#tab, 44100, 16, 1)
|
||||
statistics.duration = math.floor(sounddata:getDuration() * 10000) / 10
|
||||
|
||||
-- Stuff for the wave view
|
||||
local waveview = {}
|
||||
local j = 0
|
||||
local max = -1
|
||||
local min = 1
|
||||
local avg = 0.5
|
||||
|
||||
local t = love.timer.getTime()
|
||||
for i = 0, #tab - 1 do
|
||||
|
||||
local v = tab[i + 1]
|
||||
-- Copy the sample over to the SoundData
|
||||
sounddata:setSample(i, v)
|
||||
|
||||
-- Add the minimal and maximal sample to the wave view
|
||||
-- every 256 samples. This is how Audacity does it, actually.
|
||||
j = j + 1
|
||||
min = math.min(v, min)
|
||||
max = math.max(v, max)
|
||||
if j >= 256 then
|
||||
waveview[#waveview + 1] = min
|
||||
waveview[#waveview + 1] = max
|
||||
j = 0
|
||||
min, max = 1, -1
|
||||
end
|
||||
end
|
||||
t = love.timer.getTime() - t
|
||||
statistics.transfer = math.floor(t * 10000) / 10
|
||||
|
||||
updateWaveCanvas(waveview)
|
||||
updateStatistics()
|
||||
|
||||
if sounddata then
|
||||
source = love.audio.newSource(sounddata)
|
||||
source:play()
|
||||
playbutton:SetText("Stop Playing")
|
||||
playing = true
|
||||
end
|
||||
end
|
||||
|
||||
function createSeedBox()
|
||||
local f = lf.Create("form"):SetName("Random Seed")
|
||||
|
||||
seed = lf.Create("numberbox")
|
||||
:SetValue(math.floor(love.timer.getTime()))
|
||||
:SetMax(math.huge)
|
||||
:SetMin(-math.huge)
|
||||
:SetWidth(100)
|
||||
|
||||
f:AddItem(seed):SetPos(5, 240)
|
||||
end
|
||||
|
||||
function createPresetGenerators()
|
||||
local f = lf.Create("form")
|
||||
:SetName("Preset Generators")
|
||||
local generators = {
|
||||
{"Pickup/Coin", sound.randomPickup},
|
||||
{"Laser/Shoot", sound.randomLaser},
|
||||
{"Explosion", sound.randomExplosion},
|
||||
{"Powerup", sound.randomPowerup},
|
||||
{"Hit/Hurt", sound.randomHit},
|
||||
{"Jump", sound.randomJump},
|
||||
{"Blip/Select", sound.randomBlip}
|
||||
}
|
||||
|
||||
for i, v in ipairs(generators) do
|
||||
local b = lf.Create("button")
|
||||
:SetText(v[1])
|
||||
:SetWidth(100)
|
||||
f:AddItem(b)
|
||||
|
||||
b.OnClick = function(self)
|
||||
v[2](sound, seed:GetValue())
|
||||
seed:SetValue(seed:GetValue() + 1)
|
||||
updateParameters()
|
||||
playSound()
|
||||
end
|
||||
end
|
||||
|
||||
f:SetPos(5, 5):SetWidth(110)
|
||||
end
|
||||
|
||||
function createRandomizers()
|
||||
local f = lf.Create("form"):SetName("Randomizers")
|
||||
|
||||
local b = lf.Create("button")
|
||||
:SetText("Mutate")
|
||||
:SetWidth(100)
|
||||
f:AddItem(b)
|
||||
|
||||
b.OnClick = function(self)
|
||||
sound:mutate()
|
||||
updateParameters()
|
||||
playSound()
|
||||
end
|
||||
|
||||
local b = lf.Create("button")
|
||||
:SetText("Randomize")
|
||||
:SetWidth(100)
|
||||
f:AddItem(b)
|
||||
|
||||
b.OnClick = function(self)
|
||||
sound:randomize(seed:GetValue())
|
||||
updateParameters()
|
||||
seed:SetValue(seed:GetValue() + 1)
|
||||
playSound()
|
||||
end
|
||||
|
||||
f:SetPos(5, 515):SetSize(110, 80)
|
||||
end
|
||||
|
||||
function createParameters()
|
||||
local f = lf.Create("form"):SetName("Parameters")
|
||||
|
||||
local l = lf.Create("list")
|
||||
:SetSpacing(5)
|
||||
:SetPadding(5)
|
||||
:SetSize(340, 565)
|
||||
f:AddItem(l)
|
||||
|
||||
|
||||
-- Waveforms
|
||||
l:AddItem(lf.Create("text"):SetPos(0, pheight):SetText("Wave Form"))
|
||||
|
||||
local m = lf.Create("multichoice")
|
||||
for i = 0, #waveFormList do
|
||||
m:AddChoice(waveFormList[i])
|
||||
end
|
||||
m:SetChoice("Square")
|
||||
|
||||
m.OnChoiceSelected = function(o, c)
|
||||
sound.wavetype = waveFormList[c]
|
||||
end
|
||||
|
||||
l:AddItem(m)
|
||||
guiparams.waveform = m
|
||||
|
||||
|
||||
-- Repeat speed
|
||||
local t = lf.Create("text")
|
||||
:SetText("Repeat Speed 0")
|
||||
:SetPos(0, pheight)
|
||||
|
||||
local s = lf.Create("slider")
|
||||
:SetWidth(120)
|
||||
:SetMinMax(0, 1)
|
||||
:SetValue(sound.repeatspeed)
|
||||
|
||||
s.OnValueChanged = function(o)
|
||||
local v = o:GetValue()
|
||||
if v <= 0.02 and v >= -0.02 and v ~= 0 then
|
||||
o:SetValue(0)
|
||||
sound.repeatspeed = 0
|
||||
t:SetText("Repeat Speed 0")
|
||||
else
|
||||
sound.repeatspeed = v
|
||||
t:SetText("Repeat Speed " .. tostring(math.floor(v * 100) / 100))
|
||||
end
|
||||
end
|
||||
|
||||
l:AddItem(t):AddItem(s)
|
||||
guiparams.repeatspeed = {s, t}
|
||||
|
||||
|
||||
for i1, v1 in ipairs(guicategories) do
|
||||
local c = lf.Create("collapsiblecategory"):SetText(v1[1])
|
||||
l:AddItem(c)
|
||||
|
||||
local p = lf.Create("panel")
|
||||
local pheight = 0
|
||||
p.Draw = function() end
|
||||
c:SetObject(p)
|
||||
|
||||
guiparams[v1[2]] = {}
|
||||
|
||||
for i2, v2 in ipairs(v1[3]) do
|
||||
lf.Create("text", p)
|
||||
:SetText(v2[1])
|
||||
:SetPos(0, pheight)
|
||||
|
||||
local t = lf.Create("text", p)
|
||||
:SetText("0")
|
||||
:SetPos(95, pheight)
|
||||
|
||||
local s = lf.Create("slider", p)
|
||||
:SetPos(130, pheight - 3)
|
||||
:SetWidth(170)
|
||||
:SetMinMax(v2[3], v2[4])
|
||||
:SetValue(sound[v1[2]][v2[2]])
|
||||
|
||||
s.OnValueChanged = function(o)
|
||||
local v = o:GetValue()
|
||||
if v <= 0.02 and v >= -0.02 and v ~= 0 then
|
||||
o:SetValue(0)
|
||||
sound[v1[2]][v2[2]] = 0
|
||||
t:SetText("0")
|
||||
else
|
||||
sound[v1[2]][v2[2]] = v
|
||||
t:SetText(math.floor(v * 100) / 100)
|
||||
end
|
||||
end
|
||||
|
||||
guiparams[v1[2]][v2[2]] = {s, t}
|
||||
pheight = pheight + 30
|
||||
end
|
||||
|
||||
p:SetHeight(pheight - 10)
|
||||
end
|
||||
|
||||
|
||||
f:SetPos(125, 5):SetSize(350, 590)
|
||||
end
|
||||
|
||||
function createActionButtons()
|
||||
local f = lf.Create("form"):SetName("Actions")
|
||||
|
||||
local b = lf.Create("button")
|
||||
:SetText("Generate and Play")
|
||||
:SetWidth(140)
|
||||
|
||||
b.OnClick = function(o)
|
||||
if not playing then
|
||||
playSound()
|
||||
else
|
||||
stopSound()
|
||||
end
|
||||
end
|
||||
|
||||
playbutton = b
|
||||
f:AddItem(b)
|
||||
|
||||
|
||||
local fr = lf.Create("frame")
|
||||
:SetName("File Picker")
|
||||
:SetSize(400, 300)
|
||||
:Center()
|
||||
:SetVisible(false)
|
||||
:SetModal(false)
|
||||
|
||||
local frl = lf.Create("columnlist", fr)
|
||||
:SetPos(5, 30)
|
||||
:SetSize(390, 235)
|
||||
:AddColumn("Name")
|
||||
|
||||
local frt = lf.Create("textinput", fr)
|
||||
:SetPos(5, 270)
|
||||
:SetWidth(300)
|
||||
|
||||
local frb = lf.Create("button", fr)
|
||||
:SetPos(315, 270)
|
||||
|
||||
frl.OnRowSelected = function(p, row, data)
|
||||
frt:SetText(data[1])
|
||||
end
|
||||
|
||||
fr.OnClose = function(o)
|
||||
frl:Clear()
|
||||
fr:SetVisible(false):SetModal(false)
|
||||
return false
|
||||
end
|
||||
|
||||
local function saveHandler(type, cb)
|
||||
return function()
|
||||
fr:SetName("Save to ." .. type)
|
||||
frt:SetText("sound." .. type)
|
||||
frb:SetText("Save")
|
||||
|
||||
love.filesystem.getDirectoryItems("sounds", function(name)
|
||||
if name:find(type, #type-#name+1, true) then
|
||||
frl:AddRow(name)
|
||||
end
|
||||
end)
|
||||
|
||||
frb.OnClick = function(o)
|
||||
local name = frt:GetText()
|
||||
if (#name > 0) then
|
||||
local f = love.filesystem.newFile("sounds/" .. name, "w")
|
||||
if f then
|
||||
cb(f)
|
||||
frl:Clear()
|
||||
fr:SetVisible(false):SetModal(false)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
frt.OnEnter = frb.OnClick
|
||||
fr:SetVisible(true)
|
||||
:SetModal(true)
|
||||
:Center()
|
||||
end
|
||||
end
|
||||
|
||||
local function loadHandler(type, cb)
|
||||
return function()
|
||||
fr:SetName("Load from ." .. type)
|
||||
frt:SetText("sound." .. type)
|
||||
frb:SetText("Load")
|
||||
|
||||
love.filesystem.getDirectoryItems("sounds", function(name)
|
||||
if name:find(type, #type-#name+1, true) then
|
||||
frl:AddRow(name)
|
||||
end
|
||||
end)
|
||||
|
||||
frb.OnClick = function(o)
|
||||
local name = frt:GetText()
|
||||
if (#name > 0) then
|
||||
local f = love.filesystem.newFile("sounds/" .. name, "r")
|
||||
if f then
|
||||
cb(f)
|
||||
frl:Clear()
|
||||
fr:SetVisible(false):SetModal(false)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
frt.OnEnter = frb.OnClick
|
||||
fr:SetVisible(true)
|
||||
:SetModal(true)
|
||||
:Center()
|
||||
end
|
||||
end
|
||||
|
||||
|
||||
local sb = lf.Create("button")
|
||||
:SetText("Save Lua")
|
||||
:SetWidth(67)
|
||||
sb.OnClick = saveHandler("lua", function(f) sound:save(f, true) end)
|
||||
f:AddItem(sb)
|
||||
|
||||
local lb = lf.Create("button")
|
||||
:SetText("Load Lua")
|
||||
:SetWidth(67)
|
||||
lb.OnClick = loadHandler("lua", function(f) sound:load(f) end)
|
||||
f:AddItem(lb)
|
||||
|
||||
local bsb = lf.Create("button")
|
||||
:SetText("Save binary")
|
||||
:SetWidth(67)
|
||||
bsb.OnClick = saveHandler("sfs", function(f) sound:saveBinary(f) end)
|
||||
f:AddItem(bsb)
|
||||
|
||||
local blb = lf.Create("button")
|
||||
:SetText("Load binary")
|
||||
:SetWidth(67)
|
||||
blb.OnClick = loadHandler("sfs", function(f) sound:loadBinary(f) end)
|
||||
f:AddItem(blb)
|
||||
|
||||
local eb = lf.Create("button")
|
||||
:SetText("Export WAV")
|
||||
:SetWidth(140)
|
||||
eb.OnClick = saveHandler("wav", function(f) sound:exportWAV(f) end)
|
||||
f:AddItem(eb)
|
||||
|
||||
f:SetPos(485, 455):SetSize(150, 140)
|
||||
|
||||
lb:SetPos(78, 47)
|
||||
bsb:SetY(77)
|
||||
blb:SetPos(78, 77)
|
||||
eb:SetY(107)
|
||||
end
|
||||
|
||||
function createOther()
|
||||
local f = lf.Create("form")
|
||||
:SetName("Wave View")
|
||||
:SetPos(485, 5)
|
||||
:SetSize(150, 170)
|
||||
|
||||
local draw = function(o)
|
||||
if source then
|
||||
love.graphics.setColor(255, 255, 255)
|
||||
love.graphics.draw(wavecanvas, 495, 25)
|
||||
|
||||
-- Draw a fancy position cursor
|
||||
local pos = source:tell("samples")
|
||||
local max = sounddata:getSampleCount()
|
||||
local x = 495 + (pos / max) * 125
|
||||
love.graphics.setColor(255, 153, 0)
|
||||
love.graphics.line(x, 25, x, 165)
|
||||
end
|
||||
|
||||
lf.skins.available["Orange"].DrawForm(o)
|
||||
end
|
||||
f.Draw = draw
|
||||
|
||||
|
||||
local f = lf.Create("form"):SetName("Volume")
|
||||
|
||||
local t = lf.Create("text"):SetText("Master 0.5")
|
||||
f:AddItem(t)
|
||||
|
||||
|
||||
local s = lf.Create("slider")
|
||||
:SetMinMax(0, 1)
|
||||
:SetSize(135, 20)
|
||||
|
||||
s.OnValueChanged = function(o)
|
||||
local v = o:GetValue()
|
||||
if v <= 0.52 and v >= 0.48 and v ~= 0.5 then
|
||||
o:SetValue(0.5)
|
||||
v = 0.5
|
||||
end
|
||||
sound.volume.master = v
|
||||
t:SetText("Master " .. tostring(math.floor(v * 100) / 100))
|
||||
end
|
||||
|
||||
s:SetValue(sound.volume.master)
|
||||
f:AddItem(s)
|
||||
|
||||
|
||||
local t = lf.Create("text"):SetText("Sound 0.5")
|
||||
f:AddItem(t)
|
||||
|
||||
local s = lf.Create("slider")
|
||||
:SetMinMax(0, 1)
|
||||
:SetSize(135, 20)
|
||||
|
||||
s.OnValueChanged = function(o)
|
||||
local v = o:GetValue()
|
||||
if v <= 0.52 and v >= 0.48 and v ~= 0.5 then
|
||||
o:SetValue(0.5)
|
||||
v = 0.5
|
||||
end
|
||||
sound.volume.sound = v
|
||||
t:SetText("Sound " .. tostring(math.floor(v * 100) / 100))
|
||||
end
|
||||
|
||||
s:SetValue(sound.volume.sound)
|
||||
f:AddItem(s)
|
||||
|
||||
|
||||
f:SetPos(485, 340):SetWidth(150)
|
||||
|
||||
|
||||
local f = lf.Create("form"):SetName("Times / Duration")
|
||||
|
||||
local t = lf.Create("text"):SetText("Generation: 0ms")
|
||||
f:AddItem(t)
|
||||
statistics.generationtext = t
|
||||
|
||||
local t = lf.Create("text"):SetText("Transfer: 0ms")
|
||||
f:AddItem(t)
|
||||
statistics.transfertext = t
|
||||
|
||||
local t = lf.Create("text"):SetText("Wave View: 0ms")
|
||||
f:AddItem(t)
|
||||
statistics.waveviewtext = t
|
||||
|
||||
local t = lf.Create("text"):SetText("Duration: 0ms")
|
||||
f:AddItem(t)
|
||||
statistics.durationtext = t
|
||||
|
||||
f:SetPos(485, 185):SetWidth(150)
|
||||
end
|
||||
|
||||
function updateParameters()
|
||||
-- Iterate through the list of parameters and update all of them
|
||||
for i1, v1 in ipairs(guicategories) do
|
||||
for i2, v2 in ipairs(v1[3]) do
|
||||
local v = sound[v1[2]][v2[2]]
|
||||
local s, t = unpack(guiparams[v1[2]][v2[2]])
|
||||
s:SetValue(v)
|
||||
t:SetText(math.floor(v * 100) / 100)
|
||||
end
|
||||
end
|
||||
|
||||
local s, t = unpack(guiparams.repeatspeed)
|
||||
local v = sound.repeatspeed
|
||||
|
||||
s:SetValue(v)
|
||||
t:SetText("Repeat Speed " .. tostring(math.floor(v * 100) / 100))
|
||||
|
||||
guiparams.waveform:SetChoice(waveFormList[sound.wavetype])
|
||||
end
|
||||
|
||||
function updateWaveCanvas(waveview)
|
||||
local t = love.timer.getTime()
|
||||
wavecanvas:clear()
|
||||
love.graphics.setCanvas(wavecanvas)
|
||||
love.graphics.setColor(255, 255, 255)
|
||||
love.graphics.setLineStyle("rough")
|
||||
|
||||
-- Iterate through the passed table and draw all lines to the canvas
|
||||
local step = 125 / #waveview
|
||||
local last = 70
|
||||
for i, v in ipairs(waveview) do
|
||||
local x = (i * step)
|
||||
local y = (-v + 1) * 70
|
||||
|
||||
love.graphics.line(x - step, last, x, y)
|
||||
last = y
|
||||
end
|
||||
|
||||
-- Draw the zero line
|
||||
love.graphics.setColor(255, 80, 51, 200)
|
||||
love.graphics.line(0, 70, 125, 70)
|
||||
|
||||
love.graphics.setCanvas()
|
||||
t = love.timer.getTime() - t
|
||||
statistics.waveview = math.floor(t * 10000) / 10
|
||||
end
|
||||
|
||||
function updateStatistics()
|
||||
statistics.durationtext:SetText("Duration: " .. statistics.duration .. " ms")
|
||||
statistics.transfertext:SetText("Transfer: " .. statistics.transfer .. " ms")
|
||||
statistics.waveviewtext:SetText("Wave View: " .. statistics.waveview .. " ms")
|
||||
statistics.generationtext:SetText("Generation: " .. statistics.generation .. " ms")
|
||||
end
|
||||
|
||||
function love.load()
|
||||
require("loveframes")
|
||||
lf = loveframes
|
||||
lf.util.SetActiveSkin("Orange")
|
||||
|
||||
love.graphics.setBackgroundColor(200, 200, 200)
|
||||
|
||||
if not love.filesystem.isDirectory("sounds") then
|
||||
love.filesystem.createDirectory("sounds")
|
||||
end
|
||||
|
||||
sound = sfxr.newSound()
|
||||
|
||||
createSeedBox()
|
||||
createPresetGenerators()
|
||||
createRandomizers()
|
||||
createParameters()
|
||||
createActionButtons()
|
||||
createOther()
|
||||
|
||||
wavecanvas = love.graphics.newCanvas(125, 140)
|
||||
|
||||
love.mousepressed = lf.mousepressed
|
||||
love.mousereleased = lf.mousereleased
|
||||
love.keyreleased = lf.keyreleased
|
||||
love.textinput = lf.textinput
|
||||
end
|
||||
|
||||
function love.update(dt)
|
||||
lf.update(dt)
|
||||
if source then
|
||||
if playing and not source:isPlaying() then
|
||||
playing = false
|
||||
playbutton:SetText("Generate and Play")
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
function love.draw()
|
||||
lf.draw()
|
||||
end
|
||||
|
||||
function love.keypressed(key)
|
||||
if key == " " then
|
||||
playSound()
|
||||
elseif key == "escape" then
|
||||
love.event.push("quit")
|
||||
end
|
||||
lf.keypressed(key)
|
||||
end
|
||||
1799
libs/sfxrlua/docs/api/sfxr.html
Normal file
1799
libs/sfxrlua/docs/api/sfxr.html
Normal file
File diff suppressed because it is too large
Load diff
1799
libs/sfxrlua/docs/index.html
Normal file
1799
libs/sfxrlua/docs/index.html
Normal file
File diff suppressed because it is too large
Load diff
304
libs/sfxrlua/docs/ldoc_pale.css
Normal file
304
libs/sfxrlua/docs/ldoc_pale.css
Normal file
|
|
@ -0,0 +1,304 @@
|
|||
/* BEGIN RESET
|
||||
|
||||
Copyright (c) 2010, Yahoo! Inc. All rights reserved.
|
||||
Code licensed under the BSD License:
|
||||
http://developer.yahoo.com/yui/license.html
|
||||
version: 2.8.2r1
|
||||
*/
|
||||
html {
|
||||
color: #000;
|
||||
background: #FFF;
|
||||
}
|
||||
body,div,dl,dt,dd,ul,ol,li,h1,h2,h3,h4,h5,h6,pre,code,form,fieldset,legend,input,button,textarea,p,blockquote,th,td {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
table {
|
||||
border-collapse: collapse;
|
||||
border-spacing: 0;
|
||||
}
|
||||
fieldset,img {
|
||||
border: 0;
|
||||
}
|
||||
address,caption,cite,code,dfn,em,strong,th,var,optgroup {
|
||||
font-style: inherit;
|
||||
font-weight: inherit;
|
||||
}
|
||||
del,ins {
|
||||
text-decoration: none;
|
||||
}
|
||||
li {
|
||||
list-style: disc;
|
||||
margin-left: 20px;
|
||||
}
|
||||
caption,th {
|
||||
text-align: left;
|
||||
}
|
||||
h1,h2,h3,h4,h5,h6 {
|
||||
font-size: 100%;
|
||||
font-weight: bold;
|
||||
}
|
||||
q:before,q:after {
|
||||
content: '';
|
||||
}
|
||||
abbr,acronym {
|
||||
border: 0;
|
||||
font-variant: normal;
|
||||
}
|
||||
sup {
|
||||
vertical-align: baseline;
|
||||
}
|
||||
sub {
|
||||
vertical-align: baseline;
|
||||
}
|
||||
legend {
|
||||
color: #000;
|
||||
}
|
||||
input,button,textarea,select,optgroup,option {
|
||||
font-family: inherit;
|
||||
font-size: inherit;
|
||||
font-style: inherit;
|
||||
font-weight: inherit;
|
||||
}
|
||||
input,button,textarea,select {*font-size:100%;
|
||||
}
|
||||
/* END RESET */
|
||||
|
||||
body {
|
||||
margin-left: 1em;
|
||||
margin-right: 1em;
|
||||
font-family: arial, helvetica, geneva, sans-serif;
|
||||
background-color: #ffffff; margin: 0px;
|
||||
}
|
||||
|
||||
code, tt { font-family: monospace; font-size: 1.1em; }
|
||||
span.parameter { font-family:monospace; }
|
||||
span.parameter:after { content:":"; }
|
||||
span.types:before { content:"("; }
|
||||
span.types:after { content:")"; }
|
||||
.type { font-weight: bold; font-style:italic }
|
||||
|
||||
body, p, td, th { font-size: .95em; line-height: 1.2em;}
|
||||
|
||||
p, ul { margin: 10px 0 0 0px;}
|
||||
|
||||
strong { font-weight: bold;}
|
||||
|
||||
em { font-style: italic;}
|
||||
|
||||
h1 {
|
||||
font-size: 1.5em;
|
||||
margin: 0 0 20px 0;
|
||||
}
|
||||
h2, h3, h4 { margin: 15px 0 10px 0; }
|
||||
h2 { font-size: 1.25em; }
|
||||
h3 { font-size: 1.15em; }
|
||||
h4 { font-size: 1.06em; }
|
||||
|
||||
a:link { font-weight: bold; color: #004080; text-decoration: none; }
|
||||
a:visited { font-weight: bold; color: #006699; text-decoration: none; }
|
||||
a:link:hover { text-decoration: underline; }
|
||||
|
||||
hr {
|
||||
color:#cccccc;
|
||||
background: #00007f;
|
||||
height: 1px;
|
||||
}
|
||||
|
||||
blockquote { margin-left: 3em; }
|
||||
|
||||
ul { list-style-type: disc; }
|
||||
|
||||
p.name {
|
||||
font-family: "Andale Mono", monospace;
|
||||
padding-top: 1em;
|
||||
}
|
||||
|
||||
pre {
|
||||
background-color: rgb(245, 245, 245);
|
||||
border: 1px solid #C0C0C0; /* silver */
|
||||
padding: 10px;
|
||||
margin: 10px 0 10px 0;
|
||||
overflow: auto;
|
||||
font-family: "Andale Mono", monospace;
|
||||
}
|
||||
|
||||
pre.example {
|
||||
font-size: .85em;
|
||||
}
|
||||
|
||||
table.index { border: 1px #00007f; }
|
||||
table.index td { text-align: left; vertical-align: top; }
|
||||
|
||||
#container {
|
||||
margin-left: 1em;
|
||||
margin-right: 1em;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
#product {
|
||||
text-align: center;
|
||||
border-bottom: 1px solid #cccccc;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
#product big {
|
||||
font-size: 2em;
|
||||
}
|
||||
|
||||
#main {
|
||||
background-color:#FFFFFF; // #f0f0f0;
|
||||
//border-left: 2px solid #cccccc;
|
||||
}
|
||||
|
||||
#navigation {
|
||||
float: left;
|
||||
width: 14em;
|
||||
vertical-align: top;
|
||||
background-color:#FFFFFF; // #f0f0f0;
|
||||
border-right: 2px solid #cccccc;
|
||||
overflow: visible;
|
||||
}
|
||||
|
||||
#navigation h2 {
|
||||
background-color:#FFFFFF;//:#e7e7e7;
|
||||
font-size:1.1em;
|
||||
color:#000000;
|
||||
text-align: left;
|
||||
padding:0.2em;
|
||||
//border-top:1px solid #dddddd;
|
||||
border-bottom:1px solid #dddddd;
|
||||
}
|
||||
|
||||
#navigation ul
|
||||
{
|
||||
font-size:1em;
|
||||
list-style-type: none;
|
||||
margin: 1px 1px 10px 1px;
|
||||
}
|
||||
|
||||
#navigation li {
|
||||
text-indent: -1em;
|
||||
display: block;
|
||||
margin: 3px 0px 0px 22px;
|
||||
}
|
||||
|
||||
#navigation li li a {
|
||||
margin: 0px 3px 0px -1em;
|
||||
}
|
||||
|
||||
#content {
|
||||
margin-left: 14em;
|
||||
padding: 1em;
|
||||
width: 700px;
|
||||
border-left: 2px solid #cccccc;
|
||||
// border-right: 2px solid #cccccc;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
#about {
|
||||
clear: both;
|
||||
padding: 5px;
|
||||
border-top: 2px solid #cccccc;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
@media print {
|
||||
body {
|
||||
font: 12pt "Times New Roman", "TimeNR", Times, serif;
|
||||
}
|
||||
a { font-weight: bold; color: #004080; text-decoration: underline; }
|
||||
|
||||
#main {
|
||||
background-color: #ffffff;
|
||||
border-left: 0px;
|
||||
}
|
||||
|
||||
#container {
|
||||
margin-left: 2%;
|
||||
margin-right: 2%;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
#content {
|
||||
padding: 1em;
|
||||
background-color: #ffffff;
|
||||
}
|
||||
|
||||
#navigation {
|
||||
display: none;
|
||||
}
|
||||
pre.example {
|
||||
font-family: "Andale Mono", monospace;
|
||||
font-size: 10pt;
|
||||
page-break-inside: avoid;
|
||||
}
|
||||
}
|
||||
|
||||
table.module_list {
|
||||
border-width: 1px;
|
||||
border-style: solid;
|
||||
border-color: #cccccc;
|
||||
border-collapse: collapse;
|
||||
}
|
||||
table.module_list td {
|
||||
border-width: 1px;
|
||||
padding: 3px;
|
||||
border-style: solid;
|
||||
border-color: #cccccc;
|
||||
}
|
||||
table.module_list td.name { background-color: #f0f0f0; ; min-width: 200px; }
|
||||
table.module_list td.summary { width: 100%; }
|
||||
|
||||
table.function_list {
|
||||
border-width: 1px;
|
||||
border-style: solid;
|
||||
border-color: #cccccc;
|
||||
border-collapse: collapse;
|
||||
}
|
||||
table.function_list td {
|
||||
border-width: 1px;
|
||||
padding: 3px;
|
||||
border-style: solid;
|
||||
border-color: #cccccc;
|
||||
}
|
||||
table.function_list td.name { background-color: #f6f6ff; ; min-width: 200px; }
|
||||
table.function_list td.summary { width: 100%; }
|
||||
|
||||
dl.table dt, dl.function dt {border-top: 1px solid #ccc; padding-top: 1em;}
|
||||
dl.table dd, dl.function dd {padding-bottom: 1em; margin: 10px 0 0 20px;}
|
||||
dl.table h3, dl.function h3 {font-size: .95em;}
|
||||
|
||||
ul.nowrap {
|
||||
overflow:auto;
|
||||
whitespace:nowrap;
|
||||
}
|
||||
|
||||
/* stop sublists from having initial vertical space */
|
||||
ul ul { margin-top: 0px; }
|
||||
ol ul { margin-top: 0px; }
|
||||
ol ol { margin-top: 0px; }
|
||||
ul ol { margin-top: 0px; }
|
||||
|
||||
/* make the target distinct; helps when we're navigating to a function */
|
||||
a:target + * {
|
||||
background-color: #FF9;
|
||||
}
|
||||
|
||||
|
||||
/* styles for prettification of source */
|
||||
pre .comment { color: #558817; }
|
||||
pre .constant { color: #a8660d; }
|
||||
pre .escape { color: #844631; }
|
||||
pre .keyword { color: #aa5050; font-weight: bold; }
|
||||
pre .library { color: #0e7c6b; }
|
||||
pre .marker { color: #512b1e; background: #fedc56; font-weight: bold; }
|
||||
pre .string { color: #8080ff; }
|
||||
pre .number { color: #f8660d; }
|
||||
pre .operator { color: #2239a8; font-weight: bold; }
|
||||
pre .preprocessor, pre .prepro { color: #a33243; }
|
||||
pre .global { color: #800080; }
|
||||
pre .user-keyword { color: #800080; }
|
||||
pre .prompt { color: #558817; }
|
||||
pre .url { color: #272fc2; text-decoration: underline; }
|
||||
|
||||
28
libs/sfxrlua/rockspec/sfxr-0.0.2-1.rockspec
Normal file
28
libs/sfxrlua/rockspec/sfxr-0.0.2-1.rockspec
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
package = "sfxr"
|
||||
version = "0.0.2-1"
|
||||
source = {
|
||||
url = "git://github.com/nucular/sfxrlua",
|
||||
tag = "v0.0.2"
|
||||
}
|
||||
description = {
|
||||
summary = "A port of the sfxr sound effect synthesizer to Lua",
|
||||
detailed = [[
|
||||
A port of the sfxr sound effect synthesizer to pure Lua, designed to be used
|
||||
together with the awesome LÖVE game framework.
|
||||
]],
|
||||
homepage = "https://github.com/nucular/sfxrlua",
|
||||
license = "MIT/X11"
|
||||
}
|
||||
dependencies = {
|
||||
"lua ~> 5.1"
|
||||
-- bitop?
|
||||
}
|
||||
build = {
|
||||
type = "builtin",
|
||||
modules = {
|
||||
sfxr = "sfxr.lua"
|
||||
},
|
||||
copy_directories = {
|
||||
"docs"
|
||||
}
|
||||
}
|
||||
28
libs/sfxrlua/rockspec/sfxr-scm-1.rockspec
Normal file
28
libs/sfxrlua/rockspec/sfxr-scm-1.rockspec
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
package = "sfxr"
|
||||
version = "scm-1"
|
||||
source = {
|
||||
url = "git://github.com/nucular/sfxrlua",
|
||||
branch = "master"
|
||||
}
|
||||
description = {
|
||||
summary = "A port of the sfxr sound effect synthesizer to Lua",
|
||||
detailed = [[
|
||||
A port of the sfxr sound effect synthesizer to pure Lua, designed to be used
|
||||
together with the awesome LÖVE game framework.
|
||||
]],
|
||||
homepage = "https://github.com/nucular/sfxrlua",
|
||||
license = "MIT/X11"
|
||||
}
|
||||
dependencies = {
|
||||
"lua ~> 5.1"
|
||||
-- bitop?
|
||||
}
|
||||
build = {
|
||||
type = "builtin",
|
||||
modules = {
|
||||
sfxr = "sfxr.lua"
|
||||
},
|
||||
copy_directories = {
|
||||
"docs"
|
||||
}
|
||||
}
|
||||
1536
libs/sfxrlua/sfxr.lua
Normal file
1536
libs/sfxrlua/sfxr.lua
Normal file
File diff suppressed because it is too large
Load diff
Loading…
Add table
Add a link
Reference in a new issue