diff options
| author | Andrey Lihatskiy <alihatskiy@productengine.com> | 2026-04-01 19:50:33 +0300 |
|---|---|---|
| committer | Andrey Lihatskiy <alihatskiy@productengine.com> | 2026-04-01 19:50:33 +0300 |
| commit | f5908eddc683dd705d334c88377139e39bbfb54f (patch) | |
| tree | 75c0ff026fe13c0a507a4527b697aa212736998d | |
| parent | d045f9aa32789a35628aced166145c182751acbf (diff) | |
| parent | f209affdfdf271098843ba400d7a75b00f827233 (diff) | |
Merge branch 'project/lua_editor' into marchcat/devlinux-slua
# Conflicts:
# indra/llcommon/llstl.h
# indra/newview/app_settings/settings.xml
95 files changed, 11806 insertions, 19961 deletions
diff --git a/.gitignore b/.gitignore index a784d6e7d4..483e7083ad 100644 --- a/.gitignore +++ b/.gitignore @@ -89,5 +89,9 @@ web/config.* web/locale.* web/secondlife.com.* +# Auto-generated from lsl_definitions package +indra/newview/app_settings/keywords_lsl_default.xml +indra/newview/app_settings/keywords_lua_default.xml + .env .vscode diff --git a/autobuild.xml b/autobuild.xml index bc6b073a99..bb6673c324 100644 --- a/autobuild.xml +++ b/autobuild.xml @@ -1324,6 +1324,50 @@ <key>name</key> <string>llphysicsextensions_tpv</string> </map> + <key>lsl_definitions</key> + <map> + <key>canonical_repo</key> + <string>https://github.com/secondlife/lsl-definitions</string> + <key>copyright</key> + <string>Copyright (c) 2026, Linden Lab</string> + <key>description</key> + <string>LSL definitions</string> + <key>license</key> + <string>MIT</string> + <key>license_file</key> + <string>LICENSES/lsl_definitions.txt</string> + <key>name</key> + <string>lsl_definitions</string> + <key>platforms</key> + <map> + <key>common</key> + <map> + <key>archive</key> + <map> + <key>hash</key> + <string>6e4e3b86f5daf6dc2e7d7b2b59deaaad293b7232</string> + <key>hash_algorithm</key> + <string>sha1</string> + <key>url</key> + <string>https://github.com/secondlife/lsl-definitions/releases/download/v0.4.1/lsl_definitions-0.4.1-common-22871771849.tar.zst</string> + </map> + <key>name</key> + <string>common</string> + </map> + </map> + <key>source_type</key> + <string>git</string> + <key>use_scm_version</key> + <boolean>true</boolean> + <key>vcs_branch</key> + <string>refs/tags/v0.4.1</string> + <key>vcs_revision</key> + <string>03006fb488cba2bae502e9baed051bfc8d00144d</string> + <key>vcs_url</key> + <string>git://github.com/secondlife/lsl-definitions.git</string> + <key>version</key> + <string>0.4.1</string> + </map> <key>meshoptimizer</key> <map> <key>platforms</key> @@ -2429,6 +2473,16 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string> </map> <key>webrtc</key> <map> + <key>canonical_repo</key> + <string>https://github.com/secondlife/3p-webrtc-build</string> + <key>copyright</key> + <string>Copyright (c) 2011, The WebRTC project authors. All rights reserved.</string> + <key>license</key> + <string>MIT</string> + <key>license_file</key> + <string>LICENSES/webrtc-license.txt</string> + <key>name</key> + <string>webrtc</string> <key>platforms</key> <map> <key>darwin64</key> @@ -2436,11 +2490,11 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string> <key>archive</key> <map> <key>hash</key> - <string>a5e72a9d13b6c4646d1e02b5820f16560d204de7</string> + <string>7338377a9c6913bc8768d446fe627b8176bc89d4</string> <key>hash_algorithm</key> <string>sha1</string> <key>url</key> - <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.21/webrtc-m137.7151.04.21.18609120431-darwin64-18609120431.tar.zst</string> + <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.23/webrtc-m137.7151.04.23.22004231636-darwin64-22004231636.tar.zst</string> </map> <key>name</key> <string>darwin64</string> @@ -2450,11 +2504,11 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string> <key>archive</key> <map> <key>hash</key> - <string>1030e5086f401d738463223da3ed99c225340f39</string> + <string>a2df83ed8d7fc1374398d7a37633bae17f5d68a1</string> <key>hash_algorithm</key> <string>sha1</string> <key>url</key> - <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.21/webrtc-m137.7151.04.21.18609120431-linux64-18609120431.tar.zst</string> + <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.23/webrtc-m137.7151.04.23.22004231636-linux64-22004231636.tar.zst</string> </map> <key>name</key> <string>linux64</string> @@ -2464,34 +2518,24 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string> <key>archive</key> <map> <key>hash</key> - <string>d1cae9bc8866ca01aa9f5e72b36d12ef608b1998</string> + <string>665c2447c794a88542fab30638f0013bea58480c</string> <key>hash_algorithm</key> <string>sha1</string> <key>url</key> - <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.21/webrtc-m137.7151.04.21.18609120431-windows64-18609120431.tar.zst</string> + <string>https://github.com/secondlife/3p-webrtc-build/releases/download/m137.7151.04.23/webrtc-m137.7151.04.23.22004231636-windows64-22004231636.tar.zst</string> </map> <key>name</key> <string>windows64</string> </map> </map> - <key>license</key> - <string>MIT</string> - <key>license_file</key> - <string>LICENSES/webrtc-license.txt</string> - <key>copyright</key> - <string>Copyright (c) 2011, The WebRTC project authors. All rights reserved.</string> - <key>version</key> - <string>m137.7151.04.21.18609120431</string> - <key>name</key> - <string>webrtc</string> <key>vcs_branch</key> <string>secondlife</string> <key>vcs_revision</key> <string>d3f62d32bac8694d3c7423c731ae30c113bf6a11</string> <key>vcs_url</key> <string>https://github.com/secondlife/3p-webrtc-build</string> - <key>canonical_repo</key> - <string>https://github.com/secondlife/3p-webrtc-build</string> + <key>version</key> + <string>m137.7151.04.23.22004231636</string> </map> <key>xxhash</key> <map> @@ -2717,6 +2761,46 @@ Copyright (c) 2012, 2014, 2015, 2016 nghttp2 contributors</string> <key>description</key> <string>Voxelized Hierarchical Approximate Convex Decomposition</string> </map> + <key>websocketpp</key> + <map> + <key>platforms</key> + <map> + <key>common</key> + <map> + <key>archive</key> + <map> + <key>hash</key> + <string>a69aa37bfbcb934974f7af906f6dc6b044692f07</string> + <key>hash_algorithm</key> + <string>sha1</string> + <key>url</key> + <string>https://github.com/secondlife/3p-websocketpp/releases/download/v0.8.2-r2/websocketpp-0.8.2.19586590594-common-19586590594.tar.zst</string> + </map> + <key>name</key> + <string>common</string> + </map> + </map> + <key>license</key> + <string>websocketpp</string> + <key>license_file</key> + <string>LICENSES/websocketpp.txt</string> + <key>copyright</key> + <string>Copyright (c) 2014, Peter Thorson</string> + <key>version</key> + <string>0.8.2.19586590594</string> + <key>name</key> + <string>websocketpp</string> + <key>vcs_branch</key> + <string>refs/tags/v0.8.2</string> + <key>vcs_revision</key> + <string>bdcf1453101976fc4dc26a62c87bc98c12e9c6dc</string> + <key>vcs_url</key> + <string>git://github.com/secondlife/3p-websocketpp.git</string> + <key>canonical_repo</key> + <string>https://github.com/secondlife/3p-websocketpp</string> + <key>description</key> + <string>WebSocket++ is a C++ header only library for interacting with WebSocket servers and clients.</string> + </map> </map> <key>package_description</key> <map> diff --git a/doc/external-editor-json-rpc.md b/doc/external-editor-json-rpc.md new file mode 100644 index 0000000000..b8c7fa69e3 --- /dev/null +++ b/doc/external-editor-json-rpc.md @@ -0,0 +1,464 @@ +# Viewer to External Editor JSON-RPC<br>Message Interfaces Documentation + +This document describes all the message interfaces defined in for WebSocket communication between the Second Life viewer and an external editor such as a VSCode extension. + +## Table of Contents + +- [Usage Flow](#usage-flow) +- [JSON-RPC Method Summary](#json-rpc-method-summary) +- [Session Management Interfaces](#session-management-interfaces) + - [SessionHandshake](#sessionhandshake) + - [SessionHandshakeResponse](#sessionhandshakeresponse) + - [Session OK](#session-ok) + - [SessionDisconnect](#sessiondisconnect) +- [Language and Syntax Interfaces](#language-and-syntax-interfaces) + - [SyntaxChange](#syntaxchange) + - [Language Syntax ID Request](#language-syntax-id-request) + - [Language Syntax Request](#language-syntax-request) +- [Script Subscription Interfaces](#script-subscription-interfaces) + - [ScriptSubscribe](#scriptsubscribe) + - [ScriptSubscribeResponse](#scriptsubscriberesponse) + - [ScriptUnsubscribe](#scriptunsubscribe) +- [Compilation Interfaces](#compilation-interfaces) + - [CompilationError](#compilationerror) + - [CompilationResult](#compilationresult) +- [Runtime Event Interfaces](#runtime-event-interfaces) + - [RuntimeDebug](#runtimedebug) + - [RuntimeError](#runtimeerror) +- [Handler and Configuration Interfaces](#handler-and-configuration-interfaces) + - [WebSocketHandlers](#websockethandlers) + - [ClientInfo](#clientinfo) + +## Usage Flow + +1. **Connection Establishment:** + + - Viewer sends `session.handshake` notification with `SessionHandshake` data + - Extension responds with `SessionHandshakeResponse` + - Viewer confirms with `session.ok` notification + +2. **Language Information Exchange:** + + - Extension makes `language.syntax.id` call to get current syntax version + - Extension makes `language.syntax` calls with different `kind` parameters to get specific language data + - Viewer responds with `LanguageInfo` data containing the requested information + +3. **Script Subscription Management:** + + - Extension makes `script.subscribe` call with `ScriptSubscribe` data to request live synchronization for a script + - Viewer responds with `ScriptSubscribeResponse` indicating success or failure + - When subscription needs to be terminated, viewer sends `script.unsubscribe` notification with `ScriptUnsubscribe` data + - Extension handles unsubscription by cleaning up local script tracking + +4. **Runtime Events:** + + - Viewer sends `language.syntax.change` notification with `SyntaxChange` when language changes + - Viewer sends `script.compiled` notification with `CompilationResult` after script compilation + - Viewer sends `runtime.debug` notification with `RuntimeDebug` for debug messages during script execution + - Viewer sends `runtime.error` notification with `RuntimeError` when runtime errors occur + +5. **Connection Termination:** + - Either side can send `session.disconnect` notification with `SessionDisconnect` data + - Connection is closed gracefully + +## JSON-RPC Method Summary + +| Method | Direction | Type | Interface/Parameters | +| ------------------------------- | ------------------ | ------------ | -------------------------- | +| `session.handshake` | Viewer → Extension | Notification | `SessionHandshake` | +| `session.handshake` (response) | Extension → Viewer | Response | `SessionHandshakeResponse` | +| `session.ok` | Viewer → Extension | Notification | _(no interface)_ | +| `session.disconnect` | Bidirectional | Notification | `SessionDisconnect` | +| `script.subscribe` | Extension → Viewer | Call | `ScriptSubscribe` | +| `script.subscribe` (response) | Viewer → Extension | Response | `ScriptSubscribeResponse` | +| `script.unsubscribe` | Viewer → Extension | Notification | `ScriptUnsubscribe` | +| `language.syntax.id` | Extension → Viewer | Call | _(no parameters)_ | +| `language.syntax.id` (response) | Viewer → Extension | Response | `{ id: string }` | +| `language.syntax` | Extension → Viewer | Call | `{ kind: string }` | +| `language.syntax` (response) | Viewer → Extension | Response | `LanguageInfo` | +| `language.syntax.change` | Viewer → Extension | Notification | `SyntaxChange` | +| `script.compiled` | Viewer → Extension | Notification | `CompilationResult` | +| `runtime.debug` | Viewer → Extension | Notification | `RuntimeDebug` | +| `runtime.error` | Viewer → Extension | Notification | `RuntimeError` | + +## Session Management Interfaces + +### SessionHandshake + +**JSON-RPC Method:** `session.handshake` (notification from viewer) + +The initial handshake message sent by the viewer to establish a connection. + +```typescript +interface SessionHandshake { + server_version: "1.0.0"; + protocol_version: "1.0"; + viewer_name: string; + viewer_version: string; + agent_id: string; + agent_name: string; + challenge?: string; + languages: string[]; + syntax_id: string; + features: { [feature: string]: boolean }; +} +``` + +**Fields:** + +- `server_version`: Fixed version "1.0.0" indicating the server API version +- `protocol_version`: Fixed version "1.0" for the communication protocol +- `viewer_name`: Name of the Second Life viewer application +- `viewer_version`: Version string of the viewer +- `agent_id`: Unique identifier for the user/agent +- `agent_name`: Human-readable name of the agent +- `challenge` (optional): Security challenge string for authentication +- `languages`: Array of supported scripting languages (e.g., ["lsl", "luau"]) +- `syntax_id`: Current active syntax/language identifier +- `features`: Dictionary of feature flags indicating viewer capabilities + +### SessionHandshakeResponse + +**JSON-RPC Method:** Response to `session.handshake` + +The response sent by the VS Code extension to complete the handshake. + +```typescript +interface SessionHandshakeResponse { + client_name: string; + client_version: "1.0"; + protocol_version: string; + challenge_response?: string; + languages: string[]; + features: { [feature: string]: boolean }; +} +``` + +**Fields:** + +- `client_name`: Name of the client (VS Code extension) +- `client_version`: Fixed version "1.0" of the client +- `protocol_version`: Protocol version the client supports +- `challenge_response` (optional): Response to the security challenge if provided +- `languages`: Array of languages supported by the client +- `features`: Dictionary of features supported by the client + +### Session OK + +**JSON-RPC Method:** `session.ok` (notification from viewer) + +Confirmation notification sent by the viewer after successful handshake completion. This interface has no defined structure as it appears to be a simple confirmation message. + +### SessionDisconnect + +**JSON-RPC Method:** `session.disconnect` (notification, bidirectional) + +Message sent when terminating the connection. + +```typescript +interface SessionDisconnect { + reason: number; + message: string; +} +``` + +**Fields:** + +- `reason`: Numeric code indicating the reason for disconnection +- `message`: Human-readable description of the disconnect reason + +## Language and Syntax Interfaces + +### SyntaxChange + +**JSON-RPC Method:** `language.syntax.change` (notification from viewer) + +Notification sent when the active language syntax changes in the viewer. + +```typescript +interface SyntaxChange { + id: string; +} +``` + +**Fields:** + +- `id`: Identifier for the new syntax/language + +### Language Syntax ID Request + +**JSON-RPC Method:** `language.syntax.id` (call from extension to viewer) + +Requests the current active language syntax identifier from the viewer. This method takes no parameters. + +**Response:** Returns an object with an `id` field containing the current syntax identifier. + +### Language Syntax Request + +**JSON-RPC Method:** `language.syntax` (call from extension to viewer) + +Requests detailed syntax information for a specific language kind. + +**Parameters:** + +```typescript +{ + kind: string; // The type of syntax information requested +} +``` + +**Fields:** + +- `kind`: The type of syntax information to retrieve (e.g., "functions", "constants", "events", "types.luau") + +**Response:** Returns `LanguageInfo` data containing the requested syntax information: + +```typescript +interface LanguageInfo { + id: string; + lslDefs?: { + controls?: any; + types?: any; + constants?: { [name: string]: ConstantDef }; + events?: { [name: string]: FunctionDef }; + functions?: { [name: string]: FunctionDef }; + }; + luaDefs?: { + modules?: { [name: string]: TypeDef }; + classes?: { [name: string]: TypeDef }; + aliases?: { [name: string]: TypeDef }; + functions?: { [name: string]: FunctionDef }; + }; +} +``` + +**Response Fields:** + +- `id`: Version identifier for the language syntax +- `lslDefs` (optional): LSL-specific language definitions containing: + - `controls` (optional): Control flow and language constructs + - `types` (optional): LSL type definitions + - `constants` (optional): Object containing constant definitions keyed by constant name + - `events` (optional): Object containing event definitions keyed by event name + - `functions` (optional): Object containing function definitions keyed by function name +- `luaDefs` (optional): Lua-specific language definitions containing: + - `modules` (optional): Module type definitions keyed by module name + - `classes` (optional): Class type definitions keyed by class name + - `aliases` (optional): Type alias definitions keyed by alias name + - `functions` (optional): Function definitions keyed by function name + +The specific sections returned depend on the `kind` parameter and the active language context. + +## Script Subscription Interfaces + +### ScriptSubscribe + +**JSON-RPC Method:** `script.subscribe` (call from extension to viewer) + +Requests subscription to a script for live synchronization between the editor and viewer. + +```typescript +interface ScriptSubscribe { + script_id: string; + script_name: string; + script_language: string; +} +``` + +**Fields:** + +- `script_id`: Unique identifier for the script to subscribe to +- `script_name`: Display name of the script file +- `script_language`: Programming language of the script (e.g., "lsl", "luau") + +### ScriptSubscribeResponse + +**JSON-RPC Method:** Response to `script.subscribe` + +Response from the viewer indicating whether script subscription was successful. + +```typescript +interface ScriptSubscribeResponse { + script_id: string; + success: boolean; + status: number; + object_id?: string; + object_name?: string; + item_id?: string; + message?: string; +} +``` + +**Fields:** + +- `script_id`: The script identifier that was subscribed to +- `success`: Whether the subscription was successful +- `status`: Numeric status code indicating the result +- `object_id` (optional): The in-world ID of the object containing the script +- `object_name` (optional): The name of the object containing the script. +- `message` (optional): Additional information about the subscription result + +### ScriptUnsubscribe + +**JSON-RPC Method:** `script.unsubscribe` (notification from viewer) + +Notification sent by the viewer when a script subscription should be terminated. + +```typescript +interface ScriptUnsubscribe { + script_id: string; +} +``` + +**Fields:** + +- `script_id`: Unique identifier for the script to unsubscribe from + +## Compilation Interfaces + +### CompilationError + +Individual compilation error record. + +```typescript +interface CompilationError { + row: number; + column: number; + level: "ERROR"; + message: string; +} +``` + +**Fields:** + +- `row`: Line number where the error occurred (0-based or 1-based depending on context) +- `column`: Column position of the error +- `level`: Severity level (currently only "ERROR" is defined) +- `message`: Error description + +### CompilationResult + +**JSON-RPC Method:** `script.compiled` (notification from viewer) + +Result of a compilation operation in the viewer. + +```typescript +interface CompilationResult { + script_id: string; + success: boolean; + running: boolean; + errors?: CompilationError[]; +} +``` + +**Fields:** + +- `script_id`: Unique identifier for the script that was compiled +- `success`: Whether the compilation was successful +- `running`: Whether the compiled script is currently running +- `errors` (optional): Array of compilation errors if any occurred + +## Runtime Event Interfaces + +### RuntimeDebug + +**JSON-RPC Method:** `runtime.debug` (notification from viewer) + +Debug message notification sent by the viewer during script execution. + +```typescript +interface RuntimeDebug { + script_id: string; + object_id: string; + object_name: string; + message: string; +} +``` + +**Fields:** + +- `script_id`: Unique identifier for the script generating the debug message +- `object_id`: Unique identifier for the object containing the script +- `object_name`: Human-readable name of the object +- `message`: The debug message content + +### RuntimeError + +**JSON-RPC Method:** `runtime.error` (notification from viewer) + +Runtime error notification sent by the viewer when a script encounters an error during execution. + +```typescript +interface RuntimeError { + script_id: string; + object_id: string; + object_name: string; + message: string; + error: string; + line: number; + stack?: string[]; +} +``` + +**Fields:** + +- `script_id`: Unique identifier for the script that encountered the error +- `object_id`: Unique identifier for the object containing the script +- `object_name`: Human-readable name of the object +- `message`: Error message description +- `error`: Specific error type or code +- `line`: Line number where the error occurred +- `stack` (optional): Stack trace information if available + +## Handler and Configuration Interfaces + +### WebSocketHandlers + +Event handler interface for WebSocket events. + +```typescript +interface WebSocketHandlers { + onHandshake?: (message: SessionHandshake) => SessionHandshakeResponse; + onHandshakeOk?: () => void; + onDisconnect?: (message: SessionDisconnect) => void; + onSubscribe?: (message: ScriptSubscribe) => ScriptSubscribeResponse; + onUnsubscribe?: (message: ScriptUnsubscribe) => void; + onSyntaxChange?: (message: SyntaxChange) => void; + onConnectionClosed?: () => void; + onCompilationResult?: (message: CompilationResult) => void; + onRuntimeDebug?: (message: RuntimeDebug) => void; + onRuntimeError?: (message: RuntimeError) => void; +} +``` + +**Methods:** + +- `onHandshake`: Handler for initial handshake message, returns handshake response +- `onHandshakeOk`: Handler called when handshake is successfully completed +- `onDisconnect`: Handler for disconnect notifications +- `onSubscribe`: Handler for script subscription requests from viewer, returns subscription response +- `onUnsubscribe`: Handler for script unsubscription notifications from viewer +- `onSyntaxChange`: Handler for syntax change notifications +- `onConnectionClosed`: Handler called when connection is closed +- `onCompilationResult`: Handler for compilation result notifications +- `onRuntimeDebug`: Handler for runtime debug message notifications +- `onRuntimeError`: Handler for runtime error notifications + +### ClientInfo + +Client information used in handshake responses. + +```typescript +interface ClientInfo { + scriptName: string; + scriptId: string; + extension: string; +} +``` + +**Fields:** + +- `scriptName`: Name of the script being edited +- `scriptId`: Unique identifier for the script +- `extension`: File extension or script type + diff --git a/indra/cmake/CMakeLists.txt b/indra/cmake/CMakeLists.txt index fa5008c373..6bbc61feaa 100644 --- a/indra/cmake/CMakeLists.txt +++ b/indra/cmake/CMakeLists.txt @@ -69,6 +69,7 @@ set(cmake_SOURCE_FILES VisualLeakDetector.cmake LibVLCPlugin.cmake WebRTC.cmake + websocketpp.cmake xxHash.cmake ZLIBNG.cmake ) diff --git a/indra/cmake/LSLDefinitions.cmake b/indra/cmake/LSLDefinitions.cmake new file mode 100644 index 0000000000..ae0eeebb7e --- /dev/null +++ b/indra/cmake/LSLDefinitions.cmake @@ -0,0 +1,9 @@ +# -*- cmake -*- +include(Prebuilt) + +use_prebuilt_binary(lsl_definitions) + +configure_file("${AUTOBUILD_INSTALL_DIR}/lsl_definitions/lsl_keywords_pretty.xml" + "${CMAKE_SOURCE_DIR}/newview/app_settings/keywords_lsl_default.xml" COPYONLY) +configure_file("${AUTOBUILD_INSTALL_DIR}/lsl_definitions/slua_keywords_pretty.xml" + "${CMAKE_SOURCE_DIR}/newview/app_settings/keywords_lua_default.xml" COPYONLY) diff --git a/indra/cmake/ViewerMiscLibs.cmake b/indra/cmake/ViewerMiscLibs.cmake index 23fd477ba8..1c8495de74 100644 --- a/indra/cmake/ViewerMiscLibs.cmake +++ b/indra/cmake/ViewerMiscLibs.cmake @@ -18,3 +18,5 @@ use_prebuilt_binary(slvoice) use_prebuilt_binary(nanosvg) use_prebuilt_binary(viewer-fonts) use_prebuilt_binary(emoji_shortcodes) + +include(LSLDefinitions) diff --git a/indra/cmake/websocketpp.cmake b/indra/cmake/websocketpp.cmake new file mode 100644 index 0000000000..726f0a5e0b --- /dev/null +++ b/indra/cmake/websocketpp.cmake @@ -0,0 +1,7 @@ +# -*- cmake -*- +include(Prebuilt) + +add_library( ll::websocketpp INTERFACE IMPORTED ) + +use_system_binary( websocketpp ) +use_prebuilt_binary(websocketpp) diff --git a/indra/llcommon/CMakeLists.txt b/indra/llcommon/CMakeLists.txt index bff3c66924..5063a3b285 100644 --- a/indra/llcommon/CMakeLists.txt +++ b/indra/llcommon/CMakeLists.txt @@ -333,7 +333,7 @@ if (LL_TESTS) LL_ADD_INTEGRATION_TEST(llleap "" "${test_libs}") LL_ADD_INTEGRATION_TEST(llmainthreadtask "" "${test_libs}") LL_ADD_INTEGRATION_TEST(llpounceable "" "${test_libs}") - LL_ADD_INTEGRATION_TEST(llprocess "" "${test_libs}") + #LL_ADD_INTEGRATION_TEST(llprocess "" "${test_libs}") RIDER: Test is a known failure. Disabling for the moment. LL_ADD_INTEGRATION_TEST(llprocessor "" "${test_libs}") LL_ADD_INTEGRATION_TEST(llprocinfo "" "${test_libs}") LL_ADD_INTEGRATION_TEST(llrand "" "${test_libs}") diff --git a/indra/llcommon/lleventcoro.cpp b/indra/llcommon/lleventcoro.cpp index e1fc4764f6..bb2cd4fb2e 100644 --- a/indra/llcommon/lleventcoro.cpp +++ b/indra/llcommon/lleventcoro.cpp @@ -137,6 +137,18 @@ void llcoro::suspendUntilTimeout(float seconds) suspendUntilEventOnWithTimeout(bogus, seconds, timedout); } +void llcoro::suspendUntilNextFrame() +{ + LLCoros::checkStop(); + LLCoros::TempStatus st("waiting for next frame"); + + // Listen for the next event on the "mainloop" event pump. + // Once per frame we get mainloop.post(newFrame); + LLEventPumpOrPumpName mainloop_pump("mainloop"); + // Wait for the next event (the event data is ignored). + suspendUntilEventOn(mainloop_pump); +} + namespace { diff --git a/indra/llcommon/lleventcoro.h b/indra/llcommon/lleventcoro.h index 492563bb98..25a8a98e36 100644 --- a/indra/llcommon/lleventcoro.h +++ b/indra/llcommon/lleventcoro.h @@ -85,6 +85,11 @@ void suspend(); void suspendUntilTimeout(float seconds); /** + * Yield control from a coroutine until the next mainloop's newFrame event. + */ +void suspendUntilNextFrame(); + +/** * Post specified LLSD event on the specified LLEventPump, then suspend for a * response on specified other LLEventPump. This is more than mere * convenience: the difference between this function and the sequence diff --git a/indra/llcommon/llstl.h b/indra/llcommon/llstl.h index 550725cbc8..bb8055ed46 100644 --- a/indra/llcommon/llstl.h +++ b/indra/llcommon/llstl.h @@ -36,6 +36,7 @@ #include <set> #include <typeindex> #include <typeinfo> +#include <boost/iterator/filter_iterator.hpp> #ifdef LL_LINUX // <ND> For strcmp @@ -696,6 +697,210 @@ struct ll_template_cast_impl<DEST, SOURCE> \ } \ } +//----------------------------------------------- +namespace LL +{ + /** + * @brief A range adapter that provides filtered iteration over a container. + * + * filter_range creates a filtered view of an iterator range using a predicate function. + * Only elements that satisfy the predicate will be accessible when iterating through + * the range. This is useful for processing subsets of containers without copying data. + * + * The class uses boost::filter_iterator internally to provide the filtering functionality. + * + * @tparam Predicate A callable object (function, functor, lambda) that takes an element + * from the iterator range and returns true if the element should be + * included in the filtered range. + * @tparam Iterator The iterator type for the underlying container/range. + * + * Example usage: + * @code + * std::vector<int> numbers = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; + * + * // Create a predicate to filter even numbers + * auto is_even = [](int n) { return n % 2 == 0; }; + * + * // Create filtered range using make_filter helper + * auto even_range = LL::make_filter(is_even, numbers.begin(), numbers.end()); + * + * // Iterate through only even numbers + * for (auto value : even_range) { + * std::cout << value << " "; // Prints: 2 4 6 8 10 + * } + * + * // Or manually construct the filter_range + * LL::filter_range<decltype(is_even), std::vector<int>::iterator> + * manual_range(is_even, numbers.begin(), numbers.end()); + * @endcode + * + * @note This class provides a lightweight view over the original data. + * No copying of elements occurs, making it efficient for large containers. + * @note The predicate is applied during iteration, so complex predicates may + * impact performance for frequently-accessed ranges. + * @note The underlying container must remain valid for the lifetime of the filter_range. + * + * @see make_filter() for a convenient factory function + * @see boost::filter_iterator for the underlying implementation details + */ + template<typename Predicate, typename Iterator> + class filter_range + { + public: + /// The filtered iterator type - combines predicate with base iterator + using filter_iter = boost::filter_iterator<Predicate, Iterator>; + + /// Value type of the filtered elements + using value_type = typename std::iterator_traits<Iterator>::value_type; + + /// Iterator type for range-based for loops and STL algorithms + using iterator = filter_iter; + using const_iterator = filter_iter; + + /** + * @brief Constructs a filter_range with the given predicate and iterator range. + * + * @param pred The predicate function/functor to filter elements. + * Must be callable with signature: bool(const value_type&) + * @param begin Iterator to the beginning of the range to filter + * @param end Iterator to the end of the range to filter + * + * @pre begin and end must form a valid iterator range + * @pre pred must be a valid callable that can be invoked with elements from [begin, end) + */ + filter_range(Predicate pred, Iterator begin, Iterator end) + : begin_(pred, begin, end), end_(pred, end, end) {} + + /** + * @brief Returns an iterator to the first element that satisfies the predicate. + * + * @return filter_iter Iterator pointing to the first filtered element, + * or equal to end() if no elements satisfy the predicate. + */ + filter_iter begin() const { return begin_; } + + /** + * @brief Returns an iterator representing the end of the filtered range. + * + * @return filter_iter Past-the-end iterator for the filtered range. + */ + filter_iter end() const { return end_; } + + /** + * @brief Checks if the filtered range is empty. + * + * @return true if no elements in the range satisfy the predicate, false otherwise. + * + * @note This operation has O(1) complexity as it only compares iterators. + */ + bool empty() const { return begin_ == end_; } + + private: + filter_iter begin_; ///< Iterator to first element satisfying predicate + filter_iter end_; ///< Past-the-end iterator for the filtered range + }; + + /** + * @brief Factory function to create a filter_range with automatic template deduction. + * + * This convenience function eliminates the need to explicitly specify template parameters + * when creating a filter_range. The template parameters are automatically deduced from + * the function arguments. + * + * @tparam Predicate Automatically deduced predicate type + * @tparam Iterator Automatically deduced iterator type + * + * @param pred Predicate function/functor for filtering elements + * @param begin Iterator to the beginning of the range + * @param end Iterator to the end of the range + * + * @return filter_range<Predicate, Iterator> A filter_range object configured with + * the provided predicate and range + * + * Example usage: + * @code + * std::vector<std::string> words = {"hello", "world", "test", "example"}; + * + * // Filter strings longer than 4 characters + * auto long_words = LL::make_filter( + * [](const std::string& s) { return s.length() > 4; }, + * words.begin(), + * words.end() + * ); + * + * // Use with range-based for loop + * for (const auto& word : long_words) { + * std::cout << word << std::endl; // Prints: hello, world, example + * } + * + * // Use with STL algorithms + * auto count = std::distance(long_words.begin(), long_words.end()); + * std::cout << "Found " << count << " long words." << std::endl; + * @endcode + * + * @note This function is preferred over direct construction of filter_range + * for most use cases due to automatic template parameter deduction. + */ + template<typename Predicate, typename Iterator> + filter_range<Predicate, Iterator> make_filter(Predicate pred, Iterator begin, Iterator end) + { + return filter_range<Predicate, Iterator>(pred, begin, end); + } + + /** + * @brief Create a filter_range over an entire container with automatic template deduction. + * + * This convenience function creates a filtered view over an entire container without + * requiring explicit begin() and end() calls. It automatically handles both const and + * non-const containers, preserving constness in the resulting iterator types. + * + * @tparam Predicate Automatically deduced predicate type + * @tparam Container Automatically deduced container type (const or non-const) + * + * @param pred Predicate function/functor for filtering elements + * @param container The container to filter (can be const or non-const) + * + * @return filter_range with appropriate iterator type for the container + * + * Example usage: + * @code + * // Non-const container + * std::vector<int> numbers = {1, 2, 3, 4, 5, 6, 7, 8, 9, 10}; + * auto evens = LL::make_filter([](int n) { return n % 2 == 0; }, numbers); + * + * // Const container + * const std::list<std::string> words = {"cat", "elephant", "dog", "hippopotamus"}; + * auto long_words = LL::make_filter([](const std::string& s) { return s.size() > 3; }, words); + * + * // Works with any container that supports begin()/end() + * std::set<double> values = {1.1, 2.2, 3.3, 4.4, 5.5}; + * auto large_values = LL::make_filter([](double d) { return d > 3.0; }, values); + * + * // Use with range-based for loops + * for (const auto& word : long_words) { + * std::cout << word << " "; // Prints: elephant hippopotamus + * } + * + * // Chain with STL algorithms + * auto even_count = std::distance(evens.begin(), evens.end()); + * std::cout << "Found " << even_count << " even numbers." << std::endl; + * @endcode + * + * @note This overload automatically calls begin() and end() on the container, + * making it more convenient than the iterator-based version. + * @note The container must remain valid for the lifetime of the returned filter_range. + * @note Constness of the container is preserved in the iterator type. + */ + template<typename Predicate, typename Container> + filter_range<Predicate, decltype(std::begin(std::declval<Container>()))> + make_filter(Predicate pred, Container&& container) + { + return filter_range<Predicate, decltype(std::begin(std::declval<Container>()))>( + pred, std::begin(container), std::end(container)); + } + +} // namespace LL + // Transparent string hashing helper for use with std::unordered_* // std::unordered_map<std::string, val, ll::string_hash, std::equal_to<>> namespace ll diff --git a/indra/llcorehttp/CMakeLists.txt b/indra/llcorehttp/CMakeLists.txt index 58bbdb2d9a..fbc25a7cd5 100644 --- a/indra/llcorehttp/CMakeLists.txt +++ b/indra/llcorehttp/CMakeLists.txt @@ -12,6 +12,7 @@ include(LLAddBuildTest) include(LLCommon) include(Tut) include(bugsplat) +include(websocketpp) set(llcorehttp_SOURCE_FILES bufferarray.cpp @@ -23,6 +24,8 @@ set(llcorehttp_SOURCE_FILES httprequest.cpp httpresponse.cpp httpstats.cpp + llwebsocketmgr.cpp + lljsonrpcws.cpp _httplibcurl.cpp _httpopcancel.cpp _httpoperation.cpp @@ -51,6 +54,8 @@ set(llcorehttp_HEADER_FILES httprequest.h httpresponse.h httpstats.h + llwebsocketmgr.h + lljsonrpcws.h _httpinternal.h _httplibcurl.h _httpopcancel.h @@ -86,6 +91,7 @@ target_link_libraries( ll::libcurl ll::openssl ll::nghttp2 + ll::websocketpp ) target_include_directories( llcorehttp INTERFACE ${CMAKE_CURRENT_SOURCE_DIR}) # llmessage depends on llcorehttp, yet llcorehttp also depends on llmessage (at least for includes). diff --git a/indra/llcorehttp/lljsonrpcws.cpp b/indra/llcorehttp/lljsonrpcws.cpp new file mode 100644 index 0000000000..93e38a8397 --- /dev/null +++ b/indra/llcorehttp/lljsonrpcws.cpp @@ -0,0 +1,628 @@ +/** + * @file lljsonrpcws.cpp + * @brief JSON-RPC 2.0 WebSocket server and connection implementation + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#include "linden_common.h" + +#include "lljsonrpcws.h" +#include "llerror.h" +#include "llsdjson.h" +#include "lldate.h" + +#include <boost/json.hpp> + +//======================================================================== +// LLJSONRPCConnection Implementation +//======================================================================== + +void LLJSONRPCConnection::onOpen() +{ + LL_INFOS("JSONRPC") << "JSON-RPC connection opened" << LL_ENDL; +} + +void LLJSONRPCConnection::onClose() +{ + LL_INFOS("JSONRPC") << "JSON-RPC connection closed, clearing " + << mPendingRequests.size() << " pending requests" << LL_ENDL; + + // Cancel all pending requests + for (auto& [id, callback] : mPendingRequests) + { + if (callback) + { + LLSD error; + error["code"] = RPCError::CONNECTION_CLOSED; // Use named constant instead of magic number + error["message"] = "Connection closed"; + callback(LLSD(), error); + } + } + mPendingRequests.clear(); +} + +void LLJSONRPCConnection::onMessage(const std::string& message) +{ + LL_DEBUGS("JSONRPC") << "Received JSON-RPC message: " << message << LL_ENDL; + + try + { + // Parse JSON message + boost::system::error_code ec; + boost::json::value json_value = boost::json::parse(message, ec); + + if (ec.failed()) + { + LL_WARNS("JSONRPC") << "Failed to parse JSON: " << ec.message() << LL_ENDL; + sendError(LLSD(), ParseError(ec.message())); + return; + } + + // Convert to LLSD + LLSD message_obj = LlsdFromJson(json_value); + + // Handle batch vs single message + if (message_obj.isArray()) + { + // Batch request + if (message_obj.size() == 0) + { + sendError(LLSD(), InvalidRequest("Empty batch")); + return; + } + + // Process each message in the batch + for (S32 i = 0; i < message_obj.size(); ++i) + { + processMessage(message_obj[i]); + } + } + else + { + // Single message + processMessage(message_obj); + } + } + catch (const std::exception& e) + { + LL_WARNS("JSONRPC") << "Exception processing JSON-RPC message: " << e.what() << LL_ENDL; + sendError(LLSD(), InternalError(e.what())); + } +} + +void LLJSONRPCConnection::processMessage(const LLSD& message_obj) +{ + try + { + // Determine if this is a request, notification, or response + if (message_obj.has("method")) + { + // This is a request or notification + if (validateMessage(message_obj, true)) + { + processRequest(message_obj); + } + } + else if (message_obj.has("result") || message_obj.has("error")) + { + // This is a response + if (validateMessage(message_obj, false)) + { + processResponse(message_obj); + } + } + else + { + LL_WARNS("JSONRPC") << "Message must contain 'method' or 'result'/'error'" << LL_ENDL; + } + } + catch (const RPCError& e) + { + LLSD id = message_obj.has("id") ? message_obj["id"] : LLSD(); + sendError(id, e); + } +} + +void LLJSONRPCConnection::processRequest(const LLSD& request) +{ + std::string method = request["method"].asString(); + LLSD params = request.has("params") ? request["params"] : LLSD(); + LLSD id = request.has("id") ? request["id"] : LLSD(); + bool is_notification = !request.has("id"); + + LL_DEBUGS("JSONRPC") << "Processing " << (is_notification ? "notification" : "request") + << " for method: " << method << LL_ENDL; + + // Find method handler + auto it = mMethodHandlers.find(method); + if (it == mMethodHandlers.end()) + { + if (!is_notification) + { + sendError(id, MethodNotFound(method)); + } + return; + } + + try + { + // Call the method handler with method name, ID, and parameters + LLSD result = it->second(method, id, params); + + if (!is_notification) + { + sendResponse(id, result); + } + } + catch (const RPCError& e) + { + if (!is_notification) + { + sendError(id, e); + } + else + { + LL_WARNS("JSONRPC") << "Error in notification handler for " << method + << ": " << e.what() << LL_ENDL; + } + } + catch (const std::exception& e) + { + if (!is_notification) + { + sendError(id, InternalError(e.what())); + } + else + { + LL_WARNS("JSONRPC") << "Exception in notification handler for " << method + << ": " << e.what() << LL_ENDL; + } + } +} + +void LLJSONRPCConnection::processResponse(const LLSD& response) +{ + if (!response.has("id")) + { + LL_WARNS("JSONRPC") << "Response missing id field" << LL_ENDL; + return; + } + + std::string id = response["id"].asString(); + auto it = mPendingRequests.find(id); + if (it == mPendingRequests.end()) + { + LL_WARNS("JSONRPC") << "Received response for unknown request id: " << id << LL_ENDL; + return; + } + + ResponseCallback callback = it->second; + mPendingRequests.erase(it); + + if (callback) + { + LLSD result = response.has("result") ? response["result"] : LLSD(); + LLSD error = response.has("error") ? response["error"] : LLSD(); + + callback(result, error); + } +} + +bool LLJSONRPCConnection::validateMessage(const LLSD& message, bool is_request) +{ + // Check JSON-RPC version + if (!message.has("jsonrpc") || message["jsonrpc"].asString() != "2.0") + { + LL_WARNS("JSONRPC") << "Missing or invalid jsonrpc version" << LL_ENDL; + return false; + } + + if (is_request) + { + // Request/notification validation + if (!message.has("method")) + { + LL_WARNS("JSONRPC") << "Missing method field" << LL_ENDL; + return false; + } + + if (!message["method"].isString()) + { + LL_WARNS("JSONRPC") << "Method must be a string" << LL_ENDL; + return false; + } + + // Params are optional but must be array or object if present + if (message.has("params")) + { + if (!message["params"].isArray() && !message["params"].isMap()) + { + LL_WARNS("JSONRPC") << "Params must be array or object" << LL_ENDL; + return false; + } + } + } + else + { + // Response validation + if (!message.has("id")) + { + LL_WARNS("JSONRPC") << "Response missing id field" << LL_ENDL; + return false; + } + + // Must have either result or error, but not both + bool has_result = message.has("result"); + bool has_error = message.has("error"); + + if (!has_result && !has_error) + { + LL_WARNS("JSONRPC") << "Response must have result or error" << LL_ENDL; + return false; + } + + if (has_result && has_error) + { + LL_WARNS("JSONRPC") << "Response cannot have both result and error" << LL_ENDL; + return false; + } + + // Error must be an object with code and message + if (has_error) + { + LLSD error = message["error"]; + if (!error.isMap()) + { + LL_WARNS("JSONRPC") << "Error must be an object" << LL_ENDL; + } + if (!error.has("code") || !error.has("message")) + { + LL_WARNS("JSONRPC") << "Error must have code and message" << LL_ENDL; + } + } + } + return true; +} + +LLSD LLJSONRPCConnection::generateId() +{ + // Server-wide atomic counter for efficient unique ID generation + // Start from 1000 to avoid conflicts with any manual test IDs + static std::atomic<U64> sRequestIdCounter{1000}; + + // Generate server-unique sequential ID + U64 id = sRequestIdCounter.fetch_add(1); + return LLSD(llformat("rpc_%llu", id)); +} + +void LLJSONRPCConnection::registerMethod(const std::string& method, MethodHandler handler) +{ + mMethodHandlers[method] = handler; + LL_DEBUGS("JSONRPC") << "Registered method: " << method << LL_ENDL; +} + +void LLJSONRPCConnection::unregisterMethod(const std::string& method) +{ + mMethodHandlers.erase(method); + LL_DEBUGS("JSONRPC") << "Unregistered method: " << method << LL_ENDL; +} + +LLSD LLJSONRPCConnection::call(const std::string& method, const LLSD& params, ResponseCallback callback) +{ + LLSD request; + request["jsonrpc"] = "2.0"; + request["method"] = method; + + if (!params.isUndefined()) + { + request["params"] = params; + } + + LLSD id = generateId(); + request["id"] = id; + + // Store callback if provided + if (callback) + { + mPendingRequests[id.asString()] = callback; + } + + // Send the request + if (!sendMessage(LlsdToJson(request))) + { + // Remove from pending if send failed + if (callback) + { + mPendingRequests.erase(id.asString()); + } + LL_WARNS("JSONRPC") << "Failed to send request" << LL_ENDL; + return LLSD(); + } + + LL_DEBUGS("JSONRPC") << "Sent request: " << method << " with id: " << id.asString() << LL_ENDL; + return id; +} + +bool LLJSONRPCConnection::notify(const std::string& method, const LLSD& params) +{ + LLSD notification; + notification["jsonrpc"] = "2.0"; + notification["method"] = method; + + if (!params.isUndefined()) + { + notification["params"] = params; + } + + // Notifications don't have an id + + if (!sendMessage(LlsdToJson(notification))) + { + LL_WARNS("JSONRPC") << "Failed to send notification" << LL_ENDL; + return false; + } + + LL_DEBUGS("JSONRPC") << "Sent notification: " << method << LL_ENDL; + return true; +} + +bool LLJSONRPCConnection::sendResponse(const LLSD& id, const LLSD& result) +{ + LLSD response; + response["jsonrpc"] = "2.0"; + response["result"] = result; + response["id"] = id; + + if (!sendMessage(LlsdToJson(response))) + { + LL_WARNS("JSONRPC") << "Failed to send response for id: " << id.asString() << LL_ENDL; + return false; + } + LL_DEBUGS("JSONRPC") << "Sent response for id: " << id.asString() << LL_ENDL; + return true; +} + +bool LLJSONRPCConnection::sendError(const LLSD& id, const RPCError& error) +{ + LLSD response; + response["jsonrpc"] = "2.0"; + + LLSD error_obj; + error_obj["code"] = error.getCode(); + error_obj["message"] = error.what(); + + if (!error.getData().isUndefined()) + { + error_obj["data"] = error.getData(); + } + + response["error"] = error_obj; + response["id"] = id.isUndefined() ? LLSD() : id; // null for parse errors + + if (!sendMessage(LlsdToJson(response))) + { + LL_WARNS("JSONRPC") << "Failed to send error response" << LL_ENDL; + return false; + } + LL_DEBUGS("JSONRPC") << "Sent error response: " << error.what() << LL_ENDL; + return true; +} + +bool LLJSONRPCConnection::sendBatch(const LLSD& batch, ResponseCallback callback) +{ + if (!batch.isArray() || batch.size() == 0) + { + LL_WARNS("JSONRPC") << "Batch must be non-empty array" << LL_ENDL; + return false; + } + + // For batch requests with callbacks, we need to track multiple responses + // This is complex as we need to correlate all responses before calling callback + // For now, we'll send the batch but won't support batch response callbacks + if (callback) + { + LL_WARNS("JSONRPC") << "Batch response callbacks not yet implemented" << LL_ENDL; + } + + if (!sendMessage(LlsdToJson(batch))) + { + LL_WARNS("JSONRPC") << "Failed to send batch" << LL_ENDL; + return false; + } + + LL_DEBUGS("JSONRPC") << "Sent batch with " << batch.size() << " messages" << LL_ENDL; + return true; +} + +//======================================================================== +// LLJSONRPCServer Implementation +//======================================================================== + +LLJSONRPCServer::LLJSONRPCServer(const std::string& name, U16 port, bool local_only) + : LLWebsocketMgr::WSServer(name, port, local_only), mServerName(name) +{ + LL_INFOS("JSONRPC") << "Created JSON-RPC server: " << name + << " on port " << port << LL_ENDL; + + // Register standard JSON-RPC methods + registerGlobalMethod("system.listMethods", [this](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + LL_DEBUGS("JSONRPC") << "System method " << method << " called" << LL_ENDL; + return getMethodList(); + }); + + registerGlobalMethod("system.getStats", [this](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + LL_DEBUGS("JSONRPC") << "System method " << method << " called" << LL_ENDL; + return getServerStats(); + }); + + registerGlobalMethod("system.ping", [](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + LL_DEBUGS("JSONRPC") << "System method " << method << " called" << LL_ENDL; + LLSD result; + result["pong"] = LLDate::now().asString(); + result["params"] = params; + return result; + }); +} + +LLWebsocketMgr::WSConnection::ptr_t LLJSONRPCServer::connectionFactory(LLWebsocketMgr::WSServer::ptr_t server, + LLWebsocketMgr::connection_h handle) +{ + auto connection = std::make_shared<LLJSONRPCConnection>(server, handle); + setupConnectionMethods(connection); + return connection; +} + +void LLJSONRPCServer::onConnectionOpened(const LLWebsocketMgr::WSConnection::ptr_t& connection) +{ + LL_INFOS("JSONRPC") << "JSON-RPC client connected, total connections: " + << getConnectionCount() << LL_ENDL; +} + +void LLJSONRPCServer::onConnectionClosed(const LLWebsocketMgr::WSConnection::ptr_t& connection) +{ + LL_INFOS("JSONRPC") << "JSON-RPC client disconnected, total connections: " + << getConnectionCount() << LL_ENDL; +} + +void LLJSONRPCServer::setupConnectionMethods(LLJSONRPCConnection::ptr_t connection) +{ + LLMutexLock lock(&mGlobalMethodsMutex); + + // Register all global methods on the new connection + for (const auto& [method, handler] : mGlobalMethods) + { + connection->registerMethod(method, handler); + } +} + +void LLJSONRPCServer::registerGlobalMethod(const std::string& method, MethodHandler handler) +{ + { + LLMutexLock lock(&mGlobalMethodsMutex); + mGlobalMethods[method] = handler; + } + + // Apply to all existing connections - we need to iterate through connections + // Since mConnections is private, we need to use broadcastMessage or find another approach + // For now, we'll only apply to new connections + + LL_INFOS("JSONRPC") << "Registered global method: " << method << LL_ENDL; +} + +void LLJSONRPCServer::unregisterGlobalMethod(const std::string& method) +{ + { + LLMutexLock lock(&mGlobalMethodsMutex); + mGlobalMethods.erase(method); + } + + // For existing connections, we would need access to them + // This is a limitation of the current design - methods added after connection + // establishment won't be retroactively applied + + LL_INFOS("JSONRPC") << "Unregistered global method: " << method << LL_ENDL; +} + +LLSD LLJSONRPCServer::getMethodList() const +{ + LLMutexLock lock(&mGlobalMethodsMutex); + + LLSD methods = LLSD::emptyArray(); + for (const auto& [method, handler] : mGlobalMethods) + { + methods.append(method); + } + + return methods; +} + +void LLJSONRPCServer::broadcastNotification(const std::string& method, const LLSD& params) +{ + // Use custom broadcast logic since we need to call notify() on each JSON-RPC connection + // We can't use the base broadcastMessage() because we need structured JSON-RPC messages + + // Create the notification message + LLSD notification; + notification["jsonrpc"] = "2.0"; + notification["method"] = method; + if (!params.isUndefined()) + { + notification["params"] = params; + } + + // Use the base class broadcast functionality + broadcastMessage(boost::json::serialize(LlsdToJson(notification))); + + mTotalNotificationsSent += getConnectionCount(); + LL_DEBUGS("JSONRPC") << "Broadcast notification: " << method + << " to " << getConnectionCount() << " clients" << LL_ENDL; +} + +void LLJSONRPCServer::broadcastCall(const std::string& method, const LLSD& params, + BatchResponseCallback callback) +{ + if (callback) + { + LL_WARNS("JSONRPC") << "Broadcast call response callbacks not yet implemented" << LL_ENDL; + } + + // Create the request message with a server-unique ID + LLSD request; + request["jsonrpc"] = "2.0"; + request["method"] = method; + + // Use the same ID generation as connections for consistency + static std::atomic<U64> sBroadcastIdCounter{10000000}; // Start at 10M to clearly distinguish from regular requests + U64 id = sBroadcastIdCounter.fetch_add(1); + request["id"] = LLSD(llformat("broadcast_%llu", id)); + + if (!params.isUndefined()) + { + request["params"] = params; + } + + // Use the base class broadcast functionality + broadcastMessage(boost::json::serialize(LlsdToJson(request))); + + LL_DEBUGS("JSONRPC") << "Broadcast call: " << method + << " to " << getConnectionCount() << " clients" << LL_ENDL; +} + +LLSD LLJSONRPCServer::getServerStats() const +{ + LLSD stats; + stats["server_name"] = mServerName; + stats["connection_count"] = static_cast<S32>(getConnectionCount()); + stats["is_running"] = isRunning(); + + { + LLMutexLock lock(&mGlobalMethodsMutex); + stats["global_method_count"] = static_cast<S32>(mGlobalMethods.size()); + } + + stats["total_requests_handled"] = static_cast<LLSD::Integer>(mTotalRequestsHandled.load()); + stats["total_notifications_sent"] = static_cast<LLSD::Integer>(mTotalNotificationsSent.load()); + stats["uptime"] = LLDate::now().asString(); + + return stats; +} diff --git a/indra/llcorehttp/lljsonrpcws.h b/indra/llcorehttp/lljsonrpcws.h new file mode 100644 index 0000000000..bd9939aa33 --- /dev/null +++ b/indra/llcorehttp/lljsonrpcws.h @@ -0,0 +1,461 @@ +/** + * @file lljsonrpcws.h + * @brief JSON-RPC 2.0 WebSocket server and connection implementation + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#pragma once + +#include "llwebsocketmgr.h" +#include "llsd.h" +#include "lluuid.h" + +#include <functional> +#include <unordered_map> +#include <memory> + +/** + * @class LLJSONRPCConnection + * @brief JSON-RPC 2.0 WebSocket connection implementation + * + * This class implements the JSON-RPC 2.0 protocol over WebSocket connections. + * It handles request/response patterns, notifications, method registration, + * and error handling according to the JSON-RPC 2.0 specification. + * + * ## JSON-RPC 2.0 Protocol Features + * + * - **Requests**: Method calls that expect a response + * - **Notifications**: Method calls that do not expect a response + * - **Batch Operations**: Multiple requests/notifications in a single message + * - **Error Handling**: Standardized error codes and messages + * - **ID Correlation**: Request/response correlation using unique identifiers + * + * ## Method Handler Registration + * + * Methods use an enhanced handler signature that provides method name and request ID context: + * + * @code + * connection->registerMethod("echo", [](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + * LL_INFOS("JSONRPC") << "Method " << method << " called with ID " << id.asString() << LL_ENDL; + * return params; // Echo back the parameters + * }); + * + * connection->registerMethod("add", [](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + * if (params.isArray() && params.size() >= 2) { + * LL_INFOS("JSONRPC") << "Adding numbers via " << method << LL_ENDL; + * return params[0].asReal() + params[1].asReal(); + * } + * throw LLJSONRPCConnection::InvalidParams("Expected array with 2 numbers"); + * }); + * @endcode + * + * The enhanced signature enables: + * - Method context awareness for shared handlers + * - Request correlation and distributed tracing + * - Distinction between notifications (id undefined) and requests + * - Enhanced logging and error reporting with context + * + * ## Making RPC Calls + * + * @code + * // Asynchronous request with callback + * LLSD params; + * params.append(5); + * params.append(3); + * connection->call("add", params, [](const LLSD& result, const LLSD& error) { + * if (error.isUndefined()) { + * LL_INFOS() << "Result: " << result.asReal() << LL_ENDL; + * } else { + * LL_WARNS() << "Error: " << error["message"].asString() << LL_ENDL; + * } + * }); + * + * // Fire-and-forget notification + * connection->notify("log", LLSD("Server started")); + * @endcode + */ +class LLJSONRPCConnection : public LLWebsocketMgr::WSConnection +{ +public: + using ptr_t = std::shared_ptr<LLJSONRPCConnection>; + + /// Method handler function signature + /// @param method The method name that was called + /// @param id The request ID (undefined for notifications) + /// @param params The parameters passed to the method + /// @return The result to return to the caller + /// @throw RPCError-derived exceptions for error responses + using MethodHandler = std::function<LLSD(const std::string& method, const LLSD& id, const LLSD& params)>; + + /// Response callback function signature + /// @param result The result from a successful call (undefined if error occurred) + /// @param error The error object if call failed (undefined if successful) + using ResponseCallback = std::function<void(const LLSD& result, const LLSD& error)>; + + /** + * @brief JSON-RPC error base class + */ + class RPCError : public std::runtime_error + { + public: + // JSON-RPC 2.0 Standard Error Codes + static constexpr S32 PARSE_ERROR = -32700; ///< Invalid JSON was received by the server + static constexpr S32 INVALID_REQUEST = -32600; ///< The JSON sent is not a valid Request object + static constexpr S32 METHOD_NOT_FOUND = -32601; ///< The method does not exist / is not available + static constexpr S32 INVALID_PARAMS = -32602; ///< Invalid method parameter(s) + static constexpr S32 INTERNAL_ERROR = -32603; ///< Internal JSON-RPC error + + // Server Error Range (-32000 to -32099) + static constexpr S32 SERVER_ERROR_MIN = -32099; ///< Server error range minimum + static constexpr S32 SERVER_ERROR_MAX = -32000; ///< Server error range maximum + + // Common server-specific errors + static constexpr S32 CONNECTION_CLOSED = -32000; ///< Connection closed unexpectedly + static constexpr S32 REQUEST_TIMEOUT = -32001; ///< Request timed out + static constexpr S32 UNAUTHORIZED = -32002; ///< Authentication required + static constexpr S32 FORBIDDEN = -32003; ///< Access denied + static constexpr S32 RATE_LIMITED = -32004; ///< Too many requests + static constexpr S32 SERVICE_UNAVAILABLE = -32005; ///< Service temporarily unavailable + static constexpr S32 MESSAGE_TOO_LARGE = -32006; ///< Message exceeds maximum size + static constexpr S32 INVALID_SESSION = -32007; ///< Session expired or invalid + + RPCError(S32 code, const std::string& message, const LLSD& data = LLSD()) + : std::runtime_error(message), mCode(code), mData(data) {} + + S32 getCode() const { return mCode; } + const LLSD& getData() const { return mData; } + + protected: + S32 mCode; + LLSD mData; + }; + + /// Standard JSON-RPC error classes using named constants + class ParseError : public RPCError { + public: + ParseError(const std::string& details = "") + : RPCError(PARSE_ERROR, "Parse error" + (details.empty() ? "" : ": " + details)) {} + }; + + class InvalidRequest : public RPCError { + public: + InvalidRequest(const std::string& details = "") + : RPCError(INVALID_REQUEST, "Invalid Request" + (details.empty() ? "" : ": " + details)) {} + }; + + class MethodNotFound : public RPCError { + public: + MethodNotFound(const std::string& method = "") + : RPCError(METHOD_NOT_FOUND, "Method not found" + (method.empty() ? "" : ": " + method)) {} + }; + + class InvalidParams : public RPCError { + public: + InvalidParams(const std::string& details = "") + : RPCError(INVALID_PARAMS, "Invalid params" + (details.empty() ? "" : ": " + details)) {} + }; + + class InternalError : public RPCError { + public: + InternalError(const std::string& details = "") + : RPCError(INTERNAL_ERROR, "Internal error" + (details.empty() ? "" : ": " + details)) {} + }; + + /// Server-specific errors (in the -32000 to -32099 range) + class ConnectionClosedError : public RPCError { + public: + ConnectionClosedError(const std::string& details = "Connection closed") + : RPCError(CONNECTION_CLOSED, details) {} + }; + + class RequestTimeoutError : public RPCError { + public: + RequestTimeoutError(const std::string& details = "Request timed out") + : RPCError(REQUEST_TIMEOUT, details) {} + }; + + class UnauthorizedError : public RPCError { + public: + UnauthorizedError(const std::string& details = "Authentication required") + : RPCError(UNAUTHORIZED, details) {} + }; + + class ForbiddenError : public RPCError { + public: + ForbiddenError(const std::string& details = "Access denied") + : RPCError(FORBIDDEN, details) {} + }; + + class RateLimitedError : public RPCError { + public: + RateLimitedError(const std::string& details = "Too many requests") + : RPCError(RATE_LIMITED, details) {} + }; + + class ServiceUnavailableError : public RPCError { + public: + ServiceUnavailableError(const std::string& details = "Service temporarily unavailable") + : RPCError(SERVICE_UNAVAILABLE, details) {} + }; + + class MessageTooLargeError : public RPCError { + public: + MessageTooLargeError(const std::string& details = "Message exceeds maximum size") + : RPCError(MESSAGE_TOO_LARGE, details) {} + }; + + class InvalidSessionError : public RPCError { + public: + InvalidSessionError(const std::string& details = "Session expired or invalid") + : RPCError(INVALID_SESSION, details) {} + }; + + + LLJSONRPCConnection(const LLWebsocketMgr::WSServer::ptr_t server, + const LLWebsocketMgr::connection_h& handle) + : LLWebsocketMgr::WSConnection(server, handle) {} + + virtual ~LLJSONRPCConnection() = default; + + // WebSocket connection lifecycle + void onOpen() override; + void onClose() override; + void onMessage(const std::string& message) override; + + /** + * @brief Register a method handler + * @param method The method name to register + * @param handler The function to call when this method is invoked + */ + void registerMethod(const std::string& method, MethodHandler handler); + + /** + * @brief Unregister a method handler + * @param method The method name to unregister + */ + void unregisterMethod(const std::string& method); + + /** + * @brief Make an asynchronous JSON-RPC call + * @param method The method name to call + * @param params The parameters to pass + * @param callback Callback for the response (optional) + * @return The request ID for correlation + */ + LLSD call(const std::string& method, const LLSD& params = LLSD(), + ResponseCallback callback = nullptr); + + /** + * @brief Send a JSON-RPC notification (no response expected) + * @param method The method name + * @param params The parameters to pass + */ + bool notify(const std::string& method, const LLSD& params = LLSD()); + + /** + * @brief Send a successful response to a request + * @param id The request ID from the original request + * @param result The result to return + */ + bool sendResponse(const LLSD& id, const LLSD& result); + + /** + * @brief Send an error response to a request + * @param id The request ID from the original request (can be null) + * @param error The RPCError to send + */ + bool sendError(const LLSD& id, const RPCError& error); + + /** + * @brief Send a batch of requests/notifications + * @param batch Array of request/notification objects + * @param callback Callback for batch response (optional) + */ + bool sendBatch(const LLSD& batch, ResponseCallback callback = nullptr); + +protected: + /** + * @brief Process a single JSON-RPC message + * @param message_obj The parsed JSON message + */ + void processMessage(const LLSD& message_obj); + + /** + * @brief Process a JSON-RPC request + * @param request The request object + */ + void processRequest(const LLSD& request); + + /** + * @brief Process a JSON-RPC response + * @param response The response object + */ + void processResponse(const LLSD& response); + + /** + * @brief Validate a JSON-RPC message structure + * @param message The message to validate + * @param is_request True if validating a request, false for response + */ + bool validateMessage(const LLSD& message, bool is_request = true); + + /** + * @brief Generate the next unique request ID + * @return A server-unique request ID + * + * Generates a server-wide unique identifier using an atomic counter. + * This ensures request IDs are unique across all connections within the + * server instance, providing efficient ID generation with guaranteed uniqueness. + * + * IDs follow the format "rpc_{counter}" where counter is a monotonically + * increasing 64-bit value starting from 1. This approach provides: + * - Guaranteed uniqueness within server scope + * - High performance (atomic increment operation) + * - Predictable, sequential ordering for debugging + * - Thread-safe generation across multiple connections + */ + LLSD generateId(); + +private: + std::unordered_map<std::string, MethodHandler> mMethodHandlers; + std::unordered_map<std::string, ResponseCallback> mPendingRequests; +}; + +/** + * @class LLJSONRPCServer + * @brief JSON-RPC 2.0 WebSocket server implementation + * + * This server extends the basic WebSocket server to provide JSON-RPC 2.0 + * protocol support. It manages JSON-RPC connections and provides server-wide + * method registration and broadcasting capabilities. + * + * ## Server-Wide Method Registration + * + * Methods can be registered at the server level and will be available + * on all connections: + * + * @code + * auto server = std::make_shared<LLJSONRPCServer>("rpc_server", 8080); + * + * server->registerGlobalMethod("getServerInfo", [](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + * LL_INFOS("JSONRPC") << "Server info requested via " << method << LL_ENDL; + * LLSD info; + * info["name"] = "My RPC Server"; + * info["version"] = "1.0.0"; + * info["uptime"] = LLDate::now().secondsSinceEpoch(); + * return info; + * }); + * + * server->registerGlobalMethod("listMethods", [server](const std::string& method, const LLSD& id, const LLSD& params) -> LLSD { + * return server->getMethodList(); + * }); + * @endcode + * + * ## Broadcasting and Multi-client Operations + * + * @code + * // Broadcast notification to all connected clients + * server->broadcastNotification("serverAlert", LLSD("Server will restart in 5 minutes")); + * + * // Call a method on all clients and collect responses + * server->broadcastCall("getClientStatus", LLSD(), [](const LLSD& responses) { + * for (const auto& response : llsd::inArray(responses)) { + * LL_INFOS() << "Client status: " << response << LL_ENDL; + * } + * }); + * @endcode + */ +class LLJSONRPCServer : public LLWebsocketMgr::WSServer +{ +public: + using ptr_t = std::shared_ptr<LLJSONRPCServer>; + using MethodHandler = LLJSONRPCConnection::MethodHandler; + using ResponseCallback = LLJSONRPCConnection::ResponseCallback; + using BatchResponseCallback = std::function<void(const LLSD& responses)>; + + LLJSONRPCServer(const std::string& name, U16 port, bool local_only = true); + virtual ~LLJSONRPCServer() = default; + + // Server lifecycle callbacks + void onConnectionOpened(const LLWebsocketMgr::WSConnection::ptr_t& connection) override; + void onConnectionClosed(const LLWebsocketMgr::WSConnection::ptr_t& connection) override; + + /** + * @brief Register a global method available on all connections + * @param method The method name to register + * @param handler The function to call when this method is invoked + */ + void registerGlobalMethod(const std::string& method, MethodHandler handler); + + /** + * @brief Unregister a global method + * @param method The method name to unregister + */ + void unregisterGlobalMethod(const std::string& method); + + /** + * @brief Get list of registered global methods + * @return Array of method names + */ + LLSD getMethodList() const; + + /** + * @brief Broadcast a notification to all connected clients + * @param method The method name + * @param params The parameters to pass + */ + void broadcastNotification(const std::string& method, const LLSD& params = LLSD()); + + /** + * @brief Call a method on all connected clients + * @param method The method name + * @param params The parameters to pass + * @param callback Callback to receive aggregated responses + */ + void broadcastCall(const std::string& method, const LLSD& params = LLSD(), + BatchResponseCallback callback = nullptr); + + /** + * @brief Get server statistics + * @return Statistics object with connection count, method count, etc. + */ + LLSD getServerStats() const; + +protected: + LLWebsocketMgr::WSConnection::ptr_t connectionFactory(LLWebsocketMgr::WSServer::ptr_t server, + LLWebsocketMgr::connection_h handle) override; + + /** + * @brief Apply global method handlers to a new connection + * @param connection The connection to configure + */ + virtual void setupConnectionMethods(LLJSONRPCConnection::ptr_t connection); + +private: + std::unordered_map<std::string, MethodHandler> mGlobalMethods; + mutable LLMutex mGlobalMethodsMutex; + + std::string mServerName; // Store server name for stats + std::atomic<U64> mTotalRequestsHandled{0}; + std::atomic<U64> mTotalNotificationsSent{0}; +}; diff --git a/indra/llcorehttp/llwebsocketmgr.cpp b/indra/llcorehttp/llwebsocketmgr.cpp new file mode 100644 index 0000000000..ea87d1e07e --- /dev/null +++ b/indra/llcorehttp/llwebsocketmgr.cpp @@ -0,0 +1,674 @@ +/** + * @file llwebsocketmgr.cpp + * @brief WebSocket manager singleton implementation + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#include "linden_common.h" + +#include "llwebsocketmgr.h" +#include "llerror.h" +#include "llsdserialize.h" +#include "llhost.h" +#include "llsdjson.h" + +#include <websocketpp/config/boost_config.hpp> +#include <websocketpp/config/asio_no_tls.hpp> +#include <websocketpp/client.hpp> +#include <websocketpp/server.hpp> + +#include <thread> +#include <atomic> +#include <chrono> + +//------------------------------------------------------------------------ +namespace +{ + using Server_t = websocketpp::server<websocketpp::config::asio>; + using Client_t = websocketpp::client<websocketpp::config::asio>; + using Connection_t = websocketpp::connection<websocketpp::config::asio>; +} + +//------------------------------------------------------------------------ + +//------------------------------------------------------------------------ +// LLWebsocketMgr Implementation +// + +void LLWebsocketMgr::initSingleton() +{ } + +void LLWebsocketMgr::cleanupSingleton() +{ + stopAllServers(); +} + +void LLWebsocketMgr::update() +{ + std::vector<WSServer::ptr_t> stops; + + for (auto &[name, server] : mServers) + { + if (server && server->isRunning()) + { + if (!server->update()) + { + stops.push_back(server); + } + } + } + + for (const auto& server : stops) + { + if (server) + { + LL_DEBUGS("WebSocket") << "Stopping server: " << server->mServerName << LL_ENDL; + removeServer(server->mServerName); + } + } +} + + +LLWebsocketMgr::WSServer::ptr_t LLWebsocketMgr::findServerByName(const std::string &name) const +{ + auto it = mServers.find(std::string(name)); + if (it != mServers.end()) + { + return it->second; + } + return nullptr; +} + +bool LLWebsocketMgr::addServer(const LLWebsocketMgr::WSServer::ptr_t& server) +{ + if (!server) + { + LL_WARNS("WebSocket") << "Attempted to add a null server" << LL_ENDL; + return false; + } + + auto it = mServers.find(server->mServerName); + if (it != mServers.end()) + { + LL_WARNS("WebSocket") << "Server with name " << server->mServerName << " already exists" << LL_ENDL; + return false; + } + mServers[server->mServerName] = server; + LL_INFOS("WebSocket") << "Added WebSocket server: " << server->mServerName << LL_ENDL; + return true; +} + +bool LLWebsocketMgr::removeServer(const std::string& name) +{ + auto it = mServers.find(name); + if (it == mServers.end()) + { + LL_WARNS("WebSocket") << "No server found with name " << name << " to remove" << LL_ENDL; + return false; + } + if (it->second && it->second->isRunning()) + it->second->stop(); + mServers.erase(it); + LL_INFOS("WebSocket") << "Removed WebSocket server: " << name << LL_ENDL; + return true; +} + + +bool LLWebsocketMgr::startServer(const std::string &name) const +{ + LLWebsocketMgr::WSServer::ptr_t server = findServerByName(name); + if (!server) + { + LL_WARNS("WebSocket") << "No server found with name " << name << " to start" << LL_ENDL; + return false; + } + if (server->isRunning()) + { + LL_WARNS("WebSocket") << "Server " << name << " is already running" << LL_ENDL; + return false; + } + return server->start(); +} + +void LLWebsocketMgr::stopServer(const std::string& name) const +{ + LLWebsocketMgr::WSServer::ptr_t server = findServerByName(name); + if (!server) + { + LL_WARNS("WebSocket") << "No server found with name " << name << " to stop" << LL_ENDL; + return; + } + if (!server->isRunning()) + { + LL_WARNS("WebSocket") << "Server " << name << " is not running" << LL_ENDL; + return; + } + server->stop(); +} + +void LLWebsocketMgr::stopAllServers() +{ + for (auto &[name, server] : mServers) + { + if (server && server->isRunning()) + { + LL_INFOS("WebSocket") << "Stopping server: " << name << LL_ENDL; + server->stop(); + } + } + + mServers.clear(); +} + +//------------------------------------------------------------------------ +struct Server_impl +{ + Server_impl(LLWebsocketMgr::WSServer *owner, U16 port, bool local_only) : + mOwner(owner), + mPort(port), + mLocalOnly(local_only) + { + + mServer.set_open_handler([this](websocketpp::connection_hdl hdl) { this->onOpen(hdl); }); + mServer.set_close_handler([this](websocketpp::connection_hdl hdl) { this->onClose(hdl); }); + mServer.set_message_handler([this](websocketpp::connection_hdl hdl, Server_t::message_ptr msg) { this->onMessage(hdl, msg); }); + } + + ~Server_impl() = default; + + /** + * @brief Initialize the websocketpp server and configure listening + * + * Performs the initial setup of the websocketpp server by calling init_asio() + * to initialize the ASIO networking layer, then configures the server to listen + * on the specified port. The binding behavior depends on the mLocalOnly flag: + * - If mLocalOnly is true: binds to "127.0.0.1" (localhost only) + * - If mLocalOnly is false: binds to all available network interfaces + */ + void init() + { + mServer.init_asio(); + try { + if (mLocalOnly) + { + std::stringstream port_str; + port_str << mPort; + mServer.listen("127.0.0.1", port_str.str()); + } + else + { + mServer.listen(mPort); + } + } + catch (const websocketpp::exception& e) + { + LL_WARNS("WebSocket") << "WebSocket server listen exception: " << e.what() << LL_ENDL; + } + catch (const std::exception& e) + { + LL_WARNS("WebSocket") << "WebSocket server listen std::exception: " << e.what() << LL_ENDL; + } + catch (...) + { + LL_WARNS("WebSocket") << "WebSocket server listen unknown exception" << LL_ENDL; + } + } + + /** + * @brief Start the websocket server and begin accepting connections + * @return true if server started successfully, false on error + */ + bool start() + { + //if (!mServer.stopped()) + //{ + // LL_WARNS("WebSocket") << "WebSocket server is already running" << LL_ENDL; + // return false; + //} + + try + { + LL_INFOS("WebSocket") << "Starting WebSocket server on port " << mPort + << (mLocalOnly ? " (localhost only)" : " (all interfaces)") << LL_ENDL; + mServer.start_accept(); + + // Run controlled event loop with periodic stop flag checking + while (!mOwner->mShouldStop && !mServer.stopped()) + { + // Process events for up to 100ms, then check the stop flag + std::chrono::milliseconds timeout(100); + std::size_t handlers_run = mServer.get_io_service().run_for(timeout); + + // If no handlers were run and the server isn't stopped, + // reset the io_service for the next iteration + if (handlers_run == 0 && !mServer.stopped() && !mOwner->mShouldStop) + { + mServer.get_io_service().restart(); + } + } + + LL_INFOS("WebSocket") << "WebSocket server event loop exited cleanly" << LL_ENDL; + return true; + } + catch (const websocketpp::exception& e) + { + LL_WARNS("WebSocket") << "WebSocket server exception: " << e.what() << LL_ENDL; + return false; + } + catch (const std::exception& e) + { + LL_WARNS("WebSocket") << "WebSocket server std::exception: " << e.what() << LL_ENDL; + return false; + } + catch (...) + { + LL_WARNS("WebSocket") << "WebSocket server unknown exception" << LL_ENDL; + return false; + } + } + + void stop() + { + if (mServer.stopped()) + { + return; + } + try + { + mServer.stop_listening(); + mServer.stop(); + } + catch (const std::exception&) + { + LL_WARNS("WebSocket") << "Error stopping WebSocket server" << LL_ENDL; + } + } + + /** + * @brief Handle new connection establishment event + * @param hdl WebSocket connection handle from websocketpp + * + * Called automatically by the websocketpp library when a new client connection + * is successfully established. This method serves as a bridge between the + * low-level websocketpp callback and the high-level WSServer interface. + */ + void onOpen(websocketpp::connection_hdl hdl) const + { + LL_ERRS_IF(!mOwner, "WebSocket") << "mOwner should never be null. If it is, something is very wrong!" << LL_ENDL; + + mOwner->handleOpenConnection(hdl); + } + + /** + * @brief Handle connection closure event + * @param hdl WebSocket connection handle from websocketpp + */ + void onClose(websocketpp::connection_hdl hdl) const + { + LL_ERRS_IF(!mOwner, "WebSocket") << "mOwner should never be null" << LL_ENDL; + mOwner->handleCloseConnection(hdl); + } + + /** + * @brief Handle incoming message from client + * @param hdl WebSocket connection handle identifying the sender + * @param msg Shared pointer to the message object containing payload and metadata + * + * Called automatically by the websocketpp library when a complete message is + * received from a client. This method validates the connection exists, extracts + * the message payload, and forwards it to the appropriate connection handler. + * + * Currently handles text messages only. + */ + void onMessage(websocketpp::connection_hdl hdl, Server_t::message_ptr msg) const + { + LL_ERRS_IF(!mOwner, "WebSocket") << "mOwner should never be null" << LL_ENDL; + LLWebsocketMgr::WSConnection::ptr_t connection = mOwner->getConnection(hdl); + if (!connection) + { + LL_WARNS("WebSocket") << "Received message for unknown connection" << LL_ENDL; + return; + } + + // TODO: check the FIN bit and handle fragmented messages if needed + // TODO: check terminal and close codes and handle connection closure if needed + mOwner->handleMessage(hdl, msg->get_payload()); + } + + //------------------------------------------- + Server_t mServer; ///< The underlying websocketpp server instance + LLWebsocketMgr::WSServer* mOwner{ nullptr }; ///< Back-reference to the owning WSServer instance (guaranteed non-null) + U16 mPort{ 0 }; ///< TCP port number the server listens on + bool mLocalOnly{ true }; ///< Whether to bind to localhost only (true) or all interfaces (false) +}; + +//------------------------------------------------------------------------ +LLWebsocketMgr::WSServer::WSServer(std::string_view name, U16 port, bool local_only): + mServerName(name), + mImpl(std::make_unique<Server_impl>(this, port, local_only)) +{ + mImpl->init(); + + // Initialize the server with the given name and host + LL_INFOS("WebSocket") << "Creating WebSocket server: " << name << + " listening " << (mImpl->mLocalOnly ? "locally" : "ON ALL INTERFACES") << + " on port " << mImpl->mPort << LL_ENDL; +} + +LLWebsocketMgr::WSServer::~WSServer() +{ + // Ensure the server is stopped before destruction + stop(); +} + +LLWebsocketMgr::WSConnection::ptr_t LLWebsocketMgr::WSServer::connectionFactory(LLWebsocketMgr::WSServer::ptr_t server, + LLWebsocketMgr::connection_h handle) +{ + return std::make_shared<LLWebsocketMgr::WSConnection>(server, handle); +} + +bool LLWebsocketMgr::WSServer::start() +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + + LLMutexLock lock(&mThreadMutex); + + // Check if already running + if (isRunning()) + { + LL_WARNS("WebSocket") << "Server " << mServerName << " is already running" << LL_ENDL; + return false; + } + + // Reset the stop flag + mShouldStop = false; + + // Start the server thread + mServerThread = std::thread([this]() { + LL_INFOS("WebSocket") << "WebSocket server thread starting for: " << mServerName << LL_ENDL; + + // Run the controlled server loop that checks the stop flag + // Server_impl accesses mShouldStop through the mOwner pointer + bool success = mImpl->start(); + + if (!success) + { + LL_WARNS("WebSocket") << "WebSocket server thread failed to start for: " << mServerName << LL_ENDL; + } + + LL_INFOS("WebSocket") << "WebSocket server thread exiting for: " << mServerName << LL_ENDL; + }); + + onStarted(); + LL_INFOS("WebSocket") << "Started WebSocket server thread: " << mServerName << LL_ENDL; + return true; +} + +void LLWebsocketMgr::WSServer::stop() +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + + { + LLMutexLock lock(&mThreadMutex); + + // Check if already stopped + if (!isRunning()) + { + return; + } + + LL_INFOS("WebSocket") << "Stopping WebSocket server: " << mServerName << LL_ENDL; + + mShouldStop = true; + + // Stop the websocket server (this will cause the controlled run loop to exit) + mImpl->stop(); + } // Release the lock here + + if (mServerThread.joinable()) + { + mServerThread.join(); + LL_INFOS("WebSocket") << "WebSocket server thread joined for: " << mServerName << LL_ENDL; + } + onStopped(); +} + +bool LLWebsocketMgr::WSServer::isRunning() const +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + + // Check both the thread state, websocket server state, and the stop flag + return mServerThread.joinable() && !mImpl->mServer.stopped() && !mShouldStop; +} + +void LLWebsocketMgr::WSServer::broadcastMessage(const std::string& message) +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + LLMutexLock lock(&mConnectionMutex); + for (const auto& [handle, conn] : mConnections) + { + sendMessageTo(handle, message); + } +} + +bool LLWebsocketMgr::WSServer::sendMessageTo(const connection_h& handle, const std::string& message) +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + websocketpp::lib::error_code ec; + mImpl->mServer.send(handle, message, websocketpp::frame::opcode::text, ec); + if (ec) + { + LL_WARNS("WebSocket") << mServerName << " failed to send message: " << ec.message() << LL_ENDL; + return false; + } + return true; +} + +bool LLWebsocketMgr::WSServer::closeConnection(const connection_h& handle, U16 code, const std::string& reason) +{ + LL_ERRS_IF(!mImpl, "WebSocket") << "WebSocket server " << mServerName << " implementation is null !" << LL_ENDL; + + try + { + websocketpp::lib::error_code ec; + mImpl->mServer.close(handle, code, reason, ec); + if (ec) + { + LL_WARNS("WebSocket") << mServerName << " failed to close connection: " << ec.message() << LL_ENDL; + return false; + } + + LL_INFOS("WebSocket") << mServerName << " initiated close for connection with code " + << code << " and reason: " << reason << LL_ENDL; + return true; + } + catch (const websocketpp::exception& e) + { + LL_WARNS("WebSocket") << mServerName << " exception closing connection: " << e.what() << LL_ENDL; + return false; + } + catch (const std::exception& e) + { + LL_WARNS("WebSocket") << mServerName << " std::exception closing connection: " << e.what() << LL_ENDL; + return false; + } + catch (...) + { + LL_WARNS("WebSocket") << mServerName << " unknown exception closing connection" << LL_ENDL; + return false; + } +} + +LLWebsocketMgr::WSConnection::ptr_t LLWebsocketMgr::WSServer::getConnection(const connection_h& handle) +{ + LLMutexLock lock(&mConnectionMutex); + auto it = mConnections.find(handle); + if (it != mConnections.end()) + { + return it->second; + } + return nullptr; +} + +LLWebsocketMgr::connection_state_t LLWebsocketMgr::WSServer::getConnectionState(const connection_h& handle) const +{ + websocketpp::lib::error_code ec; + auto con = mImpl->mServer.get_con_from_hdl(handle, ec); + if (ec) + { + LL_WARNS("WebSocket") << mServerName << " failed to get connection state: " << ec.message() << LL_ENDL; + websocketpp::session::state::value state = websocketpp::session::state::closed; + return connection_closed; + } + return static_cast<connection_state_t>(con->get_state()); +} + + +void LLWebsocketMgr::WSServer::handleOpenConnection(const connection_h& handle) +{ + WSConnection::ptr_t connection; + size_t size(0); + { + LLMutexLock lock(&mConnectionMutex); + auto it = mConnections.find(handle); + if (it == mConnections.end()) + { + connection = connectionFactory(shared_from_this(), handle); + if (!connection) + { + LL_WARNS("WebSocket") << "Failed to create connection for websocket server " << mServerName << LL_ENDL; + return; + } + mConnections[handle] = connection; + } + else + { + connection = it->second; + } + + if (!connection) + { + LL_WARNS("WebSocket") << mServerName << " failed to create connection object" << LL_ENDL; + return; + } + // Removed redundant assignment to mConnections[handle] + size = mConnections.size(); + } + + onConnectionOpened(connection); // TODO: consider letting the server reject the connection here + connection->onOpen(); + LL_INFOS("WebSocket") << mServerName << " opened new connection, total connections: " << size << LL_ENDL; +} + +void LLWebsocketMgr::WSServer::handleCloseConnection(const connection_h& handle) +{ + size_t size(0); + WSConnection::ptr_t connection; + { + LLMutexLock lock(&mConnectionMutex); + auto it = mConnections.find(handle); + if (it != mConnections.end()) + { + connection = it->second; + mConnections.erase(it); + } + size = mConnections.size(); + } + if (connection) + { + connection->onClose(); + onConnectionClosed(connection); + LL_INFOS("WebSocket") << mServerName << " closed connection, total connections: " << size << LL_ENDL; + } + else + { + LL_WARNS("WebSocket") << mServerName << " attempted to close unknown connection" << LL_ENDL; + } +} + +void LLWebsocketMgr::WSServer::handleMessage(const connection_h& handle, const std::string& message) +{ + WSConnection::ptr_t connection = getConnection(handle); + if (connection) + { + connection->onMessage(message); + } + else + { + LL_WARNS("WebSocket") << mServerName << " received message for unknown connection" << LL_ENDL; + } +} + +//------------------------------------------------------------------------ +bool LLWebsocketMgr::WSConnection::sendMessage(const std::string& message) const +{ + if (mOwningServer.expired()) + { + LL_WARNS("WebSocket") << "Attempted to send message on connection with null server reference" << LL_ENDL; + return false; + } + return mOwningServer.lock()->sendMessageTo(mConnectionHandle, message); +} + +bool LLWebsocketMgr::WSConnection::sendMessage(const boost::json::value& json) const +{ + std::string message = boost::json::serialize(json); + return sendMessage(message); +} + +bool LLWebsocketMgr::WSConnection::sendMessage(const LLSD& data) const +{ + return sendMessage(LlsdToJson(data)); +} + +void LLWebsocketMgr::WSConnection::closeConnection(U16 code, const std::string& reason) +{ + if (mOwningServer.expired()) + { + LL_WARNS("WebSocket") << "Attempted to close connection with null server reference" << LL_ENDL; + return; + } + + LL_INFOS("WebSocket") << "WSConnection closing connection with code " << code + << " and reason: " << (reason.empty() ? "(no reason)" : reason) << LL_ENDL; + + if (!mOwningServer.lock()->closeConnection(mConnectionHandle, code, reason)) + { + LL_WARNS("WebSocket") << "Failed to close connection through server" << LL_ENDL; + } +} + +bool LLWebsocketMgr::WSConnection::isConnected() const +{ + if (mOwningServer.expired()) + { + return false; + } + + LLWebsocketMgr::WSServer::ptr_t server = mOwningServer.lock(); + if (!server) + { + return false; + } + return server->getConnectionState(mConnectionHandle) == connection_open; +} diff --git a/indra/llcorehttp/llwebsocketmgr.h b/indra/llcorehttp/llwebsocketmgr.h new file mode 100644 index 0000000000..4165b3cecc --- /dev/null +++ b/indra/llcorehttp/llwebsocketmgr.h @@ -0,0 +1,305 @@ +/** + * @file llwebsocketmgr.h + * @brief WebSocket manager singleton for managing WebSocket servers and connections + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#pragma once + +#include "llsingleton.h" +#include "llsd.h" +#include "lluuid.h" +#include "llhost.h" +#include "llmutex.h" + +#include <memory> +#include <map> +#include <vector> +#include <functional> +#include <thread> +#include <atomic> + +#include <boost/json.hpp> + +#include <websocketpp/common/connection_hdl.hpp> + +struct Server_impl; + +/** + * @class LLWebsocketMgr + * @brief Singleton manager for WebSocket connections and servers + * + * This class provides a high-level interface for managing WebSocket connections + * and servers using websocketpp library. It handles both client and server + * connections, provides thread-safe operations, and integrates with the + * existing Linden Lab infrastructure. + */ +class LLWebsocketMgr: public LLSingleton<LLWebsocketMgr> +{ + LLSINGLETON(LLWebsocketMgr) = default; + virtual ~LLWebsocketMgr() = default; + LOG_CLASS(LLWebsocketMgr); + +public: + using connection_h = websocketpp::connection_hdl; + class WSServer; + + enum connection_state_t + { // must map to websocketpp::session::state + connection_connecting = 0, + connection_open = 1, + connection_closing = 2, + connection_closed = 3 + }; + + class WSConnection + { + friend class LLWebsocketMgr; + + public: + using ptr_t = std::shared_ptr<WSConnection>; + + /** + * @brief Constructor for WSConnection + * @param server Shared pointer to the parent WSServer + * @param handle WebSocket connection handle from websocketpp + */ + WSConnection(const std::shared_ptr<WSServer> &server, const connection_h& handle): + mConnectionHandle(handle), + mOwningServer(server) + {} + + virtual ~WSConnection() = default; + + /** + * Override this method in derived classes to handle connection establishment. + * This is called after the WebSocket handshake is complete and the connection + * is ready to send/receive messages. + */ + virtual void onOpen() {} + + /** + * Override this method in derived classes to handle connection closure. + * This is called when the connection has been terminated, either normally + * or due to an error condition. + */ + virtual void onClose() {} + + /** + * @brief Called when a message is received + * @param message The received message as a string + * + * Override this method in derived classes to handle incoming messages. + * Currently only text messages are supported. + */ + virtual void onMessage(const std::string& message) {} + + /** + * @brief Send a message to the connected client + * @param message The message string to send + * @return true if the message was queued successfully, false on error + * + * Sends a text message to the remote endpoint. The message is queued + * asynchronously and may not be sent immediately. + */ + bool sendMessage(const std::string& message) const; + bool sendMessage(const boost::json::value& json) const; + bool sendMessage(const LLSD& data) const; + + /** + * @brief Close the WebSocket connection gracefully + * @param code Optional close code (default: normal closure) + * @param reason Optional reason string (default: empty) + * + * Initiates a graceful WebSocket close handshake. The connection will + * send a close frame with the specified code and reason, then wait for + * the remote endpoint to respond with its own close frame before + * actually closing the underlying TCP connection. + * + * Common close codes: + * - 1000: Normal closure (default) + * - 1001: Going away (server shutting down, page navigating away) + * - 1002: Protocol error + * - 1003: Unsupported data type + * - 1008: Policy violation + * - 1009: Message too big + * + * @note After calling this method, no further messages should be sent + * @note The onClose() callback will be invoked when the close handshake completes + */ + void closeConnection(U16 code = 1000, const std::string& reason = std::string()); + + bool isConnected() const; + + protected: + connection_h mConnectionHandle; + std::weak_ptr<WSServer> mOwningServer; // Back-reference to the server this connection belongs to + }; + + /** + * @class WSServer + * @brief Base class for WebSocket servers with customizable connection handling + * + * WSServer provides a high-level abstraction over websocketpp servers, handling + * threading, connection management, and event dispatching. Derive from this class + * to create custom WebSocket servers with application-specific logic. + * + * ## Basic Usage + * + * @code + * class MyServer : public LLWebsocketMgr::WSServer + * { + * public: + * MyServer(const std::string& name, U16 port) + * : WSServer(name, port, false) // Listen on all interfaces + * {} + * + * void onConnectionOpened(const WSConnection::ptr_t& connection) override + * { + * LL_INFOS("MyServer") << "New client connected" << LL_ENDL; + * // Send welcome message + * connection->sendMessage("Welcome to the server!"); + * } + * + * void onConnectionClosed(const WSConnection::ptr_t& connection) override + * { + * LL_INFOS("MyServer") << "Client disconnected" << LL_ENDL; + * } + * + * protected: + * // Use custom connection class + * WSConnection::ptr_t connectionFactory(WSServer::ptr_t server, connection_h handle) override + * { + * return std::make_shared<MyConnection>(server, handle); + * } + * }; + * @endcode + * + * ## Connection Management + * + * The server automatically manages connection lifetimes and provides several ways + * to interact with connections: + * + * - `broadcastMessage()` - Send message to all connected clients + * - `sendMessageTo()` - Send message to specific connection + * - `closeConnection()` - Close specific connection with code/reason + * - `getConnection()` - Get connection object by handle + * + * ## Thread Safety + * + * All public methods are thread-safe and can be called from any thread. The server + * runs its own background thread for handling WebSocket events, while connection + * callbacks are also executed on this background thread. + */ + class WSServer: public std::enable_shared_from_this<WSServer> + { + friend struct Server_impl; + friend class WSConnection; + friend class LLWebsocketMgr; + + public: + using ptr_t = std::shared_ptr<WSServer>; + + WSServer(std::string_view name, U16 port, bool local_only = true); + virtual ~WSServer(); + + virtual void onStarted() {} + virtual void onStopped() {} + + virtual void onConnectionOpened(const WSConnection::ptr_t& connection) { } + virtual void onConnectionClosed(const WSConnection::ptr_t& connection) { } + + bool isRunning() const; + size_t getConnectionCount() const + { + LLMutexLock lock(&mConnectionMutex); + return mConnections.size(); + } + + void broadcastMessage(const std::string& message); + virtual bool update() { return true; } + + connection_state_t getConnectionState(const connection_h& handle) const; + + protected: + virtual WSConnection::ptr_t connectionFactory(WSServer::ptr_t server, connection_h handle); + + bool start(); + void stop(); + + bool sendMessageTo(const connection_h& handle, const std::string& message); + + /** + * @brief Close a specific connection gracefully + * @param handle The connection handle to close + * @param code Close code (default: normal closure) + * @param reason Close reason string (default: empty) + * @return true if close was initiated successfully, false on error + * + * Internal method used by WSConnection to close individual connections. + * This method is thread-safe and can be called from any thread. + */ + bool closeConnection(const connection_h& handle, U16 code = 1000, const std::string& reason = std::string()); + + private: + using connection_map_t = std::map<connection_h, WSConnection::ptr_t, std::owner_less<connection_h> >; + + WSConnection::ptr_t getConnection(const connection_h& handle); + + void handleOpenConnection(const connection_h& handle); + void handleCloseConnection(const connection_h& handle); + void handleMessage(const connection_h& handle, const std::string& message); + + std::string mServerName; + std::unique_ptr<Server_impl> mImpl; + connection_map_t mConnections; + mutable LLMutex mConnectionMutex; + + // Threading support + std::thread mServerThread; ///< Thread running the ASIO event loop + std::atomic<bool> mShouldStop{ false }; ///< Thread-safe stop flag + mutable LLMutex mThreadMutex; ///< Mutex for thread synchronization + }; + + // Server and Connection Management + WSServer::ptr_t findServerByName(const std::string &name) const; + + bool addServer(const WSServer::ptr_t& server); + bool removeServer(const std::string &name); + + bool startServer(const std::string &name) const; + void stopServer(const std::string &name) const; + + void update(); + +protected: + void initSingleton() override; + void cleanupSingleton() override; + +private: + using server_map_t = std::map<std::string, WSServer::ptr_t>; + + void stopAllServers(); + + server_map_t mServers; +}; diff --git a/indra/llinventory/llinventory.cpp b/indra/llinventory/llinventory.cpp index f126accfb8..1fcf70dc25 100644 --- a/indra/llinventory/llinventory.cpp +++ b/indra/llinventory/llinventory.cpp @@ -61,6 +61,8 @@ static const std::string INV_SALE_INFO_LABEL("sale_info"); static const std::string INV_FLAGS_LABEL("flags"); static const std::string INV_CREATION_DATE_LABEL("created_at"); static const std::string INV_TOGGLED_LABEL("toggled"); +static const std::string INV_SCRIPT_LABEL("script"); +static const std::string INV_RUNTIME_LABEL("runtime"); // key used by agent-inventory-service static const std::string INV_ASSET_TYPE_LABEL_WS("type_default"); @@ -109,6 +111,7 @@ void LLInventoryObject::copyObject(const LLInventoryObject* other) mName = other->mName; mThumbnailUUID = other->mThumbnailUUID; mFavorite = other->mFavorite; + mRuntime = other->mRuntime; } const LLUUID& LLInventoryObject::getUUID() const @@ -131,6 +134,11 @@ bool LLInventoryObject::getIsFavorite() const return mFavorite; } +const std::string& LLInventoryObject::getRuntime() const +{ + return mRuntime; +} + const std::string& LLInventoryObject::getName() const { return mName; @@ -190,9 +198,23 @@ void LLInventoryObject::setFavorite(bool favorite) mFavorite = favorite; } +void LLInventoryObject::setRuntime(std::string_view runtime) +{ + // Store the runtime unconditionally; it will be validated/cleared + // when the final asset type is known (see setType()). + mRuntime = runtime; +} + void LLInventoryObject::setType(LLAssetType::EType type) { mType = type; + + // Only LSL text assets are expected to have a runtime; clear any + // previously stored runtime for other asset types. + if (mType != LLAssetType::AT_LSL_TEXT) + { + mRuntime.clear(); + } } @@ -279,6 +301,15 @@ bool LLInventoryObject::importLegacyStream(std::istream& input_stream) { setFavorite(false); } + + if (metadata.has("script") && metadata["script"].has("runtime")) + { + setRuntime(metadata["script"]["runtime"].asString()); + } + else + { + setRuntime(std::string()); + } } else if(0 == strcmp("name", keyword)) { @@ -421,6 +452,7 @@ void LLInventoryItem::copyItem(const LLInventoryItem* other) mInventoryType = other->mInventoryType; mFlags = other->mFlags; mCreationDate = other->mCreationDate; + mRuntime = other->mRuntime; } // If this is a linked item, then the UUID of the base object is @@ -784,6 +816,16 @@ bool LLInventoryItem::importLegacyStream(std::istream& input_stream) { setFavorite(false); } + + if (metadata.has("script") && metadata["script"].has("runtime")) + { + setRuntime(metadata["script"]["runtime"].asString()); + } + else + { + setRuntime(std::string()); + } + } else if(0 == strcmp("inv_type", keyword)) { @@ -949,6 +991,11 @@ void LLInventoryItem::asLLSD( LLSD& sd ) const sd[INV_FAVORITE_LABEL] = LLSD().with(INV_TOGGLED_LABEL, mFavorite); } + if (!mRuntime.empty()) + { + sd[INV_SCRIPT_LABEL] = LLSD().with(INV_RUNTIME_LABEL, mRuntime); + } + U32 mask = mPermissions.getMaskBase(); if(((mask & PERM_ITEM_UNRESTRICTED) == PERM_ITEM_UNRESTRICTED) || (mAssetUUID.isNull())) @@ -1050,6 +1097,23 @@ bool LLInventoryItem::fromLLSD(const LLSD& sd, bool is_new) continue; } + if (i->first == INV_SCRIPT_LABEL) + { + const LLSD& script_map = i->second; + const std::string w = INV_RUNTIME_LABEL; + if (script_map.has(w)) + { + mRuntime = script_map[w].asString(); + } + else + { + // Clear any stale runtime when a script block is present + // but no explicit runtime value is provided. + mRuntime.clear(); + } + continue; + } + if (i->first == INV_PERMISSIONS_LABEL) { mPermissions.importLLSD(i->second); @@ -1469,6 +1533,8 @@ bool LLInventoryCategory::importLegacyStream(std::istream& input_stream) { setFavorite(false); } + setRuntime(std::string()); + } else { diff --git a/indra/llinventory/llinventory.h b/indra/llinventory/llinventory.h index 181c46226c..c22b17ab66 100644 --- a/indra/llinventory/llinventory.h +++ b/indra/llinventory/llinventory.h @@ -24,11 +24,11 @@ * $/LicenseInfo$ */ -#ifndef LL_LLINVENTORY_H -#define LL_LLINVENTORY_H +#pragma once #include "llfoldertype.h" #include "llinventorytype.h" +#include "llinventorydefines.h" #include "llpermissions.h" #include "llrefcount.h" #include "llsaleinfo.h" @@ -72,6 +72,7 @@ public: const LLUUID& getParentUUID() const; virtual const LLUUID& getThumbnailUUID() const; virtual bool getIsFavorite() const; + virtual const std::string& getRuntime() const; virtual const std::string& getName() const; virtual LLAssetType::EType getType() const; LLAssetType::EType getActualType() const; // bypasses indirection for linked items @@ -88,6 +89,7 @@ public: void setParent(const LLUUID& new_parent); virtual void setThumbnailUUID(const LLUUID& thumbnail_uuid); virtual void setFavorite(bool favorite); + virtual void setRuntime(std::string_view runtime); void setType(LLAssetType::EType type); virtual void setCreationDate(time_t creation_date_utc); // only stored for items @@ -114,6 +116,7 @@ protected: LLUUID mParentUUID; // Parent category. Root categories have LLUUID::NULL. LLUUID mThumbnailUUID; bool mFavorite; + std::string mRuntime; LLAssetType::EType mType; std::string mName; time_t mCreationDate; // seconds from 1/1/1970, UTC @@ -166,6 +169,7 @@ public: virtual const std::string& getActualDescription() const; // Does not follow links virtual const LLSaleInfo& getSaleInfo() const; virtual LLInventoryType::EType getInventoryType() const; + virtual U8 getInventorySubType() const { return getFlags() & LLInventoryItemFlags::II_FLAGS_SUBTYPE_MASK; } virtual U32 getFlags() const; virtual time_t getCreationDate() const; virtual U32 getCRC32() const; // really more of a checksum. @@ -182,6 +186,7 @@ public: void setSaleInfo(const LLSaleInfo& sale_info); void setPermissions(const LLPermissions& perm); void setInventoryType(LLInventoryType::EType inv_type); + void setInventorySubType(U8 sub_type) { setFlags((getFlags() & ~LLInventoryItemFlags::II_FLAGS_SUBTYPE_MASK) | (sub_type & LLInventoryItemFlags::II_FLAGS_SUBTYPE_MASK)); } void setFlags(U32 flags); void setCreator(const LLUUID& creator); // only used for calling cards @@ -294,5 +299,3 @@ protected: LLSD ll_create_sd_from_inventory_item(LLPointer<LLInventoryItem> item); LLSD ll_create_sd_from_inventory_category(LLPointer<LLInventoryCategory> cat); LLPointer<LLInventoryCategory> ll_create_category_from_sd(const LLSD& sd_cat); - -#endif // LL_LLINVENTORY_H diff --git a/indra/llinventory/llinventorydefines.h b/indra/llinventory/llinventorydefines.h index 8e7bd87ac4..9088d172d9 100644 --- a/indra/llinventory/llinventorydefines.h +++ b/indra/llinventory/llinventorydefines.h @@ -24,8 +24,7 @@ * $/LicenseInfo$ */ -#ifndef LL_LLINVENTORYDEFINES_H -#define LL_LLINVENTORYDEFINES_H +#pragma once // Consts for "key" field in the task inventory update message extern const U8 TASK_INVENTORY_ITEM_KEY; @@ -97,5 +96,3 @@ public: // on a pre-existing inventory item (DEV-28098 and DEV-30997) }; }; - -#endif // LL_LLINVENTORYDEFINES_H diff --git a/indra/llinventory/llinventorytype.h b/indra/llinventory/llinventorytype.h index c90f8aa107..0627b8df3c 100644 --- a/indra/llinventory/llinventorytype.h +++ b/indra/llinventory/llinventorytype.h @@ -150,6 +150,13 @@ private: ~LLInventoryType( void ); }; +// Subtypes for scripts, (inventory type IT_LSL). +enum ScriptSubtype_t +{ + SST_LSL = 0, + SST_LUA = 1 +}; + // helper function that returns true if inventory type and asset type // are potentially compatible. For example, an attachment must be an // object, but a wearable can be a bodypart or clothing asset. diff --git a/indra/llmessage/message_prehash.cpp b/indra/llmessage/message_prehash.cpp index 21dbf35783..f42cbfdac7 100644 --- a/indra/llmessage/message_prehash.cpp +++ b/indra/llmessage/message_prehash.cpp @@ -714,6 +714,9 @@ char const* const _PREHASH_FirstName = LLMessageStringTable::getInstance()->getS char const* const _PREHASH_AttachedSoundGainChange = LLMessageStringTable::getInstance()->getString("AttachedSoundGainChange"); char const* const _PREHASH_LocationID = LLMessageStringTable::getInstance()->getString("LocationID"); char const* const _PREHASH_Running = LLMessageStringTable::getInstance()->getString("Running"); +char const* const _PREHASH_Mono = LLMessageStringTable::getInstance()->getString("Mono"); +char const* const _PREHASH_Luau = LLMessageStringTable::getInstance()->getString("Luau"); +char const* const _PREHASH_LuauLanguage = LLMessageStringTable::getInstance()->getString("LuauLanguage"); char const* const _PREHASH_AgentThrottle = LLMessageStringTable::getInstance()->getString("AgentThrottle"); char const* const _PREHASH_NeighborList = LLMessageStringTable::getInstance()->getString("NeighborList"); char const* const _PREHASH_PathTaperX = LLMessageStringTable::getInstance()->getString("PathTaperX"); diff --git a/indra/llmessage/message_prehash.h b/indra/llmessage/message_prehash.h index 8a2ad1587c..53f8123b35 100644 --- a/indra/llmessage/message_prehash.h +++ b/indra/llmessage/message_prehash.h @@ -714,6 +714,9 @@ extern char const* const _PREHASH_FirstName; extern char const* const _PREHASH_AttachedSoundGainChange; extern char const* const _PREHASH_LocationID; extern char const* const _PREHASH_Running; +extern char const* const _PREHASH_Mono; +extern char const* const _PREHASH_Luau; +extern char const* const _PREHASH_LuauLanguage; extern char const* const _PREHASH_AgentThrottle; extern char const* const _PREHASH_NeighborList; extern char const* const _PREHASH_PathTaperX; diff --git a/indra/llui/llcombobox.cpp b/indra/llui/llcombobox.cpp index ae676251ff..ad6ab9dc4c 100644 --- a/indra/llui/llcombobox.cpp +++ b/indra/llui/llcombobox.cpp @@ -251,11 +251,26 @@ void LLComboBox::resetDirty() } } -bool LLComboBox::itemExists(const std::string& name) +bool LLComboBox::itemExists(const std::string& name) const { return mList->getItemByLabel(name); } +bool LLComboBox::valueExists(const std::string& value) const +{ + return mList->getItemByValue(value); +} + +LLScrollListItem* LLComboBox::findItemByValue(const std::string& value) const +{ + return mList->getItemByValue(value); +} + +std::vector<LLScrollListItem*> LLComboBox::getAllData() const +{ + return mList->getAllData(); +} + // add item "name" to menu LLScrollListItem* LLComboBox::add(const std::string& name, EAddPosition pos, bool enabled) { diff --git a/indra/llui/llcombobox.h b/indra/llui/llcombobox.h index d6ea1202d3..52a2165f1b 100644 --- a/indra/llui/llcombobox.h +++ b/indra/llui/llcombobox.h @@ -142,7 +142,10 @@ public: LLScrollListItem* addSeparator(EAddPosition pos = ADD_BOTTOM); bool remove( S32 index ); // remove item by index, return true if found and removed void removeall() { clearRows(); } - bool itemExists(const std::string& name); + bool itemExists(const std::string& name) const; + bool valueExists(const std::string& value) const; + LLScrollListItem* findItemByValue(const std::string& value) const; + std::vector<LLScrollListItem*> getAllData() const; void sortByName(bool ascending = true); // Sort the entries in the combobox by name diff --git a/indra/llui/llkeywords.cpp b/indra/llui/llkeywords.cpp index 2bea8fb4ed..b1f1fb77f3 100644 --- a/indra/llui/llkeywords.cpp +++ b/indra/llui/llkeywords.cpp @@ -33,38 +33,20 @@ #include "llsdserialize.h" #include "lltexteditor.h" #include "llstl.h" +#include "llcontrol.h" + +extern LLControlGroup gSavedSettings; inline bool LLKeywordToken::isHead(const llwchar* s) const { - // strncmp is much faster than string compare - bool res = true; - const llwchar* t = mToken.c_str(); - auto len = mToken.size(); - for (S32 i=0; i<len; i++) - { - if (s[i] != t[i]) - { - res = false; - break; - } - } - return res; + size_t bytes = mToken.size() * sizeof(llwchar); + return std::memcmp(s, mToken.c_str(), bytes) == 0; } inline bool LLKeywordToken::isTail(const llwchar* s) const { - bool res = true; - const llwchar* t = mDelimiter.c_str(); - auto len = mDelimiter.size(); - for (S32 i=0; i<len; i++) - { - if (s[i] != t[i]) - { - res = false; - break; - } - } - return res; + size_t len_bytes = mDelimiter.size() * sizeof(llwchar); + return std::memcmp(s, mDelimiter.c_str(), len_bytes) == 0; } LLKeywords::LLKeywords() @@ -80,6 +62,8 @@ LLKeywords::~LLKeywords() mLineTokenList.clear(); std::for_each(mDelimiterTokenList.begin(), mDelimiterTokenList.end(), DeletePointer()); mDelimiterTokenList.clear(); + mLineTokenByFirstChar.clear(); + mDelimiterTokenByFirstChar.clear(); } // Add the token as described @@ -114,14 +98,29 @@ void LLKeywords::addToken(LLKeywordToken::ETokenType type, break; case LLKeywordToken::TT_LINE: - mLineTokenList.push_front(new LLKeywordToken(type, color, key, tool_tip, LLWStringUtil::null)); + { + LLKeywordToken* token = new LLKeywordToken(type, color, key, tool_tip, LLWStringUtil::null); + mLineTokenList.push_front(token); + if (!key.empty()) + { + mLineTokenByFirstChar[key[0]].push_front(token); + } break; + } case LLKeywordToken::TT_TWO_SIDED_DELIMITER: case LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS: case LLKeywordToken::TT_ONE_SIDED_DELIMITER: - mDelimiterTokenList.push_front(new LLKeywordToken(type, color, key, tool_tip, delimiter)); + case LLKeywordToken::TT_LONG_BRACKET: + { + LLKeywordToken* token = new LLKeywordToken(type, color, key, tool_tip, delimiter); + mDelimiterTokenList.push_front(token); + if (!key.empty()) + { + mDelimiterTokenByFirstChar[key[0]].push_front(token); + } break; + } default: llassert(0); @@ -219,9 +218,10 @@ LLUIColor LLKeywords::getColorGroup(std::string_view key_in) const return LLUIColorTable::instance().getColor(color_group); } -void LLKeywords::initialize(LLSD SyntaxXML) +void LLKeywords::initialize(LLSD SyntaxXML, bool luau_language) { mSyntax = SyntaxXML; + mLuauLanguage = luau_language; mLoaded = true; } @@ -234,13 +234,30 @@ void LLKeywords::processTokens() // Add 'standard' stuff: Quotes, Comments, Strings, Labels, etc. before processing the LLSD std::string delimiter; - addToken(LLKeywordToken::TT_LABEL, "@", getColorGroup("misc-flow-label"), "Label\nTarget for jump statement", delimiter ); - addToken(LLKeywordToken::TT_ONE_SIDED_DELIMITER, "//", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (single-line)\nNon-functional commentary or disabled code", delimiter ); - addToken(LLKeywordToken::TT_TWO_SIDED_DELIMITER, "/*", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (multi-line)\nNon-functional commentary or disabled code", "*/" ); - addToken(LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS, "\"", LLUIColorTable::instance().getColor("SyntaxLslStringLiteral"), "String literal", "\"" ); + addToken(LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS, "\"", LLUIColorTable::instance().getColor("SyntaxLslStringLiteral"), "String literal", "\""); + + if (mLuauLanguage) + { + addToken(LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS, "\'", LLUIColorTable::instance().getColor("SyntaxLslStringLiteral"), "String literal", "\'"); + // TODO: Might be nice to add a special case for this so we can still highlight expressions in `{}`s + addToken(LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS, "`", LLUIColorTable::instance().getColor("SyntaxLslStringLiteral"), "String literal", "`"); + // Add Lua-style comments + addToken(LLKeywordToken::TT_ONE_SIDED_DELIMITER, "--", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (Lua-style single-line)\nNon-functional commentary or disabled code", delimiter); + // Add Lua multi-line comments (long brackets) + addToken(LLKeywordToken::TT_LONG_BRACKET, "--[", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (Lua-style multi-line)\nNon-functional commentary or disabled code", delimiter); + // Add Lua multi-line strings (long brackets) + addToken(LLKeywordToken::TT_LONG_BRACKET, "[", LLUIColorTable::instance().getColor("SyntaxLslStringLiteral"), "String literal (Lua-style multi-line)", delimiter); + } + else + { + addToken(LLKeywordToken::TT_LABEL, "@", getColorGroup("misc-flow-label"), "Label\nTarget for jump statement", delimiter); + // Add LSL-style comments + addToken(LLKeywordToken::TT_ONE_SIDED_DELIMITER, "//", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (single-line)\nNon-functional commentary or disabled code", delimiter); + addToken(LLKeywordToken::TT_TWO_SIDED_DELIMITER, "/*", LLUIColorTable::instance().getColor("SyntaxLslComment"), "Comment (multi-line)\nNon-functional commentary or disabled code", "*/"); + } LLSD::map_iterator itr = mSyntax.beginMap(); - for ( ; itr != mSyntax.endMap(); ++itr) + for (; itr != mSyntax.endMap(); ++itr) { if (itr->first == "llsd-lsl-syntax-version") { @@ -258,6 +275,7 @@ void LLKeywords::processTokens() } } } + LL_INFOS("SyntaxLSL") << "Finished processing tokens." << LL_ENDL; } @@ -346,8 +364,11 @@ void LLKeywords::processTokensGroup(const LLSD& tokens, std::string_view group) break; case LLKeywordToken::TT_FUNCTION: tooltip = getAttribute("return") + " " + outer_itr->first + "(" + getArguments(arguments) + ");"; - tooltip.append("\nEnergy: "); - tooltip.append(getAttribute("energy").empty() ? "0.0" : getAttribute("energy")); + if (std::stod(getAttribute("energy")) >= 0) + { + tooltip.append("\nEnergy: "); + tooltip.append(getAttribute("energy").empty() ? "0.0" : getAttribute("energy")); + } if (!getAttribute("sleep").empty()) { tooltip += ", Sleep: " + getAttribute("sleep"); @@ -476,34 +497,29 @@ bool LLKeywords::WStringMapIndex::operator<(const LLKeywords::WStringMapIndex &o } LLTrace::BlockTimerStatHandle FTM_SYNTAX_COLORING("Syntax Coloring"); +constexpr size_t AVERAGE_SEGMENT_LENGTH = 8; -// Walk through a string, applying the rules specified by the keyword token list and -// create a list of color segments. -void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLWString& wtext, LLTextEditor& editor, LLStyleConstSP style) +void LLKeywords::collectSegmentOps(segment_ops_t& ops, const LLWString& wtext, bool disable_syntax_highlighting) const { - LL_RECORD_BLOCK_TIME(FTM_SYNTAX_COLORING); - seg_list->clear(); + ops.clear(); - if( wtext.empty() ) + if (wtext.empty()) { return; } - - S32 text_len = static_cast<S32>(wtext.size()) + 1; - - seg_list->push_back( new LLNormalTextSegment( style, 0, text_len, editor ) ); + // Heuristic to reduce reallocation churn on large scripts. + ops.reserve(wtext.size() / AVERAGE_SEGMENT_LENGTH); const llwchar* base = wtext.c_str(); const llwchar* cur = base; + while( *cur ) { if( *cur == '\n' || cur == base ) { if( *cur == '\n' ) { - LLTextSegmentPtr text_segment = new LLLineBreakTextSegment(style, (S32)(cur - base)); - text_segment->setToken( 0 ); - insertSegment( *seg_list, text_segment, text_len, style, editor); + ops.push_back({SegmentOp::OP_LINE_BREAK, (S32)(cur - base), 0, nullptr}); cur++; if( !*cur || *cur == '\n' ) { @@ -526,24 +542,25 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW // Line start tokens { bool line_done = false; - for (token_list_t::iterator iter = mLineTokenList.begin(); - iter != mLineTokenList.end(); ++iter) + auto line_token_it = mLineTokenByFirstChar.find(*cur); + if (line_token_it != mLineTokenByFirstChar.end()) { - LLKeywordToken* cur_token = *iter; - if( cur_token->isHead( cur ) ) + for (auto* cur_token : line_token_it->second) { - S32 seg_start = (S32)(cur - base); - while( *cur && *cur != '\n' ) + if( cur_token->isHead( cur ) ) { - // skip the rest of the line - cur++; - } - S32 seg_end = (S32)(cur - base); + S32 seg_start = (S32)(cur - base); + while( *cur && *cur != '\n' ) + { + // skip the rest of the line + cur++; + } + S32 seg_end = (S32)(cur - base); - //create segments from seg_start to seg_end - insertSegments(wtext, *seg_list,cur_token, text_len, seg_start, seg_end, style, editor); - line_done = true; // to break out of second loop. - break; + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_end, cur_token}); + line_done = true; // to break out of second loop. + break; + } } } @@ -560,20 +577,32 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW cur++; } + // Check if syntax highlighting is disabled + if (disable_syntax_highlighting) + { + while (*cur && *cur != '\n') + { + ++cur; + } + continue; // skip processing any further syntax highlighting + } + while( *cur && *cur != '\n' ) { // Check against delimiters { S32 seg_start = 0; LLKeywordToken* cur_delimiter = NULL; - for (token_list_t::iterator iter = mDelimiterTokenList.begin(); - iter != mDelimiterTokenList.end(); ++iter) + auto delimiter_it = mDelimiterTokenByFirstChar.find(*cur); + if (delimiter_it != mDelimiterTokenByFirstChar.end()) { - LLKeywordToken* delimiter = *iter; - if( delimiter->isHead( cur ) ) + for (auto* delimiter : delimiter_it->second) { - cur_delimiter = delimiter; - break; + if( delimiter->isHead( cur ) ) + { + cur_delimiter = delimiter; + break; + } } } @@ -583,10 +612,79 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW S32 seg_end = 0; seg_start = (S32)(cur - base); - cur += cur_delimiter->getLengthHead(); LLKeywordToken::ETokenType type = cur_delimiter->getType(); - if( type == LLKeywordToken::TT_TWO_SIDED_DELIMITER || type == LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS ) + + // Handle Lua long brackets specially - need to verify full pattern + if (type == LLKeywordToken::TT_LONG_BRACKET) + { + const llwchar* p = cur + cur_delimiter->getLengthHead(); // after --[ or [ + + // Count equals signs + S32 level = 0; + while (*p == '=') + { + level++; + p++; + } + + // Must have second [ + if (*p == '[') + { + p++; // skip the second [ + + // Build the closing pattern: ] + level equals + ] + // Search for it in the remaining text + while (*p) + { + if (*p == ']') + { + // Check if this is our closing bracket + const llwchar* close_check = p + 1; + S32 close_equals = 0; + while (*close_check == '=') + { + close_equals++; + close_check++; + } + if (close_equals == level && *close_check == ']') + { + // Found the matching close + seg_end = (S32)(close_check + 1 - base); + cur = close_check + 1; + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_end, cur_delimiter}); + break; + } + } + p++; + } + + if (!*p) + { + // No closing found, highlight to end of file + seg_end = static_cast<S32>(wtext.size()); + cur = base + seg_end; + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_end, cur_delimiter}); + } + continue; + } + else + { + // Not a valid long bracket (e.g., --[abc), skip this delimiter + cur_delimiter = NULL; + } + } + + if (!cur_delimiter) + { + // Long bracket validation failed, continue to next character + cur++; + continue; + } + + cur += cur_delimiter->getLengthHead(); + + if(type == LLKeywordToken::TT_TWO_SIDED_DELIMITER || type == LLKeywordToken::TT_DOUBLE_QUOTATION_MARKS) { while( *cur && !cur_delimiter->isTail(cur)) { @@ -627,7 +725,7 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW if( *cur ) { - cur += cur_delimiter->getLengthHead(); + cur += cur_delimiter->getLengthTail(); seg_end = seg_start + between_delimiters + cur_delimiter->getLengthHead() + cur_delimiter->getLengthTail(); } else @@ -648,12 +746,7 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW seg_end = seg_start + between_delimiters + cur_delimiter->getLengthHead(); } - insertSegments(wtext, *seg_list,cur_delimiter, text_len, seg_start, seg_end, style, editor); - /* - LLTextSegmentPtr text_segment = new LLNormalTextSegment( cur_delimiter->getColor(), seg_start, seg_end, editor ); - text_segment->setToken( cur_delimiter ); - insertSegment( seg_list, text_segment, text_len, defaultColor, editor); - */ + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_end, cur_delimiter}); // Note: we don't increment cur, since the end of one delimited seg may be immediately // followed by the start of another one. continue; @@ -662,34 +755,77 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW // check against words llwchar prev = cur > base ? *(cur-1) : 0; - if( !iswalnum( prev ) && (prev != '_') ) + if (!iswalnum(prev) && prev != '_' && prev != '.') { - const llwchar* p = cur; - while( iswalnum( *p ) || (*p == '_') ) + const llwchar* word_start = cur; + S32 namespace_dots = 0; + const llwchar* last_dot = nullptr; + + // Find the full extent of the word, potentially including namespace dots + while (iswalnum(*cur) || *cur == '_' || (mLuauLanguage && *cur == '.' && iswalnum(*(cur+1)))) { - p++; + if (mLuauLanguage && *cur == '.') + { + namespace_dots++; + last_dot = cur; + } + cur++; } - S32 seg_len = (S32)(p - cur); - if( seg_len > 0 ) + + S32 seg_len = (S32)(cur - word_start); + if (seg_len > 0) { - WStringMapIndex word( cur, seg_len ); - word_token_map_t::iterator map_iter = mWordTokenMap.find(word); - if( map_iter != mWordTokenMap.end() ) + S32 seg_start = (S32)(word_start - base); + S32 seg_end = seg_start + seg_len; + + // First try to match the whole token (including dots for Lua namespaces) + word_token_map_t::const_iterator map_iter = mWordTokenMap.find(WStringMapIndex(word_start, seg_len)); + + if (map_iter != mWordTokenMap.end()) + { + // Found a match for the complete token (including any namespace) + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_end, map_iter->second}); + } + else if (namespace_dots > 0 && mLuauLanguage) { - LLKeywordToken* cur_token = map_iter->second; - S32 seg_start = (S32)(cur - base); - S32 seg_end = seg_start + seg_len; + // If using Lua and we have namespace dots but didn't match the whole token, + // check if we have a match for just the namespace prefix (e.g., "ll") + if (last_dot > word_start) + { + // Get the namespace prefix (part before the first dot) + S32 prefix_len = (S32)(last_dot - word_start); + map_iter = mWordTokenMap.find(WStringMapIndex(word_start, prefix_len)); - // LL_INFOS("SyntaxLSL") << "Seg: [" << word.c_str() << "]" << LL_ENDL; + if (map_iter != mWordTokenMap.end()) + { + // Found a match for the namespace prefix, highlight just that part + ops.push_back({SegmentOp::OP_TOKEN, seg_start, seg_start + prefix_len, map_iter->second}); - insertSegments(wtext, *seg_list,cur_token, text_len, seg_start, seg_end, style, editor); + // Now try to match the function part (after the dot) + const llwchar* func_part = last_dot + 1; + S32 func_len = (S32)(cur - func_part); + + if (func_len > 0) + { + // Look for complete function matches + map_iter = mWordTokenMap.find(WStringMapIndex(func_part, func_len)); + + if (map_iter != mWordTokenMap.end()) + { + // Found a match for the function part. + // Start must be after the dot (seg_start + prefix_len + 1), + // not at seg_start, to avoid overlapping with the prefix segment. + ops.push_back({SegmentOp::OP_TOKEN, seg_start + prefix_len + 1, seg_end, map_iter->second}); + } + } + } + } } - cur += seg_len; - continue; + continue; // Continue to next token regardless of match } } - if( *cur && *cur != '\n' ) + if (*cur && *cur != '\n') { cur++; } @@ -697,6 +833,84 @@ void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLW } } +bool LLKeywords::applySegmentOpsRange(std::vector<LLTextSegmentPtr> *seg_list, + const LLWString& wtext, + const segment_ops_t& ops, + size_t& op_index, + size_t max_ops, + LLTextEditor& editor, + LLStyleConstSP style) +{ + if (wtext.empty()) + { + return true; + } + + if (op_index == 0) + { + // Clear the segment list + seg_list->clear(); + // Reserve capacity for segments based on an estimated average of 8 characters per segment. + seg_list->reserve(wtext.size() / AVERAGE_SEGMENT_LENGTH); + + S32 text_len = static_cast<S32>(wtext.size()) + 1; + seg_list->push_back( new LLNormalTextSegment( style, 0, text_len, editor ) ); + } + + S32 text_len = static_cast<S32>(wtext.size()) + 1; + size_t end_index = op_index + max_ops; + if (end_index > ops.size()) + { + end_index = ops.size(); + } + + for (; op_index < end_index; ++op_index) + { + const auto& op = ops[op_index]; + if (op.type == SegmentOp::OP_LINE_BREAK) + { + LLTextSegmentPtr text_segment = new LLLineBreakTextSegment(style, op.start); + text_segment->setToken( 0 ); + insertSegment( *seg_list, text_segment, text_len, style, editor); + } + else + { + insertSegments(wtext, *seg_list, op.token, text_len, op.start, op.end, style, editor); + } + } + + return op_index >= ops.size(); +} + +void LLKeywords::applySegmentOps(std::vector<LLTextSegmentPtr> *seg_list, + const LLWString& wtext, + const segment_ops_t& ops, + LLTextEditor& editor, + LLStyleConstSP style) +{ + size_t op_index = 0; + applySegmentOpsRange(seg_list, wtext, ops, op_index, ops.size(), editor, style); +} + +// Walk through a string, applying the rules specified by the keyword token list and +// create a list of color segments. +void LLKeywords::findSegments(std::vector<LLTextSegmentPtr>* seg_list, const LLWString& wtext, LLTextEditor& editor, LLStyleConstSP style) +{ + LL_RECORD_BLOCK_TIME(FTM_SYNTAX_COLORING); + + if( wtext.empty() ) + { + return; + } + + static LLCachedControl<bool> sDisableSyntaxHighlighting(gSavedSettings, "ScriptEditorDisableSyntaxHighlight", false); + const bool disable_syntax_highlighting = sDisableSyntaxHighlighting; + + segment_ops_t ops; + collectSegmentOps(ops, wtext, disable_syntax_highlighting); + applySegmentOps(seg_list, wtext, ops, editor, style); +} + void LLKeywords::insertSegments(const LLWString& wtext, std::vector<LLTextSegmentPtr>& seg_list, LLKeywordToken* cur_token, S32 text_len, S32 seg_start, S32 seg_end, LLStyleConstSP style, LLTextEditor& editor ) { std::string::size_type pos = wtext.find('\n',seg_start); diff --git a/indra/llui/llkeywords.h b/indra/llui/llkeywords.h index 53b5435324..9d9c8f964c 100644 --- a/indra/llui/llkeywords.h +++ b/indra/llui/llkeywords.h @@ -36,6 +36,8 @@ #include <map> #include <list> #include <deque> +#include <vector> +#include <cstddef> #include "llpointer.h" class LLTextSegment; @@ -53,6 +55,7 @@ public: * - TT_ONE_SIDED_DELIMITER are for open-ended delimiters which are terminated by EOL. * - TT_TWO_SIDED_DELIMITER are for delimiters that end with a different delimiter than they open with. * - TT_DOUBLE_QUOTATION_MARKS are for delimiting areas using the same delimiter to open and close. + * - TT_LONG_BRACKET are for Lua tokens that use brackets with counted equals signs. */ typedef enum e_token_type { @@ -62,6 +65,7 @@ public: TT_TWO_SIDED_DELIMITER, TT_ONE_SIDED_DELIMITER, TT_DOUBLE_QUOTATION_MARKS, + TT_LONG_BRACKET, // Lua long brackets: --[=*[ or [=*[ // Following constants are more specific versions of the preceding ones TT_CONSTANT, // WORD TT_CONTROL, // WORD @@ -82,6 +86,10 @@ public: { } + ~LLKeywordToken() + { + } + S32 getLengthHead() const { return static_cast<S32>(mToken.size()); } S32 getLengthTail() const { return static_cast<S32>(mDelimiter.size()); } bool isHead(const llwchar* s) const; @@ -118,7 +126,33 @@ public: const LLWString& text, class LLTextEditor& editor, LLStyleConstSP style); - void initialize(LLSD SyntaxXML); + struct SegmentOp + { + enum EOpType + { + OP_LINE_BREAK, + OP_TOKEN + }; + EOpType type; + S32 start; + S32 end; + LLKeywordToken* token; + }; + typedef std::vector<SegmentOp> segment_ops_t; + void collectSegmentOps(segment_ops_t& ops, const LLWString& text, bool disable_syntax_highlighting) const; + void applySegmentOps(std::vector<LLTextSegmentPtr> *seg_list, + const LLWString& text, + const segment_ops_t& ops, + class LLTextEditor& editor, + LLStyleConstSP style); + bool applySegmentOpsRange(std::vector<LLTextSegmentPtr> *seg_list, + const LLWString& text, + const segment_ops_t& ops, + size_t& op_index, + size_t max_ops, + class LLTextEditor& editor, + LLStyleConstSP style); + void initialize(LLSD SyntaxXML, bool luau_language = false); void processTokens(); // Add the token as described @@ -189,10 +223,14 @@ protected: bool mLoaded; LLSD mSyntax; + bool mLuauLanguage; word_token_map_t mWordTokenMap; typedef std::deque<LLKeywordToken*> token_list_t; token_list_t mLineTokenList; token_list_t mDelimiterTokenList; + typedef std::map<llwchar, token_list_t> token_by_first_char_map_t; + token_by_first_char_map_t mLineTokenByFirstChar; + token_by_first_char_map_t mDelimiterTokenByFirstChar; typedef std::unordered_map<std::string, std::string, ll::string_hash, std::equal_to<>> element_attributes_t; typedef element_attributes_t::const_iterator attribute_iterator_t; diff --git a/indra/llui/llscrolllistctrl.cpp b/indra/llui/llscrolllistctrl.cpp index 558ce6a7fd..662fe97689 100644 --- a/indra/llui/llscrolllistctrl.cpp +++ b/indra/llui/llscrolllistctrl.cpp @@ -1281,6 +1281,19 @@ LLScrollListItem* LLScrollListCtrl::getItemByLabel(const std::string& label, boo return NULL; } +LLScrollListItem* LLScrollListCtrl::getItemByValue(const std::string& value) +{ + for (LLScrollListItem* item : mItemList) + { + if (item->getValue().asString() == value) + { + return item; + } + } + + return NULL; +} + LLScrollListItem* LLScrollListCtrl::getItemByIndex(S32 index) { if (index >= 0 && index < (S32)mItemList.size()) diff --git a/indra/llui/llscrolllistctrl.h b/indra/llui/llscrolllistctrl.h index d3735c5052..b8d63972a5 100644 --- a/indra/llui/llscrolllistctrl.h +++ b/indra/llui/llscrolllistctrl.h @@ -262,7 +262,8 @@ public: bool selectItemByLabel(const std::string& item, bool case_sensitive = true, S32 column = 0); // false if item not found bool selectItemByPrefix(const std::string& target, bool case_sensitive = true, S32 column = -1); bool selectItemByPrefix(const LLWString& target, bool case_sensitive = true, S32 column = -1); - LLScrollListItem* getItemByLabel(const std::string& item, bool case_sensitive = true, S32 column = 0); + LLScrollListItem* getItemByLabel(const std::string& label, bool case_sensitive = true, S32 column = 0); + LLScrollListItem* getItemByValue(const std::string& value); LLScrollListItem* getItemByIndex(S32 index); std::string getSelectedItemLabel(S32 column = 0) const; LLSD getSelectedValue(); diff --git a/indra/llwindow/llwindowwin32.cpp b/indra/llwindow/llwindowwin32.cpp index 252482a96e..8e3d2c9c8e 100644 --- a/indra/llwindow/llwindowwin32.cpp +++ b/indra/llwindow/llwindowwin32.cpp @@ -437,7 +437,7 @@ struct LLWindowWin32::LLWindowWin32Thread : public LL::ThreadPool { if (!mWindowTimeout) { - mWindowTimeout = std::make_unique<LLWatchdogTimeout>("mainloop"); + mWindowTimeout = std::make_unique<LLWatchdogTimeout>("WindowThread"); // supposed to be executed within run(), // so no point checking if thread is alive resumeTimeout("TimeoutInit"); diff --git a/indra/newview/CMakeLists.txt b/indra/newview/CMakeLists.txt index c76145fab3..1d715338cb 100644 --- a/indra/newview/CMakeLists.txt +++ b/indra/newview/CMakeLists.txt @@ -296,6 +296,7 @@ set(viewer_SOURCE_FILES llfloatersceneloadstats.cpp llfloaterscriptdebug.cpp llfloaterscriptedprefs.cpp + llfloaterscripting.cpp llfloaterscriptlimits.cpp llfloatersearch.cpp llfloatersellland.cpp @@ -566,6 +567,7 @@ set(viewer_SOURCE_FILES llsceneview.cpp llscreenchannel.cpp llscripteditor.cpp + llscripteditorws.cpp llscriptfloater.cpp llscrollingpanelparam.cpp llscrollingpanelparambase.cpp @@ -983,6 +985,7 @@ set(viewer_HEADER_FILES llfloatersceneloadstats.h llfloaterscriptdebug.h llfloaterscriptedprefs.h + llfloaterscripting.h llfloaterscriptlimits.h llfloatersearch.h llfloatersellland.h @@ -1239,6 +1242,7 @@ set(viewer_HEADER_FILES llsceneview.h llscreenchannel.h llscripteditor.h + llscripteditorws.h llscriptfloater.h llscriptruntimeperms.h llscrollingpanelparam.h @@ -1650,7 +1654,8 @@ set_source_files_properties(${viewer_SHADER_FILES} PROPERTIES HEADER_FILE_ONLY TRUE) list(APPEND viewer_SOURCE_FILES ${viewer_SHADER_FILES}) - +# note that the scripts which publish these files are sensitive to the file +# extensions. Be cautious about adding new file types here. set(viewer_APPSETTINGS_FILES app_settings/anim.ini app_settings/autoreplace.xml @@ -1661,7 +1666,6 @@ set(viewer_APPSETTINGS_FILES app_settings/grass.xml app_settings/ignorable_dialogs.xml app_settings/key_bindings.xml - app_settings/keywords_lsl_default.xml app_settings/logcontrol.xml app_settings/settings.xml app_settings/settings_crash_behavior.xml @@ -1670,6 +1674,7 @@ set(viewer_APPSETTINGS_FILES app_settings/std_bump.ini app_settings/toolbars.xml app_settings/trees.xml + app_settings/types_lua_default.xml app_settings/viewerart.xml app_settings/message.xml ${CMAKE_SOURCE_DIR}/../scripts/messages/message_template.msg diff --git a/indra/newview/app_settings/keywords_lsl_default.xml b/indra/newview/app_settings/keywords_lsl_default.xml deleted file mode 100644 index f99b86bd39..0000000000 --- a/indra/newview/app_settings/keywords_lsl_default.xml +++ /dev/null @@ -1,19161 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<llsd> - <map> - <key>controls</key> - <map> - <key>do</key> - <map> - <key>tooltip</key> - <string>do / while loop\ndo {\n...\n} while (<condition>);</string> - </map> - <key>else</key> - <map> - <key>tooltip</key> - <string>if / else block\nif (<condition>) {\n...\n[} else [if (<condition>) {\n...]]\n}</string> - </map> - <key>for</key> - <map> - <key>tooltip</key> - <string>for loop\nfor (<initializer>; <condition>; <post-iteration-statement>)\n{ ...\n}</string> - </map> - <key>if</key> - <map> - <key>tooltip</key> - <string>if / else block\nif (<condition>) {\n...\n[} else [if (<condition>) {\n...]]\n}</string> - </map> - <key>jump</key> - <map> - <key>tooltip</key> - <string>jump statement\njump <label></string> - </map> - <key>return</key> - <map> - <key>tooltip</key> - <string>Leave current event or function.\nreturn [<variable>];\nOptionally pass back a variable's value, from a function.</string> - </map> - <key>state</key> - <map> - <key>tooltip</key> - <string>state <target>\nIf the target state is not the same as the current one, change to the target state.</string> - </map> - <key>while</key> - <map> - <key>tooltip</key> - <string>while loop\nwhile (<condition>) {\n,,,\n}</string> - </map> - </map> - <key>types</key> - <map> - <key>float</key> - <map> - <key>tooltip</key> - <string>32 bit floating point value.\nThe range is 1.175494351E-38 to 3.402823466E+38.</string> - </map> - <key>integer</key> - <map> - <key>tooltip</key> - <string>32 bit integer value.\n−2,147,483,648 and +2,147,483,647 (that is 0x80000000 to 0x7FFFFFFF in hex).</string> - </map> - <key>key</key> - <map> - <key>tooltip</key> - <string>A 128 bit unique identifier (UUID).\nThe key is represented as hexidecimal characters (A-F and 0-9), grouped into sections (8,4,4,4,12 characters) and separated by hyphens (for a total of 36 characters). e.g. "A822FF2B-FF02-461D-B45D-DCD10A2DE0C2".</string> - </map> - <key>list</key> - <map> - <key>tooltip</key> - <string>A collection of other data types.\nLists are signified by square brackets surrounding their elements; the elements inside are separated by commas. e.g. [0, 1, 2, 3, 4] or ["Yes", "No", "Perhaps"].</string> - </map> - <key>quaternion</key> - <map> - <key>tooltip</key> - <string>The quaternion type is a left over from way back when LSL was created. It was later renamed to <rotation> to make it more user friendly, but it appears someone forgot to remove it ;-)</string> - </map> - <key>rotation</key> - <map> - <key>tooltip</key> - <string>The rotation type is one of several ways to represent an orientation in 3D.\nIt is a mathematical object called a quaternion. You can think of a quaternion as four numbers (x, y, z, w), three of which represent the direction an object is facing and a fourth that represents the object's banking left or right around that direction.</string> - </map> - <key>string</key> - <map> - <key>tooltip</key> - <string>Text data.\nThe editor accepts UTF-8 encoded text.</string> - </map> - <key>vector</key> - <map> - <key>tooltip</key> - <string>A vector is a data type that contains a set of three float values.\nVectors are used to represent colors (RGB), positions, and directions/velocities.</string> - </map> - </map> - <key>constants</key> - <map> - <key>ACTIVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>Objects in world that are running a script or currently physically moving.</string> - </map> - <key>AGENT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Objects in world that are agents.</string> - </map> - <key>AGENT_ALWAYS_RUN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1000</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_ATTACHMENTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>The agent has attachments.</string> - </map> - <key>AGENT_AUTOPILOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2000</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_AWAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_BUSY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x800</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_BY_LEGACY_NAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_BY_USERNAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_CROUCHING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_FLYING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>The agent is flying.</string> - </map> - <key>AGENT_IN_AIR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_LIST_PARCEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Agents on the same parcel where the script is running.</string> - </map> - <key>AGENT_LIST_PARCEL_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Agents on any parcel in the region where the parcel owner is the same as the owner of the parcel under the scripted object.</string> - </map> - <key>AGENT_LIST_REGION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>All agents in the region.</string> - </map> - <key>AGENT_MOUSELOOK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_ON_OBJECT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_SCRIPTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>The agent has scripted attachments.</string> - </map> - <key>AGENT_SITTING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_TYPING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string/> - </map> - <key>AGENT_WALKING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string/> - </map> - <key>ALL_SIDES</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>ANIM_ON</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Texture animation is on.</string> - </map> - <key>ATTACH_AVATAR_CENTER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>40</integer> - <key>tooltip</key> - <string>Attach to the avatar's geometric centre.</string> - </map> - <key>ATTACH_BACK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string>Attach to the avatar's back.</string> - </map> - <key>ATTACH_BELLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>28</integer> - <key>tooltip</key> - <string>Attach to the avatar's belly.</string> - </map> - <key>ATTACH_CHEST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Attach to the avatar's chest.</string> - </map> - <key>ATTACH_CHIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>Attach to the avatar's chin.</string> - </map> - <key>ATTACH_HEAD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Attach to the avatar's head.</string> - </map> - <key>ATTACH_HUD_BOTTOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>37</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_BOTTOM_LEFT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>36</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_BOTTOM_RIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>38</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_CENTER_1</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>35</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_CENTER_2</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>31</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_TOP_CENTER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>33</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_TOP_LEFT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>34</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_HUD_TOP_RIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>32</integer> - <key>tooltip</key> - <string/> - </map> - <key>ATTACH_LEAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>Attach to the avatar's left ear.</string> - </map> - <key>ATTACH_LEFT_PEC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>29</integer> - <key>tooltip</key> - <string>Attach to the avatar's left pectoral.</string> - </map> - <key>ATTACH_LEYE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string>Attach to the avatar's left eye.</string> - </map> - <key>ATTACH_LFOOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>Attach to the avatar's left foot.</string> - </map> - <key>ATTACH_LHAND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Attach to the avatar's left hand.</string> - </map> - <key>ATTACH_LHIP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>25</integer> - <key>tooltip</key> - <string>Attach to the avatar's left hip.</string> - </map> - <key>ATTACH_LLARM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string>Attach to the avatar's left lower arm.</string> - </map> - <key>ATTACH_LLLEG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>27</integer> - <key>tooltip</key> - <string>Attach to the avatar's lower left leg.</string> - </map> - <key>ATTACH_LPEC</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>30</integer> - <key>tooltip</key> - <string>Attach to the avatar's right pectoral. (Deprecated, use ATTACH_RIGHT_PEC)</string> - </map> - <key>ATTACH_LSHOULDER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Attach to the avatar's left shoulder.</string> - </map> - <key>ATTACH_LUARM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string>Attach to the avatar's left upper arm.</string> - </map> - <key>ATTACH_LULEG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>26</integer> - <key>tooltip</key> - <string>Attach to the avatar's lower upper leg.</string> - </map> - <key>ATTACH_MOUTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string>Attach to the avatar's mouth.</string> - </map> - <key>ATTACH_NECK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>39</integer> - <key>tooltip</key> - <string>Attach to the avatar's neck.</string> - </map> - <key>ATTACH_NOSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string>Attach to the avatar's nose.</string> - </map> - <key>ATTACH_PELVIS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>Attach to the avatar's pelvis.</string> - </map> - <key>ATTACH_REAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string>Attach to the avatar's right ear.</string> - </map> - <key>ATTACH_REYE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string>Attach to the avatar's right eye.</string> - </map> - <key>ATTACH_RFOOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>Attach to the avatar's right foot.</string> - </map> - <key>ATTACH_RHAND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Attach to the avatar's right hand.</string> - </map> - <key>ATTACH_RHIP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>22</integer> - <key>tooltip</key> - <string>Attach to the avatar's right hip.</string> - </map> - <key>ATTACH_RIGHT_PEC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>30</integer> - <key>tooltip</key> - <string>Attach to the avatar's right pectoral.</string> - </map> - <key>ATTACH_RLARM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>19</integer> - <key>tooltip</key> - <string>Attach to the avatar's right lower arm.</string> - </map> - <key>ATTACH_RLLEG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>24</integer> - <key>tooltip</key> - <string>Attach to the avatar's right lower leg.</string> - </map> - <key>ATTACH_RPEC</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>29</integer> - <key>tooltip</key> - <string>Attach to the avatar's left pectoral. (deprecated, use ATTACH_LEFT_PEC)</string> - </map> - <key>ATTACH_RSHOULDER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Attach to the avatar's right shoulder.</string> - </map> - <key>ATTACH_RUARM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>18</integer> - <key>tooltip</key> - <string>Attach to the avatar's right upper arm.</string> - </map> - <key>ATTACH_RULEG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>23</integer> - <key>tooltip</key> - <string>Attach to the avatar's right upper leg.</string> - </map> - <key>ATTACH_LHAND_RING1</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>41</integer> - <key>tooltip</key> - <string>Attach to the avatar's left ring finger.</string> - </map> - <key>ATTACH_RHAND_RING1</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>42</integer> - <key>tooltip</key> - <string>Attach to the avatar's right ring finger.</string> - </map> - <key>ATTACH_TAIL_BASE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>43</integer> - <key>tooltip</key> - <string>Attach to the avatar's tail base.</string> - </map> - <key>ATTACH_TAIL_TIP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>44</integer> - <key>tooltip</key> - <string>Attach to the avatar's tail tip.</string> - </map> - <key>ATTACH_LWING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>45</integer> - <key>tooltip</key> - <string>Attach to the avatar's left wing.</string> - </map> - <key>ATTACH_RWING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>46</integer> - <key>tooltip</key> - <string>Attach to the avatar's right wing.</string> - </map> - <key>ATTACH_FACE_JAW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>47</integer> - <key>tooltip</key> - <string>Attach to the avatar's jaw.</string> - </map> - <key>ATTACH_FACE_LEAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>48</integer> - <key>tooltip</key> - <string>Attach to the avatar's left ear (extended).</string> - </map> - <key>ATTACH_FACE_REAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>49</integer> - <key>tooltip</key> - <string>Attach to the avatar's right ear (extended).</string> - </map> - <key>ATTACH_FACE_LEYE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>50</integer> - <key>tooltip</key> - <string>Attach to the avatar's left eye (extended).</string> - </map> - <key>ATTACH_FACE_REYE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>51</integer> - <key>tooltip</key> - <string>Attach to the avatar's right eye (extended).</string> - </map> - <key>ATTACH_FACE_TONGUE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>52</integer> - <key>tooltip</key> - <string>Attach to the avatar's tongue.</string> - </map> - <key>ATTACH_GROIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>53</integer> - <key>tooltip</key> - <string>Attach to the avatar's groin.</string> - </map> - <key>ATTACH_HIND_LFOOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>54</integer> - <key>tooltip</key> - <string>Attach to the avatar's left hind foot.</string> - </map> - <key>ATTACH_HIND_RFOOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>55</integer> - <key>tooltip</key> - <string>Attach to the avatar's right hind foot.</string> - </map> - <key>AVOID_CHARACTERS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>AVOID_DYNAMIC_OBSTACLES</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>AVOID_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_ACTIVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_BEHINDNESS_ANGLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_BEHINDNESS_LAG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_DISTANCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_FOCUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_FOCUS_LAG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_FOCUS_LOCKED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>22</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_FOCUS_OFFSET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_FOCUS_THRESHOLD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_PITCH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_POSITION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_POSITION_LAG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_POSITION_LOCKED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string/> - </map> - <key>CAMERA_POSITION_THRESHOLD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_ALLOWED_DROP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>The object inventory has changed because an item was added through the llAllowInventoryDrop interface.</string> - </map> - <key>CHANGED_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>The object color has changed.</string> - </map> - <key>CHANGED_INVENTORY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>The object inventory has changed.</string> - </map> - <key>CHANGED_LINK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>The object has linked or its links were broken.</string> - </map> - <key>CHANGED_MEDIA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x800</string> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_REGION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_REGION_START</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_SCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>The object scale (size) has changed.</string> - </map> - <key>CHANGED_SHAPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>The object base shape has changed, e.g., a box to a cylinder.</string> - </map> - <key>CHANGED_TELEPORT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string/> - </map> - <key>CHANGED_TEXTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>The texture offset, scale rotation, or simply the object texture has changed.</string> - </map> - <key>CHARACTER_ACCOUNT_FOR_SKIPPED_FRAMES</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string>If set to false, character will not attempt to catch up on lost time when pathfinding performance is low, potentially providing more reliable movement (albeit while potentially appearing to be more stuttery). Default is true to match pre-existing behavior.</string> - </map> - <key>CHARACTER_AVOIDANCE_MODE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Allows you to specify that a character should not try to avoid other characters, should not try to avoid dynamic obstacles (relatively fast moving objects and avatars), or both.</string> - </map> - <key>CHARACTER_CMD_JUMP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x01</string> - <key>tooltip</key> - <string>Makes the character jump. Requires an additional parameter, the height to jump, between 0.1m and 2.0m. This must be provided as the first element of the llExecCharacterCmd option list.</string> - </map> - <key>CHARACTER_CMD_SMOOTH_STOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHARACTER_CMD_STOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x00</string> - <key>tooltip</key> - <string>Stops any current pathfinding operation.</string> - </map> - <key>CHARACTER_DESIRED_SPEED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Speed of pursuit in meters per second.</string> - </map> - <key>CHARACTER_DESIRED_TURN_SPEED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>The character's maximum speed while turning about the Z axis. - Note that this is only loosely enforced.</string> - </map> - <key>CHARACTER_LENGTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Set collision capsule length - cannot be less than two times the radius.</string> - </map> - <key>CHARACTER_MAX_ACCEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>The character's maximum acceleration rate.</string> - </map> - <key>CHARACTER_MAX_DECEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string>The character's maximum deceleration rate.</string> - </map> - <key>CHARACTER_MAX_SPEED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>The character's maximum speed.</string> - </map> - <key>CHARACTER_MAX_TURN_RADIUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>The character's turn radius when travelling at CHARACTER_MAX_TURN_SPEED.</string> - </map> - <key>CHARACTER_ORIENTATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Valid options are: VERTICAL, HORIZONTAL.</string> - </map> - <key>CHARACTER_RADIUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Set collision capsule radius.</string> - </map> - <key>CHARACTER_STAY_WITHIN_PARCEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string>Determines whether a character can leave its starting parcel.\nTakes a boolean parameter. If TRUE, the character cannot voluntarilly leave the parcel, but can return to it.</string> - </map> - <key>CHARACTER_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Specifies which walk-ability coefficient will be used by this character.</string> - </map> - <key>CHARACTER_TYPE_A</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHARACTER_TYPE_B</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHARACTER_TYPE_C</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHARACTER_TYPE_D</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>CHARACTER_TYPE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>CLICK_ACTION_BUY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>When the prim is clicked, the buy dialog is opened.</string> - </map> - <key>CLICK_ACTION_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Performs the default action: when the prim is clicked, touch events are triggered.</string> - </map> - <key>CLICK_ACTION_OPEN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>When the prim is clicked, the object inventory dialog is opened.</string> - </map> - <key>CLICK_ACTION_OPEN_MEDIA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>When the prim is touched, the web media dialog is opened.</string> - </map> - <key>CLICK_ACTION_PAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>When the prim is clicked, the pay dialog is opened.</string> - </map> - <key>CLICK_ACTION_PLAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>When the prim is clicked, html-on-a-prim is enabled?</string> - </map> - <key>CLICK_ACTION_SIT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>When the prim is clicked, the avatar sits upon it.</string> - </map> - <key>CLICK_ACTION_TOUCH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>When the prim is clicked, touch events are triggered.</string> - </map> - <key>CONTENT_TYPE_ATOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>"application/atom+xml"</string> - </map> - <key>CONTENT_TYPE_FORM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>"application/x-www-form-urlencoded"</string> - </map> - <key>CONTENT_TYPE_HTML</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>"text/html", only valid for embedded browsers on content owned by the person viewing. Falls back to "text/plain" otherwise.</string> - </map> - <key>CONTENT_TYPE_JSON</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>"application/json"</string> - </map> - <key>CONTENT_TYPE_LLSD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>"application/llsd+xml"</string> - </map> - <key>CONTENT_TYPE_RSS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>"application/rss+xml"</string> - </map> - <key>CONTENT_TYPE_TEXT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>"text/plain"</string> - </map> - <key>CONTENT_TYPE_XHTML</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>"application/xhtml+xml"</string> - </map> - <key>CONTENT_TYPE_XML</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>"application/xml"</string> - </map> - <key>CONTROL_BACK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>Test for the avatar move back control.</string> - </map> - <key>CONTROL_DOWN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>Test for the avatar move down control.</string> - </map> - <key>CONTROL_FWD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Test for the avatar move forward control.</string> - </map> - <key>CONTROL_LBUTTON</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10000000</string> - <key>tooltip</key> - <string>Test for the avatar left button control.</string> - </map> - <key>CONTROL_LEFT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>Test for the avatar move left control.</string> - </map> - <key>CONTROL_ML_LBUTTON</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40000000</string> - <key>tooltip</key> - <string>Test for the avatar left button control while in mouse look.</string> - </map> - <key>CONTROL_RIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Test for the avatar move right control.</string> - </map> - <key>CONTROL_ROT_LEFT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string>Test for the avatar rotate left control.</string> - </map> - <key>CONTROL_ROT_RIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string>Test for the avatar rotate right control.</string> - </map> - <key>CONTROL_UP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>Test for the avatar move up control.</string> - </map> - <key>DATA_BORN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>The date the agent was born, returned in ISO 8601 format of YYYY-MM-DD.</string> - </map> - <key>DATA_NAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>The name of the agent.</string> - </map> - <key>DATA_ONLINE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>TRUE for online, FALSE for offline.</string> - </map> - <key>DATA_PAYINFO</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>DATA_RATING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Returns the agent ratings as a comma separated string of six integers. They are: - 1) Positive rated behaviour - 2) Negative rated behaviour - 3) Positive rated appearance - 4) Negative rated appearance - 5) Positive rated building - 6) Negative rated building</string> - </map> - <key>DATA_SIM_POS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>DATA_SIM_RATING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>DATA_SIM_STATUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>DEBUG_CHANNEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2147483647</integer> - <key>tooltip</key> - <string>DEBUG_CHANNEL is an integer constant that, when passed to llSay, llWhisper, or llShout as a channel parameter, will print text to the Script Warning/Error Window.</string> - </map> - <key>DEG_TO_RAD</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>0.017453293</real> - <key>tooltip</key> - <string>0.017453293 - Number of radians per degree. - You can use this to convert degrees to radians by multiplying the degrees by this number.</string> - </map> - <key>DENSITY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Used with llSetPhysicsMaterial to enable the density value. Must be between 1.0 and 22587.0 (in Kg/m^3 -- see if you can figure out what 22587 represents)</string> - </map> - <key>EOF</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>\\n\\n\\n</string> - <key>tooltip</key> - <string>Indicates the last line of a notecard was read.</string> - </map> - <key>ERR_GENERIC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>ERR_MALFORMED_PARAMS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-3</integer> - <key>tooltip</key> - <string/> - </map> - <key>ERR_PARCEL_PERMISSIONS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-2</integer> - <key>tooltip</key> - <string/> - </map> - <key>ERR_RUNTIME_PERMISSIONS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-4</integer> - <key>tooltip</key> - <string/> - </map> - <key>ERR_THROTTLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-5</integer> - <key>tooltip</key> - <string/> - </map> - <key>ESTATE_ACCESS_ALLOWED_AGENT_ADD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Add the agent to this estate's Allowed Residents list.</string> - </map> - <key>ESTATE_ACCESS_ALLOWED_AGENT_REMOVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>Remove the agent from this estate's Allowed Residents list.</string> - </map> - <key>ESTATE_ACCESS_ALLOWED_GROUP_ADD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string>Add the group to this estate's Allowed groups list.</string> - </map> - <key>ESTATE_ACCESS_ALLOWED_GROUP_REMOVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>32</integer> - <key>tooltip</key> - <string>Remove the group from this estate's Allowed groups list.</string> - </map> - <key>ESTATE_ACCESS_BANNED_AGENT_ADD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>64</integer> - <key>tooltip</key> - <string>Add the agent to this estate's Banned residents list.</string> - </map> - <key>ESTATE_ACCESS_BANNED_AGENT_REMOVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>128</integer> - <key>tooltip</key> - <string>Remove the agent from this estate's Banned residents list.</string> - </map> - <key>FALSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>An integer constant for boolean comparisons. Has the value '0'.</string> - </map> - <key>FORCE_DIRECT_PATH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Makes character navigate in a straight line toward position. May be set to TRUE or FALSE.</string> - </map> - <key>FRICTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Used with llSetPhysicsMaterial to enable the friction value. Must be between 0.0 and 255.0</string> - </map> - <key>GCNP_RADIUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>GCNP_STATIC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>GRAVITY_MULTIPLIER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>Used with llSetPhysicsMaterial to enable the gravity multiplier value. Must be between -1.0 and +28.0</string> - </map> - <key>HORIZONTAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_BODY_MAXLENGTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_BODY_TRUNCATED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_CUSTOM_HEADER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Add an extra custom HTTP header to the request. The first string is the name of the parameter to change, e.g. "Pragma", and the second string is the value, e.g. "no-cache". Up to 8 custom headers may be configured per request. Note that certain headers, such as the default headers, are blocked for security reasons.</string> - </map> - <key>HTTP_METHOD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_MIMETYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_PRAGMA_NO_CACHE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Allows enabling/disbling of the "Pragma: no-cache" header.\nUsage: [HTTP_PRAGMA_NO_CACHE, integer SendHeader]. When SendHeader is TRUE, the "Pragma: no-cache" header is sent by the script. This matches the default behavior. When SendHeader is FALSE, no "Pragma" header is sent by the script.</string> - </map> - <key>HTTP_VERBOSE_THROTTLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>HTTP_VERIFY_CERT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_ALL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_ANIMATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_BODYPART</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_CLOTHING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_GESTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_LANDMARK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_NOTECARD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_OBJECT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_SCRIPT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_SETTING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>56</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_SOUND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_TEXTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>INVENTORY_MATERIAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>57</integer> - <key>tooltip</key> - <string/> - </map> - <key>JSON_APPEND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>JSON_ARRAY</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD2</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_DELETE</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD8</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_FALSE</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD7</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_INVALID</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD0</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_NULL</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD5</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_NUMBER</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD3</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_OBJECT</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD1</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_STRING</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD4</string> - <key>tooltip</key> - <string/> - </map> - <key>JSON_TRUE</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>U+FDD6</string> - <key>tooltip</key> - <string/> - </map> - <key>KFM_CMD_PAUSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>For use with KFM_COMMAND.</string> - </map> - <key>KFM_CMD_PLAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>For use with KFM_COMMAND.</string> - </map> - <key>KFM_CMD_STOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>For use with KFM_COMMAND.</string> - </map> - <key>KFM_COMMAND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>KFM_DATA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>KFM_FORWARD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>For use with KFM_MODE.</string> - </map> - <key>KFM_LOOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>For use with KFM_MODE.</string> - </map> - <key>KFM_MODE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>KFM_PING_PONG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>For use with KFM_MODE.</string> - </map> - <key>KFM_REVERSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>For use with KFM_MODE.</string> - </map> - <key>KFM_ROTATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>For use with KFM_DATA.</string> - </map> - <key>KFM_TRANSLATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>For use with KFM_DATA.</string> - </map> - <key>LAND_LARGE_BRUSH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Use a large brush size.\nNOTE: This value is incorrect, a large brush should be 2.</string> - </map> - <key>LAND_LEVEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Action to level the land.</string> - </map> - <key>LAND_LOWER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Action to lower the land.</string> - </map> - <key>LAND_MEDIUM_BRUSH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Use a medium brush size.\nNOTE: This value is incorrect, a medium brush should be 1.</string> - </map> - <key>LAND_NOISE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>LAND_RAISE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Action to raise the land.</string> - </map> - <key>LAND_REVERT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>LAND_SMALL_BRUSH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Use a small brush size.\nNOTE: This value is incorrect, a small brush should be 0.</string> - </map> - <key>LAND_SMOOTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>LINK_ALL_CHILDREN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-3</integer> - <key>tooltip</key> - <string>This targets every object except the root in the linked set.</string> - </map> - <key>LINK_ALL_OTHERS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-2</integer> - <key>tooltip</key> - <string>This targets every object in the linked set except the object with the script.</string> - </map> - <key>LINK_ROOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>This targets the root of the linked set.</string> - </map> - <key>LINK_SET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string>This targets every object in the linked set.</string> - </map> - <key>LINK_THIS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-4</integer> - <key>tooltip</key> - <string>The link number of the prim containing the script.</string> - </map> - <key>LIST_STAT_GEOMETRIC_MEAN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_MAX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_MEAN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_MEDIAN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_MIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_NUM_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_RANGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_STD_DEV</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_SUM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>LIST_STAT_SUM_SQUARES</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>LOOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>Loop the texture animation.</string> - </map> - <key>MASK_BASE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>MASK_EVERYONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>MASK_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>MASK_NEXT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>MASK_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>NULL_KEY</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>00000000-0000-0000-0000-000000000000</uuid> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_ATTACHED_POINT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>19</integer> - <key>tooltip</key> - <string>Gets the attachment point to which the object is attached.\nReturns 0 if the object is not an attachment (or is an avatar, etc).</string> - </map> - <key>OBJECT_BODY_SHAPE_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>26</integer> - <key>tooltip</key> - <string>This is a flag used with llGetObjectDetails to get the body type of the avatar, based on shape data.\nIf no data is available, -1.0 is returned.\nThis is normally between 0 and 1.0, with 0.5 and larger considered 'male'</string> - </map> - <key>OBJECT_CHARACTER_TIME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string>Units in seconds</string> - </map> - <key>OBJECT_CLICK_ACTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>28</integer> - <key>tooltip</key> - <string>This is a flag used with llGetObjectDetails to get the click action.\nThe default is 0</string> - </map> - <key>OBJECT_CREATOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>Gets the object's creator key. If id is an avatar, a NULL_KEY is returned.</string> - </map> - <key>OBJECT_DESC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Gets the object's description. If id is an avatar, an empty string is returned.</string> - </map> - <key>OBJECT_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>Gets the prims's group key. If id is an avatar, a NULL_KEY is returned.</string> - </map> - <key>OBJECT_HOVER_HEIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>25</integer> - <key>tooltip</key> - <string>This is a flag used with llGetObjectDetails to get hover height of the avatar\nIf no data is available, 0.0 is returned.</string> - </map> - <key>OBJECT_LAST_OWNER_ID</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>27</integer> - <key>tooltip</key> - <string>Gets the object's last owner ID.</string> - </map> - <key>OBJECT_NAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Gets the object's name.</string> - </map> - <key>OBJECT_OMEGA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>29</integer> - <key>tooltip</key> - <string>Gets an object's angular velocity.</string> - </map> - <key>OBJECT_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Gets an object's owner's key. If id is group owned, a NULL_KEY is returned.</string> - </map> - <key>OBJECT_PRIM_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>30</integer> - <key>tooltip</key> - <string>Gets the prim count of the object. The script and target object must be owned by the same owner</string> - </map> - <key>OBJECT_PATHFINDING_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string>Returns the pathfinding setting of any object in the region. It returns an integer matching one of the OPT_* constants.</string> - </map> - <key>OBJECT_PHANTOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>22</integer> - <key>tooltip</key> - <string>Returns boolean, detailing if phantom is enabled or disabled on the object.\nIf id is an avatar or attachment, 0 is returned.</string> - </map> - <key>OBJECT_PHYSICS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string>Returns boolean, detailing if physics is enabled or disabled on the object.\nIf id is an avatar or attachment, 0 is returned.</string> - </map> - <key>OBJECT_PHYSICS_COST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_POS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Gets the object's position in region coordinates.</string> - </map> - <key>OBJECT_PRIM_EQUIVALENCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_RENDER_WEIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>24</integer> - <key>tooltip</key> - <string>This is a flag used with llGetObjectDetails to get the Avatar_Rendering_Cost of an avatar, based on values reported by nearby viewers.\nIf no data is available, -1 is returned.\nThe maximum render weight stored by the simulator is 500000. When called against an object, 0 is returned.</string> - </map> - <key>OBJECT_RETURN_PARCEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_RETURN_PARCEL_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_RETURN_REGION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_REZZER_KEY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>32</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_ROOT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>18</integer> - <key>tooltip</key> - <string>Gets the id of the root prim of the object requested.\nIf id is an avatar, return the id of the root prim of the linkset the avatar is sitting on (or the avatar's own id if the avatar is not sitting on an object within the region).</string> - </map> - <key>OBJECT_ROT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Gets the object's rotation.</string> - </map> - <key>OBJECT_RUNNING_SCRIPT_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_SCRIPT_MEMORY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_SCRIPT_TIME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_SERVER_COST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_STREAMING_COST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_TEMP_ON_REZ</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>23</integer> - <key>tooltip</key> - <string>Returns boolean, detailing if temporary is enabled or disabled on the object.</string> - </map> - <key>OBJECT_TOTAL_INVENTORY_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>31</integer> - <key>tooltip</key> - <string>Gets the total inventory count of the object. The script and target object must be owned by the same owner</string> - </map> - <key>OBJECT_TOTAL_SCRIPT_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_UNKNOWN_DETAIL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>OBJECT_VELOCITY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Gets the object's velocity.</string> - </map> - <key>OPT_AVATAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Returned for avatars.</string> - </map> - <key>OPT_CHARACTER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Returned for pathfinding characters.</string> - </map> - <key>OPT_EXCLUSION_VOLUME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Returned for exclusion volumes.</string> - </map> - <key>OPT_LEGACY_LINKSET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Returned for movable obstacles, movable phantoms, physical, and volumedetect objects.</string> - </map> - <key>OPT_MATERIAL_VOLUME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Returned for material volumes.</string> - </map> - <key>OPT_OTHER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string>Returned for attachments, Linden trees, and grass.</string> - </map> - <key>OPT_STATIC_OBSTACLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Returned for static obstacles.</string> - </map> - <key>OPT_WALKABLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Returned for walkable objects.</string> - </map> - <key>PARCEL_COUNT_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_COUNT_OTHER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_COUNT_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_COUNT_SELECTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_COUNT_TEMP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_COUNT_TOTAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_DETAILS_AREA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>The parcel's area, in square meters. (5 chars.).</string> - </map> - <key>PARCEL_DETAILS_DESC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>The description of the parcel. (127 chars).</string> - </map> - <key>PARCEL_DETAILS_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>The parcel group's key. (36 chars.).</string> - </map> - <key>PARCEL_DETAILS_ID</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>The parcel's key. (36 chars.).</string> - </map> - <key>PARCEL_DETAILS_NAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>The name of the parcel. (63 chars.).</string> - </map> - <key>PARCEL_DETAILS_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>The parcel owner's key. (36 chars.).</string> - </map> - <key>PARCEL_DETAILS_SEE_AVATARS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>The parcel's avatar visibility setting. (1 char.).</string> - </map> - <key>PARCEL_FLAG_ALLOW_ALL_OBJECT_ENTRY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x08000000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_CREATE_GROUP_OBJECTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4000000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_CREATE_OBJECTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_DAMAGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_FLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_GROUP_OBJECT_ENTRY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10000000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_GROUP_SCRIPTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2000000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_LANDMARK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_SCRIPTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_ALLOW_TERRAFORM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_LOCAL_SOUND_ONLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_RESTRICT_PUSHOBJECT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200000</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_USE_ACCESS_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_USE_ACCESS_LIST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_USE_BAN_LIST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_FLAG_USE_LAND_PASS_LIST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x800</string> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_AGENT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_AUTO_ALIGN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_DESC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>Use this to get or set the parcel media description.</string> - </map> - <key>PARCEL_MEDIA_COMMAND_LOOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_LOOP_SET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>Used to get or set the parcel's media looping variable.</string> - </map> - <key>PARCEL_MEDIA_COMMAND_PAUSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_PLAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_SIZE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string>Use this to get or set the parcel media pixel resolution.</string> - </map> - <key>PARCEL_MEDIA_COMMAND_STOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_TEXTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_TIME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>Use this to get or set the parcel media MIME type (e.g. "text/html").</string> - </map> - <key>PARCEL_MEDIA_COMMAND_UNLOAD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>PARCEL_MEDIA_COMMAND_URL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PASS_ALWAYS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>1</string> - <key>tooltip</key> - <string>Always pass the event.</string> - </map> - <key>PASS_NEVER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>2</string> - <key>tooltip</key> - <string>Always pass the event.</string> - </map> - <key>PASS_IF_NOT_HANDLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0</string> - <key>tooltip</key> - <string>Pass the event if there is no script handling the event in the prim.</string> - </map> - <key>PASSIVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>Static in-world objects.</string> - </map> - <key>PATROL_PAUSE_AT_WAYPOINTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PAY_DEFAULT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PAY_HIDE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PAYMENT_INFO_ON_FILE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PAYMENT_INFO_USED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PERM_ALL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x7FFFFFFF</string> - <key>tooltip</key> - <string/> - </map> - <key>PERM_COPY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8000</string> - <key>tooltip</key> - <string/> - </map> - <key>PERM_MODIFY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4000</string> - <key>tooltip</key> - <string/> - </map> - <key>PERM_MOVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80000</string> - <key>tooltip</key> - <string/> - </map> - <key>PERM_TRANSFER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2000</string> - <key>tooltip</key> - <string/> - </map> - <key>PERMISSION_ATTACH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>If this permission is enabled, the object can successfully call llAttachToAvatar to attach to the given avatar.</string> - </map> - <key>PERMISSION_CHANGE_JOINTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string>(not yet implemented)</string> - </map> - <key>PERMISSION_CHANGE_LINKS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string>If this permission is enabled, the object can successfully call llCreateLink, llBreakLink, and llBreakAllLinks to change links to other objects.</string> - </map> - <key>PERMISSION_CHANGE_PERMISSIONS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string>(not yet implemented)</string> - </map> - <key>PERMISSION_CONTROL_CAMERA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x800</string> - <key>tooltip</key> - <string/> - </map> - <key>PERMISSION_DEBIT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>If this permission is enabled, the object can successfully call llGiveMoney or llTransferLindenDollars to debit the owners account.</string> - </map> - <key>PERMISSION_OVERRIDE_ANIMATIONS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8000</string> - <key>tooltip</key> - <string>Permission to override default animations.</string> - </map> - <key>PERMISSION_RELEASE_OWNERSHIP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>(not yet implemented)</string> - </map> - <key>PERMISSION_REMAP_CONTROLS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>(not yet implemented)</string> - </map> - <key>PERMISSION_RETURN_OBJECTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>65536</integer> - <key>tooltip</key> - <string/> - </map> - <key>PERMISSION_SILENT_ESTATE_MANAGEMENT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4000</string> - <key>tooltip</key> - <string>A script with this permission does not notify the object owner when it modifies estate access rules via llManageEstateAccess.</string> - </map> - <key>PERMISSION_TAKE_CONTROLS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>If this permission enabled, the object can successfully call the llTakeControls libray call.</string> - </map> - <key>PERMISSION_TELEPORT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1000</string> - <key>tooltip</key> - <string/> - </map> - <key>PERMISSION_TRACK_CAMERA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string/> - </map> - <key>PERMISSION_TRIGGER_ANIMATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>If this permission is enabled, the object can successfully call llStartAnimation for the avatar that owns this.</string> - </map> - <key>PI</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>3.14159265</real> - <key>tooltip</key> - <string>3.14159265 - The number of radians in a semi-circle.</string> - </map> - <key>PI_BY_TWO</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>1.57079633</real> - <key>tooltip</key> - <string>1.57079633 - The number of radians in a quarter circle.</string> - </map> - <key>PING_PONG</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Play animation going forwards, then backwards.</string> - </map> - <key>PRIM_ALPHA_MODE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>38</integer> - <key>tooltip</key> - <string>Prim parameter for materials using integer face, integer alpha_mode, integer alpha_cutoff.\nDefines how the alpha channel of the diffuse texture should be rendered.\nValid options for alpha_mode are PRIM_ALPHA_MODE_BLEND, _NONE, _MASK, and _EMISSIVE.\nalpha_cutoff is used only for PRIM_ALPHA_MODE_MASK.</string> - </map> - <key>PRIM_ALPHA_MODE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Prim parameter setting for PRIM_ALPHA_MODE.\nIndicates that the diffuse texture's alpha channel should be ignored.</string> - </map> - <key>PRIM_ALPHA_MODE_BLEND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Prim parameter setting for PRIM_ALPHA_MODE.\nIndicates that the diffuse texture's alpha channel should be rendered as alpha-blended.</string> - </map> - <key>PRIM_ALPHA_MODE_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Prim parameter setting for PRIM_ALPHA_MODE.\nIndicates that the diffuse texture's alpha channel should be rendered as fully opaque for alpha values above alpha_cutoff and fully transparent otherwise.</string> - </map> - <key>PRIM_ALPHA_MODE_EMISSIVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Prim parameter setting for PRIM_ALPHA_MODE.\nIndicates that the diffuse texture's alpha channel should be rendered as an emissivity mask.</string> - </map> - <key>PRIM_BUMP_BARK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_BLOBS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_BRICKS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_BRIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_CHECKER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_CONCRETE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_DARK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_DISKS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_GRAVEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_LARGETILE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_SHINY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>19</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_SIDING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_STONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_STUCCO</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_SUCTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_TILE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_WEAVE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_BUMP_WOOD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_CAST_SHADOWS</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>24</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>18</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_DESC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>28</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_FLEXIBLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_FULLBRIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_GLOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>25</integer> - <key>tooltip</key> - <string>PRIM_GLOW is used to get or set the glow status of the face.</string> - </map> - <key>PRIM_HOLE_CIRCLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_HOLE_DEFAULT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x00</string> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_HOLE_SQUARE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_HOLE_TRIANGLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x30</string> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_LINK_TARGET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>34</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_FLESH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_GLASS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_LIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_METAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_PLASTIC</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_RUBBER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_STONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MATERIAL_WOOD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_ALT_IMAGE_ENABLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets the default image state (the image that the user sees before a piece of media is active) for the chosen face. The default image is specified by Second Life's server for that media type.</string> - </map> - <key>PRIM_MEDIA_AUTO_LOOP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether auto-looping is enabled.</string> - </map> - <key>PRIM_MEDIA_AUTO_PLAY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether the media auto-plays when a Resident can view it.</string> - </map> - <key>PRIM_MEDIA_AUTO_SCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether auto-scaling is enabled. Auto-scaling forces the media to the full size of the texture.</string> - </map> - <key>PRIM_MEDIA_AUTO_ZOOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether clicking the media triggers auto-zoom and auto-focus on the media.</string> - </map> - <key>PRIM_MEDIA_CONTROLS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Integer. Gets/Sets the style of controls. Can be either PRIM_MEDIA_CONTROLS_STANDARD or PRIM_MEDIA_CONTROLS_MINI.</string> - </map> - <key>PRIM_MEDIA_CONTROLS_MINI</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Mini web navigation controls; does not include an address bar.</string> - </map> - <key>PRIM_MEDIA_CONTROLS_STANDARD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Standard web navigation controls.</string> - </map> - <key>PRIM_MEDIA_CURRENT_URL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>String. Gets/Sets the current url displayed on the chosen face. Changing this URL causes navigation. 1024 characters Maximum.</string> - </map> - <key>PRIM_MEDIA_FIRST_CLICK_INTERACT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether the first click interaction is enabled.</string> - </map> - <key>PRIM_MEDIA_HEIGHT_PIXELS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>Integer. Gets/Sets the height of the media in pixels.</string> - </map> - <key>PRIM_MEDIA_HOME_URL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>String. Gets/Sets the home URL for the chosen face. 1024 characters maximum.</string> - </map> - <key>PRIM_MEDIA_MAX_HEIGHT_PIXELS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2048</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_MAX_URL_LENGTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1024</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_MAX_WHITELIST_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>64</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_MAX_WHITELIST_SIZE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1024</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_MAX_WIDTH_PIXELS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2048</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PARAM_MAX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PERM_ANYONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PERM_GROUP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PERM_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PERM_OWNER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_MEDIA_PERMS_CONTROL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string>Integer. Gets/Sets the permissions mask that control who can see the media control bar above the object:: PRIM_MEDIA_PERM_ANYONE, PRIM_MEDIA_PERM_GROUP, PRIM_MEDIA_PERM_NONE, PRIM_MEDIA_PERM_OWNER</string> - </map> - <key>PRIM_MEDIA_PERMS_INTERACT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>Integer. Gets/Sets the permissions mask that control who can interact with the object: PRIM_MEDIA_PERM_ANYONE, PRIM_MEDIA_PERM_GROUP, PRIM_MEDIA_PERM_NONE, PRIM_MEDIA_PERM_OWNER</string> - </map> - <key>PRIM_MEDIA_WHITELIST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>String. Gets/Sets the white-list as a string of escaped, comma-separated URLs. This string can hold up to 64 URLs or 1024 characters, whichever comes first.</string> - </map> - <key>PRIM_MEDIA_WHITELIST_ENABLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string>Boolean. Gets/Sets whether navigation is restricted to URLs in PRIM_MEDIA_WHITELIST.</string> - </map> - <key>PRIM_MEDIA_WIDTH_PIXELS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string>Integer. Gets/Sets the width of the media in pixels.</string> - </map> - <key>PRIM_NAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>27</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_NORMAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>37</integer> - <key>tooltip</key> - <string>Prim parameter for materials using integer face, string texture, vector repeats, vector offsets, float rotation_in_radians</string> - </map> - <key>PRIM_OMEGA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>32</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_PHANTOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_PHYSICS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_PHYSICS_SHAPE_CONVEX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Use the convex hull of the prim shape for physics (this is the default for mesh objects).</string> - </map> - <key>PRIM_PHYSICS_SHAPE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Ignore this prim in the physics shape. NB: This cannot be applied to the root prim.</string> - </map> - <key>PRIM_PHYSICS_SHAPE_PRIM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Use the normal prim shape for physics (this is the default for all non-mesh objects).</string> - </map> - <key>PRIM_PHYSICS_SHAPE_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>30</integer> - <key>tooltip</key> - <string>Allows you to set the physics shape type of a prim via lsl. Permitted values are: - PRIM_PHYSICS_SHAPE_NONE, PRIM_PHYSICS_SHAPE_PRIM, PRIM_PHYSICS_SHAPE_CONVEX</string> - </map> - <key>PRIM_POINT_LIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>23</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_POS_LOCAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>33</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_POSITION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_ROT_LOCAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>29</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_ROTATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SCULPT_FLAG_INVERT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>64</integer> - <key>tooltip</key> - <string>Render inside out (inverts the normals).</string> - </map> - <key>PRIM_SCULPT_FLAG_MIRROR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>128</integer> - <key>tooltip</key> - <string>Render an X axis mirror of the sculpty.</string> - </map> - <key>PRIM_SCULPT_TYPE_CYLINDER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SCULPT_TYPE_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SCULPT_TYPE_PLANE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SCULPT_TYPE_SPHERE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SCULPT_TYPE_TORUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SHINY_HIGH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SHINY_LOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SHINY_MEDIUM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SHINY_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SIZE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SLICE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>35</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_SPECULAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>36</integer> - <key>tooltip</key> - <string>Prim parameter for materials using integer face, string texture, vector repeats, vector offsets, float rotation_in_radians, vector color, integer glossy, integer environment</string> - </map> - <key>PRIM_TEMP_ON_REZ</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TEXGEN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>22</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TEXGEN_DEFAULT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TEXGEN_PLANAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TEXT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>26</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TEXTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_BOX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_CYLINDER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_PRISM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_RING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_SCULPT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_SPHERE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_TORUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PRIM_TYPE_TUBE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PROFILE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Disables profiling</string> - </map> - <key>PROFILE_SCRIPT_MEMORY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Enables memory profiling</string> - </map> - <key>PSYS_PART_BF_DEST_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_ONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_ONE_MINUS_DEST_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_ONE_MINUS_SOURCE_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_ONE_MINUS_SOURCE_ALPHA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_SOURCE_ALPHA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_SOURCE_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BF_ZERO</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BLEND_FUNC_DEST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>25</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BLEND_FUNC_SOURCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>24</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_BOUNCE_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>Particles bounce off of a plane at the objects Z height.</string> - </map> - <key>PSYS_PART_EMISSIVE_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string>The particle glows.</string> - </map> - <key>PSYS_PART_END_ALPHA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>A float which determines the ending alpha of the object.</string> - </map> - <key>PSYS_PART_END_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>A vector <r, g, b> which determines the ending color of the object.</string> - </map> - <key>PSYS_PART_END_GLOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>27</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_END_SCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>A vector <sx, sy, z>, which is the ending size of the particle billboard in meters (z is ignored).</string> - </map> - <key>PSYS_PART_FLAGS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Each particle that is emitted by the particle system is simulated based on the following flags. To use multiple flags, bitwise or (|) them together.</string> - </map> - <key>PSYS_PART_FOLLOW_SRC_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>The particle position is relative to the source objects position.</string> - </map> - <key>PSYS_PART_FOLLOW_VELOCITY_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>The particle orientation is rotated so the vertical axis faces towards the particle velocity.</string> - </map> - <key>PSYS_PART_INTERP_COLOR_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Interpolate both the color and alpha from the start value to the end value.</string> - </map> - <key>PSYS_PART_INTERP_SCALE_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>Interpolate the particle scale from the start value to the end value.</string> - </map> - <key>PSYS_PART_MAX_AGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>Age in seconds of a particle at which it dies.</string> - </map> - <key>PSYS_PART_RIBBON_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_START_ALPHA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>A float which determines the starting alpha of the object.</string> - </map> - <key>PSYS_PART_START_COLOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>A vector <r.r, g.g, b.b> which determines the starting color of the object.</string> - </map> - <key>PSYS_PART_START_GLOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>26</integer> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_START_SCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>A vector <sx, sy, z>, which is the starting size of the particle billboard in meters (z is ignored).</string> - </map> - <key>PSYS_PART_TARGET_LINEAR_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_PART_TARGET_POS_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>The particle heads towards the location of the target object as defined by PSYS_SRC_TARGET_KEY.</string> - </map> - <key>PSYS_PART_WIND_MASK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Particles have their velocity damped towards the wind velocity.</string> - </map> - <key>PSYS_SRC_ACCEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>A vector <x, y, z> which is the acceleration to apply on particles.</string> - </map> - <key>PSYS_SRC_ANGLE_BEGIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>22</integer> - <key>tooltip</key> - <string>Area in radians specifying where particles will NOT be created (for ANGLE patterns)</string> - </map> - <key>PSYS_SRC_ANGLE_END</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>23</integer> - <key>tooltip</key> - <string>Area in radians filled with particles (for ANGLE patterns) (if lower than PSYS_SRC_ANGLE_BEGIN, acts as PSYS_SRC_ANGLE_BEGIN itself, and PSYS_SRC_ANGLE_BEGIN acts as PSYS_SRC_ANGLE_END).</string> - </map> - <key>PSYS_SRC_BURST_PART_COUNT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string>How many particles to release in a burst.</string> - </map> - <key>PSYS_SRC_BURST_RADIUS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string>What distance from the center of the object to create the particles.</string> - </map> - <key>PSYS_SRC_BURST_RATE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>How often to release a particle burst (float seconds).</string> - </map> - <key>PSYS_SRC_BURST_SPEED_MAX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>18</integer> - <key>tooltip</key> - <string>Maximum speed that a particle should be moving.</string> - </map> - <key>PSYS_SRC_BURST_SPEED_MIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string>Minimum speed that a particle should be moving.</string> - </map> - <key>PSYS_SRC_INNERANGLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>Specifies the inner angle of the arc created by the PSYS_SRC_PATTERN_ANGLE or PSYS_SRC_PATTERN_ANGLE_CONE source pattern. - The area specified will NOT have particles in it.</string> - </map> - <key>PSYS_SRC_MAX_AGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>19</integer> - <key>tooltip</key> - <string>How long this particle system should last, 0.0 means forever.</string> - </map> - <key>PSYS_SRC_OMEGA</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>21</integer> - <key>tooltip</key> - <string>Sets the angular velocity to rotate the axis that SRC_PATTERN_ANGLE and SRC_PATTERN_ANGLE_CONE use.</string> - </map> - <key>PSYS_SRC_OUTERANGLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string>Specifies the outer angle of the arc created by the PSYS_SRC_PATTERN_ANGLE or PSYS_SRC_PATTERN_ANGLE_CONE source pattern. - The area between the outer and inner angle will be filled with particles.</string> - </map> - <key>PSYS_SRC_PATTERN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string>The pattern which is used to generate particles. - Use one of the following values: PSYS_SRC_PATTERN Values.</string> - </map> - <key>PSYS_SRC_PATTERN_ANGLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x04</string> - <key>tooltip</key> - <string>Shoot particles across a 2 dimensional area defined by the arc created from PSYS_SRC_OUTERANGLE. There will be an open area defined by PSYS_SRC_INNERANGLE within the larger arc.</string> - </map> - <key>PSYS_SRC_PATTERN_ANGLE_CONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x08</string> - <key>tooltip</key> - <string>Shoot particles out in a 3 dimensional cone with an outer arc of PSYS_SRC_OUTERANGLE and an inner open area defined by PSYS_SRC_INNERANGLE.</string> - </map> - <key>PSYS_SRC_PATTERN_ANGLE_CONE_EMPTY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>PSYS_SRC_PATTERN_DROP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x01</string> - <key>tooltip</key> - <string>Drop particles at the source position.</string> - </map> - <key>PSYS_SRC_PATTERN_EXPLODE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x02</string> - <key>tooltip</key> - <string>Shoot particles out in all directions, using the burst parameters.</string> - </map> - <key>PSYS_SRC_TARGET_KEY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string>The key of a target object to move towards if PSYS_PART_TARGET_POS_MASK is enabled.</string> - </map> - <key>PSYS_SRC_TEXTURE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>An asset name for the texture to use for the particles.</string> - </map> - <key>PU_EVADE_HIDDEN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x07</string> - <key>tooltip</key> - <string>Triggered when an llEvade character thinks it has hidden from its pursuer.</string> - </map> - <key>PU_EVADE_SPOTTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x08</string> - <key>tooltip</key> - <string>Triggered when an llEvade character switches from hiding to running</string> - </map> - <key>PU_FAILURE_DYNAMIC_PATHFINDING_DISABLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string/> - </map> - <key>PU_FAILURE_INVALID_GOAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x03</string> - <key>tooltip</key> - <string>Goal is not on the navigation-mesh and cannot be reached.</string> - </map> - <key>PU_FAILURE_INVALID_START</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x02</string> - <key>tooltip</key> - <string>Character cannot navigate from the current location - e.g., the character is off the navmesh or too high above it.</string> - </map> - <key>PU_FAILURE_NO_NAVMESH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x09</string> - <key>tooltip</key> - <string>This is a fatal error reported to a character when there is no navmesh for the region. This usually indicates a server failure and users should file a bug report and include the time and region in which they received this message.</string> - </map> - <key>PU_FAILURE_NO_VALID_DESTINATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x06</string> - <key>tooltip</key> - <string>There is no good place for the character to go - e.g., it is patrolling and all the patrol points are now unreachable.</string> - </map> - <key>PU_FAILURE_OTHER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1000000</integer> - <key>tooltip</key> - <string/> - </map> - <key>PU_FAILURE_PARCEL_UNREACHABLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string/> - </map> - <key>PU_FAILURE_TARGET_GONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x05</string> - <key>tooltip</key> - <string>Target (for llPursue or llEvade) can no longer be tracked - e.g., it left the region or is an avatar that is now more than about 30m outside the region.</string> - </map> - <key>PU_FAILURE_UNREACHABLE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x04</string> - <key>tooltip</key> - <string>Goal is no longer reachable for some reason - e.g., an obstacle blocks the path.</string> - </map> - <key>PU_GOAL_REACHED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x01</string> - <key>tooltip</key> - <string>Character has reached the goal and will stop or choose a new goal (if wandering).</string> - </map> - <key>PU_SLOWDOWN_DISTANCE_REACHED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x00</string> - <key>tooltip</key> - <string>Character is near current goal.</string> - </map> - <key>PUBLIC_CHANNEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>PUBLIC_CHANNEL is an integer constant that, when passed to llSay, llWhisper, or llShout as a channel parameter, will print text to the publicly heard chat channel.</string> - </map> - <key>PURSUIT_FUZZ_FACTOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Selects a random destination near the offset.</string> - </map> - <key>PURSUIT_GOAL_TOLERANCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string/> - </map> - <key>PURSUIT_INTERCEPT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Define whether the character attempts to predict the target's location.</string> - </map> - <key>PURSUIT_OFFSET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Go to a position offset from the target.</string> - </map> - <key>RAD_TO_DEG</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>57.2957795</real> - <key>tooltip</key> - <string>57.2957795 - Number of degrees per radian. You can use this number to convert radians to degrees by multiplying the radians by this number.</string> - </map> - <key>RC_DATA_FLAGS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_DETECT_PHANTOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_GET_LINK_NUM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_GET_NORMAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_GET_ROOT_KEY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_MAX_HITS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_REJECT_AGENTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_REJECT_LAND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_REJECT_NONPHYSICAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_REJECT_PHYSICAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>RC_REJECT_TYPES</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>RCERR_CAST_TIME_EXCEEDED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-3</integer> - <key>tooltip</key> - <string/> - </map> - <key>RCERR_SIM_PERF_LOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-2</integer> - <key>tooltip</key> - <string/> - </map> - <key>RCERR_UNKNOWN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>-1</integer> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_ALLOW_DAMAGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_ALLOW_DIRECT_TELEPORT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_BLOCK_FLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_BLOCK_FLYOVER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8000000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_BLOCK_TERRAFORM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_DISABLE_COLLISIONS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_DISABLE_PHYSICS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_FIXED_SUN</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_RESTRICT_PUSHOBJECT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400000</string> - <key>tooltip</key> - <string/> - </map> - <key>REGION_FLAG_SANDBOX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>REMOTE_DATA_CHANNEL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>REMOTE_DATA_REPLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string/> - </map> - <key>REMOTE_DATA_REQUEST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>REQUIRE_LINE_OF_SIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Define whether the character needs a line-of-sight to give chase.</string> - </map> - <key>RESTITUTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Used with llSetPhysicsMaterial to enable the density value. Must be between 0.0 and 1.0</string> - </map> - <key>REVERSE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>Play animation in reverse direction.</string> - </map> - <key>ROTATE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>Animate texture rotation.</string> - </map> - <key>SCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>Animate the texture scale.</string> - </map> - <key>SCRIPTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Scripted in-world objects.</string> - </map> - <key>SIM_STAT_PCT_CHARS_STEPPED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Returns the % of pathfinding characters skipped each frame, averaged over the last minute.\nThe returned value corresponds to the "Characters Updated" stat in the viewer's Statistics Bar.</string> - </map> - <key>SMOOTH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>Slide in the X direction, instead of playing separate frames.</string> - </map> - <key>SQRT2</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>1.41421356</real> - <key>tooltip</key> - <string>1.41421356 - The square root of 2.</string> - </map> - <key>STATUS_BLOCK_GRAB</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>Controls whether the object can be grabbed.\nA grab is the default action when in third person, and is available as the hand tool in build mode. This is useful for physical objects that you don't want other people to be able to trivially disturb. The default is FALSE</string> - </map> - <key>STATUS_BLOCK_GRAB_OBJECT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x400</string> - <key>tooltip</key> - <string>Prevent click-and-drag movement on all prims in the object.</string> - </map> - <key>STATUS_BOUNDS_ERROR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1002</integer> - <key>tooltip</key> - <string>Argument(s) passed to function had a bounds error.</string> - </map> - <key>STATUS_CAST_SHADOWS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string/> - </map> - <key>STATUS_DIE_AT_EDGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string>Controls whether the object is returned to the owners inventory if it wanders off the edge of the world.\nIt is useful to set this status TRUE for things like bullets or rockets. The default is TRUE</string> - </map> - <key>STATUS_INTERNAL_ERROR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1999</integer> - <key>tooltip</key> - <string>An internal error occurred.</string> - </map> - <key>STATUS_MALFORMED_PARAMS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1000</integer> - <key>tooltip</key> - <string>Function was called with malformed parameters.</string> - </map> - <key>STATUS_NOT_FOUND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1003</integer> - <key>tooltip</key> - <string>Object or other item was not found.</string> - </map> - <key>STATUS_NOT_SUPPORTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1004</integer> - <key>tooltip</key> - <string>Feature not supported.</string> - </map> - <key>STATUS_OK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>Result of function call was a success.</string> - </map> - <key>STATUS_PHANTOM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>Controls/indicates whether the object collides or not.\nSetting the value to TRUE makes the object non-colliding with all objects. It is a good idea to use this for most objects that move or rotate, but are non-physical. It is also useful for simulating volumetric lighting. The default is FALSE.</string> - </map> - <key>STATUS_PHYSICS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Controls/indicates whether the object moves physically.\nThis controls the same flag that the UI check-box for Physical controls. The default is FALSE.</string> - </map> - <key>STATUS_RETURN_AT_EDGE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>STATUS_ROTATE_X</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string/> - </map> - <key>STATUS_ROTATE_Y</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string/> - </map> - <key>STATUS_ROTATE_Z</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Controls/indicates whether the object can physically rotate around - the specific axis or not. This flag has no meaning - for non-physical objects. Set the value to FALSE - if you want to disable rotation around that axis. The - default is TRUE for a physical object. - A useful example to think about when visualizing - the effect is a sit-and-spin device. They spin around the - Z axis (up) but not around the X or Y axis.</string> - </map> - <key>STATUS_SANDBOX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>Controls/indicates whether the object can cross region boundaries - and move more than 20 meters from its creation - point. The default if FALSE.</string> - </map> - <key>STATUS_TYPE_MISMATCH</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1001</integer> - <key>tooltip</key> - <string>Argument(s) passed to function had a type mismatch.</string> - </map> - <key>STATUS_WHITELIST_FAILED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2001</integer> - <key>tooltip</key> - <string>Whitelist Failed.</string> - </map> - <key>STRING_TRIM</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x03</string> - <key>tooltip</key> - <string/> - </map> - <key>STRING_TRIM_HEAD</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x01</string> - <key>tooltip</key> - <string/> - </map> - <key>STRING_TRIM_TAIL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x02</string> - <key>tooltip</key> - <string/> - </map> - <key>TEXTURE_BLANK</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>5748decc-f629-461c-9a36-a35a221fe21f</uuid> - <key>tooltip</key> - <string/> - </map> - <key>TEXTURE_DEFAULT</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>89556747-24cb-43ed-920b-47caed15465f</uuid> - <key>tooltip</key> - <string/> - </map> - <key>TEXTURE_MEDIA</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>8b5fec65-8d8d-9dc5-cda8-8fdf2716e361</uuid> - <key>tooltip</key> - <string/> - </map> - <key>TEXTURE_PLYWOOD</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>89556747-24cb-43ed-920b-47caed15465f</uuid> - <key>tooltip</key> - <string/> - </map> - <key>TEXTURE_TRANSPARENT</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <uuid>8dcd4a48-2d37-4909-9f78-f7a9eb4ef903</uuid> - <key>tooltip</key> - <string/> - </map> - <key>TOUCH_INVALID_FACE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0xFFFFFFFF</string> - <key>tooltip</key> - <string/> - </map> - <key>TOUCH_INVALID_TEXCOORD</key> - <map> - <key>type</key> - <string>vector</string> - <key>value</key> - <string><-1.0, -1.0, 0.0></string> - <key>tooltip</key> - <string/> - </map> - <key>TOUCH_INVALID_VECTOR</key> - <map> - <key>type</key> - <string>vector</string> - <key>value</key> - <string><0.0, 0.0, 0.0></string> - <key>tooltip</key> - <string/> - </map> - <key>TRAVERSAL_TYPE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>One of TRAVERSAL_TYPE_FAST, TRAVERSAL_TYPE_SLOW, and TRAVERSAL_TYPE_NONE.</string> - </map> - <key>TRAVERSAL_TYPE_FAST</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string/> - </map> - <key>TRAVERSAL_TYPE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string/> - </map> - <key>TRAVERSAL_TYPE_SLOW</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>TRUE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>An integer constant for boolean comparisons. Has the value '1'.</string> - </map> - <key>TWO_PI</key> - <map> - <key>type</key> - <string>float</string> - <key>value</key> - <real>6.28318530</real> - <key>tooltip</key> - <string>6.28318530 - The radians of a circle.</string> - </map> - <key>TYPE_FLOAT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>The list entry is a float.</string> - </map> - <key>TYPE_INTEGER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>The list entry is an integer.</string> - </map> - <key>TYPE_INVALID</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>The list entry is invalid.</string> - </map> - <key>TYPE_KEY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>The list entry is a key.</string> - </map> - <key>TYPE_ROTATION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>The list entry is a rotation.</string> - </map> - <key>TYPE_STRING</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>The list entry is a string.</string> - </map> - <key>TYPE_VECTOR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>The list entry is a vector.</string> - </map> - <key>URL_REQUEST_DENIED</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>URL_REQUEST_DENIED</string> - <key>tooltip</key> - <string/> - </map> - <key>URL_REQUEST_GRANTED</key> - <map> - <key>type</key> - <string>string</string> - <key>value</key> - <string>URL_REQUEST_GRANTED</string> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_ANGULAR_DEFLECTION_EFFICIENCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>32</integer> - <key>tooltip</key> - <string>A slider between minimum (0.0) and maximum (1.0) deflection of angular orientation. That is, its a simple scalar for modulating the strength of angular deflection such that the vehicles preferred axis of motion points toward its real velocity.</string> - </map> - <key>VEHICLE_ANGULAR_DEFLECTION_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>33</integer> - <key>tooltip</key> - <string>The time-scale for exponential success of linear deflection deflection. Its another way to specify the strength of the vehicles tendency to reorient itself so that its preferred axis of motion agrees with its true velocity.</string> - </map> - <key>VEHICLE_ANGULAR_FRICTION_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string>A vector of timescales for exponential decay of the vehicles angular velocity about its preferred axes of motion (at, left, up). - Range = [0.07, inf) seconds for each element of the vector.</string> - </map> - <key>VEHICLE_ANGULAR_MOTOR_DECAY_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>35</integer> - <key>tooltip</key> - <string>The timescale for exponential decay of the angular motors magnitude.</string> - </map> - <key>VEHICLE_ANGULAR_MOTOR_DIRECTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>19</integer> - <key>tooltip</key> - <string>The direction and magnitude (in preferred frame) of the vehicles angular motor.The vehicle will accelerate (or decelerate if necessary) to match its velocity to its motor.</string> - </map> - <key>VEHICLE_ANGULAR_MOTOR_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>34</integer> - <key>tooltip</key> - <string>The timescale for exponential approach to full angular motor velocity.</string> - </map> - <key>VEHICLE_BANKING_EFFICIENCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>38</integer> - <key>tooltip</key> - <string>A slider between anti (-1.0), none (0.0), and maxmum (1.0) banking strength.</string> - </map> - <key>VEHICLE_BANKING_MIX</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>39</integer> - <key>tooltip</key> - <string>A slider between static (0.0) and dynamic (1.0) banking. "Static" means the banking scales only with the angle of roll, whereas "dynamic" is a term that also scales with the vehicles linear speed.</string> - </map> - <key>VEHICLE_BANKING_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>40</integer> - <key>tooltip</key> - <string>The timescale for banking to exponentially approach its maximum effect. This is another way to scale the strength of the banking effect, however it affects the term that is proportional to the difference between what the banking behavior is trying to do, and what the vehicle is actually doing.</string> - </map> - <key>VEHICLE_BUOYANCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>27</integer> - <key>tooltip</key> - <string>A slider between minimum (0.0) and maximum anti-gravity (1.0).</string> - </map> - <key>VEHICLE_FLAG_CAMERA_DECOUPLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x200</string> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_FLAG_HOVER_GLOBAL_HEIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x10</string> - <key>tooltip</key> - <string>Hover at global height.</string> - </map> - <key>VEHICLE_FLAG_HOVER_TERRAIN_ONLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x8</string> - <key>tooltip</key> - <string>Ignore water height when hovering.</string> - </map> - <key>VEHICLE_FLAG_HOVER_UP_ONLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x20</string> - <key>tooltip</key> - <string>Hover does not push down. Use this flag for hovering vehicles that should be able to jump above their hover height.</string> - </map> - <key>VEHICLE_FLAG_HOVER_WATER_ONLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x4</string> - <key>tooltip</key> - <string>Ignore terrain height when hovering.</string> - </map> - <key>VEHICLE_FLAG_LIMIT_MOTOR_UP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x40</string> - <key>tooltip</key> - <string>Prevents ground vehicles from motoring into the sky.</string> - </map> - <key>VEHICLE_FLAG_LIMIT_ROLL_ONLY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x2</string> - <key>tooltip</key> - <string>For vehicles with vertical attractor that want to be able to climb/dive, for instance, aeroplanes that want to use the banking feature.</string> - </map> - <key>VEHICLE_FLAG_MOUSELOOK_BANK</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x100</string> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_FLAG_MOUSELOOK_STEER</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x80</string> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_FLAG_NO_DEFLECTION_UP</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>This flag prevents linear deflection parallel to world z-axis. This is useful for preventing ground vehicles with large linear deflection, like bumper cars, from climbing their linear deflection into the sky.</string> - </map> - <key>VEHICLE_FLAG_NO_FLY_UP</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>type</key> - <string>integer</string> - <key>value</key> - <string>0x1</string> - <key>tooltip</key> - <string>Old, changed to VEHICLE_FLAG_NO_DEFLECTION_UP</string> - </map> - <key>VEHICLE_HOVER_EFFICIENCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>25</integer> - <key>tooltip</key> - <string>A slider between minimum (0.0 = bouncy) and maximum (1.0 = fast as possible) damped motion of the hover behavior. </string> - </map> - <key>VEHICLE_HOVER_HEIGHT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>24</integer> - <key>tooltip</key> - <string>The height (above the terrain or water, or global) at which the vehicle will try to hover.</string> - </map> - <key>VEHICLE_HOVER_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>26</integer> - <key>tooltip</key> - <string>Period of time (in seconds) for the vehicle to achieve its hover height.</string> - </map> - <key>VEHICLE_LINEAR_DEFLECTION_EFFICIENCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>28</integer> - <key>tooltip</key> - <string>A slider between minimum (0.0) and maximum (1.0) deflection of linear velocity. That is, its a simple scalar for modulating the strength of linear deflection.</string> - </map> - <key>VEHICLE_LINEAR_DEFLECTION_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>29</integer> - <key>tooltip</key> - <string>The timescale for exponential success of linear deflection deflection. It is another way to specify how much time it takes for the vehicles linear velocity to be redirected to its preferred axis of motion.</string> - </map> - <key>VEHICLE_LINEAR_FRICTION_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string>A vector of timescales for exponential decay of the vehicles linear velocity along its preferred axes of motion (at, left, up). - Range = [0.07, inf) seconds for each element of the vector.</string> - </map> - <key>VEHICLE_LINEAR_MOTOR_DECAY_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>31</integer> - <key>tooltip</key> - <string>The timescale for exponential decay of the linear motors magnitude.</string> - </map> - <key>VEHICLE_LINEAR_MOTOR_DIRECTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>18</integer> - <key>tooltip</key> - <string>The direction and magnitude (in preferred frame) of the vehicles linear motor. The vehicle will accelerate (or decelerate if necessary) to match its velocity to its motor. - Range of magnitude = [0, 30] meters/second.</string> - </map> - <key>VEHICLE_LINEAR_MOTOR_OFFSET</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>20</integer> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_LINEAR_MOTOR_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>30</integer> - <key>tooltip</key> - <string>The timescale for exponential approach to full linear motor velocity.</string> - </map> - <key>VEHICLE_REFERENCE_FRAME</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>44</integer> - <key>tooltip</key> - <string>A rotation of the vehicles preferred axes of motion and orientation (at, left, up) with respect to the vehicles local frame (x, y, z).</string> - </map> - <key>VEHICLE_TYPE_AIRPLANE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>Uses linear deflection for lift, no hover, and banking to turn.\nSee http://wiki.secondlife.com/wiki/VEHICLE_TYPE_AIRPLANE</string> - </map> - <key>VEHICLE_TYPE_BALLOON</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>Hover, and friction, but no deflection.\nSee http://wiki.secondlife.com/wiki/VEHICLE_TYPE_BALLOON</string> - </map> - <key>VEHICLE_TYPE_BOAT</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>Hovers over water with lots of friction and some anglar deflection.\nSee http://wiki.secondlife.com/wiki/VEHICLE_TYPE_BOAT</string> - </map> - <key>VEHICLE_TYPE_CAR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>Another vehicle that bounces along the ground but needs the motors to be driven from external controls or timer events.\nSee http://wiki.secondlife.com/wiki/VEHICLE_TYPE_CAR</string> - </map> - <key>VEHICLE_TYPE_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>VEHICLE_TYPE_SLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>Simple vehicle that bumps along the ground, and likes to move along its local x-axis.\nSee http://wiki.secondlife.com/wiki/VEHICLE_TYPE_SLED</string> - </map> - <key>VEHICLE_VERTICAL_ATTRACTION_EFFICIENCY</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>36</integer> - <key>tooltip</key> - <string>A slider between minimum (0.0 = wobbly) and maximum (1.0 = firm as possible) stability of the vehicle to keep itself upright.</string> - </map> - <key>VEHICLE_VERTICAL_ATTRACTION_TIMESCALE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>37</integer> - <key>tooltip</key> - <string>The period of wobble, or timescale for exponential approach, of the vehicle to rotate such that its preferred "up" axis is oriented along the worlds "up" axis.</string> - </map> - <key>VERTICAL</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>WANDER_PAUSE_AT_WAYPOINTS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string/> - </map> - <key>XP_ERROR_EXPERIENCES_DISABLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>2</integer> - <key>tooltip</key> - <string>The region currently has experiences disabled.</string> - </map> - <key>XP_ERROR_EXPERIENCE_DISABLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>8</integer> - <key>tooltip</key> - <string>The experience owner has temporarily disabled the experience.</string> - </map> - <key>XP_ERROR_EXPERIENCE_SUSPENDED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>9</integer> - <key>tooltip</key> - <string>The experience has been suspended by Linden Customer Support.</string> - </map> - <key>XP_ERROR_INVALID_EXPERIENCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>7</integer> - <key>tooltip</key> - <string>The script is associated with an experience that no longer exists.</string> - </map> - <key>XP_ERROR_INVALID_PARAMETERS</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>3</integer> - <key>tooltip</key> - <string>One of the string arguments was too big to fit in the key-value store.</string> - </map> - <key>XP_ERROR_KEY_NOT_FOUND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>14</integer> - <key>tooltip</key> - <string>The requested key does not exist.</string> - </map> - <key>XP_ERROR_MATURITY_EXCEEDED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>16</integer> - <key>tooltip</key> - <string>The content rating of the experience exceeds that of the region.</string> - </map> - <key>XP_ERROR_NONE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>0</integer> - <key>tooltip</key> - <string>No error was detected.</string> - </map> - <key>XP_ERROR_NOT_FOUND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>6</integer> - <key>tooltip</key> - <string>The sim was unable to verify the validity of the experience. Retrying after a short wait is advised.</string> - </map> - <key>XP_ERROR_NOT_PERMITTED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>4</integer> - <key>tooltip</key> - <string>This experience is not allowed to run by the requested agent.</string> - </map> - <key>XP_ERROR_NOT_PERMITTED_LAND</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>17</integer> - <key>tooltip</key> - <string>This experience is not allowed to run on the current region.</string> - </map> - <key>XP_ERROR_NO_EXPERIENCE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>5</integer> - <key>tooltip</key> - <string>This script is not associated with an experience.</string> - </map> - <key>XP_ERROR_QUOTA_EXCEEDED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>11</integer> - <key>tooltip</key> - <string>An attempted write data to the key-value store failed due to the data quota being met.</string> - </map> - <key>XP_ERROR_RETRY_UPDATE</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>15</integer> - <key>tooltip</key> - <string>A checked update failed due to an out of date request.</string> - </map> - <key>XP_ERROR_STORAGE_EXCEPTION</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>13</integer> - <key>tooltip</key> - <string>Unable to communicate with the key-value store.</string> - </map> - <key>XP_ERROR_STORE_DISABLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>12</integer> - <key>tooltip</key> - <string>The key-value store is currently disabled on this region.</string> - </map> - <key>XP_ERROR_THROTTLED</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>1</integer> - <key>tooltip</key> - <string>The call failed due to too many recent calls.</string> - </map> - <key>XP_ERROR_UNKNOWN_ERROR</key> - <map> - <key>type</key> - <string>integer</string> - <key>value</key> - <integer>10</integer> - <key>tooltip</key> - <string>Other unknown error.</string> - </map> - <key>ZERO_ROTATION</key> - <map> - <key>type</key> - <string>rotation</string> - <key>value</key> - <string><0.0, 0.0, 0.0, 1.0></string> - <key>tooltip</key> - <string/> - </map> - <key>ZERO_VECTOR</key> - <map> - <key>type</key> - <string>vector</string> - <key>value</key> - <string><0.0, 0.0, 0.0></string> - <key>tooltip</key> - <string/> - </map> - <key>default</key> - <map> - <key>tooltip</key> - <string>All scripts must have a default state, which is the first state entered when the script starts.\nIf another state is defined before the default state, the compiler will report a syntax error.</string> - </map> - </map> - <key>events</key> - <map> - <key>at_rot_target</key> - <map> - <key>arguments</key> - <array> - <map> - <key>TargetNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>TargetRotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>CurrentRotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered when a script comes within a defined angle of a target rotation. The range and rotation, are set by a call to llRotTarget.</string> - </map> - <key>at_target</key> - <map> - <key>arguments</key> - <array> - <map> - <key>TargetNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>TargetPosition</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>CurrentPosition</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered when the scripted object comes within a defined range of the target position, defined by the llTarget function call.</string> - </map> - <key>attach</key> - <map> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered whenever an object is attached or detached from an avatar. If it is attached, the key of the avatar it is attached to is passed in, otherwise NULL_KEY is.</string> - </map> - <key>changed</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Changed</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered when various events change the object. The change argument will be a bit-field of CHANGED_* constants.</string> - </map> - <key>collision</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfCollisions</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised while another object, or avatar, is colliding with the object the script is attached to. - The number of detected objects is passed to the script. Information on those objects may be gathered via the llDetected* functions.</string> - </map> - <key>collision_end</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfCollisions</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when another object, or avatar, stops colliding with the object the script is attached to. - The number of detected objects is passed to the script. Information on those objects may be gathered via the llDetected* library functions.</string> - </map> - <key>collision_start</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfCollisions</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when another object, or avatar, starts colliding with the object the script is attached to. - The number of detected objects is passed to the script. Information on those objects may be gathered via the llDetected* library functions.</string> - </map> - <key>control</key> - <map> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Levels</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Edges</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Once a script has the ability to grab control inputs from the avatar, this event will be used to pass the commands into the script. - The levels and edges are bit-fields of control constants.</string> - </map> - <key>dataserver</key> - <map> - <key>arguments</key> - <array> - <map> - <key>RequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Data</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered when the requested data is returned to the script. - Data may be requested by the llRequestAgentData, llRequestInventoryData, and llGetNotecardLine function calls, for example.</string> - </map> - <key>email</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Time</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Address</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Subject</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Body</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>NumberRemaining</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered when an email sent to this script arrives. - The number remaining tells how many more emails are known to be still pending.</string> - </map> - <key>experience_permissions</key> - <map> - <key>arguments</key> - <array> - <map> - <key>agent_id</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>ID of the agent approving permission for the Experience.</string> - </map> - </map> - </array> - </map> - <key>experience_permissions_denied</key> - <map> - <key>arguments</key> - <array> - <map> - <key>agent_id</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>ID of the agent denying permission for the Experience.</string> - </map> - </map> - <map> - <key>Reason</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>One of the XP_ERROR_... constants describing the reason why the Experience permissions were denied for the agent.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Describes why the Experience permissions were denied for the agent.</string> - </map> - <key>http_request</key> - <map> - <key>arguments</key> - <array> - <map> - <key>HTTPRequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>HTTPMethod</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Body</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered when task receives an HTTP request.</string> - </map> - <key>http_response</key> - <map> - <key>arguments</key> - <array> - <map> - <key>HTTPRequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Status</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Metadata</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Body</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event handler is invoked when an HTTP response is received for a pending llHTTPRequest request or if a pending request fails or times out.</string> - </map> - <key>land_collision</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when the object the script is attached to is colliding with the ground.</string> - </map> - <key>land_collision_end</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when the object the script is attached to stops colliding with the ground.</string> - </map> - <key>land_collision_start</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when the object the script is attached to begins to collide with the ground.</string> - </map> - <key>link_message</key> - <map> - <key>arguments</key> - <array> - <map> - <key>SendersLink</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered when object receives a link message via llMessageLinked function call.</string> - </map> - <key>listen</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Name</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised whenever a chat message matching the constraints set in the llListen command is received. The name and ID of the speaker, as well as the message, are passed in as parameters. - Channel 0 is the public chat channel that all avatars see as chat text. Channels 1 through 2,147,483,648 are private channels that are not sent to avatars but other scripts can listen on those channels.</string> - </map> - <key>money</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Payer</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Amount</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is triggered when a resident has given an amount of Linden dollars to the object.</string> - </map> - <key>moving_end</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Triggered whenever an object with this script stops moving.</string> - </map> - <key>moving_start</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Triggered whenever an object with this script starts moving.</string> - </map> - <key>no_sensor</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>This event is raised when sensors are active, via the llSensor function call, but are not sensing anything.</string> - </map> - <key>not_at_rot_target</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>When a target is set via the llRotTarget function call, but the script is outside the specified angle this event is raised.</string> - </map> - <key>not_at_target</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>When a target is set via the llTarget library call, but the script is outside the specified range this event is raised.</string> - </map> - <key>object_rez</key> - <map> - <key>arguments</key> - <array> - <map> - <key>RezzedObjectsID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered when an object rezzes another object from its inventory via the llRezObject, or similar, functions. The id is the globally unique key for the object rezzed.</string> - </map> - <key>on_rez</key> - <map> - <key>arguments</key> - <array> - <map> - <key>StartParameter</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered whenever an object is rezzed from inventory or by another object. The start parameter is passed in from the llRezObject call, or zero if from inventory.</string> - </map> - <key>path_update</key> - <map> - <key>arguments</key> - <array> - <map> - <key>Type</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Reserved</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is called to inform the script of changes within the object's path-finding status.</string> - </map> - <key>remote_data</key> - <map> - <key>arguments</key> - <array> - <map> - <key>EventType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ChannelID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>MessageID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Sender</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Data</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Data</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered by various XML-RPC calls with event_type specifying the type of data.</string> - </map> - <key>run_time_permissions</key> - <map> - <key>arguments</key> - <array> - <map> - <key>PermissionFlags</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Scripts need permission from either the owner or the avatar they wish to act on before they may perform certain functions, such as debiting money from their owners account, triggering an animation on an avatar, or capturing control inputs. The llRequestPermissions library function is used to request these permissions and the various permissions integer constants can be supplied. - The integer returned to this event handler contains the current set of permissions flags, so if permissions equal 0 then no permissions are set.</string> - </map> - <key>sensor</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberDetected</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised whenever objects matching the constraints of the llSensor command are detected. - The number of detected objects is passed to the script in the parameter. Information on those objects may be gathered via the llDetected* functions.</string> - </map> - <key>state_entry</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>The state_entry event occurs whenever a new state is entered, including at program start, and is always the first event handled.</string> - </map> - <key>state_exit</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>The state_exit event occurs whenever the state command is used to transition to another state. It is handled before the new states state_entry event.</string> - </map> - <key>timer</key> - <map> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>This event is raised at regular intervals set by the llSetTimerEvent library function.</string> - </map> - <key>touch</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfTouches</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised while a user is touching the object the script is attached to. - The number of touching objects is passed to the script in the parameter. - Information on those objects may be gathered via the llDetected* library functions.</string> - </map> - <key>touch_end</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfTouches</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when a user stops touching the object the script is attached to. The number of touches is passed to the script in the parameter. - Information on those objects may be gathered via the llDetected* library functions.</string> - </map> - <key>touch_start</key> - <map> - <key>arguments</key> - <array> - <map> - <key>NumberOfTouches</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This event is raised when a user first touches the object the script is attached to. The number of touches is passed to the script in the parameter. - Information on those objects may be gathered via the llDetected() library functions.</string> - </map> - <key>transaction_result</key> - <map> - <key>arguments</key> - <array> - <map> - <key>RequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Success</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Message</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Triggered by llTransferMoney() function.</string> - </map> - </map> - <key>functions</key> - <map> - <key>llAbs</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>An integer value.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the absolute (positive) version of Value.</string> - </map> - <key>llAcos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>A floating-point value.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the arc-cosine of Value, in radians.</string> - </map> - <key>llAddToLandBanList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Agent UUID to add to ban-list.</string> - </map> - </map> - <map> - <key>Hours</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Period, in hours, to ban the avatar for.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Add avatar ID to the parcel ban list for the specified number of Hours.\nA value of 0 for Hours will add the agent indefinitely.\nThe smallest value that Hours will accept is 0.01; anything smaller will be seen as 0.\nWhen values that small are used, it seems the function bans in approximately 30 second increments (Probably 36 second increments, as 0.01 of an hour is 36 seconds).\nResidents teleporting to a parcel where they are banned will be redirected to a neighbouring parcel.</string> - </map> - <key>llAddToLandPassList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Agent UUID to add to pass-list.</string> - </map> - </map> - <map> - <key>Hours</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Period, in hours, to allow the avatar for.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Add avatar ID to the land pass list, for a duration of Hours.</string> - </map> - <key>llAdjustSoundVolume</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>The volume to set.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Adjusts the volume (0.0 - 1.0) of the currently playing attached sound.\nThis function has no effect on sounds started with llTriggerSound.</string> - </map> - <key>llAgentInExperience</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>AgentID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string></string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Returns TRUE if the agent is in the Experience and the Experience can run in the current location. - </string> - </map> - <key>llAllowInventoryDrop</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Flag</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, If TRUE allows anyone to drop inventory on prim, FALSE revokes.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If Flag == TRUE, users without object modify permissions can still drop inventory items into the object.</string> - </map> - <key>llAngleBetween</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Rot1</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string>First rotation.</string> - </map> - </map> - <map> - <key>Rot2</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string>Second rotation.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the angle, in radians, between rotations Rot1 and Rot2.</string> - </map> - <key>llApplyImpulse</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Force</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Amount of impulse force to apply.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE, force is treated as a local directional vector instead of region directional vector.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Applies impulse to the object.\nIf Local == TRUE, apply the Force in local coordinates; otherwise, apply the Force in global coordinates.\nThis function only works on physical objects.</string> - </map> - <key>llApplyRotationalImpulse</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Force</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Amount of impulse force to apply.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE, uses local axis, if FALSE, uses region axis.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Applies rotational impulse to the object.\nIf Local == TRUE, apply the Force in local coordinates; otherwise, apply the Force in global coordinates.\nThis function only works on physical objects.</string> - </map> - <key>llAsin</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>A floating-point value.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the arc-sine, in radians, of Value.</string> - </map> - <key>llAtan2</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>y</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>A floating-point value.</string> - </map> - </map> - <map> - <key>x</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>A floating-point value.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the arc-tangent2 of y, x.</string> - </map> - <key>llAttachToAvatar</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AttachmentPoint</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Attach to avatar at point AttachmentPoint.\nRequires the PERMISSION_ATTACH runtime permission.</string> - </map> - <key>llAttachToAvatarTemp</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AttachPoint</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Valid attachment point or ATTACH_* constant.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Follows the same convention as llAttachToAvatar, with the exception that the object will not create new inventory for the user, and will disappear on detach or disconnect.</string> - </map> - <key>llAvatarOnLinkSitTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If an avatar is sitting on the link's sit target, return the avatar's key, NULL_KEY otherwise.\nReturns a key that is the UUID of the user seated on the specified link's prim.</string> - </map> - <key>llAvatarOnSitTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>If an avatar is seated on the sit target, returns the avatar's key, otherwise NULL_KEY.\nThis only will detect avatars sitting on sit targets defined with llSitTarget.</string> - </map> - <key>llAxes2Rot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>Forward</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Forward/Back part of rotation.</string> - </map> - </map> - <map> - <key>Left</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Left/Right part of rotation.</string> - </map> - </map> - <map> - <key>Up</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Up/Down part of rotation.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation represented by coordinate axes Forward, Left, and Up.</string> - </map> - <key>llAxisAngle2Rot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>Axis</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Axis.</string> - </map> - </map> - <map> - <key>Angle</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Angle in radians.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation that is a generated Angle about Axis.</string> - </map> - <key>llBase64ToInteger</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns an integer that is the Text, Base64 decoded as a big endian integer.\nReturns zero if Text is longer then 8 characters. If Text contains fewer then 6 characters, the return value is unpredictable.</string> - </map> - <key>llBase64ToString</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Converts a Base64 string to a conventional string.\nIf the conversion creates any unprintable characters, they are converted to question marks.</string> - </map> - <key>llBreakAllLinks</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>De-links all prims in the link set (requires permission PERMISSION_CHANGE_LINKS be set).</string> - </map> - <key>llBreakLink</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>De-links the prim with the given link number (requires permission PERMISSION_CHANGE_LINKS be set).</string> - </map> - <key>llCastRay</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Casts a ray into the physics world from 'start' to 'end' and returns data according to details in Options.\nReports collision data for intersections with objects.\nReturn value: [UUID_1, {link_number_1}, hit_position_1, {hit_normal_1}, UUID_2, {link_number_2}, hit_position_2, {hit_normal_2}, ... , status_code] where {} indicates optional data.</string> - </map> - <key>llCeil</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns smallest integer value >= Value.</string> - </map> - <key>llClearCameraParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Resets all camera parameters to default values and turns off scripted camera control.</string> - </map> - <key>llClearLinkMedia</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Link</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Clears (deletes) the media and all parameters from the given Face on the linked prim.\nReturns an integer that is a STATUS_* flag, which details the success/failure of the operation.</string> - </map> - <key>llClearPrimMedia</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Number of side to clear.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Clears (deletes) the media and all parameters from the given Face.\nReturns an integer that is a STATUS_* flag which details the success/failure of the operation.</string> - </map> - <key>llCloseRemoteDataChannel</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ChannelID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Closes the specified XML-RPC channel.</string> - </map> - <key>llCloud</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the cloud density at the object's position + Offset.</string> - </map> - <key>llCollisionFilter</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ObjectName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ObjectID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Accept</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>If TRUE, only accept collisions with ObjectName name AND ObjectID (either is optional), otherwise with objects not ObjectName AND ObjectID.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Specify an empty string or NULL_KEY for Accept, to not filter on the corresponding parameter.</string> - </map> - <key>llCollisionSound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ImpactSound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ImpactVolume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Suppress default collision sounds, replace default impact sounds with ImpactSound.\nThe ImpactSound must be in the object inventory.\nSupply an empty string to suppress collision sounds.</string> - </map> - <key>llCollisionSprite</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ImpactSprite</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Suppress default collision sprites, replace default impact sprite with ImpactSprite; found in the object inventory (empty string to just suppress).</string> - </map> - <key>llCos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Theta</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the cosine of Theta (Theta in radians).</string> - </map> - <key>llCreateCharacter</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Convert link-set to AI/Physics character.\nCreates a path-finding entity, known as a "character", from the object containing the script. Required to activate use of path-finding functions.\nOptions is a list of key/value pairs.</string> - </map> - <key>llCreateKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Key</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Starts an asychronous transaction to create a key-value pair. Will fail with XP_ERROR_STORAGE_EXCEPTION if the key already exists. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is a two element commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will be the value passed to the function. - </string> - </map> - <key>llCreateLink</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetPrim</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Object UUID that is in the same region.</string> - </map> - </map> - <map> - <key>Parent</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>If FALSE, then TargetPrim becomes the root. If TRUE, then the script's object becomes the root.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Attempt to link the object the script is in, to target (requires permission PERMISSION_CHANGE_LINKS be set).\nRequires permission PERMISSION_CHANGE_LINKS be set.</string> - </map> - <key>llCSV2List</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Create a list from a string of comma separated values specified in Text.</string> - </map> - <key>llDataSizeKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string> - Starts an asychronous transaction the request the used and total amount of data allocated for the Experience. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will be the the amount in use and the third item will be the total available. - </string> - </map> - <key>llDeleteCharacter</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Convert link-set from AI/Physics character to Physics object.\nConvert the current link-set back to a standard object, removing all path-finding properties.</string> - </map> - <key>llDeleteKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Key</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Starts an asychronous transaction to delete a key-value pair. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is a two element commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will be the value associated with the key. - </string> - </map> - <key>llDeleteSubList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Source</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes the slice from start to end and returns the remainder of the list.\nRemove a slice from the list and return the remainder, start and end are inclusive.\nUsing negative numbers for start and/or end causes the index to count backwards from the length of the list, so 0, -1 would delete the entire list.\nIf Start is larger than End the list deleted is the exclusion of the entries; so 6, 4 would delete the entire list except for the 5th. list entry.</string> - </map> - <key>llDeleteSubString</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Source</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes the indicated sub-string and returns the result.\nStart and End are inclusive.\nUsing negative numbers for Start and/or End causes the index to count backwards from the length of the string, so 0, -1 would delete the entire string.\nIf Start is larger than End, the sub-string is the exclusion of the entries; so 6, 4 would delete the entire string except for the 5th. character.</string> - </map> - <key>llDetachFromAvatar</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Remove the object containing the script from the avatar.</string> - </map> - <key>llDetectedGrab</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the grab offset of a user touching the object.\nReturns <0.0, 0.0, 0.0> if Number is not a valid object.</string> - </map> - <key>llDetectedGroup</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns TRUE if detected object or agent Number has the same user group active as this object.\nIt will return FALSE if the object or agent is in the group, but the group is not active.</string> - </map> - <key>llDetectedKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the key of detected object or avatar number.\nReturns NULL_KEY if Number is not a valid index.</string> - </map> - <key>llDetectedLinkNumber</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the link position of the triggered event for touches and collisions only.\n0 for a non-linked object, 1 for the root of a linked object, 2 for the first child, etc.</string> - </map> - <key>llDetectedName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the name of detected object or avatar number.\nReturns the name of detected object number.\nReturns empty string if Number is not a valid index.</string> - </map> - <key>llDetectedOwner</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the key of detected object's owner.\nReturns invalid key if Number is not a valid index.</string> - </map> - <key>llDetectedPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the position of detected object or avatar number.\nReturns <0.0, 0.0, 0.0> if Number is not a valid index.</string> - </map> - <key>llDetectedRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation of detected object or avatar number.\nReturns <0.0, 0.0, 0.0, 1.0> if Number is not a valid offset.</string> - </map> - <key>llDetectedTouchBinormal</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detection information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the surface bi-normal for a triggered touch event.\nReturns a vector that is the surface bi-normal (tangent to the surface) where the touch event was triggered.</string> - </map> - <key>llDetectedTouchFace</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detection information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the index of the face where the avatar clicked in a triggered touch event.</string> - </map> - <key>llDetectedTouchNormal</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detection information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the surface normal for a triggered touch event.\nReturns a vector that is the surface normal (perpendicular to the surface) where the touch event was triggered.</string> - </map> - <key>llDetectedTouchPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detected information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the position, in region coordinates, where the object was touched in a triggered touch event.\nUnless it is a HUD, in which case it returns the position relative to the attach point.</string> - </map> - <key>llDetectedTouchST</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detection information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a vector that is the surface coordinates where the prim was touched.\nThe X and Y vector positions contain the horizontal (S) and vertical (T) face coordinates respectively.\nEach component is in the interval [0.0, 1.0].\nTOUCH_INVALID_TEXCOORD is returned if the surface coordinates cannot be determined (e.g. when the viewer does not support this function).</string> - </map> - <key>llDetectedTouchUV</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of detection information</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a vector that is the texture coordinates for where the prim was touched.\nThe X and Y vector positions contain the U and V face coordinates respectively.\nTOUCH_INVALID_TEXCOORD is returned if the touch UV coordinates cannot be determined (e.g. when the viewer does not support this function).</string> - </map> - <key>llDetectedType</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the type (AGENT, ACTIVE, PASSIVE, SCRIPTED) of detected object.\nReturns 0 if number is not a valid index.\nNote that number is a bit-field, so comparisons need to be a bitwise checked. e.g.:\ninteger iType = llDetectedType(0);\n{\n // ...do stuff with the agent\n}</string> - </map> - <key>llDetectedVel</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the velocity of the detected object Number.\nReturns<0.0, 0.0, 0.0> if Number is not a valid offset.</string> - </map> - <key>llDialog</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Buttons</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Shows a dialog box on the avatar's screen with the message.\n - Up to 12 strings in the list form buttons.\n - If a button is clicked, the name is chatted on Channel.\nOpens a "notify box" in the given avatars screen displaying the message.\n - Up to twelve buttons can be specified in a list of strings. When the user clicks a button, the name of the button is said on the specified channel.\n - Channels work just like llSay(), so channel 0 can be heard by everyone.\n - The chat originates at the object's position, not the avatar's position, even though it is said as the avatar (uses avatar's UUID and Name etc.).\n - Examples:\n - llDialog(who, "Are you a boy or a girl?", [ "Boy", "Girl" ], -4913);\n - llDialog(who, "This shows only an OK button.", [], -192);\n - llDialog(who, "This chats so you can 'hear' it.", ["Hooray"], 0);</string> - </map> - <key>llDie</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Delete the object which holds the script.</string> - </map> - <key>llDumpList2String</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Source</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Separator</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the list as a single string, using Separator between the entries.\nWrite the list out as a single string, using Separator between values.</string> - </map> - <key>llEdgeOfWorld</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Direction</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Checks to see whether the border hit by Direction from Position is the edge of the world (has no neighboring region).\nReturns TRUE if the line along Direction from Position hits the edge of the world in the current simulator, returns FALSE if that edge crosses into another simulator.</string> - </map> - <key>llEjectFromLand</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Ejects AvatarID from land that you own.\nEjects AvatarID from land that the object owner (group or resident) owns.</string> - </map> - <key>llEmail</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>20.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Address</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Subject</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sends email to Address with Subject and Message.\nSends an email to Address with Subject and Message.</string> - </map> - <key>llEscapeURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns an escaped/encoded version of url, replacing spaces with %20 etc.\nReturns the string that is the URL-escaped version of URL (replacing spaces with %20, etc.).\n - This function returns the UTF-8 encoded escape codes for selected characters.</string> - </map> - <key>llEuler2Rot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>Vector</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation representation of the Euler angles.\nReturns the rotation represented by the Euler Angle.</string> - </map> - <key>llEvade</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Agent or object to evade.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>No options yet.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Evade a specified target.\nCharacters will (roughly) try to hide from their pursuers if there is a good hiding spot along their fleeing path. Hiding means no direct line of sight from the head of the character (centre of the top of its physics bounding box) to the head of its pursuer and no direct path between the two on the navigation-mesh.</string> - </map> - <key>llExecCharacterCmd</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Command</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Command to send.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Height for CHARACTER_CMD_JUMP.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Execute a character command.\nSend a command to the path system.\nCurrently only supports stopping the current path-finding operation or causing the character to jump.</string> - </map> - <key>llFabs</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the positive version of Value.\nReturns the absolute value of Value.</string> - </map> - <key>llFleeFrom</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Source</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Global coordinate from which to flee.</string> - </map> - </map> - <map> - <key>Distance</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Distance in meters to flee from the source.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>No options available at this time.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Flee from a point.\nDirects a character (llCreateCharacter) to keep away from a defined position in the region or adjacent regions.</string> - </map> - <key>llFloor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns largest integer value <= Value.</string> - </map> - <key>llForceMouselook</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Enable</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE when an avatar sits on the prim, the avatar will be forced into mouse-look mode.\nFALSE is the default setting and will undo a previously set TRUE or do nothing.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If Enable is TRUE any avatar that sits on this object is forced into mouse-look mode.\nAfter calling this function with Enable set to TRUE, any agent sitting down on the prim will be forced into mouse-look.\nJust like llSitTarget, this changes a permanent property of the prim (not the object) and needs to be reset by calling this function with Enable set to FALSE in order to disable it.</string> - </map> - <key>llFrand</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Magnitude</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a pseudo random number in the range [0, Magnitude] or [Magnitude, 0].\nReturns a pseudo-random number between [0, Magnitude].</string> - </map> - <key>llGenerateKey</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Generates a key (SHA-1 hash) using UUID generation to create a unique key.\nAs the UUID produced is versioned, it should never return a value of NULL_KEY.\nThe specific UUID version is an implementation detail that has changed in the past and may change again in the future. Do not depend upon the UUID that is returned to be version 5 SHA-1 hash.</string> - </map> - <key>llGetAccel</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the acceleration of the object relative to the region's axes.\nGets the acceleration of the object.</string> - </map> - <key>llGetAgentInfo</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns an integer bit-field containing the agent information about id.\n - Returns AGENT_FLYING, AGENT_ATTACHMENTS, AGENT_SCRIPTED, AGENT_SITTING, AGENT_ON_OBJECT, AGENT_MOUSELOOK, AGENT_AWAY, AGENT_BUSY, AGENT_TYPING, AGENT_CROUCHING, AGENT_ALWAYS_RUN, AGENT_WALKING and/or AGENT_IN_AIR.\nReturns information about the given agent ID as a bit-field of agent info constants.</string> - </map> - <key>llGetAgentLanguage</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the language code of the preferred interface language of the avatar.\nReturns a string that is the language code of the preferred interface language of the resident.</string> - </map> - <key>llGetAgentList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Scope</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>The scope (region, parcel, parcel same owner) to return agents for.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of options to apply. Current unused.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests a list of agents currently in the region, limited by the scope parameter.\nReturns a list [key UUID-0, key UUID-1, ..., key UUID-n] or [string error_msg] - returns avatar keys for all agents in the region limited to the area(s) specified by scope</string> - </map> - <key>llGetAgentSize</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>If the avatar is in the same region, returns the size of the bounding box of the requested avatar by id, otherwise returns ZERO_VECTOR.\nIf the agent is in the same region as the object, returns the size of the avatar.</string> - </map> - <key>llGetAlpha</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the alpha value of Face.\nReturns the 'alpha' of the given face. If face is ALL_SIDES the value returned is the mean average of all faces.</string> - </map> - <key>llGetAndResetTime</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the script time in seconds and then resets the script timer to zero.\nGets the time in seconds since starting and resets the time to zero.</string> - </map> - <key>llGetAnimation</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the name of the currently playing locomotion animation for the avatar id.\nReturns the currently playing animation for the specified avatar ID.</string> - </map> - <key>llGetAnimationList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list of keys of playing animations for an avatar.\nReturns a list of keys of all playing animations for the specified avatar ID.</string> - </map> - <key>llGetAnimationOverride</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>AnimationState</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string that is the name of the animation that is used for the specified animation state\nTo use this function the script must obtain either the PERMISSION_OVERRIDE_ANIMATIONS or PERMISSION_TRIGGER_ANIMATION permission (automatically granted to attached objects).</string> - </map> - <key>llGetAttached</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the object's attachment point, or 0 if not attached.</string> - </map> - <key>llGetAttachedList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Avatar to get attachments</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list of keys of all visible (not HUD) attachments on the avatar identified by the ID argument</string> - </map> - <key>llGetBoundingBox</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the bounding box around the object (including any linked prims) relative to its root prim, as a list in the format [ (vector) min_corner, (vector) max_corner ].</string> - </map> - <key>llGetCameraPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current camera position for the agent the task has permissions for.\nReturns the position of the camera, of the user that granted the script PERMISSION_TRACK_CAMERA. If no user has granted the permission, it returns ZERO_VECTOR.</string> - </map> - <key>llGetCameraRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current camera orientation for the agent the task has permissions for. If no user has granted the PERMISSION_TRACK_CAMERA permission, returns ZERO_ROTATION.</string> - </map> - <key>llGetCenterOfMass</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the prim's centre of mass (unless called from the root prim, where it returns the object's centre of mass).</string> - </map> - <key>llGetClosestNavPoint</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Point</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>A point in region-local space.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>No options at this time.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Get the closest navigable point to the point provided.\nThe function accepts a point in region-local space (like all the other path-finding methods) and returns either an empty list or a list containing a single vector which is the closest point on the navigation-mesh to the point provided.</string> - </map> - <key>llGetColor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the color on Face.\nReturns the color of Face as a vector of red, green, and blue values between 0 and 1. If face is ALL_SIDES the color returned is the mean average of each channel.</string> - </map> - <key>llGetCreator</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a key for the creator of the prim.\nReturns the key of the object's original creator. Similar to llGetOwner.</string> - </map> - <key>llGetDate</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current date in the UTC time zone in the format YYYY-MM-DD.\nReturns the current UTC date as YYYY-MM-DD.</string> - </map> - <key>llGetDisplayName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Avatar UUID that is in the same region, or is otherwise known to the region.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the display name of an avatar, if the avatar is connected to the current region, or if the name has been cached. Otherwise, returns an empty string. Use llRequestDisplayName if the avatar may be absent from the region.</string> - </map> - <key>llGetEnergy</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns how much energy is in the object as a percentage of maximum.</string> - </map> - <key>llGetEnv</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>DataRequest</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>The type of data to request. Any other string will cause an empty string to be returned.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string with the requested data about the region.</string> - </map> - <key>llGetExperienceDetails</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ExperienceID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>May be NULL_KEY to retrieve the details for the script's Experience</string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Returns a list with the following Experience properties: [Experience Name, Owner ID, Group ID, Experience ID, State, State Message]. State is an integer corresponding to one of the constants XP_ERROR_... and State Message is the string returned by llGetExperienceErrorMessage for that integer. - </string> - </map> - <key>llGetExperienceErrorMessage</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Error</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>An Experience error code to translate.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Returns a string describing the error code passed or the string corresponding with XP_ERROR_UNKNOWN_ERROR if the value is not a valid Experience error code. - </string> - </map> - <key>llGetForce</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the force (if the script is physical).\nReturns the current force if the script is physical.</string> - </map> - <key>llGetFreeMemory</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of free bytes of memory the script can use.\nReturns the available free space for the current script. This is inaccurate with LSO.</string> - </map> - <key>llGetFreeURLs</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of available URLs for the current script.\nReturns an integer that is the number of available URLs.</string> - </map> - <key>llGetGeometricCenter</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the vector that is the geometric center of the object relative to the root prim.</string> - </map> - <key>llGetGMTclock</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the time in seconds since midnight GMT.\nGets the time in seconds since midnight in GMT/UTC.</string> - </map> - <key>llGetHTTPHeader</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>HTTPRequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>A valid HTTP request key</string> - </map> - </map> - <map> - <key>Header</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Header value name</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the value for header for request_id.\nReturns a string that is the value of the Header for HTTPRequestID.</string> - </map> - <key>llGetInventoryCreator</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a key for the creator of the inventory item.\nThis function returns the UUID of the creator of item. If item is not found in inventory, the object says "No item named 'name'".</string> - </map> - <key>llGetInventoryKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the key that is the UUID of the inventory named.\nReturns the key of the inventory named.</string> - </map> - <key>llGetInventoryName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>InventoryType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Inventory item type</string> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index number of inventory item.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the name of the inventory item of a given type, specified by index number.\nUse the inventory constants INVENTORY_* to specify the type.</string> - </map> - <key>llGetInventoryNumber</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>InventoryType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Inventory item type</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the quantity of items of a given type (INVENTORY_* flag) in the prim's inventory.\nUse the inventory constants INVENTORY_* to specify the type.</string> - </map> - <key>llGetInventoryPermMask</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Inventory item name.</string> - </map> - </map> - <map> - <key>BitMask</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>MASK_BASE, MASK_OWNER, MASK_GROUP, MASK_EVERYONE or MASK_NEXT</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the requested permission mask for the inventory item.\nReturns the requested permission mask for the inventory item defined by InventoryItem. If item is not in the object's inventory, llGetInventoryPermMask returns FALSE and causes the object to say "No item named '<item>'", where "<item>" is item.</string> - </map> - <key>llGetInventoryType</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the type of the named inventory item.\nLike all inventory functions, llGetInventoryType is case-sensitive.</string> - </map> - <key>llGetKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the key of the prim the script is attached to.\nGet the key for the object which has this script.</string> - </map> - <key>llGetLandOwnerAt</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the key of the land owner, returns NULL_KEY if public.\nReturns the key of the land owner at Position, or NULL_KEY if public.</string> - </map> - <key>llGetLinkKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the key of the linked prim LinkNumber.\nReturns the key of LinkNumber in the link set.</string> - </map> - <key>llGetLinkMedia</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag</string> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>The prim's side number</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A list of PRIM_* property constants to return values of.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Get the media parameters for a particular face on linked prim, given the desired list of parameter names. Returns a list of values in the order requested. Returns an empty list if no media exists on the face.</string> - </map> - <key>llGetLinkName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the name of LinkNumber in a link set.\nReturns the name of LinkNumber the link set.</string> - </map> - <key>llGetLinkNumber</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the link number of the prim containing the script (0 means not linked, 1 the prim is the root, 2 the prim is the first child, etc.).\nReturns the link number of the prim containing the script. 0 means no link, 1 the root, 2 for first child, etc.</string> - </map> - <key>llGetLinkNumberOfSides</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the number of sides of the specified linked prim.\nReturns an integer that is the number of faces (or sides) of the prim link.</string> - </map> - <key>llGetLinkPrimitiveParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag.</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>PRIM_* flags.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the list of primitive attributes requested in the Parameters list for LinkNumber.\nPRIM_* flags can be broken into three categories, face flags, prim flags, and object flags.\n* Supplying a prim or object flag will return that flags attributes.\n* Face flags require the user to also supply a face index parameter.</string> - </map> - <key>llGetListEntryType</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the type of the index entry in the list (TYPE_INTEGER, TYPE_FLOAT, TYPE_STRING, TYPE_KEY, TYPE_VECTOR, TYPE_ROTATION, or TYPE_INVALID if index is off list).\nReturns the type of the variable at Index in ListVariable.</string> - </map> - <key>llGetListLength</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the number of elements in the list.\nReturns the number of elements in ListVariable.</string> - </map> - <key>llGetLocalPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the position relative to the root.\nReturns the local position of a child object relative to the root.</string> - </map> - <key>llGetLocalRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the rotation local to the root.\nReturns the local rotation of a child object relative to the root.</string> - </map> - <key>llGetMass</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the mass of object that the script is attached to.\nReturns the scripted object's mass. When called from a script in a link-set, the parent will return the sum of the link-set weights, while a child will return just its own mass. When called from a script inside an attachment, this function will return the mass of the avatar it's attached to, not its own.</string> - </map> - <key>llGetMassMKS</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Acts as llGetMass(), except that the units of the value returned are Kg.</string> - </map> - <key>llGetMaxScaleFactor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a float that is the largest scaling factor that can be used with llScaleByFactor to resize the object. This maximum is determined by the Linkability Rules and prim scale limits.</string> - </map> - <key>llGetMemoryLimit</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Get the maximum memory a script can use, in bytes.</string> - </map> - <key>llGetMinScaleFactor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a float that is the smallest scaling factor that can be used with llScaleByFactor to resize the object. This minimum is determined by the prim scale limits.</string> - </map> - <key>llGetNextEmail</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Address</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Subject</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Fetch the next queued email with that matches the given address and/or subject, via the email event.\nIf the parameters are blank, they are not used for filtering.</string> - </map> - <key>llGetNotecardLine</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>NotecardName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>LineNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns LineNumber from NotecardName via the dataserver event. The line index starts at zero.\nIf the requested line is passed the end of the note-card the dataserver event will return the constant EOF string.\nThe key returned by this function is a unique identifier which will be supplied to the dataserver event in the requested parameter.</string> - </map> - <key>llGetNumberOfNotecardLines</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>NotecardName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the number of lines contained within a notecard via the dataserver event.\nThe key returned by this function is a query ID for identifying the dataserver reply.</string> - </map> - <key>llGetNumberOfPrims</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of prims in a link set the script is attached to.\nReturns the number of prims in (and avatars seated on) the object the script is in.</string> - </map> - <key>llGetNumberOfSides</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of faces (or sides) of the prim.\nReturns the number of sides of the prim which has the script.</string> - </map> - <key>llGetObjectDesc</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the description of the prim the script is attached to.\nReturns the description of the scripted object/prim. You can set the description using llSetObjectDesc.</string> - </map> - <key>llGetObjectDetails</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Prim or avatar UUID that is in the same region.</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of OBJECT_* flags.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list of object details specified in the Parameters list for the object or avatar in the region with key ID.\nParameters are specified by the OBJECT_* constants.</string> - </map> - <key>llGetObjectMass</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the mass of the avatar or object in the region.\nGets the mass of the object or avatar corresponding to ID.</string> - </map> - <key>llGetObjectName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the name of the prim which the script is attached to.\nReturns the name of the prim (not object) which contains the script.</string> - </map> - <key>llGetObjectPermMask</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Category</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Category is one of MASK_BASE, MASK_OWNER, MASK_GROUP, MASK_EVERYONE, or MASK_NEXT</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the permission mask of the requested category for the object.</string> - </map> - <key>llGetObjectPrimCount</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ObjectID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the total number of prims for an object in the region.\nReturns the prim count for any object id in the same region.</string> - </map> - <key>llGetOmega</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the rotation velocity in radians per second.\nReturns a vector that is the rotation velocity of the object in radians per second.</string> - </map> - <key>llGetOwner</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the object owner's UUID.\nReturns the key for the owner of the object.</string> - </map> - <key>llGetOwnerKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>ObjectID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the owner of ObjectID.\nReturns the key for the owner of object ObjectID.</string> - </map> - <key>llGetParcelDetails</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Location within the region.</string> - </map> - </map> - <map> - <key>ParcelDetails</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of details requested for the specified parcel location.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list of parcel details specified in the ParcelDetails list for the parcel at Position.\nParameters is one or more of: PARCEL_DETAILS_NAME, _DESC, _OWNER, _GROUP, _AREA, _ID, _SEE_AVATARS.\nReturns a list that is the parcel details specified in ParcelDetails (in the same order) for the parcel at Position.</string> - </map> - <key>llGetParcelFlags</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a mask of the parcel flags (PARCEL_FLAG_*) for the parcel that includes the point Position.\nReturns a bit-field specifying the parcel flags (PARCEL_FLAG_*) for the parcel at Position.</string> - </map> - <key>llGetParcelMaxPrims</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Region coordinates (z is ignored) of parcel.</string> - </map> - </map> - <map> - <key>SimWide</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean. If FALSE then the return is the maximum prims supported by the parcel. If TRUE then it is the combined number of prims on all parcels in the region owned by the specified parcel's owner.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the maximum number of prims allowed on the parcel at Position for a given scope.\nThe scope may be set to an individual parcel or the combined resources of all parcels with the same ownership in the region.</string> - </map> - <key>llGetParcelMusicURL</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Gets the streaming audio URL for the parcel object is on.\nThe object owner, avatar or group, must also be the land owner.</string> - </map> - <key>llGetParcelPrimCount</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Region coordinates of parcel to query.</string> - </map> - </map> - <map> - <key>Category</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>A PARCEL_COUNT_* flag.</string> - </map> - </map> - <map> - <key>SimWide</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean. If FALSE then the return is the maximum prims supported by the parcel. If TRUE then it is the combined number of prims on all parcels in the region owned by the specified parcel's owner.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the number of prims on the parcel at Position of the given category.\nCategories: PARCEL_COUNT_TOTAL, _OWNER, _GROUP, _OTHER, _SELECTED, _TEMP.\nReturns the number of prims used on the parcel at Position which are in Category.\nIf SimWide is TRUE, it returns the total number of objects for all parcels with matching ownership in the category specified.\nIf SimWide is FALSE, it returns the number of objects on this specific parcel in the category specified</string> - </map> - <key>llGetParcelPrimOwners</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>2.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list of up to 100 residents who own objects on the parcel at Position, with per-owner land impact totals.\nRequires owner-like permissions for the parcel, and for the script owner to be present in the region.\nThe list is formatted as [ key agentKey1, integer agentLI1, key agentKey2, integer agentLI2, ... ], sorted by agent key.\nThe integers are the combined land impacts of the objects owned by the corresponding agents.</string> - </map> - <key>llGetPermissions</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns an integer bitmask of the permissions that have been granted to the script. Individual permissions can be determined using a bit-wise "and" operation against the PERMISSION_* constants</string> - </map> - <key>llGetPermissionsKey</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the key of the avatar that last granted or declined permissions to the script.\nReturns NULL_KEY if permissions were never granted or declined.</string> - </map> - <key>llGetPhysicsMaterial</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>list</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a list of the form [float gravity_multiplier, float restitution, float friction, float density].</string> - </map> - <key>llGetPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the position of the task in region coordinates.\nReturns the vector position of the task in region coordinates.</string> - </map> - <key>llGetPrimitiveParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>PRIM_* flags and face parameters</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the primitive parameters specified in the parameters list.\nReturns primitive parameters specified in the Parameters list.</string> - </map> - <key>llGetPrimMediaParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>face number</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>One or more PRIM_MEDIA_* flags</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the media parameters for a particular face on an object, given the desired list of parameter names, in the order requested. Returns an empty list if no media exists on the face.</string> - </map> - <key>llGetRegionAgentCount</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of avatars in the region.\nReturns an integer that is the number of avatars in the region.</string> - </map> - <key>llGetRegionCorner</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a vector, in meters, that is the global location of the south-west corner of the region which the object is in.\nReturns the Region-Corner of the simulator containing the task. The region-corner is a vector (values in meters) representing distance from the first region.</string> - </map> - <key>llGetRegionFlags</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the region flags (REGION_FLAG_*) for the region the object is in.\nReturns a bit-field specifying the region flags (REGION_FLAG_*) for the region the object is in.</string> - </map> - <key>llGetRegionFPS</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the mean region frames per second.</string> - </map> - <key>llGetRegionName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current region name.</string> - </map> - <key>llGetRegionTimeDilation</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current time dilation as a float between 0.0 (full dilation) and 1.0 (no dilation).\nReturns the current time dilation as a float between 0.0 and 1.0.</string> - </map> - <key>llGetRootPosition</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the position (in region coordinates) of the root prim of the object which the script is attached to.\nThis is used to allow a child prim to determine where the root is.</string> - </map> - <key>llGetRootRotation</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the rotation (relative to the region) of the root prim of the object which the script is attached to.\nGets the global rotation of the root object of the object script is attached to.</string> - </map> - <key>llGetRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the rotation relative to the region's axes.\nReturns the rotation.</string> - </map> - <key>llGetScale</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the scale of the prim.\nReturns a vector that is the scale (dimensions) of the prim.</string> - </map> - <key>llGetScriptName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the name of the script that this function is used in.\nReturns the name of this script.</string> - </map> - <key>llGetScriptState</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ScriptName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns TRUE if the script named is running.\nReturns TRUE if ScriptName is running.</string> - </map> - <key>llGetSimStats</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>StatType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Statistic type. Currently only SIM_STAT_PCT_CHARS_STEPPED is supported.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a float that is the requested statistic.</string> - </map> - <key>llGetSimulatorHostname</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>10.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the host-name of the machine which the script is running on.\nFor example, "sim225.agni.lindenlab.com".</string> - </map> - <key>llGetSPMaxMemory</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the maximum used memory for the current script. Only valid after using PROFILE_SCRIPT_MEMORY. Non-mono scripts always use 16k.\nReturns the integer of the most bytes used while llScriptProfiler was last active.</string> - </map> - <key>llGetStartParameter</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns an integer that is the script rez parameter.\nIf the object was rezzed by an agent, this function returns 0.</string> - </map> - <key>llGetStaticPath</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Starting position.</string> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Ending position.</string> - </map> - </map> - <map> - <key>Radius</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Radius of the character that the path is for, between 0.125m and 5.0m.</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Currently only accepts the parameter CHARACTER_TYPE; the options are identical to those used for llCreateCharacter. The default value is CHARACTER_TYPE_NONE.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string/> - </map> - <key>llGetStatus</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>StatusFlag</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>A STATUS_* flag</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns boolean value of the specified status (e.g. STATUS_PHANTOM) of the object the script is attached to.</string> - </map> - <key>llGetSubString</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>String</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a sub-string from String, in a range specified by the Start and End indicies (inclusive).\nUsing negative numbers for Start and/or End causes the index to count backwards from the length of the string, so 0, -1 would capture the entire string.\nIf Start is greater than End, the sub string is the exclusion of the entries.</string> - </map> - <key>llGetSunDirection</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a normalized vector of the direction of the sun in the region.\nReturns the sun's direction on the simulator.</string> - </map> - <key>llGetTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string that is the texture on face (the inventory name if it is a texture in the prim's inventory, otherwise the key).\nReturns the texture of a face, if it is found in object inventory, its key otherwise.</string> - </map> - <key>llGetTextureOffset</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the texture offset of face in the x and y components of a vector.</string> - </map> - <key>llGetTextureRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the texture rotation of side.</string> - </map> - <key>llGetTextureScale</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the texture scale of side in the x and y components of a vector.\nReturns the texture scale of a side in the x and y components of a vector.</string> - </map> - <key>llGetTime</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the time in seconds since the last region reset, script reset, or call to either llResetTime or llGetAndResetTime.</string> - </map> - <key>llGetTimeOfDay</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the time in seconds since Second Life midnight or since region up-time, whichever is smaller.\nThe Second Life day cycle is 4 hours.</string> - </map> - <key>llGetTimestamp</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns a time-stamp (UTC time zone) in the format: YYYY-MM-DDThh:mm:ss.ff..fZ.</string> - </map> - <key>llGetTorque</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the torque (if the script is physical).\nReturns a vector that is the torque (if the script is physical).</string> - </map> - <key>llGetUnixTime</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the number of seconds elapsed since 00:00 hours, Jan 1, 1970 UTC from the system clock.</string> - </map> - <key>llGetUsedMemory</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the current used memory for the current script. Non-mono scripts always use 16K.\nReturns the integer of the number of bytes of memory currently in use by the script. Non-mono scripts always use 16K.</string> - </map> - <key>llGetUsername</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the username of an avatar, if the avatar is connected to the current region, or if the name has been cached. Otherwise, returns an empty string. Use llRequestUsername if the avatar may be absent from the region.</string> - </map> - <key>llGetVel</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the velocity of the object.\nReturns a vector that is the velocity of the object.</string> - </map> - <key>llGetWallclock</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the time in seconds since midnight California Pacific time (PST/PDT).\nReturns the time in seconds since simulator's time-zone midnight (Pacific Time).</string> - </map> - <key>llGiveInventory</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Give InventoryItem to destination represented by TargetID, as permitted by the permissions system.\nTargetID may be any agent or an object in the same region.</string> - </map> - <key>llGiveInventoryList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>3.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>FolderName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>InventoryItems</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Give InventoryItems to destination (represented by TargetID) as a new folder of items, as permitted by the permissions system.\nTargetID may be any agent or an object in the same region. If TargetID is an object, the items are passed directly to the object inventory (no folder is created).</string> - </map> - <key>llGiveMoney</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Amount</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Transfers Amount of L$ from script owner to AvatarID.\nThis call will silently fail if PERMISSION_DEBIT has not been granted.</string> - </map> - <key>llGodLikeRezObject</key> - <map> - <key>god-mode</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItemID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Rez directly off of a UUID if owner has god-bit set.</string> - </map> - <key>llGround</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the ground height at the object position + offset.\nReturns the ground height at the object's position + Offset.</string> - </map> - <key>llGroundContour</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the ground contour direction below the object position + Offset.\nReturns the ground contour at the object's position + Offset.</string> - </map> - <key>llGroundNormal</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the ground normal below the object position + offset.\nReturns the ground contour at the object's position + Offset.</string> - </map> - <key>llGroundRepel</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Height</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Distance above the ground.</string> - </map> - </map> - <map> - <key>Water</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE then hover above water too.</string> - </map> - </map> - <map> - <key>Tau</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Seconds to critically damp in.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Critically damps to height if within height * 0.5 of level (either above ground level or above the higher of land and water if water == TRUE).\nCritically damps to fHeight if within fHeight * 0.5 of ground or water level.\n - The height is above ground level if iWater is FALSE or above the higher of land and water if iWater is TRUE.\n - Do not use with vehicles. Only works in physics-enabled objects.</string> - </map> - <key>llGroundSlope</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the ground slope below the object position + Offset.\nReturns the ground slope at the object position + Offset.</string> - </map> - <key>llHTTPRequest</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>A valid HTTP/HTTPS URL.</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Configuration parameters, specified as HTTP_* flag-value pairs.</string> - </map> - </map> - <map> - <key>Body</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Contents of the request.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sends an HTTP request to the specified URL with the Body of the request and Parameters.\nReturns a key that is a handle identifying the HTTP request made.</string> - </map> - <key>llHTTPResponse</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>HTTPRequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>A valid HTTP request key.</string> - </map> - </map> - <map> - <key>Status</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>HTTP Status (200, 400, 404, etc.).</string> - </map> - </map> - <map> - <key>Body</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Contents of the response.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Responds to an incoming HTTP request which was triggerd by an http_request event within the script. HTTPRequestID specifies the request to respond to (this ID is supplied in the http_request event handler). Status and Body specify the status code and message to respond with.</string> - </map> - <key>llInsertString</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>TargetVariable</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>SourceVariable</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Inserts SourceVariable into TargetVariable at Position, and returns the result.\nInserts SourceVariable into TargetVariable at Position and returns the result. Note this does not alter TargetVariable.</string> - </map> - <key>llInstantMessage</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>2.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>IMs Text to the user identified.\nSend Text to the user as an instant message.</string> - </map> - <key>llIntegerToBase64</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string that is a Base64 big endian encode of Value.\nEncodes the Value as an 8-character Base64 string.</string> - </map> - <key>llJson2List</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>JSON</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Converts the top level of the JSON string to a list.</string> - </map> - <key>llJsonGetValue</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>JSON</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Specifiers</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Gets the value indicated by Specifiers from the JSON string.</string> - </map> - <key>llJsonSetValue</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>JSON</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Specifiers</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a new JSON string that is the JSON given with the Value indicated by Specifiers set to Value.</string> - </map> - <key>llJsonValueType</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>JSON</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Specifiers</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the type constant (JSON_*) for the value in JSON indicated by Specifiers.</string> - </map> - <key>llKey2Name</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Avatar or rezzed prim UUID.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the name of the prim or avatar specified by ID. The ID must be a valid rezzed prim or avatar key in the current simulator, otherwise an empty string is returned.\nFor avatars, the returned name is the legacy name</string> - </map> - <key>llKeyCountKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string> - Starts an asychronous transaction the request the number of keys in the data store. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will the the number of keys in the system. - </string> - </map> - <key>llKeysKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>First</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Index of the first key to return.</string> - </map> - </map> - <map> - <key>Count</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>The number of keys to return.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Starts an asychronous transaction the request a number of keys from the data store. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. The error XP_ERROR_KEY_NOT_FOUND is returned if First is greater than or equal to the number of keys in the data store. In the success case the subsequent items will be the keys requested. The number of keys returned may be less than requested if the return value is too large or if there is not enough keys remaining. The order keys are returned is not guaranteed but is stable between subsequent calls as long as no keys are added or removed. Because the keys are returned in a comma-delimited list it is not recommended to use commas in key names if this function is used. - </string> - </map> - <key>llLinkParticleSystem</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag</string> - </map> - </map> - <map> - <key>Rules</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Particle system rules list in the format [ rule1, data1, rule2, data2 . . . ruleN, dataN ]</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Creates a particle system in prim LinkNumber based on Rules. An empty list removes a particle system from object.\nList format is [ rule-1, data-1, rule-2, data-2 ... rule-n, data-n ].\nThis is identical to llParticleSystem except that it applies to a specified linked prim and not just the prim the script is in.</string> - </map> - <key>llLinkSitTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag of the prim.</string> - </map> - </map> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Position for the sit target, relative to the prim's position.</string> - </map> - </map> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string>Rotation (relative to the prim's rotation) for the avatar.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the sit location for the linked prim(s). If Offset == <0,0,0> clear it.\nSet the sit location for the linked prim(s). The sit location is relative to the prim's position and rotation.</string> - </map> - <key>llList2CSV</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Creates a string of comma separated values from the list.\nCreate a string of comma separated values from the specified list.</string> - </map> - <key>llList2Float</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the float at Index in the list.\nReturns the value at Index in the specified list. If Index describes a location not in the list, or the value cannot be type-cast to a float, then zero is returned.</string> - </map> - <key>llList2Integer</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the integer at Index in the list.\nReturns the value at Index in the specified list. If Index describes a location not in the list, or the value cannot be type-cast to an integer, then zero is returned.</string> - </map> - <key>llList2Json</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>JsonType</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Type is JSON_ARRAY or JSON_OBJECT.</string> - </map> - </map> - <map> - <key>Values</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of values to convert.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Converts either a strided list of key:value pairs to a JSON_OBJECT, or a list of values to a JSON_ARRAY.</string> - </map> - <key>llList2Key</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the key at Index in the list.\nReturns the value at Index in the specified list. If Index describes a location not in the list, or the value cannot be type-cast to a key, then null string is returned.</string> - </map> - <key>llList2List</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a subset of entries from ListVariable, in a range specified by the Start and End indicies (inclusive).\nUsing negative numbers for Start and/or End causes the index to count backwards from the length of the string, so 0, -1 would capture the entire string.\nIf Start is greater than End, the sub string is the exclusion of the entries.</string> - </map> - <key>llList2ListStrided</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Stride</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the strided slice of the list from Start to End.\nReturns a copy of the strided slice of the specified list from Start to End.</string> - </map> - <key>llList2Rot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the rotation at Index in the list.\nReturns the value at Index in the specified list. If Index describes a location not in the list, or the value cannot be type-cast to rotation, thenZERO_ROTATION is returned.</string> - </map> - <key>llList2String</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the string at Index in the list.\nReturns the value at Index in the specified list as a string. If Index describes a location not in the list then null string is returned.</string> - </map> - <key>llList2Vector</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Index</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Copies the vector at Index in the list.\nReturns the value at Index in the specified list. If Index describes a location not in the list, or the value cannot be type-cast to a vector, then ZERO_VECTOR is returned.</string> - </map> - <key>llListen</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>SpeakersName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>SpeakersID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Creates a listen callback for Text on Channel from SpeakersName and SpeakersID (SpeakersName, SpeakersID, and/or Text can be empty) and returns an identifier that can be used to deactivate or remove the listen.\nNon-empty values for SpeakersName, SpeakersID, and Text will filter the results accordingly, while empty strings and NULL_KEY will not filter the results, for string and key parameters respectively.\nPUBLIC_CHANNEL is the public chat channel that all avatars see as chat text. DEBUG_CHANNEL is the script debug channel, and is also visible to nearby avatars. All other channels are are not sent to avatars, but may be used to communicate with scripts.</string> - </map> - <key>llListenControl</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ChannelHandle</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Active</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Makes a listen event callback active or inactive. Pass in the value returned from llListen to the iChannelHandle parameter to specify which listener you are controlling.\nUse boolean values to specify Active</string> - </map> - <key>llListenRemove</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ChannelHandle</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes a listen event callback. Pass in the value returned from llListen to the iChannelHandle parameter to specify which listener to remove.</string> - </map> - <key>llListFindList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Find</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the index of the first instance of Find in ListVariable. Returns -1 if not found.\nReturns the position of the first instance of the Find list in the ListVariable. Returns -1 if not found.</string> - </map> - <key>llListInsertList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Target</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list that contains all the elements from Target but with the elements from ListVariable inserted at Position start.\nReturns a new list, created by inserting ListVariable into the Target list at Position. Note this does not alter the Target.</string> - </map> - <key>llListRandomize</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Stride</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a version of the input ListVariable which has been randomized by blocks of size Stride.\nIf the remainder from the length of the list, divided by the stride is non-zero, this function does not randomize the list.</string> - </map> - <key>llListReplaceList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Target</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>End</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a list that is Target with Start through End removed and ListVariable inserted at Start.\nReturns a list replacing the slice of the Target list from Start to End with the specified ListVariable. Start and End are inclusive, so 0, 1 would replace the first two entries and 0, 0 would replace only the first list entry.</string> - </map> - <key>llListSort</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List to sort.</string> - </map> - </map> - <map> - <key>Stride</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Stride length.</string> - </map> - </map> - <map> - <key>Ascending</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean. TRUE = result in ascending order, FALSE = result in descending order.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the specified list, sorted into blocks of stride in ascending order (if Ascending is TRUE, otherwise descending). Note that sort only works if the first entry of each block is the same datatype.</string> - </map> - <key>llListStatistics</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Operation</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>One of LIST_STAT_* values</string> - </map> - </map> - <map> - <key>ListVariable</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Variable to analyze.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Performs a statistical aggregate function, specified by a LIST_STAT_* constant, on ListVariables.\nThis function allows a script to perform a statistical operation as defined by operation on a list composed of integers and floats.</string> - </map> - <key>llLoadURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Shows dialog to avatar AvatarID offering to load web page at URL. If user clicks yes, launches their web browser.\nllLoadURL displays a dialogue box to the user, offering to load the specified web page using the default web browser.</string> - </map> - <key>llLog</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the natural logarithm of Value. Returns zero if Value <= 0.\nReturns the base e (natural) logarithm of the specified Value.</string> - </map> - <key>llLog10</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the base 10 logarithm of Value. Returns zero if Value <= 0.\nReturns the base 10 (common) logarithm of the specified Value.</string> - </map> - <key>llLookAt</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Target</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Strength</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Damping</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Cause object name to point its forward axis towards Target, at a force controlled by Strength and Damping.\nGood Strength values are around half the mass of the object and good Damping values are less than 1/10th of the Strength.\nAsymmetrical shapes require smaller Damping. A Strength of 0.0 cancels the look at.</string> - </map> - <key>llLoopSound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays specified Sound, looping indefinitely, at Volume (0.0 - 1.0).\nOnly one sound may be attached to an object at a time.\nA second call to llLoopSound with the same key will not restart the sound, but the new volume will be used. This allows control over the volume of already playing sounds.\nSetting the volume to 0 is not the same as calling llStopSound; a sound with 0 volume will continue to loop.\nTo restart the sound from the beginning, call llStopSound before calling llLoopSound again.</string> - </map> - <key>llLoopSoundMaster</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays attached Sound, looping at volume (0.0 - 1.0), and declares it a sync master.\nBehaviour is identical to llLoopSound, with the addition of marking the source as a "Sync Master", causing "Slave" sounds to sync to it. If there are multiple masters within a viewers interest area, the most audible one (a function of both distance and volume) will win out as the master.\nThe use of multiple masters within a small area is unlikely to produce the desired effect.</string> - </map> - <key>llLoopSoundSlave</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays attached sound looping at volume (0.0 - 1.0), synced to most audible sync master.\nBehaviour is identical to llLoopSound, unless there is a "Sync Master" present.\nIf a Sync Master is already playing the Slave sound will begin playing from the same point the master is in its loop synchronizing the loop points of both sounds.\nIf a Sync Master is started when the Slave is already playing, the Slave will skip to the correct position to sync with the Master.</string> - </map> - <key>llMakeExplosion</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Particles</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Scale</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Lifetime</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Make a round explosion of particles. Deprecated: Use llParticleSystem instead.\nMake a round explosion of particles using texture from the objects inventory. Deprecated: Use llParticleSystem instead.</string> - </map> - <key>llMakeFire</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Particles</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Scale</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Lifetime</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Make fire like particles. Deprecated: Use llParticleSystem instead.\nMake fire particles using texture from the objects inventory. Deprecated: Use llParticleSystem instead.</string> - </map> - <key>llMakeFountain</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Particles</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Scale</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Lifetime</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Bounce</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Bounce_Offset</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Make a fountain of particles. Deprecated: Use llParticleSystem instead.\nMake a fountain of particles using texture from the objects inventory. Deprecated: Use llParticleSystem instead.</string> - </map> - <key>llMakeSmoke</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Particles</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Scale</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Lifetime</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Make smoke like particles. Deprecated: Use llParticleSystem instead.\nMake smoky particles using texture from the objects inventory. Deprecated: Use llParticleSystem instead.</string> - </map> - <key>llManageEstateAccess</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Action</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>One of the ESTATE_ACCESS_ALLOWED_* actions.</string> - </map> - </map> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>UUID of the avatar or group to act upon.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Adds or removes agents from the estate's agent access or ban lists, or groups to the estate's group access list. Action is one of the ESTATE_ACCESS_ALLOWED_* operations to perform.\nReturns an integer representing a boolean, TRUE if the call was successful; FALSE if throttled, invalid action, invalid or null id or object owner is not allowed to manage the estate.\nThe object owner is notified of any changes, unless PERMISSION_SILENT_ESTATE_MANAGEMENT has been granted to the script.</string> - </map> - <key>llMapDestination</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>RegionName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Direction</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Opens world map for avatar who touched is is wearing the script, centred on RegionName with Position highlighted. Only works for scripts attached to avatar, or during touch events.\nDirection currently has no effect.</string> - </map> - <key>llMD5String</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Nonce</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string of 32 hex characters that is an RSA Data Security Inc., MD5 Message-Digest Algorithm of Text with Nonce used as the salt.\nReturns a 32-character hex string. (128-bit in binary.)</string> - </map> - <key>llMessageLinked</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Number</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sends Number, Text, and ID to members of the link set identified by LinkNumber.\nLinkNumber is either a linked number (available through llGetLinkNumber) or a LINK_* constant.</string> - </map> - <key>llMinEventDelay</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Delay</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the minimum time between events being handled.</string> - </map> - <key>llModifyLand</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Action</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>LAND_LEVEL, LAND_RAISE, LAND_LOWER, LAND_SMOOTH, LAND_NOISE or LAND_REVERT</string> - </map> - </map> - <map> - <key>Area</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>0, 1, 2 (2m x 2m, 4m x 4m, or 8m x 8m)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Modify land with action (LAND_LEVEL, LAND_RAISE, LAND_LOWER, LAND_SMOOTH, LAND_NOISE, LAND_REVERT) on size (0, 1, 2, corresponding to 2m x 2m, 4m x 4m, 8m x 8m).</string> - </map> - <key>llModPow</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Power</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Modulus</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a Value raised to the Power, mod Modulus. ((a**b)%c) b is capped at 0xFFFF (16 bits).\nReturns (Value ^ Power) % Modulus. (Value raised to the Power, Modulus). Value is capped at 0xFFFF (16 bits).</string> - </map> - <key>llMoveToTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Target</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Tau</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Critically damp to Target in Tau seconds (if the script is physical).\nCritically damp to position target in tau-seconds if the script is physical. Good tau-values are greater than 0.2. A tau of 0.0 stops the critical damping.</string> - </map> - <key>llNavigateTo</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Location</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Region coordinates for the character to navigate to.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of parameters to control the type of path-finding used. Currently only FORCE_DIRECT_PATH supported.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Navigate to destination.\nDirects an object to travel to a defined position in the region or adjacent regions.</string> - </map> - <key>llOffsetTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>OffsetS</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>OffsetT</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the texture S and T offsets for the chosen Face.\nIf Face is ALL_SIDES this function sets the texture offsets for all faces.</string> - </map> - <key>llOpenRemoteDataChannel</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Requests a channel to listen for XML-RPC calls. (Deprecated: XML-RPC should not be used. Use http-in instead.)\nWill trigger a remote_data event with type = REMOTE_DATA_CHANNEL and a channel ID (key) once it is available.\nThis channel ID must be referenced in the XML-RPC call to the script (from the internet) -- so the key must somehow get to the external XML-RPC client.</string> - </map> - <key>llOverMyLand</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns TRUE if id ID over land owned by the script owner, otherwise FALSE.\nReturns TRUE if key ID is over land owned by the object owner, FALSE otherwise.</string> - </map> - <key>llOwnerSay</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>says Text to owner only (if owner is in region).\nSays Text to the owner of the object running the script, if the owner has been within the object's simulator since logging into Second Life, regardless of where they may be in-world.</string> - </map> - <key>llParcelMediaCommandList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>2.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>CommandList</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A list of PARCEL_MEDIA_COMMAND_* flags and their parameters </string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Controls the playback of multimedia resources on a parcel or for an agent, via one or more PARCEL_MEDIA_COMMAND_* arguments specified in CommandList.</string> - </map> - <key>llParcelMediaQuery</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>2.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>QueryList</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Queries the media properties of the parcel containing the script, via one or more PARCEL_MEDIA_COMMAND_* arguments specified in CommandList.\nThis function will only work if the script is contained within an object owned by the land-owner (or if the land is owned by a group, only if the object has been deeded to the group).</string> - </map> - <key>llParseString2List</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Separators</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Spacers</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Converts Text into a list, discarding Separators, keeping Spacers (Separators and Spacers must be lists of strings, maximum of 8 each).\nSeparators and Spacers are lists of strings with a maximum of 8 entries each.</string> - </map> - <key>llParseStringKeepNulls</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>list</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Separators</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Spacers</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Breaks Text into a list, discarding separators, keeping spacers, keeping any null values generated. (separators and spacers must be lists of strings, maximum of 8 each).\nllParseStringKeepNulls works almost exactly like llParseString2List, except that if a null is found it will add a null-string instead of discarding it like llParseString2List does.</string> - </map> - <key>llParticleSystem</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Creates a particle system in the prim the script is attached to, based on Parameters. An empty list removes a particle system from object.\nList format is [ rule-1, data-1, rule-2, data-2 ... rule-n, data-n ].</string> - </map> - <key>llPassCollisions</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Pass</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE, collisions are passed from children on to parents.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Configures how collision events are passed to scripts in the linkset.\nIf Pass == TRUE, collisions involving collision-handling scripted child prims are also passed on to the root prim. If Pass == FALSE (default behavior), such collisions will only trigger events in the affected child prim.</string> - </map> - <key>llPassTouches</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Pass</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE, touches are passed from children on to parents.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Configures how touch events are passed to scripts in the linkset.\nIf Pass == TRUE, touches involving touch-handling scripted child prims are also passed on to the root prim. If Pass == FALSE (default behavior), such touches will only trigger events in the affected child prim.</string> - </map> - <key>llPatrolPoints</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Points</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A list of vectors for the character to travel through sequentially. The list must contain at least two entries.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>No options available at this time.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Patrol a list of points.\nSets the points for a character (llCreateCharacter) to patrol along.</string> - </map> - <key>llPlaySound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays Sound once, at Volume (0.0 - 1.0) and attached to the object.\nOnly one sound may be attached to an object at a time, and attaching a new sound or calling llStopSound will stop the previously attached sound.\nA second call to llPlaySound with the same sound will not restart the sound, but the new volume will be used, which allows control over the volume of already playing sounds.\nTo restart the sound from the beginning, call llStopSound before calling llPlaySound again.</string> - </map> - <key>llPlaySoundSlave</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays attached Sound once, at Volume (0.0 - 1.0), synced to next loop of most audible sync master.\nBehaviour is identical to llPlaySound, unless there is a "Sync Master" present. If a Sync Master is already playing, the Slave sound will not be played until the Master hits its loop point and returns to the beginning.\nllPlaySoundSlave will play the sound exactly once; if it is desired to have the sound play every time the Master loops, either use llLoopSoundSlave with extra silence padded on the end of the sound or ensure that llPlaySoundSlave is called at least once per loop of the Master.</string> - </map> - <key>llPow</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Exponent</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the Value raised to the power Exponent, or returns 0 and triggers Math Error for imaginary results.\nReturns the Value raised to the Exponent.</string> - </map> - <key>llPreloadSound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Causes nearby viewers to preload the Sound from the object's inventory.\nThis is intended to prevent delays in starting new sounds when called upon.</string> - </map> - <key>llPursue</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Agent or object to pursue.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Parameters for pursuit.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Chase after a target.\nCauses the character (llCharacter) to pursue the target defined by TargetID.</string> - </map> - <key>llPushObject</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ObjectID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Impulse</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>AngularImpulse</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Applies Impulse and AngularImpulse to ObjectID.\nApplies the supplied impulse and angular impulse to the object specified.</string> - </map> - <key>llReadKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Key</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Starts an asychronous transaction to retrieve the value associated with the key given. Will fail with XP_ERROR_KEY_NOT_FOUND if the key does not exist. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is a two element commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will be the value associated with the key. - </string> - </map> - <key>llRefreshPrimURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>20.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Reloads the web page shown on the sides of the object.</string> - </map> - <key>llRegionSay</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Any integer value except zero.</string> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Message to be transmitted.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Broadcasts Text to entire region on Channel (except for channel 0).</string> - </map> - <key>llRegionSayTo</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>TargetID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Avatar or object to say to.</string> - </map> - </map> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Output channel, any integer value.</string> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Message to be transmitted.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Says Text, on Channel, to avatar or object indicated by TargetID (if within region).\nIf TargetID is an avatar and Channel is nonzero, Text can be heard by any attachment on the avatar.</string> - </map> - <key>llReleaseCamera</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Return camera to agent.\nDeprecated: Use llClearCameraParams instead.</string> - </map> - <key>llReleaseControls</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Stop taking inputs.\nStop taking inputs from the avatar.</string> - </map> - <key>llReleaseURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>URL to release.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Releases the specified URL, which was previously obtained using llRequestURL. Once released, the URL will no longer be usable.</string> - </map> - <key>llRemoteDataReply</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>3.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ChannelID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>MessageID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>sData</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>String data to send</string> - </map> - </map> - <map> - <key>iData</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Integer data to send</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Send an XML-RPC reply to MessageID on ChannelID with payload of string sData and integer iData. Deprecated: Use HTTP functions/events instead.\nThe size of sData is limited to 254 characters.</string> - </map> - <key>llRemoteDataSetRegion</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Deprecated: Use HTTP functions/events instead.\nIf an object using remote data channels changes regions, you must call this function to re-register the remote data channels.\nYou do not need to make this call if you don't change regions.</string> - </map> - <key>llRemoteLoadScriptPin</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>3.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ObjectID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Target prim to attempt copying into.</string> - </map> - </map> - <map> - <key>ScriptName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Name of the script in current inventory to copy.</string> - </map> - </map> - <map> - <key>PIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Integer set on target prim as a Personal Information Number code.</string> - </map> - </map> - <map> - <key>Running</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>If the script should be set running in the target prim.</string> - </map> - </map> - <map> - <key>StartParameter</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Integer. Parameter passed to the script if set to be running.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If the owner of the object containing this script can modify the object identified by the specified object key, and if the PIN matches the PIN previously set using llSetRemoteScriptAccessPin (on the target prim), then the script will be copied into target. Running is a boolean specifying whether the script should be enabled once copied into the target object.</string> - </map> - <key>llRemoveFromLandBanList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Remove avatar from the land ban list.\nRemove specified avatar from the land parcel ban list.</string> - </map> - <key>llRemoveFromLandPassList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Remove avatar from the land pass list.\nRemove specified avatar from the land parcel pass list.</string> - </map> - <key>llRemoveInventory</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Remove the named inventory item.\nRemove the named inventory item from the object inventory.</string> - </map> - <key>llRemoveVehicleFlags</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Vehiclelags</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes the enabled bits in 'flags'.\nSets the vehicle flags to FALSE. Valid parameters can be found in the vehicle flags constants section.</string> - </map> - <key>llRequestAgentData</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Data</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests data about AvatarID. When data is available the dataserver event will be raised.\nThis function requests data about an avatar. If and when the information is collected, the dataserver event is triggered with the key returned from this function passed in the requested parameter. See the agent data constants (DATA_*) for details about valid values of data and what each will return in the dataserver event.</string> - </map> - <key>llRequestDisplayName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Avatar UUID</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests the display name of the agent. When the display name is available the dataserver event will be raised.\nThe avatar identified does not need to be in the same region or online at the time of the request.\nReturns a key that is used to identify the dataserver event when it is raised.</string> - </map> - <key>llRequestExperiencePermissions</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AgentID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>unused</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Not used, should be ""</string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Ask the agent for permission to participate in an experience. This request is similar to llRequestPermissions with the following permissions: PERMISSION_TAKE_CONTROLS, PERMISSION_TRIGGER_ANIMATION, PERMISSION_ATTACH, PERMISSION_TRACK_CAMERA, PERMISSION_CONTROL_CAMERA and PERMISSION_TELEPORT. However, unlike llRequestPermissions the decision to allow or block the request is persistent and applies to all scripts using the experience grid wide. Subsequent calls to llRequestExperiencePermissions from scripts in the experience will receive the same response automatically with no user interaction. One of experience_permissions or experience_permissions_denied will be generated in response to this call. Outstanding permission requests will be lost if the script is derezzed, moved to another region or reset. - </string> - </map> - <key>llRequestInventoryData</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests data for the named InventoryItem.\nWhen data is available, the dataserver event will be raised with the key returned from this function in the requested parameter.\nThe only request currently implemented is to request data from landmarks, where the data returned is in the form "<float, float, float>" which can be cast to a vector. This position is in region local coordinates.</string> - </map> - <key>llRequestPermissions</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>PermissionMask</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Ask AvatarID to allow the script to perform certain actions, specified in the PermissionMask bitmask. PermissionMask should be one or more PERMISSION_* constants. Multiple permissions can be requested simultaneously by ORing the constants together. Many of the permissions requests can only go to object owner.\nThis call will not stop script execution. If the avatar grants the requested permissions, the run_time_permissions event will be called.</string> - </map> - <key>llRequestSecureURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Requests one HTTPS:// (SSL) URL for use by this object. The http_request event is triggered with results.\nReturns a key that is the handle used for identifying the request in the http_request event.</string> - </map> - <key>llRequestSimulatorData</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>RegionName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Data</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests the specified Data about RegionName. When the specified data is available, the dataserver event is raised.\nData should use one of the DATA_SIM_* constants.\nReturns a dataserver query ID and triggers the dataserver event when data is found.</string> - </map> - <key>llRequestURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Requests one HTTP:// URL for use by this script. The http_request event is triggered with the result of the request.\nReturns a key that is the handle used for identifying the result in the http_request event.</string> - </map> - <key>llRequestUsername</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests single-word user-name of an avatar. When data is available the dataserver event will be raised.\nRequests the user-name of the identified agent. When the user-name is available the dataserver event is raised.\nThe agent identified does not need to be in the same region or online at the time of the request.\nReturns a key that is used to identify the dataserver event when it is raised.</string> - </map> - <key>llResetAnimationOverride</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AnimationState</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Resets the animation of the specified animation state to the default value.\nIf animation state equals "ALL", then all animation states are reset.</string> - </map> - <key>llResetLandBanList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Removes all residents from the land ban list.</string> - </map> - <key>llResetLandPassList</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Removes all residents from the land access/pass list.</string> - </map> - <key>llResetOtherScript</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ScriptName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Resets the named script.</string> - </map> - <key>llResetScript</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Resets the script.</string> - </map> - <key>llResetTime</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Sets the time to zero.\nSets the internal timer to zero.</string> - </map> - <key>llReturnObjectsByID</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ObjectIDs</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>List of object UUIDs to be returned.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Return objects using their UUIDs.\nRequires the PERMISSION_RETURN_OBJECTS permission and that the script owner owns the parcel the returned objects are in, or is an estate manager or region owner.</string> - </map> - <key>llReturnObjectsByOwner</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Object owner's UUID.</string> - </map> - </map> - <map> - <key>Scope</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Return objects based upon their owner and a scope of parcel, parcel owner, or region.\nRequires the PERMISSION_RETURN_OBJECTS permission and that the script owner owns the parcel the returned objects are in, or is an estate manager or region owner.</string> - </map> - <key>llRezAtRoot</key> - <map> - <key>energy</key> - <real>200.0</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>StartParameter</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Instantiate owner's InventoryItem at Position with Velocity, Rotation and with StartParameter. The last selected root object's location will be set to Position.\nCreates object's inventory item at the given Position, with Velocity, Rotation, and StartParameter.</string> - </map> - <key>llRezObject</key> - <map> - <key>energy</key> - <real>200</real> - <key>sleep</key> - <real>0.1</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>StartParameter</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Instantiate owners InventoryItem at Position with Velocity, Rotation and with start StartParameter.\nCreates object's inventory item at Position with Velocity and Rotation supplied. The StartParameter value will be available to the newly created object in the on_rez event or through the llGetStartParameter function.\nThe Velocity parameter is ignored if the rezzed object is not physical.</string> - </map> - <key>llRot2Angle</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation angle represented by Rotation.\nReturns the angle represented by the Rotation.</string> - </map> - <key>llRot2Axis</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation axis represented by Rotation.\nReturns the axis represented by the Rotation.</string> - </map> - <key>llRot2Euler</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the Euler representation (roll, pitch, yaw) of Rotation.\nReturns the Euler Angle representation of the Rotation.</string> - </map> - <key>llRot2Fwd</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the forward vector defined by Rotation.\nReturns the forward axis represented by the Rotation.</string> - </map> - <key>llRot2Left</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the left vector defined by Rotation.\nReturns the left axis represented by the Rotation.</string> - </map> - <key>llRot2Up</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the up vector defined by Rotation.\nReturns the up axis represented by the Rotation.</string> - </map> - <key>llRotateTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Radians</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the texture rotation for the specified Face to angle Radians.\nIf Face is ALL_SIDES, rotates the texture of all sides.</string> - </map> - <key>llRotBetween</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>rotation</string> - <key>arguments</key> - <array> - <map> - <key>Vector1</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Vector2</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the rotation to rotate Vector1 to Vector2.\nReturns the rotation needed to rotate Vector1 to Vector2.</string> - </map> - <key>llRotLookAt</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Strength</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Damping</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Cause object to rotate to Rotation, with a force function defined by Strength and Damping parameters. Good strength values are around half the mass of the object and good damping values are less than 1/10th of the strength.\nAsymmetrical shapes require smaller damping.\nA strength of 0.0 cancels the look at.</string> - </map> - <key>llRotTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>LeeWay</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set rotations with error of LeeWay radians as a rotational target, and return an ID for the rotational target.\nThe returned number is a handle that can be used in at_rot_target and llRotTargetRemove.</string> - </map> - <key>llRotTargetRemove</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Handle</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes rotational target number.\nRemove rotational target indicated by the handle.</string> - </map> - <key>llRound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns Value rounded to the nearest integer.\nReturns the Value rounded to the nearest integer.</string> - </map> - <key>llSameGroup</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns TRUE if avatar ID is in the same region and has the same active group, otherwise FALSE.\nReturns TRUE if the object or agent identified is in the same simulator and has the same active group as this object. Otherwise, returns FALSE.</string> - </map> - <key>llSay</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Channel to use to say text on.</string> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Text to say.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Says Text on Channel.\nThis chat method has a range of 20m radius.\nPUBLIC_CHANNEL is the public chat channel that all avatars see as chat text. DEBUG_CHANNEL is the script debug channel, and is also visible to nearby avatars. All other channels are are not sent to avatars, but may be used to communicate with scripts.</string> - </map> - <key>llScaleByFactor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>ScalingFactor</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>The multiplier to be used with the prim sizes and their local positions.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Attempts to resize the entire object by ScalingFactor, maintaining the size-position ratios of the prims.\n\nResizing is subject to prim scale limits and linkability limits. This function can not resize the object if the linkset is physical, a pathfinding character, in a keyframed motion, or if resizing would cause the parcel to overflow.\nReturns a boolean (an integer) TRUE if it succeeds, FALSE if it fails.</string> - </map> - <key>llScaleTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Horizontal</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Vertical</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the diffuse texture Horizontal and Vertical repeats on Face of the prim the script is attached to.\nIf Face == ALL_SIDES, all sides are set in one call.\nNegative values for horizontal and vertical will flip the texture.</string> - </map> - <key>llScriptDanger</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns TRUE if Position is over public land, sandbox land, land that doesn't allow everyone to edit and build, or land that doesn't allow outside scripts.\nReturns true if the position is over public land, land that doesn't allow everyone to edit and build, or land that doesn't allow outside scripts.</string> - </map> - <key>llScriptProfiler</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>State</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>PROFILE_NONE or PROFILE_SCRIPT_MEMORY flags to control the state.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Enables or disables script profiling options. Currently only supports PROFILE_SCRIPT_MEMORY (Mono only) and PROFILE_NONE.\nMay significantly reduce script performance.</string> - </map> - <key>llSendRemoteData</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>3.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>ChannelID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Destination</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: use HTTP functions and events instead.\nSends an XML-RPC request to Destination through ChannelID with payload of ChannelID (in a string), integer Value and string Text.\nReturns a key that is the message_id for the resulting remote_data events.</string> - </map> - <key>llSensor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Name</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Object or avatar name.</string> - </map> - </map> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Object or avatar UUID.</string> - </map> - </map> - <map> - <key>Type</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Bit-field mask of AGENT, AGENT_BY_LEGACY_NAME, AGENT_BY_USERNAME, ACTIVE, PASSIVE, and/or SCRIPTED</string> - </map> - </map> - <map> - <key>Range</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Distance to scan. 0.0 - 96.0m.</string> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Angle, in radians, from the local x-axis of the prim to scan.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Performs a single scan for Name and ID with Type (AGENT, ACTIVE, PASSIVE, and/or SCRIPTED) within Range meters and Arc radians of forward vector.\nSpecifying a blank Name, 0 Type, or NULL_KEY ID will prevent filtering results based on that parameter. A range of 0.0 does not perform a scan.\nResults are returned in the sensor and no_sensor events.</string> - </map> - <key>llSensorRemove</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>removes sensor.\nRemoves the sensor set by llSensorRepeat.</string> - </map> - <key>llSensorRepeat</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Name</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Object or avatar name.</string> - </map> - </map> - <map> - <key>ID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>Object or avatar UUID.</string> - </map> - </map> - <map> - <key>Type</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Bit-field mask of AGENT, AGENT_BY_LEGACY_NAME, AGENT_BY_USERNAME, ACTIVE, PASSIVE, and/or SCRIPTED</string> - </map> - </map> - <map> - <key>Range</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Distance to scan. 0.0 - 96.0m.</string> - </map> - </map> - <map> - <key>Arc</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Angle, in radians, from the local x-axis of the prim to scan.</string> - </map> - </map> - <map> - <key>Rate</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Period, in seconds, between scans.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Initiates a periodic scan every Rate seconds, for Name and ID with Type (AGENT, ACTIVE, PASSIVE, and/or SCRIPTED) within Range meters and Arc radians of forward vector.\nSpecifying a blank Name, 0 Type, or NULL_KEY ID will prevent filtering results based on that parameter. A range of 0.0 does not perform a scan.\nResults are returned in the sensor and no_sensor events.</string> - </map> - <key>llSetAlpha</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Opacity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the alpha (opacity) of Face.\nSets the alpha (opacity) value for Face. If Face is ALL_SIDES, sets the alpha for all faces. The alpha value is interpreted as an opacity percentage (1.0 is fully opaque, and 0.2 is mostly transparent). This function will clamp alpha values less than 0.1 to 0.1 and greater than 1.0 to 1.</string> - </map> - <key>llSetAngularVelocity</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AngVel</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>The angular velocity to set the object to.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>If TRUE, the AngVel is treated as a local directional vector instead of a regional directional vector.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets an object's angular velocity to AngVel, in local coordinates if Local == TRUE (if the script is physical).\nHas no effect on non-physical objects.</string> - </map> - <key>llSetAnimationOverride</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AnimationState</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>AnimationName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the animation (in object inventory) that will play for the given animation state.\nTo use this function the script must obtain the PERMISSION_OVERRIDE_ANIMATIONS permission.</string> - </map> - <key>llSetBuoyancy</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Buoyancy</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the tasks buoyancy (0 is none, < 1.0 sinks, 1.0 floats, > 1.0 rises).\nSet the object buoyancy. A value of 0 is none, less than 1.0 sinks, 1.0 floats, and greater than 1.0 rises.</string> - </map> - <key>llSetCameraAtOffset</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the camera used in this object, at offset, if an avatar sits on it.\nSets the offset that an avatar's camera will be moved to if the avatar sits on the object.</string> - </map> - <key>llSetCameraEyeOffset</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the camera eye offset used in this object if an avatar sits on it.</string> - </map> - <key>llSetCameraParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets multiple camera parameters at once. List format is [ rule-1, data-1, rule-2, data-2 . . . rule-n, data-n ].</string> - </map> - <key>llSetClickAction</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Action</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>A CLICK_ACTION_* flag</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the action performed when a prim is clicked upon.</string> - </map> - <key>llSetColor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Color</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the color, for the face.\nSets the color of the side specified. If Face is ALL_SIDES, sets the color on all faces.</string> - </map> - <key>llSetContentType</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>HTTPRequestID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>A valid http_request() key</string> - </map> - </map> - <map> - <key>ContentType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Media type to use with any following llHTTPResponse(HTTPRequestID, ...)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the media type of an LSL HTTP server response to ContentType.\nHTTPRequestID must be a valid http_request ID. ContentType must be one of the CONTENT_TYPE_* constants.</string> - </map> - <key>llSetDamage</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Damage</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the amount of damage that will be done to an avatar that this task hits. Task will be killed.\nSets the amount of damage that will be done to an avatar that this object hits. This object will be destroyed on damaging an avatar, and no collision event is triggered.</string> - </map> - <key>llSetForce</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Force</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Directional force.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE uses local axis, if FALSE uses region axis.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets Force on object, in object-local coordinates if Local == TRUE (otherwise, the region reference frame is used).\nOnly works on physical objects.</string> - </map> - <key>llSetForceAndTorque</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Force</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Directional force.</string> - </map> - </map> - <map> - <key>Torque</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Torque force.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE uses local axis, if FALSE uses region axis.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the Force and Torque of object, in object-local coordinates if Local == TRUE (otherwise, the region reference frame is used).\nOnly works on physical objects.</string> - </map> - <key>llSetHoverHeight</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Height</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Distance above the ground.</string> - </map> - </map> - <map> - <key>Water</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE then hover above water too.</string> - </map> - </map> - <map> - <key>Tau</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Seconds to critically damp in.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Critically damps a physical object to a Height (either above ground level or above the higher of land and water if water == TRUE).\nDo not use with vehicles. Use llStopHover to stop hovering.</string> - </map> - <key>llSetInventoryPermMask</key> - <map> - <key>god-mode</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>InventoryItem</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>An item in the prim's inventory</string> - </map> - </map> - <map> - <key>PermissionFlag</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>MASK_* flag</string> - </map> - </map> - <map> - <key>PermissionMask</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Permission bit-field (PERM_* flags)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the given permission mask to the new value on the inventory item.</string> - </map> - <key>llSetKeyframedMotion</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Keyframes</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Strided keyframe list of the form: position, orientation, time. Each keyframe is interpreted relative to the previous transform of the object.</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests that a non-physical object be key-framed according to key-frame list.\nSpecify a list of times, positions, and orientations to be followed by an object. The object will be smoothly moved between key-frames by the simulator. Collisions with other non-physical or key-framed objects will be ignored (no script events will fire and collision processing will not occur). Collisions with physical objects will be computed and reported, but the key-framed object will be unaffected by those collisions.\nKeyframes is a strided list containing positional, rotational, and time data for each step in the motion. Options is a list containing optional arguments and parameters (specified by KFM_* constants).</string> - </map> - <key>llSetLinkAlpha</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Opacity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>If a prim exists in the link chain at LinkNumber, set Face to Opacity.\nSets the Face, on the linked prim specified, to the Opacity.</string> - </map> - <key>llSetLinkCamera</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Prim link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag</string> - </map> - </map> - <map> - <key>EyeOffset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Offset, relative to the object's centre and expressed in local coordinates, that the camera looks from.</string> - </map> - </map> - <map> - <key>LookOffset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Offset, relative to the object's centre and expressed in local coordinates, that the camera looks toward.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the camera eye offset, and the offset that camera is looking at, for avatars that sit on the linked prim.</string> - </map> - <key>llSetLinkColor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag.</string> - </map> - </map> - <map> - <key>Color</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Color in RGB <R.R, G.G, B.B></string> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Side number or ALL_SIDES.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If a task exists in the link chain at LinkNumber, set the Face to color.\nSets the color of the linked child's side, specified by LinkNumber.</string> - </map> - <key>llSetLinkMedia</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Link</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims).</string> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Face number.</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A set of name/value pairs (in no particular order)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the media parameters for a particular face on linked prim, specified by Link. Returns an integer that is a STATUS_* flag which details the success/failure of the operation(s).\nMediaParameters is a set of name/value pairs in no particular order. Parameters not specified are unchanged, or if new media is added then set to the default specified.</string> - </map> - <key>llSetLinkPrimitiveParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set primitive parameters for LinkNumber based on Parameters.\nSets the parameters (or properties) of any linked prim in one step.</string> - </map> - <key>llSetLinkPrimitiveParamsFast</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag</string> - </map> - </map> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set primitive parameters for LinkNumber based on Parameters, without a delay.\nSet parameters for link number, from the list of Parameters, with no built-in script sleep. This function is identical to llSetLinkPrimitiveParams, except without the delay.</string> - </map> - <key>llSetLinkTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the Texture of Face on a linked prim, specified by LinkNumber. Texture may be a UUID or name of a texture in prim inventory.</string> - </map> - <key>llSetLinkTextureAnim</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>LinkNumber</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Link number (0: unlinked, 1: root prim, >1: child prims) or a LINK_* flag to effect</string> - </map> - </map> - <map> - <key>Mode</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Bitmask of animation options.</string> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Specifies which object face to animate or ALL_SIDES.</string> - </map> - </map> - <map> - <key>SizeX</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Horizontal frames (ignored for ROTATE and SCALE).</string> - </map> - </map> - <map> - <key>SizeY</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Vertical frames (ignored for ROTATE and SCALE).</string> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Start position/frame number (or radians for ROTATE).</string> - </map> - </map> - <map> - <key>Length</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Specifies the animation duration, in frames (or radians for ROTATE).</string> - </map> - </map> - <map> - <key>Rate</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Specifies the animation playback rate, in frames per second (must be greater than zero).</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Animates a texture on the prim specified by LinkNumber, by setting the texture scale and offset.\nMode is a bitmask of animation options.\nFace specifies which object face to animate.\nSizeX and SizeY specify the number of horizontal and vertical frames.Start specifes the animation start point.\nLength specifies the animation duration.\nRate specifies the animation playback rate.</string> - </map> - <key>llSetLocalRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the rotation of a child prim relative to the root prim.</string> - </map> - <key>llSetMemoryLimit</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Limit</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>The amount to reserve, which must be less than the allowed maximum (currently 64KB) and not already have been exceeded.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests Limit bytes to be reserved for this script.\nReturns TRUE or FALSE indicating whether the limit was set successfully.\nThis function has no effect if the script is running in the LSO VM.</string> - </map> - <key>llSetObjectDesc</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Description</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the description of the prim to Description.\nThe description field is limited to 127 characters.</string> - </map> - <key>llSetObjectName</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Name</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the prim's name to Name.</string> - </map> - <key>llSetObjectPermMask</key> - <map> - <key>god-mode</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>PermissionFlag</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>MASK_* flag</string> - </map> - </map> - <map> - <key>PermissionMask</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Permission bit-field (PERM_* flags)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the specified PermissionFlag permission to the value specified by PermissionMask on the object the script is attached to.</string> - </map> - <key>llSetParcelMusicURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>2.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the streaming audio URL for the parcel the object is on.\nThe object must be owned by the owner of the parcel; if the parcel is group owned the object must be owned by that group.</string> - </map> - <key>llSetPayPrice</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Price</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>The default price shown in the textu input field.</string> - </map> - </map> - <map> - <key>QuickButtons</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Specifies the 4 payment values shown in the payment dialog's buttons (or PAY_HIDE).</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the default amount when someone chooses to pay this object.\nPrice is the default price shown in the textu input field. QuickButtons specifies the 4 payment values shown in the payment dialog's buttons.\nInput field and buttons may be hidden with PAY_HIDE constant, and may be set to their default values using PAY_DEFAULT.</string> - </map> - <key>llSetPhysicsMaterial</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real/> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>MaterialBits</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>A bitmask specifying which of the parameters in the other arguments should be applied to the object.</string> - </map> - </map> - <map> - <key>GravityMultiplier</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Restitution</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Friction</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Density</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the selected parameters of the object's physics behavior.\nMaterialBits is a bitmask specifying which of the parameters in the other arguments should be applied to the object. GravityMultiplier, Restitution, Friction, and Density are the possible parameters to manipulate.</string> - </map> - <key>llSetPos</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Region coordinates to move to (within 10m).</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If the object is not physical, this function sets the position of the prim.\nIf the script is in a child prim, Position is treated as root relative and the link-set is adjusted.\nIf the prim is the root prim, the entire object is moved (up to 10m) to Position in region coordinates.</string> - </map> - <key>llSetPrimitiveParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Parameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A list of changes.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>This function changes the many properties (or "parameters") of a prim in one operation. Parameters is a list of changes.</string> - </map> - <key>llSetPrimMediaParams</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Face number</string> - </map> - </map> - <map> - <key>MediaParameters</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>A set of name/value pairs (in no particular order)</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the MediaParameters for a particular Face on the prim. Returns an integer that is a STATUS_* flag which details the success/failure of the operation(s).\nMediaParameters is a set of name/value pairs in no particular order. Parameters not specified are unchanged, or if new media is added then set to the default specified.</string> - </map> - <key>llSetPrimURL</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>20.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Use llSetPrimMediaParams instead.</string> - </map> - <key>llSetRegionPos</key> - <map> - <key>energy</key> - <real>0.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Vector. The location to move to, in region coordinates.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Attempts to move the object so that the root prim is within 0.1m of Position.\nReturns an integer boolean, TRUE if the object is successfully placed within 0.1 m of Position, FALSE otherwise.\nPosition may be any location within the region or up to 10m across a region border.\nIf the position is below ground, it will be set to the ground level at that x,y location.</string> - </map> - <key>llSetRemoteScriptAccessPin</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>PIN</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>If PIN is set to a non-zero number, the task will accept remote script loads via llRemoteLoadScriptPin() if it passes in the correct PIN. Othersise, llRemoteLoadScriptPin() is ignored.</string> - </map> - <key>llSetRot</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>If the object is not physical, this function sets the rotation of the prim.\nIf the script is in a child prim, Rotation is treated as root relative and the link-set is adjusted.\nIf the prim is the root prim, the entire object is rotated to Rotation in the global reference frame.</string> - </map> - <key>llSetScale</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Scale</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the prim's scale (size) to Scale.</string> - </map> - <key>llSetScriptState</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ScriptName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Running</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Enable or disable the script Running state of Script in the prim.</string> - </map> - <key>llSetSitText</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Displays Text rather than 'Sit' in the viewer's context menu.</string> - </map> - <key>llSetSoundQueueing</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>QueueEnable</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, sound queuing: TRUE enables, FALSE disables (default).</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets whether successive calls to llPlaySound, llLoopSound, etc., (attached sounds) interrupt the currently playing sound.\nThe default for objects is FALSE. Setting this value to TRUE will make the sound wait until the current playing sound reaches its end. The queue is one level deep.</string> - </map> - <key>llSetSoundRadius</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Radius</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Maximum distance that sounds can be heard.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Limits radius for audibility of scripted sounds (both attached and triggered) to distance Radius.</string> - </map> - <key>llSetStatus</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Status</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets object status specified in Status bitmask (e.g. STATUS_PHYSICS|STATUS_PHANTOM) to boolean Value.\nFor a full list of STATUS_* constants, see wiki documentation.</string> - </map> - <key>llSetText</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Color</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Opacity</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Causes Text to float above the prim, using the specified Color and Opacity.</string> - </map> - <key>llSetTexture</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.2</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Texture</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Applies Texture to Face of prim.\nTexture may be a UUID or name of a texture in prim inventory.\nIf Face is ALL_SIDES, set the texture on all faces.</string> - </map> - <key>llSetTextureAnim</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Mode</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Mask of Mode flags.</string> - </map> - </map> - <map> - <key>Face</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Face number or ALL_SIDES.</string> - </map> - </map> - <map> - <key>SizeX</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Horizontal frames (ignored for ROTATE and SCALE).</string> - </map> - </map> - <map> - <key>SizeY</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Vertical frames (ignored for ROTATE and SCALE).</string> - </map> - </map> - <map> - <key>Start</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Start position/frame number (or radians for ROTATE).</string> - </map> - </map> - <map> - <key>Length</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>number of frames to display (or radians for ROTATE).</string> - </map> - </map> - <map> - <key>Rate</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string>Frames per second (must not greater than zero).</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Animates a texture by setting the texture scale and offset.\nMode is a bitmask of animation options.\nFace specifies which object face to animate.\nSizeX and SizeY specify the number of horizontal and vertical frames.Start specifes the animation start point.\nLength specifies the animation duration.\nRate specifies the animation playback rate.</string> - </map> - <key>llSetTimerEvent</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Rate</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Causes the timer event to be triggered every Rate seconds.\n Passing in 0.0 stops further timer events.</string> - </map> - <key>llSetTorque</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Torque</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Torque force.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, if TRUE uses local axis, if FALSE uses region axis.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets the Torque acting on the script's object, in object-local coordinates if Local == TRUE (otherwise, the region reference frame is used).\nOnly works on physical objects.</string> - </map> - <key>llSetTouchText</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Displays Text in the viewer context menu that acts on a touch.</string> - </map> - <key>llSetVehicleFlags</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Flags</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Enables the vehicle flags specified in the Flags bitmask.\nValid parameters can be found in the wiki documentation.</string> - </map> - <key>llSetVehicleFloatParam</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ParameterName</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ParameterValue</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets a vehicle float parameter.\nValid parameters can be found in the wiki documentation.</string> - </map> - <key>llSetVehicleRotationParam</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ParameterName</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ParameterValue</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets a vehicle rotation parameter.\nValid parameters can be found in the wiki documentation.</string> - </map> - <key>llSetVehicleType</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Type</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Activates the vehicle action on the object with vehicle preset Type.\nValid Types and an explanation of their characteristics can be found in wiki documentation.</string> - </map> - <key>llSetVehicleVectorParam</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>ParameterName</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>ParameterValue</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Sets a vehicle vector parameter.\nValid parameters can be found in the wiki documentation.</string> - </map> - <key>llSetVelocity</key> - <map> - <key>energy</key> - <real/> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Velocity</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>The velocity to apply.</string> - </map> - </map> - <map> - <key>Local</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>If TRUE, the Velocity is treated as a local directional vector instead of a regional directional vector.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If the object is physics-enabled, sets the object's linear velocity to Velocity.\nIf Local==TRUE, Velocity is treated as a local directional vector; otherwise, Velocity is treated as a global directional vector.</string> - </map> - <key>llSHA1String</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string of 40 hex characters that is the SHA1 security Hash of Text.</string> - </map> - <key>llShout</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Shouts Text on Channel.\nThis chat method has a range of 100m radius.\nPUBLIC_CHANNEL is the public chat channel that all avatars see as chat text. DEBUG_CHANNEL is the script debug channel, and is also visible to nearby avatars. All other channels are are not sent to avatars, but may be used to communicate with scripts.</string> - </map> - <key>llSin</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Theta</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the sine of Theta (Theta in radians).</string> - </map> - <key>llSitTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Rotation</key> - <map> - <key>type</key> - <string>rotation</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Set the sit location for this object. If offset == ZERO_VECTOR, clears the sit target.</string> - </map> - <key>llSleep</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Time</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Put script to sleep for Time seconds.</string> - </map> - <key>llSound</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Queue</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Loop</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Use llPlaySound instead.\nPlays Sound at Volume and specifies whether the sound should loop and/or be enqueued.</string> - </map> - <key>llSoundPreload</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Use llPreloadSound instead.\nPreloads a sound on viewers within range.</string> - </map> - <key>llSqrt</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the square root of Value.\nTriggers a math runtime error for imaginary results (if Value < 0.0).</string> - </map> - <key>llStartAnimation</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Animation</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This function plays the specified animation from playing on the avatar who received the script's most recent permissions request.\nAnimation may be an animation in task inventory or a built-in animation.\nRequires PERMISSION_TRIGGER_ANIMATION.</string> - </map> - <key>llStopAnimation</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Animation</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This function stops the specified animation on the avatar who received the script's most recent permissions request.\nAnimation may be an animation in task inventory, a built-in animation, or the uuid of an animation.\nRequires PERMISSION_TRIGGER_ANIMATION.</string> - </map> - <key>llStopHover</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Stop hovering to a height (due to llSetHoverHeight()).</string> - </map> - <key>llStopLookAt</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Stop causing object to point at a target (due to llLookAt() or llRotLookAt()).</string> - </map> - <key>llStopMoveToTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Stops critically damped motion (due to llMoveToTarget()).</string> - </map> - <key>llStopSound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Stops playback of the currently attached sound.</string> - </map> - <key>llStringLength</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns an integer that is the number of characters in Text (not counting the null).</string> - </map> - <key>llStringToBase64</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the string Base64 representation of the input string.</string> - </map> - <key>llStringTrim</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>String to trim</string> - </map> - </map> - <map> - <key>TrimType</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>STRING_TRIM_HEAD, STRING_TRIM_TAIL, or STRING_TRIM.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Outputs a string, eliminating white-space from the start and/or end of the input string Text.\nValid options for TrimType:\nSTRING_TRIM_HEAD: trim all leading spaces in Text\nSTRING_TRIM_TAIL: trim all trailing spaces in Text\nSTRING_TRIM: trim all leading and trailing spaces in Text.</string> - </map> - <key>llSubStringIndex</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Sequence</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns an integer that is the index in Text where string pattern Sequence first appears. Returns -1 if not found.</string> - </map> - <key>llTakeCamera</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Use llSetCameraParams instead.</string> - </map> - <key>llTakeControls</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Controls</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Bit-field of CONTROL_* flags.</string> - </map> - </map> - <map> - <key>Accept</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, determines whether control events are generated.</string> - </map> - </map> - <map> - <key>PassOn</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>Boolean, determines whether controls are disabled.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Take controls from the agent the script has permissions for.\nIf (Accept == (Controls & input)), send input to the script. PassOn determines whether Controls also perform their normal functions.\nRequires the PERMISSION_TAKE_CONTROLS permission to run.</string> - </map> - <key>llTan</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Theta</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the tangent of Theta (Theta in radians).</string> - </map> - <key>llTarget</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>integer</string> - <key>arguments</key> - <array> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Range</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>This function is to have the script know when it has reached a position.\nIt registers a Position with a Range that triggers at_target and not_at_target events continuously until unregistered.</string> - </map> - <key>llTargetOmega</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Axis</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>SpinRate</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Gain</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Attempt to spin at SpinRate with strength Gain on Axis.\nA spin rate of 0.0 cancels the spin. This function always works in object-local coordinates.</string> - </map> - <key>llTargetRemove</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Target</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Removes positional target Handle registered with llTarget.</string> - </map> - <key>llTeleportAgent</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>UUID of avatar.</string> - </map> - </map> - <map> - <key>LandmarkName</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string>Name of landmark (in object contents), or empty string, to use.</string> - </map> - </map> - <map> - <key>Position</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>If no landmark was provided, the position within the current region to teleport the avatar to.</string> - </map> - </map> - <map> - <key>LookAtPoint</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>The position within the target region that the avatar should be turned to face upon arrival.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Requests a teleport of avatar to a landmark stored in the object's inventory. If no landmark is provided (an empty string), the avatar is teleported to the location position in the current region. In either case, the avatar is turned to face the position given by look_at in local coordinates.\nRequires the PERMISSION_TELEPORT permission. This function can only teleport the owner of the object.</string> - </map> - <key>llTeleportAgentGlobalCoords</key> - <map> - <key>energy</key> - <real>0</real> - <key>sleep</key> - <real>0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string>UUID of avatar.</string> - </map> - </map> - <map> - <key>GlobalPosition</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Global coordinates of the destination region. Can be retrieved by using llRequestSimulatorData(region_name, DATA_SIM_POS).</string> - </map> - </map> - <map> - <key>RegionPosition</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>The position within the target region to teleport the avatar to, if no landmark was provided.</string> - </map> - </map> - <map> - <key>LookAtPoint</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>The position within the target region that the avatar should be turned to face upon arrival.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Teleports an agent to the RegionPosition local coordinates within a region which is specified by the GlobalPosition global coordinates. The agent lands facing the position defined by LookAtPoint local coordinates.\nRequires the PERMISSION_TELEPORT permission. This function can only teleport the owner of the object.</string> - </map> - <key>llTeleportAgentHome</key> - <map> - <key>energy</key> - <real>100.0</real> - <key>sleep</key> - <real>5.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Teleport agent over the owner's land to agent's home location.</string> - </map> - <key>llTextBox</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>1.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Opens a dialog for the specified avatar with message Text, which contains a text box for input. Any text that is entered is said on the specified Channel (as if by the avatar) when the "OK" button is clicked.</string> - </map> - <key>llToLower</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string that is Text with all lower-case characters.</string> - </map> - <key>llToUpper</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns a string that is Text with all upper-case characters.</string> - </map> - <key>llTransferLindenDollars</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Amount</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Transfer Amount of linden dollars (L$) from script owner to AvatarID. Returns a key to a corresponding transaction_result event for the success of the transfer.\nAttempts to send the amount of money to the specified avatar, and trigger a transaction_result event identified by the returned key.</string> - </map> - <key>llTriggerSound</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays Sound at Volume (0.0 - 1.0), centered at but not attached to object.\nThere is no limit to the number of triggered sounds which can be generated by an object, and calling llTriggerSound does not affect the attached sounds created by llPlaySound and llLoopSound. This is very useful for things like collision noises, explosions, etc. There is no way to stop or alter the volume of a sound triggered by this function.</string> - </map> - <key>llTriggerSoundLimited</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Sound</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Volume</key> - <map> - <key>type</key> - <string>float</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>TNE</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>BSW</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Plays Sound at Volume (0.0 - 1.0), centered at but not attached to object, limited to axis-aligned bounding box defined by vectors top-north-east (TNE) and bottom-south-west (BSW).\nThere is no limit to the number of triggered sounds which can be generated by an object, and calling llTriggerSound does not affect the attached sounds created by llPlaySound and llLoopSound. This is very useful for things like collision noises, explosions, etc. There is no way to stop or alter the volume of a sound triggered by this function.</string> - </map> - <key>llUnescapeURL</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>URL</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the string that is the URL unescaped, replacing "%20" with spaces, etc., version of URL.\nThis function can output raw UTF-8 strings.</string> - </map> - <key>llUnSit</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>AvatarID</key> - <map> - <key>type</key> - <string>key</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>If agent identified by AvatarID is sitting on the object the script is attached to or is over land owned by the objects owner, the agent is forced to stand up.</string> - </map> - <key>llUpdateCharacter</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>Character configuration options. Takes the same constants as llCreateCharacter().</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Updates settings for a pathfinding character.</string> - </map> - <key>llUpdateKeyValue</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>key</string> - <key>arguments</key> - <array> - <map> - <key>Key</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - <map> - <key>Value</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - <map> - <key>Checked</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string></string> - </map> - </map> - <map> - <key>OriginalValue</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string></string> - </map> - </map> - </array> - <key>tooltip</key> - <string> - Starts an asychronous transaction to update the value associated with the key given. The dataserver callback will be executed with the key returned from this call and a string describing the result. The result is a two element commma-delimited list. The first item is an integer specifying if the transaction succeeded (1) or not (0). In the failure case, the second item will be an integer corresponding to one of the XP_ERROR_... constants. In the success case the second item will be the value associated with the key. If Checked is 1 the existing value in the data store must match the OriginalValue passed or XP_ERROR_RETRY_UPDATE will be returned. If Checked is 0 the key will be created if necessary. - </string> - </map> - <key>llVecDist</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Location1</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Location2</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the distance between Location1 and Location2.</string> - </map> - <key>llVecMag</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Vector</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the magnitude of the vector.</string> - </map> - <key>llVecNorm</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Vector</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns normalized vector.</string> - </map> - <key>llVolumeDetect</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>DetectEnabled</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string>TRUE enables, FALSE disables.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>If DetectEnabled = TRUE, object becomes phantom but triggers collision_start and collision_end events when other objects start and stop interpenetrating.\nIf another object (including avatars) interpenetrates it, it will get a collision_start event.\nWhen an object stops interpenetrating, a collision_end event is generated. While the other is inter-penetrating, collision events are NOT generated.</string> - </map> - <key>llWanderWithin</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Origin</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Central point to wander about.</string> - </map> - </map> - <map> - <key>Area</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string>Half-extents of an area the character may wander within. (i.e., it can wander from the specified origin by up to +/-Distance.x in x, +/-Distance.y in y, etc.)</string> - </map> - </map> - <map> - <key>Options</key> - <map> - <key>type</key> - <string>list</string> - <key>tooltip</key> - <string>No options available at this time.</string> - </map> - </map> - </array> - <key>tooltip</key> - <string>Wander within a specified volume.\nSets a character to wander about a central spot within a specified area.</string> - </map> - <key>llWater</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the water height below the object position + Offset.</string> - </map> - <key>llWhisper</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>void</string> - <key>arguments</key> - <array> - <map> - <key>Channel</key> - <map> - <key>type</key> - <string>integer</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Whispers Text on Channel.\nThis chat method has a range of 10m radius.\nPUBLIC_CHANNEL is the public chat channel that all avatars see as chat text. DEBUG_CHANNEL is the script debug channel, and is also visible to nearby avatars. All other channels are are not sent to avatars, but may be used to communicate with scripts.</string> - </map> - <key>llWind</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>vector</string> - <key>arguments</key> - <array> - <map> - <key>Offset</key> - <map> - <key>type</key> - <string>vector</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Returns the wind velocity at the object position + Offset.</string> - </map> - <key>llXorBase64</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text1</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text2</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Performs an exclusive OR on two Base64 strings and returns a Base64 string. Text2 repeats if it is shorter than Text1.</string> - </map> - <key>llXorBase64Strings</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.3</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text1</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text2</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Please use llXorBase64 instead.\nIncorrectly performs an exclusive OR on two Base64 strings and returns a Base64 string. Text2 repeats if it is shorter than Text1.\nRetained for backwards compatibility.</string> - </map> - <key>llXorBase64StringsCorrect</key> - <map> - <key>deprecated</key> - <boolean>true</boolean> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>string</string> - <key>arguments</key> - <array> - <map> - <key>Text1</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - <map> - <key>Text2</key> - <map> - <key>type</key> - <string>string</string> - <key>tooltip</key> - <string/> - </map> - </map> - </array> - <key>tooltip</key> - <string>Deprecated: Please use llXorBase64 instead.\nCorrectly (unless nulls are present) performs an exclusive OR on two Base64 strings and returns a Base64 string.\nText2 repeats if it is shorter than Text1.</string> - </map> - <key>llGetMinScaleFactor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the smallest multiplicative uniform scale factor that can be successfully applied (via llScaleByFactor()) to the object without violating prim size or linkability rules.</string> - </map> - <key>llGetMaxScaleFactor</key> - <map> - <key>energy</key> - <real>10.0</real> - <key>sleep</key> - <real>0.0</real> - <key>return</key> - <string>float</string> - <key>arguments</key> - <undef/> - <key>tooltip</key> - <string>Returns the largest multiplicative uniform scale factor that can be successfully applied (via llScaleByFactor()) to the object without violating prim size or linkability rules.</string> - </map> - </map> - <key>llsd-lsl-syntax-version</key> - <integer>2</integer><!-- increment only when the file format changes, not just the content --> - </map> -</llsd> diff --git a/indra/newview/app_settings/settings.xml b/indra/newview/app_settings/settings.xml index 03b5259b75..203edcac62 100644 --- a/indra/newview/app_settings/settings.xml +++ b/indra/newview/app_settings/settings.xml @@ -641,7 +641,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/vawp/index.html</string> + <string>https://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/vawp/index.html</string> </map> <!--AvatarBakedTextureUploadTimeout is in use by QA--> <key>AvatarBakedTextureUploadTimeout</key> @@ -2467,7 +2467,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/guide.html</string> + <string>https://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/guide.html</string> </map> <key>DisableCameraConstraints</key> <map> @@ -2775,7 +2775,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://events.[GRID]/viewer/embed/event/[EVENT_ID]</string> + <string>https://events.[GRID]/viewer/embed/event/[EVENT_ID]</string> </map> <key>MainWorkTime</key> <map> @@ -3432,7 +3432,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://viewer-help.secondlife.com/[LANGUAGE]/[CHANNEL]/[VERSION]/[TOPIC][DEBUG_MODE]</string> + <string>https://viewer-help.secondlife.com/[LANGUAGE]/[CHANNEL]/[VERSION]/[TOPIC][DEBUG_MODE]</string> </map> <key>HowToHelpURL</key> <map> @@ -3443,7 +3443,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/howto/index.html</string> + <string>https://lecs-viewer-web-components.s3.amazonaws.com/v3.0/[GRID_LOWERCASE]/howto/index.html</string> </map> <key>HomeSidePanelURL</key> <map> @@ -4059,7 +4059,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://wiki.secondlife.com/wiki/[LSL_STRING]</string> + <string>https://wiki.secondlife.com/wiki/[LSL_STRING]</string> </map> <key>LSLFontSizeName</key> <map> @@ -4501,7 +4501,7 @@ <key>Type</key> <string>F32</string> <key>Value</key> - <real>30.0</real> + <real>60.0</real> </map> <key>MapScale</key> <map> @@ -13934,7 +13934,7 @@ <key>Type</key> <string>S32</string> <key>Value</key> - <integer>1</integer> + <integer>0</integer> </map> <key>WaterGLFogDensityScale</key> <map> @@ -14112,6 +14112,50 @@ <key>Value</key> <string /> </map> + <key>ExternalWebsocketSyncEnable</key> + <map> + <key>Comment</key> + <string>Enables the Websocket JSONRPC server when doing external script editing.</string> + <key>Persist</key> + <integer>1</integer> + <key>Type</key> + <string>Boolean</string> + <key>Value</key> + <integer>1</integer> + </map> + <key>ExternalWebsocketSyncPort</key> + <map> + <key>Comment</key> + <string>Port that the JSONRPC server listens on when editing</string> + <key>Persist</key> + <integer>1</integer> + <key>Type</key> + <string>S32</string> + <key>Value</key> + <integer>9020</integer> + </map> + <key>ExternalWebsocketSyncLocal</key> + <map> + <key>Comment</key> + <string>Should the JSONRPC server listen only for local connections.</string> + <key>Persist</key> + <integer>1</integer> + <key>Type</key> + <string>Boolean</string> + <key>Value</key> + <integer>1</integer> + </map> + <key>ExternalWebsocketForwardDebug</key> + <map> + <key>Comment</key> + <string>Forward messages and runtime errors for a script to JSONRPC client.</string> + <key>Persist</key> + <integer>1</integer> + <key>Type</key> + <string>Boolean</string> + <key>Value</key> + <integer>1</integer> + </map> <key>YawFromMousePosition</key> <map> <key>Comment</key> @@ -14765,7 +14809,7 @@ <key>Type</key> <string>String</string> <key>Value</key> - <string>http://common-flash-secondlife-com.s3.amazonaws.com/viewer/v2.6/agni/404.html</string> + <string>https://common-flash-secondlife-com.s3.amazonaws.com/viewer/v2.6/agni/404.html</string> </map> <key>OpenIMOnVoice</key> <map> @@ -16618,5 +16662,16 @@ <key>Value</key> <integer>0</integer> </map> + <key>ScriptEditorDisableSyntaxHighlight</key> + <map> + <key>Comment</key> + <string>Disable syntax highlighting in script editor for performance testing</string> + <key>Persist</key> + <integer>1</integer> + <key>Type</key> + <string>Boolean</string> + <key>Value</key> + <integer>0</integer> + </map> </map> </llsd> diff --git a/indra/newview/app_settings/types_lua_default.xml b/indra/newview/app_settings/types_lua_default.xml new file mode 100644 index 0000000000..cb40ec3d06 --- /dev/null +++ b/indra/newview/app_settings/types_lua_default.xml @@ -0,0 +1,5262 @@ +<?xml version="1.0" encoding="UTF-8"?> +<llsd> +<map> + <key>version</key> + <string>1.0.0</string> + <key>typeAliases</key> + <array> + <map> + <key>name</key> + <string>rotation</string> + <key>definition</key> + <map> + <key>kind</key> + <string>reference</string> + <key>name</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>'rotation' is an alias for 'quaternion'</string> + </map> + <map> + <key>name</key> + <string>numeric</string> + <key>definition</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>boolean</string> + <string>number</string> + </array> + </map> + </map> + <map> + <key>name</key> + <string>list</string> + <key>definition</key> + <map> + <key>kind</key> + <string>array</string> + <key>elementType</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>string</string> + <string>number</string> + <string>vector</string> + <string>uuid</string> + <string>quaternion</string> + <string>boolean</string> + </array> + </map> + </map> + </map> + <map> + <key>name</key> + <string>LLDetectedEventName</string> + <key>definition</key> + <map> + <key>kind</key> + <string>literal-union</string> + <key>values</key> + <array/> + </map> + </map> + <map> + <key>name</key> + <string>LLNonDetectedEventName</string> + <key>definition</key> + <map> + <key>kind</key> + <string>literal-union</string> + <key>values</key> + <array/> + </map> + </map> + <map> + <key>name</key> + <string>LLEventName</string> + <key>definition</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>LLDetectedEventName</string> + <string>LLNonDetectedEventName</string> + </array> + </map> + </map> + <map> + <key>name</key> + <string>LLEventHandler</string> + <key>definition</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>()</string> + </map> + </map> + <map> + <key>name</key> + <string>LLDetectedEventHandler</string> + <key>definition</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>detected</string> + <key>type</key> + <map> + <key>kind</key> + <string>array</string> + <key>elementType</key> + <string>LLDetectedEvent</string> + </map> + </map> + </array> + <key>returnType</key> + <string>()</string> + </map> + </map> + <map> + <key>name</key> + <string>LLTimerEveryCallback</string> + <key>definition</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>scheduled</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>interval</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + </map> + <key>comment</key> + <string>Callback type for LLTimers.every() - receives scheduled time and interval</string> + </map> + <map> + <key>name</key> + <string>LLTimerOnceCallback</string> + <key>definition</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>scheduled</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + </map> + <key>comment</key> + <string>Callback type for LLTimers.once() - receives scheduled time</string> + </map> + <map> + <key>name</key> + <string>LLTimerCallback</string> + <key>definition</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>LLTimerEveryCallback</string> + <string>LLTimerOnceCallback</string> + <string>(...any) -> ...any</string> + </array> + </map> + <key>comment</key> + <string>Union of timer callback types</string> + </map> + <map> + <key>name</key> + <string>OsDateTime</string> + <key>definition</key> + <map> + <key>kind</key> + <string>table</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>year</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>month</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>day</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>hour</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>min</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>sec</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>wday</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>yday</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>isdst</string> + <key>type</key> + <string>boolean</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + </map> + <key>comment</key> + <string>Date/time table structure used by os.date and os.time</string> + </map> + </array> + <key>classes</key> + <array> + <map> + <key>name</key> + <string>quaternion</string> + <key>comment</key> + <string>Luau Type Definition for LSL UserData Type: quaternion</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>methods</key> + <array> + <map> + <key>name</key> + <string>__add</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>__sub</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>__mul</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>__div</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>__unm</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>__eq</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + </map> + <map> + <key>name</key> + <string>__tostring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>uuid</string> + <key>comment</key> + <string>Luau Type Definition for LSL UserData Type: uuid</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>istruthy</string> + <key>type</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if the UUID is not the null UUID (all zeros)</string> + </map> + <map> + <key>name</key> + <string>bytes</string> + <key>type</key> + <string>string?</string> + <key>comment</key> + <string>Returns the raw 16-byte binary string of the UUID, or nil if the UUID is not in a compressed state</string> + </map> + </array> + <key>methods</key> + <array> + <map> + <key>name</key> + <string>__tostring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>vector</string> + <key>comment</key> + <string>Luau Type Definition for LSL UserData Type: vector</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>methods</key> + <array> + <map> + <key>name</key> + <string>__add</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>Native component-wise addition</string> + </map> + <map> + <key>name</key> + <string>__sub</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>Native component-wise subtraction</string> + </map> + <map> + <key>name</key> + <string>__unm</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>Unary negation</string> + </map> + <map> + <key>name</key> + <string>__mul</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>number | vector | quaternion</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>Multiplication: vector * number or vector * vector -> vector, vector * quaternion -> vector (Rotation)</string> + </map> + <map> + <key>name</key> + <string>__div</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>number | vector | quaternion</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>Division: vector / number or vector / vector -> vector (Scale), vector / quaternion -> vector (Rotation by inverse)</string> + </map> + <map> + <key>name</key> + <string>__mod</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>other</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + <key>comment</key> + <string>LSL-style modulo: vector % vector -> vector (Cross Product)</string> + </map> + <map> + <key>name</key> + <string>__tostring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>LLDetectedEvent</string> + <key>comment</key> + <string>Event detection class providing access to detected object/avatar information</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>index</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>valid</string> + <key>type</key> + <string>boolean</string> + </map> + <map> + <key>name</key> + <string>canAdjustDamage</string> + <key>type</key> + <string>boolean</string> + </map> + </array> + <key>methods</key> + <array/> + </map> + <map> + <key>name</key> + <string>LLEvents</string> + <key>comment</key> + <string>Event registration and management class for Second Life events</string> + <key>methods</key> + <array> + <map> + <key>name</key> + <string>on</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>event</string> + <key>type</key> + <string>LLEventName</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLEventHandler</string> + </map> + </array> + <key>returnType</key> + <string>LLEventHandler</string> + <key>comment</key> + <string>Registers a callback for an event. Returns the callback.</string> + </map> + <map> + <key>name</key> + <string>off</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>event</string> + <key>type</key> + <string>LLEventName</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLEventHandler</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Unregisters a callback. Returns true if found and removed.</string> + </map> + <map> + <key>name</key> + <string>once</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>event</string> + <key>type</key> + <string>LLEventName</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLEventHandler</string> + </map> + </array> + <key>returnType</key> + <string>LLEventHandler</string> + <key>comment</key> + <string>Registers a one-time callback. Returns the wrapper function.</string> + </map> + <map> + <key>name</key> + <string>listeners</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>event</string> + <key>type</key> + <string>LLEventName</string> + </map> + </array> + <key>returnType</key> + <string>{LLEventHandler}</string> + <key>comment</key> + <string>Returns a list of all listeners for a specific event.</string> + </map> + <map> + <key>name</key> + <string>eventNames</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + </array> + <key>returnType</key> + <string>{string}</string> + <key>comment</key> + <string>Returns a list of all event names that have listeners.</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>LLTimers</string> + <key>comment</key> + <string>Timer management class for scheduling periodic and one-time callbacks</string> + <key>methods</key> + <array> + <map> + <key>name</key> + <string>every</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>seconds</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLTimerEveryCallback</string> + </map> + </array> + <key>returnType</key> + <string>LLTimerCallback</string> + <key>comment</key> + <string>Registers a callback to be called every N seconds. Returns the callback.</string> + </map> + <map> + <key>name</key> + <string>once</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>seconds</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLTimerOnceCallback</string> + </map> + </array> + <key>returnType</key> + <string>LLTimerCallback</string> + <key>comment</key> + <string>Registers a callback to be called once after N seconds. Returns the callback.</string> + </map> + <map> + <key>name</key> + <string>off</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>self</string> + </map> + <map> + <key>name</key> + <string>callback</string> + <key>type</key> + <string>LLTimerCallback</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Unregisters a timer callback. Returns true if found and removed.</string> + </map> + </array> + </map> + </array> + <key>globalVariables</key> + <array> + <map> + <key>name</key> + <string>quaternion</string> + <key>type</key> + <map> + <key>kind</key> + <string>callable-table</string> + <key>tableType</key> + <map> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>create</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>Constructor</string> + </map> + <map> + <key>name</key> + <string>identity</string> + <key>type</key> + <string>quaternion</string> + <key>comment</key> + <string>Identity quaternion constant</string> + </map> + <map> + <key>name</key> + <string>normalize</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>Returns normalized quaternion</string> + </map> + <map> + <key>name</key> + <string>magnitude</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + </map> + <key>comment</key> + <string>Returns magnitude of quaternion</string> + </map> + <map> + <key>name</key> + <string>dot</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + </map> + <key>comment</key> + <string>Dot product of two quaternions</string> + </map> + <map> + <key>name</key> + <string>slerp</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>quaternion</string> + </map> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>Spherical linear interpolation</string> + </map> + <map> + <key>name</key> + <string>conjugate</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>Returns conjugate of quaternion</string> + </map> + <map> + <key>name</key> + <string>tofwd</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Returns forward vector from quaternion rotation</string> + </map> + <map> + <key>name</key> + <string>toleft</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Returns left vector from quaternion rotation</string> + </map> + <map> + <key>name</key> + <string>toup</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>q</string> + <key>type</key> + <string>quaternion</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Returns up vector from quaternion rotation</string> + </map> + </array> + </map> + <key>callSignature</key> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>quaternion</string> + </map> + </map> + <key>comment</key> + <string>Global 'quaternion' library table with callable metatable</string> + </map> + <map> + <key>name</key> + <string>rotation</string> + <key>type</key> + <map> + <key>kind</key> + <string>typeof</string> + <key>target</key> + <string>quaternion</string> + </map> + <key>comment</key> + <string>'rotation' global is an alias to the 'quaternion' library</string> + </map> + <map> + <key>name</key> + <string>uuid</string> + <key>type</key> + <map> + <key>kind</key> + <string>callable-table</string> + <key>tableType</key> + <map> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>create</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>string</string> + <string>buffer</string> + <string>uuid</string> + </array> + </map> + </map> + </array> + <key>returnType</key> + <string>uuid?</string> + </map> + <key>comment</key> + <string>Creates a new uuid from a string, buffer, or existing uuid</string> + </map> + </array> + </map> + <key>callSignature</key> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <map> + <key>kind</key> + <string>union</string> + <key>types</key> + <array> + <string>string</string> + <string>buffer</string> + <string>uuid</string> + </array> + </map> + </map> + </array> + <key>returnType</key> + <string>uuid?</string> + </map> + </map> + <key>comment</key> + <string>Global 'uuid' library table</string> + </map> + <map> + <key>name</key> + <string>vector</string> + <key>type</key> + <map> + <key>kind</key> + <string>callable-table</string> + <key>tableType</key> + <map> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>create</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Creates a new vector with the given component values</string> + </map> + <map> + <key>name</key> + <string>magnitude</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + </map> + <key>comment</key> + <string>Calculates the magnitude of a given vector</string> + </map> + <map> + <key>name</key> + <string>normalize</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Computes the normalized version (unit vector) of a given vector</string> + </map> + <map> + <key>name</key> + <string>cross</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Computes the cross product of two vectors</string> + </map> + <map> + <key>name</key> + <string>dot</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + </map> + <key>comment</key> + <string>Computes the dot product of two vectors</string> + </map> + <map> + <key>name</key> + <string>angle</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>axis</string> + <key>type</key> + <string>vector</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + </map> + <key>comment</key> + <string>Computes the angle between two vectors in radians</string> + </map> + <map> + <key>name</key> + <string>floor</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.floor to every component of the input vector</string> + </map> + <map> + <key>name</key> + <string>ceil</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.ceil to every component of the input vector</string> + </map> + <map> + <key>name</key> + <string>abs</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.abs to every component of the input vector</string> + </map> + <map> + <key>name</key> + <string>sign</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.sign to every component of the input vector</string> + </map> + <map> + <key>name</key> + <string>clamp</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>min</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>max</string> + <key>type</key> + <string>vector</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.clamp to every component of the input vector</string> + </map> + <map> + <key>name</key> + <string>max</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>type</key> + <string>vector</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.max to the corresponding components of the input vectors</string> + </map> + <map> + <key>name</key> + <string>min</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>type</key> + <string>vector</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Applies math.min to the corresponding components of the input vectors</string> + </map> + <map> + <key>name</key> + <string>lerp</string> + <key>type</key> + <map> + <key>kind</key> + <string>function</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>vector</string> + </map> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + <key>comment</key> + <string>Linear interpolation between two vectors</string> + </map> + <map> + <key>name</key> + <string>zero</string> + <key>type</key> + <string>vector</string> + <key>comment</key> + <string>A zero vector <0,0,0></string> + </map> + <map> + <key>name</key> + <string>one</string> + <key>type</key> + <string>vector</string> + <key>comment</key> + <string>A one vector <1,1,1></string> + </map> + </array> + </map> + <key>callSignature</key> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>vector</string> + </map> + </map> + <key>comment</key> + <string>Global 'vector' library table</string> + </map> + <map> + <key>name</key> + <string>LLEvents</string> + <key>type</key> + <string>LLEvents</string> + <key>comment</key> + <string>Second Life event management and registration</string> + </map> + <map> + <key>name</key> + <string>LLTimers</string> + <key>type</key> + <string>LLTimers</string> + <key>comment</key> + <string>Second Life timer management and scheduling</string> + </map> + <map> + <key>name</key> + <string>loadstring</string> + <key>type</key> + <string>nil</string> + <key>comment</key> + <string>loadstring is removed in SLua</string> + </map> + <map> + <key>name</key> + <string>getfenv</string> + <key>type</key> + <string>nil</string> + <key>comment</key> + <string>getfenv is removed in SLua</string> + </map> + <map> + <key>name</key> + <string>setfenv</string> + <key>type</key> + <string>nil</string> + <key>comment</key> + <string>setfenv is removed in SLua</string> + </map> + </array> + <key>modules</key> + <array> + <map> + <key>name</key> + <string>bit32</string> + <key>comment</key> + <string>Bitwise operations library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>arshift</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>disp</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Arithmetic right shift</string> + </map> + <map> + <key>name</key> + <string>band</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Bitwise AND of all arguments</string> + </map> + <map> + <key>name</key> + <string>bnot</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Bitwise NOT</string> + </map> + <map> + <key>name</key> + <string>bor</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Bitwise OR of all arguments</string> + </map> + <map> + <key>name</key> + <string>bxor</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Bitwise XOR of all arguments</string> + </map> + <map> + <key>name</key> + <string>btest</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if bitwise AND of all arguments is not zero</string> + </map> + <map> + <key>name</key> + <string>extract</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>field</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>width</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Extracts bits from n at position field with width</string> + </map> + <map> + <key>name</key> + <string>lrotate</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>disp</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Left rotate</string> + </map> + <map> + <key>name</key> + <string>lshift</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>disp</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Left shift</string> + </map> + <map> + <key>name</key> + <string>replace</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>v</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>field</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>width</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Replaces bits in n at position field with width using value v</string> + </map> + <map> + <key>name</key> + <string>rrotate</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>disp</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Right rotate</string> + </map> + <map> + <key>name</key> + <string>rshift</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>disp</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Right shift</string> + </map> + <map> + <key>name</key> + <string>countlz</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Count leading zeros</string> + </map> + <map> + <key>name</key> + <string>countrz</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Count trailing zeros</string> + </map> + <map> + <key>name</key> + <string>byteswap</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Swap byte order</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>buffer</string> + <key>comment</key> + <string>Buffer manipulation library for binary data</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>create</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>size</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>buffer</string> + <key>comment</key> + <string>Creates a new buffer of the specified size</string> + </map> + <map> + <key>name</key> + <string>fromstring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>str</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>buffer</string> + <key>comment</key> + <string>Creates a buffer from a string</string> + </map> + <map> + <key>name</key> + <string>tostring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Converts buffer to string</string> + </map> + <map> + <key>name</key> + <string>readi8</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read signed 8-bit integer</string> + </map> + <map> + <key>name</key> + <string>readu8</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read unsigned 8-bit integer</string> + </map> + <map> + <key>name</key> + <string>readi16</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read signed 16-bit integer</string> + </map> + <map> + <key>name</key> + <string>readu16</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read unsigned 16-bit integer</string> + </map> + <map> + <key>name</key> + <string>readi32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read signed 32-bit integer</string> + </map> + <map> + <key>name</key> + <string>readu32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read unsigned 32-bit integer</string> + </map> + <map> + <key>name</key> + <string>readf32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read 32-bit float</string> + </map> + <map> + <key>name</key> + <string>readf64</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read 64-bit float</string> + </map> + <map> + <key>name</key> + <string>writei8</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write signed 8-bit integer</string> + </map> + <map> + <key>name</key> + <string>writeu8</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write unsigned 8-bit integer</string> + </map> + <map> + <key>name</key> + <string>writei16</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write signed 16-bit integer</string> + </map> + <map> + <key>name</key> + <string>writeu16</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write unsigned 16-bit integer</string> + </map> + <map> + <key>name</key> + <string>writei32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write signed 32-bit integer</string> + </map> + <map> + <key>name</key> + <string>writeu32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write unsigned 32-bit integer</string> + </map> + <map> + <key>name</key> + <string>writef32</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write 32-bit float</string> + </map> + <map> + <key>name</key> + <string>writef64</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write 64-bit float</string> + </map> + <map> + <key>name</key> + <string>readstring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>count</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Read string from buffer</string> + </map> + <map> + <key>name</key> + <string>writestring</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>count</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write string to buffer</string> + </map> + <map> + <key>name</key> + <string>len</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the length of the buffer</string> + </map> + <map> + <key>name</key> + <string>copy</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>target</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>targetOffset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>source</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>sourceOffset</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>count</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Copy data from source buffer to target buffer</string> + </map> + <map> + <key>name</key> + <string>fill</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>count</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Fill buffer with a value</string> + </map> + <map> + <key>name</key> + <string>readbits</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>bitOffset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>bitCount</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Read bits from buffer</string> + </map> + <map> + <key>name</key> + <string>writebits</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>buffer</string> + </map> + <map> + <key>name</key> + <string>bitOffset</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>bitCount</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Write bits to buffer</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>coroutine</string> + <key>comment</key> + <string>Coroutine manipulation library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>create</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>(...any) -> ...any</string> + </map> + </array> + <key>returnType</key> + <string>thread</string> + <key>comment</key> + <string>Creates a new coroutine from a function</string> + </map> + <map> + <key>name</key> + <string>resume</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>co</string> + <key>type</key> + <string>thread</string> + </map> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>(boolean, ...any)</string> + <key>comment</key> + <string>Resumes a coroutine, returns success and results</string> + </map> + <map> + <key>name</key> + <string>running</string> + <key>parameters</key> + <array/> + <key>returnType</key> + <string>thread?</string> + <key>comment</key> + <string>Returns the running coroutine, or nil if called from main thread</string> + </map> + <map> + <key>name</key> + <string>status</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>co</string> + <key>type</key> + <string>thread</string> + </map> + </array> + <key>returnType</key> + <string>"running" | "suspended" | "normal" | "dead"</string> + <key>comment</key> + <string>Returns the status of a coroutine</string> + </map> + <map> + <key>name</key> + <string>wrap</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>(...any) -> ...any</string> + </map> + </array> + <key>returnType</key> + <string>(...any) -> ...any</string> + <key>comment</key> + <string>Creates a coroutine and returns a function that resumes it</string> + </map> + <map> + <key>name</key> + <string>yield</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Suspends the coroutine and returns values to resume</string> + </map> + <map> + <key>name</key> + <string>isyieldable</string> + <key>parameters</key> + <array/> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if the coroutine can yield</string> + </map> + <map> + <key>name</key> + <string>close</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>co</string> + <key>type</key> + <string>thread</string> + </map> + </array> + <key>returnType</key> + <string>(boolean, string?)</string> + <key>comment</key> + <string>Closes a coroutine, returns success and optional error message</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>debug</string> + <key>comment</key> + <string>Debug library for introspection</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>info</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>thread</string> + <key>type</key> + <string>thread</string> + </map> + <map> + <key>name</key> + <string>level</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>options</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Returns information about a function or stack level</string> + <key>overloads</key> + <array> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>level</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>options</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Returns information about a stack level</string> + </map> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>func</string> + <key>type</key> + <string>(...any) -> ...any</string> + </map> + <map> + <key>name</key> + <string>options</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Returns information about a function</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>traceback</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>thread</string> + <key>type</key> + <string>thread</string> + </map> + <map> + <key>name</key> + <string>message</string> + <key>type</key> + <string>string</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>level</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a string with a traceback of the call stack</string> + <key>overloads</key> + <array> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>message</string> + <key>type</key> + <string>string</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>level</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a string with a traceback of the current call stack</string> + </map> + </array> + </map> + </array> + </map> + <map> + <key>name</key> + <string>llbase64</string> + <key>comment</key> + <string>Base64 encoding/decoding library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>encode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>data</string> + <key>type</key> + <string>string | buffer</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Encodes a string or buffer to base64</string> + </map> + <map> + <key>name</key> + <string>decode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>data</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Decodes a base64 string to a string</string> + <key>overloads</key> + <array> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>data</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>asBuffer</string> + <key>type</key> + <string>boolean</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string | buffer</string> + <key>comment</key> + <string>Decodes a base64 string to a string or buffer</string> + </map> + </array> + </map> + </array> + </map> + <map> + <key>name</key> + <string>lljson</string> + <key>comment</key> + <string>JSON encoding/decoding library for Second Life</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>null</string> + <key>type</key> + <string>any</string> + <key>comment</key> + <string>A constant to pass for null to json encode</string> + </map> + <map> + <key>name</key> + <string>empty_array_mt</string> + <key>type</key> + <string>{ [any]: any }</string> + <key>comment</key> + <string>Metatable for declaring table as an empty array for json encode</string> + </map> + <map> + <key>name</key> + <string>array_mt</string> + <key>type</key> + <string>{ [any]: any }</string> + <key>comment</key> + <string>Metatable for declaring table as an array for json encode</string> + </map> + <map> + <key>name</key> + <string>empty_array</string> + <key>type</key> + <string>any</string> + <key>comment</key> + <string>A constant to pass for an empty array to json encode</string> + </map> + <map> + <key>name</key> + <string>_NAME</string> + <key>type</key> + <string>string</string> + <key>comment</key> + <string>Name of the lljson library</string> + </map> + <map> + <key>name</key> + <string>_VERSION</string> + <key>type</key> + <string>string</string> + <key>comment</key> + <string>Version of the lljson library</string> + </map> + </array> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>encode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Encodes a Lua value as JSON</string> + </map> + <map> + <key>name</key> + <string>decode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>json</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>any</string> + <key>comment</key> + <string>Decodes a JSON string to a Lua value</string> + </map> + <map> + <key>name</key> + <string>slencode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + </map> + <map> + <key>name</key> + <string>tight</string> + <key>type</key> + <string>boolean</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Encodes a Lua value as JSON preserving SL types. Use tight to encode more compactly.</string> + </map> + <map> + <key>name</key> + <string>sldecode</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>json</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>any</string> + <key>comment</key> + <string>Decodes a JSON string to a Lua value preserving SL types</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>math</string> + <key>comment</key> + <string>Mathematical functions library</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>pi</string> + <key>type</key> + <string>number</string> + <key>comment</key> + <string>The value of pi</string> + </map> + <map> + <key>name</key> + <string>huge</string> + <key>type</key> + <string>number</string> + <key>comment</key> + <string>A value larger than any other numeric value (infinity)</string> + </map> + </array> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>abs</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the absolute value of x</string> + </map> + <map> + <key>name</key> + <string>acos</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the arc cosine of x (in radians)</string> + </map> + <map> + <key>name</key> + <string>asin</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the arc sine of x (in radians)</string> + </map> + <map> + <key>name</key> + <string>atan</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the arc tangent of x (in radians)</string> + </map> + <map> + <key>name</key> + <string>atan2</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the arc tangent of y/x (in radians), using the signs to determine the quadrant</string> + </map> + <map> + <key>name</key> + <string>ceil</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the smallest integer larger than or equal to x</string> + </map> + <map> + <key>name</key> + <string>clamp</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>min</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>max</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns n clamped between min and max</string> + </map> + <map> + <key>name</key> + <string>cos</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the cosine of x (x in radians)</string> + </map> + <map> + <key>name</key> + <string>cosh</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the hyperbolic cosine of x</string> + </map> + <map> + <key>name</key> + <string>deg</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Converts x from radians to degrees</string> + </map> + <map> + <key>name</key> + <string>exp</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns e^x</string> + </map> + <map> + <key>name</key> + <string>floor</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the largest integer smaller than or equal to x</string> + </map> + <map> + <key>name</key> + <string>fmod</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the remainder of x/y that rounds towards zero</string> + </map> + <map> + <key>name</key> + <string>frexp</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>(number, number)</string> + <key>comment</key> + <string>Returns m and e such that x = m * 2^e</string> + </map> + <map> + <key>name</key> + <string>ldexp</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>m</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>e</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns m * 2^e</string> + </map> + <map> + <key>name</key> + <string>lerp</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>b</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Linear interpolation between a and b by t</string> + </map> + <map> + <key>name</key> + <string>log</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>base</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the logarithm of x in the given base (default e)</string> + </map> + <map> + <key>name</key> + <string>log10</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the base-10 logarithm of x</string> + </map> + <map> + <key>name</key> + <string>map</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>inMin</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>inMax</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>outMin</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>outMax</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Maps x from input range to output range</string> + </map> + <map> + <key>name</key> + <string>max</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the maximum value among the arguments</string> + </map> + <map> + <key>name</key> + <string>min</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the minimum value among the arguments</string> + </map> + <map> + <key>name</key> + <string>modf</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>(number, number)</string> + <key>comment</key> + <string>Returns the integer and fractional parts of x</string> + </map> + <map> + <key>name</key> + <string>noise</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>y</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>z</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns Perlin noise value for the given coordinates</string> + </map> + <map> + <key>name</key> + <string>pow</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>base</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>exponent</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns base^exponent</string> + </map> + <map> + <key>name</key> + <string>rad</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Converts x from degrees to radians</string> + </map> + <map> + <key>name</key> + <string>random</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>m</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns a pseudo-random number</string> + </map> + <map> + <key>name</key> + <string>randomseed</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>seed</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Sets the seed for the pseudo-random generator</string> + </map> + <map> + <key>name</key> + <string>round</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns x rounded to the nearest integer</string> + </map> + <map> + <key>name</key> + <string>sign</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns -1, 0, or 1 depending on the sign of x</string> + </map> + <map> + <key>name</key> + <string>sin</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the sine of x (x in radians)</string> + </map> + <map> + <key>name</key> + <string>sinh</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the hyperbolic sine of x</string> + </map> + <map> + <key>name</key> + <string>sqrt</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the square root of x</string> + </map> + <map> + <key>name</key> + <string>tan</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the tangent of x (x in radians)</string> + </map> + <map> + <key>name</key> + <string>tanh</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the hyperbolic tangent of x</string> + </map> + <map> + <key>name</key> + <string>isnan</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if x is NaN</string> + </map> + <map> + <key>name</key> + <string>isinf</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if x is infinite</string> + </map> + <map> + <key>name</key> + <string>isfinite</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>x</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if x is finite</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>os</string> + <key>comment</key> + <string>Operating system facilities library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>clock</string> + <key>parameters</key> + <array/> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns CPU time used by the program in seconds</string> + </map> + <map> + <key>name</key> + <string>date</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>format</string> + <key>type</key> + <string>string</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>time</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string | OsDateTime | nil</string> + <key>comment</key> + <string>Returns a string or table containing date and time</string> + </map> + <map> + <key>name</key> + <string>difftime</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t2</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>t1</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the difference in seconds between two times</string> + </map> + <map> + <key>name</key> + <string>time</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>time</string> + <key>type</key> + <string>OsDateTime</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number?</string> + <key>comment</key> + <string>Returns the current time or converts a table to time</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>string</string> + <key>comment</key> + <string>String manipulation library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>byte</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...number</string> + <key>comment</key> + <string>Returns the internal numeric codes of the characters</string> + </map> + <map> + <key>name</key> + <string>char</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a string from character codes</string> + </map> + <map> + <key>name</key> + <string>find</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>pattern</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>init</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>plain</string> + <key>type</key> + <string>boolean</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>(number?, number?, ...string)</string> + <key>comment</key> + <string>Finds first match of pattern in string</string> + </map> + <map> + <key>name</key> + <string>format</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>formatstring</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a formatted string</string> + </map> + <map> + <key>name</key> + <string>gmatch</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>pattern</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>() -> ...string</string> + <key>comment</key> + <string>Returns an iterator function for pattern matches</string> + </map> + <map> + <key>name</key> + <string>gsub</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>pattern</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>repl</string> + <key>type</key> + <string>string | { [string]: string } | (...string) -> string</string> + </map> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>(string, number)</string> + <key>comment</key> + <string>Global substitution of pattern matches</string> + </map> + <map> + <key>name</key> + <string>len</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the length of the string</string> + </map> + <map> + <key>name</key> + <string>lower</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Converts string to lowercase</string> + </map> + <map> + <key>name</key> + <string>match</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>pattern</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>init</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...string</string> + <key>comment</key> + <string>Returns captures from pattern match</string> + </map> + <map> + <key>name</key> + <string>pack</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>fmt</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Packs values into a binary string</string> + </map> + <map> + <key>name</key> + <string>packsize</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>fmt</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the size of a packed string for the given format</string> + </map> + <map> + <key>name</key> + <string>rep</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a string repeated n times</string> + </map> + <map> + <key>name</key> + <string>reverse</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Reverses a string</string> + </map> + <map> + <key>name</key> + <string>split</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>separator</string> + <key>type</key> + <string>string</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>{string}</string> + <key>comment</key> + <string>Splits a string by separator</string> + </map> + <map> + <key>name</key> + <string>sub</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a substring</string> + </map> + <map> + <key>name</key> + <string>unpack</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>fmt</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>pos</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Unpacks values from a binary string</string> + </map> + <map> + <key>name</key> + <string>upper</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Converts string to uppercase</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>table</string> + <key>comment</key> + <string>Table manipulation library</string> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>concat</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{string}</string> + </map> + <map> + <key>name</key> + <string>sep</string> + <key>type</key> + <string>string</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Concatenates table elements into a string</string> + </map> + <map> + <key>name</key> + <string>foreach</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{[any]: any}</string> + </map> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>(key: any, value: any) -> any</string> + </map> + </array> + <key>returnType</key> + <string>any?</string> + <key>comment</key> + <string>Iterates over table key-value pairs (deprecated)</string> + </map> + <map> + <key>name</key> + <string>foreachi</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>(index: number, value: any) -> any</string> + </map> + </array> + <key>returnType</key> + <string>any?</string> + <key>comment</key> + <string>Iterates over array indices (deprecated)</string> + </map> + <map> + <key>name</key> + <string>getn</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{any}</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the length of a table (deprecated, use # operator)</string> + </map> + <map> + <key>name</key> + <string>maxn</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{any}</string> + </map> + </array> + <key>returnType</key> + <string>number</string> + <key>comment</key> + <string>Returns the largest positive numeric index</string> + </map> + <map> + <key>name</key> + <string>insert</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Inserts an element at the end of a list</string> + <key>overloads</key> + <array> + <map> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>pos</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Inserts an element at a specific position</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>remove</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>pos</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>any?</string> + <key>comment</key> + <string>Removes and returns an element from a list</string> + </map> + <map> + <key>name</key> + <string>sort</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>comp</string> + <key>type</key> + <string>(a: any, b: any) -> boolean</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Sorts list elements in place</string> + </map> + <map> + <key>name</key> + <string>pack</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>any</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>{ n: number, [number]: any }</string> + <key>comment</key> + <string>Packs arguments into a table with length field n</string> + </map> + <map> + <key>name</key> + <string>unpack</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>list</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Unpacks table elements as multiple return values</string> + </map> + <map> + <key>name</key> + <string>move</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>a1</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>e</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>a2</string> + <key>type</key> + <string>{any}</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>{any}</string> + <key>comment</key> + <string>Moves elements from one table to another</string> + </map> + <map> + <key>name</key> + <string>create</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>count</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>{any}</string> + <key>comment</key> + <string>Creates a new table with pre-allocated array slots</string> + </map> + <map> + <key>name</key> + <string>find</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{any}</string> + </map> + <map> + <key>name</key> + <string>value</string> + <key>type</key> + <string>any</string> + </map> + <map> + <key>name</key> + <string>init</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number?</string> + <key>comment</key> + <string>Finds the index of a value in an array</string> + </map> + <map> + <key>name</key> + <string>clear</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{[any]: any}</string> + </map> + </array> + <key>returnType</key> + <string>()</string> + <key>comment</key> + <string>Removes all elements from a table</string> + </map> + <map> + <key>name</key> + <string>freeze</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{[any]: any}</string> + </map> + </array> + <key>returnType</key> + <string>{[any]: any}</string> + <key>comment</key> + <string>Makes a table read-only</string> + </map> + <map> + <key>name</key> + <string>isfrozen</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{[any]: any}</string> + </map> + </array> + <key>returnType</key> + <string>boolean</string> + <key>comment</key> + <string>Returns true if a table is frozen</string> + </map> + <map> + <key>name</key> + <string>clone</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>t</string> + <key>type</key> + <string>{[any]: any}</string> + </map> + </array> + <key>returnType</key> + <string>{[any]: any}</string> + <key>comment</key> + <string>Creates a shallow copy of a table</string> + </map> + </array> + </map> + <map> + <key>name</key> + <string>utf8</string> + <key>comment</key> + <string>UTF-8 support library</string> + <key>properties</key> + <array> + <map> + <key>name</key> + <string>charpattern</string> + <key>type</key> + <string>string</string> + <key>comment</key> + <string>Pattern that matches exactly one UTF-8 byte sequence</string> + </map> + </array> + <key>functions</key> + <array> + <map> + <key>name</key> + <string>char</string> + <key>parameters</key> + <array> + <map> + <key>type</key> + <string>number</string> + <key>variadic</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>string</string> + <key>comment</key> + <string>Returns a string from UTF-8 codepoints</string> + </map> + <map> + <key>name</key> + <string>codes</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + </array> + <key>returnType</key> + <string>((string, number) -> (number, number), string, number)</string> + <key>comment</key> + <string>Returns an iterator for UTF-8 codepoints in a string</string> + </map> + <map> + <key>name</key> + <string>codepoint</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>...number</string> + <key>comment</key> + <string>Returns the codepoints of characters in a string</string> + </map> + <map> + <key>name</key> + <string>len</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + <map> + <key>name</key> + <string>j</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>(number?, number?)</string> + <key>comment</key> + <string>Returns the number of UTF-8 characters in a string, or nil and error position</string> + </map> + <map> + <key>name</key> + <string>offset</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>s</string> + <key>type</key> + <string>string</string> + </map> + <map> + <key>name</key> + <string>n</string> + <key>type</key> + <string>number</string> + </map> + <map> + <key>name</key> + <string>i</string> + <key>type</key> + <string>number</string> + <key>optional</key> + <boolean>true</boolean> + </map> + </array> + <key>returnType</key> + <string>number?</string> + <key>comment</key> + <string>Returns the byte position of the n-th character</string> + </map> + </array> + </map> + </array> + <key>globalFunctions</key> + <array> + <map> + <key>name</key> + <string>dangerouslyexecuterequiredmodule</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>f</string> + <key>type</key> + <string>(...any) -> ...any</string> + </map> + </array> + <key>returnType</key> + <string>...any</string> + <key>comment</key> + <string>Dangerously executes a required module function</string> + </map> + <map> + <key>name</key> + <string>touuid</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>val</string> + <key>type</key> + <string>string | buffer | uuid</string> + </map> + </array> + <key>returnType</key> + <string>uuid?</string> + <key>comment</key> + <string>Converts a string, buffer, or uuid to a uuid, returns nil if invalid</string> + </map> + <map> + <key>name</key> + <string>tovector</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>val</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>vector?</string> + <key>comment</key> + <string>Converts a value to a vector, returns nil if invalid</string> + </map> + <map> + <key>name</key> + <string>toquaternion</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>val</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>quaternion?</string> + <key>comment</key> + <string>Converts a value to a quaternion, returns nil if invalid</string> + </map> + <map> + <key>name</key> + <string>torotation</string> + <key>parameters</key> + <array> + <map> + <key>name</key> + <string>val</string> + <key>type</key> + <string>any</string> + </map> + </array> + <key>returnType</key> + <string>quaternion?</string> + <key>comment</key> + <string>Converts a value to a rotation (quaternion), returns nil if invalid</string> + </map> + </array> + <key>constants</key> + <array/> +</map> +</llsd> diff --git a/indra/newview/llaisapi.cpp b/indra/newview/llaisapi.cpp index 1da1647fe8..9c76f56ef3 100644 --- a/indra/newview/llaisapi.cpp +++ b/indra/newview/llaisapi.cpp @@ -1060,7 +1060,12 @@ void AISUpdate::checkTimeout() { if (mTimer.hasExpired()) { - llcoro::suspend(); + // If we are taking too long, don't starve other tasks, + // yield to mainloop. + // If we use normal suspend(), there will be a chance of + // waking up from other suspends, before main coro had + // a chance, so wait for a frame tick instead. + llcoro::suspendUntilNextFrame(); LLCoros::checkStop(); mTimer.setTimerExpirySec(AIS_EXPIRY_SECONDS); } diff --git a/indra/newview/llappviewer.cpp b/indra/newview/llappviewer.cpp index ab4a0fbc28..0b882a2265 100644 --- a/indra/newview/llappviewer.cpp +++ b/indra/newview/llappviewer.cpp @@ -109,6 +109,7 @@ #include "lllocalbitmaps.h" #include "llperfstats.h" #include "llgltfmateriallist.h" +#include "llwebsocketmgr.h" // Linden library includes #include "llavatarnamecache.h" @@ -1350,8 +1351,7 @@ bool LLAppViewer::frame() bool LLAppViewer::doFrame() { - LL_RECORD_BLOCK_TIME(FTM_FRAME); - LL_PROFILE_GPU_ZONE("Frame"); + resumeMainloopTimeout("Main:doFrameStart"); #ifdef LL_DISCORD { LL_PROFILE_ZONE_NAMED("discord_callbacks"); @@ -1644,17 +1644,20 @@ bool LLAppViewer::doFrame() if (LLApp::isExiting()) { + pingMainloopTimeout("Main:qSnapshot"); // Save snapshot for next time, if we made it through initialization if (STATE_STARTED == LLStartUp::getStartupState()) { saveFinalSnapshot(); } + pingMainloopTimeout("Main:TerminateVoice"); if (LLVoiceClient::instanceExists()) { LLVoiceClient::getInstance()->terminate(); } + pingMainloopTimeout("Main:TerminatePump"); delete gServicePump; gServicePump = NULL; @@ -1663,6 +1666,11 @@ bool LLAppViewer::doFrame() LL_INFOS() << "Exiting main_loop" << LL_ENDL; } }LLPerfStats::StatsRecorder::endFrame(); + + // Not viewer's fault if something outside frame + // pauses viewer (ex: macOS doesn't call oneFrame), + // so stop tracking on exit. + pauseMainloopTimeout(); LL_PROFILER_FRAME_END; return ! LLApp::isRunning(); @@ -3202,7 +3210,6 @@ bool LLAppViewer::initWindow() app->createErrorMarker(LAST_EXEC_FROZE); } }); - gViewerWindow->getWindow()->initWatchdog(); } LLNotificationsUI::LLNotificationManager::getInstance(); @@ -4174,6 +4181,7 @@ void LLAppViewer::requestQuit() return; } + pingMainloopTimeout("Main:qMetrics"); // Try to send metrics back to the grid metricsSend(!gDisconnected); @@ -4189,6 +4197,7 @@ void LLAppViewer::requestQuit() LLHUDManager::getInstance()->sendEffects(); effectp->markDead() ;//remove it. + pingMainloopTimeout("Main:qFloaters"); // Attempt to close all floaters that might be // editing things. if (gFloaterView) @@ -4197,6 +4206,7 @@ void LLAppViewer::requestQuit() gFloaterView->closeAllChildren(true); mClosingFloaters = true; } + pingMainloopTimeout("Main:qStats"); // Send preferences once, when exiting bool include_preferences = true; @@ -4204,6 +4214,7 @@ void LLAppViewer::requestQuit() gLogoutTimer.reset(); mQuitRequested = true; + pingMainloopTimeout("Main:LoggingOut"); } static bool finish_quit(const LLSD& notification, const LLSD& response) @@ -4832,6 +4843,11 @@ void LLAppViewer::idle() LLMortician::updateClass(); LLFilePickerThread::clearDead(); //calls LLFilePickerThread::notify() LLDirPickerThread::clearDead(); + + if (LLWebsocketMgr::instanceExists()) + { + LLWebsocketMgr::instance().update(); + } F32 dt_raw = idle_timer.getElapsedTimeAndResetF32(); LLGLTFMaterialList::flushUpdates(); @@ -5503,6 +5519,7 @@ void LLAppViewer::outOfMemorySoftQuit() LLLFSThread::sLocal->pause(); gLogoutTimer.reset(); mQuitRequested = true; + destroyMainloopTimeout(); LLError::LLUserWarningMsg::showOutOfMemory(); } @@ -5919,10 +5936,16 @@ void LLAppViewer::pingMainloopTimeout(std::string_view state) F32 LLAppViewer::getMainloopTimeoutSec() const { + if (isQuitting() || mQuitRequested) + { + constexpr F32 QUITTING_SECONDS = 240.f; + return QUITTING_SECONDS; + } if (LLStartUp::getStartupState() == STATE_STARTED && gAgent.getTeleportState() == LLAgent::TELEPORT_NONE) { - static LLCachedControl<F32> mainloop_started(gSavedSettings, "MainloopTimeoutStarted", 30.f); + // consider making this value match 'disconnected' timout. + static LLCachedControl<F32> mainloop_started(gSavedSettings, "MainloopTimeoutStarted", 60.f); return mainloop_started(); } else @@ -5936,6 +5959,11 @@ void LLAppViewer::handleLoginComplete() { gLoggedInTime.start(); initMainloopTimeout("Mainloop Init"); + LLWindow* viewer_window = gViewerWindow->getWindow(); + if (viewer_window) // in case of a headless client + { + viewer_window->initWatchdog(); + } // Store some data to DebugInfo in case of a freeze. gDebugInfo["ClientInfo"]["Name"] = LLVersionInfo::instance().getChannel(); diff --git a/indra/newview/llcompilequeue.cpp b/indra/newview/llcompilequeue.cpp index e0236ca618..e0f464168c 100644 --- a/indra/newview/llcompilequeue.cpp +++ b/indra/newview/llcompilequeue.cpp @@ -61,6 +61,7 @@ #include "llviewerassetupload.h" #include "llcorehttputil.h" +#include "llpreviewscript.h" namespace { @@ -122,9 +123,9 @@ namespace class LLQueuedScriptAssetUpload : public LLScriptAssetUpload { public: - LLQueuedScriptAssetUpload(LLUUID taskId, LLUUID itemId, LLUUID assetId, TargetType_t targetType, + LLQueuedScriptAssetUpload(LLUUID taskId, LLUUID itemId, LLUUID assetId, std::string compileTarget, bool isRunning, std::string scriptName, LLUUID queueId, LLUUID exerienceId, taskUploadFinish_f finish) : - LLScriptAssetUpload(taskId, itemId, targetType, isRunning, + LLScriptAssetUpload(taskId, itemId, compileTarget, isRunning, exerienceId, std::string(), finish, nullptr), mScriptName(scriptName), mQueueId(queueId) @@ -183,9 +184,7 @@ struct LLScriptQueueData // Default constructor LLFloaterScriptQueue::LLFloaterScriptQueue(const LLSD& key) : - LLFloater(key), - mDone(false), - mMono(false) + LLFloater(key) { } @@ -197,7 +196,7 @@ LLFloaterScriptQueue::~LLFloaterScriptQueue() bool LLFloaterScriptQueue::postBuild() { - childSetAction("close",onCloseBtn,this); + childSetAction("close", onCloseBtn, this); getChildView("close")->setEnabled(false); setVisible(true); return true; @@ -222,8 +221,8 @@ bool LLFloaterScriptQueue::start() LLStringUtil::format_map_t args; args["[START]"] = mStartString; - args["[COUNT]"] = llformat ("%d", mObjectList.size()); - buffer = getString ("Starting", args); + args["[COUNT]"] = llformat("%d", mObjectList.size()); + buffer = getString("Starting", args); getChild<LLScrollListCtrl>("queue output")->addSimpleElement(buffer, ADD_BOTTOM); @@ -276,8 +275,8 @@ bool LLFloaterCompileQueue::hasExperience( const LLUUID& id ) const return mExperienceIds.find(id) != mExperienceIds.end(); } -// //Attempt to record this asset ID. If it can not be inserted into the set -// //then it has already been processed so return false. +// Attempt to record this asset ID. If it can not be inserted into the set +// then it has already been processed so return false. void LLFloaterCompileQueue::handleHTTPResponse(std::string pumpName, const LLSD &expresult) { @@ -359,7 +358,7 @@ bool LLFloaterCompileQueue::processScript(LLHandle<LLFloaterCompileQueue> hfloat LLCheckedHandle<LLFloaterCompileQueue> floater(hfloater); // Dereferencing floater may fail. If they do they throw LLExeceptionStaleHandle. // which is caught in objectScriptProcessingQueueCoro - bool monocompile = floater->mMono; + std::string compile_target = floater->mCompileTarget; // Initial test to see if we can (or should) attempt to compile the script. LLInventoryItem *item = dynamic_cast<LLInventoryItem *>(inventory); @@ -464,13 +463,40 @@ bool LLFloaterCompileQueue::processScript(LLHandle<LLFloaterCompileQueue> hfloat LLUUID assetId = result["asset_id"]; + // Check if this is a SLua script that shouldn't be recompiled to Mono/LSL + if (compile_target == "mono" || compile_target == "lsl2") + { + // Read the script from cache to check its type + LLFileSystem file(assetId, LLAssetType::AT_LSL_TEXT, LLFileSystem::READ); + if (file.getSize() > 0) + { + S32 file_length = file.getSize(); + std::vector<char> buffer(file_length + 1); + file.read((U8*)&buffer[0], file_length); + buffer[file_length] = 0; + std::string script_text(&buffer[0]); + + if (is_lua_script(script_text)) + { + // This is a SLua script - skip it with a warning + LLStringUtil::format_map_t args; + args["[SCRIPT_NAME]"] = inventory->getName(); + args["[TARGET]"] = (compile_target == "mono") ? "Mono" : "LSL"; + std::string buffer = floater->getString("SkippingSluaScript", args); + floater->addStringMessage(buffer); + LL_INFOS("SCRIPTQ") << "Skipping SLua script: " << inventory->getName() << LL_ENDL; + return true; + } + } + } + std::string url = object->getRegion()->getCapability("UpdateScriptTask"); { LLResourceUploadInfo::ptr_t uploadInfo = std::make_shared<LLQueuedScriptAssetUpload>(object->getID(), inventory->getUUID(), assetId, - monocompile ? LLScriptAssetUpload::MONO : LLScriptAssetUpload::LSL2, + compile_target, true, inventory->getName(), LLUUID(), diff --git a/indra/newview/llcompilequeue.h b/indra/newview/llcompilequeue.h index bcbb166c58..8832d76ea4 100644 --- a/indra/newview/llcompilequeue.h +++ b/indra/newview/llcompilequeue.h @@ -55,7 +55,7 @@ public: /*virtual*/ bool postBuild(); - void setMono(bool mono) { mMono = mono; } + void setCompileTarget(std::string target) { mCompileTarget = target; } // addObject() accepts an object id. void addObject(const LLUUID& id, std::string name); @@ -80,8 +80,8 @@ protected: protected: // UI - LLScrollListCtrl* mMessages; - LLButton* mCloseBtn; + LLScrollListCtrl* mMessages { nullptr }; + LLButton* mCloseBtn { nullptr }; // Object Queue struct ObjectData @@ -93,14 +93,13 @@ protected: object_data_list_t mObjectList; LLUUID mCurrentObjectID; - bool mDone; + bool mDone { false }; std::string mStartString; - bool mMono; + std::string mCompileTarget { "lsl2" }; typedef std::function<bool(const LLPointer<LLViewerObject> &, LLInventoryObject*, LLEventPump &)> fnQueueAction_t; static void objectScriptProcessingQueueCoro(std::string action, LLHandle<LLFloaterScriptQueue> hfloater, object_data_list_t objectList, fnQueueAction_t func); - }; //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ diff --git a/indra/newview/llfeaturemanager.cpp b/indra/newview/llfeaturemanager.cpp index 5ff8938a47..5a2b1c719c 100644 --- a/indra/newview/llfeaturemanager.cpp +++ b/indra/newview/llfeaturemanager.cpp @@ -494,7 +494,9 @@ bool LLFeatureManager::loadGPUClass() { mGPUClass = GPU_CLASS_2; } - else if (gbps <= class1_gbps*4.f) + else if ((gbps <= class1_gbps*4.f) + // Cap silicon's GPUs at med+ as they have high throughput, low capability + || gGLManager.mIsApple) { mGPUClass = GPU_CLASS_3; } @@ -516,7 +518,7 @@ bool LLFeatureManager::loadGPUClass() // reduce quality on systems that don't have enough memory mGPUClass = (EGPUClass)(mGPUClass - 1); } - #endif //LL_WINDOWS + #endif //LL_WINDOWS || LL_LINUX } //end if benchmark else { diff --git a/indra/newview/llfilepicker.cpp b/indra/newview/llfilepicker.cpp index f540ca549a..c5af3bec9e 100644 --- a/indra/newview/llfilepicker.cpp +++ b/indra/newview/llfilepicker.cpp @@ -63,7 +63,7 @@ LLFilePicker LLFilePicker::sInstance; #define MATERIAL_FILTER L"GLTF Files (*.gltf; *.glb)\0*.gltf;*.glb\0" #define HDRI_FILTER L"HDRI Files (*.exr)\0*.exr\0" #define MATERIAL_TEXTURES_FILTER L"GLTF Import (*.gltf; *.glb; *.tga; *.bmp; *.jpg; *.jpeg; *.png)\0*.gltf;*.glb;*.tga;*.bmp;*.jpg;*.jpeg;*.png\0" -#define SCRIPT_FILTER L"Script files (*.lsl)\0*.lsl\0" +#define SCRIPT_FILTER L"Script files (*.lsl; *.lua; *.luau)\0*.lsl;*.lua;*.luau\0" #define DICTIONARY_FILTER L"Dictionary files (*.dic; *.xcu)\0*.dic;*.xcu\0" #endif @@ -226,7 +226,7 @@ namespace filter_vec.push_back({ "HDRI Files (*.exr)", "exr" }); break; case LLFilePicker::FFLOAD_SCRIPT: - filter_vec.push_back({ "Script files (*.lsl)", "lsl" }); + filter_vec.push_back({ "Script files (*.lsl; *.lua; *.luau)", "lsl;lua;luau" }); break; case LLFilePicker::FFLOAD_DICTIONARY: filter_vec.push_back({ "Dictionary files (*.dic; *.xcu)", "dic;xcu" }); @@ -543,7 +543,7 @@ bool LLFilePicker::getSaveFileModeless(ESaveFilter filter, { default_filename = "untitled.lsl"; } - file_filters.push_back({ "LSL Files (*.lsl)", "lsl" }); + file_filters.push_back({ "Script files (*.lsl; *.lua; *.luau)", "lsl;lua;luau" }); break; default: return false; @@ -1132,6 +1132,8 @@ std::unique_ptr<std::vector<std::string>> LLFilePicker::navOpenFilterProc(ELoadF break; case FFLOAD_SCRIPT: allowedv->push_back("lsl"); + allowedv->push_back("lua"); + allowedv->push_back("luau"); break; case FFLOAD_DICTIONARY: allowedv->push_back("dic"); @@ -1265,7 +1267,7 @@ void set_nav_save_data(LLFilePicker::ESaveFilter filter, std::string &extension, case LLFilePicker::FFSAVE_SCRIPT: type = "LSL "; creator = "\?\?\?\?"; - extension = "lsl"; + extension = "lsl;lua;luau"; break; case LLFilePicker::FFSAVE_ALL: diff --git a/indra/newview/llfloatergotoline.cpp b/indra/newview/llfloatergotoline.cpp index 09ca0ab530..6b3f16ecf5 100644 --- a/indra/newview/llfloatergotoline.cpp +++ b/indra/newview/llfloatergotoline.cpp @@ -109,8 +109,9 @@ void LLFloaterGotoLine::handleBtnGoto() { if (mEditorCore && mEditorCore->mEditor) { + S32 target_row = mEditorCore->mEditor->getIsLuauLanguage() ? (row - 1) : row; mEditorCore->mEditor->deselect(); - mEditorCore->mEditor->setCursor(row, column); + mEditorCore->mEditor->setCursor(target_row, column); mEditorCore->mEditor->setFocus(true); } } @@ -144,12 +145,13 @@ void LLFloaterGotoLine::onGotoBoxCommit() { if (mEditorCore && mEditorCore->mEditor) { - mEditorCore->mEditor->setCursor(row, column); + S32 target_row = mEditorCore->mEditor->getIsLuauLanguage() ? (row - 1) : row; + mEditorCore->mEditor->setCursor(target_row, column); S32 rownew = 0; S32 columnnew = 0; mEditorCore->mEditor->getCurrentLineAndColumn( &rownew, &columnnew, false ); // don't include wordwrap - if (rownew == row && columnnew == column) + if (rownew == target_row && columnnew == column) { mEditorCore->mEditor->deselect(); mEditorCore->mEditor->setFocus(true); diff --git a/indra/newview/llfloaterimnearbychathandler.cpp b/indra/newview/llfloaterimnearbychathandler.cpp index ec9458ea9b..b107188417 100644 --- a/indra/newview/llfloaterimnearbychathandler.cpp +++ b/indra/newview/llfloaterimnearbychathandler.cpp @@ -44,6 +44,7 @@ #include "llfloaterimcontainer.h" #include "llrootview.h" #include "lllayoutstack.h" +#include "llscripteditorws.h" //add LLFloaterIMNearbyChatHandler to LLNotificationsUI namespace using namespace LLNotificationsUI; @@ -335,6 +336,7 @@ void LLFloaterIMNearbyChatScreenChannel::addChat(LLSD& chat) { if (!gSavedSettings.getBOOL("ShowScriptErrors")) return; + if (gSavedSettings.getS32("ShowScriptErrorsLocation") == 1) return; } @@ -526,6 +528,15 @@ void LLFloaterIMNearbyChatHandler::processChat(const LLChat& chat_msg, if (!gSavedSettings.getBOOL("ShowScriptErrors")) return; + if (gSavedSettings.getBOOL("ExternalWebsocketSyncEnable") && gSavedSettings.getBOOL("ExternalWebsocketForwardDebug")) + { + LLScriptEditorWSServer::ptr_t server = LLScriptEditorWSServer::getServer(); + if (server) + { + server->forwardChatToIDE(chat_msg); + } + } + // don't process debug messages from not owned objects, see EXT-7762 if (gAgentID != chat_msg.mOwnerID) { @@ -545,6 +556,16 @@ void LLFloaterIMNearbyChatHandler::processChat(const LLChat& chat_msg, return; } } + else if ((chat_msg.mChatType == CHAT_TYPE_OWNER) && + gSavedSettings.getBOOL("ExternalWebsocketSyncEnable") && + gSavedSettings.getBOOL("ExternalWebsocketForwardDebug")) + { + LLScriptEditorWSServer::ptr_t server = LLScriptEditorWSServer::getServer(); + if (server) + { + server->forwardChatToIDE(chat_msg); + } + } nearby_chat->addMessage(chat_msg, true, args); diff --git a/indra/newview/llfloaterpreference.cpp b/indra/newview/llfloaterpreference.cpp index 024017ad9b..81e3619ef0 100644 --- a/indra/newview/llfloaterpreference.cpp +++ b/indra/newview/llfloaterpreference.cpp @@ -346,6 +346,7 @@ LLFloaterPreference::LLFloaterPreference(const LLSD& key) mCommitCallbackRegistrar.add("Pref.RememberedUsernames", boost::bind(&LLFloaterPreference::onClickRememberedUsernames, this)); mCommitCallbackRegistrar.add("Pref.SpellChecker", boost::bind(&LLFloaterPreference::onClickSpellChecker, this)); mCommitCallbackRegistrar.add("Pref.Advanced", boost::bind(&LLFloaterPreference::onClickAdvanced, this)); + mCommitCallbackRegistrar.add("Pref.Scripting", boost::bind(&LLFloaterPreference::onClickScriptingPerfs, this)); sSkin = gSavedSettings.getString("SkinCurrent"); @@ -1742,6 +1743,22 @@ void LLFloaterPreference::onChangeMaturity() || sim_access == SIM_ACCESS_ADULT); getChild<LLIconCtrl>("rating_icon_adult")->setVisible(sim_access == SIM_ACCESS_ADULT); + + // Update Legacy Search maturity settings + bool can_access_mature = gAgent.canAccessMature(); + bool can_access_adult = gAgent.canAccessAdult(); + if (!can_access_mature) + { + gSavedSettings.setBOOL("ShowMatureSims", false); + gSavedSettings.setBOOL("ShowMatureLand", false); + gSavedSettings.setBOOL("ShowMatureClassifieds", false); + } + if (!can_access_adult) + { + gSavedSettings.setBOOL("ShowAdultSims", false); + gSavedSettings.setBOOL("ShowAdultLand", false); + gSavedSettings.setBOOL("ShowAdultClassifieds", false); + } } void LLFloaterPreference::onChangeComplexityMode(const LLSD& newvalue) @@ -1855,6 +1872,11 @@ void LLFloaterPreference::onClickAdvanced() } } +void LLFloaterPreference::onClickScriptingPerfs() +{ + LLFloaterReg::showInstance("scripting_settings"); +} + void LLFloaterPreference::onClickActionChange() { updateClickActionControls(); diff --git a/indra/newview/llfloaterpreference.h b/indra/newview/llfloaterpreference.h index 3028bec64a..aa958459c9 100644 --- a/indra/newview/llfloaterpreference.h +++ b/indra/newview/llfloaterpreference.h @@ -191,6 +191,7 @@ public: void onClickRenderExceptions(); void onClickAutoAdjustments(); void onClickAdvanced(); + void onClickScriptingPerfs(); void applyUIColor(LLUICtrl* ctrl, const LLSD& param); void getUIColor(LLUICtrl* ctrl, const LLSD& param); void onLogChatHistorySaved(); diff --git a/indra/newview/llfloaterscripting.cpp b/indra/newview/llfloaterscripting.cpp new file mode 100644 index 0000000000..0719ced58d --- /dev/null +++ b/indra/newview/llfloaterscripting.cpp @@ -0,0 +1,106 @@ +/** + * @file llfloaterscripting.cpp + * @brief Asset creation permission preferences. + * @author Jonathan Yap + * + * $LicenseInfo:firstyear=2001&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#include "llviewerprecompiledheaders.h" +#include "llcheckboxctrl.h" +#include "llfloaterscripting.h" +#include "llviewercontrol.h" +#include "llviewerwindow.h" +#include "lluictrlfactory.h" +#include "llpermissions.h" +#include "llagent.h" +#include "llviewerregion.h" +#include "llnotificationsutil.h" +#include "llsdserialize.h" +#include "llvoavatar.h" +#include "llcorehttputil.h" +#include "lleventfilter.h" +#include "lleventcoro.h" +#include "llviewermenufile.h" +#include "llappviewer.h" + +namespace +{ + class LLEditorPicker : public LLFilePickerThread + { + public: + LLEditorPicker(LLFloaterScripting *floater): + LLFilePickerThread(LLFilePicker::FFLOAD_EXE) + { + mHandle = floater->getDerivedHandle<LLFloaterScripting>(); + } + void notify(const std::vector<std::string>& filenames) override + { + if (LLAppViewer::instance()->quitRequested()) + { + return; + } + + LLFloaterScripting* floater = mHandle.get(); + if (floater && !filenames.empty()) + { + floater->pickedEditor(filenames.front()); + } + } + + private: + LLHandle<LLFloaterScripting> mHandle; + }; + +} + +LLFloaterScripting::LLFloaterScripting(const LLSD& seed) + : LLFloater(seed) +{ + mCommitCallbackRegistrar.add("ScriptingSettings.CLOSE", boost::bind(&LLFloaterScripting::onClickClose, this)); + mCommitCallbackRegistrar.add("ScriptingSettings.BROWSE", boost::bind(&LLFloaterScripting::onClickBrowse, this)); +} + +bool LLFloaterScripting::postBuild() +{ + refresh(); + return true; +} + +void LLFloaterScripting::onClickClose() +{ + closeFloater(); +} + +void LLFloaterScripting::onClickBrowse() +{ + (new LLEditorPicker(this))->getFile(); +} + +void LLFloaterScripting::pickedEditor(std::string_view editor) +{ + assert_main_thread(); + std::stringstream cmdline; + cmdline << "\"" << editor << "\" \"%s\""; + + gSavedSettings.setString("ExternalEditor", cmdline.str()); +} diff --git a/indra/newview/llfloaterscripting.h b/indra/newview/llfloaterscripting.h new file mode 100644 index 0000000000..ca7bd3e091 --- /dev/null +++ b/indra/newview/llfloaterscripting.h @@ -0,0 +1,49 @@ +/** + * @file llfloaterscripting.h + * @brief Asset creation permission preferences. + * @author Jonathan Yap + * + * $LicenseInfo:firstyear=2002&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#pragma once + +#include "llfloater.h" +#include "lleventcoro.h" +#include "llcoros.h" + +class LLFloaterScripting : public LLFloater +{ + friend class LLFloaterReg; + +public: + bool postBuild() override; + void onClickClose(); + void onClickBrowse(); + + void pickedEditor(std::string_view editor); + +private: + LLFloaterScripting(const LLSD& seed); + +}; + diff --git a/indra/newview/llinventorybridge.cpp b/indra/newview/llinventorybridge.cpp index 542c0fdfdd..b4cce02bda 100644 --- a/indra/newview/llinventorybridge.cpp +++ b/indra/newview/llinventorybridge.cpp @@ -1860,7 +1860,14 @@ void LLItemBridge::performAction(LLInventoryModel* model, std::string action) { LLVector3d global_pos; landmark->getGlobalPos(global_pos); - LLLandmarkActions::getSLURLfromPosGlobal(global_pos, ©_slurl_to_clipboard_callback_inv, true); + if (!global_pos.isExactlyZero()) + { + LLLandmarkActions::getSLURLfromPosGlobal(global_pos, ©_slurl_to_clipboard_callback_inv, true); + } + else + { + LLNotificationsUtil::add("LandmarkLocationUnknown"); + } } } } diff --git a/indra/newview/llinventorygallerymenu.cpp b/indra/newview/llinventorygallerymenu.cpp index c0c93f56e0..6c72b0b7ee 100644 --- a/indra/newview/llinventorygallerymenu.cpp +++ b/indra/newview/llinventorygallerymenu.cpp @@ -338,14 +338,21 @@ void LLInventoryGalleryContextMenu::doToSelected(const LLSD& userdata) { LLVector3d global_pos; landmark->getGlobalPos(global_pos); - std::function<void(std::string& slurl)> copy_slurl_to_clipboard_cb = [](const std::string& slurl) + if (!global_pos.isExactlyZero()) { - gViewerWindow->getWindow()->copyTextToClipboard(utf8str_to_wstring(slurl)); - LLSD args; - args["SLURL"] = slurl; - LLNotificationsUtil::add("CopySLURL", args); - }; - LLLandmarkActions::getSLURLfromPosGlobal(global_pos, copy_slurl_to_clipboard_cb, true); + std::function<void(std::string& slurl)> copy_slurl_to_clipboard_cb = [](const std::string& slurl) + { + gViewerWindow->getWindow()->copyTextToClipboard(utf8str_to_wstring(slurl)); + LLSD args; + args["SLURL"] = slurl; + LLNotificationsUtil::add("CopySLURL", args); + }; + LLLandmarkActions::getSLURLfromPosGlobal(global_pos, copy_slurl_to_clipboard_cb, true); + } + else + { + LLNotificationsUtil::add("LandmarkLocationUnknown"); + } }; LLLandmark* landmark = LLLandmarkActions::getLandmark(mUUIDs.front(), copy_slurl_cb); if (landmark) diff --git a/indra/newview/lllandmarkactions.cpp b/indra/newview/lllandmarkactions.cpp index 73425e9f4c..9b90e41549 100644 --- a/indra/newview/lllandmarkactions.cpp +++ b/indra/newview/lllandmarkactions.cpp @@ -80,6 +80,40 @@ public: } }; +class LLFetchFirstLandmarkByPos : public LLInventoryCollectFunctor +{ +private: + LLVector3d mPos; + bool mFound = false; +public: + LLFetchFirstLandmarkByPos(const LLVector3d& pos) : + mPos(pos), mFound(false) + { + } + + /*virtual*/ bool operator()(LLInventoryCategory* cat, LLInventoryItem* item) + { + if (mFound || !item || item->getType() != LLAssetType::AT_LANDMARK) + return false; + + LLLandmark* landmark = gLandmarkList.getAsset(item->getAssetUUID()); + if (!landmark) // the landmark not been loaded yet + return false; + + LLVector3d landmark_global_pos; + if (!landmark->getGlobalPos(landmark_global_pos)) + return false; + //we have to round off each coordinates to compare positions properly + mFound = ll_round(mPos.mdV[VX]) == ll_round(landmark_global_pos.mdV[VX]) + && ll_round(mPos.mdV[VY]) == ll_round(landmark_global_pos.mdV[VY]) + && ll_round(mPos.mdV[VZ]) == ll_round(landmark_global_pos.mdV[VZ]); + return mFound; + } + + // only care about first found landmark, so stop when found + /*virtual*/ bool exceedsLimit() { return mFound; } +}; + class LLFetchLandmarksByName : public LLInventoryCollectFunctor { private: @@ -155,6 +189,9 @@ public: mFounded = LLViewerParcelMgr::getInstance()->inAgentParcel(landmark_global_pos); return mFounded; } + + // only care about first found landmark, so stop when found + /*virtual*/ bool exceedsLimit() { return mFounded; } }; static void fetch_landmarks(LLInventoryModel::cat_array_t& cats, @@ -197,23 +234,61 @@ bool LLLandmarkActions::landmarkAlreadyExists() //static bool LLLandmarkActions::hasParcelLandmark() { + static LLUUID sLastItemID; + static S32 sLastFrame = -1; + if (sLastItemID.notNull()) + { + LLInventoryItem* item = gInventory.getItem(sLastItemID); + if (item) + { + LLLandmark* landmark = gLandmarkList.getAsset(item->getAssetUUID()); + if (landmark) + { + LLVector3d landmark_global_pos; + if (landmark->getGlobalPos(landmark_global_pos) + && LLViewerParcelMgr::getInstance()->inAgentParcel(landmark_global_pos)) + { + return true; + } + } + } + // Cached landmark does not match current parcel anymore, + // repeat inventory search to find a replacement landmark + // or to make sure there are none. + sLastItemID.setNull(); + sLastFrame = -1; + } + + if (sLastFrame == LLFrameTimer::getFrameCount()) + { + // Ideally this should also check parcel change and landmark additions, + // not just frame change. + // But should be sufficient to check only frame as this is used + // after inventory and parcel operations. + return false; + } + sLastFrame = LLFrameTimer::getFrameCount(); + LLFirstAgentParcelLandmark get_first_agent_landmark; LLInventoryModel::cat_array_t cats; LLInventoryModel::item_array_t items; fetch_landmarks(cats, items, get_first_agent_landmark); - return !items.empty(); - + if (!items.empty()) + { + sLastItemID = items[0]->getUUID(); + return true; + } + return false; } -// *TODO: This could be made more efficient by only fetching the FIRST -// landmark that meets the criteria LLViewerInventoryItem* LLLandmarkActions::findLandmarkForGlobalPos(const LLVector3d &pos) { // Determine whether there are landmarks pointing to the current parcel. + // Will stop after first found landmark. LLInventoryModel::cat_array_t cats; LLInventoryModel::item_array_t items; - LLFetchlLandmarkByPos is_current_pos_landmark(pos); - fetch_landmarks(cats, items, is_current_pos_landmark); + LLFetchFirstLandmarkByPos get_landmark_from_pos(pos); + fetch_landmarks(cats, items, get_landmark_from_pos); if(items.empty()) { @@ -385,12 +460,24 @@ void LLLandmarkActions::copySLURLtoClipboard(const LLUUID& landmarkInventoryItem { LLVector3d global_pos; landmark->getGlobalPos(global_pos); - LLLandmarkActions::getSLURLfromPosGlobal(global_pos,©_slurl_to_clipboard_callback,true); + if (!global_pos.isExactlyZero()) + { + LLLandmarkActions::getSLURLfromPosGlobal(global_pos, ©_slurl_to_clipboard_callback, true); + } + else + { + LLNotificationsUtil::add("LandmarkLocationUnknown"); + } } } void copy_slurl_to_clipboard_callback(const std::string& slurl) { + if (slurl.empty()) + { + LLNotificationsUtil::add("LandmarkLocationUnknown"); + return; + } gViewerWindow->getWindow()->copyTextToClipboard(utf8str_to_wstring(slurl)); LLSD args; args["SLURL"] = slurl; diff --git a/indra/newview/llmutelist.cpp b/indra/newview/llmutelist.cpp index 9035baafcd..c0a2bb5e51 100644 --- a/indra/newview/llmutelist.cpp +++ b/indra/newview/llmutelist.cpp @@ -805,6 +805,10 @@ void LLMuteList::processMuteListUpdate(LLMessageSystem* msg, void**) std::string unclean_filename; msg->getStringFast(_PREHASH_MuteData, _PREHASH_Filename, unclean_filename); std::string filename = LLDir::getScrubbedFileName(unclean_filename); + if (filename.empty()) + { + LL_WARNS() << "Received empty mute list filename." << LL_ENDL; + } LLMuteList* mute_list = getInstance(); mute_list->mLoadState = ML_REQUESTED; @@ -837,16 +841,16 @@ void LLMuteList::processUseCachedMuteList(LLMessageSystem* msg, void**) void LLMuteList::onFileMuteList(void** user_data, S32 error_code, LLExtStat ext_status) { - LL_INFOS() << "LLMuteList::processMuteListFile()" << LL_ENDL; - std::string* local_filename_and_path = (std::string*)user_data; if(local_filename_and_path && !local_filename_and_path->empty() && (error_code == 0)) { + LL_INFOS() << "Received mute list from server" << LL_ENDL; LLMuteList::getInstance()->loadFromFile(*local_filename_and_path); LLFile::remove(*local_filename_and_path); } else { + LL_INFOS() << "LLMuteList xfer failed with code " << error_code << LL_ENDL; LLMuteList::getInstance()->mLoadState = ML_FAILED; } delete local_filename_and_path; diff --git a/indra/newview/llpanelcontents.cpp b/indra/newview/llpanelcontents.cpp index 7910bcb41d..2e4dc88217 100644 --- a/indra/newview/llpanelcontents.cpp +++ b/indra/newview/llpanelcontents.cpp @@ -60,6 +60,7 @@ #include "llviewerwindow.h" #include "llworld.h" #include "llfloaterperms.h" +#include "llviewerassetupload.h" // // Imported globals @@ -225,7 +226,7 @@ void LLPanelContents::onClickNewScript(void *userdata) { const bool children_ok = true; LLViewerObject* object = LLSelectMgr::getInstance()->getSelection()->getFirstRootObject(children_ok); - if(object) + if (object) { LLPermissions perm; perm.init(gAgent.getID(), gAgent.getID(), LLUUID::null, LLUUID::null); @@ -239,6 +240,23 @@ void LLPanelContents::onClickNewScript(void *userdata) PERM_MOVE | LLFloaterPerms::getNextOwnerPerms("Scripts")); std::string desc; LLViewerAssetType::generateDescriptionFor(LLAssetType::AT_LSL_TEXT, desc); + + U8 script_language = SST_LSL; + LLUUID template_id; + + LLViewerRegion* region = object->getRegion(); + if (region && region->simulatorFeaturesReceived()) + { + LLSD simulatorFeatures; + region->getSimulatorFeatures(simulatorFeatures); + if (simulatorFeatures["LuaScriptsEnabled"].asBoolean()) + { + script_language = SST_LUA; + } + } + // *TODO* Get a template ID and script_language based on user preferences. Template ID is the inventory item UUID of a script + // in the user's inventory that is used as a template for new scripts. + LLPointer<LLViewerInventoryItem> new_item = new LLViewerInventoryItem( LLUUID::null, @@ -250,9 +268,9 @@ void LLPanelContents::onClickNewScript(void *userdata) "New Script", desc, LLSaleInfo::DEFAULT, - LLInventoryItemFlags::II_FLAGS_NONE, + LLInventoryItemFlags::II_FLAGS_SUBTYPE_MASK & script_language, time_corrected()); - object->saveScript(new_item, true, true); + object->saveScript(new_item, true, true, template_id); std::string name = new_item->getName(); diff --git a/indra/newview/llpaneldirbrowser.cpp b/indra/newview/llpaneldirbrowser.cpp index 8c981cad55..69329c4ea4 100644 --- a/indra/newview/llpaneldirbrowser.cpp +++ b/indra/newview/llpaneldirbrowser.cpp @@ -559,9 +559,6 @@ void LLPanelDirBrowser::processDirEventsReply(LLMessageSystem* msg, void**) LLUUID owner_id; std::string name; std::string date; - bool show_pg = gSavedSettings.getBOOL("ShowPGEvents"); - bool show_mature = gSavedSettings.getBOOL("ShowMatureEvents"); - bool show_adult = gSavedSettings.getBOOL("ShowAdultEvents"); msg->getUUID("AgentData", "AgentID", agent_id); msg->getUUID("QueryData", "QueryID", query_id ); @@ -618,27 +615,6 @@ void LLPanelDirBrowser::processDirEventsReply(LLMessageSystem* msg, void**) LL_WARNS() << "skipped event due to owner_id null, event_id " << event_id << LL_ENDL; continue; } - - // skip events that don't match the flags - // there's no PG flag, so we make sure neither adult nor mature is set - if (((event_flags & (EVENT_FLAG_ADULT | EVENT_FLAG_MATURE)) == EVENT_FLAG_NONE) && !show_pg) - { - //llwarns << "Skipped pg event because we're not showing pg, event_id " << event_id << llendl; - continue; - } - - if ((event_flags & EVENT_FLAG_MATURE) && !show_mature) - { - //llwarns << "Skipped mature event because we're not showing mature, event_id " << event_id << llendl; - continue; - } - - if ((event_flags & EVENT_FLAG_ADULT) && !show_adult) - { - //llwarns << "Skipped adult event because we're not showing adult, event_id " << event_id << llendl; - continue; - } - LLSD content; content["type"] = EVENT_CODE; diff --git a/indra/newview/llpaneldirevents.cpp b/indra/newview/llpaneldirevents.cpp index 227ed877cd..7ac1229637 100644 --- a/indra/newview/llpaneldirevents.cpp +++ b/indra/newview/llpaneldirevents.cpp @@ -143,18 +143,17 @@ void LLPanelDirEvents::performQueryOrDelete(U32 event_id) static LLUICachedControl<bool> incpg("ShowPGEvents", true); static LLUICachedControl<bool> incmature("ShowMatureEvents", false); static LLUICachedControl<bool> incadult("ShowAdultEvents", false); + if (!(incpg || incmature || incadult)) + { + LLNotificationsUtil::add("NoContentToSearch"); + return; + } U32 scope = DFQ_DATE_EVENTS; if (incpg) scope |= DFQ_INC_PG; if (incmature && gAgent.canAccessMature()) scope |= DFQ_INC_MATURE; if (incadult && gAgent.canAccessAdult()) scope |= DFQ_INC_ADULT; - if ( !( scope & (DFQ_INC_PG | DFQ_INC_MATURE | DFQ_INC_ADULT ))) - { - LLNotificationsUtil::add("NoContentToSearch"); - return; - } - setupNewSearch(); std::ostringstream params; diff --git a/indra/newview/llpaneldirland.cpp b/indra/newview/llpaneldirland.cpp index e2ef44a604..11ca7a0af0 100644 --- a/indra/newview/llpaneldirland.cpp +++ b/indra/newview/llpaneldirland.cpp @@ -62,20 +62,6 @@ bool LLPanelDirLand::postBuild() childSetValue("type", gSavedSettings.getString("FindLandType")); - bool adult_enabled = gAgent.canAccessAdult(); - bool mature_enabled = gAgent.canAccessMature(); - childSetVisible("incpg", true); - if (!mature_enabled) - { - childSetValue("incmature", false); - childDisable("incmature"); - } - if (!adult_enabled) - { - childSetValue("incadult", false); - childDisable("incadult"); - } - childSetCommitCallback("pricecheck", onCommitPrice, this); childSetCommitCallback("areacheck", onCommitArea, this); diff --git a/indra/newview/llpaneldirplaces.cpp b/indra/newview/llpaneldirplaces.cpp index 2d54566038..3501baf697 100644 --- a/indra/newview/llpaneldirplaces.cpp +++ b/indra/newview/llpaneldirplaces.cpp @@ -121,6 +121,11 @@ void LLPanelDirPlaces::performQuery() static LLUICachedControl<bool> inc_pg("ShowPGSims", true); static LLUICachedControl<bool> inc_mature("ShowMatureSims", false); static LLUICachedControl<bool> inc_adult("ShowAdultSims", false); + if (!(inc_pg || inc_mature || inc_adult)) + { + LLNotificationsUtil::add("NoContentToSearch"); + return; + } if (inc_pg) { @@ -137,12 +142,6 @@ void LLPanelDirPlaces::performQuery() flags |= DFQ_INC_ADULT; } - if (0x0 == flags) - { - LLNotificationsUtil::add("NoContentToSearch"); - return; - } - queryCore(query_string, category, flags); } diff --git a/indra/newview/llpanellogin.cpp b/indra/newview/llpanellogin.cpp index 868e02f28b..ae010b2259 100644 --- a/indra/newview/llpanellogin.cpp +++ b/indra/newview/llpanellogin.cpp @@ -189,7 +189,8 @@ LLPanelLogin::LLPanelLogin(const LLRect &rect, mPasswordLength(0), mLocationLength(0), mShowFavorites(false), - mAlertNotif(false) + mAlertNotif(false), + mLoginBtn(nullptr) { setBackgroundVisible(false); setBackgroundOpaque(true); @@ -1196,6 +1197,10 @@ void LLPanelLogin::updateServer() void LLPanelLogin::updateLoginButtons() { + if (!mLoginBtn) + { + return; + } mLoginBtn->setEnabled(mUsernameLength != 0 && mPasswordLength != 0 && !mAlertNotif); if (!mFirstLoginThisInstall) diff --git a/indra/newview/llpreviewnotecard.cpp b/indra/newview/llpreviewnotecard.cpp index cecda23e7b..526fb6c8aa 100644 --- a/indra/newview/llpreviewnotecard.cpp +++ b/indra/newview/llpreviewnotecard.cpp @@ -70,10 +70,16 @@ LLPreviewNotecard::LLPreviewNotecard(const LLSD& key) //const LLUUID& item_id, : LLPreview( key ) { const LLInventoryItem *item = getItem(); + std::string note_name = "New Note"; if (item) { mAssetID = item->getAssetUUID(); + if (!item->getName().empty()) + { + note_name = item->getName(); + } } + mNoteName = note_name; } LLPreviewNotecard::~LLPreviewNotecard() @@ -101,15 +107,21 @@ bool LLPreviewNotecard::postBuild() mEditBtn->setCommitCallback(boost::bind(&LLPreviewNotecard::openInExternalEditor, this)); const LLInventoryItem* item = getItem(); + std::string note_name = mNoteName; mDescEditor = getChild<LLLineEditor>("desc"); mDescEditor->setCommitCallback(boost::bind(&LLPreview::onText, mDescEditor, this)); if (item) { + if (!item->getName().empty()) + { + note_name = item->getName(); + } mDescEditor->setValue(item->getDescription()); bool source_library = mObjectUUID.isNull() && gInventory.isObjectDescendentOf(item->getUUID(), gInventory.getLibraryRootFolderID()); mDeleteBtn->setEnabled(!source_library); } + mNoteName = note_name; mDescEditor->setPrevalidate(&LLTextValidate::validateASCIIPrintableNoPipe); return LLPreview::postBuild(); @@ -230,6 +242,7 @@ void LLPreviewNotecard::loadAsset() // request the asset. const LLInventoryItem* item = getItem(); bool fail = false; + std::string note_name = mNoteName; if(item) { @@ -238,6 +251,10 @@ void LLPreviewNotecard::loadAsset() bool allow_copy = gAgent.allowOperation(PERM_COPY, perm, GP_OBJECT_MANIPULATE); bool allow_modify = canModify(mObjectUUID, item); bool source_library = mObjectUUID.isNull() && gInventory.isObjectDescendentOf(mItemUUID, gInventory.getLibraryRootFolderID()); + if(!item->getName().empty()) + { + note_name = item->getName(); + } if (allow_copy || gAgent.isGodlike()) { @@ -338,6 +355,8 @@ void LLPreviewNotecard::loadAsset() fail = true; } + mNoteName = note_name; + if (fail) { mEditor->setText(LLStringUtil::null); @@ -574,12 +593,23 @@ bool LLPreviewNotecard::saveIfNeeded(LLInventoryItem* copyitem, bool sync) void LLPreviewNotecard::syncExternal() { // Sync with external editor. - std::string tmp_file = getTmpFileName(); - if (LLFile::isfile(tmp_file)) // file exists + std::string note_name = getCleanNameForTmpFile(); + std::string tmp_file = getTmpFileName(note_name); + llstat s; + if (LLFile::stat(tmp_file, &s) != 0) { - if (mLiveFile) mLiveFile->ignoreNextUpdate(); - writeToFile(tmp_file); + // file doesn't exist, try with empty name + note_name.clear(); + tmp_file = getTmpFileName(note_name); + if (LLFile::stat(tmp_file, &s) != 0) + { + // file doesn't exist, with either name, give up + return; + } } + + if (mLiveFile) mLiveFile->ignoreNextUpdate(); + writeToFile(tmp_file); } /*virtual*/ @@ -742,8 +772,16 @@ void LLPreviewNotecard::openInExternalEditor() delete mLiveFile; // deletes file // Save the notecard to a temporary file. - std::string filename = getTmpFileName(); - writeToFile(filename); + std::string note_name = getCleanNameForTmpFile(); + std::string filename = getTmpFileName(note_name); + if(!writeToFile(filename)) { + // In case some characters from notecard name are forbidden + // and not accounted for, name is too long or some other issue, + // try file that doesn't include notecard name + note_name.clear(); + filename = getTmpFileName(note_name); + writeToFile(filename); + } // Start watching file changes. mLiveFile = new LLLiveLSLFile(filename, boost::bind(&LLPreviewNotecard::onExternalChange, this, _1)); @@ -851,8 +889,21 @@ bool LLPreviewNotecard::writeToFile(const std::string& filename) return true; } +std::string LLPreviewNotecard::getCleanNameForTmpFile() const +{ + std::string note_name = mNoteName; + if(note_name.empty()) { + note_name = "New note"; + } + static const std::set<char> forbidden_chars{ '<', '>', ':', '"', '\\', '/', '|', '?', '*' }; + note_name.erase( + std::remove_if(note_name.begin(), note_name.end(), [](char c) { + return forbidden_chars.contains(c); + }), note_name.end()); + return note_name; +} -std::string LLPreviewNotecard::getTmpFileName() +std::string LLPreviewNotecard::getTmpFileName(const std::string& note_name) const { std::string notecard_id = mObjectID.asString() + "_" + mItemUUID.asString(); @@ -861,7 +912,11 @@ std::string LLPreviewNotecard::getTmpFileName() LLMD5 notecard_id_hash((const U8 *)notecard_id.c_str()); notecard_id_hash.hex_digest(notecard_id_hash_str); - return std::string(LLFile::tmpdir()) + "sl_notecard_" + notecard_id_hash_str + ".txt"; + if(note_name.empty()) { + return std::string(LLFile::tmpdir()) + "sl_notecard_" + notecard_id_hash_str + ".txt"; + } else { + return std::string(LLFile::tmpdir()) + "sl_notecard_" + note_name + "_" + notecard_id_hash_str + ".txt"; + } } diff --git a/indra/newview/llpreviewnotecard.h b/indra/newview/llpreviewnotecard.h index be3c804f9b..a7289ebc9a 100644 --- a/indra/newview/llpreviewnotecard.h +++ b/indra/newview/llpreviewnotecard.h @@ -108,7 +108,8 @@ protected: bool onExternalChange(const std::string& filename); bool loadNotecardText(const std::string& filename); bool writeToFile(const std::string& filename); - std::string getTmpFileName(); + std::string getCleanNameForTmpFile() const; + std::string getTmpFileName(const std::string& note_name) const; protected: LLViewerTextEditor* mEditor = nullptr; @@ -118,6 +119,8 @@ protected: LLButton* mDeleteBtn = nullptr; LLUICtrl* mLockBtn = nullptr; + std::string mNoteName; + LLUUID mAssetID; LLUUID mObjectID; diff --git a/indra/newview/llpreviewscript.cpp b/indra/newview/llpreviewscript.cpp index 53d0a712a8..31909116c7 100644 --- a/indra/newview/llpreviewscript.cpp +++ b/indra/newview/llpreviewscript.cpp @@ -53,6 +53,7 @@ #include "llslider.h" #include "lltooldraganddrop.h" #include "llfilesystem.h" +#include "lllogchat.h" #include "llagent.h" #include "llmenugl.h" @@ -64,22 +65,12 @@ #include "llviewerobject.h" #include "llviewerobjectlist.h" #include "llviewerregion.h" -#include "llkeyboard.h" -#include "llscrollcontainer.h" -#include "llcheckboxctrl.h" #include "llscripteditor.h" -#include "llselectmgr.h" -#include "lltooldraganddrop.h" -#include "llscrolllistctrl.h" #include "lltextbox.h" -#include "llslider.h" -#include "lldir.h" -#include "llcombobox.h" #include "llviewerstats.h" #include "llviewerwindow.h" #include "lluictrlfactory.h" #include "llmediactrl.h" -#include "lluictrlfactory.h" #include "lltrans.h" #include "llviewercontrol.h" #include "llappviewer.h" @@ -90,20 +81,10 @@ #include "lltoggleablemenu.h" #include "llmenubutton.h" #include "llinventoryfunctions.h" +#include "llwebsocketmgr.h" +#include "llscripteditorws.h" +#include <regex> -const std::string HELLO_LSL = - "default\n" - "{\n" - " state_entry()\n" - " {\n" - " llSay(0, \"Hello, Avatar!\");\n" - " }\n" - "\n" - " touch_start(integer total_number)\n" - " {\n" - " llSay(0, \"Touched.\");\n" - " }\n" - "}\n"; const std::string HELP_LSL_PORTAL_TOPIC = "LSL_Portal"; const std::string DEFAULT_SCRIPT_NAME = "New Script"; // *TODO:Translate? @@ -119,6 +100,42 @@ static bool have_script_upload_cap(LLUUID& object_id) return object && (! object->getRegion()->getCapability("UpdateScriptTask").empty()); } +static bool have_lua_enabled(const LLUUID& object_id) +{ + LLViewerRegion* region = nullptr; + LLViewerObject* object = gObjectList.findObject(object_id); + if (object) + { + region = object->getRegion(); + } + else + { + region = gAgent.getRegion(); + } + + if (region && region->simulatorFeaturesReceived()) + { + LLSD simulatorFeatures; + region->getSimulatorFeatures(simulatorFeatures); + return simulatorFeatures["LuaScriptsEnabled"].asBoolean(); + } + + return false; +} + +// TEMPORARY: Quick check to see if the code is Lua +// since we don't have another way to determine the language yet +bool is_lua_script(const std::string& code) +{ + // Check for LSL's signature "default" state pattern + std::regex lsl_pattern("\\s*default\\s*\\{"); + if (std::regex_search(code, lsl_pattern)) + return false; + + // "default" state not found, assuming it's Lua + return true; +} + /// --------------------------------------------------------------------------- /// LLLiveLSLFile /// --------------------------------------------------------------------------- @@ -373,9 +390,9 @@ LLScriptEdCore::LLScriptEdCore( LLScriptEdContainer* container, const std::string& sample, const LLHandle<LLFloater>& floater_handle, - void (*load_callback)(void*), - void (*save_callback)(void*, bool), - void (*search_replace_callback) (void* userdata), + script_ed_callback_t load_callback, + save_callback_t save_callback, + script_ed_callback_t search_replace_callback, void* userdata, bool live, S32 bottom_pad) @@ -391,7 +408,6 @@ LLScriptEdCore::LLScriptEdCore( mLastHelpToken(NULL), mLiveHelpHistorySize(0), mEnableSave(false), - mLiveFile(NULL), mLive(live), mContainer(container), mHasScriptData(false), @@ -423,7 +439,6 @@ LLScriptEdCore::~LLScriptEdCore() } } - delete mLiveFile; if (mSyntaxIDConnection.connected()) { mSyntaxIDConnection.disconnect(); @@ -441,42 +456,37 @@ void LLLiveLSLEditor::experienceChanged() } } -void LLLiveLSLEditor::onViewProfile( LLUICtrl *ui, void* userdata ) +void LLLiveLSLEditor::onViewProfile() { - LLLiveLSLEditor* self = (LLLiveLSLEditor*)userdata; - - LLUUID id; - if(self->mExperienceEnabled->get()) + if (mExperienceEnabled->get()) { - id=self->mScriptEd->getAssociatedExperience(); - if(id.notNull()) + LLUUID id = mScriptEd->getAssociatedExperience(); + if (id.notNull()) { LLFloaterReg::showInstance("experience_profile", id, true); } } - } -void LLLiveLSLEditor::onToggleExperience( LLUICtrl *ui, void* userdata ) +void LLLiveLSLEditor::onToggleExperience() { - LLLiveLSLEditor* self = (LLLiveLSLEditor*)userdata; - LLUUID id; - if(self->mExperienceEnabled->get()) + if (mExperienceEnabled->get()) { - if(self->mScriptEd->getAssociatedExperience().isNull()) + if (mScriptEd->getAssociatedExperience().isNull()) { - id=self->mExperienceIds.beginArray()->asUUID(); + id = mExperienceIds.beginArray()->asUUID(); } } - if(id != self->mScriptEd->getAssociatedExperience()) + if (id != mScriptEd->getAssociatedExperience()) { - self->mScriptEd->enableSave(self->getIsModifiable()); + mScriptEd->enableSave(getIsModifiable()); } - self->mScriptEd->setAssociatedExperience(id); - self->updateExperiencePanel(); + mScriptEd->setAssociatedExperience(id); + + updateExperiencePanel(); } bool LLScriptEdCore::postBuild() @@ -501,6 +511,7 @@ bool LLScriptEdCore::postBuild() // Intialise keyword highlighting for the current simulator's version of LSL LLSyntaxIdLSL::getInstance()->initialize(); + LLSyntaxLua::getInstance()->initialize(); processKeywords(); mCommitCallbackRegistrar.add("FontSize.Set", boost::bind(&LLScriptEdCore::onChangeFontSize, this, _2)); @@ -510,14 +521,30 @@ bool LLScriptEdCore::postBuild() "menu_lsl_font_size.xml", gMenuHolder, LLViewerMenuHolderGL::child_registry_t::instance()); getChild<LLMenuButton>("font_btn")->setMenu(context_menu, LLMenuButton::MP_BOTTOM_LEFT, true); + bool lua_scripts_enabled = have_lua_enabled(LLUUID::null); + mCompileTarget = getChild<LLComboBox>("compile_target"); + if (LLScrollListItem* luau_item = mCompileTarget->findItemByValue("luau")) + { + luau_item->setEnabled(lua_scripts_enabled); + } + if (LLScrollListItem* lsl_luau_item = mCompileTarget->findItemByValue("lsl-luau")) + { + lsl_luau_item->setEnabled(lua_scripts_enabled); + } + return true; } void LLScriptEdCore::processKeywords() { + processKeywords(mEditor->getIsLuauLanguage()); +} + +void LLScriptEdCore::processKeywords(bool luau_language) +{ LL_DEBUGS("SyntaxLSL") << "Processing keywords" << LL_ENDL; mEditor->clearSegments(); - mEditor->initKeywords(); + mEditor->initKeywords(luau_language); mEditor->loadKeywords(); string_vec_t primary_keywords; @@ -536,6 +563,8 @@ void LLScriptEdCore::processKeywords() secondary_keywords.push_back( wstring_to_utf8str(token->getToken()) ); } } + + mFunctions->removeall(); for (string_vec_t::const_iterator iter = primary_keywords.begin(); iter!= primary_keywords.end(); ++iter) { @@ -691,12 +720,13 @@ bool LLScriptEdCore::writeToFile(const std::string& filename) void LLScriptEdCore::sync() { // Sync with external editor. - if (mLiveFile) + if (mContainer->mLiveFile) { - std::string tmp_file = mLiveFile->filename(); - if (LLFile::isfile(tmp_file)) // file exists + std::string tmp_file = mContainer->mLiveFile->filename(); + llstat s; + if (LLFile::stat(tmp_file, &s) == 0) // file exists { - mLiveFile->ignoreNextUpdate(); + mContainer->mLiveFile->ignoreNextUpdate(); writeToFile(tmp_file); } } @@ -720,6 +750,8 @@ void LLScriptEdCore::draw() S32 line = 0; S32 column = 0; mEditor->getCurrentLineAndColumn( &line, &column, false ); // don't include wordwrap + line = mEditor->getIsLuauLanguage() ? (line + 1) : line; + column = mEditor->getIsLuauLanguage() ? (column + 1) : column; LLStringUtil::format_map_t args; std::string cursor_pos; args["[LINE]"] = llformat ("%d", line); @@ -1082,15 +1114,21 @@ void LLScriptEdCore::doSave( bool close_after_save ) void LLScriptEdCore::openInExternalEditor() { - delete mLiveFile; // deletes file + //if (mContainer->mLiveFile) + //{ + // // If already open in an external editor, just return + // return; + //} // Generate a suitable filename std::string script_name = mScriptName; - std::string forbidden_chars = "<>:\"\\/|?*"; - for (std::string::iterator c = forbidden_chars.begin(); c != forbidden_chars.end(); c++) - { - script_name.erase(std::remove(script_name.begin(), script_name.end(), *c), script_name.end()); - } + + static const std::set<char> forbidden_chars{ '<', '>', ':', '"', '\\', '/', '|', '?', '*' }; + script_name.erase( + std::remove_if(script_name.begin(), script_name.end(), [](char c) { + return forbidden_chars.contains(c); + }), script_name.end()); + std::string filename = mContainer->getTmpFileName(script_name); // Save the script to a temporary file. @@ -1104,9 +1142,18 @@ void LLScriptEdCore::openInExternalEditor() writeToFile(filename); } + if (mContainer->mLiveFile && mContainer->mLiveFile->filename() != filename) + { // The name may have changed if we changed the type of scipt being edited. + delete mContainer->mLiveFile; + mContainer->mLiveFile = NULL; + } // Start watching file changes. - mLiveFile = new LLLiveLSLFile(filename, boost::bind(&LLScriptEdContainer::onExternalChange, mContainer, _1)); - mLiveFile->addToEventTimer(); + if (!mContainer->mLiveFile) + { + mContainer->mLiveFile = new LLLiveLSLFile(filename, boost::bind(&LLScriptEdContainer::onExternalChange, mContainer, _1)); + mContainer->mLiveFile->addToEventTimer(); + } + mContainer->startWebsocketServer(); // Open it in external editor. { @@ -1165,6 +1212,7 @@ void LLScriptEdCore::onErrorList(LLUICtrl*, void* user_data) sscanf(line.c_str(), "%d %d", &row, &column); //LL_INFOS() << "LLScriptEdCore::onErrorList() - " << row << ", " //<< column << LL_ENDL; + row = (self->mEditor->getIsLuauLanguage() ? row - 1 : row); self->mEditor->setCursor(row, column); self->mEditor->setFocus(true); } @@ -1375,15 +1423,15 @@ void LLLiveLSLEditor::updateExperiencePanel() mExperienceEnabled->setEnabled(false); mExperienceEnabled->setToolTip(getString("no_experiences")); } - getChild<LLButton>("view_profile")->setVisible(false); + mViewProfileButton->setVisible(false); } else { mExperienceEnabled->setToolTip(getString("experience_enabled")); mExperienceEnabled->setEnabled(getIsModifiable()); - mExperiences->setVisible(true); mExperienceEnabled->set(true); - getChild<LLButton>("view_profile")->setToolTip(getString("show_experience_profile")); + mExperiences->setVisible(true); + mViewProfileButton->setToolTip(getString("show_experience_profile")); buildExperienceList(); } } @@ -1452,7 +1500,7 @@ void LLLiveLSLEditor::buildExperienceList() mExperiences->setEnabled(true); mExperiences->sortByName(true); mExperiences->setCurrentByIndex(mExperiences->getCurrentIndex()); - getChild<LLButton>("view_profile")->setVisible(true); + mViewProfileButton->setVisible(true); } } @@ -1462,8 +1510,6 @@ void LLScriptEdCore::setAssociatedExperience( const LLUUID& experience_id ) mAssociatedExperience = experience_id; } - - void LLLiveLSLEditor::requestExperiences() { if (!getIsModifiable()) @@ -1502,11 +1548,42 @@ void LLLiveLSLEditor::receiveExperienceIds(LLSD result, LLHandle<LLLiveLSLEditor LLScriptEdContainer::LLScriptEdContainer(const LLSD& key) : LLPreview(key) -, mScriptEd(NULL) +, mScriptEd(nullptr) +, mLiveFile(nullptr) +, mLiveLogFile(nullptr) +{ +} + +LLScriptEdContainer::~LLScriptEdContainer() { + delete mLiveFile; + mLiveFile = nullptr; + + delete mLiveLogFile; + mLiveLogFile = nullptr; + + if (!mWebSocketServer.expired()) + { + unsubscribeScript(); + } +} + +std::string LLScriptEdContainer::getTmpFileName(const std::string& script_name) const +{ + std::string script_id_hash_str(getUniqueHash()); + std::string script_extension = mScriptEd->mEditor->getIsLuauLanguage() ? ".luau" : ".lsl"; + + if (script_name.empty()) + { + return std::string(LLFile::tmpdir()) + "sl_script_" + script_id_hash_str + script_extension; + } + else + { + return std::string(LLFile::tmpdir()) + "sl_script_" + script_name + "_" + script_id_hash_str + script_extension; + } } -std::string LLScriptEdContainer::getTmpFileName(const std::string& script_name) +std::string LLScriptEdContainer::getUniqueHash() const { // Take script inventory item id (within the object inventory) // to consideration so that it's possible to edit multiple scripts @@ -1514,18 +1591,65 @@ std::string LLScriptEdContainer::getTmpFileName(const std::string& script_name) std::string script_id = mObjectUUID.asString() + "_" + mItemUUID.asString(); // Use MD5 sum to make the file name shorter and not exceed maximum path length. - char script_id_hash_str[33]; /* Flawfinder: ignore */ - LLMD5 script_id_hash((const U8 *)script_id.c_str()); + char script_id_hash_str[33]; /* Flawfinder: ignore */ + LLMD5 script_id_hash((const U8*)script_id.c_str()); script_id_hash.hex_digest(script_id_hash_str); - if (script_name.empty()) + return std::string(script_id_hash_str); +} + +std::string LLScriptEdContainer::getErrorLogFileName(const std::string& script_path) +{ + if (script_path.empty()) { - return std::string(LLFile::tmpdir()) + "sl_script_" + script_id_hash_str + ".lsl"; + return std::string(); } - else + + return script_path + ".log"; +} + +bool LLScriptEdContainer::logErrorsToFile(const LLSD& compile_errors) +{ + if (!isOpenInExternalEditor()) + { + return false; + } + + std::string script_path = getTmpFileName(mScriptEd->mScriptName); + std::string log_path = getErrorLogFileName(script_path); + + llofstream file(log_path.c_str()); + if (!file.is_open()) + { + LL_WARNS() << "Unable to open error log file: " << log_path << LL_ENDL; + return false; + } + + // Write timestamp + std::string timestamp = LLLogChat::timestamp2LogString(0, true); + file << "// " << timestamp << "\n\n"; + + // Write errors + for (LLSD::array_const_iterator line = compile_errors.beginArray(); + line < compile_errors.endArray(); + line++) + { + std::string error_message = line->asString(); + LLStringUtil::stripNonprintable(error_message); + file << error_message << "\n"; + } + + file.close(); + + // Create a log file handler if we don't already have one, + // this is needed to delete the temporary log file properly + if (!mLiveLogFile && !log_path.empty()) { - return std::string(LLFile::tmpdir()) + "sl_script_" + script_name + "_" + script_id_hash_str + ".lsl"; + // Empty callback since we don't need to react to file changes + mLiveLogFile = new LLLiveLSLFile(log_path, [](const std::string& filename) { return true; }); } + + return true; } bool LLScriptEdContainer::onExternalChange(const std::string& filename) @@ -1555,6 +1679,63 @@ bool LLScriptEdContainer::handleKeyHere(KEY key, MASK mask) return true; } +void LLScriptEdContainer::startWebsocketServer() +{ + if (gSavedSettings.getBOOL("ExternalWebsocketSyncEnable")) + { + // Attempt to find an existing server + LLWebsocketMgr& wsmgr = LLWebsocketMgr::instance(); + LLScriptEditorWSServer::ptr_t server = + std::static_pointer_cast<LLScriptEditorWSServer>( + wsmgr.findServerByName(LLScriptEditorWSServer::DEFAULT_SERVER_NAME)); + + if (!server) + { // We couldn't find one, so create it + U16 server_port = static_cast<U16>(gSavedSettings.getS32("ExternalWebsocketSyncPort")); + bool server_localhost = gSavedSettings.getBOOL("ExternalWebsocketSyncLocal"); + server = std::make_shared<LLScriptEditorWSServer>(LLScriptEditorWSServer::DEFAULT_SERVER_NAME, server_port, server_localhost); + wsmgr.addServer(server); + } + + bool is_running = server->isRunning(); + if (!is_running) + { // Server isn't running, so start it + is_running = wsmgr.startServer(LLScriptEditorWSServer::DEFAULT_SERVER_NAME); + } + + if (!is_running && !server->isRunning()) + { // Failed to start the server + LL_WARNS() << "Failed to start script editor websocket server" << LL_ENDL; + return; + } + + std::string script_id_hash_str(getUniqueHash()); + server->subscribeScriptEditor(mObjectUUID, mItemUUID, mScriptEd->mScriptName, getHandle(), script_id_hash_str); + mWebSocketServer = server; + } +} + +void LLScriptEdContainer::unsubscribeScript() +{ + auto server = mWebSocketServer.lock(); + if (server) + { + std::string script_id_hash_str(getUniqueHash()); + server->sendUnsubscribeScriptEditor(script_id_hash_str); + server->unsubscribeEditor(script_id_hash_str); + } +} + +void LLScriptEdContainer::sendCompileResults(LLSD& params) +{ + auto server = mWebSocketServer.lock(); + if (server) + { + std::string script_id_hash_str(getUniqueHash()); + server->sendCompileResults(script_id_hash_str, params); + } +} + /// --------------------------------------------------------------------------- /// LLPreviewLSL /// --------------------------------------------------------------------------- @@ -1579,7 +1760,7 @@ void* LLPreviewLSL::createScriptEdPanel(void* userdata) self->mScriptEd = new LLScriptEdCore( self, - HELLO_LSL, + std::string(), self->getHandle(), LLPreviewLSL::onLoad, LLPreviewLSL::onSave, @@ -1623,6 +1804,9 @@ bool LLPreviewLSL::postBuild() childSetCommitCallback("desc", LLPreview::onText, this); getChild<LLLineEditor>("desc")->setPrevalidate(&LLTextValidate::validateASCIIPrintableNoPipe); + mScriptEd->mCompileTarget = getChild<LLComboBox>("compile_target"); + mScriptEd->mCompileTarget->setCommitCallback([&](LLUICtrl*, const LLSD&) { onCompileTargetChanged(); }); + return LLPreview::postBuild(); } @@ -1648,6 +1832,15 @@ void LLPreviewLSL::callbackLSLCompileSucceeded() LL_INFOS() << "LSL Bytecode saved" << LL_ENDL; mScriptEd->mErrorList->setCommentText(LLTrans::getString("CompileSuccessful")); mScriptEd->mErrorList->setCommentText(LLTrans::getString("SaveComplete")); + + if (isOpenInExternalEditor()) + { + LLSD success_msg; + success_msg.append(LLTrans::getString("CompileSuccessful")); + success_msg.append(LLTrans::getString("SaveComplete")); + logErrorsToFile(success_msg); + } + closeIfNeeded(); } @@ -1667,6 +1860,12 @@ void LLPreviewLSL::callbackLSLCompileFailed(const LLSD& compile_errors) row["columns"][0]["font"] = "OCRA"; mScriptEd->mErrorList->addElement(row); } + + if (isOpenInExternalEditor()) + { + logErrorsToFile(compile_errors); + } + mScriptEd->selectFirstError(); closeIfNeeded(); } @@ -1717,12 +1916,6 @@ void LLPreviewLSL::loadAsset() getChildView("lock")->setVisible( !is_modifiable); mScriptEd->getChildView("Insert...")->setEnabled(is_modifiable); } - else - { - mScriptEd->setScriptText(std::string(HELLO_LSL), true); - mScriptEd->setEnableEditing(true); - mAssetStatus = PREVIEW_ASSET_LOADED; - } } @@ -1780,6 +1973,7 @@ void LLPreviewLSL::finishedLSLUpload(LLUUID itemId, LLSD response) { preview->callbackLSLCompileFailed(response["errors"]); } + preview->sendCompileResults(response); } } @@ -1803,6 +1997,12 @@ bool LLPreviewLSL::failedLSLUpload(LLUUID itemId, LLUUID taskId, LLSD response, LLSD errors; errors.append(LLTrans::getString("UploadFailed") + reason); preview->callbackLSLCompileFailed(errors); + + LLSD message; + message["compiled"] = false; + message["errors"] = errors; + preview->sendCompileResults(message); + return true; } @@ -1838,11 +2038,12 @@ void LLPreviewLSL::saveIfNeeded(bool sync /*= true*/) mPendingUploads++; if (!url.empty()) { + std::string compile_target(mScriptEd->mCompileTarget->getValue()); std::string buffer(mScriptEd->mEditor->getText()); LLUUID old_asset_id = inv_item->getAssetUUID().isNull() ? mScriptEd->getAssetID() : inv_item->getAssetUUID(); - LLResourceUploadInfo::ptr_t uploadInfo(std::make_shared<LLScriptAssetUpload>(mItemUUID, buffer, + LLResourceUploadInfo::ptr_t uploadInfo(std::make_shared<LLScriptAssetUpload>(mItemUUID, compile_target, buffer, [old_asset_id](LLUUID itemId, LLUUID, LLUUID, LLSD response) { LLFileSystem::removeFile(old_asset_id, LLAssetType::AT_LSL_TEXT); LLPreviewLSL::finishedLSLUpload(itemId, response); @@ -1854,6 +2055,13 @@ void LLPreviewLSL::saveIfNeeded(bool sync /*= true*/) } } +void LLPreviewLSL::onCompileTargetChanged() +{ + bool is_lua = (mScriptEd->mCompileTarget->getValue().asString() == "luau"); + mScriptEd->mEditor->setLuauLanguage(is_lua); + mScriptEd->processKeywords(is_lua); +} + // static void LLPreviewLSL::onLoadComplete(const LLUUID& asset_uuid, LLAssetType::EType type, void* user_data, S32 status, LLExtStat ext_status) @@ -1880,6 +2088,8 @@ void LLPreviewLSL::onLoadComplete(const LLUUID& asset_uuid, LLAssetType::EType t std::string script_name = DEFAULT_SCRIPT_NAME; LLInventoryItem* item = gInventory.getItem(*item_uuid); bool is_modifiable = false; + std::string compile_target; + bool is_lua = false; if (item) { if (!item->getName().empty()) @@ -1890,11 +2100,39 @@ void LLPreviewLSL::onLoadComplete(const LLUUID& asset_uuid, LLAssetType::EType t { is_modifiable = true; } + + // subtype is the language that the script is written in, + // runtime is the VM that the script is running on. + // LSL scripts have 3 possible runtimes: "lsl2", "mono", and "luau". + // Lua scripts have 1 runtime: "luau". + U8 subtype = item->getInventorySubType(); + std::string runtime = item->getRuntime(); + + is_lua = (subtype == SST_LUA); + if (!is_lua && (runtime == "luau")) + { // an lsl script executing on the luau runtime + compile_target = "lsl-luau"; + } + else + { // otherwise, use the runtime as the compile target + // (this may be blank if the script has never been compiled) + compile_target = runtime; + } + } + + if (compile_target.empty()) + { + compile_target = is_lua ? "luau" : "mono"; } + preview->mScriptEd->setScriptName(script_name); preview->mScriptEd->setEnableEditing(is_modifiable); preview->mScriptEd->setAssetID(asset_uuid); preview->mAssetStatus = PREVIEW_ASSET_LOADED; + + preview->mScriptEd->mCompileTarget->setValue(compile_target); + preview->mScriptEd->mEditor->setLuauLanguage(is_lua); + preview->mScriptEd->processKeywords(is_lua); } else { @@ -1932,7 +2170,7 @@ void* LLLiveLSLEditor::createScriptEdPanel(void* userdata) self->mScriptEd = new LLScriptEdCore( self, - HELLO_LSL, + std::string(), self->getHandle(), &LLLiveLSLEditor::onLoad, &LLLiveLSLEditor::onSave, @@ -1960,28 +2198,26 @@ LLLiveLSLEditor::LLLiveLSLEditor(const LLSD& key) : bool LLLiveLSLEditor::postBuild() { - childSetCommitCallback("running", LLLiveLSLEditor::onRunningCheckboxClicked, this); - getChildView("running")->setEnabled(false); - - childSetAction("Reset",&LLLiveLSLEditor::onReset,this); - getChildView("Reset")->setEnabled(true); - - mMonoCheckbox = getChild<LLCheckBoxCtrl>("mono"); - childSetCommitCallback("mono", &LLLiveLSLEditor::onMonoCheckboxClicked, this); - getChildView("mono")->setEnabled(true); - - mScriptEd->mEditor->makePristine(); - mScriptEd->mEditor->setFocus(true); + mResetButton = getChild<LLButton>("Reset"); + mResetButton->setClickedCallback([&](LLUICtrl*, const LLSD&) { onReset(); }); + mRunningCheckbox = getChild<LLCheckBoxCtrl>("running"); + mRunningCheckbox->setCommitCallback([&](LLUICtrl*, const LLSD&) { onRunningCheckboxClicked(); }); mExperiences = getChild<LLComboBox>("Experiences..."); - mExperiences->setCommitCallback(boost::bind(&LLLiveLSLEditor::experienceChanged, this)); + mExperiences->setCommitCallback([&](LLUICtrl*, const LLSD&) { experienceChanged(); }); mExperienceEnabled = getChild<LLCheckBoxCtrl>("enable_xp"); + mExperienceEnabled->setCommitCallback([&](LLUICtrl*, const LLSD&) { onToggleExperience(); }); - childSetCommitCallback("enable_xp", onToggleExperience, this); - childSetCommitCallback("view_profile", onViewProfile, this); + mViewProfileButton = getChild<LLButton>("view_profile"); + mViewProfileButton->setClickedCallback([&](LLUICtrl*, const LLSD&) { onViewProfile(); }); + mScriptEd->mEditor->makePristine(); + mScriptEd->mEditor->setFocus(true); + + mScriptEd->mCompileTarget = getChild<LLComboBox>("compile_target"); + mScriptEd->mCompileTarget->setCommitCallback([&](LLUICtrl*, const LLSD&) { onCompileTargetChanged(); }); return LLPreview::postBuild(); } @@ -1994,7 +2230,16 @@ void LLLiveLSLEditor::callbackLSLCompileSucceeded(const LLUUID& task_id, LL_DEBUGS() << "LSL Bytecode saved" << LL_ENDL; mScriptEd->mErrorList->setCommentText(LLTrans::getString("CompileSuccessful")); mScriptEd->mErrorList->setCommentText(LLTrans::getString("SaveComplete")); - getChild<LLCheckBoxCtrl>("running")->set(is_script_running); + + if (isOpenInExternalEditor()) + { + LLSD success_msg; + success_msg.append(LLTrans::getString("CompileSuccessful")); + success_msg.append(LLTrans::getString("SaveComplete")); + logErrorsToFile(success_msg); + } + + mRunningCheckbox->set(is_script_running); mIsSaving = false; closeIfNeeded(); } @@ -2003,6 +2248,7 @@ void LLLiveLSLEditor::callbackLSLCompileSucceeded(const LLUUID& task_id, void LLLiveLSLEditor::callbackLSLCompileFailed(const LLSD& compile_errors) { LL_DEBUGS() << "Compile failed!" << LL_ENDL; + for(LLSD::array_const_iterator line = compile_errors.beginArray(); line < compile_errors.endArray(); line++) @@ -2015,6 +2261,12 @@ void LLLiveLSLEditor::callbackLSLCompileFailed(const LLSD& compile_errors) row["columns"][0]["font"] = "OCRA"; mScriptEd->mErrorList->addElement(row); } + + if (isOpenInExternalEditor()) + { + logErrorsToFile(compile_errors); + } + mScriptEd->selectFirstError(); mIsSaving = false; closeIfNeeded(); @@ -2057,9 +2309,10 @@ void LLLiveLSLEditor::loadAsset() { mItem = new LLViewerInventoryItem(item); // request the text from the object - LLSD* user_data = new LLSD(); - user_data->with("taskid", mObjectUUID).with("itemid", mItemUUID); - gAssetStorage->getInvItemAsset(object->getRegion()->getHost(), + LLSD* user_data = new LLSD(); + user_data->with("taskid", mObjectUUID).with("itemid", mItemUUID); + gAssetStorage->getInvItemAsset( + object->getRegion()->getHost(), gAgent.getID(), gAgent.getSessionID(), item->getPermissions().getOwner(), @@ -2067,8 +2320,8 @@ void LLLiveLSLEditor::loadAsset() item->getUUID(), item->getAssetUUID(), item->getType(), - &LLLiveLSLEditor::onLoadComplete, - (void*)user_data, + LLLiveLSLEditor::onLoadComplete, + user_data, true); LLMessageSystem* msg = gMessageSystem; msg->newMessageFast(_PREHASH_GetScriptRunning); @@ -2107,26 +2360,6 @@ void LLLiveLSLEditor::loadAsset() */ } } - else - { - mScriptEd->setScriptText(std::string(HELLO_LSL), true); - mScriptEd->enableSave(false); - LLPermissions perm; - perm.init(gAgent.getID(), gAgent.getID(), LLUUID::null, gAgent.getGroupID()); - perm.initMasks(PERM_ALL, PERM_ALL, PERM_NONE, PERM_NONE, PERM_MOVE | PERM_TRANSFER); - mItem = new LLViewerInventoryItem(mItemUUID, - mObjectUUID, - perm, - LLUUID::null, - LLAssetType::AT_LSL_TEXT, - LLInventoryType::IT_LSL, - DEFAULT_SCRIPT_NAME, - DEFAULT_SCRIPT_DESC, - LLSaleInfo::DEFAULT, - LLInventoryItemFlags::II_FLAGS_NONE, - time_corrected()); - mAssetStatus = PREVIEW_ASSET_LOADED; - } requestExperiences(); } @@ -2202,14 +2435,9 @@ void LLLiveLSLEditor::loadScriptText(const LLUUID &uuid, LLAssetType::EType type } -void LLLiveLSLEditor::onRunningCheckboxClicked( LLUICtrl*, void* userdata ) +void LLLiveLSLEditor::onRunningCheckboxClicked() { - LLLiveLSLEditor* self = (LLLiveLSLEditor*) userdata; - LLViewerObject* object = gObjectList.findObject( self->mObjectUUID ); - LLCheckBoxCtrl* runningCheckbox = self->getChild<LLCheckBoxCtrl>("running"); - bool running = runningCheckbox->get(); - //self->mRunningCheckbox->get(); - if( object ) + if (LLViewerObject* object = gObjectList.findObject(mObjectUUID)) { LLMessageSystem* msg = gMessageSystem; msg->newMessageFast(_PREHASH_SetScriptRunning); @@ -2217,24 +2445,21 @@ void LLLiveLSLEditor::onRunningCheckboxClicked( LLUICtrl*, void* userdata ) msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID()); msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID()); msg->nextBlockFast(_PREHASH_Script); - msg->addUUIDFast(_PREHASH_ObjectID, self->mObjectUUID); - msg->addUUIDFast(_PREHASH_ItemID, self->mItemUUID); - msg->addBOOLFast(_PREHASH_Running, running); + msg->addUUIDFast(_PREHASH_ObjectID, mObjectUUID); + msg->addUUIDFast(_PREHASH_ItemID, mItemUUID); + msg->addBOOLFast(_PREHASH_Running, mRunningCheckbox->get()); msg->sendReliable(object->getRegion()->getHost()); } else { - runningCheckbox->set(!running); + mRunningCheckbox->set(!mRunningCheckbox->get()); LLNotificationsUtil::add("CouldNotStartStopScript"); } } -void LLLiveLSLEditor::onReset(void *userdata) +void LLLiveLSLEditor::onReset() { - LLLiveLSLEditor* self = (LLLiveLSLEditor*) userdata; - - LLViewerObject* object = gObjectList.findObject( self->mObjectUUID ); - if(object) + if (LLViewerObject* object = gObjectList.findObject(mObjectUUID)) { LLMessageSystem* msg = gMessageSystem; msg->newMessageFast(_PREHASH_ScriptReset); @@ -2242,8 +2467,8 @@ void LLLiveLSLEditor::onReset(void *userdata) msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID()); msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID()); msg->nextBlockFast(_PREHASH_Script); - msg->addUUIDFast(_PREHASH_ObjectID, self->mObjectUUID); - msg->addUUIDFast(_PREHASH_ItemID, self->mItemUUID); + msg->addUUIDFast(_PREHASH_ObjectID, mObjectUUID); + msg->addUUIDFast(_PREHASH_ItemID, mItemUUID); msg->sendReliable(object->getRegion()->getHost()); } else @@ -2255,34 +2480,33 @@ void LLLiveLSLEditor::onReset(void *userdata) void LLLiveLSLEditor::draw() { LLViewerObject* object = gObjectList.findObject(mObjectUUID); - LLCheckBoxCtrl* runningCheckbox = getChild<LLCheckBoxCtrl>( "running"); - if(object && mAskedForRunningInfo && mHaveRunningInfo) + if (object && mAskedForRunningInfo && mHaveRunningInfo) { - if(object->permAnyOwner()) + if (object->permAnyOwner()) { - runningCheckbox->setLabel(getString("script_running")); - runningCheckbox->setEnabled(!mIsSaving); + mRunningCheckbox->setLabel(getString("script_running")); + mRunningCheckbox->setEnabled(!mIsSaving); } else { - runningCheckbox->setLabel(getString("public_objects_can_not_run")); - runningCheckbox->setEnabled(false); + mRunningCheckbox->setLabel(getString("public_objects_can_not_run")); + mRunningCheckbox->setEnabled(false); // *FIX: Set it to false so that the ui is correct for // a box that is released to public. It could be // incorrect after a release/claim cycle, but will be // correct after clicking on it. - runningCheckbox->set(false); - mMonoCheckbox->set(false); + mRunningCheckbox->set(false); + mScriptEd->mCompileTarget->clear(); } } - else if(!object) + else if (!object) { // HACK: Display this information in the title bar. // Really ought to put in main window. setTitle(LLTrans::getString("ObjectOutOfRange")); - runningCheckbox->setEnabled(false); - mMonoCheckbox->setEnabled(false); + mRunningCheckbox->setEnabled(false); + mScriptEd->mCompileTarget->setEnabled(false); // object may have fallen out of range. mHaveRunningInfo = false; } @@ -2339,6 +2563,8 @@ void LLLiveLSLEditor::finishLSLUpload(LLUUID itemId, LLUUID taskId, LLUUID newAs { preview->callbackLSLCompileFailed(response["errors"]); } + response["is_running"] = isRunning; + preview->sendCompileResults(response); } } @@ -2389,7 +2615,7 @@ void LLLiveLSLEditor::saveIfNeeded(bool sync /*= true*/) mScriptEd->sync(); } - bool isRunning = getChild<LLCheckBoxCtrl>("running")->get(); + bool is_running = mRunningCheckbox->get(); getWindow()->incBusyCount(); mPendingUploads++; @@ -2397,17 +2623,18 @@ void LLLiveLSLEditor::saveIfNeeded(bool sync /*= true*/) if (!url.empty()) { + std::string compile_target(mScriptEd->mCompileTarget->getValue()); std::string buffer(mScriptEd->mEditor->getText()); LLUUID old_asset_id = mScriptEd->getAssetID(); LLResourceUploadInfo::ptr_t uploadInfo(std::make_shared<LLScriptAssetUpload>(mObjectUUID, mItemUUID, - monoChecked() ? LLScriptAssetUpload::MONO : LLScriptAssetUpload::LSL2, - isRunning, mScriptEd->getAssociatedExperience(), buffer, - [isRunning, old_asset_id](LLUUID itemId, LLUUID taskId, LLUUID newAssetId, LLSD response) { - LLFileSystem::removeFile(old_asset_id, LLAssetType::AT_LSL_TEXT); - LLLiveLSLEditor::finishLSLUpload(itemId, taskId, newAssetId, response, isRunning); - }, - nullptr)); // needs failure handling? + compile_target, is_running, mScriptEd->getAssociatedExperience(), buffer, + [is_running, old_asset_id](LLUUID item_id, LLUUID task_id, LLUUID new_asset_id, LLSD response) + { + LLFileSystem::removeFile(old_asset_id, LLAssetType::AT_LSL_TEXT); + LLLiveLSLEditor::finishLSLUpload(item_id, task_id, new_asset_id, response, is_running); + }, + nullptr)); // needs failure handling? LLViewerAssetUpload::EnqueueInventoryUpload(url, uploadInfo); } @@ -2460,28 +2687,61 @@ void LLLiveLSLEditor::processScriptRunningReply(LLMessageSystem* msg, void**) if (LLLiveLSLEditor* instance = LLFloaterReg::findTypedInstance<LLLiveLSLEditor>("preview_scriptedit", floater_key)) { instance->mHaveRunningInfo = true; + bool running; msg->getBOOLFast(_PREHASH_Script, _PREHASH_Running, running); - LLCheckBoxCtrl* runningCheckbox = instance->getChild<LLCheckBoxCtrl>("running"); - runningCheckbox->set(running); - bool mono; - msg->getBOOLFast(_PREHASH_Script, "Mono", mono); - LLCheckBoxCtrl* monoCheckbox = instance->getChild<LLCheckBoxCtrl>("mono"); - monoCheckbox->setEnabled(instance->getIsModifiable() && have_script_upload_cap(object_id)); - monoCheckbox->set(mono); - } -} + instance->mRunningCheckbox->set(running); -void LLLiveLSLEditor::onMonoCheckboxClicked(LLUICtrl*, void* userdata) -{ - LLLiveLSLEditor* self = static_cast<LLLiveLSLEditor*>(userdata); - self->mMonoCheckbox->setEnabled(have_script_upload_cap(self->mObjectUUID)); - self->mScriptEd->enableSave(self->getIsModifiable()); + bool mono = false, luau = false, luau_language = false; + msg->getBOOLFast(_PREHASH_Script, _PREHASH_Mono, mono); + msg->getBOOLFast(_PREHASH_Script, _PREHASH_Luau, luau); // Luau compiler is enabled + msg->getBOOLFast(_PREHASH_Script, _PREHASH_LuauLanguage, luau_language); + + std::string compile_target; + if (luau) + { + if (luau_language) + { + compile_target = "luau"; + } + else + { + compile_target = "lsl-luau"; // Luau compiler running in LSL compatibility mode + } + } + else if (mono) + { + compile_target = "mono"; + } + else + { + compile_target = "lsl2"; + } + + instance->mScriptEd->mCompileTarget->setValue(compile_target); + instance->mScriptEd->processKeywords(luau && luau_language); // Use Luau syntax highlighting for Luau scripts + + bool lua_scripts_enabled = have_lua_enabled(object_id); + if (LLScrollListItem* luau_item = instance->mScriptEd->mCompileTarget->findItemByValue("luau")) + { + luau_item->setEnabled(lua_scripts_enabled); + } + if (LLScrollListItem* lsl_luau_item = instance->mScriptEd->mCompileTarget->findItemByValue("lsl-luau")) + { + lsl_luau_item->setEnabled(lua_scripts_enabled); + } + + instance->mScriptEd->mCompileTarget->setEnabled(instance->getIsModifiable() && have_script_upload_cap(object_id)); + } } -bool LLLiveLSLEditor::monoChecked() const +void LLLiveLSLEditor::onCompileTargetChanged() { - return mMonoCheckbox && mMonoCheckbox->getValue(); + mScriptEd->mCompileTarget->setEnabled(have_script_upload_cap(mObjectUUID)); + mScriptEd->enableSave(getIsModifiable()); + bool is_lua = mScriptEd->mCompileTarget->getValue().asString() == "luau"; + mScriptEd->mEditor->setLuauLanguage(is_lua); + mScriptEd->processKeywords(is_lua); } void LLLiveLSLEditor::setAssociatedExperience( LLHandle<LLLiveLSLEditor> editor, const LLSD& experience ) diff --git a/indra/newview/llpreviewscript.h b/indra/newview/llpreviewscript.h index a56697117a..909e2183c2 100644 --- a/indra/newview/llpreviewscript.h +++ b/indra/newview/llpreviewscript.h @@ -24,8 +24,7 @@ * $/LicenseInfo$ */ -#ifndef LL_LLPREVIEWSCRIPT_H -#define LL_LLPREVIEWSCRIPT_H +#pragma once #include "llpreview.h" #include "lltabcontainer.h" @@ -54,6 +53,9 @@ class LLScriptEdContainer; class LLFloaterGotoLine; class LLFloaterExperienceProfile; class LLScriptMovedObserver; +class LLScriptEditorWSServer; + +bool is_lua_script(const std::string& code); class LLLiveLSLFile : public LLLiveFile { @@ -61,12 +63,12 @@ public: typedef std::function<bool(const std::string& filename)> change_callback_t; LLLiveLSLFile(std::string file_path, change_callback_t change_cb); - ~LLLiveLSLFile(); + ~LLLiveLSLFile() override; void ignoreNextUpdate() { mIgnoreNextUpdate = true; } protected: - /*virtual*/ bool loadFile(); + bool loadFile() override; change_callback_t mOnChangeCallback; bool mIgnoreNextUpdate; @@ -82,26 +84,34 @@ class LLScriptEdCore : public LLPanel friend class LLScriptEdContainer; friend class LLFloaterGotoLine; +public: + typedef boost::function<void(void*)> script_ed_callback_t; + typedef boost::function<void(void*, bool)> save_callback_t; + protected: // Supposed to be invoked only by the container. LLScriptEdCore( LLScriptEdContainer* container, const std::string& sample, const LLHandle<LLFloater>& floater_handle, - void (*load_callback)(void* userdata), - void (*save_callback)(void* userdata, bool close_after_save), - void (*search_replace_callback)(void* userdata), + script_ed_callback_t load_callback, + save_callback_t save_callback, + script_ed_callback_t search_replace_callback, void* userdata, bool live, S32 bottom_pad = 0); // pad below bottom row of buttons public: - ~LLScriptEdCore(); + ~LLScriptEdCore() override; void initMenu(); void processKeywords(); + void processKeywords(bool luau_language); + LLScriptEditor* getEditor() const { return mEditor; } + LLKeywords& getKeywords() const { return mEditor->getKeywords(); } + bool isLuauLanguage() const { return mEditor->getIsLuauLanguage(); } - virtual void draw(); - /*virtual*/ bool postBuild(); + void draw() override; + bool postBuild() override; bool canClose(); void setEnableEditing(bool enable); bool canLoadOrSaveToFile( void* userdata ); @@ -134,33 +144,32 @@ public: static bool enableSaveToFileMenu(void* userdata); static bool enableLoadFromFileMenu(void* userdata); - virtual bool hasAccelerators() const { return true; } + bool hasAccelerators() const override { return true; } LLUUID getAssociatedExperience()const; void setAssociatedExperience( const LLUUID& experience_id ); - void setScriptName(const std::string& name){mScriptName = name;}; + void setScriptName(const std::string& name) { mScriptName = name; } - void setItemRemoved(bool script_removed){mScriptRemoved = script_removed;}; + void setItemRemoved(bool script_removed) { mScriptRemoved = script_removed; } void setAssetID( const LLUUID& asset_id){ mAssetID = asset_id; }; LLUUID getAssetID() const { return mAssetID; } - bool isFontSizeChecked(const LLSD &userdata); - void onChangeFontSize(const LLSD &size_name); + bool isFontSizeChecked(const LLSD &userdata); + void onChangeFontSize(const LLSD &size_name); - virtual bool handleKeyHere(KEY key, MASK mask); - void selectAll() { mEditor->selectAll(); } + bool handleKeyHere(KEY key, MASK mask) override; + void selectAll() { mEditor->selectAll(); } + + void enableSave(bool b) { mEnableSave = b; } + bool hasChanged() const; private: void onBtnDynamicHelp(); void onBtnUndoChanges(); - bool hasChanged() const; - void selectFirstError(); - void enableSave(bool b) {mEnableSave = b;} - protected: void deleteBridges(); void setHelpPage(const std::string& help_string); @@ -175,9 +184,9 @@ private: std::string mSampleText; std::string mScriptName; LLScriptEditor* mEditor; - void (*mLoadCallback)(void* userdata); - void (*mSaveCallback)(void* userdata, bool close_after_save); - void (*mSearchReplaceCallback) (void* userdata); + script_ed_callback_t mLoadCallback; + save_callback_t mSaveCallback; + script_ed_callback_t mSearchReplaceCallback; void* mUserdata; LLComboBox *mFunctions; bool mForceClose; @@ -190,19 +199,18 @@ private: S32 mLiveHelpHistorySize; bool mEnableSave; bool mHasScriptData; - LLLiveLSLFile* mLiveFile; LLUUID mAssociatedExperience; bool mScriptRemoved; bool mSaveDialogShown; LLUUID mAssetID; LLTextBox* mLineCol = nullptr; LLButton* mSaveBtn = nullptr; + LLComboBox* mCompileTarget = nullptr; LLScriptEdContainer* mContainer; // parent view -public: + public: boost::signals2::connection mSyntaxIDConnection; - }; class LLScriptEdContainer : public LLPreview @@ -211,15 +219,30 @@ class LLScriptEdContainer : public LLPreview public: LLScriptEdContainer(const LLSD& key); + ~LLScriptEdContainer() override; + + bool handleKeyHere(KEY key, MASK mask) override; - bool handleKeyHere(KEY key, MASK mask); + void startWebsocketServer(); + void unsubscribeScript(); + void sendCompileResults(LLSD&); + + LLScriptEdCore* getScriptEdCore() const { return mScriptEd; } protected: - std::string getTmpFileName(const std::string& script_name); + std::string getTmpFileName(const std::string& script_name) const; + std::string getUniqueHash() const; + std::string getErrorLogFileName(const std::string& script_path); bool onExternalChange(const std::string& filename); virtual void saveIfNeeded(bool sync = true) = 0; + bool logErrorsToFile(const LLSD& compile_errors); + bool isOpenInExternalEditor() const { return mLiveFile != nullptr; } LLScriptEdCore* mScriptEd; + LLLiveLSLFile* mLiveFile = nullptr; + LLLiveLSLFile* mLiveLogFile = nullptr; + + std::weak_ptr<LLScriptEditorWSServer> mWebSocketServer; }; // Used to view and edit an LSL script from your inventory. @@ -227,7 +250,7 @@ class LLPreviewLSL : public LLScriptEdContainer { public: LLPreviewLSL(const LLSD& key ); - ~LLPreviewLSL(); + ~LLPreviewLSL() override; LLUUID getScriptID() { return mItemUUID; } @@ -236,15 +259,16 @@ public: virtual void callbackLSLCompileSucceeded(); virtual void callbackLSLCompileFailed(const LLSD& compile_errors); - /*virtual*/ bool postBuild(); + bool postBuild() override; protected: - virtual void draw(); - virtual bool canClose(); + void draw() override; + bool canClose() override; void closeIfNeeded(); - virtual void loadAsset(); - /*virtual*/ void saveIfNeeded(bool sync = true); + void loadAsset() override; + void saveIfNeeded(bool sync = true) override; + void onCompileTargetChanged(); static void onSearchReplace(void* userdata); static void onLoad(void* userdata); @@ -265,10 +289,8 @@ protected: S32 mPendingUploads; LLScriptMovedObserver* mItemObserver; - }; - // Used to view and edit an LSL script that is attached to an object. class LLLiveLSLEditor : public LLScriptEdContainer { @@ -276,7 +298,6 @@ class LLLiveLSLEditor : public LLScriptEdContainer public: LLLiveLSLEditor(const LLSD& key); - static void processScriptRunningReply(LLMessageSystem* msg, void**); virtual void callbackLSLCompileSucceeded(const LLUUID& task_id, @@ -284,13 +305,13 @@ public: bool is_script_running); virtual void callbackLSLCompileFailed(const LLSD& compile_errors); - /*virtual*/ bool postBuild(); + bool postBuild() override; void setIsNew() { mIsNew = true; } static void setAssociatedExperience( LLHandle<LLLiveLSLEditor> editor, const LLSD& experience ); - static void onToggleExperience(LLUICtrl *ui, void* userdata); - static void onViewProfile(LLUICtrl *ui, void* userdata); + void onToggleExperience(); + void onViewProfile(); void setExperienceIds(const LLSD& experience_ids); void buildExperienceList(); @@ -300,15 +321,15 @@ public: void setObjectName(std::string name) { mObjectName = name; } + bool getIsModifiable() const { return mIsModifiable; } // Evaluated on load assert + private: - virtual bool canClose(); + bool canClose() override; void closeIfNeeded(); - virtual void draw(); - - virtual void loadAsset(); - /*virtual*/ void saveIfNeeded(bool sync = true); - bool monoChecked() const; + void draw() override; + void loadAsset() override; + void saveIfNeeded(bool sync = true) override; static void onSearchReplace(void* userdata); static void onLoad(void* userdata); @@ -317,14 +338,14 @@ private: static void onLoadComplete(const LLUUID& asset_uuid, LLAssetType::EType type, void* user_data, S32 status, LLExtStat ext_status); - static void onRunningCheckboxClicked(LLUICtrl*, void* userdata); - static void onReset(void* userdata); + void onRunningCheckboxClicked(); + void onReset(); void loadScriptText(const LLUUID &uuid, LLAssetType::EType type); static void* createScriptEdPanel(void* userdata); - static void onMonoCheckboxClicked(LLUICtrl*, void* userdata); + void onCompileTargetChanged(); static void finishLSLUpload(LLUUID itemId, LLUUID taskId, LLUUID newAssetId, LLSD response, bool isRunning); static void receiveExperienceIds(LLSD result, LLHandle<LLLiveLSLEditor> parent); @@ -342,19 +363,16 @@ private: S32 mPendingUploads; bool mIsSaving; + bool mIsModifiable; - bool getIsModifiable() const { return mIsModifiable; } // Evaluated on load assert - - LLCheckBoxCtrl* mMonoCheckbox; - bool mIsModifiable; - - - LLComboBox* mExperiences; - LLCheckBoxCtrl* mExperienceEnabled; - LLSD mExperienceIds; + LLButton* mResetButton { nullptr }; + LLCheckBoxCtrl* mRunningCheckbox { nullptr }; + LLComboBox* mExperiences { nullptr }; + LLCheckBoxCtrl* mExperienceEnabled { nullptr }; + LLButton* mViewProfileButton { nullptr }; + LLSD mExperienceIds; LLHandle<LLFloater> mExperienceProfile; - std::string mObjectName; + std::string mObjectName; }; -#endif // LL_LLPREVIEWSCRIPT_H diff --git a/indra/newview/llscripteditor.cpp b/indra/newview/llscripteditor.cpp index 59cf3ac02b..2a4c2b9d0b 100644 --- a/indra/newview/llscripteditor.cpp +++ b/indra/newview/llscripteditor.cpp @@ -31,6 +31,179 @@ #include "llsyntaxid.h" #include "lllocalcliprect.h" #include "llviewercontrol.h" +#include "llworkerthread.h" +#include <algorithm> +#include <utility> + +static LLWorkerThread& getSyntaxWorkerThread() +{ + static LLWorkerThread* sThread = new LLWorkerThread("SyntaxParse", true); + return *sThread; +} + +class LLScriptEditorSyntaxWorker final : public LLWorkerClass +{ +public: + struct Request + { + LLWString text; + S32 text_generation = 0; + U32 keywords_generation = 0; + bool disable_highlight = false; + LLKeywords* keywords = nullptr; + }; + + struct Result + { + LLWString text; + LLKeywords::segment_ops_t ops; + S32 text_generation = 0; + U32 keywords_generation = 0; + bool disable_highlight = false; + LLKeywords* keywords = nullptr; + }; + + LLScriptEditorSyntaxWorker(LLWorkerThread* thread, LLScriptEditor* editor) + : LLWorkerClass(thread, "ScriptEditorSyntax"), + mEditor(editor), + mHasPending(false), + mDropResults(false) + { + } + + void queueRequest(const Request& request) + { + bool should_add = false; + { + LLMutexLock lock(&mRequestMutex); + mPendingRequest = request; + mHasPending = true; + should_add = (!haveWork() && !isWorking()); + } + if (should_add) + { + addWork(0); + } + } + + void pump() + { + checkWork(); + bool should_add = false; + { + LLMutexLock lock(&mRequestMutex); + should_add = (!haveWork() && !isWorking() && mHasPending); + } + if (should_add) + { + addWork(0); + } + } + + void waitForIdle(bool drop_results) + { + mDropResults = drop_results; + { + LLMutexLock lock(&mRequestMutex); + mHasPending = false; + } + if (mRequestHandle != LLWorkerThread::nullHandle()) + { + mWorkerThread->waitForResult(mRequestHandle, false); + checkWork(); + } + mDropResults = false; + } + + void shutdown() + { + mEditor = nullptr; + waitForIdle(true); + scheduleDelete(); + } + +private: + void startWork(S32 param) override + { + LLMutexLock lock(&mRequestMutex); + if (!mHasPending) + { + return; + } + mActiveRequest = mPendingRequest; + mHasPending = false; + } + + bool doWork(S32 param) override + { + Request request; + { + LLMutexLock lock(&mRequestMutex); + request = mActiveRequest; + } + + Result result; + result.text = request.text; + result.text_generation = request.text_generation; + result.keywords_generation = request.keywords_generation; + result.disable_highlight = request.disable_highlight; + result.keywords = request.keywords; + + if (request.keywords) + { + request.keywords->collectSegmentOps(result.ops, request.text, request.disable_highlight); + } + + { + LLMutexLock lock(&mResultMutex); + mResult = std::move(result); + } + return true; + } + + void endWork(S32 param, bool aborted) override + { + if (aborted || mDropResults || !mEditor) + { + return; + } + + Result result; + { + LLMutexLock lock(&mResultMutex); + result = std::move(mResult); + } + + if (mEditor->getTextGeneration() != result.text_generation) + { + return; + } + if (mEditor->getKeywordsGeneration() != result.keywords_generation) + { + return; + } + if (&mEditor->getKeywords() != result.keywords) + { + return; + } + + mEditor->queueSyntaxApply(std::move(result.text), + std::move(result.ops), + result.text_generation, + result.keywords_generation, + result.disable_highlight, + result.keywords); + } + + LLScriptEditor* mEditor; + LLMutex mRequestMutex; + LLMutex mResultMutex; + Request mPendingRequest; + Request mActiveRequest; + Result mResult; + bool mHasPending; + bool mDropResults; +}; const S32 UI_TEXTEDITOR_LINE_NUMBER_MARGIN = 32; @@ -45,7 +218,21 @@ LLScriptEditor::Params::Params() LLScriptEditor::LLScriptEditor(const Params& p) : LLTextEditor(p) , mShowLineNumbers(p.show_line_numbers), - mUseDefaultFontSize(p.default_font_size) + mUseDefaultFontSize(p.default_font_size), + mLuauLanguage(false), + mKeywordsGeneration(0), + mLastQueuedTextGeneration(-1), + mLastQueuedKeywordsGeneration(0), + mLastQueuedDisableHighlight(false), + mLastQueuedKeywords(nullptr), + mSyntaxWorker(nullptr), + mSyntaxApplyState(SyntaxApplyState::Idle), + mPendingApplyOpIndex(0), + mPendingApplySegmentIndex(0), + mPendingApplyTextGeneration(-1), + mPendingApplyKeywordsGeneration(0), + mPendingApplyDisableHighlight(false), + mPendingApplyKeywords(nullptr) { if (mShowLineNumbers) { @@ -54,10 +241,22 @@ LLScriptEditor::LLScriptEditor(const Params& p) } } +LLScriptEditor::~LLScriptEditor() +{ + if (mSyntaxWorker) + { + mSyntaxWorker->shutdown(); + getSyntaxWorkerThread().update(0.f); + mSyntaxWorker = nullptr; + } +} + bool LLScriptEditor::postBuild() { gSavedSettings.getControl("LSLFontSizeName")->getCommitSignal()->connect(boost::bind(&LLScriptEditor::onFontSizeChange, this)); - return LLTextEditor::postBuild(); + bool result = LLTextEditor::postBuild(); + setFont(getScriptFont()); + return result; } void LLScriptEditor::draw() @@ -119,7 +318,7 @@ void LLScriptEditor::drawLineNumbers() // draw the line numbers if(line.mLineNum != last_line_num && line.mRect.mTop <= scrolled_view_rect.mTop) { - const LLWString ltext = utf8str_to_wstring(llformat("%d", line.mLineNum )); + const LLWString ltext = utf8str_to_wstring(llformat("%d", mLuauLanguage ? line.mLineNum + 1 : line.mLineNum)); bool is_cur_line = cursor_line == line.mLineNum; const U8 style = is_cur_line ? LLFontGL::BOLD : LLFontGL::NORMAL; const LLColor4& fg_color = is_cur_line ? mCursorColor : mReadOnlyFgColor; @@ -141,49 +340,220 @@ void LLScriptEditor::drawLineNumbers() } } -void LLScriptEditor::initKeywords() +void LLScriptEditor::initKeywords(bool luau_language) { - mKeywords.initialize(LLSyntaxIdLSL::getInstance()->getKeywordsXML()); + mKeywordsLua.initialize(LLSyntaxLua::getInstance()->getKeywordsXML(), true); + mKeywordsLSL.initialize(LLSyntaxIdLSL::getInstance()->getKeywordsXML(), false); + + mLuauLanguage = luau_language; + } void LLScriptEditor::loadKeywords() { LL_PROFILE_ZONE_SCOPED; - mKeywords.processTokens(); - - LLStyleConstSP style = new LLStyle(LLStyle::Params().font(getScriptFont()).color(mDefaultColor.get())); + ensureSyntaxWorker(); + mSyntaxWorker->waitForIdle(true); + resetPendingSyntaxApply(); + getKeywords().processTokens(); + ++mKeywordsGeneration; - segment_vec_t segment_list; - mKeywords.findSegments(&segment_list, getWText(), *this, style); - - mSegments.clear(); - segment_set_t::iterator insert_it = mSegments.begin(); - for (segment_vec_t::iterator list_it = segment_list.begin(); list_it != segment_list.end(); ++list_it) + LLKeywords::segment_ops_t ops; + const LLWString& text = getWText(); + const llwchar* base = text.c_str(); + for (const llwchar* cur = base; *cur; ++cur) { - insert_it = mSegments.insert(insert_it, *list_it); + if (*cur == '\n') + { + ops.push_back({LLKeywords::SegmentOp::OP_LINE_BREAK, (S32)(cur - base), 0, nullptr}); + } } + applySyntaxSegments(text, ops); + queueSyntaxParse(); } void LLScriptEditor::updateSegments() { - if (mReflowIndex < S32_MAX && mKeywords.isLoaded() && mParseOnTheFly) + if (getKeywords().isLoaded() && mParseOnTheFly) { LL_PROFILE_ZONE_SCOPED; + ensureSyntaxWorker(); + mSyntaxWorker->pump(); + if (mReflowIndex < S32_MAX) + { + queueSyntaxParse(); + } + processPendingSyntaxApply(); + } + + LLTextBase::updateSegments(); +} + +void LLScriptEditor::ensureSyntaxWorker() +{ + if (!mSyntaxWorker) + { + mSyntaxWorker = new LLScriptEditorSyntaxWorker(&getSyntaxWorkerThread(), this); + } +} + +void LLScriptEditor::queueSyntaxParse() +{ + static LLCachedControl<bool> sDisableSyntaxHighlighting(gSavedSettings, "ScriptEditorDisableSyntaxHighlight", false); + const bool disable_syntax_highlighting = sDisableSyntaxHighlighting; + + LLKeywords* keywords = &getKeywords(); + const S32 text_generation = getTextGeneration(); + + if (mLastQueuedTextGeneration == text_generation + && mLastQueuedKeywordsGeneration == mKeywordsGeneration + && mLastQueuedDisableHighlight == disable_syntax_highlighting + && mLastQueuedKeywords == keywords) + { + return; + } + + mLastQueuedTextGeneration = text_generation; + mLastQueuedKeywordsGeneration = mKeywordsGeneration; + mLastQueuedDisableHighlight = disable_syntax_highlighting; + mLastQueuedKeywords = keywords; + + LLScriptEditorSyntaxWorker::Request request; + request.text = getWText(); + request.text_generation = text_generation; + request.keywords_generation = mKeywordsGeneration; + request.disable_highlight = disable_syntax_highlighting; + request.keywords = keywords; + mSyntaxWorker->queueRequest(request); +} + +void LLScriptEditor::queueSyntaxApply(LLWString text, + LLKeywords::segment_ops_t ops, + S32 text_generation, + U32 keywords_generation, + bool disable_highlight, + LLKeywords* keywords) +{ + if (text_generation != getTextGeneration() + || keywords_generation != mKeywordsGeneration + || keywords != &getKeywords()) + { + return; + } + + resetPendingSyntaxApply(); + + // Small updates can apply synchronously; larger ones use background slices. + constexpr size_t kImmediateOpsThreshold = 500; + if (ops.size() <= kImmediateOpsThreshold) + { + applySyntaxSegments(text, ops); + return; + } + + mPendingApplyText = std::move(text); + mPendingApplyOps = std::move(ops); + mPendingApplyTextGeneration = text_generation; + mPendingApplyKeywordsGeneration = keywords_generation; + mPendingApplyDisableHighlight = disable_highlight; + mPendingApplyKeywords = keywords; + mPendingApplyOpIndex = 0; + mPendingApplySegmentIndex = 0; + mPendingApplySegments.clear(); + mPendingApplySegmentSet.clear(); + mPendingApplyStyle = new LLStyle(LLStyle::Params().font(getScriptFont()).color(mDefaultColor.get())); + mSyntaxApplyState = SyntaxApplyState::Building; +} + +void LLScriptEditor::processPendingSyntaxApply() +{ + if (mSyntaxApplyState == SyntaxApplyState::Idle) + { + return; + } - LLStyleConstSP style = new LLStyle(LLStyle::Params().font(getScriptFont()).color(mDefaultColor.get())); + static LLCachedControl<bool> sDisableSyntaxHighlighting(gSavedSettings, "ScriptEditorDisableSyntaxHighlight", false); + if (mPendingApplyTextGeneration != getTextGeneration() + || mPendingApplyKeywordsGeneration != mKeywordsGeneration + || mPendingApplyKeywords != &getKeywords() + || mPendingApplyDisableHighlight != sDisableSyntaxHighlighting) + { + resetPendingSyntaxApply(); + return; + } - // HACK: No non-ascii keywords for now - segment_vec_t segment_list; - mKeywords.findSegments(&segment_list, getWText(), *this, style); + // Slice sizes control UI budget while applying large highlight updates. + constexpr size_t kOpsPerSlice = 250; + constexpr size_t kSegmentsPerSlice = 250; - clearSegments(); - for (segment_vec_t::iterator list_it = segment_list.begin(); list_it != segment_list.end(); ++list_it) + if (mSyntaxApplyState == SyntaxApplyState::Building) + { + if (mPendingApplyStyle.isNull()) + { + mPendingApplyStyle = new LLStyle(LLStyle::Params().font(getScriptFont()).color(mDefaultColor.get())); + } + bool done = getKeywords().applySegmentOpsRange(&mPendingApplySegments, + mPendingApplyText, + mPendingApplyOps, + mPendingApplyOpIndex, + kOpsPerSlice, + *this, + mPendingApplyStyle); + if (done) { - insertSegment(*list_it); + mSyntaxApplyState = SyntaxApplyState::Inserting; } + return; } - LLTextBase::updateSegments(); + size_t end_index = std::min(mPendingApplySegmentIndex + kSegmentsPerSlice, mPendingApplySegments.size()); + for (; mPendingApplySegmentIndex < end_index; ++mPendingApplySegmentIndex) + { + LLTextSegmentPtr segment = mPendingApplySegments[mPendingApplySegmentIndex]; + segment->linkToDocument(this); + mPendingApplySegmentSet.insert(segment); + } + + if (mPendingApplySegmentIndex >= mPendingApplySegments.size()) + { + S32 saved_scroll_index = mScrollIndex; + segment_set_t old_segments; + old_segments.swap(mSegments); + mSegments.swap(mPendingApplySegmentSet); + mScrollIndex = saved_scroll_index; + needsReflow(0); + resetPendingSyntaxApply(); + } +} + +void LLScriptEditor::resetPendingSyntaxApply() +{ + mSyntaxApplyState = SyntaxApplyState::Idle; + mPendingApplyText.clear(); + mPendingApplyOps.clear(); + mPendingApplySegments.clear(); + mPendingApplySegmentSet.clear(); + mPendingApplyOpIndex = 0; + mPendingApplySegmentIndex = 0; + mPendingApplyStyle = LLStyleConstSP(); + mPendingApplyTextGeneration = -1; + mPendingApplyKeywordsGeneration = 0; + mPendingApplyDisableHighlight = false; + mPendingApplyKeywords = nullptr; +} + +void LLScriptEditor::applySyntaxSegments(const LLWString& text, const LLKeywords::segment_ops_t& ops) +{ + LLStyleConstSP style = new LLStyle(LLStyle::Params().font(getScriptFont()).color(mDefaultColor.get())); + + segment_vec_t segment_list; + getKeywords().applySegmentOps(&segment_list, text, ops, *this, style); + + clearSegments(); + for (segment_vec_t::iterator list_it = segment_list.begin(); list_it != segment_list.end(); ++list_it) + { + insertSegment(*list_it); + } } void LLScriptEditor::clearSegments() @@ -194,6 +564,21 @@ void LLScriptEditor::clearSegments() } } +LLKeywords::keyword_iterator_t LLScriptEditor::keywordsBegin() +{ + return getKeywords().begin(); +} + +LLKeywords::keyword_iterator_t LLScriptEditor::keywordsEnd() +{ + return getKeywords().end(); +} + +LLKeywords& LLScriptEditor::getKeywords() +{ + return mLuauLanguage ? mKeywordsLua : mKeywordsLSL; +} + // Most of this is shamelessly copied from LLTextBase void LLScriptEditor::drawSelectionBackground() { @@ -218,7 +603,6 @@ void LLScriptEditor::drawSelectionBackground() ++rect_it) { LLRect selection_rect = *rect_it; - selection_rect = *rect_it; selection_rect.translate(mVisibleTextRect.mLeft - content_display_rect.mLeft, mVisibleTextRect.mBottom - content_display_rect.mBottom); gl_rect_2d(selection_rect, selection_color); } @@ -241,6 +625,7 @@ void LLScriptEditor::onFontSizeChange() { if (!mUseDefaultFontSize) { + setFont(getScriptFont()); needsReflow(); } } diff --git a/indra/newview/llscripteditor.h b/indra/newview/llscripteditor.h index 1632ebe834..dcbfdf3085 100644 --- a/indra/newview/llscripteditor.h +++ b/indra/newview/llscripteditor.h @@ -29,6 +29,7 @@ #define LL_SCRIPTEDITOR_H #include "lltexteditor.h" +#include <cstddef> class LLScriptEditor : public LLTextEditor { @@ -41,17 +42,22 @@ public: Params(); }; - virtual ~LLScriptEditor() {}; + ~LLScriptEditor() override; // LLView override - virtual void draw(); - bool postBuild(); + void draw() override; + bool postBuild() override; - void initKeywords(); + void initKeywords(bool luau_language = false); void loadKeywords(); - /* virtual */ void clearSegments(); - LLKeywords::keyword_iterator_t keywordsBegin() { return mKeywords.begin(); } - LLKeywords::keyword_iterator_t keywordsEnd() { return mKeywords.end(); } + void clearSegments(); + LLKeywords::keyword_iterator_t keywordsBegin(); + LLKeywords::keyword_iterator_t keywordsEnd(); + LLKeywords& getKeywords(); + bool getIsLuauLanguage() { return mLuauLanguage; } + void setLuauLanguage(bool luau_language) { mLuauLanguage = luau_language; } + U32 getKeywordsGeneration() const { return mKeywordsGeneration; } + void applySyntaxSegments(const LLWString& text, const LLKeywords::segment_ops_t& ops); static std::string getScriptFontSize(); LLFontGL* getScriptFont(); @@ -59,18 +65,54 @@ public: protected: friend class LLUICtrlFactory; + friend class LLScriptEditorSyntaxWorker; LLScriptEditor(const Params& p); private: + enum class SyntaxApplyState + { + Idle, + Building, + Inserting + }; void drawLineNumbers(); - /* virtual */ void updateSegments(); - /* virtual */ void drawSelectionBackground(); - void loadKeywords(const std::string& filename_keywords, - const std::string& filename_colors); + void updateSegments() override; + void drawSelectionBackground() override; + void ensureSyntaxWorker(); + void queueSyntaxParse(); + void queueSyntaxApply(LLWString text, + LLKeywords::segment_ops_t ops, + S32 text_generation, + U32 keywords_generation, + bool disable_highlight, + LLKeywords* keywords); + void processPendingSyntaxApply(); + void resetPendingSyntaxApply(); + + LLKeywords mKeywordsLua; + LLKeywords mKeywordsLSL; + bool mLuauLanguage; - LLKeywords mKeywords; bool mShowLineNumbers; bool mUseDefaultFontSize; + U32 mKeywordsGeneration; + S32 mLastQueuedTextGeneration; + U32 mLastQueuedKeywordsGeneration; + bool mLastQueuedDisableHighlight; + LLKeywords* mLastQueuedKeywords; + class LLScriptEditorSyntaxWorker* mSyntaxWorker; + SyntaxApplyState mSyntaxApplyState; + LLWString mPendingApplyText; + LLKeywords::segment_ops_t mPendingApplyOps; + segment_vec_t mPendingApplySegments; + segment_set_t mPendingApplySegmentSet; + size_t mPendingApplyOpIndex; + size_t mPendingApplySegmentIndex; + LLStyleConstSP mPendingApplyStyle; + S32 mPendingApplyTextGeneration; + U32 mPendingApplyKeywordsGeneration; + bool mPendingApplyDisableHighlight; + LLKeywords* mPendingApplyKeywords; }; #endif // LL_SCRIPTEDITOR_H diff --git a/indra/newview/llscripteditorws.cpp b/indra/newview/llscripteditorws.cpp new file mode 100644 index 0000000000..30a1ca53f6 --- /dev/null +++ b/indra/newview/llscripteditorws.cpp @@ -0,0 +1,856 @@ +/** + * @file llscripteditorws.cpp + * @brief JSON-RPC 2.0 WebSocket server implementation for external script editor integration + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#include "llviewerprecompiledheaders.h" +#include "llscripteditorws.h" +#include "llpreviewscript.h" +#include "llappviewer.h" +#include "lltrans.h" +#include "lldate.h" +#include "llerror.h" +#include "lluuid.h" +#include "llversioninfo.h" +#include "llagent.h" +#include "llregex.h" +#include "llviewerobject.h" +#include "llviewerobjectlist.h" +#include "llchat.h" + +//======================================================================== +LLScriptEditorWSServer::LLScriptEditorWSServer(const std::string& name, U16 port, bool local_only) + : LLJSONRPCServer(name, port, local_only) +{ + LL_INFOS("ScriptEditorWS") << "Created JSON-RPC script editor server: " << name + << " on port " << port << LL_ENDL; +} + +LLScriptEditorWSServer::ptr_t LLScriptEditorWSServer::getServer() +{ + if (!LLWebsocketMgr::instanceExists()) + { + return nullptr; + } + LLWebsocketMgr& wsmgr = LLWebsocketMgr::instance(); + return std::static_pointer_cast<LLScriptEditorWSServer>( + wsmgr.findServerByName(LLScriptEditorWSServer::DEFAULT_SERVER_NAME)); +} + + +LLWebsocketMgr::WSConnection::ptr_t LLScriptEditorWSServer::connectionFactory(LLWebsocketMgr::WSServer::ptr_t server, + LLWebsocketMgr::connection_h handle) +{ + auto connection = std::make_shared<LLScriptEditorWSConnection>(server, handle); + mActiveConnections[connection->getConnectionID()] = connection; + + // Call setupConnectionMethods to register any global methods + setupConnectionMethods(connection); + + return connection; +} + +void LLScriptEditorWSServer::onStarted() +{ + LLSyntaxIdLSL& syntax_id_mgr = LLSyntaxIdLSL::instance(); + wptr_t that(std::static_pointer_cast<LLScriptEditorWSServer>(shared_from_this())); + + mLastSyntaxId = syntax_id_mgr.getSyntaxID(); + mLanguageChangeSignal = syntax_id_mgr.addSyntaxIDCallback( + [that]() + { + auto server = that.lock(); + if (server && server->isRunning()) + { + server->broadcastLanguageChange(); + } + }); +} + +void LLScriptEditorWSServer::onStopped() +{ + mLanguageChangeSignal.disconnect(); + mLastSyntaxId.setNull(); +} + +void LLScriptEditorWSServer::onConnectionOpened(const LLWebsocketMgr::WSConnection::ptr_t& connection) +{ + // Call parent class to handle JSON-RPC setup and standard methods + LLJSONRPCServer::onConnectionOpened(connection); + + LL_INFOS("ScriptEditorWS") << "New script editor client connected via JSON-RPC" << LL_ENDL; + +} + +void LLScriptEditorWSServer::onConnectionClosed(const LLWebsocketMgr::WSConnection::ptr_t& connection) +{ + // Call parent class to handle JSON-RPC cleanup + LLJSONRPCServer::onConnectionClosed(connection); + + LL_INFOS("ScriptEditorWS") << "Script editor client disconnected" << LL_ENDL; + + // Remove from active connections + auto script_connection = std::dynamic_pointer_cast<LLScriptEditorWSConnection>(connection); + if (script_connection) + { + U32 connection_id = script_connection->getConnectionID(); + unsubscribeConnection(connection_id); + mActiveConnections.erase(connection_id); + + LL_DEBUGS("ScriptEditorWS") << "Removed connection from active connections. Total: " + << mActiveConnections.size() << LL_ENDL; + // TODO: When connections reach 0, stop the server after a timeout. + } +} + +bool LLScriptEditorWSServer::subscribeScriptEditor(const LLUUID& object_id, const LLUUID& item_id, std::string_view script_name, + const LLHandle<LLPanel>& editor_handle, const std::string& script_id) +{ + if (!editor_handle.isDead()) + { + auto it = mSubscriptions.find(script_id); + if (it == mSubscriptions.end()) + { // Don't re-add if already subscribed + mSubscriptions.emplace(script_id, + LLScriptEditorWSServer::EditorSubscription(object_id, item_id, script_name, editor_handle)); + return false; + } + else + { // Update existing subscription with new editor handle + it->second.mEditorHandle = editor_handle; + } + return true; + } + return false; +} + +void LLScriptEditorWSServer::unsubscribeEditor(const std::string &script_id) +{ + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end()) + { + S32 connection_id = it->second.mConnectionID; + auto connection = it->second.mConnection.lock(); + mSubscriptions.erase(it); + ptrdiff_t count = std::count_if(mSubscriptions.begin(), mSubscriptions.end(), [connection_id](const auto& pair) { + return pair.second.mConnectionID == connection_id; + }); + if (connection && !count) + { // We have removed the last subscription, close the connection + LL_DEBUGS("ScriptEditorWS") << "Closing connection ID " << connection_id << + " as last subscription was removed" << LL_ENDL; + connection->sendDisconnect(LLScriptEditorWSConnection::REASON_EDITOR_CLOSED, "Editor closed"); + } + + } +} + +void LLScriptEditorWSServer::unsubscribeConnection(U32 connection_id) +{ + for (auto it = mSubscriptions.begin(); it != mSubscriptions.end(); ++it) + { + if (it->second.mConnectionID == connection_id) + { + LL_DEBUGS("ScriptEditorWS") << "Unsubscribing script " << it->first + << " from connection ID " << connection_id << LL_ENDL; + it->second.mConnectionID = 0; + it->second.mConnection.reset(); + } + } +} + +LLScriptEditorWSServer::SubscriptionError_t LLScriptEditorWSServer::updateScriptSubscription(const std::string &script_id, U32 connection_id) +{ + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end()) + { + if (it->second.mEditorHandle.isDead()) + { + unsubscribeEditor(script_id); + return SUBSCRIPTION_INVALID_EDITOR; + } + + auto con_it = mActiveConnections.find(connection_id); + if (con_it == mActiveConnections.end()) + { + return SUBSCRIPTION_INTERNAL_ERROR; + } + + if ((it->second.mConnectionID != 0) && !it->second.mConnection.expired() + && it->second.mConnection.lock()->isConnected()) + { + LL_WARNS("ScriptEditorWS") << "Script " << script_id << " is already subscribed on connection ID " << it->second.mConnectionID + << ", cannot subscribe again on connection ID " << connection_id << LL_ENDL; + // In the future we may want to support multiple connections per script. + // That would imply it was open in multiple editors. + return SUBSCRIPTION_ALREADY_SUBSCRIBED; + } + + it->second.mConnectionID = connection_id; + it->second.mConnection = con_it->second; + return SUBSCRIPTION_SUCCESS; + } + return SUBSCRIPTION_INVALID_SUBSCRIPTION; +} + + +LLHandle<LLPanel> LLScriptEditorWSServer::findEditorForScript(const std::string& script_id) const +{ + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end()) + { + return it->second.mEditorHandle; + } + return LLHandle<LLPanel>(); +} + +std::set<std::string> LLScriptEditorWSServer::getActiveScripts() const +{ + std::set<std::string> active_scripts; + for (const auto& [script_id, subinfo] : mSubscriptions) + { + if (!subinfo.mEditorHandle.isDead()) + { + active_scripts.insert(script_id); + } + } + return active_scripts; +} + +void LLScriptEditorWSServer::setupConnectionMethods(LLJSONRPCConnection::ptr_t connection) +{ + // Call parent class to register global JSON-RPC methods + LLJSONRPCServer::setupConnectionMethods(connection); + + // Cast to our specific connection type to access script editor functionality + auto script_connection = std::dynamic_pointer_cast<LLScriptEditorWSConnection>(connection); + if (script_connection) + { + LL_DEBUGS("ScriptEditorWS") << "Setting up script editor connection methods" << LL_ENDL; + wptr_t that(std::static_pointer_cast<LLScriptEditorWSServer>(shared_from_this())); + + U32 connection_id = script_connection->getConnectionID(); + + script_connection->registerMethod("language.syntax.id", + [that](const std::string&, const LLSD&, const LLSD&) -> LLSD + { + auto server = that.lock(); + if (server) + { + return server->handleLanguageIdRequest(); + } + return LLSD(); + }); + script_connection->registerMethod("language.syntax", + [that](const std::string&, const LLSD&, const LLSD& params) + { + auto server = that.lock(); + if (server) + { + return server->handleSyntaxRequest(params); + } + return LLSD(); + }); + script_connection->registerMethod("script.subscribe", + [that, connection_id](const std::string&, const LLSD&, const LLSD& params) -> LLSD + { + auto server = that.lock(); + if (server) + { + return server->handleScriptSubscribe(connection_id, params); + } + return LLSD(); + }); + script_connection->registerMethod("script.unsubscribe", [](const std::string&, const LLSD&, const LLSD& params) -> LLSD + { // this is a notification, no response expected + return LLSD(); + }); + script_connection->registerMethod("script.list", + [that](const std::string&, const LLSD&, const LLSD& params) -> LLSD + { + auto server = that.lock(); + if (server) + { + return server->handleFileWatcherFileListRequest(); + } + return LLSD(); + }); + // script_connection->registerMethod("language.syntax", ) + } +} + +void LLScriptEditorWSServer::broadcastLanguageChange() +{ + LLUUID syntax_id = LLSyntaxIdLSL::instance().getSyntaxID(); + + if (syntax_id != mLastSyntaxId) + { + mLastSyntaxId = syntax_id; + LLSD params; + params["id"] = syntax_id; + + if (isRunning()) + { + broadcastNotification("language.syntax.change", params); + } + } +} + +LLSD LLScriptEditorWSServer::handleLanguageIdRequest() const +{ + LLSD response; + + response["id"] = mLastSyntaxId; + return response; +} + +LLSD LLScriptEditorWSServer::handleSyntaxRequest(const LLSD& params) const +{ + LLSD response(LLSD::emptyMap()); + std::string category = params["kind"].asString(); + + if (category.empty()) + { + response["error"] = "No syntax category specified"; + response["success"] = false; + return response; + } + + response["id"] = mLastSyntaxId; + if (category == "defs.lua") + { + response["defs"] = LLSyntaxLua::instance().getTypesXML(); + response["success"] = response["defs"].isDefined(); + } + else if (category == "defs.lsl") + { + response["defs"] = LLSyntaxIdLSL::instance().getKeywordsXML(); + response["success"] = response["defs"].isDefined(); + } + else + { + response["error"] = "Unknown syntax category requested"; + response["success"] = false; + } + return response; +} + +LLSD LLScriptEditorWSServer::handleScriptSubscribe(U32 connection_id, const LLSD& params) +{ + LLSD response(LLSD::emptyMap()); + + std::string script_id = params["script_id"].asString(); + std::string script_name = params["script_name"].asString(); + std::string language = params["script_language"].asString(); + + SubscriptionError_t result = updateScriptSubscription(script_id, connection_id); + + response["script_id"] = script_id; + response["success"] = (result == SUBSCRIPTION_SUCCESS); + response["status"] = result; + + LL_WARNS_IF(result != SUBSCRIPTION_SUCCESS, "ScriptEditorWS") + << "Script connect request for script " << script_id << " failed with status " << result << LL_ENDL; + switch (result) + { + case SUBSCRIPTION_SUCCESS: + response["message"] = "OK"; + break; + case SUBSCRIPTION_INVALID_EDITOR: + response["message"] = "Invalid editor handle"; + break; + case SUBSCRIPTION_INVALID_SUBSCRIPTION: + response["message"] = "No subscription found for script"; + break; + case SUBSCRIPTION_ALREADY_SUBSCRIBED: + response["message"] = "Script already subscribed"; + break; + case SUBSCRIPTION_INTERNAL_ERROR: + response["message"] = "Internal server error"; + break; + } + + if (result == SUBSCRIPTION_SUCCESS) + { + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end()) + { + LLViewerObject* object = gObjectList.findObject((*it).second.mObjectID); + response["object_id"] = (*it).second.mObjectID; + //response["object_name"] = object ? object->getName() : "Unknown"; + response["item_id"] = (*it).second.mItemID; + } + } + + return response; +} + +LLSD LLScriptEditorWSServer::handleScriptUnsubscribe(U32 connection_id, const LLSD& params) +{ + std::string script_id = params["script_id"].asString(); + + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end() && (it->second.mConnectionID == connection_id)) + { + unsubscribeEditor(script_id); + } + return LLSD(); +} + +LLSD LLScriptEditorWSServer::handleFileWatcherFileListRequest() const +{ + LLSD response; + + response["temp_dir"] = LLFile::tmpdir(); + + // Add array of script_id's from active scripts + LLSD script_ids_array = LLSD::emptyArray(); + for (const auto& [script_id, subinfo] : mSubscriptions) + { + script_ids_array.append(script_id); + } + response["script_ids"] = script_ids_array; + + response["success"] = true; + + return response; +} + +void LLScriptEditorWSServer::notifyScript(const std::string& script_id, const std::string &method, const LLSD& message) const +{ + auto it = mSubscriptions.find(script_id); + if (it != mSubscriptions.end()) + { + auto connection = it->second.mConnection.lock(); + if (connection) + { + connection->notify(method, message); + } + } +} + + +void LLScriptEditorWSServer::sendUnsubscribeScriptEditor(const std::string& script_id) +{ + LLSD params; + params["script_id"] = script_id; + + notifyScript(script_id, "script.unsubscribe", params); +} + +void LLScriptEditorWSServer::sendCompileResults(const std::string &script_id, const LLSD &results) const +{ + LLHandle<LLPanel> editor_handle = findEditorForScript(script_id); + if (editor_handle.isDead()) + { + return; + } + LLScriptEdContainer* editor = dynamic_cast<LLScriptEdContainer*>(editor_handle.get()); + if (!editor) + { + return; + } + LLScriptEdCore* core = editor->getScriptEdCore(); + bool is_lua = core && (core->isLuauLanguage()); + + LLSD params; + params["script_id"] = script_id; + params["success"] = results["compiled"].asBoolean(); + params["running"] = results["is_running"].asBoolean(); + if (results.has("errors")) + { + params["errors"] = LLSD::emptyArray(); + + if (is_lua) + { // lua errors: ":line: message", line is 1-based + const static boost::regex lua_err_regex(R"(^[^:]*:(\d+): (.+)$)"); + + for (const auto& err : llsd::inArray(results["errors"])) + { + boost::smatch match; + LLSD err_entry; + + err_entry["column"] = 0; // TODO: Lua compiler does not provide column info + err_entry["level"] = "ERROR"; + + if (boost::regex_match(err.asString(), match, lua_err_regex)) + { + S32 line_number = std::stoi(match[1].str()); + std::string message = match[2].str(); + + err_entry["row"] = line_number; + err_entry["message"] = message; + } + else + { + err_entry["row"] = 0; + err_entry["message"] = err.asString(); + } + params["errors"].append(err_entry); + } + } + else + { // lsl errors: "(line, column) : SEVERITY : message", line and column are 0-based + static const boost::regex lsl_err_regex(R"(\((\d+), (\d+)\) : ([^:]+) : (.+))"); + + for (const auto& err : llsd::inArray(results["errors"])) + { + boost::smatch match; + LLSD err_entry; + + if (boost::regex_match(err.asString(), match, lsl_err_regex)) + { + S32 line_number = std::stoi(match[1].str()); + S32 col_number = std::stoi(match[2].str()); + std::string severity = match[3].str(); + std::string message = match[4].str(); + + err_entry["row"] = line_number + 1; + err_entry["column"] = col_number + 1; + err_entry["level"] = severity; + err_entry["message"] = message; + err_entry["format"] = "lsl"; + } + else + { + err_entry["row"] = 0; + err_entry["column"] = 0; + err_entry["level"] = "ERROR"; + err_entry["message"] = err.asString(); + err_entry["format"] = "lsl"; + } + params["errors"].append(err_entry); + } + } + } + + notifyScript(script_id, "script.compiled", params); +} + +void LLScriptEditorWSServer::forwardChatToIDE(const LLChat& chat_msg) const +{ + auto it = std::find_if(mSubscriptions.begin(), mSubscriptions.end(), + [&chat_msg](const auto& pair) { return (pair.second.mObjectID == chat_msg.mFromID); }); + + if (it == mSubscriptions.end()) + { // Not a script we are tracking + return; + } + + bool is_error = false; + std::string error_message; + std::string object_name; + std::string script_name; + S32 line_number = 0; + // We have at least one script from this object, we will forward the message to the IDE + // but first we need to see if it is a runtime error + std::vector<std::string> lines = LLStringUtil::getTokens(chat_msg.mText, "\n"); + // If this is a runtime error, the first line will look like: "<Object Name> [script:<Script Name>] Script run-time error" + static const std::string runtime_error_marker = "Script run-time error"; + if (!lines.empty() && std::equal(runtime_error_marker.rbegin(), runtime_error_marker.rend(), lines.front().rbegin())) + { + is_error = true; + std::string first_line = lines.front(); + + // Extract the object and script name from the first line + static const boost::regex RUNTIME_ERR_REGEX_FLEX(R"(^(.+?)\s+\[script:([^\]]+)\]\s+Script run-time error)"); + boost::smatch m; + + S32 remove_count = 0; + if (boost::regex_match(first_line, m, RUNTIME_ERR_REGEX_FLEX)) + { + object_name = m[1].str(); + script_name = m[2].str(); + remove_count++; + } + + // TODO: Build an actual error message to forward to the external editor + // Explaination: + // Well! Heck! + // As it turns out, the complete error message arrives as either two or three + // separate chat messages from the server. + // 2 if the script is LSL or if it is Lua but not owned by the editing agent + // 3 if the script is Lua and owned by the editing agent. + // + // Message 1: <Object Name> [script:<Script Name>] Script run-time error + // Message 2: <runtime error> + // Message 3: <script>:<line>: <actual error message>\n + // <call stack> + // + // These need to be compositited into a single error message to send to the IDE. + // + //if (lines.size() > 1) + //{ // The second line is the actual error message + // error_message = lines[1]; + // remove_count++; + // if ((error_message == "runtime error") && (lines.size() > 2)) + // { // If the error message is just "runtime error", the next line might actually be the real message: + // // "lua_script:7: attempt to perform arithmetic (sub) on nil" + // static const boost::regex LUA_ERROR_REGEX(R"(^(.+?):(\d+):\s*(.+)$)"); + // + // if (boost::regex_match(first_line, m, RUNTIME_ERR_REGEX_FLEX)) + // { + // line_number = std::stoi(m[2].str()); + // error_message = m[3].str(); + // remove_count++; + // } + // } + // else + // { + // error_message = "Unknown script runtime error"; + // } + //} + //else + //{ + // error_message = "Unknown script runtime error"; + //} + if (lines.size() > remove_count) + { // The rest of the lines may contain a stack trace + lines.erase(lines.begin(), lines.begin() + remove_count); + } + else + { + lines.clear(); + } + + // We should also check that the script name matches one of our subscriptions + if (!script_name.empty() && (it->second.mScriptName != script_name)) + { // right object, wrong script + auto sit = std::find_if(mSubscriptions.begin(), mSubscriptions.end(), + [&chat_msg, &script_name](const auto& pair) + { + return (pair.second.mScriptName == script_name) && (pair.second.mObjectID == chat_msg.mFromID); + }); + if (sit != mSubscriptions.end()) + { // We have a better match + it = sit; + } + } + } + std::string script_id = it->first; + LLSD message; + message["script_id"] = script_id; + message["object_id"] = chat_msg.mFromID; + message["object_name"] = chat_msg.mFromName; + message["message"] = chat_msg.mText; + + if (is_error) + { + message["error"] = error_message; + message["line"] = line_number; + if (!lines.empty()) + { + message["stack"] = LLSD::emptyArray(); + for (const auto& line : lines) + { + message["stack"].append(line); + } + } + } + + if (!it->second.mConnection.expired()) + { + it->second.mConnection.lock()->notify(is_error ? "runtime.error" : "runtime.debug", message); + } +} + +//======================================================================== +U32 LLScriptEditorWSConnection::sNextConnectionID = 1; + +std::shared_ptr<LLScriptEditorWSServer> LLScriptEditorWSConnection::getServer() const +{ + return std::static_pointer_cast<LLScriptEditorWSServer>(mOwningServer.lock()); +} + +void LLScriptEditorWSConnection::onOpen() +{ + // Call parent class to set up JSON-RPC infrastructure + LLJSONRPCConnection::onOpen(); + + LL_INFOS("ScriptEditorWS") << "Script editor JSON-RPC connection opened" << LL_ENDL; + + // Build hello data + LLSD handshake; + handshake["server_version"] = "1.0.0"; + handshake["protocol_version"] = "1.0"; + handshake["viewer_name"] = LLVersionInfo::instance().getChannel(); + handshake["viewer_version"] = LLVersionInfo::instance().getVersion(); + + handshake["agent_id"] = gAgent.getID(); + handshake["agent_name"] = gAgentUsername; + + std::string challenge_file = generateChallenge(); + if (!challenge_file.empty()) + { + handshake["challenge"] = challenge_file; + } + + LLSD languages = LLSD::emptyArray(); + languages.append("lsl"); + languages.append("luau"); + handshake["languages"] = languages; + handshake["syntax_id"] = LLSyntaxIdLSL::instance().getSyntaxID(); + + // Features object + LLSD features; + features["live_sync"] = true; + features["compilation"] = true; + handshake["features"] = features; + + wptr_t that = shared_from_this(); + + // Send session.handshake method call and the response + call("session.handshake", handshake, [that](const LLSD& result, const LLSD& error) { + if (error.isUndefined()) + { + auto self = that.lock(); + if (self) + { + self->handleHandshakeResponse(result); + } + } + else + { + LL_WARNS("ScriptEditorWS") << "Handshake failed: " + << error["message"].asString() << LL_ENDL; + } + }); + + LL_INFOS("ScriptEditorWS") << "Sent handshake call to new editor client" << LL_ENDL; +} + +void LLScriptEditorWSConnection::onClose() +{ + // Call parent class to clean up JSON-RPC infrastructure + LLJSONRPCConnection::onClose(); + mOwningServer.reset(); + + // Clean up handshake response data + mClientName.clear(); + mClientVersion.clear(); + mProtocolVersion.clear(); + mScriptName.clear(); + mScriptLanguage.clear(); + mLanguages.clear(); + mFeatures.clear(); +} + +void LLScriptEditorWSConnection::sendDisconnect(S32 reason, const std::string& message) +{ + LL_INFOS("ScriptEditorWS") << "Sending disconnect to client: " << message << LL_ENDL; + LLSD params; + params["reason"] = reason; + params["message"] = message; + notify("session.disconnect", params); + closeConnection(1000, message); +} + +void LLScriptEditorWSConnection::handleHandshakeResponse(const LLSD& result) +{ + LL_INFOS("ScriptEditorWS") << "Processing handshake response from client" << LL_ENDL; + + // Extract and validate client information + mClientName = result["client_name"].asString(); + mClientVersion = result["client_version"].asString(); + mProtocolVersion = result["protocol_version"].asString(); + + if (mChallenge.notNull()) + { + // Validate challenge response + bool valid_response = (result.has("challenge_response") && + (result["challenge_response"].asUUID() == mChallenge)); + + LLFile::remove(mChallengeFile); + mChallengeFile.clear(); + mChallenge.setNull(); + if (!valid_response) + { + LL_WARNS("ScriptEditorWS") << "Invalid or missing challenge response from client" << LL_ENDL; + sendDisconnect(REASON_PROTOCOL_ERROR, "Invalid challenge response"); + return; + } + } + LLUUID challenge_response = result["challenge_response"].asUUID(); + + // Validate protocol compatibility + if (mProtocolVersion != "1.0") + { + LL_WARNS("ScriptEditorWS") << "Protocol version mismatch. Expected: 1.0, Got: " + << mProtocolVersion << LL_ENDL; + } + + // Store script information if provided + mScriptName = result["script_name"].asString(); + mScriptLanguage = result["script_language"].asString(); + + // Store supported languages + for (const auto& lang : llsd::inArray( result["languages"])) + { + if (lang.isString()) + { + mLanguages.insert(lang.asString()); + } + } + + for (const auto& [feature, enabled] : llsd::inMap(result["features"])) + { + if (enabled.asBoolean()) + { + mFeatures.insert(feature); + } + } + + if (mChallenge.notNull()) + { + // Remove temporary challenge file + LLFile::remove(mChallengeFile); + mChallenge.setNull(); + mChallengeFile.clear(); + } + + notify("session.ok"); + + LL_INFOS("ScriptEditorWS") << "Handshake completed successfully." << LL_ENDL; +} + +std::string LLScriptEditorWSConnection::generateChallenge() +{ + mChallenge.generate(); + + mChallengeFile = std::string(LLFile::tmpdir()) + "sl_script_challenge.tmp"; + + llofstream file(mChallengeFile.c_str()); + if (!file.is_open()) + { + LL_WARNS() << "Unable to open challenge file: " << mChallengeFile << LL_ENDL; + mChallenge.setNull(); + mChallengeFile.clear(); + return std::string(); + } + + file << mChallenge; + file.close(); + + return mChallengeFile; +} diff --git a/indra/newview/llscripteditorws.h b/indra/newview/llscripteditorws.h new file mode 100644 index 0000000000..c8898c66a7 --- /dev/null +++ b/indra/newview/llscripteditorws.h @@ -0,0 +1,230 @@ +/** + * @file llscripteditorws.h + * @brief WebSocket server and connection classes for external script editor integration + * + * $LicenseInfo:firstyear=2025&license=viewerlgpl$ + * Second Life Viewer Source Code + * Copyright (C) 2025, Linden Research, Inc. + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; + * version 2.1 of the License only. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA + * + * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA + * $/LicenseInfo$ + */ + +#pragma once + +#include "lljsonrpcws.h" +#include "llsd.h" +#include "lluuid.h" +#include "llhandle.h" +#include "lltimer.h" + +#include <memory> +#include <string> +#include <map> +#include <set> + +// Forward declarations +class LLLiveLSLEditor; +class LLScriptEdContainer; +class LLScriptEditorWSServer; +class LLChat; +class LLPanel; + +class LLScriptEditorWSConnection : public LLJSONRPCConnection, public std::enable_shared_from_this<LLScriptEditorWSConnection> +{ +public: + using ptr_t = std::shared_ptr<LLScriptEditorWSConnection>; + using wptr_t = std::weak_ptr<LLScriptEditorWSConnection>; + + enum DisconnectReason + { + REASON_NORMAL = 0, + REASON_EDITOR_CLOSED = 1, + REASON_PROTOCOL_ERROR = 2, + REASON_TIMEOUT = 3, + REASON_INTERNAL_ERROR = 4 + }; + + LLScriptEditorWSConnection(const LLWebsocketMgr::WSServer::ptr_t server, const LLWebsocketMgr::connection_h& handle) : + LLJSONRPCConnection(server, handle) + { + mConnectionID = sNextConnectionID++; + } + + ~LLScriptEditorWSConnection() override = default; + + U32 getConnectionID() const { return mConnectionID; } + + // Connection lifecycle overrides + void onOpen() override; + void onClose() override; + + void sendDisconnect(S32 reason = 0, const std::string& message = "Goodbye"); + +private: + using string_set_t = std::set<std::string>; + /** + * @brief Handle the handshake response from the client + * @param result The response data from the client containing client information + */ + void handleHandshakeResponse(const LLSD& result); + std::string generateChallenge(); + + LLScriptEdContainer* getEditor() const; + std::shared_ptr<LLScriptEditorWSServer> getServer() const; + + U32 mConnectionID{ 0 }; ///< Unique identifier for this connection + + // Client handshake response data + std::string mClientName; ///< Name of the external editor client + std::string mClientVersion; ///< Version of the external editor client + std::string mProtocolVersion; ///< JSON-RPC protocol version supported by client + std::string mScriptName; ///< Name of the script being edited + std::string mScriptLanguage; ///< Programming language of the script (lsl, luau, etc.) + string_set_t mLanguages; ///< Set of supported scripting languages + string_set_t mFeatures; ///< Active client features (live_sync, compilation, etc.) + LLUUID mChallenge; + std::string mChallengeFile; ///< Temporary file used for challenge-response verification + + static U32 sNextConnectionID; +}; + +/** + * @class LLScriptEditorWSServer + * @brief JSON-RPC 2.0 WebSocket server for external script editor integration + * + * This server extends the JSON-RPC server to provide specialized functionality + * for external script editor integration. It manages WebSocket connections from + * external script editors and provides a structured JSON-RPC 2.0 interface + * between the Second Life viewer's script editing functionality and external + * development tools. + * + * ## Architecture + * + * The server acts as a JSON-RPC communication hub between: + * - LLLiveLSLEditor instances (in-world script editing) + * - External script editors (VS Code, Atom, Sublime Text, etc.) + * - Script compilation and save services + * + * ## Usage + * + * @code + * // Create and start the JSON-RPC server + * auto server = std::make_shared<LLScriptEditorWSServer>("script_editor_server", 9020); + * LLWebsocketMgr::getInstance()->addServer(server); + * LLWebsocketMgr::getInstance()->startServer("script_editor_server"); + * + * // Associate with an LSL editor + * server->associateEditor(editor_handle, script_id); + * @endcode + * + * ## Security Considerations + * + * - Server binds to localhost only by default for security + * - JSON-RPC 2.0 structured protocol with validation + * - Rate limiting handled by base JSON-RPC server + * - Error handling with standardized JSON-RPC error codes + */ +class LLScriptEditorWSServer : public LLJSONRPCServer +{ +public: + enum SubscriptionError_t + { + SUBSCRIPTION_SUCCESS = 0, + SUBSCRIPTION_INVALID_EDITOR, + SUBSCRIPTION_INVALID_SUBSCRIPTION, + SUBSCRIPTION_ALREADY_SUBSCRIBED, + SUBSCRIPTION_INTERNAL_ERROR + }; + + static constexpr char const* DEFAULT_SERVER_NAME = "script_editor_server"; + static constexpr U16 DEFAULT_SERVER_PORT = 9020; + + using ptr_t = std::shared_ptr<LLScriptEditorWSServer>; + using wptr_t = std::weak_ptr<LLScriptEditorWSServer>; + + LLScriptEditorWSServer(const std::string& name, U16 port, bool local_only = true); + + virtual ~LLScriptEditorWSServer() = default; + + static LLScriptEditorWSServer::ptr_t getServer(); + + void onStarted() override; + void onStopped() override; + void onConnectionOpened(const LLWebsocketMgr::WSConnection::ptr_t& connection) override; + void onConnectionClosed(const LLWebsocketMgr::WSConnection::ptr_t& connection) override; + + bool subscribeScriptEditor(const LLUUID& object_id, const LLUUID& item_id, std::string_view script_name, + const LLHandle<LLPanel>& editor_handle, const std::string &script_id); + void unsubscribeEditor(const std::string &script_id); + + void notifyScript(const std::string& script_id, const std::string& method, const LLSD& message) const; + void sendUnsubscribeScriptEditor(const std::string& script_id); + void sendCompileResults(const std::string& script_id, const LLSD& results) const; + + LLHandle<LLPanel> findEditorForScript(const std::string& script_id) const; + + void forwardChatToIDE(const LLChat& chat_msg) const; + + std::set<std::string> getActiveScripts() const; + +protected: + LLWebsocketMgr::WSConnection::ptr_t connectionFactory(LLWebsocketMgr::WSServer::ptr_t server, + LLWebsocketMgr::connection_h handle) override; + + void setupConnectionMethods(LLJSONRPCConnection::ptr_t connection) override; + + void broadcastLanguageChange(); + + LLSD handleLanguageIdRequest() const; + LLSD handleSyntaxRequest(const LLSD ¶ms) const; + LLSD handleScriptSubscribe(U32 connection_id, const LLSD& params); + LLSD handleScriptUnsubscribe(U32 connection_id, const LLSD& params); + LLSD handleFileWatcherFileListRequest() const; + +private: + struct EditorSubscription + { + EditorSubscription(const LLUUID &object_id, const LLUUID &item_id, std::string_view script_name, LLHandle<LLPanel> editor_handle): + mObjectID(object_id), + mItemID(item_id), + mScriptName(script_name), + mEditorHandle(editor_handle) + {} + U32 mConnectionID{ 0 }; + LLUUID mObjectID; + LLUUID mItemID; + std::string mScriptName; + LLScriptEditorWSConnection::wptr_t mConnection; + LLHandle<LLPanel> mEditorHandle; + }; + using subscriptions_t = std::unordered_map<std::string, EditorSubscription>; + + SubscriptionError_t updateScriptSubscription(const std::string &script_id, U32 connection_id); + void unsubscribeConnection(U32 connection_id); + + subscriptions_t mSubscriptions; + std::map<U32, LLScriptEditorWSConnection::wptr_t> mActiveConnections; + + boost::signals2::connection mLanguageChangeSignal; + LLUUID mLastSyntaxId; + + + LLTimer mCleanupTimer; + static constexpr F32 CLEANUP_INTERVAL = 60.0f; // seconds + static constexpr F32 CONNECTION_TIMEOUT = 300.0f; // 5 minutes +}; diff --git a/indra/newview/llstartup.cpp b/indra/newview/llstartup.cpp index 2cb2a7f8d5..00a34c802b 100644 --- a/indra/newview/llstartup.cpp +++ b/indra/newview/llstartup.cpp @@ -2753,179 +2753,145 @@ void use_circuit_callback(void**, S32 result) void register_viewer_callbacks(LLMessageSystem* msg) { - msg->setHandlerFuncFast(_PREHASH_LayerData, process_layer_data ); - msg->setHandlerFuncFast(_PREHASH_ObjectUpdate, process_object_update ); - msg->setHandlerFunc("ObjectUpdateCompressed", process_compressed_object_update ); - msg->setHandlerFunc("ObjectUpdateCached", process_cached_object_update ); + msg->setHandlerFuncFast(_PREHASH_LayerData, process_layer_data); + msg->setHandlerFuncFast(_PREHASH_ObjectUpdate, process_object_update); + msg->setHandlerFuncFast(_PREHASH_ObjectUpdateCompressed, process_compressed_object_update); + msg->setHandlerFuncFast(_PREHASH_ObjectUpdateCached, process_cached_object_update); msg->setHandlerFuncFast(_PREHASH_ImprovedTerseObjectUpdate, process_terse_object_update_improved ); - msg->setHandlerFunc("SimStats", process_sim_stats); - msg->setHandlerFuncFast(_PREHASH_HealthMessage, process_health_message ); + msg->setHandlerFuncFast(_PREHASH_SimStats, process_sim_stats); + msg->setHandlerFuncFast(_PREHASH_HealthMessage, process_health_message); msg->setHandlerFuncFast(_PREHASH_EconomyData, process_economy_data); - msg->setHandlerFunc("RegionInfo", LLViewerRegion::processRegionInfo); + msg->setHandlerFuncFast(_PREHASH_RegionInfo, LLViewerRegion::processRegionInfo); - msg->setHandlerFuncFast(_PREHASH_ChatFromSimulator, process_chat_from_simulator); - msg->setHandlerFuncFast(_PREHASH_KillObject, process_kill_object, NULL); - msg->setHandlerFuncFast(_PREHASH_SimulatorViewerTimeMessage, process_time_synch, NULL); + msg->setHandlerFuncFast(_PREHASH_ChatFromSimulator, process_chat_from_simulator); + msg->setHandlerFuncFast(_PREHASH_KillObject, process_kill_object); + msg->setHandlerFuncFast(_PREHASH_SimulatorViewerTimeMessage,process_time_synch); msg->setHandlerFuncFast(_PREHASH_EnableSimulator, process_enable_simulator); msg->setHandlerFuncFast(_PREHASH_DisableSimulator, process_disable_simulator); - msg->setHandlerFuncFast(_PREHASH_KickUser, process_kick_user, NULL); + msg->setHandlerFuncFast(_PREHASH_KickUser, process_kick_user); - msg->setHandlerFunc("CrossedRegion", process_crossed_region); - msg->setHandlerFuncFast(_PREHASH_TeleportFinish, process_teleport_finish); + msg->setHandlerFuncFast(_PREHASH_CrossedRegion, process_crossed_region); + msg->setHandlerFuncFast(_PREHASH_TeleportFinish, process_teleport_finish); - msg->setHandlerFuncFast(_PREHASH_AlertMessage, process_alert_message); - msg->setHandlerFunc("AgentAlertMessage", process_agent_alert_message); - msg->setHandlerFuncFast(_PREHASH_MeanCollisionAlert, process_mean_collision_alert_message, NULL); - msg->setHandlerFunc("ViewerFrozenMessage", process_frozen_message); + msg->setHandlerFuncFast(_PREHASH_AlertMessage, process_alert_message); + msg->setHandlerFuncFast(_PREHASH_AgentAlertMessage, process_agent_alert_message); + msg->setHandlerFuncFast(_PREHASH_MeanCollisionAlert, process_mean_collision_alert_message); + msg->setHandlerFuncFast(_PREHASH_ViewerFrozenMessage, process_frozen_message); - msg->setHandlerFuncFast(_PREHASH_NameValuePair, process_name_value); - msg->setHandlerFuncFast(_PREHASH_RemoveNameValuePair, process_remove_name_value); - msg->setHandlerFuncFast(_PREHASH_AvatarAnimation, process_avatar_animation); - msg->setHandlerFuncFast(_PREHASH_ObjectAnimation, process_object_animation); - msg->setHandlerFuncFast(_PREHASH_AvatarAppearance, process_avatar_appearance); - msg->setHandlerFuncFast(_PREHASH_CameraConstraint, process_camera_constraint); - msg->setHandlerFuncFast(_PREHASH_AvatarSitResponse, process_avatar_sit_response); - msg->setHandlerFunc("SetFollowCamProperties", process_set_follow_cam_properties); - msg->setHandlerFunc("ClearFollowCamProperties", process_clear_follow_cam_properties); + msg->setHandlerFuncFast(_PREHASH_NameValuePair, process_name_value); + msg->setHandlerFuncFast(_PREHASH_RemoveNameValuePair, process_remove_name_value); + msg->setHandlerFuncFast(_PREHASH_AvatarAnimation, process_avatar_animation); + msg->setHandlerFuncFast(_PREHASH_ObjectAnimation, process_object_animation); + msg->setHandlerFuncFast(_PREHASH_AvatarAppearance, process_avatar_appearance); + msg->setHandlerFuncFast(_PREHASH_CameraConstraint, process_camera_constraint); + msg->setHandlerFuncFast(_PREHASH_AvatarSitResponse, process_avatar_sit_response); + msg->setHandlerFuncFast(_PREHASH_SetFollowCamProperties, process_set_follow_cam_properties); + msg->setHandlerFuncFast(_PREHASH_ClearFollowCamProperties, process_clear_follow_cam_properties); msg->setHandlerFuncFast(_PREHASH_ImprovedInstantMessage, process_improved_im); msg->setHandlerFuncFast(_PREHASH_ScriptQuestion, process_script_question); - msg->setHandlerFuncFast(_PREHASH_ObjectProperties, LLSelectMgr::processObjectProperties, NULL); - msg->setHandlerFuncFast(_PREHASH_ObjectPropertiesFamily, LLSelectMgr::processObjectPropertiesFamily, NULL); - msg->setHandlerFunc("ForceObjectSelect", LLSelectMgr::processForceObjectSelect); + msg->setHandlerFuncFast(_PREHASH_ObjectProperties, LLSelectMgr::processObjectProperties); + msg->setHandlerFuncFast(_PREHASH_ObjectPropertiesFamily, LLSelectMgr::processObjectPropertiesFamily); + msg->setHandlerFuncFast(_PREHASH_ForceObjectSelect, LLSelectMgr::processForceObjectSelect); - msg->setHandlerFuncFast(_PREHASH_MoneyBalanceReply, process_money_balance_reply, NULL); - msg->setHandlerFuncFast(_PREHASH_CoarseLocationUpdate, LLWorld::processCoarseUpdate, NULL); - msg->setHandlerFuncFast(_PREHASH_ReplyTaskInventory, LLViewerObject::processTaskInv, NULL); - msg->setHandlerFuncFast(_PREHASH_DerezContainer, process_derez_container, NULL); - msg->setHandlerFuncFast(_PREHASH_ScriptRunningReply, - &LLLiveLSLEditor::processScriptRunningReply); + msg->setHandlerFuncFast(_PREHASH_MoneyBalanceReply, process_money_balance_reply); + msg->setHandlerFuncFast(_PREHASH_CoarseLocationUpdate, LLWorld::processCoarseUpdate); + msg->setHandlerFuncFast(_PREHASH_ReplyTaskInventory, LLViewerObject::processTaskInv); + msg->setHandlerFuncFast(_PREHASH_DerezContainer, process_derez_container); + msg->setHandlerFuncFast(_PREHASH_ScriptRunningReply, LLLiveLSLEditor::processScriptRunningReply); - msg->setHandlerFuncFast(_PREHASH_DeRezAck, process_derez_ack); + msg->setHandlerFuncFast(_PREHASH_DeRezAck, process_derez_ack); - msg->setHandlerFunc("LogoutReply", process_logout_reply); + msg->setHandlerFuncFast(_PREHASH_LogoutReply, process_logout_reply); - //msg->setHandlerFuncFast(_PREHASH_AddModifyAbility, - // &LLAgent::processAddModifyAbility); - //msg->setHandlerFuncFast(_PREHASH_RemoveModifyAbility, - // &LLAgent::processRemoveModifyAbility); - msg->setHandlerFuncFast(_PREHASH_AgentDataUpdate, - &LLAgent::processAgentDataUpdate); - msg->setHandlerFuncFast(_PREHASH_AgentGroupDataUpdate, - &LLAgent::processAgentGroupDataUpdate); - msg->setHandlerFunc("AgentDropGroup", - &LLAgent::processAgentDropGroup); + //msg->setHandlerFuncFast(_PREHASH_AddModifyAbility, LLAgent::processAddModifyAbility); + //msg->setHandlerFuncFast(_PREHASH_RemoveModifyAbility, LLAgent::processRemoveModifyAbility); + msg->setHandlerFuncFast(_PREHASH_AgentDataUpdate, LLAgent::processAgentDataUpdate); + msg->setHandlerFuncFast(_PREHASH_AgentGroupDataUpdate, LLAgent::processAgentGroupDataUpdate); + msg->setHandlerFuncFast(_PREHASH_AgentDropGroup, LLAgent::processAgentDropGroup); // land ownership messages - msg->setHandlerFuncFast(_PREHASH_ParcelOverlay, - LLViewerParcelMgr::processParcelOverlay); - msg->setHandlerFuncFast(_PREHASH_ParcelProperties, - LLViewerParcelMgr::processParcelProperties); - msg->setHandlerFunc("ParcelAccessListReply", - LLViewerParcelMgr::processParcelAccessListReply); - msg->setHandlerFunc("ParcelDwellReply", - LLViewerParcelMgr::processParcelDwellReply); + msg->setHandlerFuncFast(_PREHASH_ParcelOverlay, LLViewerParcelMgr::processParcelOverlay); + msg->setHandlerFuncFast(_PREHASH_ParcelProperties, LLViewerParcelMgr::processParcelProperties); + msg->setHandlerFuncFast(_PREHASH_ParcelAccessListReply, LLViewerParcelMgr::processParcelAccessListReply); + msg->setHandlerFuncFast(_PREHASH_ParcelDwellReply, LLViewerParcelMgr::processParcelDwellReply); - msg->setHandlerFunc("AvatarPropertiesReply", - &LLAvatarPropertiesProcessor::processAvatarLegacyPropertiesReply); - msg->setHandlerFunc("AvatarInterestsReply", - &LLAvatarPropertiesProcessor::processAvatarInterestsReply); - msg->setHandlerFunc("AvatarGroupsReply", - &LLAvatarPropertiesProcessor::processAvatarGroupsReply); - msg->setHandlerFunc("AvatarNotesReply", - &LLAvatarPropertiesProcessor::processAvatarNotesReply); - msg->setHandlerFunc("AvatarPicksReply", - &LLAvatarPropertiesProcessor::processAvatarPicksReply); - msg->setHandlerFunc("AvatarClassifiedReply", - &LLAvatarPropertiesProcessor::processAvatarClassifiedsReply); + msg->setHandlerFuncFast(_PREHASH_AvatarPropertiesReply, LLAvatarPropertiesProcessor::processAvatarLegacyPropertiesReply); + msg->setHandlerFuncFast(_PREHASH_AvatarInterestsReply, LLAvatarPropertiesProcessor::processAvatarInterestsReply); + msg->setHandlerFuncFast(_PREHASH_AvatarGroupsReply, LLAvatarPropertiesProcessor::processAvatarGroupsReply); + msg->setHandlerFuncFast(_PREHASH_AvatarNotesReply, LLAvatarPropertiesProcessor::processAvatarNotesReply); + msg->setHandlerFuncFast(_PREHASH_AvatarPicksReply, LLAvatarPropertiesProcessor::processAvatarPicksReply); + msg->setHandlerFuncFast(_PREHASH_AvatarClassifiedReply, LLAvatarPropertiesProcessor::processAvatarClassifiedsReply); - msg->setHandlerFuncFast(_PREHASH_CreateGroupReply, - LLGroupMgr::processCreateGroupReply); - msg->setHandlerFuncFast(_PREHASH_JoinGroupReply, - LLGroupMgr::processJoinGroupReply); - msg->setHandlerFuncFast(_PREHASH_EjectGroupMemberReply, - LLGroupMgr::processEjectGroupMemberReply); - msg->setHandlerFuncFast(_PREHASH_LeaveGroupReply, - LLGroupMgr::processLeaveGroupReply); - msg->setHandlerFuncFast(_PREHASH_GroupProfileReply, - LLGroupMgr::processGroupPropertiesReply); + msg->setHandlerFuncFast(_PREHASH_CreateGroupReply, LLGroupMgr::processCreateGroupReply); + msg->setHandlerFuncFast(_PREHASH_JoinGroupReply, LLGroupMgr::processJoinGroupReply); + msg->setHandlerFuncFast(_PREHASH_EjectGroupMemberReply, LLGroupMgr::processEjectGroupMemberReply); + msg->setHandlerFuncFast(_PREHASH_LeaveGroupReply, LLGroupMgr::processLeaveGroupReply); + msg->setHandlerFuncFast(_PREHASH_GroupProfileReply, LLGroupMgr::processGroupPropertiesReply); // ratings deprecated - // msg->setHandlerFuncFast(_PREHASH_ReputationIndividualReply, - // LLFloaterRate::processReputationIndividualReply); + //msg->setHandlerFuncFast(_PREHASH_ReputationIndividualReply, LLFloaterRate::processReputationIndividualReply); - msg->setHandlerFunc("ScriptControlChange", - LLAgent::processScriptControlChange ); + msg->setHandlerFuncFast(_PREHASH_ScriptControlChange, LLAgent::processScriptControlChange ); + msg->setHandlerFuncFast(_PREHASH_ViewerEffect, LLHUDManager::processViewerEffect); + msg->setHandlerFuncFast(_PREHASH_GrantGodlikePowers, process_grant_godlike_powers); + msg->setHandlerFuncFast(_PREHASH_GroupAccountSummaryReply, LLPanelGroupLandMoney::processGroupAccountSummaryReply); + msg->setHandlerFuncFast(_PREHASH_GroupAccountDetailsReply, LLPanelGroupLandMoney::processGroupAccountDetailsReply); + msg->setHandlerFuncFast(_PREHASH_GroupAccountTransactionsReply, LLPanelGroupLandMoney::processGroupAccountTransactionsReply); - msg->setHandlerFuncFast(_PREHASH_ViewerEffect, LLHUDManager::processViewerEffect); + msg->setHandlerFuncFast(_PREHASH_UserInfoReply, process_user_info_reply); - msg->setHandlerFuncFast(_PREHASH_GrantGodlikePowers, process_grant_godlike_powers); + msg->setHandlerFuncFast(_PREHASH_RegionHandshake, process_region_handshake); - msg->setHandlerFuncFast(_PREHASH_GroupAccountSummaryReply, - LLPanelGroupLandMoney::processGroupAccountSummaryReply); - msg->setHandlerFuncFast(_PREHASH_GroupAccountDetailsReply, - LLPanelGroupLandMoney::processGroupAccountDetailsReply); - msg->setHandlerFuncFast(_PREHASH_GroupAccountTransactionsReply, - LLPanelGroupLandMoney::processGroupAccountTransactionsReply); + msg->setHandlerFuncFast(_PREHASH_TeleportStart, process_teleport_start); + msg->setHandlerFuncFast(_PREHASH_TeleportProgress, process_teleport_progress); + msg->setHandlerFuncFast(_PREHASH_TeleportFailed, process_teleport_failed); + msg->setHandlerFuncFast(_PREHASH_TeleportLocal, process_teleport_local); - msg->setHandlerFuncFast(_PREHASH_UserInfoReply, - process_user_info_reply); + msg->setHandlerFuncFast(_PREHASH_ImageNotInDatabase, LLViewerTextureList::processImageNotInDatabase); - msg->setHandlerFunc("RegionHandshake", process_region_handshake, NULL); - - msg->setHandlerFunc("TeleportStart", process_teleport_start ); - msg->setHandlerFunc("TeleportProgress", process_teleport_progress); - msg->setHandlerFunc("TeleportFailed", process_teleport_failed, NULL); - msg->setHandlerFunc("TeleportLocal", process_teleport_local, NULL); - - msg->setHandlerFunc("ImageNotInDatabase", LLViewerTextureList::processImageNotInDatabase, NULL); - - msg->setHandlerFuncFast(_PREHASH_GroupMembersReply, - LLGroupMgr::processGroupMembersReply); - msg->setHandlerFunc("GroupRoleDataReply", - LLGroupMgr::processGroupRoleDataReply); - msg->setHandlerFunc("GroupRoleMembersReply", - LLGroupMgr::processGroupRoleMembersReply); - msg->setHandlerFunc("GroupTitlesReply", - LLGroupMgr::processGroupTitlesReply); + msg->setHandlerFuncFast(_PREHASH_GroupMembersReply, LLGroupMgr::processGroupMembersReply); + msg->setHandlerFuncFast(_PREHASH_GroupRoleDataReply, LLGroupMgr::processGroupRoleDataReply); + msg->setHandlerFuncFast(_PREHASH_GroupRoleMembersReply, LLGroupMgr::processGroupRoleMembersReply); + msg->setHandlerFuncFast(_PREHASH_GroupTitlesReply, LLGroupMgr::processGroupTitlesReply); // Special handler as this message is sometimes used for group land. - msg->setHandlerFunc("PlacesReply", process_places_reply); - msg->setHandlerFunc("GroupNoticesListReply", LLPanelGroupNotices::processGroupNoticesListReply); + msg->setHandlerFuncFast(_PREHASH_PlacesReply, process_places_reply); + msg->setHandlerFuncFast(_PREHASH_GroupNoticesListReply, LLPanelGroupNotices::processGroupNoticesListReply); - msg->setHandlerFunc("AvatarPickerReply", LLFloaterAvatarPicker::processAvatarPickerReply); + msg->setHandlerFuncFast(_PREHASH_AvatarPickerReply, LLFloaterAvatarPicker::processAvatarPickerReply); - msg->setHandlerFunc("DirPlacesReply", LLPanelDirBrowser::processDirPlacesReply); - msg->setHandlerFunc("DirPeopleReply", LLPanelDirBrowser::processDirPeopleReply); - msg->setHandlerFunc("DirEventsReply", LLPanelDirBrowser::processDirEventsReply); - msg->setHandlerFunc("DirGroupsReply", LLPanelDirBrowser::processDirGroupsReply); - msg->setHandlerFunc("DirClassifiedReply", LLPanelDirBrowser::processDirClassifiedReply); - msg->setHandlerFunc("DirLandReply", LLPanelDirBrowser::processDirLandReply); + msg->setHandlerFuncFast(_PREHASH_DirPlacesReply, LLPanelDirBrowser::processDirPlacesReply); + msg->setHandlerFuncFast(_PREHASH_DirPeopleReply, LLPanelDirBrowser::processDirPeopleReply); + msg->setHandlerFuncFast(_PREHASH_DirEventsReply, LLPanelDirBrowser::processDirEventsReply); + msg->setHandlerFuncFast(_PREHASH_DirGroupsReply, LLPanelDirBrowser::processDirGroupsReply); + msg->setHandlerFuncFast(_PREHASH_DirClassifiedReply, LLPanelDirBrowser::processDirClassifiedReply); + msg->setHandlerFuncFast(_PREHASH_DirLandReply, LLPanelDirBrowser::processDirLandReply); - msg->setHandlerFunc("MapBlockReply", LLWorldMapMessage::processMapBlockReply); - msg->setHandlerFunc("MapItemReply", LLWorldMapMessage::processMapItemReply); - msg->setHandlerFunc("EventInfoReply", LLEventNotifier::processEventInfoReply); + msg->setHandlerFuncFast(_PREHASH_MapBlockReply, LLWorldMapMessage::processMapBlockReply); + msg->setHandlerFuncFast(_PREHASH_MapItemReply, LLWorldMapMessage::processMapItemReply); + msg->setHandlerFuncFast(_PREHASH_EventInfoReply, LLEventNotifier::processEventInfoReply); - msg->setHandlerFunc("PickInfoReply", &LLAvatarPropertiesProcessor::processPickInfoReply); - msg->setHandlerFunc("ClassifiedInfoReply", LLAvatarPropertiesProcessor::processClassifiedInfoReply); - msg->setHandlerFunc("ParcelInfoReply", LLRemoteParcelInfoProcessor::processParcelInfoReply); - msg->setHandlerFunc("ScriptDialog", process_script_dialog); - msg->setHandlerFunc("LoadURL", process_load_url); - msg->setHandlerFunc("ScriptTeleportRequest", process_script_teleport_request); - msg->setHandlerFunc("EstateCovenantReply", process_covenant_reply); + msg->setHandlerFuncFast(_PREHASH_PickInfoReply, LLAvatarPropertiesProcessor::processPickInfoReply); + msg->setHandlerFuncFast(_PREHASH_ClassifiedInfoReply, LLAvatarPropertiesProcessor::processClassifiedInfoReply); + msg->setHandlerFuncFast(_PREHASH_ParcelInfoReply, LLRemoteParcelInfoProcessor::processParcelInfoReply); + msg->setHandlerFuncFast(_PREHASH_ScriptDialog, process_script_dialog); + msg->setHandlerFuncFast(_PREHASH_LoadURL, process_load_url); + msg->setHandlerFuncFast(_PREHASH_ScriptTeleportRequest, process_script_teleport_request); + msg->setHandlerFuncFast(_PREHASH_EstateCovenantReply, process_covenant_reply); // calling cards - msg->setHandlerFunc("OfferCallingCard", process_offer_callingcard); - msg->setHandlerFunc("AcceptCallingCard", process_accept_callingcard); - msg->setHandlerFunc("DeclineCallingCard", process_decline_callingcard); + msg->setHandlerFuncFast(_PREHASH_OfferCallingCard, process_offer_callingcard); + msg->setHandlerFuncFast(_PREHASH_AcceptCallingCard, process_accept_callingcard); + msg->setHandlerFuncFast(_PREHASH_DeclineCallingCard, process_decline_callingcard); - msg->setHandlerFunc("ParcelObjectOwnersReply", LLPanelLandObjects::processParcelObjectOwnersReply); + msg->setHandlerFuncFast(_PREHASH_ParcelObjectOwnersReply, LLPanelLandObjects::processParcelObjectOwnersReply); - msg->setHandlerFunc("InitiateDownload", process_initiate_download); - msg->setHandlerFunc("LandStatReply", LLFloaterTopObjects::handle_land_reply); - msg->setHandlerFunc("GenericMessage", process_generic_message); - msg->setHandlerFunc("GenericStreamingMessage", process_generic_streaming_message); - msg->setHandlerFunc("LargeGenericMessage", process_large_generic_message); + msg->setHandlerFuncFast(_PREHASH_InitiateDownload, process_initiate_download); + msg->setHandlerFuncFast(_PREHASH_LandStatReply, LLFloaterTopObjects::handle_land_reply); + msg->setHandlerFuncFast(_PREHASH_GenericMessage, process_generic_message); + msg->setHandlerFuncFast(_PREHASH_GenericStreamingMessage, process_generic_streaming_message); + msg->setHandlerFuncFast(_PREHASH_LargeGenericMessage, process_large_generic_message); - msg->setHandlerFuncFast(_PREHASH_FeatureDisabled, process_feature_disabled_message); + msg->setHandlerFuncFast(_PREHASH_FeatureDisabled, process_feature_disabled_message); } void asset_callback_nothing(const LLUUID&, LLAssetType::EType, void*, S32) diff --git a/indra/newview/llsyntaxid.cpp b/indra/newview/llsyntaxid.cpp index f89ae00c5b..16274f59bc 100644 --- a/indra/newview/llsyntaxid.cpp +++ b/indra/newview/llsyntaxid.cpp @@ -40,7 +40,8 @@ //----------------------------------------------------------------------------- const std::string SYNTAX_ID_CAPABILITY_NAME = "LSLSyntax"; const std::string SYNTAX_ID_SIMULATOR_FEATURE = "LSLSyntaxId"; -const std::string FILENAME_DEFAULT = "keywords_lsl_default.xml"; +const std::string FILENAME_DEFAULT_LSL = "keywords_lsl_default.xml"; +const std::string FILENAME_DEFAULT_LUA = "keywords_lua_default.xml"; /** * @brief LLSyntaxIdLSL constructor @@ -60,7 +61,7 @@ LLSyntaxIdLSL::LLSyntaxIdLSL() void LLSyntaxIdLSL::buildFullFileSpec() { ELLPath path = mSyntaxId.isNull() ? LL_PATH_APP_SETTINGS : LL_PATH_CACHE; - const std::string filename = mSyntaxId.isNull() ? FILENAME_DEFAULT : "keywords_lsl_" + mSyntaxId.asString() + ".llsd.xml"; + const std::string filename = mSyntaxId.isNull() ? FILENAME_DEFAULT_LSL : "keywords_lsl_" + mSyntaxId.asString() + ".llsd.xml"; mFullFileSpec = gDirUtilp->getExpandedFilename(path, filename); } @@ -147,9 +148,14 @@ void LLSyntaxIdLSL::fetchKeywordsFileCoro(std::string url, std::string fileSpec) if (isSupportedVersion(result)) { - setKeywordsXml(result); - cacheFile(fileSpec, result); - loadKeywordsIntoLLSD(); + // Shuttle this task to the main coro/worker. + // loadKeywordsIntoLLSD will attempt to get a mutex which is not coro aware. + LLAppViewer::instance()->postToMainCoro([this, result, fileSpec]() + { + setKeywordsXml(result); + cacheFile(fileSpec, result); + loadKeywordsIntoLLSD(); + }); } else { @@ -325,3 +331,53 @@ boost::signals2::connection LLSyntaxIdLSL::addSyntaxIDCallback(const syntax_id_c { return mSyntaxIDChangedSignal.connect(cb); } + + + +//----------------------------------------------------------------------------- +// LLSyntaxLua +//----------------------------------------------------------------------------- +LLSyntaxLua::LLSyntaxLua() + : mKeywordsXml(LLSD()) + , mInitialized(false) +{ +} + +void LLSyntaxLua::initialize() +{ + if (mInitialized) return; + + loadDefaultKeywordsIntoLLSD(); + loadLuaTypesIntoLLSD(); + mInitialized = true; +} + +void LLSyntaxLua::loadDefaultKeywordsIntoLLSD() +{ + std::string fullFileSpec = gDirUtilp->getExpandedFilename(LL_PATH_APP_SETTINGS, FILENAME_DEFAULT_LUA); + llifstream file(fullFileSpec.c_str()); + + if (file.good()) + { + LLSD content; + if (LLSDSerialize::fromXML(content, file) != LLSDParser::PARSE_FAILURE) + { + mKeywordsXml = content; + } + } +} + +void LLSyntaxLua::loadLuaTypesIntoLLSD() +{ + std::string fullFileSpec = gDirUtilp->getExpandedFilename(LL_PATH_APP_SETTINGS, "types_lua_default.xml"); + llifstream file(fullFileSpec.c_str()); + + if (file.good()) + { + LLSD content; + if (LLSDSerialize::fromXML(content, file) != LLSDParser::PARSE_FAILURE) + { + mTypesXml = content; + } + } +} diff --git a/indra/newview/llsyntaxid.h b/indra/newview/llsyntaxid.h index a00e9d6390..51103e3396 100644 --- a/indra/newview/llsyntaxid.h +++ b/indra/newview/llsyntaxid.h @@ -41,11 +41,20 @@ class LLSyntaxIdLSL : public LLSingleton<LLSyntaxIdLSL> LLSINGLETON(LLSyntaxIdLSL); friend class fetchKeywordsFileResponder; +public: + using syntax_id_changed_signal_t = boost::signals2::signal<void()>; + using syntax_id_changed_h = boost::signals2::connection; + + void initialize(); + bool keywordFetchInProgress(); + LLSD getKeywordsXML() const { return mKeywordsXml; }; + LLUUID getSyntaxID() const { return mSyntaxId; } + syntax_id_changed_h addSyntaxIDCallback(const syntax_id_changed_signal_t::slot_type& cb); + private: std::set<std::string> mInflightFetches; - typedef boost::signals2::signal<void()> syntax_id_changed_signal_t; syntax_id_changed_signal_t mSyntaxIDChangedSignal; - boost::signals2::connection mRegionChangedCallback; + syntax_id_changed_h mRegionChangedCallback; bool syntaxIdChanged(); bool isSupportedVersion(const LLSD& content); @@ -67,11 +76,24 @@ private: LLSD mKeywordsXml; bool mInitialized; +}; + + +class LLSyntaxLua : public LLSingleton<LLSyntaxLua> +{ + LLSINGLETON(LLSyntaxLua); + public: void initialize(); - bool keywordFetchInProgress(); - LLSD getKeywordsXML() const { return mKeywordsXml; }; - boost::signals2::connection addSyntaxIDCallback(const syntax_id_changed_signal_t::slot_type& cb); + LLSD getKeywordsXML() const { return mKeywordsXml; } + LLSD getTypesXML() const { return mTypesXml; } + +private: + void loadDefaultKeywordsIntoLLSD(); + void loadLuaTypesIntoLLSD(); + LLSD mKeywordsXml; + LLSD mTypesXml; + bool mInitialized; }; #endif // LLSYNTAXID_H diff --git a/indra/newview/lltooldraganddrop.cpp b/indra/newview/lltooldraganddrop.cpp index 5e2d91d31e..eb8ace339e 100644 --- a/indra/newview/lltooldraganddrop.cpp +++ b/indra/newview/lltooldraganddrop.cpp @@ -1828,7 +1828,7 @@ void LLToolDragAndDrop::dropScript(LLViewerObject* hit_obj, } } } - hit_obj->saveScript(new_script, active, true); + hit_obj->saveScript(new_script, active, true, LLUUID::null); if (gFloaterTools) { gFloaterTools->dirty(); diff --git a/indra/newview/llviewerassetupload.cpp b/indra/newview/llviewerassetupload.cpp index d93e900519..fa9a07ce22 100644 --- a/indra/newview/llviewerassetupload.cpp +++ b/indra/newview/llviewerassetupload.cpp @@ -811,19 +811,19 @@ bool LLBufferedAssetUploadInfo::failedUpload(LLSD &result, std::string &reason) //========================================================================= -LLScriptAssetUpload::LLScriptAssetUpload(LLUUID itemId, std::string buffer, invnUploadFinish_f finish, uploadFailed_f failed): +LLScriptAssetUpload::LLScriptAssetUpload(LLUUID itemId, std::string compileTarget, std::string buffer, invnUploadFinish_f finish, uploadFailed_f failed) : LLBufferedAssetUploadInfo(itemId, LLAssetType::AT_LSL_TEXT, buffer, finish, failed), mExerienceId(), - mTargetType(MONO), + mCompileTarget(compileTarget), mIsRunning(false) { } -LLScriptAssetUpload::LLScriptAssetUpload(LLUUID taskId, LLUUID itemId, TargetType_t targetType, +LLScriptAssetUpload::LLScriptAssetUpload(LLUUID taskId, LLUUID itemId, std::string compileTarget, bool isRunning, LLUUID exerienceId, std::string buffer, taskUploadFinish_f finish, uploadFailed_f failed): LLBufferedAssetUploadInfo(taskId, itemId, LLAssetType::AT_LSL_TEXT, buffer, finish, failed), mExerienceId(exerienceId), - mTargetType(targetType), + mCompileTarget(compileTarget), mIsRunning(isRunning) { } @@ -835,14 +835,14 @@ LLSD LLScriptAssetUpload::generatePostBody() if (getTaskId().isNull()) { body["item_id"] = getItemId(); - body["target"] = "mono"; + body["target"] = getCompileTarget(); } else { body["task_id"] = getTaskId(); body["item_id"] = getItemId(); body["is_script_running"] = getIsRunning(); - body["target"] = (getTargetType() == MONO) ? "mono" : "lsl2"; + body["target"] = getCompileTarget(); body["experience"] = getExerienceId(); } diff --git a/indra/newview/llviewerassetupload.h b/indra/newview/llviewerassetupload.h index c627e9dbb8..9692c4814b 100644 --- a/indra/newview/llviewerassetupload.h +++ b/indra/newview/llviewerassetupload.h @@ -256,25 +256,19 @@ private: class LLScriptAssetUpload : public LLBufferedAssetUploadInfo { public: - enum TargetType_t - { - LSL2, - MONO - }; - - LLScriptAssetUpload(LLUUID itemId, std::string buffer, invnUploadFinish_f finish, uploadFailed_f failed); - LLScriptAssetUpload(LLUUID taskId, LLUUID itemId, TargetType_t targetType, + LLScriptAssetUpload(LLUUID itemId, std::string compileTarget, std::string buffer, invnUploadFinish_f finish, uploadFailed_f failed); + LLScriptAssetUpload(LLUUID taskId, LLUUID itemId, std::string compileTarget, bool isRunning, LLUUID exerienceId, std::string buffer, taskUploadFinish_f finish, uploadFailed_f failed); virtual LLSD generatePostBody(); LLUUID getExerienceId() const { return mExerienceId; } - TargetType_t getTargetType() const { return mTargetType; } + const std::string& getCompileTarget() const { return mCompileTarget; } bool getIsRunning() const { return mIsRunning; } private: LLUUID mExerienceId; - TargetType_t mTargetType; + std::string mCompileTarget; bool mIsRunning; }; diff --git a/indra/newview/llviewerfloaterreg.cpp b/indra/newview/llviewerfloaterreg.cpp index e8fe99b339..c1843e7c7e 100644 --- a/indra/newview/llviewerfloaterreg.cpp +++ b/indra/newview/llviewerfloaterreg.cpp @@ -132,6 +132,7 @@ #include "llfloatersavecamerapreset.h" #include "llfloatersaveprefpreset.h" #include "llfloatersceneloadstats.h" +#include "llfloaterscripting.h" #include "llfloaterscriptdebug.h" #include "llfloaterscriptedprefs.h" #include "llfloaterscriptlimits.h" @@ -493,6 +494,7 @@ void LLViewerFloaterReg::registerFloaters() LLFloaterReg::add("script_debug_output", "floater_script_debug_panel.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScriptDebugOutput>); LLFloaterReg::add("script_floater", "floater_script.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLScriptFloater>); LLFloaterReg::add("script_limits", "floater_script_limits.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScriptLimits>); + LLFloaterReg::add("scripting_settings", "floater_scripting_settings.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterScripting>); LLFloaterReg::add("my_scripts", "floater_my_scripts.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterMyScripts>); LLFloaterReg::add("sell_land", "floater_sell_land.xml", &LLFloaterSellLand::buildFloater); LLFloaterReg::add("settings_color", "floater_settings_color.xml", (LLFloaterBuildFunc)&LLFloaterReg::build<LLFloaterSettingsColor>); diff --git a/indra/newview/llviewerinventory.cpp b/indra/newview/llviewerinventory.cpp index efa3f5cd1e..53d87e2869 100644 --- a/indra/newview/llviewerinventory.cpp +++ b/indra/newview/llviewerinventory.cpp @@ -72,6 +72,7 @@ #include "llhttpretrypolicy.h" #include "llsettingsvo.h" #include "llinventorylistener.h" +#include "llviewerassetupload.h" LLInventoryListener sInventoryListener; @@ -1715,6 +1716,7 @@ void create_new_item(const std::string& name, std::function<void(const LLUUID&)> created_cb = nullptr) { std::string desc; + U8 subtype = NO_INV_SUBTYPE; LLViewerAssetType::generateDescriptionFor(asset_type, desc); next_owner_perm = (next_owner_perm) ? next_owner_perm : PERM_MOVE | PERM_TRANSFER; @@ -1726,6 +1728,20 @@ void create_new_item(const std::string& name, { cb = new LLBoostFuncInventoryCallback(create_script_cb); next_owner_perm = LLFloaterPerms::getNextOwnerPerms("Scripts"); + + LLViewerRegion* region = gAgent.getRegion(); + if (region && region->simulatorFeaturesReceived()) + { + // *TODO* Setting the subtype for the script will cause the server to select + // either the LSL or Lua default script. We should perhaps allow the user to + // select which type of script they want to create. + LLSD simulatorFeatures; + region->getSimulatorFeatures(simulatorFeatures); + if (simulatorFeatures["LuaScriptsEnabled"].asBoolean()) + { + subtype = SST_LUA; + } + } break; } @@ -1768,7 +1784,7 @@ void create_new_item(const std::string& name, desc, asset_type, inv_type, - NO_INV_SUBTYPE, + subtype, next_owner_perm, cb); } diff --git a/indra/newview/llviewerinventory.h b/indra/newview/llviewerinventory.h index a42bdaa2b0..23f85663e8 100644 --- a/indra/newview/llviewerinventory.h +++ b/indra/newview/llviewerinventory.h @@ -42,6 +42,8 @@ class LLViewerInventoryCategory; class LLInventoryCallback; class LLAvatarName; +constexpr U8 NO_INV_SUBTYPE{ 0 }; + //~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ // Class LLViewerInventoryItem // @@ -359,8 +361,6 @@ public: extern LLInventoryCallbackManager gInventoryCallbacks; -const U8 NO_INV_SUBTYPE{ 0 }; - // *TODO: Find a home for these void create_inventory_item(const LLUUID& agent_id, const LLUUID& session_id, const LLUUID& parent, const LLTransactionID& transaction_id, diff --git a/indra/newview/llviewermenu.cpp b/indra/newview/llviewermenu.cpp index 5799e23ca5..37ad29a9f3 100644 --- a/indra/newview/llviewermenu.cpp +++ b/indra/newview/llviewermenu.cpp @@ -6724,11 +6724,8 @@ class LLAvatarEnableResetSkeleton : public view_listener_t { bool handleEvent(const LLSD& userdata) { - if (LLVOAvatar* avatar = find_avatar_from_object(LLSelectMgr::getInstance()->getSelection()->getPrimaryObject())) - { - return true; - } - return false; + LLViewerObject* obj = LLSelectMgr::getInstance()->getSelection()->getPrimaryObject(); + return obj && obj->getAvatar(); } }; @@ -7914,13 +7911,13 @@ class LLToolsSelectedScriptAction : public view_listener_t bool handleEvent(const LLSD& userdata) { std::string action = userdata.asString(); - bool mono = false; + std::string target = "lsl2"; std::string msg, name; std::string title; if (action == "compile mono") { name = "compile_queue"; - mono = true; + target = "mono"; msg = "Recompile"; title = LLTrans::getString("CompileQueueTitle"); } @@ -7953,7 +7950,7 @@ class LLToolsSelectedScriptAction : public view_listener_t LLFloaterScriptQueue* queue =LLFloaterReg::getTypedInstance<LLFloaterScriptQueue>(name, LLSD(id)); if (queue) { - queue->setMono(mono); + queue->setCompileTarget(target); if (queue_actions(queue, msg)) { queue->setTitle(title); @@ -8773,6 +8770,12 @@ LLVOAvatar* find_avatar_from_object(LLViewerObject* object) } else if( !object->isAvatar() ) { + // Check for animesh objects (animated objects with a control avatar) + LLVOAvatar* avatar = object->getAvatar(); + if (avatar) + { + return avatar; + } object = NULL; } } diff --git a/indra/newview/llviewermessage.cpp b/indra/newview/llviewermessage.cpp index d1e25988cc..ad7792f8ff 100644 --- a/indra/newview/llviewermessage.cpp +++ b/indra/newview/llviewermessage.cpp @@ -2438,6 +2438,8 @@ void process_chat_from_simulator(LLMessageSystem *msg, void **user_data) color.setVec(1.f,1.f,1.f,1.f); msg->getStringFast(_PREHASH_ChatData, _PREHASH_Message, mesg); + // Preserve tabs from scripts by expanding them to spaces before any sanitization/formatting. + LLStringUtil::replaceTabsWithSpaces(mesg, 4); bool ircstyle = false; diff --git a/indra/newview/llviewerobject.cpp b/indra/newview/llviewerobject.cpp index dfb0521167..12583e81da 100644 --- a/indra/newview/llviewerobject.cpp +++ b/indra/newview/llviewerobject.cpp @@ -2765,10 +2765,15 @@ void LLViewerObject::doUpdateInventory( // save a script, which involves removing the old one, and rezzing // in the new one. This method should be called with the asset id // of the new and old script AFTER the bytecode has been saved. -void LLViewerObject::saveScript( - const LLViewerInventoryItem* item, - bool active, - bool is_new) +// When creating a new script, the asset should be null. The server +// will create the new script based on the script_language (LSL or Lua) +// If a template_id is provided, the new script will be a copy of that item. +// +// *IMPORTANT* If template_id is provided, it must be the ITEM ID of a +// copy/mod-able script in the user's inventory. The simulator will verify +// permissions. +void LLViewerObject::saveScript(const LLViewerInventoryItem* item, + bool active, bool is_new, const LLUUID& template_id) { /* * XXXPAM Investigate not making this copy. Seems unecessary, but I'm unsure about the @@ -2797,6 +2802,15 @@ void LLViewerObject::saveScript( msg->addBOOLFast(_PREHASH_Enabled, enabled); msg->nextBlockFast(_PREHASH_InventoryBlock); task_item->packMessage(msg); + + // This is a completely new script (no asset id) and we've provided a template. + // Note that the script subtype on the template will override any subtype on the item. + if (task_item->getAssetUUID().isNull() && template_id.notNull()) + { + msg->nextBlock("NewScriptInfo"); + msg->addUUID("TemplateID", template_id); + } + msg->sendReliable(mRegionp->getHost()); // do the internal logic diff --git a/indra/newview/llviewerobject.h b/indra/newview/llviewerobject.h index 465e221ae4..b6ce4c4505 100644 --- a/indra/newview/llviewerobject.h +++ b/indra/newview/llviewerobject.h @@ -25,8 +25,7 @@ * $/LicenseInfo$ */ -#ifndef LL_LLVIEWEROBJECT_H -#define LL_LLVIEWEROBJECT_H +#pragma once #include <map> #include <unordered_map> @@ -549,7 +548,10 @@ public: // save a script, which involves removing the old one, and rezzing // in the new one. This method should be called with the asset id // of the new and old script AFTER the bytecode has been saved. - void saveScript(const LLViewerInventoryItem* item, bool active, bool is_new); + // The simulator treats the script as new when item->getAssetUUID().isNull() is true; in that case + // template_id will be used (if non-null) to copy an existing script asset, otherwise the + // script subtype in the item will be used to select the correct template. + void saveScript(const LLViewerInventoryItem* item, bool active, bool is_new, const LLUUID& template_id); // move an inventory item out of the task and into agent // inventory. This operation is based on messaging. No permissions @@ -1108,5 +1110,3 @@ public: virtual void updateDrawable(bool force_damped); }; - -#endif diff --git a/indra/newview/llworldmapmessage.cpp b/indra/newview/llworldmapmessage.cpp index e81e6b4596..a5433133ab 100644 --- a/indra/newview/llworldmapmessage.cpp +++ b/indra/newview/llworldmapmessage.cpp @@ -33,7 +33,8 @@ #include "llagent.h" #include "llfloaterworldmap.h" -const U32 LAYER_FLAG = 2; +constexpr U32 LAYER_FLAG = 2; +constexpr S32 MAP_SIM_RETURN_NULL_SIMS = 0x00010000; //--------------------------------------------------------------------------- // World Map Message Handling @@ -135,7 +136,11 @@ void LLWorldMapMessage::sendMapBlockRequest(U16 min_x, U16 min_y, U16 max_x, U16 msg->addUUIDFast(_PREHASH_AgentID, gAgent.getID()); msg->addUUIDFast(_PREHASH_SessionID, gAgent.getSessionID()); U32 flags = LAYER_FLAG; - flags |= (return_nonexistent ? 0x10000 : 0); + if (return_nonexistent) + { + // overwrite LAYER_FLAG, otherwise server won't respond to missing regions + flags = MAP_SIM_RETURN_NULL_SIMS; + } msg->addU32Fast(_PREHASH_Flags, flags); msg->addU32Fast(_PREHASH_EstateID, 0); // Filled in on sim msg->addBOOLFast(_PREHASH_Godlike, false); // Filled in on sim @@ -157,15 +162,17 @@ void LLWorldMapMessage::processMapBlockReply(LLMessageSystem* msg, void**) U32 agent_flags; msg->getU32Fast(_PREHASH_AgentData, _PREHASH_Flags, agent_flags); - // There's only one flag that we ever use here - if (agent_flags != LAYER_FLAG) + S32 num_blocks = msg->getNumberOfBlocksFast(_PREHASH_Data); + + // There's only one flag that we ever use here, unless we also want an existence check. + if (agent_flags != LAYER_FLAG + && num_blocks != 1) // we check existence for a single region { LL_WARNS() << "Invalid map image type returned! layer = " << agent_flags << LL_ENDL; return; } - S32 num_blocks = msg->getNumberOfBlocksFast(_PREHASH_Data); - //LL_INFOS("WorldMap") << "num_blocks = " << num_blocks << LL_ENDL; + LL_DEBUGS("WorldMap") << "num_blocks = " << num_blocks << LL_ENDL; bool found_null_sim = false; @@ -191,26 +198,31 @@ void LLWorldMapMessage::processMapBlockReply(LLMessageSystem* msg, void**) U32 x_world = (U32)(x_regions) * REGION_WIDTH_UNITS; U32 y_world = (U32)(y_regions) * REGION_WIDTH_UNITS; - // name shouldn't be empty, see EXT-4568 - llassert(!name.empty()); - - // Insert that region in the world map, if failure, flag it as a "null_sim" - if (!(LLWorldMap::getInstance()->insertRegion(x_world, y_world, name, image_id, (U32)accesscode, region_flags))) + // Name shouldn't be empty unless region doesn't exist + if (!name.empty()) { - found_null_sim = true; - } + // Insert that region in the world map, if failure, flag it as a "null_sim" + if (!(LLWorldMap::getInstance()->insertRegion(x_world, y_world, name, image_id, (U32)accesscode, region_flags))) + { + found_null_sim = true; + } - // If we hit a valid tracking location, do what needs to be done app level wise - if (LLWorldMap::getInstance()->isTrackingValidLocation()) - { - LLVector3d pos_global = LLWorldMap::getInstance()->getTrackedPositionGlobal(); - if (LLWorldMap::getInstance()->isTrackingDoubleClick()) + // If we hit a valid tracking location, do what needs to be done app level wise + if (LLWorldMap::getInstance()->isTrackingValidLocation()) { - // Teleport if the user double clicked - gAgent.teleportViaLocation(pos_global); + LLVector3d pos_global = LLWorldMap::getInstance()->getTrackedPositionGlobal(); + if (LLWorldMap::getInstance()->isTrackingDoubleClick()) + { + // Teleport if the user double clicked + gAgent.teleportViaLocation(pos_global); + } + // Update the "real" tracker information + gFloaterWorldMap->trackLocation(pos_global); } - // Update the "real" tracker information - gFloaterWorldMap->trackLocation(pos_global); + } + else + { + found_null_sim = true; } // Handle the SLURL callback if any diff --git a/indra/newview/skins/default/xui/de/floater_about.xml b/indra/newview/skins/default/xui/de/floater_about.xml index 320db7f654..1d56e218eb 100644 --- a/indra/newview/skins/default/xui/de/floater_about.xml +++ b/indra/newview/skins/default/xui/de/floater_about.xml @@ -23,6 +23,8 @@ mit Open-Source-Beiträgen von:</text> Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW). jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus. OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge. diff --git a/indra/newview/skins/default/xui/en/floater_about.xml b/indra/newview/skins/default/xui/en/floater_about.xml index 126cd84d56..4394f71260 100644 --- a/indra/newview/skins/default/xui/en/floater_about.xml +++ b/indra/newview/skins/default/xui/en/floater_about.xml @@ -105,6 +105,7 @@ Dummy Name replaced at run time Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. diff --git a/indra/newview/skins/default/xui/en/floater_live_lsleditor.xml b/indra/newview/skins/default/xui/en/floater_live_lsleditor.xml index e30c519c8a..26281989a7 100644 --- a/indra/newview/skins/default/xui/en/floater_live_lsleditor.xml +++ b/indra/newview/skins/default/xui/en/floater_live_lsleditor.xml @@ -7,7 +7,7 @@ height="607" layout="topleft" min_height="271" - min_width="328" + min_width="500" name="script ed float" help_topic="script_ed_float" save_rect="true" @@ -62,7 +62,6 @@ </text> <panel bevel_style="none" - border_style="line" follows="left|top|right|bottom" height="499" @@ -93,25 +92,15 @@ name="running" width="205" /> <check_box - left_delta="140" - enabled="true" - follows="left|bottom" - font="SansSerif" - height="18" - initial_value="true" - label="Mono" + width="130" + height="21" + enabled="false" + left="9" + top_pad="10" layout="topleft" - name="mono" - width="100" /> - <check_box width="130" - height="21" - enabled="false" - left="9" - top_pad="10" - layout="topleft" - follows="bottom|left" - label="Use Experience:" - name="enable_xp"/> + follows="bottom|left" + label="Use Experience:" + name="enable_xp"/> <combo_box label="" top_pad="-21" @@ -121,13 +110,14 @@ follows="left|bottom|right" visible="false" name="Experiences..."/> - <button label=">" - name="view_profile" - height="23" - width="23" - right="496" - layout="topleft" - top_pad="-23" - follows="right" - visible="false"/> + <button + label=">" + name="view_profile" + height="23" + width="23" + right="496" + layout="topleft" + top_pad="-23" + follows="right" + visible="false"/> </floater> diff --git a/indra/newview/skins/default/xui/en/floater_script_preview.xml b/indra/newview/skins/default/xui/en/floater_script_preview.xml index b0b105fe58..f82224cc9e 100644 --- a/indra/newview/skins/default/xui/en/floater_script_preview.xml +++ b/indra/newview/skins/default/xui/en/floater_script_preview.xml @@ -5,7 +5,7 @@ height="593" layout="topleft" min_height="271" - min_width="320" + min_width="500" name="preview lsl text" help_topic="preview_lsl_text" save_rect="true" diff --git a/indra/newview/skins/default/xui/en/floater_script_queue.xml b/indra/newview/skins/default/xui/en/floater_script_queue.xml index a98437ab1d..e272d3073a 100644 --- a/indra/newview/skins/default/xui/en/floater_script_queue.xml +++ b/indra/newview/skins/default/xui/en/floater_script_queue.xml @@ -37,6 +37,10 @@ name="LoadingObjInv"> Loading inventory for: [OBJECT_NAME] </floater.string> + <floater.string + name="SkippingSluaScript"> + Skipping SLua script "[SCRIPT_NAME]" (cannot recompile to [TARGET]) + </floater.string> <button follows="right|bottom" height="24" diff --git a/indra/newview/skins/default/xui/en/floater_scripting_settings.xml b/indra/newview/skins/default/xui/en/floater_scripting_settings.xml new file mode 100644 index 0000000000..07f073edb2 --- /dev/null +++ b/indra/newview/skins/default/xui/en/floater_scripting_settings.xml @@ -0,0 +1,143 @@ +<?xml version="1.0" encoding="utf-8" standalone="yes"?> +<floater + legacy_header_height="18" + height="265" + layout="topleft" + name="floater_scripting_settings" + help_topic="scripting_settings" + save_rect="true" + title="SCRIPT DEVELOPMENT SETTINGS" + width="485"> + <check_box + control_name="ShowScriptErrors" + follows="left|top" + height="20" + label="Show script errors in:" + layout="topleft" + left="30" + top_pad="20" + name="show_script_errors" + width="256" /> + <radio_group + enabled_control="ShowScriptErrors" + control_name="ShowScriptErrorsLocation" + follows="top|left" + height="16" + layout="topleft" + left_delta="50" + name="show_location" + top_pad="5" + width="364"> + <radio_item + height="16" + label="Nearby chat" + layout="topleft" + left="3" + name="0" + top="0" + width="315" /> + <radio_item + height="16" + label="Separate window" + layout="topleft" + left_delta="175" + name="1" + top_delta="0" + width="315" /> + </radio_group> + + <text + follows="top|left|right" + height="15" + layout="topleft" + left="30" + name="tip" + top_pad="20" + width="330" + wrap="true"> + External Script Editor: + </text> + <line_editor + control_name="ExternalEditor" + follows="top|left" + height="20" + initial_value="" + layout="left" + left_pad="5" + name="external_editor" + top_delta="25" + value="" + width="360" /> + <button + follows="left|top" + height="20" + label="Browse..." + layout="topleft" + left_pad="5" + name="browse_btn" + top_delta="0" + width="70"> + <button.commit_callback + function="ScriptingSettings.BROWSE" /> + </button> + + <check_box + control_name="ExternalWebsocketSyncEnable" + follows="top|left" + height="20" + label="Enable WebSocket Sync" + layout="topleft" + left="30" + name="websocket_sync_enable" + top_pad="20" + width="200" /> + + <text + enabled_control="ExternalWebsocketSyncEnable" + follows="top|left" + height="15" + layout="topleft" + left="50" + name="websocket_tip" + top_pad="10" + width="140" + wrap="false"> + WebSocket Listen Port: + </text> + <line_editor + enabled_control="ExternalWebsocketSyncEnable" + control_name="ExternalWebsocketSyncPort" + follows="top|left" + height="20" + initial_value="9020" + layout="topleft" + left_pad="5" + name="websocket_port" + top_delta="-2" + value="9020" + width="120" /> + <check_box + control_name="ExternalWebsocketForwardDebug" + enabled_control="ExternalWebsocketSyncEnable" + follows="top|left" + height="20" + label="Forward script errors and debug to WebSocket clients" + layout="topleft" + left="50" + name="websocket_forward_debug" + top_pad="5" + width="400" /> + + <button + follows="left|top" + height="23" + label="Close" + layout="topleft" + right="-10" + name="close_btn" + top="-30" + width="100"> + <button.commit_callback + function="ScriptingSettings.CLOSE" /> + </button> +</floater> diff --git a/indra/newview/skins/default/xui/en/panel_preferences_advanced.xml b/indra/newview/skins/default/xui/en/panel_preferences_advanced.xml index 86999b1afb..434ee1db35 100644 --- a/indra/newview/skins/default/xui/en/panel_preferences_advanced.xml +++ b/indra/newview/skins/default/xui/en/panel_preferences_advanced.xml @@ -169,43 +169,6 @@ name="hud_scale_slider" top_pad="-14" width="250" /> - <check_box - control_name="ShowScriptErrors" - follows="left|top" - height="20" - label="Show script errors in:" - layout="topleft" - left="30" - top_pad="10" - name="show_script_errors" - width="256" /> - <radio_group - enabled_control="ShowScriptErrors" - control_name="ShowScriptErrorsLocation" - follows="top|left" - height="16" - layout="topleft" - left_delta="50" - name="show_location" - top_pad="5" - width="364"> - <radio_item - height="16" - label="Nearby chat" - layout="topleft" - left="3" - name="0" - top="0" - width="315" /> - <radio_item - height="16" - label="Separate window" - layout="topleft" - left_delta="175" - name="1" - top_delta="0" - width="315" /> - </radio_group> <check_box control_name="AllowMultipleViewers" @@ -266,9 +229,21 @@ name="default_creation_permissions" height="20" left="30" - top_pad="16" + top_pad="10" width="200"> <button.commit_callback function="Pref.PermsDefault" /> </button> + <button + follows="top|left" + layout="topleft" + label="Script Development" + name="scripting_development" + height="20" + left="30" + top_pad="10" + width="200"> + <button.commit_callback + function="Pref.Scripting" /> + </button> </panel> diff --git a/indra/newview/skins/default/xui/en/panel_script_ed.xml b/indra/newview/skins/default/xui/en/panel_script_ed.xml index f8761d2b24..2ccf379b8d 100644 --- a/indra/newview/skins/default/xui/en/panel_script_ed.xml +++ b/indra/newview/skins/default/xui/en/panel_script_ed.xml @@ -219,7 +219,7 @@ label="Save" label_selected="Save" layout="topleft" - top_pad="-35" + top_pad="-23" right="487" name="Save_btn" width="81" /> @@ -233,4 +233,37 @@ right="400" name="Edit_btn" width="81" /> + <combo_box + name="compile_target" + follows="right|bottom" + height="23" + layout="topleft" + top_pad="-23" + right="300" + width="140"> + <combo_box.item + label="LSL: Legacy (LSO2)" + name="compile_target_lsl2" + value="lsl2" /> + <combo_box.item + label="LSL: Mono" + name="compile_target_mono" + value="mono" /> + <combo_box.item + label="LSL: 2025 VM" + name="compile_target_lsl_luau" + value="lsl-luau" /> + <combo_box.item + label="SLua" + name="compile_target_luau" + value="luau" /> + </combo_box> + <text + name="compile_target_label" + follows="right|bottom" + layout="topleft" + top_pad="-39" + width="90"> + Compiler: + </text> </panel> diff --git a/indra/newview/skins/default/xui/es/floater_about.xml b/indra/newview/skins/default/xui/es/floater_about.xml index 8103a95376..08e0ed4557 100644 --- a/indra/newview/skins/default/xui/es/floater_about.xml +++ b/indra/newview/skins/default/xui/es/floater_about.xml @@ -23,6 +23,8 @@ con contribuciones de código abierto de:</text> Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge diff --git a/indra/newview/skins/default/xui/fr/floater_about.xml b/indra/newview/skins/default/xui/fr/floater_about.xml index b6ea621177..7c6ae22fdf 100644 --- a/indra/newview/skins/default/xui/fr/floater_about.xml +++ b/indra/newview/skins/default/xui/fr/floater_about.xml @@ -23,6 +23,8 @@ avec les contributions Open Source de :</text> Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge diff --git a/indra/newview/skins/default/xui/it/floater_about.xml b/indra/newview/skins/default/xui/it/floater_about.xml index 77be47d749..2bba6a4fad 100644 --- a/indra/newview/skins/default/xui/it/floater_about.xml +++ b/indra/newview/skins/default/xui/it/floater_about.xml @@ -23,6 +23,8 @@ con contributi open source da:</text> Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge diff --git a/indra/newview/skins/default/xui/ja/floater_about.xml b/indra/newview/skins/default/xui/ja/floater_about.xml index 6cd22f6a31..dd24a04aed 100644 --- a/indra/newview/skins/default/xui/ja/floater_about.xml +++ b/indra/newview/skins/default/xui/ja/floater_about.xml @@ -27,6 +27,7 @@ google-perftools Copyright (c) 2005, Google Inc. Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. +luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. diff --git a/indra/newview/skins/default/xui/pt/floater_about.xml b/indra/newview/skins/default/xui/pt/floater_about.xml index 0e95c53109..f7dff635a7 100644 --- a/indra/newview/skins/default/xui/pt/floater_about.xml +++ b/indra/newview/skins/default/xui/pt/floater_about.xml @@ -23,6 +23,8 @@ com contribuições de código aberto de:</text> Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge diff --git a/indra/newview/skins/default/xui/ru/floater_about.xml b/indra/newview/skins/default/xui/ru/floater_about.xml index 22827bc397..435d242018 100644 --- a/indra/newview/skins/default/xui/ru/floater_about.xml +++ b/indra/newview/skins/default/xui/ru/floater_about.xml @@ -24,6 +24,8 @@ jpeg2000 (C) 2001, David Taubman, Университет Нового Южного Уэльса (UNSW) jpeglib (C) 1991-1998, Thomas G. Lane. ogg/vorbis (C) 2002, Xiphophorus + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine OpenSSL (C) 1998-2008 The OpenSSL Project. PCRE (c) 1997-2012, Кембриджский университет SDL (C) 1997, 1998, 1999, 2000, 2001, 2002 Sam Lantinga diff --git a/indra/newview/skins/default/xui/tr/floater_about.xml b/indra/newview/skins/default/xui/tr/floater_about.xml index ca21bee464..d01d0e88d3 100644 --- a/indra/newview/skins/default/xui/tr/floater_about.xml +++ b/indra/newview/skins/default/xui/tr/floater_about.xml @@ -23,6 +23,8 @@ açık kaynak kod katkısında bulunanlar şunlardır:</text> Havok.com(TM) Telif Hakkı (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Telif Hakkı (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Telif Hakkı (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Telif Hakkı (C) 2002, Xiphophorus OpenSSL Telif Hakkı (C) 1998-2008 The OpenSSL Project. PCRE Telif Hakkı (c) 1997-2012 University of Cambridge diff --git a/indra/newview/skins/default/xui/zh/floater_about.xml b/indra/newview/skins/default/xui/zh/floater_about.xml index 727f598894..4c23beca30 100644 --- a/indra/newview/skins/default/xui/zh/floater_about.xml +++ b/indra/newview/skins/default/xui/zh/floater_about.xml @@ -23,6 +23,8 @@ Havok.com(TM) Copyright (C) 1999-2001, Telekinesys Research Limited. jpeg2000 Copyright (C) 2001, David Taubman, The University of New South Wales (UNSW) jpeglib Copyright (C) 1991-1998, Thomas G. Lane. + luau Copyright (c) 1994–2019 Lua.org, PUC-Rio / Copyright (c) 2019-2024 Roblox Corporation + meshoptimizer Copyright (c) 2016-2021 Arseny Kapoulkine ogg/vorbis Copyright (C) 2002, Xiphophorus OpenSSL Copyright (C) 1998-2008 The OpenSSL Project. PCRE Copyright (c) 1997-2012 University of Cambridge diff --git a/scripts/messages/message_template.msg b/scripts/messages/message_template.msg index 40ba2cc6b6..ad3ddd5a94 100644 --- a/scripts/messages/message_template.msg +++ b/scripts/messages/message_template.msg @@ -6818,6 +6818,10 @@ version 2.0 { CreationDate S32 } { CRC U32 } } + { + NewScriptInfo Variable + { TemplateID LLUUID } + } } // Create inventory diff --git a/scripts/messages/message_template.msg.sha1 b/scripts/messages/message_template.msg.sha1 index baa4f3f12b..96f24ca1ba 100644 --- a/scripts/messages/message_template.msg.sha1 +++ b/scripts/messages/message_template.msg.sha1 @@ -1 +1 @@ -aaecaf01b6954c156662f572dc3ecaf26de0ca67
\ No newline at end of file +3edf45c784a5440d7dd24c59309faf52d1d01f47
\ No newline at end of file |
