Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- -- Font Generator for Texter
- -- Version 0.1.0
- TFGen = {}
- TFGen.MAIN_WIDTH = 611
- TFGen.MAIN_HEIGHT = 383
- TFGen.ShowSelectRect = false
- TFGen.Drawing = {
- W = 0,
- H = 0,
- StartX = 0,
- StartY = 0,
- Scrolled = 0,
- Modifier = 0
- }
- TFGen.UIItems = {
- -- { --example
- -- Type = "fill",
- -- Pos = {X=1, Y=1, W=1, H=1}, --X,Y,X2,Y2 for line
- -- Color = {R=255, G=255, B=255, A=125},
- -- Life = 555 -- -1:forever X:stop render after X frames
- -- Fadeout = {From=255, T=30} -- fadeout(alpha), "to" is always 0
- -- }
- }
- TFGen.GlyphCells = {} --structure { {X,Y,W,H} }
- TFGen.Glyph = {} -- structure: {Height, {Mtx, Pos={X, Y, W, H}, Margin={Left, Right, Top}}}
- function TFGen.Init(register)
- if( register == nil or register == true ) then
- tpt.register_keypress(TFGen._HotkeyHandler)
- end
- end
- -- Event handlers
- function TFGen._HotkeyHandler(key, keyNum, modifier, event)
- if( event==1 ) then -- Modifier record for click event
- if( keyNum == 304 and modifier == 0 ) then TFGen.Drawing.Modifier = 1 end -- shift
- if( keyNum == 306 and modifier == 0 ) then TFGen.Drawing.Modifier = 64 end -- ctrl
- if( keyNum == 308 and modifier == 0 ) then TFGen.Drawing.Modifier = 256 end -- alt
- end
- if( event==2 ) then -- Modifier record for click event
- TFGen.Drawing.Modifier = 0
- end
- if( event==1 and keyNum==116 and modifier==65 ) then -- Ctrl + Shift + t, start
- TFGen.Drawing.StartX = tpt.mousex
- TFGen.Drawing.StartY = tpt.mousey
- TFGen.Drawing.StartY = tpt.mousey
- tpt.set_pause(1)
- local notRunning = pcall( tpt.register_step, TFGen._StepHandler )
- pcall( tpt.register_keypress , TFGen._KeypressHandler)
- pcall( tpt.register_mouseclick , TFGen._ClickHandler )
- table.insert(
- TFGen.UIItems,
- {
- Type = "text",
- Text = "Select an area to place glyph rectangle.\nLeft click to place, right click to undo.\nEnter to submit, space to cancle.",
- Pos = {X=205, Y=190},
- Color = {R=255, G=255, B=25, A=255},
- Life = 180,
- Fadeout = {From=255, T=60}
- }
- )
- if( notRunning ) then
- table.insert(
- TFGen.UIItems,
- {
- Type = "text",
- Text = "Font Generator for Texter is Running...",
- Pos = {X=425, Y=365},
- Color = {R=255, G=255, B=25, A=155},
- Life = -1,
- }
- )
- end
- end
- end
- function TFGen._KeypressHandler(key, keyNum, modifier, event)
- if( event==2 and keyNum==13 and modifier==0 and TFGen.Glyph[1] == nil) then -- Enter submit glyph choice, do not respose when editing
- pcall(tpt.unregister_mouseclick, TFGen._ClickHandler)
- pcall(tpt.unregister_keypress, TFGen._KeypressHandler)
- TFGen.ShowSelectRect = false
- TFGen.Glyph = TFGen._GlyphGen(TFGen.GlyphCells)
- TFGen.GlyphCells = {}
- TFGen.Editor.Init()
- TFGen.Editor.Show(true)
- end
- if( event==2 and keyNum==32 and modifier==0 ) then -- Space cancle all
- TFGen.Reset()
- end
- end
- function TFGen._ClickHandler(x, y, button, event, scroll) -- button: 0 scroll, 1 left, 2 mid, 4 right; scroll: -1 down, 1 up
- if( button == 1 and event == 3) then -- Resize rectangle
- if( TFGen.Drawing.Modifier == 0 ) then -- none
- TFGen.Drawing.W = x - TFGen.Drawing.StartX
- TFGen.Drawing.H = y - TFGen.Drawing.StartY
- if(x > TFGen.MAIN_WIDTH )then TFGen.Drawing.W = TFGen.MAIN_WIDTH - TFGen.Drawing.StartX end
- if(y > TFGen.MAIN_HEIGHT)then TFGen.Drawing.H = TFGen.MAIN_HEIGHT - TFGen.Drawing.StartY end
- end
- return false
- end
- if( button == 1 and event == 1) then -- Start draw add rectangle
- if( TFGen.Drawing.Modifier == 0 ) then -- none
- if(x > TFGen.MAIN_WIDTH )then x = TFGen.MAIN_WIDTH end
- if(y > TFGen.MAIN_HEIGHT)then y = TFGen.MAIN_HEIGHT end
- TFGen.Drawing.StartX = x
- TFGen.Drawing.StartY = y
- TFGen.ShowSelectRect = true
- end
- return false
- end
- if( button == 1 and event == 2) then -- Add rectangle
- if( TFGen.Drawing.Modifier == 0 ) then -- none
- TFGen.ShowSelectRect = false
- if(TFGen.Drawing.W < 0)then
- TFGen.Drawing.W = -1*TFGen.Drawing.W
- TFGen.Drawing.StartX = TFGen.Drawing.StartX - TFGen.Drawing.W
- end
- if(TFGen.Drawing.H < 0)then
- TFGen.Drawing.H = -1*TFGen.Drawing.H
- TFGen.Drawing.StartY = TFGen.Drawing.StartY - TFGen.Drawing.H
- end
- if(TFGen.Drawing.W > 0 and TFGen.Drawing.H > 0)then
- table.insert(
- TFGen.GlyphCells,
- {
- X = TFGen.Drawing.StartX,
- Y = TFGen.Drawing.StartY,
- W = TFGen.Drawing.W,
- H = TFGen.Drawing.H
- }
- )
- end
- end
- return false
- end
- if( button == 4 and event == 1) then -- Undo
- table.remove(TFGen.GlyphCells)
- return false
- end
- end
- function TFGen._StepHandler()
- TFGen._DrawSelectRect(TFGen.Drawing.StartX, TFGen.Drawing.StartY, TFGen.Drawing.W, TFGen.Drawing.H)
- TFGen._DrawGUI()
- end
- function TFGen._DrawGUI()
- for i, glyph in pairs(TFGen.GlyphCells) do
- tpt.drawrect(glyph.X, glyph.Y, glyph.W, glyph.H, 255, 255, 255, 125)
- end
- for i, glyph in pairs(TFGen.Glyph) do
- if(type(glyph) == "table") then
- local m = {}
- local color = {}
- if( glyph.Margin == nil ) then
- m.top = 0
- m.left = 0
- m.right = 0
- else
- if( glyph.Margin.Top == nil ) then m.top = 0 else m.top = glyph.Margin.Top end
- if( glyph.Margin.Left == nil ) then m.left = 0 else m.left = glyph.Margin.Left end
- if( glyph.Margin.Right == nil ) then m.right = 0 else m.right = glyph.Margin.Right end
- end
- if( i == TFGen.CurrentGlyphIndex )then
- color = {R=55 , G=255, B=55 , A=125}
- else
- color = {R=255, G=255, B=125, A=125}
- end
- pcall(
- tpt.drawrect,
- glyph.Pos.X - m.left,
- glyph.Pos.Y - m.top ,
- glyph.Pos.W + m.left + m.right,
- TFGen.Glyph.Height, -- No matter what glyph.Pos.H is
- color.R, color.G, color.B, color.A
- )
- local char = glyph.Char
- if( char ~= nil) then
- if( char == " " ) then char = "space" end -- Special
- pcall(
- tpt.drawtext,
- glyph.Pos.X - m.left,
- glyph.Pos.Y - m.top - 10, -- Default font height + 3?
- i..":"..char,
- color.R, color.G, color.B, color.A
- )
- end
- end
- end
- for i, item in pairs(TFGen.UIItems) do
- --Few types, so if-else-if won't be performance critical
- if item.Pos == nil then item.Pos = {X=1, Y=1, X2=1, Y2=1, W=1, H=1} end
- if item.Color == nil then item.Color = {R=255, G=255, B=255, A=125} end
- if item.Fadeout == nil then item.Fadeout = {From = 255, T=0} end
- if item.Life == nil then item.Life = 60 end
- if item.Text == nil then item.Text = "" end
- if(item.Life > 0 or item.Life == -1) then
- if(item.Life > 0)then item.Life = item.Life - 1 end
- --fadeout, no fadeout for forever ones
- if(item.Life <= item.Fadeout.T and item.Life ~= -1)then
- item.Color.A = item.Fadeout.From * item.Life/item.Fadeout.T
- end
- if(item.Type == "text") then
- tpt.drawtext(item.Pos.X, item.Pos.Y, item.Text, item.Color.R, item.Color.G, item.Color.B, item.Color.A)
- elseif (item.Type == "pixel") then
- tpt.drawpixel(item.Pos.X, item.Pos.Y, item.Color.R, item.Color.G, item.Color.B, item.Color.A)
- elseif (item.Type == "line") then
- tpt.drawline(item.Pos.X, item.Pos.Y, item.Pos.X2, item.Pos.Y2, item.Color.R, item.Color.G, item.Color.B, item.Color.A)
- elseif (item.Type == "rect") then
- tpt.drawrect(item.Pos.X, item.Pos.Y, item.Pos.W, item.Pos.H, item.Color.R, item.Color.G, item.Color.B, item.Color.A)
- elseif (item.Type == "fill" ) then
- tpt.fillrect(item.Pos.X, item.Pos.Y, item.Pos.W, item.Pos.H, item.Color.R, item.Color.G, item.Color.B, item.Color.A)
- end
- else -- You were dead
- table.remove(TFGen.UIItems, i)
- i = i-1 --Lua will shifting down other elements to close the space, so we might jump one item off without this
- end
- end
- end
- function TFGen._DrawSelectRect(posX, posY, width, height)
- if(width < 0)then
- width = -1*width
- posX = posX - width
- end
- if(height < 0)then
- height = -1*height
- posY = posY - height
- end
- if(TFGen.ShowSelectRect)then
- tpt.drawrect(posX, posY, width, height, 255, 255, 255, 125)
- end
- end
- -- Generate glyph
- function TFGen._GlyphGen(glyphCells)
- local glyphList = {}
- glyphList.Name = "font1"
- glyphList.Height = -1
- for index, glyph in pairs(glyphCells) do
- -- Minimum Bound Box detection, using the simplest methods, O(n^2)
- local mbb = {}
- for i = 1, glyph.W do
- for j = 1, glyph.H do
- if(tpt.get_property("type", glyph.X + i, glyph.Y + j) ~= 0)then
- if(mbb.left == nil )then mbb.left = glyph.X + i end --the fisrt non-empty column
- if(mbb.right == nil or mbb.right ~= glyph.X + i)then mbb.right = glyph.X + i end --the last non-empty column
- if(mbb.top == nil or mbb.top > glyph.Y + j)then mbb.top = glyph.Y + j end --the smallest non-empty row
- if(mbb.bottom == nil or mbb.bottom < glyph.Y + j)then mbb.bottom = glyph.Y + j end --the biggest non-empty row
- end
- end
- end
- if(mbb.left ~= nil and mbb.right ~= nil and mbb.top ~= nil and mbb.bottom ~= nil) then
- local glyphArea = {X=mbb.left, Y=mbb.top, W=(mbb.right - mbb.left), H=(mbb.bottom - mbb.top)}
- local mtx = TFGen._DigitizeArea(glyphArea)
- if( (mbb.bottom - mbb.top) > glyphList.Height) then
- glyphList.Height = mbb.bottom - mbb.top
- end
- table.insert(
- glyphList,
- {
- Char = "",
- Mtx = mtx,
- Pos = glyphArea,
- Margin = {Top=0, Left=0, Right=0}
- }
- )
- end
- end
- return glyphList
- end
- -- Digitize selected area
- function TFGen._DigitizeArea(area)
- local mtx = {}
- local x1 = area.X
- local x2 = area.X + area.W
- local y1 = area.Y
- local y2 = area.Y + area.H
- if(area ~= nil and area.X ~= nil and area.Y ~= nil and area.W ~= nil and area.H ~= nil)then
- for y = y1, y2 do
- local row = {}
- for x = x1, x2 do
- local isSucceed, ptype = pcall(tpt.get_property, "type", x, y)
- if(isSucceed)then
- table.insert(row, ptype)
- else
- table.insert(row, 0)
- end
- end
- table.insert(mtx, row)
- end
- end
- return mtx
- end
- -- Reset
- function TFGen.Reset()
- pcall(tpt.unregister_step, TFGen._StepHandler)
- pcall(tpt.unregister_keypress, TFGen._KeypressHandler)
- pcall(tpt.unregister_mouseclick, TFGen._ClickHandler)
- TFGen.ShowSelectRect = false
- TFGen.GlyphCells = {}
- TFGen.Glyph = {}
- TFGen.UIItems = {}
- end
- -- The glyph editor after font generation
- TFGen.Editor = {}
- TFGen.Editor.Cons = {} -- Controls table
- TFGen.Editor.Pos = {X=100, Y=100}
- TFGen.Editor.Visable = true
- TFGen.CurrentGlyphIndex = -1
- function TFGen.Editor.Init()
- -- If no glyph generated, quit
- if(TFGen.Glyph.Height == nil or TFGen.Glyph[1] == nil)then
- TFGen.Reset()
- TFGen.Editor.Reset()
- return false
- end
- tpt.register_keypress(TFGen.Editor._KeypressHandler)
- tpt.register_mouseclick(TFGen.Editor._ClickHandler)
- TFGen.CurrentGlyphIndex = 1
- local controlHeight = 14
- -- Position to show
- local properPos = TFGen.Editor.GetClosePos(TFGen.Glyph[TFGen.CurrentGlyphIndex])
- TFGen.Editor.Pos.X = properPos.X
- TFGen.Editor.Pos.Y = properPos.Y
- local editorX = properPos.X
- local editorY = properPos.Y
- local editorW = 144
- local lines = 0 -- 1st line : 0
- local prevBtn = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight * 2 + 1, "Prev" )
- local nextBtn = Button:new( editorX + editorW/2 , editorY + controlHeight * lines , editorW/2 + 1, controlHeight * 2 + 1, "Next" )
- lines = lines + 2 -- 2nd line : 2
- local nameBtn = Button:new( editorX , editorY + controlHeight * lines , editorW + 1, controlHeight + 1, "Name: "..TFGen.Glyph.Name )
- lines = lines + 1 -- 3rd line : 3
- local charBtn = Button:new( editorX , editorY + controlHeight * lines , editorW + 1, controlHeight + 1, "Char: []" )
- lines = lines + 1 -- 4th line : 4
- local autoCharBtn = Button:new( editorX , editorY + controlHeight * lines , editorW + 1, controlHeight + 1, "Auto assign" )
- lines = lines + 1 -- 5th line : 5
- local heightLabel = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight + 1, "Font Height" )
- local heightDecBtn = Button:new( editorX + editorW*3/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "-" )
- local heightBtn = Button:new( editorX + editorW*4/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, tostring(TFGen.Glyph.Height) )
- local heightIncBtn = Button:new( editorX + editorW*5/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "+" )
- lines = lines + 1 -- 6th line : 6
- local mTopLabel = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight + 1, "Margin Top" )
- local mTopDecBtn = Button:new( editorX + editorW*3/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "-" )
- local mTopBtn = Button:new( editorX + editorW*4/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "0" )
- local mTopIncBtn = Button:new( editorX + editorW*5/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "+" )
- lines = lines + 1 -- 7th line : 7
- local mLeftLabel = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight + 1, "Margin Left" )
- local mLeftDecBtn = Button:new( editorX + editorW*3/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "-" )
- local mLeftBtn = Button:new( editorX + editorW*4/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "0" )
- local mLeftIncBtn = Button:new( editorX + editorW*5/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "+" )
- lines = lines + 1 -- 8th line : 8
- local mRightLabel = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight + 1, "Margin Right" )
- local mRightDecBtn = Button:new( editorX + editorW*3/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "-" )
- local mRightBtn = Button:new( editorX + editorW*4/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "0" )
- local mRightIncBtn = Button:new( editorX + editorW*5/6, editorY + controlHeight * lines , editorW/6 + 1, controlHeight + 1, "+" )
- lines = lines + 1 -- 9th line : 9
- local deleteBtn = Button:new( editorX , editorY + controlHeight * lines , editorW + 1, controlHeight + 1, "Delete this glyph (No undo)")
- lines = lines + 1 -- 10th line : 10
- local cancelAllBtn = Button:new( editorX , editorY + controlHeight * lines , editorW/2 + 1, controlHeight * 2 + 1, "Cancel All" )
- local submitAllBtn = Button:new( editorX + editorW/2 , editorY + controlHeight * lines , editorW/2 + 1, controlHeight * 2 + 1, "Submit All" )
- prevBtn :action ( function(sender) TFGen.Editor.CommandHandler("Prev" , sender) end )
- nextBtn :action ( function(sender) TFGen.Editor.CommandHandler("Next" , sender) end )
- nameBtn :action ( function(sender) TFGen.Editor.CommandHandler("Name" , sender) end )
- charBtn :action ( function(sender) TFGen.Editor.CommandHandler("Char" , sender) end )
- autoCharBtn :action ( function(sender) TFGen.Editor.CommandHandler("AutoAssign", sender) end )
- heightDecBtn:action ( function(sender) TFGen.Editor.CommandHandler("HeightMod" , sender) end )
- heightBtn :action ( function(sender) TFGen.Editor.CommandHandler("HeightMod" , sender) end )
- heightIncBtn:action ( function(sender) TFGen.Editor.CommandHandler("HeightMod" , sender) end )
- mTopDecBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mTopBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mTopIncBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mLeftDecBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mLeftBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mLeftIncBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mRightDecBtn:action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mRightBtn :action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- mRightIncBtn:action ( function(sender) TFGen.Editor.CommandHandler("MarginMod" , sender) end )
- deleteBtn :action ( function(sender) TFGen.Editor.CommandHandler("Delete" , sender) end )
- cancelAllBtn:action ( function(sender) TFGen.Editor.CommandHandler("CancelAll" , sender) end )
- submitAllBtn:action ( function(sender) TFGen.Editor.CommandHandler("SubmitAll" , sender) end )
- TFGen.Editor.Cons.prevBtn = prevBtn
- TFGen.Editor.Cons.nextBtn = nextBtn
- TFGen.Editor.Cons.nameBtn = nameBtn
- TFGen.Editor.Cons.charBtn = charBtn
- TFGen.Editor.Cons.autoCharBtn = autoCharBtn
- TFGen.Editor.Cons.heightLabel = heightLabel
- TFGen.Editor.Cons.heightDecBtn = heightDecBtn
- TFGen.Editor.Cons.heightBtn = heightBtn
- TFGen.Editor.Cons.heightIncBtn = heightIncBtn
- TFGen.Editor.Cons.mTopLabel = mTopLabel
- TFGen.Editor.Cons.mTopDecBtn = mTopDecBtn
- TFGen.Editor.Cons.mTopBtn = mTopBtn
- TFGen.Editor.Cons.mTopIncBtn = mTopIncBtn
- TFGen.Editor.Cons.mLeftLabel = mLeftLabel
- TFGen.Editor.Cons.mLeftDecBtn = mLeftDecBtn
- TFGen.Editor.Cons.mLeftBtn = mLeftBtn
- TFGen.Editor.Cons.mLeftIncBtn = mLeftIncBtn
- TFGen.Editor.Cons.mRightLabel = mRightLabel
- TFGen.Editor.Cons.mRightDecBtn = mRightDecBtn
- TFGen.Editor.Cons.mRightBtn = mRightBtn
- TFGen.Editor.Cons.mRightIncBtn = mRightIncBtn
- TFGen.Editor.Cons.cancelAllBtn = cancelAllBtn
- TFGen.Editor.Cons.submitAllBtn = submitAllBtn
- TFGen.Editor.Cons.deleteBtn = deleteBtn
- interface.addComponent(heightLabel )
- interface.addComponent(mTopLabel )
- interface.addComponent(mLeftLabel )
- interface.addComponent(mRightLabel )
- interface.addComponent(prevBtn )
- interface.addComponent(nextBtn )
- interface.addComponent(nameBtn )
- interface.addComponent(charBtn )
- interface.addComponent(autoCharBtn )
- interface.addComponent(heightDecBtn)
- interface.addComponent(heightBtn )
- interface.addComponent(heightIncBtn)
- interface.addComponent(mTopDecBtn )
- interface.addComponent(mTopBtn )
- interface.addComponent(mTopIncBtn )
- interface.addComponent(mLeftDecBtn )
- interface.addComponent(mLeftBtn )
- interface.addComponent(mLeftIncBtn )
- interface.addComponent(mRightDecBtn)
- interface.addComponent(mRightBtn )
- interface.addComponent(mRightIncBtn)
- interface.addComponent(deleteBtn )
- interface.addComponent(cancelAllBtn)
- interface.addComponent(submitAllBtn)
- end
- -- Command handler
- function TFGen.Editor.CommandHandler(command, sender)
- if(pcall(TFGen.Editor.Commands[command], sender) == false) then
- tpt.log("TFGen: Command \""..command.."\"is broken or undefined.")
- end
- end
- -- Commands
- TFGen.Editor.Commands = {}
- function TFGen.Editor.Commands.CancelAll()
- TFGen.Reset()
- TFGen.Editor.Reset()
- end
- function TFGen.Editor.Commands.SubmitAll()
- if( TFGen.Glyph ~= nil ) then
- TFGen.Editor.SaveFontToFile(TFGen.Glyph)
- else
- tpt.message_box("Font not saved", "No glyph found, no font saved, human.")
- end
- TFGen.Reset()
- TFGen.Editor.Reset()
- end
- function TFGen.Editor.Commands.Prev()
- TFGen.Editor.ChangeIndex(-1, true)
- TFGen.Editor.MoveTo( TFGen.Editor.GetClosePos( TFGen.Glyph[TFGen.CurrentGlyphIndex] ) )
- end
- function TFGen.Editor.Commands.Next()
- TFGen.Editor.ChangeIndex(1, true)
- TFGen.Editor.MoveTo( TFGen.Editor.GetClosePos( TFGen.Glyph[TFGen.CurrentGlyphIndex] ) )
- end
- function TFGen.Editor.Commands.Name(sender)
- local input = tpt.input("Font name", "Set the name for your font", TFGen.Glyph.Name)
- if(string.len(input)>0)then
- input = string.gsub(input, "[^%l%u%d_]*", "")
- input = string.gsub(input, "^%d+", "")
- TFGen.Glyph.Name = input
- sender:text("Name: "..TFGen.Glyph.Name)
- end
- end
- function TFGen.Editor.Commands.Char(sender)
- local currentGlyph = TFGen.Glyph[TFGen.CurrentGlyphIndex]
- local input = tpt.input("Assign the character", "Assign the character for this glyph", currentGlyph.Char)
- if(string.len(input)>0)then
- currentGlyph.Char = string.sub(input, 1, 1)
- sender:text("Char: [ "..currentGlyph.Char.." ]")
- else
- currentGlyph.Char = ""
- sender:text("Char: []")
- end
- end
- function TFGen.Editor.Commands.AutoAssign() --auto assign characters with given sequence: 0~9, A~Z, a~z, *space*`-=[]\;',./~!@#$%^&*()_+{}|:"<>? (all symbols then shift-symbols)
- local input = tpt.input("Auto assign", "Auto assign characters in order:\n0~9, A~Z, a~z, *space*`-=[]\\;',./~!@#$%^&*()_+{}|:\"<>?\nContinue?\nType 15 for all, 1 for 0~9 only, 2 for upper chars, 4 for lower, 8 for symbols. You can add them up.", "15", "Any input out of 0~15 will be ignored")
- input = tonumber(input)
- if( input ~= nil and input >= 0 and input < 16 ) then
- -- Auto assign in sequence
- local index = 1
- local glyphCount = #TFGen.Glyph
- -- 0~9
- if( bit.band(input, 1) == 1 ) then
- for i = 0, 9 do
- if( TFGen.Glyph[index] ~= nil and index <= glyphCount ) then
- TFGen.Glyph[index].Char = string.char( 48 + i )
- index = index + 1
- end
- end
- end
- -- Upper chars
- if( bit.band(input, 2) == 2 ) then
- for i = 0, 25 do
- if( TFGen.Glyph[index] ~= nil and index <= glyphCount ) then
- TFGen.Glyph[index].Char = string.char( 65 + i )
- index = index + 1
- end
- end
- end
- -- Lower chars
- if( bit.band(input, 4) == 4 ) then
- for i = 0, 25 do
- if( TFGen.Glyph[index] ~= nil and index <= glyphCount ) then
- TFGen.Glyph[index].Char = string.char( 97 + i )
- index = index + 1
- end
- end
- end
- -- Symbols, ordered in logic sequence to deliver better experience for font creators
- if( bit.band(input, 8) == 8) then
- local symbolMap = {" ", "`", "-", "=", "[", "]", "\\", ";", "'", ",", ".", "/", "~", "!", "@", "#", "$", "%", "^", "&", "*", "(", ")", "_", "+", "{", "}", "|", ":", "\"", "<", ">", "?"}
- for i = 1, 33 do -- All symbols count: 1 + 32
- if( TFGen.Glyph[index] ~= nil and index <= glyphCount ) then
- TFGen.Glyph[index].Char = symbolMap[ i ]
- index = index + 1
- end
- end
- end
- -- Clear the rest
- if( index < #TFGen.Glyph ) then
- for i = index, #TFGen.Glyph do
- TFGen.Glyph[index].Char = ""
- index = index + 1
- end
- end
- TFGen.Editor.UpdateUI()
- end
- end
- function TFGen.Editor.Commands.Delete()
- table.remove(TFGen.Glyph, TFGen.CurrentGlyphIndex)
- if(#TFGen.Glyph < 1) then -- No one left
- TFGen.Reset()
- TFGen.Editor.Reset()
- elseif(TFGen.Glyph[TFGen.CurrentGlyphIndex] == nil) then -- We just kill the last one
- TFGen.Editor.ChangeIndex(-1, true)
- TFGen.Editor.MoveTo( TFGen.Editor.GetClosePos( TFGen.Glyph[TFGen.CurrentGlyphIndex] ) )
- end
- end
- function TFGen.Editor.Commands.HeightMod(sender)
- local opt = sender:text()
- local optList = { ["+"]=1, ["-"]=-1 }
- if(opt == "+" or opt == "-")then -- Increase/Decrease btn
- TFGen.Glyph.Height = TFGen.Glyph.Height + optList[opt]
- TFGen.Editor.Cons.heightBtn:text(tostring(TFGen.Glyph.Height))
- else --Height box
- local input = tpt.input("Set font height", "Set the font height for all glyph (1~"..TFGen.MAIN_HEIGHT..")", tostring(TFGen.Glyph.Height))
- if(string.len(input)>0)then
- local h = tonumber(input)
- if(h ~= nil and h > 0 and h <= TFGen.MAIN_HEIGHT)then
- TFGen.Glyph.Height = h
- sender:text(tostring(TFGen.Glyph.Height))
- end
- end
- end
- end
- function TFGen.Editor.Commands.MarginMod(sender)
- local opt = sender:text()
- local optList = { ["+"]=1, ["-"]=-1 }
- local currentGlyphMargin = TFGen.Glyph[TFGen.CurrentGlyphIndex].Margin
- local marginType = ""
- local maxVal = 0
- if( sender == TFGen.Editor.Cons.mTopDecBtn or sender == TFGen.Editor.Cons.mTopIncBtn or sender == TFGen.Editor.Cons.mTopBtn )then
- marginType = "Top"
- maxVal = TFGen.MAIN_HEIGHT - 1
- elseif( sender == TFGen.Editor.Cons.mLeftDecBtn or sender == TFGen.Editor.Cons.mLeftIncBtn or sender == TFGen.Editor.Cons.mLeftBtn )then
- marginType = "Left"
- maxVal = TFGen.MAIN_WIDTH - 1
- elseif( sender == TFGen.Editor.Cons.mRightDecBtn or sender == TFGen.Editor.Cons.mRightIncBtn or sender == TFGen.Editor.Cons.mRightBtn)then
- marginType = "Right"
- maxVal = TFGen.MAIN_WIDTH - 1
- end
- if(opt == "+" or opt == "-")then -- Increase/Decrease btn
- currentGlyphMargin[marginType] = currentGlyphMargin[marginType] + optList[opt]
- if(marginType == "Top")then
- TFGen.Editor.Cons.mTopBtn :text(tostring(currentGlyphMargin[marginType]))
- elseif(marginType == "Left")then
- TFGen.Editor.Cons.mLeftBtn :text(tostring(currentGlyphMargin[marginType]))
- elseif(marginType == "Right")then
- TFGen.Editor.Cons.mRightBtn :text(tostring(currentGlyphMargin[marginType]))
- end
- else --Value box
- local input = tpt.input("Set Margin "..marginType, "Set the Margin "..marginType.." value ("..-maxVal.."~"..maxVal..")", tostring(currentGlyphMargin[marginType]))
- if(string.len(input)>0)then
- local val = tonumber(input)
- if(val ~= nil and math.abs(val) <= maxVal)then
- currentGlyphMargin[marginType] = val
- sender:text(tostring(currentGlyphMargin[marginType]))
- end
- end
- end
- end
- -- Handlers
- function TFGen.Editor._KeypressHandler(key, keyNum, modifier, event)
- if(TFGen.Editor.Visable and keyNum ~= 96 and keyNum ~= 122 and keyNum ~= 304 and keyNum ~= 306 and keyNum ~= 308) then -- [~], [z] and modifiers is usable
- return false
- end
- end
- function TFGen.Editor._ClickHandler(x, y, button, event, scroll) -- button: 0 scroll, 1 left, 2 mid, 4 right; scroll: -1 down, 1 up
- if( button == 0 and scroll == 1) then -- scroll up
- TFGen.Editor.Commands.Prev()
- return false
- end
- if( button == 0 and scroll == -1) then -- scroll down
- TFGen.Editor.Commands.Next()
- return false
- end
- end
- -- Helper methods
- function TFGen.Editor.Show(vis)
- if(vis == nil) then return TFGen.Editor.Visable end
- TFGen.Editor.Visable = vis
- for i, control in pairs(TFGen.Editor.Cons) do
- control:visible(vis)
- end
- end
- function TFGen.Editor.Reset()
- pcall(tpt.unregister_keypress, TFGen.Editor._KeypressHandler)
- pcall(tpt.unregister_mouseclick, TFGen.Editor._ClickHandler)
- TFGen.Editor.Show(false)
- TFGen.Editor.Cons = {}
- TFGen.CurrentGlyphIndex = -1
- end
- function TFGen.Editor.GetClosePos(glyph) -- Get the proper position close to the glyph
- local properPos = {X=0, Y=0}
- local glyphPos = {
- X = glyph.Pos.X ,
- Y = glyph.Pos.Y ,
- X2 = glyph.Pos.X + glyph.Pos.W,
- Y2 = glyph.Pos.Y + glyph.Pos.H
- }
- if(glyphPos.X > TFGen.MAIN_WIDTH/2)then -- On the right side..
- properPos.X = TFGen.MAIN_WIDTH/2 - 154
- elseif(glyphPos.X2 < TFGen.MAIN_WIDTH/2)then -- On the left side..
- properPos.X = TFGen.MAIN_WIDTH/2 + 10
- else -- Center annoying ones, let's see..
- if(math.abs(glyphPos.X - TFGen.MAIN_WIDTH/2) > math.abs(glyphPos.X2 - TFGen.MAIN_WIDTH/2))then --..more to the left..
- properPos.X = glyphPos.X2 + 10
- else --..more to the right
- properPos.X = glyphPos.X - 154
- end
- end
- -- ..and we can not exceed the main bound.
- if( properPos.X < 0 )then properPos.X = 0 end
- if( properPos.X > TFGen.MAIN_WIDTH )then properPos.X = TFGen.MAIN_WIDTH end
- properPos.Y = TFGen.MAIN_HEIGHT/2 - 77 -- lucy number
- return properPos
- end
- function TFGen.Editor.MoveTo(pos) -- Move to (pos.X, pos.Y)
- for i, control in pairs(TFGen.Editor.Cons) do
- local currentX, currentY = control:position()
- local newPos = {
- X = ( pos.X - TFGen.Editor.Pos.X ) + currentX,
- Y = ( pos.Y - TFGen.Editor.Pos.Y ) + currentY
- }
- control:position(newPos.X, newPos.Y)
- end
- TFGen.Editor.Pos = pos
- TFGen.Editor.UpdateUI()
- end
- function TFGen.Editor.ChangeIndex(direction, warp) -- Positive number to +1, negative number to -1. if warp == true, change with loop, default true
- if( warp == nil ) then warp = true end
- if( direction > 0 )then
- if( TFGen.CurrentGlyphIndex < #TFGen.Glyph ) then
- TFGen.CurrentGlyphIndex = TFGen.CurrentGlyphIndex + 1
- elseif( warp ) then
- TFGen.CurrentGlyphIndex = 1 --warp
- end
- TFGen.Editor.UpdateUI()
- end
- if( direction < 0 )then
- if( TFGen.CurrentGlyphIndex > 1 ) then
- TFGen.CurrentGlyphIndex = TFGen.CurrentGlyphIndex - 1
- elseif( warp ) then
- TFGen.CurrentGlyphIndex = #TFGen.Glyph --warp
- end
- TFGen.Editor.UpdateUI()
- end
- end
- function TFGen.Editor.UpdateUI() -- Fresh UI
- if( TFGen.CurrentGlyphIndex > 0 and TFGen.CurrentGlyphIndex <= #TFGen.Glyph ) then
- local currentGlyph = TFGen.Glyph[TFGen.CurrentGlyphIndex]
- if( string.len(currentGlyph.Char) > 0 ) then
- TFGen.Editor.Cons.charBtn :text( "Char: [ "..currentGlyph.Char.." ]" )
- else
- TFGen.Editor.Cons.charBtn :text( "Char: []" )
- end
- TFGen.Editor.Cons.mTopBtn :text( tostring(currentGlyph.Margin.Top ) )
- TFGen.Editor.Cons.mLeftBtn :text( tostring(currentGlyph.Margin.Left ) )
- TFGen.Editor.Cons.mRightBtn :text( tostring(currentGlyph.Margin.Right) )
- end
- end
- function TFGen.Editor.SaveFontToFile(glyph, cachedStr)
- local fontStr = ""
- if( cachedStr ~= nil and string.len(cachedStr) > 0 ) then
- fontStr = cachedStr
- else
- fontStr = "\n--- Font Generated by TFGen ---\n"
- fontStr = fontStr.."\nif(Texter._Fontmatrix == nil) then Texter._Fontmatrix = {} end"
- fontStr = fontStr.."\nTexter._Fontmatrix[\""..glyph.Name.."\"] = {\n\tHeight = "..glyph.Height
- local glyphStr = ""
- for i, glyph in ipairs(glyph) do
- glyphStr = ""
- local char = "nil"
- local mtx = {}
- local mtxStr = ""
- if(string.len(glyph.Char) > 0) then
- char = glyph.Char
- end
- -- Generate mtx str
- for j = 1, #glyph.Mtx do
- table.insert( mtx, "{"..table.concat(glyph.Mtx[j], ",").."}" )
- end
- mtxStr = "\n\t\t\t"..table.concat(mtx, ",\n\t\t\t")
- glyphStr = glyphStr..",\n\t[\""..char.."\"] = {\n\t\tMtx = {"..mtxStr.."\n\t\t}"
- if(glyph.Margin ~= nil and glyph.Margin.Top ~= 0 and glyph.Margin.Left ~= 0 and glyph.Margin.Right ~= 0 )then
- glyphStr = glyphStr..",\n\t\tMargin = {"
- glyphStr = glyphStr.."\n\t\t\tTop = "..glyph.Margin.Top ..","
- glyphStr = glyphStr.."\n\t\t\tLeft = "..glyph.Margin.Left ..","
- glyphStr = glyphStr.."\n\t\t\tRight = "..glyph.Margin.Right
- glyphStr = glyphStr.."\n\t\t}"
- end
- glyphStr = glyphStr.."\n\t}"
- fontStr = fontStr..glyphStr
- end
- fontStr = fontStr.."\n}"
- end
- local fontFileName = glyph.Name..".texterfont"
- local file = io.open(fontFileName, "w")
- if file then
- file:write(fontStr)
- file:close()
- local shouldMove = ""
- if( Texter ~= nil and Texter.FONT_FOLDERS_TO_LOAD ~= nil ) then
- shouldMove = tpt.input("File saved", "I can move the font to where it should be, let me try?\nType Yes to continue, anything else to cancel.", "Yes")
- else
- tpt.message_box("File saved", "Font file \""..fontFileName.."\"\nsaved to game dir, please move it to\nthe font folder.")
- end
- if( shouldMove == "Yes" ) then
- TFGen.Editor.MoveFontToFontDir(".", Texter.FONT_FOLDERS_TO_LOAD, fontFileName)
- end
- Texter.Init(false)
- else
- local shouldTryAgain = tpt.input("Unknown Error", "There is an error saving the file, should I try again?\nType Yes to continue, anything else to cancel", "Yes")
- if( shouldTryAgain == "Yes" ) then
- TFGen.Editor.SaveFontToFile(glyph, fontStr) -- Try again
- end
- end
- end
- function TFGen.Editor.MoveFontToFontDir(rootPath, foldersToLoad, fontFileName)
- local fontFolder = TFGen.Editor.FindDeepestFontFolder(rootPath, foldersToLoad, Texter.FONT_SEARCH_DEPTH)
- local success = false
- if( fontFolder~= nil and string.len(fontFolder) > 0 or foldersToLoad["."] ~= nil ) then -- If . is available, no need to move
- success = fileSystem.move(fontFileName, fontFolder.."\\"..fontFileName)
- end
- if( not success ) then
- tpt.message_box("Move font faild", "Sorry, font file \""..fontFileName.."\"\nfailed to move :(\nPlease move it to \""..fontFolder.."\".")
- end
- end
- function TFGen.Editor.FindDeepestFontFolder(rootPath, foldersToLoad, depth) -- But not the root folder
- if( rootPath == nil ) then
- rootPath = "."
- end
- if( depth == nil ) then
- depth = 1
- end
- local fontFolder = nil
- for i, folderName in ipairs(foldersToLoad) do
- if( string.match(rootPath, "\\?"..folderName.."$") ~= nil and rootPath ~= ".") then
- fontFolder = rootPath -- If it's the folder we look for
- break
- end
- end
- -- Let's check the subs for deepest one ( by overwrite fontFolder )
- if( depth > 0 ) then
- local subs = fs.list(rootPath)
- local subFontFolder = nil
- for i=1, #subs do
- if( Texter._IsFolder(rootPath.."\\"..subs[i]) ) then
- subFontFolder = TFGen.Editor.FindDeepestFontFolder(rootPath.."\\"..subs[i], foldersToLoad, depth - 1)
- end
- if( subFontFolder ~= nil and string.len(subFontFolder) > 0 ) then -- Cheers!
- fontFolder = subFontFolder
- break
- end
- end
- end
- return fontFolder
- end
- TFGen.Init()
Advertisement
Add Comment
Please, Sign In to add comment