Moar fixes

wrap unicode.lower/upper since utf8's handling of numbers differs than
oc's handling of numbers
move getCharWidth out of unicode.lua and into main.lua
Fix characters being rendered when they should be hidden by a wide
character
Fix wide characters not setting the overlapping cell as a space
Fix the overlapping character not being rendered when the wide character
is removed
Fix fill treating wide characters as not wide characters
Fix set being crashed on invalid characters
Change checkArg and compCheckArg to non merge versions, and edit the
error message in compCheckArg to be similar to actual error messages
This commit is contained in:
gamax92 2015-06-19 19:02:16 -06:00
parent 744e640bea
commit d29c2bc7d7
3 changed files with 58 additions and 32 deletions

View File

@ -3,21 +3,24 @@ local env = ...
local utf8 = require("utf8")
env.unicode = {
lower = utf8.lower,
upper = utf8.upper,
char = utf8.char,
len = utf8.len,
reverse = utf8.reverse,
sub = utf8.sub,
}
local function getCharWidth(char)
if unifont[char] ~= nil then
return #unifont[char] / 32
end
return 1
function env.unicode.lower(str)
cprint("unicode.lower", str)
if type(str) == "number" then str = tostring(str) end
checkArg(1,str,"string")
return utf8.lower(str)
end
function env.unicode.upper(str)
cprint("unicode.upper", str)
if type(str) == "number" then str = tostring(str) end
checkArg(1,str,"string")
return utf8.upper(str)
end
function env.unicode.isWide(str)
cprint("unicode.isWide", str)
checkArg(1,str,"string")

View File

@ -111,8 +111,8 @@ function elsa.draw()
SDL.renderPresent(renderer)
end
local char8 = ffi.new("uint32_t[?]", 8*16);
local char16 = ffi.new("uint32_t[?]", 16*16);
local char8 = ffi.new("uint32_t[?]", 8*16)
local char16 = ffi.new("uint32_t[?]", 16*16)
local function renderChar(char,x,y,fg,bg)
if unifont[char] == nil then
char = 63
@ -139,15 +139,31 @@ local function renderChar(char,x,y,fg,bg)
SDL.updateTexture(texture, ffi.new("SDL_Rect",{x=x,y=y,w=size*4,h=16}), pchar, (size*4) * ffi.sizeof("uint32_t"))
end
local function setPos(x,y,c,fg,bg)
local renderchange = screen.txt[y][x] ~= utf8.char(c) or screen.bg[y][x] ~= scrbgc or (screen.txt[y][x] ~= " " and screen.fg[y][x] ~= scrfgc)
local function screenSet(x,y,c)
screen.txt[y][x] = utf8.char(c)
screen.fg[y][x] = scrfgc
screen.bg[y][x] = scrbgc
screen.fgp[y][x] = scrfgp
screen.bgp[y][x] = scrbgp
end
local function setPos(x,y,c,fg,bg)
local renderchange = screen.txt[y][x] ~= utf8.char(c) or screen.bg[y][x] ~= scrbgc or (screen.txt[y][x] ~= " " and screen.fg[y][x] ~= scrfgc)
local charWidth = getCharWidth(c)
local renderafter = getCharWidth(utf8.byte(screen.txt[y][x])) > 1 and charWidth == 1 and x < width
if x > 1 and getCharWidth(utf8.byte(screen.txt[y][x-1])) > 1 then
renderchange = false
else
screenSet(x,y,c)
end
if renderchange then
renderChar(c,(x-1)*8,(y-1)*16,fg,bg)
if charWidth > 1 and x < width then
screenSet(x+1,y,32)
end
end
if renderafter then
renderChar(32,x*8,(y-1)*16,screen.fg[y][x+1],screen.bg[y][x+1])
end
end
@ -248,14 +264,14 @@ function cec.fill(x1, y1, w, h, char) -- Fills a portion of the screen at the sp
if w <= 0 or h <= 0 then
return true
end
local x2 = x1+w-1
local code = utf8.byte(char)
local x2 = x1+(w*getCharWidth(code))-1
local y2 = y1+h-1
if x2 < 1 or y2 < 1 or x1 > width or y1 > height then
return true
end
local code = utf8.byte(char)
for y = y1,y2 do
for x = x1,x2 do
for x = x1,x2,getCharWidth(code) do
setPos(x,y,code,scrfgc,scrbgc)
end
end
@ -305,7 +321,7 @@ function cec.set(x, y, value, vertical) -- Plots a string value to the screen at
if x >= 1 then
setPos(x,y,c,scrfgc,scrbgc)
end
x = x + #unifont[c]/32
x = x + getCharWidth(c)
if x > width then break end
end
end

View File

@ -45,27 +45,28 @@ machine = {
signals = {},
}
local function _checkArg(pos, n, have, ...)
local function check(have, want, ...)
if not want then
return false
else
return have == want or check(have, ...)
end
end
function checkArg(n, have, ...)
have = type(have)
local function check(want, ...)
if not want then
return false
else
return have == want or check(...)
end
end
if not check(...) then
if not check(have, ...) then
local msg = string.format("bad argument #%d (%s expected, got %s)", n, table.concat({...}, " or "), have)
error(msg, pos)
error(msg, 3)
end
end
function checkArg(...)
_checkArg(4, ...)
end
function compCheckArg(...)
_checkArg(5, ...)
function compCheckArg(n, have, ...)
have = type(have)
if not check(have, ...) then
local msg = string.format("bad arguments #%d (%s expected, got %s)", n, table.concat({...}, " or "), have)
error(msg, 4)
end
end
if true then
@ -236,6 +237,12 @@ for line in elsa.filesystem.lines("unifont.hex") do
local a,b = line:match("(.+):(.*)")
unifont[tonumber(a,16)] = b
end
function getCharWidth(char)
if unifont[char] ~= nil then
return #unifont[char] / 32
end
return 1
end
-- load api's into environment
elsa.filesystem.load("apis/computer.lua")(env)