added timelines to spec + index.html
This commit is contained in:
parent
976d222ab6
commit
afc0a77935
6 changed files with 21 additions and 1496 deletions
|
|
@ -115,6 +115,7 @@ XR Fragments allows us to better use implicit metadata inside 3D scene(files), b
|
|||
1. [XR Fragment URL Grammar](#xr-fragment-url-grammar)
|
||||
1. [Spatial Referencing 3D](#spatial-referencing-3d)
|
||||
1. [Level0: Files](#level0-files)
|
||||
1. [timelines](#timelines)
|
||||
1. [via href metadata](#via-href-metadata)
|
||||
1. [via chained extension](#via-chained-extension)
|
||||
1. [via subdocuments/xattr](#via-subdocuments-xattr)
|
||||
|
|
@ -304,6 +305,16 @@ A 3D scene-file can be considered <b>XR Fragment-compatible</b> when it contains
|
|||
There are **optional** auto-loaded [side-car files]() to enable hasslefree [XR Movies](#XR%20Movies).<br>
|
||||
they can accomodate developers or applications who (for whatever reason) must not modify the 3D scene-file (a `.glb` e.g.).
|
||||
|
||||
## Timelines
|
||||
|
||||
when a loaded file contains a timeline (animations/subtitles e.g.), then:
|
||||
|
||||
> All timelines must play (looped) by default (to enable [[XR Movies]])
|
||||
|
||||
Unless an object has multiple animations (actions e.g.), then just play the first or with name `default`.
|
||||
|
||||
|
||||
|
||||
## via href metadata
|
||||
|
||||
```
|
||||
|
|
|
|||
|
|
@ -1,465 +0,0 @@
|
|||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<title>XR Macros</title>
|
||||
<meta name="GENERATOR" content="github.com/mmarkdown/mmark Mmark Markdown Processor - mmark.miek.nl">
|
||||
<meta charset="utf-8">
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<!-- for annotated version see: https://raw.githubusercontent.com/ietf-tools/rfcxml-templates-and-schemas/main/draft-rfcxml-general-template-annotated-00.xml -->
|
||||
|
||||
|
||||
<style type="text/css">
|
||||
body{
|
||||
font-family: monospace;
|
||||
max-width: 1000px;
|
||||
font-size: 15px;
|
||||
padding: 0% 20%;
|
||||
line-height: 30px;
|
||||
color:#555;
|
||||
background:#F0F0F3
|
||||
}
|
||||
h1 { margin-top:40px; }
|
||||
pre{ line-height:18px; }
|
||||
a,a:visited,a:active{ color: #70f; }
|
||||
code{
|
||||
border: 1px solid #AAA;
|
||||
border-radius: 3px;
|
||||
padding: 0px 5px 2px 5px;
|
||||
}
|
||||
|
||||
pre{
|
||||
line-height: 18px;
|
||||
overflow: auto;
|
||||
padding: 12px;
|
||||
}
|
||||
pre + code {
|
||||
background:#DDD;
|
||||
}
|
||||
pre>code{
|
||||
border:none;
|
||||
border-radius:0px;
|
||||
padding:0;
|
||||
}
|
||||
blockquote{
|
||||
padding-left: 30px;
|
||||
margin: 0;
|
||||
border-left: 5px solid #CCC;
|
||||
}
|
||||
th {
|
||||
border-bottom: 1px solid #000;
|
||||
text-align: left;
|
||||
padding-right:45px;
|
||||
padding-left:7px;
|
||||
background: #DDD;
|
||||
}
|
||||
|
||||
td {
|
||||
border-bottom: 1px solid #CCC;
|
||||
font-size:13px;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
<br>
|
||||
<h1>XR Macros</h1>
|
||||
<br>
|
||||
|
||||
<pre>
|
||||
stream: IETF
|
||||
area: Internet
|
||||
status: informational
|
||||
author: Leon van Kammen
|
||||
date: 2023-04-12T00:00:00Z
|
||||
workgroup: Internet Engineering Task Force
|
||||
value: draft-XRMACROS-leonvankammen-00
|
||||
</pre>
|
||||
|
||||
|
||||
|
||||
<h1 class="special" id="abstract">Abstract</h1>
|
||||
|
||||
<p>This draft offers a specification for embedding macros in existing 3D scenes/assets, to offer simple interactions and configure the renderer further.<br>
|
||||
Together with URI Fragments, it allows for rich immersive experiences without the need of a complicated sandboxed scripting languages.</p>
|
||||
|
||||
<blockquote>
|
||||
<p>Almost every idea in this document is demonstrated at <a href="https://xrfragment.org">https://xrfragment.org</a>, as this spec was created during the <a href="https://xrfragment.org">XR Fragments</a> spec.</p>
|
||||
</blockquote>
|
||||
<section data-matter="main">
|
||||
<h1 id="introduction">Introduction</h1>
|
||||
|
||||
<p>How can we add more features to existing text & 3D scenes, without introducing new dataformats?<br>
|
||||
Historically, there’s many attempts to create the ultimate markuplanguage or 3D fileformat.<br>
|
||||
Their lowest common denominator is: (co)authoring using plain text.<br>
|
||||
Therefore, XR Macros allows us to enrich/connect existing dataformats, by offering a polyglot notation based on existing notations:<br></p>
|
||||
|
||||
<ol>
|
||||
<li>getting/setting common used 3D properties using querystring- or JSON-notation</li>
|
||||
<li>targeting 3D properties using the lightweight query notation present in <a href="https://xrfragment.org">XR Fragments</a></li>
|
||||
</ol>
|
||||
|
||||
<blockquote>
|
||||
<p>NOTE: The chapters in this document are ordered from highlevel to lowlevel (technical) as much as possible</p>
|
||||
</blockquote>
|
||||
|
||||
<h1 id="core-principle">Core principle</h1>
|
||||
|
||||
<ol>
|
||||
<li>XR Macros use querystrings, but are HTML-agnostic (though pseudo-XR Fragment browsers <strong>can</strong> be implemented on top of HTML/Javascript).</li>
|
||||
<li>An XR Macro is 3D metadata which starts with ‘!’ (<code>!clickme: fog=0,10</code> e.g.)</li>
|
||||
<li>Metadata-values can contain the <code>|</code> symbol to 🎲 roundrobin variable values (<code>!toggleme: fog=0,10|fog=0,1000</code> e.g.)</li>
|
||||
<li>XR Macros acts as simple eventhandlers for URI Fragments: they are automatically published on the (<a href="https://xrfragment.org">XR Fragments</a>) hashbus, to act as events (so more serious scripting languages can react to them as well).</li>
|
||||
<li>XR Macros can assign object metadata (<code>!setlocal: foo=1</code> writes <code>foo:1</code> metadata to the object containing the <code>!setlocal</code> metadata)</li>
|
||||
<li>XR Macros can assign global metadata (<code>!setfoo: #foo=1</code> writes <code>foo:1</code> metadata to the root scene-node)</li>
|
||||
</ol>
|
||||
|
||||
<blockquote>
|
||||
<p>These very simple principles allow for rich interactions and dynamic querying</p>
|
||||
</blockquote>
|
||||
|
||||
<h1 id="conventions-and-definitions">Conventions and Definitions</h1>
|
||||
|
||||
<p>See appendix below in case certain terms are not clear.</p>
|
||||
|
||||
<h1 id="list-of-xr-macros">List of XR Macros</h1>
|
||||
|
||||
<p>(XR) Macros can be embedded in 3D assets/scenes.<br>
|
||||
Macros enrich existing spatial content with a lowcode, limited logic-layer, by recursive (economic) use of the querystring syntax (which search engines and <a href="https://xrfragment.org">XR Fragments</a> already uses.<br>
|
||||
This is done by allowing string/integer variables, and the <code>|</code> symbol to roundrobin variable values.<br>
|
||||
Macros also act as events, so more serious scripting languages can react to them as well.<br></p>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>key</th>
|
||||
<th>type</th>
|
||||
<th>example (JSON)</th>
|
||||
<th>function</th>
|
||||
<th>existing compatibility</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td><code>@bg</code></td>
|
||||
<td>string</td>
|
||||
<td><code>"@bg":"#cube"</code></td>
|
||||
<td>bg: binds fog near/far based to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><code>@fog</code></td>
|
||||
<td>string</td>
|
||||
<td><code>"@fog":"#cube"</code></td>
|
||||
<td>fog: binds fog near/far based to cube x/y (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><code>@scroll</code></td>
|
||||
<td>string</td>
|
||||
<td><code>"@scroll":"#cube"</code></td>
|
||||
<td>texturescrolling: binds texture x/y/rot based to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><code>@emissive</code></td>
|
||||
<td>string</td>
|
||||
<td><code>"@emissive":"#cube"</code></td>
|
||||
<td>day/night/mood: binds material’s emissive value to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h2 id="usecase-click-object">Usecase: click object</h2>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!clickme</td>
|
||||
<td>bg=1,1,1&foo=2</td>
|
||||
<td>object clicked</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h2 id="usecase-conditional-click-object">Usecase: conditional click object</h2>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>#</td>
|
||||
<td>foo=1</td>
|
||||
<td>scene</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!clickme</td>
|
||||
<td>q=foo>2&bg=1,1,1</td>
|
||||
<td>object clicked and foo > 2</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<blockquote>
|
||||
<p>when a user clicks an object with the custom properties above, it should set the backgroundcolor to <code>1,1,1</code> when <code>foo</code> is greater than <code>2</code> (see previous example)</p>
|
||||
</blockquote>
|
||||
|
||||
<h2 id="usecase-click-object-roundrobin">Usecase: click object (roundrobin)</h2>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!cycleme</td>
|
||||
<td>day|noon|night</td>
|
||||
<td>object clicked</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<blockquote>
|
||||
<p>when a user clicks an object with the custom properties above, it should trigger either <code>day</code> <code>noon</code> or <code>night</code> in roundrobin fashion.</p>
|
||||
</blockquote>
|
||||
|
||||
<h2 id="usecase-click-object-or-uri-fragment-and-scene-load-trigger">Usecase: click object or URI fragment, and scene load trigger</h2>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>#</td>
|
||||
<td>random</td>
|
||||
<td>scene loaded</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>#random</td>
|
||||
<td>random</td>
|
||||
<td>URL contains #random</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!random</td>
|
||||
<td>day|noon|night</td>
|
||||
<td>#random, # or click</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<h2 id="usecase-present-context-menu-with-options">Usecase: present context menu with options</h2>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!random</td>
|
||||
<td>!day</td>
|
||||
<td>!noon</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
<blockquote>
|
||||
<p>When interacting with an object with more than one <code>!</code>-macro, the XR Browser should offer a contextmenu to execute a macro.</p>
|
||||
</blockquote>
|
||||
|
||||
<p>In a similar way, when <strong>any</strong> <code>!</code>-macro is present on the sceneroot, the XR Browser should offer a context-menu to execute those macro’s.</p>
|
||||
|
||||
<h2 id="event-bubble-flow">Event Bubble-flow</h2>
|
||||
|
||||
<p>click object with (<code>!clickme</code>:<code>AR</code> or <code>!clickme</code>: <code>!reset</code> e.g.)</p>
|
||||
|
||||
<pre><code> ◻
|
||||
│
|
||||
└── does current object contain this property-key (`AR` or `!reset` e.g.)?
|
||||
└── no: is there any (root)object containing property `AR`
|
||||
└── yes: evaluate its (roundrobin) XR macro-value(s) (and exit)
|
||||
└── no: trigger URL: #AR
|
||||
</code></pre>
|
||||
|
||||
<p>click object with (<code>!clickme</code>:<code>#AR|#VR</code> e.g.)</p>
|
||||
|
||||
<pre><code> ◻
|
||||
│
|
||||
└── apply the roundrobin (rotate the options, value `#AR` becomes `#VR` upon next click)
|
||||
└── is there any object with property-key (`#AR` e.g.)?
|
||||
└── no: just update the URL to `#AR`
|
||||
└── yes: apply its value to the scene, and update the URL to `#AR`
|
||||
|
||||
click object with (`!clickme`:`!foo|!bar|!flop` e.g.)
|
||||
</code></pre>
|
||||
|
||||
<p>◻
|
||||
│<br>
|
||||
└── apply the roundrobin (rotate the options, value <code>!foo</code> becomes <code>!bar</code> upon next click)
|
||||
└── is there any object with property-key (<code>!foo</code> e.g.)?
|
||||
└── no: do nothing
|
||||
└── yes: apply its value to the scene
|
||||
“`</p>
|
||||
|
||||
<blockquote>
|
||||
<p>Note that only macro’s can trigger roundrobin values or contextmenu’s, as well as roundrobin values never ending up in the toplevel URL.</p>
|
||||
</blockquote>
|
||||
|
||||
<h1 id="security-considerations">Security Considerations</h1>
|
||||
|
||||
<h1 id="iana-considerations">IANA Considerations</h1>
|
||||
|
||||
<p>This document has no IANA actions.</p>
|
||||
|
||||
<h1 id="acknowledgments">Acknowledgments</h1>
|
||||
|
||||
<ul>
|
||||
<li><a href="https://nlnet.nl">NLNET</a></li>
|
||||
<li><a href="https://futureoftext.org">Future of Text</a></li>
|
||||
<li><a href="https://visual-meta.info">visual-meta.info</a></li>
|
||||
</ul>
|
||||
|
||||
<h1 id="appendix-definitions">Appendix: Definitions</h1>
|
||||
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>definition</th>
|
||||
<th>explanation</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>scene</td>
|
||||
<td>a (local/remote) 3D scene or 3D file (index.gltf e.g.)</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>3D object</td>
|
||||
<td>an object inside a scene characterized by vertex-, face- and customproperty data.</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>XR fragments</td>
|
||||
<td>URI Fragment with spatial hints like <code>#pos=0,0,0&t=1,100</code> e.g.</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>query</td>
|
||||
<td>an URI Fragment-operator which queries object(s) from a scene like <code>#q=cube</code></td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>FPS</td>
|
||||
<td>frames per second in spatial experiences (games,VR,AR e.g.), should be as high as possible</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><code>◻</code></td>
|
||||
<td>ascii representation of an 3D object/mesh</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>(un)obtrusive</td>
|
||||
<td>obtrusive: wrapping human text/thought in XML/HTML/JSON obfuscates human text into a salad of machine-symbols and words</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</section>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
||||
|
|
@ -1,251 +0,0 @@
|
|||
%%%
|
||||
Title = "XR Macros"
|
||||
area = "Internet"
|
||||
workgroup = "Internet Engineering Task Force"
|
||||
|
||||
[seriesInfo]
|
||||
name = "XR-Macros"
|
||||
value = "draft-XRMACROS-leonvankammen-00"
|
||||
stream = "IETF"
|
||||
status = "informational"
|
||||
|
||||
date = 2023-04-12T00:00:00Z
|
||||
|
||||
[[author]]
|
||||
initials="L.R."
|
||||
surname="van Kammen"
|
||||
fullname="L.R. van Kammen"
|
||||
|
||||
%%%
|
||||
|
||||
<!-- for annotated version see: https://raw.githubusercontent.com/ietf-tools/rfcxml-templates-and-schemas/main/draft-rfcxml-general-template-annotated-00.xml -->
|
||||
|
||||
<!--{
|
||||
|
||||
<style type="text/css">
|
||||
body{
|
||||
font-family: monospace;
|
||||
max-width: 1000px;
|
||||
font-size: 15px;
|
||||
padding: 0% 20%;
|
||||
line-height: 30px;
|
||||
color:#555;
|
||||
background:#F0F0F3
|
||||
}
|
||||
h1 { margin-top:40px; }
|
||||
pre{ line-height:18px; }
|
||||
a,a:visited,a:active{ color: #70f; }
|
||||
code{
|
||||
border: 1px solid #AAA;
|
||||
border-radius: 3px;
|
||||
padding: 0px 5px 2px 5px;
|
||||
}
|
||||
|
||||
pre{
|
||||
line-height: 18px;
|
||||
overflow: auto;
|
||||
padding: 12px;
|
||||
}
|
||||
pre + code {
|
||||
background:#DDD;
|
||||
}
|
||||
pre>code{
|
||||
border:none;
|
||||
border-radius:0px;
|
||||
padding:0;
|
||||
}
|
||||
blockquote{
|
||||
padding-left: 30px;
|
||||
margin: 0;
|
||||
border-left: 5px solid #CCC;
|
||||
}
|
||||
th {
|
||||
border-bottom: 1px solid #000;
|
||||
text-align: left;
|
||||
padding-right:45px;
|
||||
padding-left:7px;
|
||||
background: #DDD;
|
||||
}
|
||||
|
||||
td {
|
||||
border-bottom: 1px solid #CCC;
|
||||
font-size:13px;
|
||||
}
|
||||
|
||||
</style>
|
||||
|
||||
<br>
|
||||
<h1>XR Macros</h1>
|
||||
<br>
|
||||
|
||||
<pre>
|
||||
stream: IETF
|
||||
area: Internet
|
||||
status: informational
|
||||
author: Leon van Kammen
|
||||
date: 2023-04-12T00:00:00Z
|
||||
workgroup: Internet Engineering Task Force
|
||||
value: draft-XRMACROS-leonvankammen-00
|
||||
</pre>
|
||||
|
||||
|
||||
}-->
|
||||
|
||||
.# Abstract
|
||||
|
||||
This draft offers a specification for embedding macros in existing 3D scenes/assets, to offer simple interactions and configure the renderer further.<br>
|
||||
Together with URI Fragments, it allows for rich immersive experiences without the need of a complicated sandboxed scripting languages.
|
||||
|
||||
> Almost every idea in this document is demonstrated at [https://xrfragment.org](https://xrfragment.org), as this spec was created during the [XR Fragments](https://xrfragment.org) spec.
|
||||
|
||||
{mainmatter}
|
||||
|
||||
# Introduction
|
||||
|
||||
How can we add more features to existing text & 3D scenes, without introducing new dataformats?<br>
|
||||
Historically, there's many attempts to create the ultimate markuplanguage or 3D fileformat.<br>
|
||||
Their lowest common denominator is: (co)authoring using plain text.<br>
|
||||
Therefore, XR Macros allows us to enrich/connect existing dataformats, by offering a polyglot notation based on existing notations:<br>
|
||||
|
||||
1. getting/setting common used 3D properties using querystring- or JSON-notation
|
||||
1. targeting 3D properties using the lightweight query notation present in [XR Fragments](https://xrfragment.org)
|
||||
|
||||
> NOTE: The chapters in this document are ordered from highlevel to lowlevel (technical) as much as possible
|
||||
|
||||
# Core principle
|
||||
|
||||
1. XR Macros use querystrings, but are HTML-agnostic (though pseudo-XR Fragment browsers **can** be implemented on top of HTML/Javascript).
|
||||
1. An XR Macro is 3D metadata which starts with '!' (`!clickme: fog=0,10` e.g.)
|
||||
1. Metadata-values can contain the `|` symbol to 🎲 roundrobin variable values (`!toggleme: fog=0,10|fog=0,1000` e.g.)
|
||||
1. XR Macros acts as simple eventhandlers for URI Fragments: they are automatically published on the ([XR Fragments](https://xrfragment.org)) hashbus, to act as events (so more serious scripting languages can react to them as well).
|
||||
1. XR Macros can assign object metadata (`!setlocal: foo=1` writes `foo:1` metadata to the object containing the `!setlocal` metadata)
|
||||
1. XR Macros can assign global metadata (`!setfoo: #foo=1` writes `foo:1` metadata to the root scene-node)
|
||||
|
||||
> These very simple principles allow for rich interactions and dynamic querying
|
||||
|
||||
# Conventions and Definitions
|
||||
|
||||
See appendix below in case certain terms are not clear.
|
||||
|
||||
# List of XR Macros
|
||||
|
||||
(XR) Macros can be embedded in 3D assets/scenes.<br>
|
||||
Macros enrich existing spatial content with a lowcode, limited logic-layer, by recursive (economic) use of the querystring syntax (which search engines and [XR Fragments](https://xrfragment.org) already uses.<br>
|
||||
This is done by allowing string/integer variables, and the `|` symbol to roundrobin variable values.<br>
|
||||
Macros also act as events, so more serious scripting languages can react to them as well.<br>
|
||||
|
||||
| key | type | example (JSON) | function | existing compatibility |
|
||||
|--------------|----------|------------------------|---------------------|----------------------------------------|
|
||||
| `@bg` | string | `"@bg":"#cube"` | bg: binds fog near/far based to cube x/y/z (anim) values | custom property in 3D fileformats |
|
||||
| `@fog` | string | `"@fog":"#cube"` | fog: binds fog near/far based to cube x/y (anim) values | custom property in 3D fileformats |
|
||||
| `@scroll` | string | `"@scroll":"#cube"` | texturescrolling: binds texture x/y/rot based to cube x/y/z (anim) values | custom property in 3D fileformats |
|
||||
| `@emissive` | string | `"@emissive":"#cube"` | day/night/mood: binds material's emissive value to cube x/y/z (anim) values | custom property in 3D fileformats |
|
||||
|
||||
## Usecase: click object
|
||||
|
||||
| custom property | value | trigger when |
|
||||
|-----------------|--------------------------|------------------------|
|
||||
| !clickme | bg=1,1,1&foo=2 | object clicked |
|
||||
|
||||
## Usecase: conditional click object
|
||||
|
||||
| custom property | value | trigger when |
|
||||
|-----------------|--------------------------|-----------------------------|
|
||||
| # | foo=1 | scene |
|
||||
| !clickme | q=foo>2&bg=1,1,1 | object clicked and foo > 2 |
|
||||
|
||||
> when a user clicks an object with the custom properties above, it should set the backgroundcolor to `1,1,1` when `foo` is greater than `2` (see previous example)
|
||||
|
||||
## Usecase: click object (roundrobin)
|
||||
|
||||
| custom property | value | trigger when |
|
||||
|-----------------|--------------------------|------------------------|
|
||||
| !cycleme | day|noon|night | object clicked |
|
||||
| day | bg=1,1,1 | roundrobin |
|
||||
| noon | bg=0.5,0.5,0.5 | roundrobin |
|
||||
| night | bg=0,0,0&foo=2 | roundrobin |
|
||||
|
||||
> when a user clicks an object with the custom properties above, it should trigger either `day` `noon` or `night` in roundrobin fashion.
|
||||
|
||||
## Usecase: click object or URI fragment, and scene load trigger
|
||||
|
||||
| custom property | value | trigger when |
|
||||
|-----------------|--------------------------|------------------------|
|
||||
| # | random | scene loaded |
|
||||
| #random | random | URL contains #random |
|
||||
| !random | day|noon|night | #random, # or click |
|
||||
| day | bg=1,1,1 | roundrobin |
|
||||
| noon | bg=0.5,0.5,0.5 | roundrobin |
|
||||
| night | bg=0,0,0&foo=2 | roundrobin |
|
||||
|
||||
## Usecase: present context menu with options
|
||||
|
||||
| custom property | value | trigger when |
|
||||
|-----------------|--------------------------|------------------------|
|
||||
| !random | !day|!noon|!night | clicked in contextmenu |
|
||||
| !day | bg=1,1,1 | clicked in contextmenu |
|
||||
| !noon | bg=0.5,0.5,0.5 | clicked in contextmenu |
|
||||
| !night | bg=0,0,0&foo=2 | clicked in contextmenu |
|
||||
|
||||
> When interacting with an object with more than one `!`-macro, the XR Browser should offer a contextmenu to execute a macro.
|
||||
|
||||
In a similar way, when **any** `!`-macro is present on the sceneroot, the XR Browser should offer a context-menu to execute those macro's.
|
||||
|
||||
## Event Bubble-flow
|
||||
|
||||
click object with (`!clickme`:`AR` or `!clickme`: `!reset` e.g.)
|
||||
```
|
||||
◻
|
||||
│
|
||||
└── does current object contain this property-key (`AR` or `!reset` e.g.)?
|
||||
└── no: is there any (root)object containing property `AR`
|
||||
└── yes: evaluate its (roundrobin) XR macro-value(s) (and exit)
|
||||
└── no: trigger URL: #AR
|
||||
```
|
||||
|
||||
click object with (`!clickme`:`#AR|#VR` e.g.)
|
||||
```
|
||||
◻
|
||||
│
|
||||
└── apply the roundrobin (rotate the options, value `#AR` becomes `#VR` upon next click)
|
||||
└── is there any object with property-key (`#AR` e.g.)?
|
||||
└── no: just update the URL to `#AR`
|
||||
└── yes: apply its value to the scene, and update the URL to `#AR`
|
||||
|
||||
click object with (`!clickme`:`!foo|!bar|!flop` e.g.)
|
||||
```
|
||||
◻
|
||||
│
|
||||
└── apply the roundrobin (rotate the options, value `!foo` becomes `!bar` upon next click)
|
||||
└── is there any object with property-key (`!foo` e.g.)?
|
||||
└── no: do nothing
|
||||
└── yes: apply its value to the scene
|
||||
```
|
||||
|
||||
> Note that only macro's can trigger roundrobin values or contextmenu's, as well as roundrobin values never ending up in the toplevel URL.
|
||||
|
||||
# Security Considerations
|
||||
|
||||
|
||||
# IANA Considerations
|
||||
|
||||
This document has no IANA actions.
|
||||
|
||||
# Acknowledgments
|
||||
|
||||
* [NLNET](https://nlnet.nl)
|
||||
* [Future of Text](https://futureoftext.org)
|
||||
* [visual-meta.info](https://visual-meta.info)
|
||||
|
||||
# Appendix: Definitions
|
||||
|
||||
|definition | explanation |
|
||||
|----------------------|-------------------------------------------------------------------------------------------------------------------------------|
|
||||
|scene | a (local/remote) 3D scene or 3D file (index.gltf e.g.) |
|
||||
|3D object | an object inside a scene characterized by vertex-, face- and customproperty data. |
|
||||
|XR fragments | URI Fragment with spatial hints like `#pos=0,0,0&t=1,100` e.g. |
|
||||
|query | an URI Fragment-operator which queries object(s) from a scene like `#q=cube` |
|
||||
|FPS | frames per second in spatial experiences (games,VR,AR e.g.), should be as high as possible |
|
||||
|`◻` | ascii representation of an 3D object/mesh |
|
||||
|(un)obtrusive | obtrusive: wrapping human text/thought in XML/HTML/JSON obfuscates human text into a salad of machine-symbols and words |
|
||||
|
||||
|
|
@ -1,392 +0,0 @@
|
|||
|
||||
|
||||
|
||||
|
||||
Internet Engineering Task Force L.R. van Kammen
|
||||
Internet-Draft 24 September 2025
|
||||
Intended status: Informational
|
||||
|
||||
|
||||
|
||||
XR Macros
|
||||
draft-XRMACROS-leonvankammen-00
|
||||
|
||||
Abstract
|
||||
|
||||
This draft offers a specification for embedding macros in existing 3D
|
||||
scenes/assets, to offer simple interactions and configure the
|
||||
renderer further.
|
||||
Together with URI Fragments, it allows for rich immersive experiences
|
||||
without the need of a complicated sandboxed scripting languages.
|
||||
|
||||
Almost every idea in this document is demonstrated at
|
||||
https://xrfragment.org (https://xrfragment.org), as this spec was
|
||||
created during the XR Fragments (https://xrfragment.org) spec.
|
||||
|
||||
Status of This Memo
|
||||
|
||||
This Internet-Draft is submitted in full conformance with the
|
||||
provisions of BCP 78 and BCP 79.
|
||||
|
||||
Internet-Drafts are working documents of the Internet Engineering
|
||||
Task Force (IETF). Note that other groups may also distribute
|
||||
working documents as Internet-Drafts. The list of current Internet-
|
||||
Drafts is at https://datatracker.ietf.org/drafts/current/.
|
||||
|
||||
Internet-Drafts are draft documents valid for a maximum of six months
|
||||
and may be updated, replaced, or obsoleted by other documents at any
|
||||
time. It is inappropriate to use Internet-Drafts as reference
|
||||
material or to cite them other than as "work in progress."
|
||||
|
||||
This Internet-Draft will expire on 28 March 2026.
|
||||
|
||||
Copyright Notice
|
||||
|
||||
Copyright (c) 2025 IETF Trust and the persons identified as the
|
||||
document authors. All rights reserved.
|
||||
|
||||
This document is subject to BCP 78 and the IETF Trust's Legal
|
||||
Provisions Relating to IETF Documents (https://trustee.ietf.org/
|
||||
license-info) in effect on the date of publication of this document.
|
||||
Please review these documents carefully, as they describe your rights
|
||||
and restrictions with respect to this document. Code Components
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 1]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
extracted from this document must include Revised BSD License text as
|
||||
described in Section 4.e of the Trust Legal Provisions and are
|
||||
provided without warranty as described in the Revised BSD License.
|
||||
|
||||
Table of Contents
|
||||
|
||||
1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 2
|
||||
2. Core principle . . . . . . . . . . . . . . . . . . . . . . . 2
|
||||
3. Conventions and Definitions . . . . . . . . . . . . . . . . . 3
|
||||
4. List of XR Macros . . . . . . . . . . . . . . . . . . . . . . 3
|
||||
4.1. Usecase: click object . . . . . . . . . . . . . . . . . . 4
|
||||
4.2. Usecase: conditional click object . . . . . . . . . . . . 4
|
||||
4.3. Usecase: click object (roundrobin) . . . . . . . . . . . 5
|
||||
4.4. Usecase: click object or URI fragment, and scene load
|
||||
trigger . . . . . . . . . . . . . . . . . . . . . . . . . 5
|
||||
4.5. Usecase: present context menu with options . . . . . . . 6
|
||||
4.6. Event Bubble-flow . . . . . . . . . . . . . . . . . . . . 6
|
||||
5. Security Considerations . . . . . . . . . . . . . . . . . . . 7
|
||||
6. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 7
|
||||
7. Acknowledgments . . . . . . . . . . . . . . . . . . . . . . . 7
|
||||
8. Appendix: Definitions . . . . . . . . . . . . . . . . . . . . 7
|
||||
|
||||
1. Introduction
|
||||
|
||||
How can we add more features to existing text & 3D scenes, without
|
||||
introducing new dataformats?
|
||||
Historically, there's many attempts to create the ultimate
|
||||
markuplanguage or 3D fileformat.
|
||||
Their lowest common denominator is: (co)authoring using plain text.
|
||||
Therefore, XR Macros allows us to enrich/connect existing
|
||||
dataformats, by offering a polyglot notation based on existing
|
||||
notations:
|
||||
|
||||
1. getting/setting common used 3D properties using querystring- or
|
||||
JSON-notation
|
||||
2. targeting 3D properties using the lightweight query notation
|
||||
present in XR Fragments (https://xrfragment.org)
|
||||
|
||||
| NOTE: The chapters in this document are ordered from highlevel to
|
||||
| lowlevel (technical) as much as possible
|
||||
|
||||
2. Core principle
|
||||
|
||||
1. XR Macros use querystrings, but are HTML-agnostic (though pseudo-
|
||||
XR Fragment browsers *can* be implemented on top of HTML/
|
||||
Javascript).
|
||||
2. An XR Macro is 3D metadata which starts with '!' (!clickme:
|
||||
fog=0,10 e.g.)
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 2]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
3. Metadata-values can contain the | symbol to 🎲 roundrobin variable
|
||||
values (!toggleme: fog=0,10|fog=0,1000 e.g.)
|
||||
4. XR Macros acts as simple eventhandlers for URI Fragments: they
|
||||
are automatically published on the (XR Fragments
|
||||
(https://xrfragment.org)) hashbus, to act as events (so more
|
||||
serious scripting languages can react to them as well).
|
||||
5. XR Macros can assign object metadata (!setlocal: foo=1 writes
|
||||
foo:1 metadata to the object containing the !setlocal metadata)
|
||||
6. XR Macros can assign global metadata (!setfoo: #foo=1 writes
|
||||
foo:1 metadata to the root scene-node)
|
||||
|
||||
| These very simple principles allow for rich interactions and
|
||||
| dynamic querying
|
||||
|
||||
3. Conventions and Definitions
|
||||
|
||||
See appendix below in case certain terms are not clear.
|
||||
|
||||
4. List of XR Macros
|
||||
|
||||
(XR) Macros can be embedded in 3D assets/scenes.
|
||||
Macros enrich existing spatial content with a lowcode, limited logic-
|
||||
layer, by recursive (economic) use of the querystring syntax (which
|
||||
search engines and XR Fragments (https://xrfragment.org) already
|
||||
uses.
|
||||
This is done by allowing string/integer variables, and the | symbol
|
||||
to roundrobin variable values.
|
||||
Macros also act as events, so more serious scripting languages can
|
||||
react to them as well.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 3]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
+=========+======+===================+=================+=============+
|
||||
|key |type |example (JSON) |function |existing |
|
||||
| | | | |compatibility|
|
||||
+=========+======+===================+=================+=============+
|
||||
|@bg |string|"@bg":"#cube" |bg: binds fog |custom |
|
||||
| | | |near/far based to|property in |
|
||||
| | | |cube x/y/z (anim)|3D |
|
||||
| | | |values |fileformats |
|
||||
+---------+------+-------------------+-----------------+-------------+
|
||||
|@fog |string|"@fog":"#cube" |fog: binds fog |custom |
|
||||
| | | |near/far based to|property in |
|
||||
| | | |cube x/y (anim) |3D |
|
||||
| | | |values |fileformats |
|
||||
+---------+------+-------------------+-----------------+-------------+
|
||||
|@scroll |string|"@scroll":"#cube" |texturescrolling:|custom |
|
||||
| | | |binds texture |property in |
|
||||
| | | |x/y/rot based to |3D |
|
||||
| | | |cube x/y/z (anim)|fileformats |
|
||||
| | | |values | |
|
||||
+---------+------+-------------------+-----------------+-------------+
|
||||
|@emissive|string|"@emissive":"#cube"|day/night/mood: |custom |
|
||||
| | | |binds material's |property in |
|
||||
| | | |emissive value to|3D |
|
||||
| | | |cube x/y/z (anim)|fileformats |
|
||||
| | | |values | |
|
||||
+---------+------+-------------------+-----------------+-------------+
|
||||
|
||||
Table 1
|
||||
|
||||
4.1. Usecase: click object
|
||||
|
||||
+=================+================+================+
|
||||
| custom property | value | trigger when |
|
||||
+=================+================+================+
|
||||
| !clickme | bg=1,1,1&foo=2 | object clicked |
|
||||
+-----------------+----------------+----------------+
|
||||
|
||||
Table 2
|
||||
|
||||
4.2. Usecase: conditional click object
|
||||
|
||||
+=================+==================+============================+
|
||||
| custom property | value | trigger when |
|
||||
+=================+==================+============================+
|
||||
| # | foo=1 | scene |
|
||||
+-----------------+------------------+----------------------------+
|
||||
| !clickme | q=foo>2&bg=1,1,1 | object clicked and foo > 2 |
|
||||
+-----------------+------------------+----------------------------+
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 4]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
Table 3
|
||||
|
||||
| when a user clicks an object with the custom properties above, it
|
||||
| should set the backgroundcolor to 1,1,1 when foo is greater than 2
|
||||
| (see previous example)
|
||||
|
||||
4.3. Usecase: click object (roundrobin)
|
||||
|
||||
+=================+================+================+
|
||||
| custom property | value | trigger when |
|
||||
+=================+================+================+
|
||||
| !cycleme | day|noon|night | object clicked |
|
||||
+-----------------+----------------+----------------+
|
||||
| day | bg=1,1,1 | roundrobin |
|
||||
+-----------------+----------------+----------------+
|
||||
| noon | bg=0.5,0.5,0.5 | roundrobin |
|
||||
+-----------------+----------------+----------------+
|
||||
| night | bg=0,0,0&foo=2 | roundrobin |
|
||||
+-----------------+----------------+----------------+
|
||||
|
||||
Table 4
|
||||
|
||||
| when a user clicks an object with the custom properties above, it
|
||||
| should trigger either day noon or night in roundrobin fashion.
|
||||
|
||||
4.4. Usecase: click object or URI fragment, and scene load trigger
|
||||
|
||||
+=================+================+======================+
|
||||
| custom property | value | trigger when |
|
||||
+=================+================+======================+
|
||||
| # | random | scene loaded |
|
||||
+-----------------+----------------+----------------------+
|
||||
| #random | random | URL contains #random |
|
||||
+-----------------+----------------+----------------------+
|
||||
| !random | day|noon|night | #random, # or click |
|
||||
+-----------------+----------------+----------------------+
|
||||
| day | bg=1,1,1 | roundrobin |
|
||||
+-----------------+----------------+----------------------+
|
||||
| noon | bg=0.5,0.5,0.5 | roundrobin |
|
||||
+-----------------+----------------+----------------------+
|
||||
| night | bg=0,0,0&foo=2 | roundrobin |
|
||||
+-----------------+----------------+----------------------+
|
||||
|
||||
Table 5
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 5]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
4.5. Usecase: present context menu with options
|
||||
|
||||
+=================+================+========================+
|
||||
| custom property | value | trigger when |
|
||||
+=================+================+========================+
|
||||
| !random | !day | !noon |
|
||||
+-----------------+----------------+------------------------+
|
||||
| !day | bg=1,1,1 | clicked in contextmenu |
|
||||
+-----------------+----------------+------------------------+
|
||||
| !noon | bg=0.5,0.5,0.5 | clicked in contextmenu |
|
||||
+-----------------+----------------+------------------------+
|
||||
| !night | bg=0,0,0&foo=2 | clicked in contextmenu |
|
||||
+-----------------+----------------+------------------------+
|
||||
|
||||
Table 6
|
||||
|
||||
| When interacting with an object with more than one !-macro, the XR
|
||||
| Browser should offer a contextmenu to execute a macro.
|
||||
|
||||
In a similar way, when *any* !-macro is present on the sceneroot, the
|
||||
XR Browser should offer a context-menu to execute those macro's.
|
||||
|
||||
4.6. Event Bubble-flow
|
||||
|
||||
click object with (!clickme:AR or !clickme: !reset e.g.)
|
||||
|
||||
◻
|
||||
│
|
||||
└── does current object contain this property-key (`AR` or `!reset` e.g.)?
|
||||
└── no: is there any (root)object containing property `AR`
|
||||
└── yes: evaluate its (roundrobin) XR macro-value(s) (and exit)
|
||||
└── no: trigger URL: #AR
|
||||
|
||||
click object with (!clickme:#AR|#VR e.g.)
|
||||
|
||||
◻
|
||||
│
|
||||
└── apply the roundrobin (rotate the options, value `#AR` becomes `#VR` upon next click)
|
||||
└── is there any object with property-key (`#AR` e.g.)?
|
||||
└── no: just update the URL to `#AR`
|
||||
└── yes: apply its value to the scene, and update the URL to `#AR`
|
||||
|
||||
click object with (`!clickme`:`!foo|!bar|!flop` e.g.)
|
||||
|
||||
◻ │
|
||||
└── apply the roundrobin (rotate the options, value !foo becomes !bar
|
||||
upon next click) └── is there any object with property-key (!foo
|
||||
e.g.)? └── no: do nothing └── yes: apply its value to the scene ```
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 6]
|
||||
|
||||
Internet-Draft XR Macros September 2025
|
||||
|
||||
|
||||
| Note that only macro's can trigger roundrobin values or
|
||||
| contextmenu's, as well as roundrobin values never ending up in the
|
||||
| toplevel URL.
|
||||
|
||||
5. Security Considerations
|
||||
|
||||
6. IANA Considerations
|
||||
|
||||
This document has no IANA actions.
|
||||
|
||||
7. Acknowledgments
|
||||
|
||||
* NLNET (https://nlnet.nl)
|
||||
* Future of Text (https://futureoftext.org)
|
||||
* visual-meta.info (https://visual-meta.info)
|
||||
|
||||
8. Appendix: Definitions
|
||||
|
||||
+===============+===================================================+
|
||||
| definition | explanation |
|
||||
+===============+===================================================+
|
||||
| scene | a (local/remote) 3D scene or 3D file |
|
||||
| | (index.gltf e.g.) |
|
||||
+---------------+---------------------------------------------------+
|
||||
| 3D object | an object inside a scene characterized by |
|
||||
| | vertex-, face- and customproperty data. |
|
||||
+---------------+---------------------------------------------------+
|
||||
| XR fragments | URI Fragment with spatial hints like |
|
||||
| | #pos=0,0,0&t=1,100 e.g. |
|
||||
+---------------+---------------------------------------------------+
|
||||
| query | an URI Fragment-operator which queries |
|
||||
| | object(s) from a scene like #q=cube |
|
||||
+---------------+---------------------------------------------------+
|
||||
| FPS | frames per second in spatial experiences |
|
||||
| | (games,VR,AR e.g.), should be as high as |
|
||||
| | possible |
|
||||
+---------------+---------------------------------------------------+
|
||||
| ◻ | ascii representation of an 3D object/mesh |
|
||||
+---------------+---------------------------------------------------+
|
||||
| (un)obtrusive | obtrusive: wrapping human text/thought in |
|
||||
| | XML/HTML/JSON obfuscates human text into |
|
||||
| | a salad of machine-symbols and words |
|
||||
+---------------+---------------------------------------------------+
|
||||
|
||||
Table 7
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
van Kammen Expires 28 March 2026 [Page 7]
|
||||
|
|
@ -1,381 +0,0 @@
|
|||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<!-- name="GENERATOR" content="github.com/mmarkdown/mmark Mmark Markdown Processor - mmark.miek.nl" -->
|
||||
<rfc version="3" ipr="trust200902" docName="draft-XRMACROS-leonvankammen-00" submissionType="IETF" category="info" xml:lang="en" xmlns:xi="http://www.w3.org/2001/XInclude" indexInclude="true" consensus="true">
|
||||
|
||||
<front>
|
||||
<title>XR Macros</title><seriesInfo value="draft-XRMACROS-leonvankammen-00" stream="IETF" status="informational" name="XR-Macros"></seriesInfo>
|
||||
<author initials="L.R." surname="van Kammen" fullname="L.R. van Kammen"><organization></organization><address><postal><street></street>
|
||||
</postal></address></author><date/>
|
||||
<area>Internet</area>
|
||||
<workgroup>Internet Engineering Task Force</workgroup>
|
||||
|
||||
<abstract>
|
||||
<t>This draft offers a specification for embedding macros in existing 3D scenes/assets, to offer simple interactions and configure the renderer further.<br />
|
||||
|
||||
Together with URI Fragments, it allows for rich immersive experiences without the need of a complicated sandboxed scripting languages.</t>
|
||||
<t>Almost every idea in this document is demonstrated at <eref target="https://xrfragment.org">https://xrfragment.org</eref>, as this spec was created during the <eref target="https://xrfragment.org">XR Fragments</eref> spec.</t>
|
||||
</abstract>
|
||||
|
||||
</front>
|
||||
|
||||
<middle>
|
||||
|
||||
<section anchor="introduction"><name>Introduction</name>
|
||||
<t>How can we add more features to existing text & 3D scenes, without introducing new dataformats?<br />
|
||||
|
||||
Historically, there's many attempts to create the ultimate markuplanguage or 3D fileformat.<br />
|
||||
|
||||
Their lowest common denominator is: (co)authoring using plain text.<br />
|
||||
|
||||
Therefore, XR Macros allows us to enrich/connect existing dataformats, by offering a polyglot notation based on existing notations:<br />
|
||||
</t>
|
||||
|
||||
<ol spacing="compact">
|
||||
<li>getting/setting common used 3D properties using querystring- or JSON-notation</li>
|
||||
<li>targeting 3D properties using the lightweight query notation present in <eref target="https://xrfragment.org">XR Fragments</eref></li>
|
||||
</ol>
|
||||
<blockquote><t>NOTE: The chapters in this document are ordered from highlevel to lowlevel (technical) as much as possible</t>
|
||||
</blockquote></section>
|
||||
|
||||
<section anchor="core-principle"><name>Core principle</name>
|
||||
|
||||
<ol spacing="compact">
|
||||
<li>XR Macros use querystrings, but are HTML-agnostic (though pseudo-XR Fragment browsers <strong>can</strong> be implemented on top of HTML/Javascript).</li>
|
||||
<li>An XR Macro is 3D metadata which starts with '!' (<tt>!clickme: fog=0,10</tt> e.g.)</li>
|
||||
<li>Metadata-values can contain the <tt>|</tt> symbol to 🎲 roundrobin variable values (<tt>!toggleme: fog=0,10|fog=0,1000</tt> e.g.)</li>
|
||||
<li>XR Macros acts as simple eventhandlers for URI Fragments: they are automatically published on the (<eref target="https://xrfragment.org">XR Fragments</eref>) hashbus, to act as events (so more serious scripting languages can react to them as well).</li>
|
||||
<li>XR Macros can assign object metadata (<tt>!setlocal: foo=1</tt> writes <tt>foo:1</tt> metadata to the object containing the <tt>!setlocal</tt> metadata)</li>
|
||||
<li>XR Macros can assign global metadata (<tt>!setfoo: #foo=1</tt> writes <tt>foo:1</tt> metadata to the root scene-node)</li>
|
||||
</ol>
|
||||
<blockquote><t>These very simple principles allow for rich interactions and dynamic querying</t>
|
||||
</blockquote></section>
|
||||
|
||||
<section anchor="conventions-and-definitions"><name>Conventions and Definitions</name>
|
||||
<t>See appendix below in case certain terms are not clear.</t>
|
||||
</section>
|
||||
|
||||
<section anchor="list-of-xr-macros"><name>List of XR Macros</name>
|
||||
<t>(XR) Macros can be embedded in 3D assets/scenes.<br />
|
||||
|
||||
Macros enrich existing spatial content with a lowcode, limited logic-layer, by recursive (economic) use of the querystring syntax (which search engines and <eref target="https://xrfragment.org">XR Fragments</eref> already uses.<br />
|
||||
|
||||
This is done by allowing string/integer variables, and the <tt>|</tt> symbol to roundrobin variable values.<br />
|
||||
|
||||
Macros also act as events, so more serious scripting languages can react to them as well.<br />
|
||||
</t>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>key</th>
|
||||
<th>type</th>
|
||||
<th>example (JSON)</th>
|
||||
<th>function</th>
|
||||
<th>existing compatibility</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td><tt>@bg</tt></td>
|
||||
<td>string</td>
|
||||
<td><tt>"@bg":"#cube"</tt></td>
|
||||
<td>bg: binds fog near/far based to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><tt>@fog</tt></td>
|
||||
<td>string</td>
|
||||
<td><tt>"@fog":"#cube"</tt></td>
|
||||
<td>fog: binds fog near/far based to cube x/y (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><tt>@scroll</tt></td>
|
||||
<td>string</td>
|
||||
<td><tt>"@scroll":"#cube"</tt></td>
|
||||
<td>texturescrolling: binds texture x/y/rot based to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><tt>@emissive</tt></td>
|
||||
<td>string</td>
|
||||
<td><tt>"@emissive":"#cube"</tt></td>
|
||||
<td>day/night/mood: binds material's emissive value to cube x/y/z (anim) values</td>
|
||||
<td>custom property in 3D fileformats</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<section anchor="usecase-click-object"><name>Usecase: click object</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!clickme</td>
|
||||
<td>bg=1,1,1&foo=2</td>
|
||||
<td>object clicked</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table></section>
|
||||
|
||||
<section anchor="usecase-conditional-click-object"><name>Usecase: conditional click object</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>#</td>
|
||||
<td>foo=1</td>
|
||||
<td>scene</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!clickme</td>
|
||||
<td>q=foo>2&bg=1,1,1</td>
|
||||
<td>object clicked and foo > 2</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table><blockquote><t>when a user clicks an object with the custom properties above, it should set the backgroundcolor to <tt>1,1,1</tt> when <tt>foo</tt> is greater than <tt>2</tt> (see previous example)</t>
|
||||
</blockquote></section>
|
||||
|
||||
<section anchor="usecase-click-object-roundrobin"><name>Usecase: click object (roundrobin)</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!cycleme</td>
|
||||
<td>day|noon|night</td>
|
||||
<td>object clicked</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table><blockquote><t>when a user clicks an object with the custom properties above, it should trigger either <tt>day</tt> <tt>noon</tt> or <tt>night</tt> in roundrobin fashion.</t>
|
||||
</blockquote></section>
|
||||
|
||||
<section anchor="usecase-click-object-or-uri-fragment-and-scene-load-trigger"><name>Usecase: click object or URI fragment, and scene load trigger</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>#</td>
|
||||
<td>random</td>
|
||||
<td>scene loaded</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>#random</td>
|
||||
<td>random</td>
|
||||
<td>URL contains #random</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!random</td>
|
||||
<td>day|noon|night</td>
|
||||
<td>#random, # or click</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>roundrobin</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table></section>
|
||||
|
||||
<section anchor="usecase-present-context-menu-with-options"><name>Usecase: present context menu with options</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>custom property</th>
|
||||
<th>value</th>
|
||||
<th>trigger when</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>!random</td>
|
||||
<td>!day</td>
|
||||
<td>!noon</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!day</td>
|
||||
<td>bg=1,1,1</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!noon</td>
|
||||
<td>bg=0.5,0.5,0.5</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>!night</td>
|
||||
<td>bg=0,0,0&foo=2</td>
|
||||
<td>clicked in contextmenu</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table><blockquote><t>When interacting with an object with more than one <tt>!</tt>-macro, the XR Browser should offer a contextmenu to execute a macro.</t>
|
||||
</blockquote><t>In a similar way, when <strong>any</strong> <tt>!</tt>-macro is present on the sceneroot, the XR Browser should offer a context-menu to execute those macro's.</t>
|
||||
</section>
|
||||
|
||||
<section anchor="event-bubble-flow"><name>Event Bubble-flow</name>
|
||||
<t>click object with (<tt>!clickme</tt>:<tt>AR</tt> or <tt>!clickme</tt>: <tt>!reset</tt> e.g.)</t>
|
||||
|
||||
<artwork><![CDATA[ ◻
|
||||
│
|
||||
└── does current object contain this property-key (`AR` or `!reset` e.g.)?
|
||||
└── no: is there any (root)object containing property `AR`
|
||||
└── yes: evaluate its (roundrobin) XR macro-value(s) (and exit)
|
||||
└── no: trigger URL: #AR
|
||||
]]>
|
||||
</artwork>
|
||||
<t>click object with (<tt>!clickme</tt>:<tt>#AR|#VR</tt> e.g.)</t>
|
||||
|
||||
<artwork><![CDATA[ ◻
|
||||
│
|
||||
└── apply the roundrobin (rotate the options, value `#AR` becomes `#VR` upon next click)
|
||||
└── is there any object with property-key (`#AR` e.g.)?
|
||||
└── no: just update the URL to `#AR`
|
||||
└── yes: apply its value to the scene, and update the URL to `#AR`
|
||||
|
||||
click object with (`!clickme`:`!foo|!bar|!flop` e.g.)
|
||||
]]>
|
||||
</artwork>
|
||||
<t>◻
|
||||
│<br />
|
||||
└── apply the roundrobin (rotate the options, value <tt>!foo</tt> becomes <tt>!bar</tt> upon next click)
|
||||
└── is there any object with property-key (<tt>!foo</tt> e.g.)?
|
||||
└── no: do nothing
|
||||
└── yes: apply its value to the scene
|
||||
```</t>
|
||||
<blockquote><t>Note that only macro's can trigger roundrobin values or contextmenu's, as well as roundrobin values never ending up in the toplevel URL.</t>
|
||||
</blockquote></section>
|
||||
</section>
|
||||
|
||||
<section anchor="security-considerations"><name>Security Considerations</name>
|
||||
</section>
|
||||
|
||||
<section anchor="iana-considerations"><name>IANA Considerations</name>
|
||||
<t>This document has no IANA actions.</t>
|
||||
</section>
|
||||
|
||||
<section anchor="acknowledgments"><name>Acknowledgments</name>
|
||||
|
||||
<ul spacing="compact">
|
||||
<li><eref target="https://nlnet.nl">NLNET</eref></li>
|
||||
<li><eref target="https://futureoftext.org">Future of Text</eref></li>
|
||||
<li><eref target="https://visual-meta.info">visual-meta.info</eref></li>
|
||||
</ul>
|
||||
</section>
|
||||
|
||||
<section anchor="appendix-definitions"><name>Appendix: Definitions</name>
|
||||
<table>
|
||||
<thead>
|
||||
<tr>
|
||||
<th>definition</th>
|
||||
<th>explanation</th>
|
||||
</tr>
|
||||
</thead>
|
||||
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>scene</td>
|
||||
<td>a (local/remote) 3D scene or 3D file (index.gltf e.g.)</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>3D object</td>
|
||||
<td>an object inside a scene characterized by vertex-, face- and customproperty data.</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>XR fragments</td>
|
||||
<td>URI Fragment with spatial hints like <tt>#pos=0,0,0&t=1,100</tt> e.g.</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>query</td>
|
||||
<td>an URI Fragment-operator which queries object(s) from a scene like <tt>#q=cube</tt></td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>FPS</td>
|
||||
<td>frames per second in spatial experiences (games,VR,AR e.g.), should be as high as possible</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td><tt>◻</tt></td>
|
||||
<td>ascii representation of an 3D object/mesh</td>
|
||||
</tr>
|
||||
|
||||
<tr>
|
||||
<td>(un)obtrusive</td>
|
||||
<td>obtrusive: wrapping human text/thought in XML/HTML/JSON obfuscates human text into a salad of machine-symbols and words</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table></section>
|
||||
|
||||
</middle>
|
||||
|
||||
</rfc>
|
||||
17
index.html
17
index.html
File diff suppressed because one or more lines are too long
Loading…
Add table
Reference in a new issue