Kwik Editor in Solar2D
Project Structure Overview
A Kwik project is organized as:
- Book > Page (a PSD file) > Layer
The names of your PSD files are used to generate related Lua files.
For example, if you have Photoshop/book/pageOne.psd
, the page is called “pageOne”.
kwik5 |
---|
App/{bookName} - assets/images/pageOne - components/pageOne - commands/pageOne - components/pageOne/index.lua |
Note: In Kwik4, page names were fixed like page01, page02, etc. In Kwik5, PSD filenames are used directly. Also, “bookshelf” in Kwik4 is now called “bookstore” for multi-book projects.
Using the Kwik Editor in Solar2D

The Kwik editor lets you edit your project with little or no code.
Page view: Select a book and navigate to a page for editing.
Component view: Add animations, buttons, etc. to layers. The editor updates your Lua code when you save component or event properties.
The image below shows the Candice layer selected for creating a linear animation.
There are three icons to switch between lists:
- Component icon: Shows layers in the page. The top bar lists Kwik components like Layer, Audio, Group, Timer, Variable, Joint.
- Action icon: Shows actions. You can create or edit actions.
- Asset icon: Lists files in the App/book/assets folder (audio, video, spritesheets, etc.) for use in your project.
For examples, with Group component you can create a group of display.newGroup in Kwik editor
groupA
layer1
layer2
Replacement components, a layer image is replaced with the following media
- imagesheet(spritesheet)
- video
- particles
- web
- map
Layer can be configured for
- button
- animation
- physics
Other Solar2D components
- audio
- short (event)
- long (stream)
- sync (audio and text)
- timer
Component Icon

Shows the layers in the current page. The top bar includes:
- Layer
- Audio
- Group
- Timer
- Variable
- Joint

Action Icon

Lets you create or edit actions.

Click “New” to create a new action.

Asset Icon

Shows buttons for listing files in the App/book/assets folder.

You can select audio, video, spritesheets, etc. from the assets folder to use in your pages at runtime.
Sometimes it’s faster to edit or add code snippets directly to your .lua
files. Understanding the code generated by the Kwik editor can help.
main.lua
See Step 3 – Solar2D Simulator > main.lua
To load a book project, use:
local env = require("env")
env.book = "book"
env.goPage = "landscape"
env.lang = ""
--
env.restore = false
--
env.mode = "development"
-- env.mode = "production"
-- env.mode = "debug" -- need kwik5-plugin src from kwiksher's repo
--
if env.mode == "development" or env.mode == "debug" then
env.props = {
name = env.book,
editor = true,
gotoPage = env.goPage,
language = env.lang, -- empty string "" is for a single language project
position = {x = 0, y = 0},
gotoLastBook = false,
unitTest = false,
httpServer = false,
showPageName = true,
turnOffNativeVideo = true
}
elseif env.mode == "production" then
env.props = {
name = env.book,
editor = false,
gotoPage = env.goPage,
language = env.lang, -- empty string "" is for a single language project
position = {x = 0, y = 0},
gotoLastBook = false,
unitTest = false,
httpServer = false,
showPageName = false,
turnOffNativeVideo = false
}
end
App/book/index.lua
Pages are defined in App/{Book Name}/index.lua
:
local scenes = {
"page1",
"page2",
"yourPageName"
}
return scenes
- You can change the order of pages in the
scenes
table. - You can add your own (custom) pages.
Note: Kwik4 used
.kwk
XML files for project properties. Kwik5 uses.lua
.
Page Index – components/page/index.lua
Each page has a file: App/{bookName}/components/{pageName}/index.lua
This file contains two main objects:
components
commands
components > layers
Layers from Photoshop (images) and other resources are listed here.
page sceneName = ...
--
local scene = require('controller.scene'page(sceneName, {
name = "page1",
components = {
layers = {
{ bg={} },
{ gotoBtn={} },
{ title={} },
{ customLayerName={} },
},
audios = { },
groups = { },
timers = { },
variables = { },
page = { }
},
commnands = { },
onInit = function(scene) print("onInit") end
})
--
return scene

You can add your own (custom) layers.
Nested layers are supported:
layers = { ... { title = {}}, { customLayerTop = { {panelOne = {}}, {panelTwo = { {buttonOne = {}}, {buttonTwo = {}} }} } } }
Layer class
Animations, buttons, and layer replacements (spritesheet, video, particles, etc.) are defined with class names in Kwik5.
For example, the “witch” > “en” layer with a linear animation has the “linear” class attached in index.lua
:
components = {
layers = {
...
witch = {
en = {
class = { "linear" }
}
}
}
}

The file
{{layer}}_{{class}}.lua
should be present in the layers/page/ folder.Multiple classes are supported. You can add your own custom class to a layer:
components = { layers = { ... { title = {}, class = {"animation", "button", "yourClass"} }, } }
Note: In Kwik4, you had to give each animation a unique name. In Kwik5, animations and buttons are identified by layer and class name—no need to assign a separate name.
components > audios, groups, timers, variables, page
components = {
...
audios = {
long = {"longOne", "longTwo"},
short = {"shortOne", "shortTwo"},
sync = {"syncOne", "syncTwo"}
},
groups = {"groupOne", "groupTwo"},
timers = {"timerOne", "timerTwo"},
variables = {"varOne", "varTwo"},
}

Action Commands
Events from buttons or animation completions are defined in the commands
table.
For example, the panelOne.OK
event comes from a button in panelOne
. It triggers the OK event, and the code in panelOne.OK.lua
in App/{bookName}/commands/{pageName}
will run.
page sceneName = ...
--
local scene = require('controller.scene'page(sceneName, {
name = "page1",
layers = {
{ bg={} },
...
},
components = {
...
},
commnands = {
"panelOne.OK",
"panelOne.Cancel",
"timerOne",
"actionOne",
},
onInit = function(scene) print("onInit") end
})
--
return scene

Component Properties
Properties for animations, buttons, and layer replacements (spritesheet, video, particles) are edited and saved with the Kwik Editor.
These property values are attached as a component class to a layer, so designers can edit without code.
kwik5 |
---|
In Photoshop, the Kwik exporter publishes .lua files with layer properties.1. In the Solar2D simulator, the Kwik editor reads these properties directly. 2. You can create or modify animations, buttons, etc. with the editor. Developers can also edit the .lua files directly in a text editor. |

- App/{Book Name}/components/{Page}/layers/{Layer}.lua
kwik5 |
---|
UI.sceneGroup = display.newGroup() |
local bg = UI.sceneGroup.bg |
Example: App/lingualSample/components/page1/layers/Candice_linear.lua
local parent,root = newModule(...)
local M = {
name = "Candice",
class = "linear", -- "Dissolve" "Path" "Linear" "Pulse" "Rotation" "Tremble" "Bounce" "Blink"
}
M.obj = require(parent.."en").obj
M.layerOptions = {
referencePoint = "Center", -- "Center" "TopLeft" "TopCenter" "TopRight" "CenterLeft" "CenterRight" "BottomLeft" "BottomLeft" "BottomRight" for text
deltaX = 0,
deltaY = 0,
}
-- animationProps
M.properties = {
type = "", -- group, page, sprite
target = "witch/en",
autoPlay = true,
delay = 0,
duration = 2000,
loop = 1,
reverse = false,
resetAtEnd = false,
--
easing = "inCircular", -- 'Linear' 'inOutExpo' 'inOutQuad' 'outExpo' 'outQuad' 'inExpo' 'inQuad' 'inBounce' 'outBounce' 'inOutBounce' 'inElastic' 'outElastic' 'inOutElastic' 'inBack' 'outBack' 'inOutBack'
-- flip
xSwipe = nil,
ySwipe = nil,
}
--
M.to = {
x = -180,
y = -100,
alpha = 1,
yScale = 1.5,
xScale = 1.5,
rotation = 30,
}
-- more option
-- action at the end of animation
M.actions = { onComplete = "" }
...
...
Note: Kwik5 is designed to be a low-code tool, making it easy to work with Lua code directly. See the next Lua section for more.
Action Command Properties
- App/{bookName}/commands/{pageName}/{commandName}.lua

Example: App/book/commands/page1/actionOne.lua
local ActionCommand = {}
local AC = require("commands.kwik.actionCommand")
--
function ActionCommand:new()
local command = {}
function command:execute(params)
local UI = params.UI
local sceneGroup = UI.sceneGroup
local layers = UI.layers
local obj = params.obj
-- local conditions = require("App." .. UI.book..".common.conditions")
-- local expressions = require("App." .. UI.book.."common.expressions")
-- target layer :sceneGroup[layerName]
-- target animation : layer.animations[index]
obj = UI:getAnimation("witch/en_linear")
AC.Animation:play(obj)
end
return setmetatable(command, {__index=AC})
end
--
ActionCommand.model = [[
{"name":"flyAnim","actions":[{"command":".animation.play","params":{"target":"witch/en_linear"}}]}
]]
--
return ActionCommand
Variables
Edit variables in the action command dialog:
- target: LCD
- Value: value..‘1’
- type: function
This generates code like:
UI.setVariable("LCD", function(value) return value..1 end)
You can also use UI.getVariable(varName)
in your own code.
See more in tutorial/keyboard/
Assets

The Kwik editor automatically creates App/book/assets/model.lua
by reading folders/files under App/book/assets
.
You can create audio components, layer replacements (video, particles, sync audio & text, spritesheets) by selecting from the asset table.
{
audios = {
{
name = "click.mp3",
path = "audios/short",
links = {{page = "page1"}}
}
},
videos = {
{
name = "videoA.mp4",
path = "videos",
links = {{page= "page01", layers = {"imageOne"}}}
},
{
name = "videoB.mp4",
path = "videos",
links = {
{page= "page01", layers = {"imageTwo"}}
}
}
},
sprites = {}
}
To set a layer for video replacement:
Click
_target
in the properties panel.Select a layer for video replacement.
You’ll see a star set in the
_target
property.
See more in get_started/component_with_asset/
Bookstore
The Bookstore module in Kwik handles multiple books in the App folder. Each book’s assets can be downloaded from your server.
See details in Bookstore

- Portrait view for library
- Book table view
Each book status: isFree, isPurchased, isDownloadable, isDownloaded
- Online icon
See the section of bookstore/components/#Photoshop files table.psd
Restore & download all
App/bookstore.lua
bookignored
hides the given names in the bookTable in the Kwik editor.
local M = {
bookignored = {"book1", "mybook", "kwikTheCat"}
}
--
local pageCommand = require("components.bookstore.controller.pageCommand")
local model = require("components.bookstore.model.base")
--
model.debug = true
model.URL = "http://localhost:8080/bookshop/"
-- model.URL = nil means simple IAP store without network download
-- downloadBtn, savingTxt won’t be used. You don't need to create them.
----------
model.TOC = "bookTOC"
model.LIBRARY_PAGES = {en = "scenes.library"}
model.DIALOG_PAGES = {en = "scenes.dialog"}
--
model.name = "catalog01"
--
--
model.books = {
bookFree = {
name = "bookFree",
versions = {},
titles = {en = "bookOne"},
descriptions = {en = "desc"},
isFree = true,
isOnlineImg = true,
isDownloadable = true,
image = "App/bookFree/assets/thumnails/page1.png",
productNames = {apple = "bookFree", google = "bookFree", amazon = "bookFree"}
},
bookOne = {
name = "bookOne",
versions = {},
titles = {en = "bookOne"},
descriptions = {en = "desc"},
isFree = false,
isOnlineImg = true, -- true
isDownloadable = true, -- true
image = "App/bookOne/assets/thumnails/page1.png",
productNames = {apple = "bookOne", google = "bookOne", amazon = "bookOne"}
}
}
...
Kwik Project File Locations
Images and Lua files from a PSD are published under the App folder by Kwik exporter in Photoshop:
kwik5 |
---|
{{project root}} |
{{project root}}/Photoshop/{{Book Name}}//*.psd |
{{project root}}/Solar2D |
{{project root}}/Solar2D/App/{{Book Name}}/assets/images |
{{project root}}/Solar2D/App/{{Book Name}}/components/{{Page}} |

Photoshop Layers fro mutiple languages
normal
book1/ page1.psd layer1 layer1_1 layer1_2 layer2 page2.psd
one .psd makes a omposer.scene of Solar2D
lang code
book1/ page1.psd layer1 en jp sp layer2
layer is displayed according to language choise of user.