On this page
- tecs.platform.os
- Capabilities
- Clipboard
- Process signals
Functions
- capabilities
- clearClipboard
- clipboardAvailable
- clipboardData
- clipboardMimeTypes
- clipboardText
- hasClipboardData
- hasClipboardText
- hasPrimarySelection
- messageBox
- openFile
- openFolder
- openURL
- power
- preferredLocales
- primarySelection
- resetCapabilities
- saveFile
- setClipboardText
- setPrimarySelection
- updateDialogs
tecs.platform.os
Runtime capabilities, clipboard access, and desktop services.
Capabilities
Ask the installed build instead of inferring support from a target name. capabilities distinguishes targets that share an operating system but differ in JIT, worker, shader, storage, or device support. It reports the process sandbox separately because that environment can restrict filesystem and child process access without changing the target.
Clipboard
The clipboard belongs to the desktop and can change between frames. events.clipboardUpdate reports a change; read the current value when the event arrives or when the user requests paste. Text stays UTF-8, keeps its line endings, and stops at the first NUL. clipboardData preserves NULs.
Headless builds report the clipboard as unavailable. Primary selection remains independent of the clipboard. On platforms without a shared primary selection, reads may return only the value this process wrote.
Process signals
SDL applications already receive SIGINT and SIGTERM as the public tecs.platform.events.on.quit event and then run their normal shutdown lifecycle. A headless loop can retain a SignalListener instead. tecs.runtime.poll transfers signals out of the native handler, and next drains them without waiting:
tecs.scoped(function(scope: tecs.Scope)
local signals <const> = scope:own(
tecs.platform.os.newSignalListener()
)
local running = true
while running do
tecs.runtime.poll()
local signal <const> = signals:next()
if signal == "interrupt" or signal == "terminate" then
running = false
end
end
end)The native handler only sets atomic flags. It never calls Lua, allocates, or locks. Repeated instances of one signal may coalesce before the next runtime poll, as operating-system signals ordinarily may. When different signals are pending in one poll, next returns them in the enum order rather than claiming an arrival order the operating system did not preserve. Closing the last listener stops interception, so a later signal follows the platform's termination behavior again.
Module contents
Constructors
| Constructor | Description |
|---|---|
newSignalListener |
Creates a listener for process signals in a headless loop. |
Types
| Type | Kind | Description |
|---|---|---|
Capabilities |
record | Describes what this build can do on this target. |
DialogFilter |
record | Describes one file-type filter. |
DialogOptions |
record | Describes dialog configuration. |
DialogResult |
record | Describes a completed dialog. |
Locale |
record | Describes one language the user prefers. |
Power |
record | Describes the machine's power source and remaining charge. |
ProcessSignal |
enum | ProcessSignal identifies an interrupt, termination, hangup, or quit request sent to this process. |
SignalListener |
interface | A SignalListener receives process signals in a headless loop. |
Functions
| Function | Kind | Description |
|---|---|---|
capabilities |
Static | Reads the capabilities of the running build. |
clearClipboard |
Static | Withdraws what this application put on the system. |
clipboardAvailable |
Static | Reports whether a clipboard is available. |
clipboardData |
Static | Returns the clipboard bytes for mimeType, or nil when it offers none. |
clipboardMimeTypes |
Static | Returns the clipboard MIME types in platform order. |
clipboardText |
Static | Returns the clipboard text, or an empty string when it holds none. |
hasClipboardData |
Static | Reports whether the clipboard offers mimeType. |
hasClipboardText |
Static | Reports whether the clipboard holds text. |
hasPrimarySelection |
Static | Reports whether the primary selection holds text. |
messageBox |
Static | Shows a native informational, warning or error dialog. |
openFile |
Static | Opens a native file picker. |
openFolder |
Static | Opens a native folder picker. |
openURL |
Static | Opens an absolute URI with the operating system's preferred application. |
power |
Static | Returns the current battery or external-power state. |
preferredLocales |
Static | Returns the user's preferred locales in priority order. |
primarySelection |
Static | Returns text from the platform's primary selection. |
resetCapabilities |
Static | Forgets the cached answer. |
saveFile |
Static | Opens a native save-file picker. |
setClipboardText |
Static | Puts text on the clipboard, replacing whatever was there. |
setPrimarySelection |
Static | Puts text in the primary selection. |
updateDialogs |
Static | Settles file and folder dialogs that have answered. |
Constructors
tecs.platform.os.newSignalListener Static
Creates a listener for process signals in a headless loop.
The listener receives "interrupt" for SIGINT, "terminate" for SIGTERM, "hangup" for SIGHUP, and "quit" for SIGQUIT on POSIX. Windows maps Ctrl-C and Ctrl-Break to "interrupt", and console close, logoff, and shutdown to "terminate". Unsupported signals simply never arrive on that platform.
SDL applications normally observe tecs.platform.events.on.quit instead. SDL converts SIGINT and SIGTERM to that event and the application performs its normal shutdown lifecycle before the process-wide runtime pump.
function tecs.platform.os.newSignalListener(
selected: {ProcessSignal}
): SignalListener, stringArguments
| Name | Type | Description |
|---|---|---|
selected |
{ProcessSignal} |
The caller supplies the signal names to retain, or omits the list to retain every supported name. An empty list and duplicate or unknown names raise as programmer errors. |
Returns
| Type | Description |
|---|---|
SignalListener |
Returns a caller-owned listener. |
string |
Returns the platform reason when native signal handling cannot be installed. |
Examples
tecs.scoped(function(scope: tecs.Scope)
local signals, reason = tecs.platform.os.newSignalListener({
"interrupt", "terminate"
})
if signals == nil then
error(reason)
end
scope:own(signals)
local running = true
local function update()
tecs.runtime.poll()
local signal <const> = signals:next()
if signal ~= nil then
running = false
end
end
while running do
update()
end
end)Types
tecs.platform.os.Capabilities record
Describes what this build can do on this target.
record tecs.platform.os.Capabilities
target: string
architecture: string
sandbox: string
jit: boolean
ffi: boolean
dynamicLibraries: boolean
hotReload: boolean
runtimeShaders: boolean
packagedShaders: boolean
shaderFormats: {string}
touch: boolean
gamepad: boolean
sensors: boolean
workers: boolean
cores: integer
writableStorage: boolean
endtecs.platform.os.Capabilities.target field
Read-only. This is the platform name, such as "macOS" or "Android". A licensed port answers with its own name instead, since everything here describes the platform actually installed.
tecs.platform.os.Capabilities.target: stringtecs.platform.os.Capabilities.architecture field
Read-only. This is the CPU architecture this build targets.
tecs.platform.os.Capabilities.architecture: stringtecs.platform.os.Capabilities.sandbox field
Read-only. Reports "none", "unknownContainer", "flatpak", "snap" or "macOS" for the process environment SDL detects. A sandbox can restrict filesystem and child-process access independently of the target and the build's other capabilities.
tecs.platform.os.Capabilities.sandbox: stringtecs.platform.os.Capabilities.jit field
Read-only. This reports whether the runtime generates machine code. False on a target that requires interpretation.
tecs.platform.os.Capabilities.jit: booleantecs.platform.os.Capabilities.ffi field
Read-only. This is always true because every supported build requires the FFI.
tecs.platform.os.Capabilities.ffi: booleantecs.platform.os.Capabilities.dynamicLibraries field
Read-only. Reports whether a library can load by name at run time. It is false where every build links every library into the executable.
tecs.platform.os.Capabilities.dynamicLibraries: booleantecs.platform.os.Capabilities.hotReload field
Read-only. Reports whether this build supports development-time content reload. Named independently of any one kind the watcher reloads.
tecs.platform.os.Capabilities.hotReload: booleantecs.platform.os.Capabilities.runtimeShaders field
Read-only. Reports whether this build can compile shaders from source at run time.
tecs.platform.os.Capabilities.runtimeShaders: booleantecs.platform.os.Capabilities.packagedShaders field
Read-only. Reports whether the engine reads shaders from a packaged artifact. Independent of runtimeShaders: a development build may have both, and a release has only this.
tecs.platform.os.Capabilities.packagedShaders: booleantecs.platform.os.Capabilities.shaderFormats field
Read-only. Lists the shader formats this target consumes. It contains one entry, since a build supplies one format.
tecs.platform.os.Capabilities.shaderFormats: {string}tecs.platform.os.Capabilities.touch field
Read-only. Reports whether the machine currently has a touch device. This describes the machine rather than of the target: a desktop with a touchscreen has one.
tecs.platform.os.Capabilities.touch: booleantecs.platform.os.Capabilities.gamepad field
Read-only. Reports true because every target reaches gamepads through the same subsystem, so only the connected devices vary, which the gamepads method on Input answers.
tecs.platform.os.Capabilities.gamepad: booleantecs.platform.os.Capabilities.sensors field
Read-only. Reports whether the device carries a gyroscope or an accelerometer. This says nothing about a gamepad's sensors, which hasSensor on Gamepad answers per device.
tecs.platform.os.Capabilities.sensors: booleantecs.platform.os.Capabilities.workers field
Read-only. Reports whether work can run off the main thread.
tecs.platform.os.Capabilities.workers: booleantecs.platform.os.Capabilities.cores field
Read-only. Reports the number of logical cores for sizing a worker pool.
tecs.platform.os.Capabilities.cores: integertecs.platform.os.Capabilities.writableStorage field
Read-only. Reports true because every target has somewhere to write, and tecs.io.files.preferencePath and tecs.io.files.cachePath answer where: the field exists so a caller can ask rather than assume, not because a target answers no.
tecs.platform.os.Capabilities.writableStorage: booleantecs.platform.os.DialogFilter record
Describes one file-type filter.
tecs.platform.os.DialogFilter.name field
Caller-writable. Sets the label shown beside the filter, such as "Images".
tecs.platform.os.DialogFilter.name: stringtecs.platform.os.DialogFilter.pattern field
Caller-writable. Sets semicolon-separated extensions, such as "png;jpg;jpeg".
tecs.platform.os.DialogFilter.pattern: stringtecs.platform.os.DialogOptions record
Describes dialog configuration.
record tecs.platform.os.DialogOptions
window: Window
filters: {DialogFilter}
defaultLocation: string
multiple: boolean
endtecs.platform.os.DialogOptions.window field
Caller-writable. Sets the window that owns the dialog.
tecs.platform.os.DialogOptions.window: Windowtecs.platform.os.DialogOptions.filters field
Caller-writable. Sets the available file-type filters.
tecs.platform.os.DialogOptions.filters: {DialogFilter}tecs.platform.os.DialogOptions.defaultLocation field
Caller-writable. Sets the initial file or folder. Omit it to let the platform choose.
tecs.platform.os.DialogOptions.defaultLocation: stringtecs.platform.os.DialogOptions.multiple field
Caller-writable. Allows the user to select more than one path.
tecs.platform.os.DialogOptions.multiple: booleantecs.platform.os.DialogResult record
Describes a completed dialog.
tecs.platform.os.DialogResult.paths field
Read-only. Contains selected paths. It is empty when the user canceled.
tecs.platform.os.DialogResult.paths: {string}tecs.platform.os.DialogResult.filter field
Read-only. Reports the one-based selected filter, or zero when no filter applies.
tecs.platform.os.DialogResult.filter: integertecs.platform.os.DialogResult.canceled field
Read-only. Reports whether the user canceled the dialog.
tecs.platform.os.DialogResult.canceled: booleantecs.platform.os.Locale record
Describes one language the user prefers.
tecs.platform.os.Locale.language field
Read-only. Contains an ISO 639 language code, such as "en".
tecs.platform.os.Locale.country field
Read-only. Contains an ISO 3166 country code, such as "US", or an empty string when the platform names only a language.
tecs.platform.os.Power record
Describes the machine's power source and remaining charge.
tecs.platform.os.Power.state field
Read-only. Reports "unknown", "onBattery", "noBattery", "charging", "charged" or "error".
tecs.platform.os.Power.seconds field
Read-only. Reports seconds of battery life remaining, or -1 when unavailable.
tecs.platform.os.Power.percent field
Read-only. Reports charge percentage in 0..100, or -1 when unavailable.
tecs.platform.os.ProcessSignal enum
ProcessSignal identifies an interrupt, termination, hangup, or quit request sent to this process.
enum tecs.platform.os.ProcessSignal
"hangup"
"interrupt"
"quit"
"terminate"
endtecs.platform.os.SignalListener interface
A SignalListener receives process signals in a headless loop.
interface tecs.platform.os.SignalListener is Closeable
isClosed: function(self): boolean
next: function(self): ProcessSignal
pending: function(self): integer
endInterfaces
| Interface |
|---|
Closeable |
tecs.platform.os.SignalListener:isClosed Instance
Returns whether this listener has been closed.
function tecs.platform.os.SignalListener.isClosed(self): booleanArguments
| Name | Type | Description |
|---|---|---|
self |
SignalListener |
The listener to inspect. |
Returns
| Type | Description |
|---|---|
boolean |
Returns true after close. |
tecs.platform.os.SignalListener:next Instance
Removes and returns one queued signal without waiting.
The call returns nil when no selected signal has arrived since the listener was created or last drained. Signals transferred by the same runtime poll are returned in enum order, not arrival order.
function tecs.platform.os.SignalListener.next(self): ProcessSignalArguments
| Name | Type | Description |
|---|---|---|
self |
SignalListener |
The open listener whose queue advances. |
Returns
| Type | Description |
|---|---|
ProcessSignal |
Returns one selected signal, or nil when none is pending. |
tecs.platform.os.SignalListener:pending Instance
Returns the number of signals waiting to be read.
Signals of the same kind may coalesce before a runtime poll. The count covers deliveries already transferred to this listener.
function tecs.platform.os.SignalListener.pending(self): integerArguments
| Name | Type | Description |
|---|---|---|
self |
SignalListener |
The open listener to inspect. |
Returns
| Type | Description |
|---|---|
integer |
Returns the queued delivery count. |
Functions
tecs.platform.os.capabilities Static
Reads the capabilities of the running build.
The function caches its answer because these values do not change while a platform remains installed. The platform generation keys the cache, so installing a platform drops the value without anybody calling resetCapabilities.
function tecs.platform.os.capabilities(): CapabilitiesArguments
None.
Returns
| Type | Description |
|---|---|
Capabilities |
The same table on every call until the platform changes. Shared, so a caller that means to keep it does not also mean to edit it. |
tecs.platform.os.clearClipboard Static
Withdraws what this application put on the system.
The clipboard is left empty rather than restored to what preceded the write, because nothing anywhere remembers what that was.
function tecs.platform.os.clearClipboard(): booleanArguments
None.
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.clipboardAvailable Static
Reports whether a clipboard is available.
False in a process that never brought up video, where every other function here answers empty or false. Distinguishes that from a clipboard that is simply empty, which no other return value can.
function tecs.platform.os.clipboardAvailable(): booleanArguments
None.
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.clipboardData Static
Returns the clipboard bytes for mimeType, or nil when it offers none.
The caller releases the returned Buffer. Returns nil rather than an empty buffer because the clipboard can offer a MIME type with no bytes, which differs from not offering that type.
function tecs.platform.os.clipboardData(mimeType: string): IOBufferArguments
| Name | Type | Description |
|---|---|---|
mimeType |
string |
Returns
| Type | Description |
|---|---|
IOBuffer |
tecs.platform.os.clipboardMimeTypes Static
Returns the clipboard MIME types in platform order.
The same list clipboardUpdate carries, for a caller that wants to ask rather than wait to be told. Empty when the clipboard is empty.
function tecs.platform.os.clipboardMimeTypes(): {string}Arguments
None.
Returns
| Type | Description |
|---|---|
{string} |
tecs.platform.os.clipboardText Static
Returns the clipboard text, or an empty string when it holds none.
Empty is also the answer when the clipboard holds something that is not text, and when there is no video. Ask hasClipboardText to tell those from text that is genuinely empty.
function tecs.platform.os.clipboardText(): stringArguments
None.
Returns
| Type | Description |
|---|---|
string |
tecs.platform.os.hasClipboardData Static
Reports whether the clipboard offers mimeType.
function tecs.platform.os.hasClipboardData(mimeType: string): booleanArguments
| Name | Type | Description |
|---|---|---|
mimeType |
string |
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.hasClipboardText Static
Reports whether the clipboard holds text.
Cheaper than reading it: no allocation crosses the boundary, and on a platform where a read negotiates with the owning application, no negotiation happens.
function tecs.platform.os.hasClipboardText(): booleanArguments
None.
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.hasPrimarySelection Static
Reports whether the primary selection holds text.
function tecs.platform.os.hasPrimarySelection(): booleanArguments
None.
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.messageBox Static
Shows a native informational, warning or error dialog.
function tecs.platform.os.messageBox(
kind: string, title: string, message: string, window: Window
): boolean, stringArguments
| Name | Type | Description |
|---|---|---|
kind |
string |
|
title |
string |
|
message |
string |
|
window |
Window |
Returns
| Type | Description |
|---|---|
boolean |
|
string |
tecs.platform.os.openFile Static
Opens a native file picker.
function tecs.platform.os.openFile(
options: DialogOptions
): Future<DialogResult>Arguments
| Name | Type | Description |
|---|---|---|
options |
DialogOptions |
Returns
| Type | Description |
|---|---|
Future<DialogResult> |
tecs.platform.os.openFolder Static
Opens a native folder picker.
function tecs.platform.os.openFolder(
options: DialogOptions
): Future<DialogResult>Arguments
| Name | Type | Description |
|---|---|---|
options |
DialogOptions |
Returns
| Type | Description |
|---|---|
Future<DialogResult> |
tecs.platform.os.openURL Static
Opens an absolute URI with the operating system's preferred application.
This is not limited to web URLs. The operating system may route https: to a browser, mailto: to a mail client, and application-specific schemes such as steam: to their registered handler. Tecs passes the string to SDL without parsing it, so the platform decides which schemes it accepts and which application handles them.
function tecs.platform.os.openURL(url: string): boolean, stringArguments
| Name | Type | Description |
|---|---|---|
url |
string |
The caller supplies a non-empty absolute URI. Embedded NUL bytes are not supported by SDL's C-string boundary. |
Returns
| Type | Description |
|---|---|
boolean |
Returns true after the operating system accepts the launch request. |
string |
Returns SDL's reason when the URI is empty, unsupported, malformed, or cannot be opened. |
tecs.platform.os.power Static
Returns the current battery or external-power state.
function tecs.platform.os.power(): PowerArguments
None.
Returns
| Type | Description |
|---|---|
Power |
tecs.platform.os.preferredLocales Static
Returns the user's preferred locales in priority order.
function tecs.platform.os.preferredLocales(): {Locale}Arguments
None.
Returns
| Type | Description |
|---|---|
{Locale} |
tecs.platform.os.primarySelection Static
Returns text from the platform's primary selection.
On X11 and Wayland, selecting text places it in a clipboard separate from the ordinary copy-and-paste clipboard, commonly pasted with the middle mouse button. Platforms without that concept expose only the value this process last supplied through setPrimarySelection; other applications do not see it. This function does not read clipboardText.
function tecs.platform.os.primarySelection(): stringArguments
None.
Returns
| Type | Description |
|---|---|
string |
Returns UTF-8 text, or an empty string when the selection is empty or no video subsystem is available. |
tecs.platform.os.resetCapabilities Static
Forgets the cached answer. Capability lookup notices a platform change without this.
function tecs.platform.os.resetCapabilities()Arguments
None.
Returns
None.
tecs.platform.os.saveFile Static
Opens a native save-file picker. Returns at most one path.
function tecs.platform.os.saveFile(
options: DialogOptions
): Future<DialogResult>Arguments
| Name | Type | Description |
|---|---|---|
options |
DialogOptions |
Returns
| Type | Description |
|---|---|
Future<DialogResult> |
tecs.platform.os.setClipboardText Static
Puts text on the clipboard, replacing whatever was there.
The platform copies the string before this call returns. Returns false when the platform refused, which includes having no video.
function tecs.platform.os.setClipboardText(text: string): booleanArguments
| Name | Type | Description |
|---|---|---|
text |
string |
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.setPrimarySelection Static
Puts text in the primary selection.
Succeeds on a platform that has no shared primary selection, where the value remains visible only to this process.
function tecs.platform.os.setPrimarySelection(text: string): booleanArguments
| Name | Type | Description |
|---|---|---|
text |
string |
Returns
| Type | Description |
|---|---|
boolean |
tecs.platform.os.updateDialogs Static
Settles file and folder dialogs that have answered.
runtime.poll calls this while a dialog is open. It remains public for a test or a specialized headless loop that deliberately drives dialogs alone.
function tecs.platform.os.updateDialogs(): integerArguments
None.
Returns
| Type | Description |
|---|---|
integer |