Last active
August 29, 2015 14:06
-
-
Save geekhunger/d19e20c53c20e63c8412 to your computer and use it in GitHub Desktop.
Simplified Painting App, made with Codea.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
--# Color | |
-- modified version from https://github.com/EmmanuelOga/columns/blob/master/utils/color.lua | |
--[[ | |
* Converts an RGB color value to HSL. Conversion formula | |
* adapted from http://en.wikipedia.org/wiki/HSL_color_space. | |
* Assumes r, g, and b are contained in the set [0, 255] and | |
* returns h, s, and l in the set [0, 1]. | |
* | |
* @param Number r The red color value | |
* @param Number g The green color value | |
* @param Number b The blue color value | |
* @return Array The HSL representation | |
]] | |
function rgb2hsl(r, g, b) | |
r,g,b = r/255, g/255, b/255 | |
local max, min = math.max(r,g,b), math.min(r,g,b) | |
local h, s, l = 0, 0, (max + min)/2 -- achromatic | |
if max ~= min then | |
local d = max - min | |
if l > .5 then s = d/(2 - max - min) else s = d/(max + min) end | |
if max == r then | |
h = (g - b)/d | |
if g < b then h = h + 6 end | |
elseif max == g then h = (b - r)/d + 2 | |
elseif max == b then h = (r - g)/d + 4 | |
end | |
h = h/6 | |
end | |
return h,s,l | |
end | |
--[[ | |
* Converts an HSL color value to RGB. Conversion formula | |
* adapted from http://en.wikipedia.org/wiki/HSL_color_space. | |
* Assumes h, s, and l are contained in the set [0, 1] and | |
* returns r, g, and b in the set [0, 255]. | |
* | |
* @param Number h The hue | |
* @param Number s The saturation | |
* @param Number l The lightness | |
* @return Array The RGB representation | |
]] | |
function hsl2rgb(h, s, l) | |
local r,g,b = l,l,l -- achromatic | |
if s ~= 0 then | |
local function hue2rgb(p, q, t) | |
if t < 0 then t = t + 1 end | |
if t > 1 then t = t - 1 end | |
if t < 1/6 then return p + (q - p) * 6 * t end | |
if t < 1/2 then return q end | |
if t < 2/3 then return p + (q - p) * (2/3 - t) * 6 end | |
return p | |
end | |
local q = l < .5 and l*(1 + s) or l + s - l*s | |
local p = 2 * l - q | |
r = hue2rgb(p, q, h + 1/3) | |
g = hue2rgb(p, q, h) | |
b = hue2rgb(p, q, h - 1/3) | |
end | |
return r*255, g*255, b*255 | |
end | |
--[[ | |
* Converts an RGB color value to HSV. Conversion formula | |
* adapted from http://en.wikipedia.org/wiki/HSV_color_space. | |
* Assumes r, g, and b are contained in the set [0, 255] and | |
* returns h, s, and v in the set [0, 1]. | |
* | |
* @param Number r The red color value | |
* @param Number g The green color value | |
* @param Number b The blue color value | |
* @return Array The HSV representation | |
]] | |
function rgb2hsv(r, g, b) | |
r, g, b = r / 255, g / 255, b / 255 | |
local max, min = math.max(r, g, b), math.min(r, g, b) | |
local h, s, v = nil, nil, max | |
local d = max - min | |
if max == 0 then s = 0 else s = d / max end | |
if max == min then h = 0 | |
else | |
if max == r then h = g < b and h + 6 or (g - b) / d | |
elseif max == g then h = (b - r) / d + 2 | |
elseif max == b then h = (r - g) / d + 4 end | |
h = h / 6 | |
end | |
return h, s, v | |
end | |
--[[ | |
* Converts an HSV color value to RGB. Conversion formula | |
* adapted from http://en.wikipedia.org/wiki/HSV_color_space. | |
* Assumes h, s, and v are contained in the set [0, 1] and | |
* returns r, g, and b in the set [0, 255]. | |
* | |
* @param Number h The hue | |
* @param Number s The saturation | |
* @param Number v The value | |
* @return Array The RGB representation | |
]] | |
function hsv2rgb(h, s, v) | |
local r, g, b | |
local i = math.floor(h * 6); | |
local f = h * 6 - i; | |
local p = v * (1 - s); | |
local q = v * (1 - f * s); | |
local t = v * (1 - (1 - f) * s); | |
i = i % 6 | |
if i == 0 then r, g, b = v, t, p | |
elseif i == 1 then r, g, b = q, v, p | |
elseif i == 2 then r, g, b = p, v, t | |
elseif i == 3 then r, g, b = p, q, v | |
elseif i == 4 then r, g, b = t, p, v | |
elseif i == 5 then r, g, b = v, p, q | |
end | |
return r * 255, g * 255, b * 255 | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
--# Main | |
Scale = .25 -- image quality settings (may affect speed also) | |
Canvas = readImage("Documents:Canvas") | |
if not Canvas then | |
supportedOrientations(CurrentOrientation, (CurrentOrientation~=3 and CurrentOrientation~=1) and CurrentOrientation+1 or CurrentOrientation-1) | |
Canvas = image(WIDTH * Scale, HEIGHT * Scale) | |
else | |
if Canvas.width < Canvas.height then | |
supportedOrientations(PORTRAIT_ANY) | |
else | |
supportedOrientations(LANDSCAPE_ANY) | |
end | |
end | |
function setup() | |
noSmooth() | |
displayMode(OVERLAY) | |
parameter.boolean("Mirror", false) | |
parameter.color("BG", loadstring(readLocalData("BG", "return color(221,219,199,255)"))(), function() | |
if BG.a < 255 then BG.a = 255 end | |
saveLocalData("BG", "return color"..tostring(BG)) | |
end) | |
parameter.color("Color", loadstring(readLocalData("Color", "return color(41,151,176,255)"))(), function() | |
if Colorpicker then Colorpicker = false end | |
if Color.a > 0 then Color.a = 255 end | |
Schade = select(3, rgb2hsl(Color.r, Color.g, Color.b)) | |
saveLocalData("Color", "return color"..tostring(Color)) | |
end) | |
parameter.boolean("Colorpicker", false) | |
parameter.number("Schade", .001, .999, Schade, function() | |
if Colorpicker then Colorpicker = false end | |
local h, s, l = rgb2hsl(Color.r, Color.g, Color.b) | |
Color = color(hsl2rgb(h, s, Schade)) | |
saveLocalData("Color", "return color"..tostring(Color)) -- fix because Color = color() doesn't trigger its prameter callback | |
end) | |
parameter.integer("Size", 1, 50, loadstring(readLocalData("Size", "return 2"))(), function() | |
saveLocalData("Size", "return "..tostring(Size)) | |
end) | |
end | |
function orientationChanged() | |
if _allowFlipping then | |
local flipped = image(Canvas.width, Canvas.height) | |
setContext(flipped) | |
sprite(Canvas, WIDTH/2 * Scale, HEIGHT/2 * Scale, -Canvas.width, Canvas.height) | |
setContext() | |
Canvas = flipped | |
else | |
_allowFlipping = true | |
end | |
end | |
local function deviceShaking() | |
local acceleration = UserAcceleration | |
local intensity = 2 -- adjust min. shaking intensity to trigger this event! | |
if UserAcceleration.x > intensity or acceleration.y > intensity or acceleration.z > intensity then | |
_deviceShakingUpdatedAt = ElapsedTime | |
_deviceShakingBegunAt = _deviceShakingBegunAt or ElapsedTime | |
-- first shake triggers listening process | |
-- listen if shaking continues for [x] seconds then device is considered shaking on purpose | |
if (ElapsedTime - _deviceShakingBegunAt) >= .5 then return true end | |
end | |
if _deviceShakingUpdatedAt and (ElapsedTime > (_deviceShakingUpdatedAt + .5)) then | |
_deviceShakingUpdatedAt = nil | |
_deviceShakingBegunAt = nil | |
end | |
return false | |
end | |
function draw() | |
background(BG) | |
sprite(Canvas, WIDTH/2, HEIGHT/2, WIDTH, HEIGHT) | |
if Mirror then | |
stroke(127) | |
strokeWidth(1) | |
line(WIDTH/2, 0, WIDTH/2, HEIGHT) | |
end | |
if Touch then | |
local size = not Colorpicker and Size*2 or 50 | |
local pos = not Colorpicker and vec2(Touch.x, Touch.y) or vec2(Touch.x, Touch.y + size) | |
fill(Color) | |
strokeWidth(1) | |
stroke(0) | |
ellipse(pos.x, pos.y, size + strokeWidth()) | |
stroke(255) | |
ellipse(pos.x, pos.y, size) | |
end | |
if deviceShaking() then | |
saveLocalData("BG", "return color(221,219,199,255)") | |
saveLocalData("Color", "return color(41,151,176,255)") | |
saveLocalData("Size", "return 2") | |
saveImage("Documents:Canvas", nil) | |
restart() | |
end | |
end | |
function touched(touch) | |
if not Touch or Touch.id == touch.id then Touch = touch end | |
if Touch.state == BEGAN then tween.resetAll() end | |
if Touch.state == ENDED then | |
if Touch.id == touch.id then | |
Touch = nil | |
if Colorpicker then Colorpicker = false end | |
if _SaveCanvas then | |
tween.delay(.375, function() saveImage("Documents:Canvas", Canvas) end) | |
_SaveCanvas = nil | |
end | |
end | |
else | |
if not Colorpicker then | |
setContext(Canvas) | |
noFill() | |
strokeWidth(Size/2) | |
stroke(Color) | |
if Color.a == 0 then | |
stroke(0,0,0,255) | |
blendMode(ZERO, ONE_MINUS_SRC_ALPHA) | |
end | |
line(Touch.prevX * Scale, Touch.prevY * Scale, Touch.x * Scale, Touch.y * Scale, ROUND) | |
if Mirror then line((WIDTH - Touch.prevX) * Scale, Touch.prevY * Scale, (WIDTH - Touch.x) * Scale, Touch.y * Scale, ROUND) end | |
setContext() | |
blendMode(NORMAL) | |
_SaveCanvas = true | |
else | |
local col = color(Canvas:get(Touch.x * Scale, Touch.y * Scale)) | |
if col == color(0,0,0,0) then col = BG end | |
if col.a < 255 then col = Color end | |
Color = col | |
Schade = select(3, rgb2hsl(Color.r, Color.g, Color.b)) | |
saveLocalData("Color", "return color"..tostring(Color)) -- fix because Color = color() doesn't trigger its prameter callback | |
end | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment