Premake4

From WxWiki
Jump to navigation Jump to search
The printable version is no longer supported and may have rendering errors. Please update your browser bookmarks and please use the default browser print function instead.

What is premake4

Premake4 is a build configuration tool that will generate project files for Visual Studio, GNU Make, Xcode, Code::Blocks, and more across Windows, Mac OS X, and Linux platform.

A simple example

Put this text in a file named "premake4.lua"

dofile "use_wxwidgets.lua"

    solution "MySolution"
        configurations {"Debug", "Release"}
        location "build" -- optional, but cleaner
        targetdir "bin"  -- optional, same here

        project "testWx"
            kind "WindowedApp"
            flags { "WinMain" }
            language "C++"
            files {"minimal.cpp"}
            wx_config {Unicode="yes", Version="2.8", Libs="core,aui"}

And use this configuration script "use_wxwidgets.lua"

-- use_wxwidgets.lua
-- wxWidgets configuration file for premake4
-- 
-- authors: [email protected]
--          [email protected] 
 
-- optional root folder of wxwidgets installation folder
--
newoption  {
    trigger     =   "wx_root",
    value       =   "PATH",
    description =   "Path to wxwidgets root folder, by default, WXWIN envvar will be used or wx-config found in path on POSIX"
}
 
-- The wx_config the parameters are.
--          Root    : path to wx root folder. Can be left empty if WXWIN is defined
--                      or if wx-config is accessible.
--          Debug   : "yes" use debug version of wxwidgets. Default to "no"
--          Version : one of '2.4', '2.5', '2.6', '2.7', '2.8', '2.9'. Default to '2.9'
--          Static  : indicates how wx is to be linked. Values are
--                      either "yes" for static linking or "no" for shared linking, Default to "no"
--          Unicode : use "yes" for unicode or "no" for ansi version.
--                      ansi version only available up to 2.8
--                      Default to "yes"
--          Universal : use universal configuration. Default to "no"
--          Libs    : a list of wx libraries that you want to link with.
--                      eg: "aui,media,html"
--                      Default to "richtext,aui,xrc,qa,html,adv,core,xml,net"; base is implicit
--          WindowsCompiler : compiler used to compile windows libraries ( "vc" or "gcc" )
 
function wx_config(options)
 
    local wrongParam = false
    local allowedWxOptions = {"Root", "Debug", "Host", "Version", "Static", "Unicode", "Universal", "Libs", "WindowsCompiler" }
    for option in pairs(options) do
        if not table.contains(allowedWxOptions, option) then
            print ("unrecognized option '"..option.. "'")
            wrongParam = true
        end
    end
    if wrongParam then print("valid options are : '" .. table.concat(allowedWxOptions, "', '").."'") end
 
    wx_config_Private( options.Root or "",
                options.Debug or "",
                options.Host or "",
                options.Version or "2.9",
                options.Static or "",
                options.Unicode or "yes",
                options.Universal or "",
                options.Libs or "richtext,aui,xrc,qa,html,adv,core,xml,net", -- base is implicit, std not valid
                options.WindowsCompiler or "vc"
                )
end
 
