Librocket
Librocket is the UI library that SCPUI uses to layout, draw, and implement the upgraded ui system within FreeSpace Open. It uses the open standards XHTML1.0 and CSS2.0 (while borrowing features from HTML5 and CSS3), and extends them with features suited towards real-time applications.
FSO's version of the library is a bugfixed fork of the original. The source code is available here.
Contents
Basics
The basic implementation of a librocket UI within FSO contains three files: RML, CSS, and LUA.
Development and Debugging
There are three main things to know when working with the librocket library within FSO.
- You can view the librocket debugger by pressing ctrl-shift-d
- You can live-reload RML and RCSS files by pressing ctrl-shift-r
- It's worth noting that Librocket will drop the existing elements and lose them in memory. This will cause a warning on game-exit.
- Librocket API warnings and errors are not currently forwarded to FSO's error handling. Because of this, simple bugs in your Lua code that uses the API cause cause FSO to crash.
RML
RML is based loosely around XHTML 1.0 and HTML 4.01, however element names are (mostly) open-ended in RML and can be used in any way that is logical for your application. All documents follow strict XML1.0 specification and where possible all libRocket elements follow their HTML equivalent.
RML maintains the core components of HTML4, including CSS and scripting. It provides a number of basic elements including input fields, radio buttons and check boxes as well as more complex enhancements such as templates and datagrids.
- Elements - The basic RML element.
- Documents - The HEAD and BODY of a document.
- Images - Referencing images.
- Style Sheets - Adding style to RML documents.
- Forms - User-input forms.
- Controls - Tabsets and window handles.
- Data Display - Data grids and data selects.
- Templates - Making all your windows look consistent.
- Events - Mouse clicks, movement, key presses, text entry.
RCSS
RCSS is based on the CSS2 specification, with certain elements removed or altered to suit the needs of libRocket. In some cases, elements have been taken from the CSS3 working draft. This document provides an overview of RCSS and the differences between RCSS and CSS, and should be read in conjunction with the CSS2 specification.
RCSS interacts with RML in an identical fashion to CSS and HTML. Style properties declared in a RCSS are attached selectively to elements defined in RML to affect layout, positioning and other style attributes (such as font, color, text decoration, etc).
If you are familiar with CSS, a good place to start is the property index, which outlines the properties and values supported in RCSS and the new functionality included. Next, read up on decorators, the new, flexible way to skin elements.
If you are not, read through this documentation while consulting the CSS2 specification for detailed examples and technical details, or skip all this for now and play around with the samples!
- Syntax and basic data types
- Selectors
- Box model
- Visual formatting model
- Visual effects
- Colors and backgrounds
- Fonts
- Text
- Cursors, Dragging and Tabbing
- Decorators
- Font effects
- Scrollbars and Sliders
- Property Index
LUA API
The Lua interface to libRocket has been designed to resemble Javascript as closely as possible. It is how the librocket UI will actually interact with the Freespace Open engine. Below is a list of property and API references.
Embedding Script
Lua code can be embedded into RML files. Inline responses to events are executed as Python code. Functions, structures and variables can be declared or included with the <script> tag, then referenced from the inline code.
Similarly to Javascript, the lua can be included from a separate file with the src attribute, or otherwise declared inline as loose content within the <script> tag. Any code embedded in this manner will be compiled with the document and will be available to inline event handlers in the RML. See the following examples.
<rml> <head> <script> def Test(): print 'Hello world!' </script> </head> <body> <button onclick="Test()">Continue</button> </body> </rml>
<rml> <head> <script src="test.py"></script> </head> <body> <button onclick="Test()">Continue</button> </body> </rml>
Attaching To Events
You can attach to user interface events statically in the RML or dynamically in the lua scripts.
- A list of events available to attach to is in the RML Events documentation.
Statically
With this method you write your code directly into the RML files, using the on* attributes. When the event is fired three global variables are set up, document, event and self.
- self - The element thats currently being processed
- document - The document the element thats currently being processed belongs to
- event - The event thats currently being processed
Using the on* attributes you write your code inline
- Example:
<button onclick="ba.print('Clicked!')"/>
LibRocket allows multiple lines of code to be put on one line, separated by a semicolon.
- Example:
<button onclick="ba.print('Line 1');ba.print('Line 2')"/>
Dynamically
The AddEventListener() method allows you to bind any callable LUA method to an event.
function print(message) ba.print(message) end function createListener() element = document:GetElementById('button') element:AddEventListener('click', function(_, _, _) print("clicked!") end) end