function wx_config_Private(wxRoot, wxDebug, wxHost, wxVersion, wxStatic, wxUnicode, wxUniversal, wxLibs, wxWindowsCompiler)
    -- some options are not allowed for newer version of wxWidgets
    if wxVersion > "2.8" then -- alphabetical comparison may fail...
    --    wxDebug = "" -- 2.9 still make debug libraries
        wxUnicode = "yes"
    end
 
    --wx_root=PATH override wxRoot parameter
    if _OPTIONS and _OPTIONS["wx_root"] then
        print ("seen option '--wx_root=" .. _OPTIONS["wx_root"] .. "' overriding default root = '" .. wxRoot .. "'")
        wxRoot = _OPTIONS["wx_root"]
    end
    -- the environment variable WXWIN override both wxRoot parameter and --wx_root option
    if os.getenv('WXWIN') then wxRoot = os.getenv('WXWIN') end
 
    if wxUnicode == "yes" then defines { "_UNICODE" } end
 
    if wxDebug == "yes" then defines { "__WXDEBUG__" }
    elseif wxDebug == "no" then flags { "Optimize" } end
 
    if wxStatic == "yes" then
        flags { "StaticRuntime" }
    else
        defines { "WXUSINGDLL" }
    end
 
 
    -- function to compensate lack of wx-config program on windows
    -- but wait, look at http://sites.google.com/site/wxconfig/ for one !
    function wx_config_for_windows(wxWindowsCompiler)
        local wxBuildType = ""  -- buildtype is one of "", "u", "d" or "ud"
        local wxDebugSuffix = "" -- debug buildsuffix is for support libraries only
        if wxUnicode ~= "no" then wxBuildType = wxBuildType .. "u" end
        if wxDebug == "yes" then
            wxBuildType = wxBuildType .. "d"
            wxDebugSuffix = "d"
        end
 
        local wxLibPath = path.join(wxRoot, "lib")
        wxLibPath = path.join(wxLibPath, wxWindowsCompiler .. "_" .. iif(wxStatic == 'yes', 'lib', 'dll'))
        -- common defines
        defines{ "__WXMSW__" }
 
        -- common include path
        includedirs {
            path.join(wxRoot, "include"),
            path.join(wxLibPath, "msw" .. wxBuildType)   -- something like "%WXWIN%\lib\vc_lib\mswud" to find "wx/setup.h"
            }
 
        -- common library path
        libdirs { wxLibPath }
 
        -- add the libs
        libVersion = string.gsub(wxVersion, '%.', '') -- remove dot from version
        links { "wxbase"..libVersion..wxBuildType } -- base lib
        for i, lib in ipairs(string.explode(wxLibs, ",")) do
            local libPrefix = 'wxmsw'
            if lib == "xml" or lib == "net" or lib == "odbc" then
                libPrefix = 'wxbase'
            end
            links { libPrefix..libVersion..wxBuildType..'_'..lib}
        end
        -- link with support libraries
        for i, lib in ipairs({"wxjpeg", "wxpng", "wxzlib", "wxtiff", "wxexpat"}) do
            links { lib..wxDebugSuffix }
        end
        links { "wxregex" .. wxBuildType }
    end
 
    -- use wx-config to figure out build parameters
    function wx_config_for_posix()
        local configCmd = "wx-config"  -- this is the wx-config command ligne
        if wxRoot ~= "" then configCmd = path.join(wxRoot, "bin/wx-config") end
 
        local function checkYesNo(value, option)
            if value == "" then return "" end
            if value == "yes" or value == "no" then return " --"..option.."="..value end
            error("wx"..option..' can only be "yes", "no" or empty' )
        end
 
        configCmd = configCmd .. checkYesNo(wxDebug, "debug")
        configCmd = configCmd .. checkYesNo(wxStatic, "static")
        configCmd = configCmd .. checkYesNo(wxUnicode, "unicode")
        configCmd = configCmd .. checkYesNo(wxUniversal, "universal")
        if wxHost ~= "" then configCmd = configCmd .. " --host=" .. wxHost end
        if wxVersion ~= "" then configCmd = configCmd .. " --version=" .. wxVersion end
 
        -- set the parameters to the curent configuration
        buildoptions{"`" .. configCmd .." --cxxflags`"}
        linkoptions{"`" .. configCmd .." --libs " .. wxLibs .. "`"}
    end
 
-- BUG: here, using any configuration() function will reset the current filter
--      and apply configuration to all project configuration...
--      see http://industriousone.com/post/add-way-refine-configuration-filter
--      and http://sourceforge.net/tracker/?func=detail&aid=2936443&group_id=71616&atid=531881
--~     configuration "not windows"
--~         wx_config_for_posix()
--~     configuration "vs*"
--~         wx_config_for_windows("vc")
--~     configuration {"windows", "codeblocks or gmake or codelitle"}
--~         wx_config_for_windows("gcc")
    if os.get() ~= "windows" then
        wx_config_for_posix()
    else
        local allowedCompiler = {"vc", "gcc"}
        if not table.contains( allowedCompiler, wxWindowsCompiler) then
            print( "wrong wxWidgets Compiler specified('"..wxWindowsCompiler.."'), should be one of '".. table.concat(allowedCompiler, "', '").."'" )
            wxWindowsCompiler = "vc"
        end
--~  BUG/WISH: I need a function like compiler.get() that return the project/configuration compiler
--~         local wxWindowsCompiler = "vc"
--~  BUG? --cc=compiler standard premake option is not registered in the _OPTIONS array
--~         if _OPTIONS and _OPTIONS["cc"] then
--~             wxWindowsCompiler = _OPTIONS.cc
--~             print("seen option '--cc=" .. _OPTIONS["cc"] .. "' overriding default cc='vc'")
--~         end
        wx_config_for_windows(wxWindowsCompiler)
    end
end

Run premake4 in the same folder to generate project files for codeblocks

premake4 codeblocks

You can specify a path to you wxwidgets library if needed (or use WXWIN environment variable )

premake4 --wx_root=c:\my_libs\wxWidgets vs2005


Tip

when the generated makefiles are used with the eclipse CDT, which has a nice auto-discovery mode where it figures out include paths by observing the output of make, you need to run it (for the first time) with make VERBOSE=1 as otherwise premake generated makefiles are silent and do not print the actual calls to the compiler and linker.