diff --git a/doc/RFC_XR_Fragments.md b/doc/RFC_XR_Fragments.md
index 3e7f3fb..fb97ddc 100644
--- a/doc/RFC_XR_Fragments.md
+++ b/doc/RFC_XR_Fragments.md
@@ -290,7 +290,7 @@ For example, to render a portal with a preview-version of the scene, create an 3
1. set the position of the camera accordingly to the vector3 values of `#pos`
1. `rot` sets the rotation of the camera (only for non-VR/AR headsets)
1. `t` sets the playbackspeed and animation-range of the current scene animation(s) or `src`-mediacontent (video/audioframes e.g., use `t=0,7,7` to 'STOP' at frame 7 e.g.)
-1. in case an `href` does not mention any `pos`-coordinate, `pos=0,0,0` will be assumed
+1. after scene load: in case an `href` does not mention any `pos`-coordinate, `pos=0,0,0` will be assumed
Here's an ascii representation of a 3D scene-graph which contains 3D objects `◻` and their metadata:
@@ -374,11 +374,12 @@ Resizing will be happen accordingly to its placeholder object `aquariumcube`, se
7. external `src` values should respect the fallback link mechanism (see [broken links](#broken-links)
8. when the placeholder object is a 2D plane, but the mimetype is 3D, then render the spatial content on that plane via a stencil buffer.
9. src-values are non-recursive: when linking to an external object (`src: foo.fbx#bar`), then `src`-metadata on object `bar` should be ignored.
-10. clicking on external `src`-values always allow sourceportation: teleporting to the origin URI to which the object belongs.
+10. an external `src`-value should always allow a sourceportation icon within 3 meter: teleporting to the origin URI to which the object belongs.
11. when only one object was cherrypicked (`#cube` e.g.), set its position to `0,0,0`
-12. equirectangular detection: when the width of an image is twice the height (aspect 2:1), an equirectangular projection is assumed.
-13. when the enduser clicks an href with `#t=1,0,0` (play) will be applied to all src mediacontent with a timeline (mp4/mp3 e.g.)
+12. when the enduser clicks an href with `#t=1,0,0` (play) will be applied to all src mediacontent with a timeline (mp4/mp3 e.g.)
+13. a non-euclidian portal can be rendered for flat 3D objects (using stencil buffer e.g.) in case ofspatial `src`-values (an object `#world3` or URL `world3.fbx` e.g.).
+* `model/gltf-binary`
* `model/gltf+json`
* `image/png`
* `image/jpg`
@@ -388,7 +389,7 @@ Resizing will be happen accordingly to its placeholder object `aquariumcube`, se
[» example 3D asset](https://github.com/coderofsalvation/xrfragment/blob/main/example/assets/src.gltf#L192)
[» discussion](https://github.com/coderofsalvation/xrfragment/issues/4)
-# Navigating content (internal/outbound href portals)
+# Navigating content href portals
navigation, portals & mutations
@@ -404,11 +405,11 @@ navigation, portals & mutations
4. URL navigation should always be reflected in the client (in case of javascript: see [[here](https://github.com/coderofsalvation/xrfragment/blob/dev/src/3rd/js/three/navigator.js) for an example navigator).
-5. In XR mode, the navigator back/forward-buttons should be always visible (using a wearable e.g., see [[here](https://github.com/coderofsalvation/xrfragment/blob/dev/example/aframe/sandbox/index.html#L26-L29) for an example wearable)
+7. In XR mode, the navigator back/forward-buttons should be always visible (using a wearable e.g., see [[here](https://github.com/coderofsalvation/xrfragment/blob/dev/example/aframe/sandbox/index.html#L26-L29) for an example wearable)
-6. in case of navigating to a new [[pos)ition, ''first'' navigate to the ''current position'' so that the ''back-button'' of the ''browser-history'' always refers to the previous position (see [[here](https://github.com/coderofsalvation/xrfragment/blob/main/src/3rd/js/three/xrf/href.js#L97))
+8. in case of navigating to a new [[pos)ition, ''first'' navigate to the ''current position'' so that the ''back-button'' of the ''browser-history'' always refers to the previous position (see [[here](https://github.com/coderofsalvation/xrfragment/blob/main/src/3rd/js/three/xrf/href.js#L97))
-7. portal-rendering: a 2:1 ratio texture-material indicates an equirectangular projection
+9. ignore previous rule in special cases, like clicking an `href` using camera-portal collision (the back-button would cause a teleport-loop)
[» example implementation](https://github.com/coderofsalvation/xrfragment/blob/main/src/3rd/js/three/xrf/href.js)
[» example 3D asset](https://github.com/coderofsalvation/xrfragment/blob/main/example/assets/href.gltf#L192)
@@ -498,7 +499,7 @@ It's simple but powerful syntax which allows filtering the scene using searcheng
1. filters are a way to traverse a scene, and filter objects based on their name, tag- or property-values.
-* see [an (outdated) example video here](https://coderofsalvation.github.io/xrfragment.media/queries.mp4) which used a dedicated `q=` variable (now deprecated)
+* see [an (outdated) example video here](https://coderofsalvation.github.io/xrfragment.media/queries.mp4) which used a dedicated `q=` variable (now deprecated and usable directly)
## including/excluding
@@ -509,7 +510,7 @@ It's simple but powerful syntax which allows filtering the scene using searcheng
| `=>` `=<`| compare float or int number (`#price=>4` e.g.) |
| `/` | reference to root-scene.
Useful in case of (preventing) showing/hiding objects in nested scenes (instanced by `src`) (*) |
-> \* = `#q=-/cube` hides object `cube` only in the root-scene (not nested `cube` objects)
`#q=-cube` hides both object `cube` in the root-scene AND nested `skybox` objects |
+> \* = `#-/cube` hides object `cube` only in the root-scene (not nested `cube` objects)
`#-cube` hides both object `cube` in the root-scene AND nested `skybox` objects |
[» example implementation](https://github.com/coderofsalvation/xrfragment/blob/main/src/3rd/js/three/xrf/q.js)
[» example 3D asset](https://github.com/coderofsalvation/xrfragment/blob/main/example/assets/filter.gltf#L192)
@@ -861,12 +862,12 @@ For example:
│ │
│ index.gltf │
│ │ │
- │ │ #: #q=-offlinetext │
+ │ │ #: #-offlinetext │
│ │ │
│ ├── ◻ buttonA │
│ │ └ href: http://foo.io/campagne.fbx │
│ │ └ href@404: ipfs://foo.io/campagne.fbx │
- │ │ └ href@400: #q=clienterrortext │
+ │ │ └ href@400: #clienterrortext │
│ │ └ ◻ offlinetext │
│ │ │
│ └── ◻ embeddedObject <--------- the meshdata inside embeddedObject will (not)
@@ -890,9 +891,9 @@ Consider 3D scenes linking to eachother using these `href` values:
These links would all show visible links to math-tagged objects in the scene.
To filter out non-related objects one could take it a step further using filters:
-* `href: schoolA.edu/projects.gltf#math&q=-topics math`
-* `href: schoolB.edu/projects.gltf#math&q=-courses math`
-* `href: university.edu/projects.gltf#math&q=-theme math`
+* `href: schoolA.edu/projects.gltf#math&-topics math`
+* `href: schoolB.edu/projects.gltf#math&-courses math`
+* `href: university.edu/projects.gltf#math&-theme math`
> This would hide all object tagged with `topic`, `courses` or `theme` (including math) so that later only objects tagged with `math` will be visible
@@ -944,7 +945,7 @@ This document has no IANA actions.
|placeholder object | a 3D object which with src-metadata (which will be replaced by the src-data.) |
|src | (HTML-piggybacked) metadata of a 3D object which instances content |
|href | (HTML-piggybacked) metadata of a 3D object which links to content |
-|filter | URI Fragment(s) which show/hide object(s) in a scene based on name/tag/property (`#q=cube&-price=>3`) |
+|filter | URI Fragment(s) which show/hide object(s) in a scene based on name/tag/property (`#cube&-price=>3`) |
|visual-meta | [visual-meta](https://visual.meta.info) data appended to text/books/papers which is indirectly visible/editable in XR. |
|requestless metadata | metadata which never spawns new requests (unlike RDF/HTML, which can cause framerate-dropping, hence not used a lot in games) |
|FPS | frames per second in spatial experiences (games,VR,AR e.g.), should be as high as possible |
@@ -952,6 +953,7 @@ This document has no IANA actions.
|extrospective | outward sensemaking ("I'm fairly sure John is a person who lives in oklahoma") |
|`◻` | 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 |
+|flat 3D object | a 3D object of which all verticies share a plane |
|BibTeX | simple tagging/citing/referencing standard for plaintext |
|BibTag | a BibTeX tag |
|(hashtag)bibs | an easy to speak/type/scan tagging SDL ([see here](https://github.com/coderofsalvation/hashtagbibs) which expands to BibTex/JSON/XML |
diff --git a/example/assets/index.glb b/example/assets/index.glb
index 1d71851..ecfa84b 100644
Binary files a/example/assets/index.glb and b/example/assets/index.glb differ
diff --git a/index.html b/index.html
index 4e7e364..66ee137 100644
--- a/index.html
+++ b/index.html
@@ -782,7 +782,7 @@ Error message and password prompt
{"created":"20230427174739986","text":"> in \u003Ca href=\"./dist/xrfragment.js\" target=\"_blank\">xrfragment.js\u003C/a>, and \u003Ca href=\"./dist/xrfragment.module.js\" target=\"_blank\">xrfragment.module.js\u003C/a>\n\nParse a fragment (key/value) and add it to an object store (if valid).\n\n> **NOTE**: You probably want to use the higher-level [URI.parse(url,filter)](#%E2%86%AA%20URI.parse%28url%2Cfilter%29) which calls this function\n\n| args | type | example | comment |\n|-|-|-|-|\n| key | string | `pos` | |\n| value | string | `1.2,3,4` | datatype must comply with [spec](#List%20of%20fragments) |\n| store | object | {} | will not be touched if validation failed, |\n\n> returns true if validated, otherwise false \n\nhere are some interactive examples:\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = {}\nok = xrfragment.Parser.parse('pos','1.2,2,3',frags)\nconsole.log( frags.pos )\n\n\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n\u003Cbr>\n\nUnknown or fragments with wrong type will be rejected:\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = {}\nok = xrfragment.Parser.parse('pos','true',frags)\nconsole.log( frags.pos )\n\n\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n# Spec \n\n> version 0.2 @ 2023-06-27T11:10:08+0200 [](https://github.com/coderofsalvation/xrfragment/actions)\n\nIn case your programming language has no parser ([check here](https://github.com/coderofsalvation/xrfragment/tree/main/dist)) you can [crosscompile it](https://github.com/coderofsalvation/xrfragment/blob/main/build.hxml), or roll your own `Parser.parse(k,v,store)` using the spec:\n\n1. requirement: receive arguments: key (string), value (string), store (writable associative array/object)\n1. add keys without values to store as [predefined view](predefined_view)\n1. check if fragment is official XR Fragment\n1. guess the type of the value (string,int,float,x,y,z,color,args,query)\n1. don't add to store if value-type is incorrect\n1. if valid, add to store\n1. prefix non-offical fragment key's with underscore (and add to store)\n\n> icanhazcode? yes, see [Parser.hx](https://github.com/coderofsalvation/xrfragment/blob/main/src/xrfragment/Parser.hx)\n\n# Tests\n \nthe spec is tested with [JSON unittests](./../src/spec) consumed by [Test.hx](./../src/Test.hx) to cross-test all languages.\n\n","tags":"[[The parser]]","title":"↪ Parser.parse(k,v,store)","modified":"20230804100127236","type":"text/markdown"},
{"created":"20230622103539209","text":"> in \u003Ca href=\"./dist/xrfragment.js\" target=\"_blank\">xrfragment.js\u003C/a>, and \u003Ca href=\"./dist/xrfragment.module.js\" target=\"_blank\">xrfragment.module.js\u003C/a>\n\nParses a [[query|queries]] and returns it in object form\n\n| args | type | example |\n|-|-|-|\n| query | string | `foo -bar`\u003Cbr>`price:1 price:\u003C10`\u003Cbr>`.someclass`|\n\n> returns each query-argument as annotated key(objects)\n\nThe AFRAME/THREE library does this for you, but here's an interactive example of parsing a query using the [[parser for other languages|https://github.com/coderofsalvation/xrfragment/tree/main/dist]]:\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = new xrfragment.Query('cube -ball_inside_cube')\nconsole.log(frags.q)\n\n\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n# Spec \n\n> version 0.2 [](https://github.com/coderofsalvation/xrfragment/actions) generated by `make doc` @ 2023-06-27T11:40:29+0200\n\nIn case your programming language has no parser ([check here](https://github.com/coderofsalvation/xrfragment/tree/main/dist)) you can [crosscompile it](https://github.com/coderofsalvation/xrfragment/blob/main/build.hxml), or roll your own `Query.parse(str)` using the spec:\n\n1. requirement: receive arguments: query (string)\n1. create an associative array/object to store query-arguments as objects\n1. detect object id's & properties `foo:1` and `foo` (reference regex: `/^.*:[>\u003C=!]?/` )\n1. detect excluders like `-foo`,`-foo:1`,`-.foo`,`-/foo` (reference regex: `/^-/` )\n1. detect root selectors like `/foo` (reference regex: `/^[-]?\\//` )\n1. detect class selectors like `.foo` (reference regex: `/^[-]?class$/` )\n1. detect number values like `foo:1` (reference regex: `/^[0-9\\.]+$/` )\n1. expand aliases like `.foo` into `class:foo`\n1. for every query token split string on `:`\n1. create an empty array `rules`\n1. then strip key-operator: convert \"-foo\" into \"foo\" \n1. add operator and value to rule-array\n1. therefore we we set `id` to `true` or `false` (false=excluder `-`)\n1. and we set `root` to `true` or `false` (true=`/` root selector is present)\n1. we convert key '/foo' into 'foo'\n1. finally we add the key/value to the store (`store.foo = {id:false,root:true}` e.g.)\n\n> icanhazcode? yes, see [Query.hx](https://github.com/coderofsalvation/xrfragment/blob/main/src/xrfragment/Query.hx)\n\n# Tests\n \nthe spec is tested with [JSON unittests](./../src/spec) consumed by [Test.hx](./../src/Test.hx) to cross-test all languages.\n\n","tags":"[[The parser]]","title":"↪ Query(query)","modified":"20230804095924737","type":"text/markdown","list-after":"List of fragments"},
{"created":"20230427150948872","text":"> in \u003Ca href=\"./dist/xrfragment.js\" target=\"_blank\">xrfragment.js\u003C/a>, and \u003Ca href=\"./dist/xrfragment.module.js\" target=\"_blank\">xrfragment.module.js\u003C/a>\n\nValidates and turns a XR fragment string (`document.location.hash` in javascript e.g.) into objectform using [Parser.parse(k,v,store)](#↪%20Parser.parse(k,v,store)).\n\n| args | type | example | comment |\n|-|-|-|-|\n| url | string | `#pos=1.2,3,4`\u003Cbr>`#pos=1.2,3,4&t=1,2`| |\n| filter | integer\u003Cbr>(bitmask) | `0` = no filter\u003Cbr>`XRF.NAVIGATOR` (default)\u003Cbr>`XRF.EMBEDDED`\u003Cbr>`XRF.PV_OVERRIDE` | filter out fragments which are not flagged with this flag.\u003Cbr>\u003Cbr>For example, parsing with `XRF.NAVIGATOR` will ignore any fragments which are not flagged as such (like `scale` in case of top-level URI navigation).\u003Cbr>On the other hand, `XRF.EMBEDDED` makes sense when parsing an embedded URI (`src: other.gltf#scale=2,2,2` e.g.)\u003Cbr> |\n\n> returns an object with validated fragment(values) as key(objects)\n\nhere are some interactive examples:\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = xrfragment.URI.parse('#pos=1.0,2.0,3.0')\nconsole.log( frags.pos )\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n\u003Cbr>\n\nYou can combine them with the `&` character:\u003Cbr>\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = xrfragment.URI.parse('#t=1,100&pos=1,2,3.1')\nconsole.log( frags.t )\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\nUnallowed fragments can be filtered out:\u003Cbr>\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">XRF = xrfragment.XRF\nfrags = xrfragment.URI.parse('#scale=1,2,3', XRF.NAVIGATOR )\nconsole.log( frags )\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n> The above is perfect for top-level browser navigation (which should not parse \u003Cb>embedded-only\u003C/b> XR Fragments like `scale` or [queries](#queries))\n\nAnother example for parsing embedded assets\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">XRF = xrfragment.XRF\nmymodel = {userData:{src: \"other.gltf#scale=2,2,2\"}} // mock THREE.js\nfrags = xrfragment.URI.parse( mymodel.userData.src, XRF.EMBEDDED )\nconsole.log( frags.scale.x )\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n> The above is perfect for embedded content (`scale` fragment is allowed here)\n\nFinally, parsing \u003Cb>custom\u003C/b> framework-specific fragments is also possible (they are prefixed with `_`)\u003Cbr>\n\n\u003Cdiv>\n \u003Ctextarea spellcheck=\"false\" autofocus class=\"sandboxify\">frags = xrfragment.URI.parse(\"#pos=0,0,1&foo=123&bar=flop\")\nconsole.log(frags._foo.int)\u003C/textarea>\n\t\u003Cpre class=\"result\">\u003C/pre>\n\u003C/div>\n\n> The above is perfect for embedded content (`scale` fragment is allowed here)\n\n# Spec\n\n> version 0.2 [](https://github.com/coderofsalvation/xrfragment/actions) generated by `make doc` @ 2023-06-27T11:18:12+0200\n\n### XR Fragment URI Grammar \n\n```\n reserved = gen-delims / sub-delims\n gen-delims = \"#\" / \"&\" \n sub-delims = \",\" / \"=\"\n```\n\n> Example: `://foo.com/my3d.asset#pos=1,0,0&prio=-5&t=0,100`\n\n| Explanation | |\n|-|-|\n| `pos=1,2,3` | vector/coordinate argument e.g. |\n| `pos=1,2,3&rot=0,90,0&q=.foo` | combinators |\n\nIn case your programming language has no parser ([check here](https://github.com/coderofsalvation/xrfragment/tree/main/dist)) you can [crosscompile it](https://github.com/coderofsalvation/xrfragment/blob/main/build.hxml), or roll your own `Parser.parse(k,v,store)` using the spec:\n\n1. store key/values into a associative array or dynamic object\n1. fragment URI starts with `#`\n1. fragments are split by `&`\n1. loop thru each fragment\n1. for each fragment split on `=` to separate key/values \n1. fragment-values are urlencoded (space becomes `+` using `encodeUriComponent` e.g.)\n1. for every recognized fragment key/value-pair call [Parser.parse](#%E2%86%AA%20Parser.parse%28k%2Cv%2Cstore%29)\n\n> icanhazcode? yes, see [URI.hx](https://github.com/coderofsalvation/xrfragment/blob/main/src/xrfragment/URI.hx)\n\n# Tests\n \nthe spec is tested with [JSON unittests](./../src/spec) consumed by [Test.hx](./../src/Test.hx) to cross-test all languages.\n","tags":"[[The parser]]","title":"↪ URI.parse(url,filter)","modified":"20230804095944433","type":"text/markdown","list-after":"List of fragments"},
-{"created":"20230830155016049","text":"\n> **DISCLAIMER**: XR Macros is a tiny logic-layer which falls outside of the scope of the XR Fragment spec (for now). \u003Cbr>They currently demonstrate features beyond the addressibility/navigation/embedding-focus of XR Fragments, and fall more into the demo/authoring-side of things. Every XR macro demonstration should potentially be replaced by piggybacking \u003Ca href=\"https://github.com/omigroup/gltf-extensions\" target=\"_blank\">OMI extensions\u003C/a> (when they support the usecase).\n\u003Cbr>\n\nXR Macros are a tiny roundrobin logic-layer **defined inside** 3D assets/scenes. \u003Cbr>\nMacros introduce a lowest-common-denominator logic-layer, by recursive, economic re-use of the querystring syntax (which the XR Fragment parser already uses).\u003Cbr>\n\u003Cbr>\nThe example XR macro's are based on common usecases & features found in 3D engines, to offer an lowcode alternative to basic experiences without requiring a scripting language.\u003Cbr>\n(Sometimes a spreadsheet will do instead of a programming language).\u003Cbr>\n\n# Spec\n\nBelow is the related section of the spec (full spec here: [[HTML|doc/RFC_XR_Macros.html]], [[TXT|doc/RFC_XR_Fragments.txt]], [[XML|doc/RFC_XR_Fragments.xml]])\n\n\u003Ciframe src=\"doc/RFC_XR_Macros.html#core-principle\" frameborder=\"0\" class=\"spec\">\u003C/iframe>\n\n# Example macros\n\n| XR macro | type | access | supported\u003Cbr>in\u003Cbr>sandbox |info |\n|----------|------|--------------|-|------|\n| **fov** |int 1..360|🔓 💥 👩 🔗|✔| hints field of view to renderer|\n| **clip** |[vector2](#vector) |🔓 💥 👩 🔗|✔| hints camera clipping to renderer |\n| **bg** |[vector3](#vector)|🔓 💥 👩 🔗|✔| hints background rgb values (0..255) to renderer\n| **fog** |[vector2](#vector)|🔓 💥 👩 🔗|✔| hints fog settings to renderer |\n| **env** |string|🔓 💥 🔗|✔|query selector / object manipulation|\n| [show](#show) |integer [0-1] |🔒 🎲 💥 🔗| ✔|show/hide [queried](#queries) object(s)|\n| [mov](#mov) |[vector3](#vector ) |🔒 🎲 💥 🔗| ✔|move [queried](#queries) object(s) \u003Cb>relatively\u003C/b> (instead of \u003Cb>absolute\u003C/b> using `#pos=`)|\n| [scale](#scale) |[vector3](#vector ) |🔓 🎲 💥 🔗| ✔|scale [queried](#queries) object(s) |\n| **prio** |int|🔒||asset loading linking|\n| **gravity** |[vector3](#vector) |🔓 💥 🔗||animation|\n| **physics** |[vector3](#vector) |🔓 💥 🔗||animation|\n| **namespace** |string|🔒||author / metadata|\n| **SPDX** |string|🔒||author / metadata|\n| **unit** |string|🔒||author / metadata|\n| **description** |string|🔒||author / metadata|\n| **session** |[url](#url ) |🔓 💥 👩 🔗 ✋?||multiparty|\n\n🔒 = value(s) can only be defined in 3D asset (immutable)\u003Cbr>\n🔓 = value(s) can be overwritten in certain context (by url)\u003Cbr>\n🎲 = multiple values will be roundrobin'ed (`#pos=0,0,0|1,0,0` e.g.)\u003Cbr>\n💥 = value(s) can be overwritten by [predefined_view](#predefined_view)\u003Cbr>\n👩 = value(s) can be overwritten when user clicks `href` (value) or top-level URL change(see [How it works](#How%20it%20works))\u003Cbr>\n🔗 = value(s) can be overwritten when 3D asset is embedded/linked as `src` value\u003Cbr>\n✋? = value(s) can be overwritten by offering confirmation/undo to user\u003Cbr>\u003Cbr>\n\n\u003Cdiv style=\"max-width:600px\">\n\u003C$videojs controls=\"controls\" aspectratio=\"16:9\" preload=\"auto\" poster=\"\" fluid=\"fluid\" class=\"vjs-big-play-centered\">\n \u003Csource src=\"https://coderofsalvation.github.io/xrfragment.media/fovfogclip.mp4\" type=\"video/mp4\"/>\n\u003C/$videojs>\n\u003C/div>\n\nfor more info see [How it works](#How%20it%20works)","tags":"Reference","title":"⏯️ XR Macros","modified":"20230921092420344","type":"text/markdown"},
+{"created":"20230830155016049","text":"\n> **DISCLAIMER**: XR Macros is a tiny logic-layer which falls outside of the scope of the XR Fragment spec (for now). \u003Cbr>They currently demonstrate features beyond the addressibility/navigation/embedding-focus of XR Fragments, and fall more into the demo/authoring-side of things. Every XR macro demonstration should potentially be replaced by piggybacking \u003Ca href=\"https://github.com/omigroup/gltf-extensions\" target=\"_blank\">OMI extensions\u003C/a> (when they support the usecase).\n\u003Cbr>\n\nXR Macros are a tiny roundrobin logic-layer **defined inside** 3D assets/scenes. \u003Cbr>\nMacros introduce a lowest-common-denominator logic-layer, by recursive, economic re-use of the querystring syntax (which the XR Fragment parser already uses).\u003Cbr>\n\u003Cbr>\nThe example XR macro's are based on common usecases & features found in 3D engines, to offer an lowcode alternative to basic experiences without requiring a scripting language.\u003Cbr>\n(Sometimes a spreadsheet will do instead of a programming language).\u003Cbr>\n\n# Spec\n\nBelow is the related section of the spec (full spec here: [[HTML|doc/RFC_XR_Macros.html]], [[TXT|doc/RFC_XR_Fragments.txt]], [[XML|doc/RFC_XR_Fragments.xml]])\n\n\u003Ciframe src=\"doc/RFC_XR_Macros.html#core-principle\" frameborder=\"0\" class=\"spec\">\u003C/iframe>\n\n# Example macros\n\n| XR macro | type | access | supported\u003Cbr>in\u003Cbr>sandbox |info |\n|----------|------|--------------|-|------|\n| **fov** |int 1..360|🔓 💥 👩 🔗|✔| hints field of view to renderer|\n| **clip** |[vector2](#vector) |🔓 💥 👩 🔗|✔| hints camera clipping to renderer |\n| **bg** |[vector3](#vector)|🔓 💥 👩 🔗|✔| hints background rgb values (0..255) to renderer\n| **fog** |[vector2](#vector)|🔓 💥 👩 🔗|✔| hints fog settings to renderer |\n| **env** |string|🔓 💥 🔗|✔|query selector / object manipulation|\n| [show](#show) |integer [0-1] |🔒 🎲 💥 🔗| ✔|show/hide [queried](#queries) object(s)|\n| [mov](#mov) |[vector3](#vector ) |🔒 🎲 💥 🔗| ✔|move [queried](#queries) object(s) \u003Cb>relatively\u003C/b> (instead of \u003Cb>absolute\u003C/b> using `#pos=`)|\n| [scale](#scale) |[vector3](#vector ) |🔓 🎲 💥 🔗| ✔|scale [queried](#queries) object(s) |\n| **prio** |int|🔒||asset loading linking|\n| **gravity** |[vector3](#vector) |🔓 💥 🔗||animation|\n| **physics** |[vector3](#vector) |🔓 💥 🔗||animation|\n| **namespace** |string|🔒||author / metadata|\n| **SPDX** |string|🔒||author / metadata|\n| **unit** |string|🔒||author / metadata|\n| **description** |string|🔒||author / metadata|\n| **session** |[url](#url ) |🔓 💥 👩 🔗 ✋?||multiparty|\n\n🔒 = value(s) can only be defined in 3D asset (immutable)\u003Cbr>\n🔓 = value(s) can be overwritten in certain context (by url)\u003Cbr>\n🎲 = multiple values will be roundrobin'ed (`#pos=0,0,0|1,0,0` e.g.)\u003Cbr>\n💥 = value(s) can be overwritten by [predefined_view](#predefined_view)\u003Cbr>\n👩 = value(s) can be overwritten when user clicks `href` (value) or top-level URL change(see [How it works](#How%20it%20works))\u003Cbr>\n🔗 = value(s) can be overwritten when 3D asset is embedded/linked as `src` value\u003Cbr>\n✋? = value(s) can be overwritten by offering confirmation/undo to user\u003Cbr>\u003Cbr>\n\n\u003Cdiv style=\"max-width:600px\">\n\u003C$videojs controls=\"controls\" aspectratio=\"16:9\" preload=\"auto\" poster=\"\" fluid=\"fluid\" class=\"vjs-big-play-centered\">\n \u003Csource src=\"https://coderofsalvation.github.io/xrfragment.media/fovfogclip.mp4\" type=\"video/mp4\"/>\n\u003C/$videojs>\n\u003C/div>\n\nfor more info see [How it works](#How%20it%20works)","tags":"","title":"⏯️ XR Macros","modified":"20231122145951626","type":"text/markdown"},
{"created":"20230830155951504","text":"this document was [moved here](#📜%20XR%20Fragments)","tags":"","title":"📜 XR fragments","modified":"20230830160038977","type":"text/markdown"},
{"created":"20230427172131986","text":"## URL Addressibility spec \n\n> v0.2 [](https://github.com/coderofsalvation/xrfragment/actions)\u003Cbr>Bare minimum addressibility URI fragments for spatial browsers & apps. \u003Cbr>It allows users to share 4D (intent) URLs to eachother like:\u003Cbr>`https://linux.world/#pos=0,0,1&t=1,100`\u003Cbr>`linuxapp://conference/nixworkshop?newuser#pos=0,0,2&t=2,200`\u003Cbr>`androidapp://page1?tutorial#pos=0,0,1&t1,100`\u003Cbr>\n\n| URI fragment | type | functionality |\n|----------|------|---------------|\n| [\u003Cb>#pos\u003C/b>=0,0,0](#pos) |[vector3](#vector ) | (re)position camera |\n| [\u003Cb>#rot\u003C/b>=0,90,0](#rot) |[vector3](#vector ) |rotate camera |\n| [\u003Cb>#t\u003C/b>=0,100](#t) |[vector3](#vector ) | (re)position time of (scene-animation or [src](#src)-mediacontent) looprange |\n| **#...** |[predefined view](#predefined_view ) or XRWG tag [selection](#Selection%20of%20interest)| referencing of objects, or local repositioning of the user|\n\n## Navigator metadata spec\n\n\n| custom property | type | functionality |\n|----------|------|--------------|\n| [href](#href) | string (uri or [predefined view](#predefined_view)) | href navigation / portals / teleporting to other XR documents|\n| [src](#src) |string (uri or [predefined view](#predefined_view) or [query](#queries)) | lazyloading of (partial) local/external assets/scenes (3D iframes) |\n| tag |string|space-separated tagging of objects (like CSS class) for XRWG and or queries|\n\n> An Easy **nocode** way to add metadata is [by adding custom properties in blender e.g.](https://docs.blender.org/manual/en/2.79/data_system/custom_properties.html). [Click here](#href) for more info\n\n## Query spec\n\n| URI Fragment| custom property | type | usage |\n|----------------|-------------|------|-------|\n| [#q=cube](#queries) |string | filtering of objects |\n\n> [click here](#queries) for more info\n\nFor more info see [How it works](#How%20it%20works)\n\n> \u003Cb>See XR Macro's\u003C/b> for [extra interaction features](#⏯️%20XR%20Macros)","tags":"Reference","title":"📜 XR Fragments","modified":"20231012150033456","type":"text/markdown"},
{"text":"(function(){\n\n/*jslint node: true, browser: true */\n/*global $tw: false */\n\"use strict\";\n\n/*\nenables js via \u003C\u003Cscript>> and disables with \u003C\u003Cscript 0>>\n*/\n\nexports.name = \"script\";\n\nexports.params = [\n\t{name: \"run\"},\n];\n\n/*\nRun the macro\n*/\nexports.run = function(run) {\n var off = run ? run.toLowerCase() : false;\n\tif(off && [\"0\",\"no\",\"off\",\"false\"].indexOf(off) > -1) {\n\t\t$tw.config.htmlUnsafeElements = [\"script\"];\n\t} else {\n\t\t$tw.config.htmlUnsafeElements = [];\n\t}\nreturn \"\";\n};\n})();","type":"application/javascript","title":"$:/.tb/macros/script","tags":"","module-type":"macro","modifier":"Tobias Beer","modified":"20150129192206415","creator":"Tobias Beer","created":"20150129001857442"},
@@ -842,7 +842,7 @@ Error message and password prompt
{"created":"20230425164931250","title":"$:/state/folded/AFRAME template","text":"show","modified":"20230425164935940"},
{"created":"20230425164931250","title":"$:/state/folded/GLSL shader template","text":"show","modified":"20230425164939576"},
{"created":"20230424142403302","text":"checked","title":"$:/state/import/select-all","modified":"20230424142404392"},
-{"created":"20230423163640468","title":"$:/state/notebook-sidebar","text":"no","modified":"20231121143302609"},
+{"created":"20230423163640468","title":"$:/state/notebook-sidebar","text":"no","modified":"20231122150009072"},
{"created":"20230423163641722","title":"$:/state/notebook-sidebar-section","text":"Reference","modified":"20231013135341050"},
{"created":"20230427102758222","title":"$:/state/plugin-info--1887569658-$:/plugins/ihm/tidgraph--50210113","text":"documentation","modified":"20230427102759911"},
{"created":"20230427092525294","title":"$:/state/plugin-info--391242618-$:/plugins/tiddlywiki/browser-storage","text":"yes","modified":"20230427092525375"},
@@ -850,7 +850,7 @@ Error message and password prompt
{"created":"20230424092949812","title":"$:/state/plugin-info-1024395336-$:/plugins/tiddlywiki/codemirror--1574138004","text":"contents","modified":"20230425143706081"},
{"created":"20230424093627704","title":"$:/state/plugin-info-833095967-Draft of '$:/core'---1604322978","text":"readme","modified":"20230424093629208"},
{"created":"20230423163649566","title":"$:/state/showeditpreview","text":"yes","modified":"20231121145510823"},
-{"created":"20230504174435745","title":"$:/state/sidebar","text":"no","modified":"20231121142235428"},
+{"created":"20230504174435745","title":"$:/state/sidebar","text":"no","modified":"20231122145923387"},
{"created":"20230423163453188","title":"$:/state/tab--1963855381","text":"$:/themes/nico/notebook/themetweaks","modified":"20230523124919651"},
{"created":"20230427092954391","title":"$:/state/tab--2112689675","text":"$:/core/ui/ControlPanel/Basics","modified":"20230523124903522"},
{"created":"20230424093058379","title":"$:/state/tab--697582678","text":"$:/core/ui/ControlPanel/Settings/TiddlyWiki","modified":"20230427093030201"},
@@ -869,7 +869,7 @@ Error message and password prompt
{"created":"20230622104329622","title":"$:/state/toc/Reference/js/AFRAME-THREE.js--403145756","text":"open","modified":"20230622104329622"},
{"created":"20230622111759784","title":"$:/state/toc/Reference/The parser-THREE.js--403145756","text":"open","modified":"20230622111759784"},
{"title":"$:/status/RequireReloadDueToPluginChange","text":"no"},
-{"title":"$:/StoryList","text":"","list":"[[XR Fragments]]"},
+{"title":"$:/StoryList","created":"20231122145939418","text":"","list":"[[XR Fragments]]","modified":"20231122145939418"},
{"created":"20230423163445948","title":"$:/theme","text":"$:/themes/nico/notebook","modified":"20230423163445948"},
{"text":"{\n \"tiddlers\": {\n \"$:/themes/nico/notebook/LICENSE\": {\n \"title\": \"$:/themes/nico/notebook/LICENSE\",\n \"created\": \"20200419141443144\",\n \"modified\": \"20210118213330307\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\nMIT License Copyright (c) 2020 [[Nicolas Petton|https://nicolas.petton.fr]] nicolas@petton.fr\\n\\nPermission is hereby granted, free of charge, to any person obtaining a copy\\nof this software and associated documentation files (the \\\"Software\\\"), to deal\\nin the Software without restriction, including without limitation the rights\\nto use, copy, modify, merge, publish, distribute, sublicense, and/or sell\\ncopies of the Software, and to permit persons to whom the Software is furnished\\nto do so, subject to the following conditions:\\n\\nThe above copyright notice and this permission notice (including the next\\nparagraph) shall be included in all copies or substantial portions of the\\nSoftware.\\n\\nTHE SOFTWARE IS PROVIDED \\\"AS IS\\\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\\nIMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS\\nFOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS\\nOR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,\\nWHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF\\nOR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\\n\"\n },\n \"$:/themes/nico/notebook/themetweaks\": {\n \"title\": \"$:/themes/nico/notebook/themetweaks\",\n \"created\": \"20201217172915960\",\n \"modified\": \"20210123211851680\",\n \"tags\": \"$:/tags/ControlPanel/Appearance\",\n \"caption\": \"{{$:/language/ThemeTweaks/ThemeTweaks}}\",\n \"text\": \"\\\\define lingo-base() $:/language/ThemeTweaks/\\n\\nYou can tweak certain aspects of the ''Notebook'' theme.\\n\\n! \u003C\u003Clingo Options>>\\n\\n|\u003C$link to=\\\"$:/themes/nico/notebook/options/stickytitles\\\">\u003C\u003Clingo Options/StickyTitles>>\u003C/$link>\u003Cbr>//\u003C\u003Clingo Options/StickyTitles/Hint>>// |\u003C$select tiddler=\\\"$:/themes/nico/notebook/options/stickytitles\\\">\u003Coption value=\\\"no\\\">{{$:/language/No}}\u003C/option>\u003Coption value=\\\"yes\\\">{{$:/language/Yes}}\u003C/option>\u003C/$select> |\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/options/codewrapping\\\">\u003C\u003Clingo Options/CodeWrapping>>\u003C/$link> |\u003C$select tiddler=\\\"$:/themes/tiddlywiki/vanilla/options/codewrapping\\\">\u003Coption value=\\\"pre\\\">{{$:/language/No}}\u003C/option>\u003Coption value=\\\"pre-wrap\\\">{{$:/language/Yes}}\u003C/option>\u003C/$select> |\\n|\u003C$link to=\\\"$:/themes/nico/notebook/options/reveal-tiddler-controls-on-hover\\\">Reveal tiddler controls on mouseover\u003C/$link> |\u003C$select tiddler=\\\"$:/themes/nico/notebook/options/reveal-tiddler-controls-on-hover\\\">\u003Coption value=\\\"no\\\">{{$:/language/No}}\u003C/option>\u003Coption value=\\\"yes\\\">{{$:/language/Yes}}\u003C/option>\u003C/$select> |\\n\\n! \u003C\u003Clingo Settings>>\\n\\n|\u003C$link to=\\\"$:/themes/nico/notebook/settings/fontfamily\\\">\u003C\u003Clingo Settings/FontFamily>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/settings/fontfamily\\\" default=\\\"\\\" tag=\\\"input\\\"/> | |\\n|\u003C$link to=\\\"$:/themes/nico/notebook/settings/codefontfamily\\\">\u003C\u003Clingo Settings/CodeFontFamily>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/settings/codefontfamily\\\" default=\\\"\\\" tag=\\\"input\\\"/> | |\\n|\u003C$link to=\\\"$:/themes/nico/notebook/settings/editorfontfamily\\\">\u003C\u003Clingo Settings/EditorFontFamily>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/settings/editorfontfamily\\\" default=\\\"\\\" tag=\\\"input\\\"/> | |\\n\\n! \u003C\u003Clingo Metrics>>\\n\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/metrics/fontsize\\\">\u003C\u003Clingo Metrics/FontSize>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/tiddlywiki/vanilla/metrics/fontsize\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/metrics/lineheight\\\">\u003C\u003Clingo Metrics/LineHeight>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/tiddlywiki/vanilla/metrics/lineheight\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/metrics/bodyfontsize\\\">\u003C\u003Clingo Metrics/BodyFontSize>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/metrics/bodyfontsize\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/metrics/bodylineheight\\\">\u003C\u003Clingo Metrics/BodyLineHeight>>\u003C/$link> |\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/metrics/bodylineheight\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint\\\">\u003C\u003Clingo Metrics/SidebarBreakpoint>>\u003C/$link>\u003Cbr>//\u003C\u003Clingo Metrics/SidebarBreakpoint/Hint>>// |^\u003C$edit-text tiddler=\\\"$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/nico/notebook/metrics/sidebar-width\\\">\u003C\u003Clingo Metrics/SidebarWidth>>\u003C/$link>\u003Cbr>//\u003C\u003Clingo Metrics/SidebarWidth/Hint>>// |^\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/metrics/sidebar-width\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n|\u003C$link to=\\\"$:/themes/nico/notebook/metrics/story-width\\\">\u003C\u003Clingo Metrics/StoryWidth>>\u003C/$link>\u003Cbr>//\u003C\u003Clingo Metrics/StoryWidth/Hint>>// |^\u003C$edit-text tiddler=\\\"$:/themes/nico/notebook/metrics/story-width\\\" default=\\\"\\\" tag=\\\"input\\\"/> |\\n\\n\"\n },\n \"$:/themes/nico/notebook/base\": {\n \"title\": \"$:/themes/nico/notebook/base\",\n \"created\": \"20200419141443144\",\n \"modified\": \"20210120224227503\",\n \"tags\": \"$:/tags/Stylesheet\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\rules only filteredtranscludeinline transcludeinline macrodef macrocallinline\\n\\n\\\\define if-sidebar(text)\\n \u003C$reveal state=\\\"$:/state/notebook-sidebar\\\" type=\\\"match\\\" text=\\\"yes\\\">\\n $text$\\n \u003C/$reveal>\\n\\\\end\\n\\n\\\\define if-reveal-tiddler-controls-on-hover(text)\\n \u003C$reveal state=\\\"$:/themes/nico/notebook/options/reveal-tiddler-controls-on-hover\\\" type=\\\"match\\\" text=\\\"yes\\\">\\n $text$\\n \u003C/$reveal>\\n\\\\end\\n \\n/* Top and bottom bars */\\n\\n/* Hide the top-right bar */\\n.tc-topbar.tc-topbar-right {\\n display: none;\\n}\\n\\ndiv.tc-sidebar-header {\\n padding: 0;\\n min-height: 0;\\n}\\n\\n.tc-story-river {\\n padding: 6px 0 !important;\\n width: 100% !important;\\n max-width: {{$:/themes/nico/notebook/metrics/story-width}} !important;\\n margin: 0 auto !important;\\n margin-top: 34px !important;\\n}\\n\\ndiv.tc-tiddler-frame {\\n width: 100%;\\n margin: 20px 0;\\n background: \u003C\u003Ccolour tiddler-background>>;\\n box-shadow: 0 5px 20px rgba(0,0,0, 0.12);\\n border-radius: 6px;\\n padding: 42px 60px 60px 60px;\\n}\\n\\nh1.tc-site-title {\\n margin-top: 14px;\\n font-size: 1.5em !important;\\n}\\n\\n.nc-bar {\\n padding: 10px;\\n height: {{$:/themes/nico/notebook/metrics/topbar-height}};\\n background: \u003C\u003Ccolour page-background>>;\\n display: flex;\\n justify-content: space-between;\\n}\\n\\n.nc-topbar-wrapper {\\n position: fixed;\\n top: 0;\\n left: 0;\\n right: 0;\\n /* The z-index needs to be above the z-index used in tiddlers in zoomin view */\\n z-index: 501;\\n}\\n\\n.nc-bar.nc-topbar {\\n top: 0;\\n background: \u003C\u003Ccolour page-background>>ee;\\n max-width: calc({{$:/themes/nico/notebook/metrics/story-width}} + 40px);\\n padding: 10px 20px;\\n margin: 0 auto;\\n}\\n\\n.nc-bar.nc-bottombar {\\n position: fixed;\\n bottom: 0;\\n left: 0;\\n right: 0;\\n /* The z-index needs to be above the z-index used in tiddlers in zoomin view */\\n z-index: 501;\\n}\\n\\n.nc-bar .left svg {\\n fill: \u003C\u003Ccolour sidebar-controls-foreground>>;\\n}\\n\\n.nc-bar input[type=\\\"search\\\"] {\\n width: 200px;\\n padding: .6em 1em;\\n margin-top: -.2em;\\n background: \u003C\u003Ccolour sidebar-button-foreground>>44;\\n color: \u003C\u003Ccolour foreground>>cc;\\n transition: all ease-in .2s;\\n border: 1px solid transparent;\\n outline: 0;\\n}\\n\\n.nc-bar input[type=\\\"search\\\"]:focus {\\n width: 300px;\\n background: \u003C\u003Ccolour tiddler-background>>;\\n color: \u003C\u003Ccolour foreground>>;\\n border: 1px solid \u003C\u003Ccolour primary>>;\\n box-shadow: 0 0 .2rem 0 \u003C\u003Ccolour primary>>;\\n}\\n\\ninput[type=\\\"search\\\"]::-webkit-search-cancel-button {\\n -webkit-appearance: auto;\\n}\\n\\n.nc-bar .tc-block-dropdown.tc-search-drop-down {\\n margin-left: 0;\\n width: 400px;\\n border: 0;\\n box-shadow: 0 0 6px 0 rgba(0,0,0,.2);\\n border-radius: 6px;\\n padding: 20px 0;\\n}\\n\\n.nc-bar p {\\n margin: 0;\\n}\\n\\n.nc-bar .tc-page-controls {\\n margin-top: 0;\\n}\\n\\n.nc-bar .tc-page-controls button {\\n margin-right: .8em;\\n}\\n\\n.nc-bar .tc-page-controls button .tc-btn-text {\\n font-size: 14px;\\n}\\n\\n.nc-bar .tc-block-dropdown {\\n max-height: 70vh;\\n overflow: auto;\\n}\\n\\n@media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .nc-topbar {\\n display: none;\\n }\\n\\n .tc-story-river {\\n padding: 0 !important;\\n margin-top: 0 !important;\\n margin-bottom: 60px !important;\\n }\\n\\n div.tc-tiddler-frame {\\n margin: 0;\\n box-shadow: none;\\n border-radius: 0;\\n border-top: 0;\\n }\\n}\\n\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .nc-bottombar {\\n display: none;\\n }\\n}\\n\\n@media(max-width: 1100px) {\\n .nc-bar input[type=\\\"search\\\"] {\\n width: 200px;\\n }\\n}\\n\\n/* Sidebar */\\n\\n@keyframes sidebar-appear {\\n 0% {\\n left: -{{$:/themes/nico/notebook/metrics/sidebar-width}};\\n }\\n 100% {\\n left: 0;\\n }\\n}\\n\\n\u003C\u003Cif-sidebar \\\"\\\"\\\"\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .nc-sidebar {\\n animation: sidebar-appear .14s;\\n padding-top: 10px;\\n }\\n}\\n\\\"\\\"\\\">>\\n\\n.nc-sidebar {\\n background: \u003C\u003Ccolour tiddler-background>>;\\n border-right: 1px solid \u003C\u003Ccolour tiddler-border>>;\\n width: {{$:/themes/nico/notebook/metrics/sidebar-width}};\\n overflow-y: auto;\\n overflow-x: hidden;\\n z-index: 500;\\n}\\n\\n.nc-sidebar .segment {\\n border-bottom: 1px solid rgba(0,0,0,.1);\\n}\\n\\n.nc-sidebar ol {\\n margin: 0;\\n padding: 0;\\n list-style: none;\\n line-height: 1.8em;\\n}\\n\\n.nc-sidebar ol ol {\\n padding-left: 18px;\\n}\\n\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .mobile-only {\\n display: none;\\n }\\n}\\n\\n@media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .desktop-only {\\n display: none;\\n }\\n}\\n\\n.nc-sidebar h1.tc-site-title {\\n margin: 0;\\n}\\n\\n.nc-sidebar p {\\n margin: 6px 0;\\n}\\n\\n.nc-sidebar .tc-site-subtitle {\\n color: \u003C\u003Ccolour site-title-foreground>>;\\n}\\n\\n.nc-sidebar .section .label {\\n padding: 2px 0;\\n color: \u003C\u003Ccolour site-title-foreground>>;\\n fill: \u003C\u003Ccolour site-title-foreground>>;\\n font-weight: bold;\\n line-height: 1.6em;\\n display: block;\\n width: 100%;\\n text-align: left;\\n padding: 8px 15px;\\n border-radius: 0;\\n}\\n\\n.nc-sidebar .section:not(.open) .label:hover {\\n background: rgba(0,0,0,.06);\\n}\\n\\n.nc-sidebar .section.open .label {\\n color: \u003C\u003Ccolour tiddler-background>>;\\n fill: \u003C\u003Ccolour tiddler-background>>;\\n background: \u003C\u003Ccolour primary>>;\\n border-bottom: 1px solid rgba(0,0,0,.1);\\n}\\n\\n.nc-sidebar .section .label .caret {\\n display: inline-block;\\n width: 15px;\\n float: right;\\n}\\n\\n.nc-sidebar .content {\\n padding: 6px 15px;\\n font-size: 1em;\\n}\\n\\n.nc-sidebar .tc-tiddlylink {\\n color: \u003C\u003Ccolour primary>>;\\n}\\n\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .nc-sidebar {\\n position: fixed;\\n left: 0;\\n top: 0;\\n bottom: 0;\\n }\\n}\\n\\n\u003C\u003Cif-sidebar \\\"\\\"\\\"\\n@media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n @keyframes sidebar-slide {\\n 0% {\\n left: -100vw;\\n }\\n 100% {\\n left: 0;\\n }\\n }\\n .nc-sidebar {\\n overflow: auto;\\n position: fixed;\\n width: 100%;\\n left: 0;\\n top: 0;\\n bottom: 48px;\\n z-index: 3000;\\n animation: sidebar-slide ease-in .2s;\\n animation-fill-mode: forwards;\\n }\\n}\\n\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .tc-page-container {\\n margin-left: {{$:/themes/nico/notebook/metrics/sidebar-width}} !important;\\n }\\n\\n .nc-topbar-wrapper {\\n left: {{$:/themes/nico/notebook/metrics/sidebar-width}};\\n }\\n}\\n\\\"\\\"\\\">>\\n\\n/* Animate the hamburger button */\\n\\n@keyframes menu-bars-1 {\\n 0% {}\\n 100% {\\n transform: rotate(-45deg) translateY(-10px) translateX(-6px);\\n fill: \u003C\u003Ccolour foreground>>;\\n }\\n}\\n\\n@keyframes menu-bars-2 {\\n 0% {}\\n 100% { opacity: 0; }\\n}\\n\\n@keyframes menu-bars-3 {\\n 0% {}\\n 100% {\\n transform: rotate(45deg) translateY(6px) translateX(2px);\\n fill: \u003C\u003Ccolour foreground>>;\\n }\\n}\\n\\n.sidebar-toggle {\\n /* position: fixed; */\\n /* top: 6px; */\\n /* left: 6px; */\\n /* z-index: 600; */\\n /* padding: 4px; */\\n /* border-radius: 8px; */\\n margin-right: 10px;\\n transition: all ease-in-out .2s;\\n fill: \u003C\u003Ccolour sidebar-controls-foreground>>;\\n}\\n\\n.sidebar-toggle:hover,\\n.sidebar-toggle.open {\\n fill: \u003C\u003Ccolour sidebar-controls-foreground-hover>>;\\n}\\n\\n/* @media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) { */\\n/* .sidebar-toggle { */\\n/* top: auto; */\\n/* bottom: 10px; */\\n/* left: 10px; */\\n/* } */\\n/* } */\\n\\n.sidebar-toggle .bars .bar {\\n transform: rotate(0) translateY(0) translateX(0);\\n opacity: 1;\\n transform-origin: 20px 10px;\\n transition: transform 0.4s ease-in-out, opacity 0.2s ease-in-out, fill .4s ease-in-out;\\n}\\n\\n.sidebar-toggle .bars .bar:nth-of-type(3) {\\n transform-origin: 20px 20px;\\n}\\n\\n.sidebar-toggle.open .bars .bar:nth-of-type(1) {\\n animation: menu-bars-1 .6s;\\n animation-fill-mode: forwards;\\n}\\n.sidebar-toggle.open .bars .bar:nth-of-type(2) {\\n animation: menu-bars-2 .6s;\\n animation-fill-mode: forwards;\\n}\\n.sidebar-toggle.open .bars .bar:nth-of-type(3) {\\n animation: menu-bars-3 .6s;\\n animation-fill-mode: forwards;\\n}\\n\\n@media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n div.tc-tiddler-frame {\\n padding: 14px;\\n }\\n}\\n\\n/* Inputs */\\n\\ninput, textarea {\\n transition: border .14s ease-in-out;\\n background: \u003C\u003Ccolour tiddler-editor-background>>;\\n border: 1px solid \u003C\u003Ccolour tiddler-editor-border>>;\\n padding: .5em;\\n border-radius: 4px;\\n}\\n\\ninput:focus, textarea:focus {\\n box-shadow: 0 0 0.2rem 0 \u003C\u003Ccolour primary>>;\\n outline: 0;\\n border-color: \u003C\u003Ccolour primary>>;\\n}\\n\\nbutton {\\n border-radius: 1.5em;\\n border: 1px solid #ccc;\\n background: \u003C\u003Ccolour tiddler-background>>;\\n padding: .3em 1em;\\n cursor: pointer;\\n transition: box-shadow ease-in .1s;\\n color: \u003C\u003Ccolor foreground>>;\\n}\\n\\nbutton:focus, button:active {\\n outline: 0 none;\\n}\\n\\nbutton.tc-btn-invisible {\\n border-radius: 0;\\n}\\n\\n.tc-editor-toolbar button,\\n.tc-editor-toolbar button.tc-btn-invisible {\\n border-radius: 3px;\\n background: \u003C\u003Ccolour tiddler-editor-background>>;\\n color: \u003C\u003Ccolour foreground>>;\\n fill: \u003C\u003Ccolour foreground>>;\\n border: 1px solid \u003C\u003Ccolour tiddler-editor-border>>;\\n}\\n\\n.tc-editor-toolbar button:hover,\\n.tc-editor-toolbar button:active {\\n border-color: \u003C\u003Ccolour primary>>;\\n background: \u003C\u003Ccolour primary>>;\\n color: \u003C\u003Ccolour background>>;\\n fill: \u003C\u003Ccolour background>>;\\n}\\n\\n.tc-tiddler-frame input.tc-edit-texteditor,\\n.tc-tiddler-frame textarea.tc-edit-texteditor,\\n.tc-tiddler-frame iframe.tc-edit-texteditor {\\n transition: border .14s ease-in-out;\\n border: 1px solid \u003C\u003Ccolour tiddler-editor-border>>;\\n background: \u003C\u003Ccolour tiddler-editor-background>>;\\n padding: 4px;\\n border-radius: 4px;\\n}\\n\\n.tc-tiddler-frame input.tc-edit-texteditor:focus,\\n.tc-tiddler-frame textarea.tc-edit-texteditor:focus,\\n.tc-tiddler-frame iframe.tc-edit-texteditor:focus {\\n box-shadow: 0 0 0.2rem 0 \u003C\u003Ccolour primary>>;\\n outline: 0;\\n border-color: \u003C\u003Ccolour primary>>;\\n}\\n\\n.tc-tiddler-controls .tc-btn-text {\\n font-size: 16px;\\n}\\n\\n\u003C\u003Cif-reveal-tiddler-controls-on-hover \\\"\\\"\\\"\\n@media (min-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .tc-tiddler-frame .tc-tiddler-controls svg {\\n opacity: 0;\\n transition: all .2s ease-in;\\n }\\n\\n .tc-tiddler-controls svg.tc-image-close-button,\\n .tc-tiddler-controls .py-toggle-todo-button svg,\\n .tc-tiddler-controls svg.tc-image-done-button,\\n .tc-tiddler-frame .tc-tiddler-controls:hover svg {\\n opacity: 1;\\n }\\n\\n .tc-tiddler-controls .py-toggle-todo-button .done svg {\\n fill: #2da562;\\n }\\n}\\n\\\"\\\"\\\">>\\n\\nbutton.tc-tag-label, span.tc-tag-label {\\n padding: 0.3em 1em !important;\\n}\\n\\n/* Fonts */\\n\\nhtml, body {\\n font-family: {{$:/themes/nico/notebook/settings/fontfamily}};\\n}\\n\\n.tc-tiddler-frame input.tc-edit-texteditor,\\n.tc-tiddler-frame textarea.tc-edit-texteditor,\\n.tc-tiddler-frame iframe.tc-edit-texteditor {\\n font-family: {{$:/themes/nico/notebook/settings/editorfontfamily}};\\n}\\n\\npre, code {\\n font-family: {{$:/themes/nico/notebook/settings/codefontfamily}};\\n}\\n\\n.tc-titlebar, .tc-site-title {\\n font-size: 28px !important;\\n line-height: 34px !important;\\n font-weight: 600 !important;\\n letter-spacing: -0.5px !important;\\n}\\n\\nh1, h2, h3, h4, h5, h6 {\\n font-weight: 600;\\n}\\n\\n.tc-tiddler-body h1,\\n.tc-tiddler-body h2,\\n.tc-tiddler-preview-preview h1,\\n.tc-tiddler-preview-preview h2 {\\n font-weight: bold;\\n}\\n\\ndiv.tc-tiddler-frame .tc-tiddler-body {\\n font-size: {{$:/themes/nico/notebook/metrics/bodyfontsize}};\\n line-height: {{$:/themes/nico/notebook/metrics/bodylineheight}};\\n}\\n\\n/* Tabs */\\n\\ndiv.tc-tab-buttons {\\n margin-bottom: -4px;\\n}\\n\\ndiv.tc-tab-buttons button {\\n font-weight: bold;\\n font-size: 1.2em;\\n line-height: 1em;\\n padding: .6em .8em .4em .8em;\\n border: 0;\\n border-radius: 0;\\n background: transparent;\\n cursor: pointer;\\n transition: background ease-in .2s;\\n}\\n\\ndiv.tc-tab-buttons button:hover {\\n background: rgba(0,0,0,.03);\\n}\\n\\ndiv.tc-tab-buttons button.tc-tab-selected {\\n border: 0;\\n background: transparent;\\n border-bottom: 4px solid \u003C\u003Ccolour primary>>;\\n}\\n\\n/* Dropdowns */\\n\\n@keyframes pop {\\n 0% {\\n transform: scale(0.8);\\n opacity: 0;\\n }\\n\\n 80% {\\n transform: scale(1.03);\\n opacity: 1;\\n }\\n\\n 100% {\\n transform: scale(1);\\n opacity: 1;\\n }\\n}\\n\\n.tc-drop-down {\\n box-shadow: 0 0 10px rgba(0,0,0,.2);\\n border-radius: 6px;\\n padding: 10px 0 !important;\\n animation: pop .15s ease-in forwards;\\n}\\n\\n.tc-drop-down a, .tc-drop-down button {\\n padding: 3px 15px !important;\\n}\\n\\n.tc-search-results {\\n line-height: 2em;\\n}\\n\\n.tc-search-results em {\\n font-weight: bold;\\n font-style: normal;\\n}\\n\\n/* Draft list */\\n\\n.tc-drafts-list {\\n font-size: .9em;\\n left: auto;\\n right: 0;\\n}\\n\\n.tc-drafts-list a {\\n padding: 6px 12px;\\n font-weight: bold;\\n border-top-left-radius: 6px;\\n border-top-right-radius: 6px;\\n display: inline-block;\\n}\\n\\n.nc-refs {\\n color: #888;\\n font-size: .9em;\\n}\\n\\n.nc-refs h4 {\\n margin-bottom: 4px;\\n}\\n\\n.nc-post-created {\\n color: #acacac;\\n font-size: .8em;\\n}\\n\"\n },\n \"$:/themes/nico/notebook/changelog\": {\n \"title\": \"$:/themes/nico/notebook/changelog\",\n \"caption\": \"ChangeLog\",\n \"created\": \"20201217180707912\",\n \"modified\": \"20210202214001915\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"! 1.4.1\\n\\n!! Fixes\\n\\n* Fix the transclusion mode of sidebar sections\\n* Fix section title rendering for tiddlers without a caption field\\n* Fix the colour of links in the sidebar when using Notebook palettes with Vanilla\\n\\n! 1.4.0\\n\\n!! Features\\n\\n* New redesigned topbar layout\\n* Add a configuration setting for the story width\\n* Add support for keyboard navigation in the search dropdown\\n\\n! 1.3.6\\n\\n!! Improvements\\n\\n* Improve the style of tabs\\n* New animation for drop-downs\\n* Use a lighter page background colour in the beige palette\\n\\n!! Fixes\\n\\n* Fix the default ctrl+shift+F shortcut for focusing the search input\\n\\n! 1.3.5\\n\\n!! Features\\n\\n* Add an option to reveal tiddler controls on mouseover\\n\\n! 1.3.4\\n\\n!! Improvements\\n\\n* Add a keyboard shortcut (alt+shift+s) to toggle Notebook sidebar\\n* Add missing colours to tiddler editor fields in the dark palette\\n\\n!! Fixes\\n\\n* Fix the size of toolbar button labels when the $:/config/Toolbar/Text is set to yes\\n\\n! 1.3.3\\n\\n!! Improvements\\n\\n* Make the sidebar more generic by using the default sidebar sections\\n\\n! 1.3.2\\n\\n!! Improvements\\n\\n* Add colours for messages in the dark palette\\n* Add colours for notification in the dark palette\\n* Set colours for messages in the beige palette\\n\\n! 1.3.1\\n\\n!! Features\\n\\n* New font family settings distinct from the Vanilla theme\\n\\n!! Improvements\\n\\n* Use a slightly lighter colour as the search input background\\n* Improve contrast of sidebar buttons in the dark palette\\n\\n!! Fixes\\n\\n* Fix tiddler control button colours in all three palettes\\n* Fix tab colours in palette-dark\\n\\n! 1.3.0\\n\\n!! Improvements\\n\\n* New dark colour palette\\n* Use a darker color for tiddler subtitles\\n* Add back the WebKit search cancel button in search inputs\\n\\n!! Fixes\\n\\n* Fix the z-index of the topbar for the zoomin story view\\n* Fix the font weight of tiddler titles in edit mode\\n\\n! 1.2.0\\n\\n!! Improvements\\n\\n* Better support for dark colour palettes\\n\\n!! Fixes\\n\\n* Fix rendering of overflowing/wrapping text in the sidebar\\n\\n! 1.1.0\\n\\n!! Features\\n\\n* New theme tweaks tab dedicated to Notebook in the control panel\\n* Inputs in the edit template are now styled consistently with other inputs\\n\\n!! Fixes\\n\\n* Fixes the position of sticky tiddler titles when the option is turned on\\n\"\n },\n \"$:/config/ShortcutInfo/notebook-focus-search\": {\n \"title\": \"$:/config/ShortcutInfo/notebook-focus-search\",\n \"text\": \"Focus on the topbar search field\"\n },\n \"$:/config/shortcuts/notebook-focus-search\": {\n \"title\": \"$:/config/shortcuts/notebook-focus-search\",\n \"text\": \"ctrl+shift+F\"\n },\n \"$:/config/Search/AutoFocus\": {\n \"title\": \"$:/config/Search/AutoFocus\",\n \"text\": \"false\"\n },\n \"$:/config/shortcuts/sidebar-search\": {\n \"title\": \"$:/config/shortcuts/sidebar-search\",\n \"text\": \"\"\n },\n \"$:/themes/nico/notebook/images/bars\": {\n \"title\": \"$:/themes/nico/notebook/images/bars\",\n \"created\": \"20200428212322206\",\n \"modified\": \"20201210210231235\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Csvg class=\\\"bars\\\" height=\\\"21pt\\\" viewBox=\\\"0 0 42 42\\\" enable-background=\\\"new 0 0 32 22.5\\\" version=\\\"1.1\\\" xmlns=\\\"http://www.w3.org/2000/svg\\\">\\n \u003Cg class=\\\"svg-menu-toggle\\\" sketch:type=\\\"MSLayerGroup\\\">\\n \u003Crect class=\\\"bar\\\" x=\\\"8\\\" y=\\\"28\\\" width=\\\"26\\\" height=\\\"4\\\">\u003C/rect>\\n \u003Crect class=\\\"bar\\\" x=\\\"8\\\" y=\\\"19\\\" width=\\\"26\\\" height=\\\"4\\\">\u003C/rect>\\n \u003Crect class=\\\"bar\\\" x=\\\"8\\\" y=\\\"10\\\" width=\\\"26\\\" height=\\\"4\\\">\u003C/rect>\\n \u003C/g>\\n\u003C/svg>\\n\"\n },\n \"$:/themes/nico/notebook/images/caret-down\": {\n \"title\": \"$:/themes/nico/notebook/images/caret-down\",\n \"created\": \"20200429194348688\",\n \"modified\": \"20201210210230919\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Csvg width=\\\"6pt\\\" xmlns=\\\"http://www.w3.org/2000/svg\\\" viewBox=\\\"0 0 320 512\\\">\u003Cpath d=\\\"M31.3 192h257.3c17.8 0 26.7 21.5 14.1 34.1L174.1 354.8c-7.8 7.8-20.5 7.8-28.3 0L17.2 226.1C4.6 213.5 13.5 192 31.3 192z\\\"/>\u003C/svg>\\n\"\n },\n \"$:/themes/nico/notebook/images/caret-right\": {\n \"title\": \"$:/themes/nico/notebook/images/caret-right\",\n \"created\": \"20200429194305719\",\n \"modified\": \"20201210210230909\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Csvg width=\\\"4pt\\\" xmlns=\\\"http://www.w3.org/2000/svg\\\" viewBox=\\\"0 0 192 512\\\">\u003Cpath d=\\\"M0 384.662V127.338c0-17.818 21.543-26.741 34.142-14.142l128.662 128.662c7.81 7.81 7.81 20.474 0 28.284L34.142 398.804C21.543 411.404 0 402.48 0 384.662z\\\"/>\u003C/svg>\\n\"\n },\n \"$:/themes/nico/notebook/images/color-switch\": {\n \"title\": \"$:/themes/nico/notebook/images/color-switch\",\n \"created\": \"20201210170859810\",\n \"creator\": \"nico\",\n \"modified\": \"20201210205606403\",\n \"modifier\": \"nico\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Csvg width=\\\"20px\\\" height=\\\"20px\\\" viewBox=\\\"0 0 16 16\\\" class=\\\"bi bi-circle-half\\\" fill=\\\"currentColor\\\" xmlns=\\\"http://www.w3.org/2000/svg\\\">\\n \u003Cpath fill-rule=\\\"evenodd\\\" d=\\\"M8 15V1a7 7 0 1 1 0 14zm0 1A8 8 0 1 1 8 0a8 8 0 0 1 0 16z\\\"/>\\n\u003C/svg\\n\"\n },\n \"$:/themes/nico/notebook/metrics/bodyfontsize\": {\n \"title\": \"$:/themes/nico/notebook/metrics/bodyfontsize\",\n \"created\": \"20200428203454207\",\n \"modified\": \"20201210205606363\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"15px\\n\"\n },\n \"$:/themes/nico/notebook/metrics/bodylineheight\": {\n \"title\": \"$:/themes/nico/notebook/metrics/bodylineheight\",\n \"created\": \"20200428203454207\",\n \"modified\": \"20201210205606363\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"22px\"\n },\n \"$:/themes/nico/notebook/metrics/sidebar-width\": {\n \"title\": \"$:/themes/nico/notebook/metrics/sidebar-width\",\n \"created\": \"20200429144554294\",\n \"modified\": \"20201210210231246\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"350px\\n\"\n },\n \"$:/themes/nico/notebook/metrics/story-width\": {\n \"title\": \"$:/themes/nico/notebook/metrics/story-width\",\n \"created\": \"20210123210054185\",\n \"modified\": \"20210123211911688\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"800px\\n\"\n },\n \"$:/themes/nico/notebook/metrics/topbar-height\": {\n \"title\": \"$:/themes/nico/notebook/metrics/topbar-height\",\n \"created\": \"20200428203454207\",\n \"modified\": \"20201210205606363\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"52px\\n\"\n },\n \"$:/themes/nico/notebook/options/stickytitles\": {\n \"title\": \"$:/themes/nico/notebook/options/stickytitles\",\n \"text\": \"no\"\n },\n \"$:/themes/nico/notebook/options/codewrapping\": {\n \"title\": \"$:/themes/nico/notebook/options/codewrapping\",\n \"text\": \"pre-wrap\"\n },\n \"$:/themes/nico/notebook/options/reveal-tiddler-controls-on-hover\": {\n \"title\": \"$:/themes/nico/notebook/options/reveal-tiddler-controls-on-hover\",\n \"text\": \"no\"\n },\n \"$:/core/ui/PageTemplate/sidebar\": {\n \"title\": \"$:/core/ui/PageTemplate/sidebar\",\n \"created\": \"20200430072116835\",\n \"modified\": \"20201217174129501\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\whitespace trim\\n\\\\define config-title()\\n$:/config/SideBarSegments/Visibility/$(listItem)$\\n\\\\end\\n\\nOverwritten by $:/themes/nico/notebook so that the default sidebar does not get rendered.\\n\"\n },\n \"$:/themes/tiddlywiki/vanilla/themetweaks\": {\n \"title\": \"$:/themes/tiddlywiki/vanilla/themetweaks\",\n \"caption\": \"{{$:/language/ThemeTweaks/ThemeTweaks}}\",\n \"created\": \"20201217163834291\",\n \"modified\": \"20201217163914434\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"Overwritten by $:/themes/nico/notebook so that the Vanilla theme tweaks do not appear in the control panel. \"\n },\n \"$:/themes/nico/notebook/palettes/palette-beige\": {\n \"title\": \"$:/themes/nico/notebook/palettes/palette-beige\",\n \"text\": \"alert-background: #ffe476\\nalert-border: #b99e2f\\nalert-highlight: #881122\\nalert-muted-foreground: #b99e2f\\nbackground: #ffffff\\nblockquote-bar: \u003C\u003Ccolour muted-foreground>>\\nbutton-background:\\nbutton-foreground:\\nbutton-border:\\ncode-background: #f7f7f9\\ncode-border: #e1e1e8\\ncode-foreground: #dd1144\\ndirty-indicator: #c63636\\ndownload-background: #66cccc\\ndownload-foreground: \u003C\u003Ccolour background>>\\ndragger-background: \u003C\u003Ccolour foreground>>\\ndragger-foreground: \u003C\u003Ccolour background>>\\ndropdown-background: \u003C\u003Ccolour background>>\\ndropdown-border: #ddd\\ndropdown-tab-background-selected: #fff\\ndropdown-tab-background: #ececec\\ndropzone-background: #da8548\\nexternal-link-background-hover: inherit\\nexternal-link-background-visited: inherit\\nexternal-link-background: inherit\\nexternal-link-foreground-hover: inherit\\nexternal-link-foreground-visited: #0000aa\\nexternal-link-foreground: #0000ee\\nforeground: #3F3B3B\\nmessage-background: #e6f5e8\\nmessage-border: #2b5532\\nmessage-foreground: #2b5532\\nmodal-backdrop: \u003C\u003Ccolour foreground>>\\nmodal-background: \u003C\u003Ccolour background>>\\nmodal-border: #999999\\nmodal-footer-background: #f5f5f5\\nmodal-footer-border: #dddddd\\nmodal-header-border: #eeeeee\\nmuted-foreground: #999999\\nnotification-background: #ffffdd\\nnotification-border: #999999\\npage-background: #f5f5ee\\npre-background: #f6f6f6\\npre-border: #cccccc\\nprimary: #7f4bca\\nselect-tag-background:\\nselect-tag-foreground:\\nsidebar-button-foreground: #a6a69c\\nsidebar-controls-foreground-hover: #000000\\nsidebar-controls-foreground: \u003C\u003Ccolour sidebar-button-foreground>>\\nsidebar-foreground-shadow: rgba(255,255,255, 0.8)\\nsidebar-foreground: #acacac\\nsidebar-muted-foreground-hover: #444444\\nsidebar-muted-foreground: #c0c0c0\\nsidebar-tab-background-selected: #ffffff\\nsidebar-tab-background: \u003C\u003Ccolour tab-background>>\\nsidebar-tab-border-selected: \u003C\u003Ccolour tab-border-selected>>\\nsidebar-tab-border: \u003C\u003Ccolour tab-border>>\\nsidebar-tab-divider: \u003C\u003Ccolour tab-divider>>\\nsidebar-tab-foreground-selected: \u003C\u003Ccolour tab-foreground-selected>>\\nsidebar-tab-foreground: \u003C\u003Ccolour tab-foreground>>\\nsidebar-tiddler-link-foreground-hover: \u003C\u003Ccolour primary>>\\nsidebar-tiddler-link-foreground: \u003C\u003Ccolour tab-foreground>>\\nsite-title-foreground: #353748\\nstatic-alert-foreground: #aaaaaa\\ntab-background-selected: #ffffff\\ntab-background: #eeeeee\\ntab-border-selected: #cccccc\\ntab-border: #cccccc\\ntab-divider: #d8d8d8\\ntab-foreground-selected: \u003C\u003Ccolour foreground>>\\ntab-foreground: #888888\\ntable-border: #dddddd\\ntable-footer-background: #a8a8a8\\ntable-header-background: #f0f0f0\\ntag-background: #ffeedd\\ntag-foreground: #000\\ntiddler-background: \u003C\u003Ccolour background>>\\ntiddler-border: #dbdbc7;\\ntiddler-controls-foreground-hover: #888888;\\ntiddler-controls-foreground-selected: #888888;\\ntiddler-controls-foreground: #cccccc\\ntiddler-editor-background: \u003C\u003Ccolour background>>\\ntiddler-editor-border-image: #ffffff\\ntiddler-editor-border: rgba(0,0,0,.2)\\ntiddler-editor-fields-even: #e0e8e0\\ntiddler-editor-fields-odd: #f0f4f0\\ntiddler-info-background: #f8f8f8\\ntiddler-info-border: #dddddd\\ntiddler-info-tab-background: #f8f8f8\\ntiddler-link-background: \u003C\u003Ccolour background>>\\ntiddler-link-foreground: \u003C\u003Ccolour primary>>\\ntiddler-subtitle-foreground: #aaaaaa\\ntiddler-title-foreground: #333\\ntoolbar-new-button:\\ntoolbar-options-button:\\ntoolbar-save-button:\\ntoolbar-info-button:\\ntoolbar-edit-button:\\ntoolbar-close-button:\\ntoolbar-delete-button:\\ntoolbar-cancel-button:\\ntoolbar-done-button:\\nuntagged-background: #999999\\nvery-muted-foreground: #888888\\n\",\n \"type\": \"application/x-tiddler-dictionary\",\n \"description\": \"A beige colour palette for Notebook\",\n \"name\": \"Notebook Beige\",\n \"tags\": \"$:/tags/Palette $:/tags/notebook/Palette\"\n },\n \"$:/themes/nico/notebook/palettes/palette-dark\": {\n \"title\": \"$:/themes/nico/notebook/palettes/palette-dark\",\n \"text\": \"alert-background: #643b43\\nalert-border: #3f181f\\nalert-highlight: #881122\\nalert-muted-foreground: #bc8b94\\nbackground: #383e49\\nblockquote-bar: \u003C\u003Ccolour muted-foreground>>\\nbutton-background:\\nbutton-border:\\nbutton-foreground:\\ncode-background: #2c323b\\ncode-border: #111\\ncode-foreground: #dd1144\\ndirty-indicator: #c63636\\ndownload-background: #98be65\\ndownload-foreground: \u003C\u003Ccolour background>>\\ndragger-background: \u003C\u003Ccolour foreground>>\\ndragger-foreground: \u003C\u003Ccolour background>>\\ndropdown-background: \u003C\u003Ccolour background>>\\ndropdown-border: #111\\ndropdown-tab-background-selected: #fff\\ndropdown-tab-background: #ececec\\ndropzone-background: #da8548\\nexternal-link-background-hover: inherit\\nexternal-link-background-visited: inherit\\nexternal-link-background: inherit\\nexternal-link-foreground-hover: inherit\\nexternal-link-foreground-visited: #61afef\\nexternal-link-foreground: #c678dd\\nforeground: #c8ced8\\nmessage-background: #2c323e\\nmessage-border: #111\\nmessage-foreground: #d5e2f1\\nmodal-backdrop: \u003C\u003Ccolour foreground>>\\nmodal-background: \u003C\u003Ccolour background>>\\nmodal-border: #999999\\nmodal-footer-background: #f5f5f5\\nmodal-footer-border: #dddddd\\nmodal-header-border: #eeeeee\\nmuted-foreground: #999999\\nnotification-background: #3a5e39\\nnotification-border: #192c19\\npage-background: #262b33\\npre-background: \u003C\u003Ccolour page-background>>\\npre-border: \u003C\u003Ccolour tiddler-border>>\\nprimary: #bf93ff\\nselect-tag-background:\\nselect-tag-foreground:\\nsidebar-button-foreground: #5e646f\\nsidebar-controls-foreground-hover: #cad2e5\\nsidebar-controls-foreground: \u003C\u003Ccolour sidebar-button-foreground>>\\nsidebar-foreground-shadow: rgba(255,255,255, 0.8)\\nsidebar-foreground: #cad2e5\\nsidebar-muted-foreground-hover: #444444\\nsidebar-muted-foreground: #c0c0c0\\nsidebar-tab-background-selected: \u003C\u003Ccolour tab-background-selected>>\\nsidebar-tab-background: \u003C\u003Ccolour tab-background>>\\nsidebar-tab-border-selected: \u003C\u003Ccolour tab-border-selected>>\\nsidebar-tab-border: \u003C\u003Ccolour tab-border>>\\nsidebar-tab-divider: \u003C\u003Ccolour tab-divider>>\\nsidebar-tab-foreground-selected: \u003C\u003Ccolour tab-foreground-selected>>\\nsidebar-tab-foreground: \u003C\u003Ccolour tab-foreground>>\\nsidebar-tiddler-link-foreground-hover: \u003C\u003Ccolour primary>>\\nsidebar-tiddler-link-foreground: \u003C\u003Ccolour tab-foreground>>\\nsite-title-foreground: \u003C\u003Ccolour foreground>>\\nstatic-alert-foreground: #aaaaaa\\ntab-background-selected: \u003C\u003Ccolour background>>\\ntab-background: \u003C\u003Ccolour page-background>>\\ntab-border-selected: \u003C\u003Ccolour foreground>>\\ntab-border: #cad2e5\\ntab-divider: #cad2e5\\ntab-foreground-selected: #ecf2ff\\ntab-foreground: #cad2e5\\ntable-border: #aaaaaa\\ntable-footer-background: #a8a8a8\\ntable-header-background: #262b33\\ntag-background: #fcb671\\ntag-foreground: #000\\ntiddler-background: \u003C\u003Ccolour background>>\\ntiddler-border: #111\\ntiddler-controls-foreground-hover: #cad2e5\\ntiddler-controls-foreground-selected: #cad2e5\\ntiddler-controls-foreground: #5e646f\\ntiddler-editor-background: \u003C\u003Ccolour background>>\\ntiddler-editor-border-image: #ffffff\\ntiddler-editor-border: rgba(255, 255, 255, 0.3)\\ntiddler-editor-fields-even: \u003C\u003Ccolour background>>\\ntiddler-editor-fields-odd: #2c323b\\ntiddler-info-background: #f8f8f8\\ntiddler-info-border: #dddddd\\ntiddler-info-tab-background: #f8f8f8\\ntiddler-link-background: \u003C\u003Ccolour background>>\\ntiddler-link-foreground: \u003C\u003Ccolour primary>>\\ntiddler-subtitle-foreground: #aaaaaa\\ntiddler-title-foreground: \u003C\u003Ccolour foreground>>\\ntoolbar-cancel-button:\\ntoolbar-close-button:\\ntoolbar-delete-button:\\ntoolbar-done-button:\\ntoolbar-edit-button:\\ntoolbar-info-button:\\ntoolbar-new-button:\\ntoolbar-options-button:\\ntoolbar-save-button:\\nuntagged-background: #999999\\nvery-muted-foreground: #888888\\n\",\n \"type\": \"application/x-tiddler-dictionary\",\n \"description\": \"A dark colour palette for Notebook\",\n \"name\": \"Notebook Dark\",\n \"tags\": \"$:/tags/Palette $:/tags/notebook/Palette\"\n },\n \"$:/themes/nico/notebook/palettes/palette-grey\": {\n \"title\": \"$:/themes/nico/notebook/palettes/palette-grey\",\n \"text\": \"alert-background: #ffe476\\nalert-border: #b99e2f\\nalert-highlight: #881122\\nalert-muted-foreground: #b99e2f\\nbackground: #ffffff\\nblockquote-bar: \u003C\u003Ccolour muted-foreground>>\\nbutton-background:\\nbutton-foreground:\\nbutton-border:\\ncode-background: #f7f7f9\\ncode-border: #e1e1e8\\ncode-foreground: #dd1144\\ndirty-indicator: #c63636\\ndownload-background: #66cccc\\ndownload-foreground: \u003C\u003Ccolour background>>\\ndragger-background: \u003C\u003Ccolour foreground>>\\ndragger-foreground: \u003C\u003Ccolour background>>\\ndropdown-background: \u003C\u003Ccolour background>>\\ndropdown-border: #ddd\\ndropdown-tab-background-selected: #fff\\ndropdown-tab-background: #ececec\\ndropzone-background: #da8548\\nexternal-link-background-hover: inherit\\nexternal-link-background-visited: inherit\\nexternal-link-background: inherit\\nexternal-link-foreground-hover: inherit\\nexternal-link-foreground-visited: #0000aa\\nexternal-link-foreground: #0000ee\\nforeground: #283c46\\nmessage-background: #ecf2ff\\nmessage-border: #cfd6e6\\nmessage-foreground: #547599\\nmodal-backdrop: \u003C\u003Ccolour foreground>>\\nmodal-background: \u003C\u003Ccolour background>>\\nmodal-border: #999999\\nmodal-footer-background: #f5f5f5\\nmodal-footer-border: #dddddd\\nmodal-header-border: #eeeeee\\nmuted-foreground: #999999\\nnotification-background: #ffffdd\\nnotification-border: #999999\\npage-background: #f4f4f4\\npre-background: #f6f6f6\\npre-border: #cccccc\\nprimary: #127edd\\nselect-tag-background:\\nselect-tag-foreground:\\nsidebar-button-foreground: #a6a69c\\nsidebar-controls-foreground-hover: #000000\\nsidebar-controls-foreground: \u003C\u003Ccolour sidebar-button-foreground>>\\nsidebar-foreground-shadow: rgba(255,255,255, 0.8)\\nsidebar-foreground: #acacac\\nsidebar-muted-foreground-hover: #444444\\nsidebar-muted-foreground: #c0c0c0\\nsidebar-tab-background-selected: #ffffff\\nsidebar-tab-background: \u003C\u003Ccolour tab-background>>\\nsidebar-tab-border-selected: \u003C\u003Ccolour tab-border-selected>>\\nsidebar-tab-border: \u003C\u003Ccolour tab-border>>\\nsidebar-tab-divider: \u003C\u003Ccolour tab-divider>>\\nsidebar-tab-foreground-selected: \u003C\u003Ccolour tab-foreground-selected>>\\nsidebar-tab-foreground: \u003C\u003Ccolour tab-foreground>>\\nsidebar-tiddler-link-foreground-hover: \u003C\u003Ccolour primary>>\\nsidebar-tiddler-link-foreground: \u003C\u003Ccolour tab-foreground>>\\nsite-title-foreground: #353748\\nstatic-alert-foreground: #aaaaaa\\ntab-background-selected: #ffffff\\ntab-background: #eeeeee\\ntab-border-selected: #cccccc\\ntab-border: #cccccc\\ntab-divider: #d8d8d8\\ntab-foreground-selected: \u003C\u003Ccolour foreground>>\\ntab-foreground: #888888\\ntable-border: #dddddd\\ntable-footer-background: #a8a8a8\\ntable-header-background: #f0f0f0\\ntag-background: #ffeedd\\ntag-foreground: #000\\ntiddler-background: \u003C\u003Ccolour background>>\\ntiddler-border: #ddd\\ntiddler-controls-foreground-hover: #888888;\\ntiddler-controls-foreground-selected: #888888;\\ntiddler-controls-foreground: #cccccc\\ntiddler-editor-background: \u003C\u003Ccolour background>>\\ntiddler-editor-border-image: #ffffff\\ntiddler-editor-border: rgba(0,0,0,.2)\\ntiddler-editor-fields-even: #e0e8e0\\ntiddler-editor-fields-odd: #f0f4f0\\ntiddler-info-background: #f8f8f8\\ntiddler-info-border: #dddddd\\ntiddler-info-tab-background: #f8f8f8\\ntiddler-link-background: \u003C\u003Ccolour background>>\\ntiddler-link-foreground: \u003C\u003Ccolour primary>>\\ntiddler-subtitle-foreground: #aaaaaa\\ntiddler-title-foreground: #333\\ntoolbar-new-button:\\ntoolbar-options-button:\\ntoolbar-save-button:\\ntoolbar-info-button:\\ntoolbar-edit-button:\\ntoolbar-close-button:\\ntoolbar-delete-button:\\ntoolbar-cancel-button:\\ntoolbar-done-button:\\nuntagged-background: #999999\\nvery-muted-foreground: #888888\\n\",\n \"type\": \"application/x-tiddler-dictionary\",\n \"description\": \"A grey color palette for Notebook\",\n \"name\": \"Notebook Grey\",\n \"tags\": \"$:/tags/Palette $:/tags/notebook/Palette\"\n },\n \"$:/themes/nico/notebook/settings/codefontfamily\": {\n \"title\": \"$:/themes/nico/notebook/settings/codefontfamily\",\n \"created\": \"20210101213404232\",\n \"modified\": \"20210101214210227\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\"Fira Mono\\\",\\\"Liberation Mono\\\",Menlo,Courier,monospace\\n\"\n },\n \"$:/themes/nico/notebook/settings/fontfamily\": {\n \"title\": \"$:/themes/nico/notebook/settings/fontfamily\",\n \"created\": \"20210101213404232\",\n \"modified\": \"20210101213411800\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\"Segoe UI\\\",Helvetica,Arial,sans-serif,\\\"Apple Color Emoji\\\",\\\"Segoe UI Emoji\\\",\\\"Segoe UI Symbol\\\"\\n\"\n },\n \"$:/themes/nico/notebook/shortcuts/notebook-focus-search\": {\n \"title\": \"$:/themes/nico/notebook/shortcuts/notebook-focus-search\",\n \"created\": \"20201210122048919\",\n \"key\": \"((notebook-focus-search))\",\n \"modified\": \"20210115130024907\",\n \"tags\": \"$:/tags/KeyboardShortcut\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$action-sendmessage $message=\\\"tm-focus-selector\\\" $param=\\\".nc-topbar input\\\"/>\\n\"\n },\n \"$:/themes/nico/notebook/shortcuts/toggle-sidebar\": {\n \"title\": \"$:/themes/nico/notebook/shortcuts/toggle-sidebar\",\n \"created\": \"20210115130000707\",\n \"key\": \"((toggle-sidebar))\",\n \"modified\": \"20210115130021883\",\n \"tags\": \"$:/tags/KeyboardShortcut\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$list\\n filter=\\\"[[$:/state/notebook-sidebar]is[missing]] [{$:/state/notebook-sidebar}removeprefix[yes]]\\\"\\n emptyMessage=\\\"\\\"\\\"\u003C$action-setfield $tiddler=\\\"$:/state/notebook-sidebar\\\" text=\\\"yes\\\"/>\\\"\\\"\\\"\\n>\\n \u003C$action-setfield $tiddler=\\\"$:/state/notebook-sidebar\\\" text=\\\"no\\\"/>\\n\u003C/$list>\\n\"\n },\n \"$:/themes/nico/notebook/stickytitles\": {\n \"title\": \"$:/themes/nico/notebook/stickytitles\",\n \"created\": \"20201217172915960\",\n \"modified\": \"20201217180034682\",\n \"tags\": \"$:/tags/Stylesheet\",\n \"text\": \"\u003C$reveal state=\\\"$:/themes/nico/notebook/options/stickytitles\\\" type=\\\"match\\\" text=\\\"yes\\\">\\n\\n.tc-tiddler-title {\\n position: -webkit-sticky;\\n position: -moz-sticky;\\n position: -o-sticky;\\n position: -ms-sticky;\\n position: sticky;\\n top: {{$:/themes/nico/notebook/metrics/topbar-height}};\\n background: \u003C\u003Ccolour tiddler-background>>;\\n z-index: 500;\\n}\\n\\n@media (max-width: {{$:/themes/tiddlywiki/vanilla/metrics/sidebarbreakpoint}}) {\\n .tc-tiddler-title {\\n top: 0;\\n }\\n}\\n\\n\u003C$list filter=\\\"[range[100]]\\\">\\n`.tc-story-river .tc-tiddler-frame:nth-child(100n+`\u003C$text text=\u003C\u003CcurrentTiddler>>/>`) {\\nz-index: `\u003C$text text={{{ [[200]subtract\u003CcurrentTiddler>] }}}/>`;\\n}\\n`\\n\u003C/$list>\\n\u003C/$reveal>\\n\"\n },\n \"$:/themes/nico/notebook/tags/Sidebar\": {\n \"title\": \"$:/themes/nico/notebook/tags/Sidebar\",\n \"created\": \"20200429164516951\",\n \"list\": \"$:/themes/nico/notebook/ui/Buttons/menu $:/themes/nico/notebook/ui/Sidebar/Headings $:/themes/nico/notebook/ui/Sidebar/Search $:/themes/nico/notebook/Sidebar/Sections\",\n \"modified\": \"20201210205606504\",\n \"type\": \"text/vnd.tiddlywiki\"\n },\n \"$:/themes/nico/notebook/tags/SidebarSection\": {\n \"title\": \"$:/themes/nico/notebook/tags/SidebarSection\",\n \"created\": \"20200429201017275\",\n \"list\": \"$:/themes/nico/notebook/ui/Sidebar/Open $:/themes/nico/notebook/ui/Sidebar/Recent $:/themes/nico/notebook/ui/Sidebar/Tools $:/themes/nico/notebook/ui/Sidebar/More\",\n \"modified\": \"20201210215658901\",\n \"type\": \"text/vnd.tiddlywiki\"\n },\n \"$:/themes/nico/notebook/ui/Bottombar\": {\n \"title\": \"$:/themes/nico/notebook/ui/Bottombar\",\n \"created\": \"20200429113453340\",\n \"modified\": \"20201210210230886\",\n \"tags\": \"$:/tags/PageTemplate\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$reveal state=\\\"$:/state/notebook-bottombar\\\" type=\\\"match\\\" text=\\\"yes\\\" default=\\\"yes\\\" retain=\\\"yes\\\" animate=\\\"yes\\\">\\n \u003Cdiv class=\\\"nc-bar nc-bottombar\\\">\\n \u003C$list filter=\\\"[all[shadows+tiddlers]tag[$:/tags/NotebookTopbar]!has[draft.of]]\\\" variable=\\\"listItem\\\">\\n \u003C$reveal type=\\\"nomatch\\\" state=\u003C\u003Cconfig-title>> text=\\\"hide\\\" tag=\\\"div\\\">\\n \u003C$transclude tiddler=\u003C\u003ClistItem>> mode=\\\"block\\\"/>\\n \u003C/$reveal>\\n \u003C/$list>\\n \u003Cdiv class=\\\"left\\\">\\n {{$:/themes/nico/notebook/ui/Buttons/menu}}\\n \u003C/div>\\n \u003Cdiv class=\\\"right\\\">\\n {{$:/core/ui/SideBarSegments/page-controls}}\\n \u003C/div>\\n \u003C/div>\\n\u003C/$reveal>\\n\\n\"\n },\n \"$:/themes/nico/notebook/ui/Buttons/SwitchPalette\": {\n \"title\": \"$:/themes/nico/notebook/ui/Buttons/SwitchPalette\",\n \"created\": \"20201210171047824\",\n \"description\": \"Toggle between grey/beige colour palette\",\n \"modified\": \"20210118213335643\",\n \"tags\": \"$:/tags/PageControls\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Cspan class=\\\"desktop-only\\\">\\n \u003C$vars\\n palettes=\\\"[all[tiddlers+shadows]tag[$:/tags/notebook/Palette]]\\\"\\n popupTiddler=\u003C\u003Cqualify \\\"$:/state/notebook/palette-dropdown\\\">>\\n >\\n \u003C$button\\n popup=\u003C\u003CpopupTiddler>>\\n tooltip=\\\"Switch colours\\\"\\n aria-label=\\\"Switch colours\\\"\\n class=\u003C\u003Ctv-config-toolbar-class>>\\n >\\n \u003C$list filter=\\\"[\u003Ctv-config-toolbar-icons>match[yes]]\\\">\\n\\t{{$:/themes/nico/notebook/images/color-switch}}\\n \u003C/$list>\\n\\n \u003C$list filter=\\\"[\u003Ctv-config-toolbar-text>match[yes]]\\\">\\n\\t\u003Cspan class=\\\"tc-btn-text\\\">Switch colours\u003C/span>\\n \u003C/$list>\\n\\n \u003C$reveal state=\u003C\u003CpopupTiddler>> type=\\\"popup\\\" position=\\\"belowleft\\\" class=\\\"tc-drop-down\\\">\\n\\t\u003C$list filter=\u003C\u003Cpalettes>>>\\n\\t \u003C$button class=\\\"tc-btn-invisible\\\">\\n\\t {{!!name}}\\n\\t \u003C$action-setfield $tiddler=\\\"$:/palette\\\" text={{!!title}}/>\\n\\t \u003C/$button>\\n\\t\u003C/$list>\\n \u003C/$reveal>\\n\\n \u003C/$button>\\n \u003C/$vars>\\n\u003C/span>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Buttons/menu\": {\n \"title\": \"$:/themes/nico/notebook/ui/Buttons/menu\",\n \"created\": \"20200429115248943\",\n \"modified\": \"20210124211756417\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$reveal state=\\\"$:/state/notebook-sidebar\\\" type=\\\"match\\\" text=\\\"yes\\\" default=\\\"no\\\" retain=\\\"yes\\\" animate=\\\"no\\\">\\n \u003C$button set=\\\"$:/state/notebook-sidebar\\\" setTo=\\\"no\\\" tooltip=\\\"Toggle menu\\\" class=\\\"tc-btn-invisible sidebar-toggle open\\\">\\n {{$:/themes/nico/notebook/images/bars}}\\n \u003C/$button>\\n\u003C/$reveal>\\n\\n\u003C$reveal type=\\\"nomatch\\\" state=\\\"$:/state/notebook-sidebar\\\" text=\\\"yes\\\">\\n \u003C$button set=\\\"$:/state/notebook-sidebar\\\" setTo=\\\"yes\\\" tooltip=\\\"Toggle menu\\\" class=\\\"tc-btn-invisible sidebar-toggle\\\">\\n {{$:/themes/nico/notebook/images/bars}}\\n \u003C/$button>\\n\u003C/$reveal>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Search\": {\n \"title\": \"$:/themes/nico/notebook/ui/Search\",\n \"created\": \"20200429191943257\",\n \"modified\": \"20210126170723413\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\define advanced-search-actions()\\n\u003C$action-setfield $tiddler=\\\"$:/temp/advancedsearch/input\\\" text={{$:/temp/notebook-search}}/>\\n\u003C$action-setfield $tiddler=\\\"$:/temp/advancedsearch/refresh\\\" text=\\\"yes\\\"/>\\n\u003C$action-navigate $to=\\\"$:/AdvancedSearch\\\"/>\\n\\\\end\\n\\n\\\\define input-accept-actions()\\n\u003C$list filter=\\\"[\u003C__tiddler__>get[text]!is[missing]] ~[\u003C__tiddler__>get[text]is[shadow]]\\\">\\n \u003C$action-navigate $to={{{ [\u003C__tiddler__>get[text]] }}}/>\\n \u003C$action-deletetiddler $filter=\\\"[[$:/temp/search]] [\u003CsearchTiddler>] [\u003CsearchListState>]\\\"/>\\n\u003C/$list>\\n\\\\end\\n\\n\\\\define cancel-search-actions()\\n\u003C$list filter=\\\"[\u003CsearchTiddler>get[text]!match{$:/temp/search}]\\\" emptyMessage=\\\"\\\"\\\"\u003C$action-deletetiddler $filter=\\\"[[$:/temp/search]] [\u003CsearchTiddler>] [\u003CsearchListState>]\\\"/>\\\"\\\"\\\">\\n \u003C$action-setfield $tiddler=\\\"$:/temp/search\\\" text={{{ [\u003CsearchTiddler>get[text]] }}}/>\\n \u003C$action-setfield $tiddler=\\\"$:/temp/search/refresh\\\" text=\\\"yes\\\"/>\u003C/$list>\\n\\\\end\\n\\n\u003C$vars editTiddler=\\\"$:/temp/search\\\"\\n searchTiddler=\\\"$:/temp/search/input\\\"\\n searchListState=\u003C\u003Cqualify \\\"$:/state/search-list/selected-item\\\">>>\\n \u003C$macrocall $name=\\\"keyboard-driven-input\\\"\\n\\t tiddler=\u003C\u003CeditTiddler>>\\n\\t storeTitle=\u003C\u003CsearchTiddler>>\\n\\t selectionStateTitle=\u003C\u003CsearchListState>>\\n\\t refreshTitle=\\\"$:/temp/search/refresh\\\"\\n\\t type=\\\"search\\\"\\n\\t tag=\\\"input\\\"\\n\\t focus={{$:/config/Search/AutoFocus}}\\n\\t focusPopup=\\\"$:/state/popup/notebook-search\\\"\\n\\t class=\\\"tc-popup-handle\\\"\\n\\t filterMinLength={{$:/config/Search/MinLength}}\\n\\t placeholder=\\\"Search...\\\"\\n\\t inputAcceptActions=\u003C\u003Cinput-accept-actions>>\\n\\t inputCancelActions=\u003C\u003Ccancel-search-actions>>\\n\\t cancelPopups=\\\"yes\\\"\\n\\t configTiddlerFilter=\\\"[[$:/state/search/currentTab]!is[missing]get[text]] ~[{$:/config/SearchResults/Default}]\\\"\\n\\t />\\n \u003C$button\\n tooltip={{$:/language/Buttons/AdvancedSearch/Hint}}\\n aria-label={{$:/language/Buttons/AdvancedSearch/Caption}}\\n class=\\\"tc-btn-invisible tc-page-controls\\\"\\n >\\n {{$:/core/images/advanced-search-button}}\\n \u003C\u003Cadvanced-search-actions>>\\n \u003C/$button>\\n \u003C$reveal tag=\\\"div\\\" class=\\\"tc-block-dropdown-wrapper\\\" state=\\\"$:/state/popup/notebook-search\\\" type=\\\"nomatch\\\" text=\\\"\\\" default=\\\"\\\">\\n \u003C$list filter=\\\"[\u003CsearchTiddler>get[text]minlength{$:/config/Search/MinLength}limit[1]]\\\" emptyMessage=\\\"\\\" variable=\\\"listItem\\\">\\n \u003Cdiv class=\\\"tc-block-dropdown tc-search-drop-down\\\">\\n \u003C$tiddler tiddler=\u003C\u003CconfigTiddler>>>\\n {{$:/themes/nico/notebook/ui/Sidebar/SearchResults}}\\n \u003C/$tiddler>\\n \u003C/div>\\n \u003C/$list>\\n \u003C/$reveal>\\n\u003C/$vars>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar/Headings\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar/Headings\",\n \"created\": \"20200429160014174\",\n \"modified\": \"20201210210231267\",\n \"tags\": \"$:/themes/nico/notebook/tags/Sidebar\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Cdiv class=\\\"segment\\\">\\n \u003Cdiv class=\\\"content\\\">\\n \u003Ch1 class=\\\"tc-site-title\\\">\\n {{$:/SiteTitle}}\\n \u003C/h1>\\n \u003Cdiv class=\\\"tc-site-subtitle\\\">\\n {{$:/SiteSubtitle}}\\n \u003C/div>\\n \u003C/div>\\n\u003C/div>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar/Search\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar/Search\",\n \"created\": \"20200429191943257\",\n \"modified\": \"20210124220152702\",\n \"tags\": \"$:/themes/nico/notebook/tags/Sidebar\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003Cdiv class=\\\"mobile-only\\\">\\n \u003Cdiv class=\\\"segment\\\">\\n \u003Cdiv class=\\\"content search\\\">\\n {{$:/themes/nico/notebook/ui/Search}}\\n \u003C/div>\\n \u003C/div>\\n\u003C/div>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar/SearchResults\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar/SearchResults\",\n \"created\": \"20200429191943257\",\n \"modified\": \"20210126164631418\",\n \"tags\": \"\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\define searchResultList()\\n \u003Csmall>{{$:/language/Search/Matches/Title}}\u003C/small>\\n\\n \u003C$list filter=\\\"[!is[system]search:title{$(searchTiddler)$}sort[title]limit[250]]\\\">\\n \u003Cspan class={{{[\u003CcurrentTiddler>addsuffix[-primaryList]] -[\u003CsearchListState>get[text]] +[then[]else[tc-list-item-selected]] }}}>\\n \u003C$transclude tiddler=\\\"$:/core/ui/ListItemTemplate\\\"/>\\n \u003C/span>\\n \u003C/$list>\\n\\n \u003Csmall>{{$:/language/Search/Matches/All}}\u003C/small>\\n\\n \u003C$list filter=\\\"[!is[system]search{$(searchTiddler)$}sort[title]limit[250]]\\\">\\n \u003Cspan class={{{[\u003CcurrentTiddler>addsuffix[-secondaryList]] -[\u003CsearchListState>get[text]] +[then[]else[tc-list-item-selected]] }}}>\\n \u003C$transclude tiddler=\\\"$:/core/ui/ListItemTemplate\\\"/>\\n \u003C/span>\\n \u003C/$list>\\n\\\\end\\n\\n\u003Cdiv class=\\\"tc-search-results\\\">\\n \u003C\u003CsearchResultList>>\\n\u003C/div>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar/SectionTemplate\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar/SectionTemplate\",\n \"created\": \"20200429161226897\",\n \"modified\": \"20210202213859460\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\define sidebarHeading()\\n\u003C$vars tv-wikilinks=\\\"no\\\">\\n \u003C$transclude field=\\\"caption\\\">\\n \u003C$view field=\\\"title\\\"/>\\n \u003C/$transclude>\\n\u003C/$vars>\\n\\\\end\\n\\n\u003C$reveal state=\\\"$:/state/notebook-sidebar-section\\\" type=\\\"match\\\" text=\u003C\u003CcurrentTiddler>> default=\\\"no\\\" animate=\\\"no\\\">\\n \u003Cdiv class=\\\"segment section open\\\">\\n \u003C$button set=\\\"$:/state/notebook-sidebar-section\\\" setTo=\\\"\\\" class=\\\"tc-btn-invisible label\\\">\\n \u003C\u003CsidebarHeading>>\\n \u003Cspan class=\\\"caret\\\">{{$:/themes/nico/notebook/images/caret-down}}\u003C/span>\\n \u003C/$button>\\n \u003Cdiv class=\\\"content\\\">\\n \u003C$transclude $tiddler=\u003C\u003CcurrentTiddler>> mode=\\\"block\\\"/>\\n \u003C/div>\\n \u003C/div>\\n\u003C/$reveal>\\n\u003C$reveal state=\\\"$:/state/notebook-sidebar-section\\\" type=\\\"nomatch\\\" text=\u003C\u003CcurrentTiddler>> default=\\\"yes\\\" animate=\\\"no\\\">\\n \u003Cdiv class=\\\"segment section\\\">\\n \u003C$button set=\\\"$:/state/notebook-sidebar-section\\\" setTo=\u003C\u003CcurrentTiddler>> class=\\\"tc-btn-invisible label\\\">\\n \u003C\u003CsidebarHeading>>\\n \u003Cspan class=\\\"caret\\\">{{$:/themes/nico/notebook/images/caret-right}}\u003C/span>\\n \u003C/$button>\\n \u003C/div>\\n\u003C/$reveal>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar/Sections\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar/Sections\",\n \"created\": \"20200429163239707\",\n \"modified\": \"20210112213620486\",\n \"tags\": \"$:/themes/nico/notebook/tags/Sidebar\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$list filter=\\\"[all[shadows+tiddlers]!has[draft.of]tag[$:/tags/SideBar]]\\\">\\n {{||$:/themes/nico/notebook/ui/Sidebar/SectionTemplate}}\\n\u003C/$list>\\n\"\n },\n \"$:/themes/nico/notebook/ui/Sidebar\": {\n \"title\": \"$:/themes/nico/notebook/ui/Sidebar\",\n \"created\": \"20200428201218885\",\n \"modified\": \"20210112213605486\",\n \"tags\": \"$:/tags/PageTemplate\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\\\\whitespace trim\\n\\\\define config-title()\\n$:/config/SideBarSegments/Visibility/$(listItem)$\\n\\\\end\\n\\n\u003C$reveal state=\\\"$:/state/notebook-sidebar\\\" type=\\\"match\\\" text=\\\"yes\\\" default=\\\"no\\\" retain=\\\"yes\\\" animate=\\\"no\\\">\\n \u003C$scrollable fallthrough=\\\"no\\\">\\n \u003Cdiv class=\\\"nc-sidebar\\\">\\n \u003C$list filter=\\\"[all[shadows+tiddlers]tag[$:/themes/nico/notebook/tags/Sidebar]!has[draft.of]]\\\" variable=\\\"listItem\\\">\\n \u003C$reveal type=\\\"nomatch\\\" state=\u003C\u003Cconfig-title>> text=\\\"hide\\\" tag=\\\"div\\\">\\n \u003C$transclude tiddler=\u003C\u003ClistItem>> mode=\\\"inline\\\"/>\\n \u003C/$reveal>\\n \u003C/$list>\\n \u003C/div>\\n \u003C/$scrollable>\\n\u003C/$reveal>\\n\\n\"\n },\n \"$:/themes/nico/notebook/ui/Topbar\": {\n \"title\": \"$:/themes/nico/notebook/ui/Topbar\",\n \"created\": \"20200428203101797\",\n \"modified\": \"20210124213834458\",\n \"tags\": \"$:/tags/PageTemplate\",\n \"type\": \"text/vnd.tiddlywiki\",\n \"text\": \"\u003C$reveal state=\\\"$:/state/notebook-topbar\\\" type=\\\"match\\\" text=\\\"yes\\\" default=\\\"yes\\\" retain=\\\"yes\\\" animate=\\\"yes\\\">\\n \u003Cdiv class=\\\"nc-topbar-wrapper\\\">\\n \u003Cdiv class=\\\"nc-bar nc-topbar tc-adjust-top-of-scroll\\\">\\n \u003C$list filter=\\\"[all[shadows+tiddlers]tag[$:/tags/NotebookTopbar]!has[draft.of]]\\\" variable=\\\"listItem\\\">\\n \u003C$reveal type=\\\"nomatch\\\" state=\u003C\u003Cconfig-title>> text=\\\"hide\\\" tag=\\\"div\\\">\\n \u003C$transclude tiddler=\u003C\u003ClistItem>> mode=\\\"block\\\"/>\\n \u003C/$reveal>\\n \u003C/$list>\\n \u003Cdiv class=\\\"left\\\">\\n\\t{{$:/themes/nico/notebook/ui/Buttons/menu}}\\n {{$:/themes/nico/notebook/ui/Search}}\\n \u003C/div>\\n \u003Cdiv class=\\\"right\\\">\\n {{$:/core/ui/SideBarSegments/page-controls}}\\n \u003C/div>\\n \u003C/div>\\n \u003C/div>\\n\u003C/$reveal>\\n\\n\"\n }\n }\n}","bag":"default","revision":"0","version":"1.4.1","type":"application/json","title":"$:/themes/nico/notebook","source":"https://github.com/NicolasPetton/Notebook","plugin-type":"theme","name":"Notebook theme","list":"LICENSE changelog","description":"A clean, uncluttered TiddlyWiki theme","dependents":"$:/themes/tiddlywiki/vanilla $:/plugins/nico/notebook-mobile","core-version":">=5.1.22","author":"NicolasPetton"},
{"created":"20200429144554294","title":"$:/themes/nico/notebook/metrics/sidebar-width","modified":"20230423163514560","tags":"","type":"text/vnd.tiddlywiki","text":"300px"},
diff --git a/src/3rd/js/aframe/index.js b/src/3rd/js/aframe/index.js
index ce1e8f9..7eb62ed 100644
--- a/src/3rd/js/aframe/index.js
+++ b/src/3rd/js/aframe/index.js
@@ -8,6 +8,8 @@ window.AFRAME.registerComponent('xrf', {
document.querySelector('[camera]').setAttribute('xrf-fade','')
AFRAME.fade = document.querySelector('[camera]').components['xrf-fade']
+ if( document.location.host.match(/localhost/) ) document.querySelector('a-scene').setAttribute("stats",'')
+
document.querySelector('a-scene').addEventListener('loaded', () => {
// enable XR fragments
diff --git a/src/3rd/js/three/hashbus.js b/src/3rd/js/three/hashbus.js
index c7df3b4..287d863 100644
--- a/src/3rd/js/three/hashbus.js
+++ b/src/3rd/js/three/hashbus.js
@@ -62,12 +62,15 @@ pub.XRWG = (opts) => {
match.map( (w) => {
if( w.key == `#${id}` ){
if( w.value && w.value[0] == '#' ){
+ frag = xrf.URI.parse( w.value )
+ v = Object.values(frag)[0]
// if value is alias, execute fragment value
xrf.hashbus.pub( w.value, xrf.model, xrf.XRF.METADATA | xrf.XRF.PV_OVERRIDE | xrf.XRF.NAVIGATOR )
+ xrf.emit('dynamicKey',{ ...opts,v,frag,id,match,scene })
}
}
})
- xrf.emit('dynamicKey',{ ...opts,v,frag,id,match,scene })
+ if( !match.length ) xrf.emit('dynamicKey',{ ...opts,v,frag,id,match,scene })
}else{
xrf.emit('dynamicKeyValue',{ ...opts,v,frag,id,match,scene })
}
diff --git a/src/3rd/js/three/xrf/dynamic/filter.js b/src/3rd/js/three/xrf/dynamic/filter.js
index eec91b7..bf2ec1e 100644
--- a/src/3rd/js/three/xrf/dynamic/filter.js
+++ b/src/3rd/js/three/xrf/dynamic/filter.js
@@ -7,7 +7,7 @@ xrf.addEventListener('dynamicKey', (opts) => {
let {scene,id,match,v} = opts
if( v.filter ){
let frags = {}
- frags[ v.fragment ] = v
+ frags[ v.filter.key ] = v
xrf.filter.scene({frag:frags,scene})
}
})
@@ -23,7 +23,7 @@ xrf.filter = function(query, cb){
xrf.filter.scene = function(opts){
let {scene,frag} = opts
-
+console.dir(opts)
xrf.filter
.sort(frag) // get (sorted) filters from XR Fragments
.process(frag,scene,opts) // show/hide things
@@ -91,6 +91,9 @@ xrf.filter.process = function(frag,scene,opts){
let processed = {}
scene.traverse( (m) => {
+
+ if( filter.root && m.isSRC ) return // ignore src nodes when root is specific (#/VR #/AR e.g.)
+
// filter on value(expression) #foo=>3 e.g.
if( filter.value && m.userData[filter.key] ){
const visible = v.filter.testProperty(filter.key, m.userData[filter.key], filter.show === false )
diff --git a/src/3rd/js/three/xrf/href.js b/src/3rd/js/three/xrf/href.js
index 86f9c79..28dcf77 100644
--- a/src/3rd/js/three/xrf/href.js
+++ b/src/3rd/js/three/xrf/href.js
@@ -41,15 +41,14 @@ xrf.frag.href = function(v, opts){
.then( () => {
const flags = v.string[0] == '#' ? xrf.XRF.PV_OVERRIDE : undefined
let toFrag = xrf.URI.parse( v.string, xrf.XRF.NAVIGATOR | xrf.XRF.PV_OVERRIDE | xrf.XRF.METADATA )
- // always keep a trail of last positions before we navigate
- if( !document.location.hash.match(lastPos) ) xrf.navigator.to(`#${lastPos}`)
+ // always commit current location (keep a trail of last positions before we navigate)
+ if( !e.nocommit && !document.location.hash.match(lastPos) ) xrf.navigator.to(`#${lastPos}`)
xrf.navigator.to(v.string) // let's surf to HREF!
})
.catch( console.error )
}
let selected = mesh.userData.XRF.href.selected = (state) => () => {
- console.log("select "+mesh.name)
if( mesh.selected == state ) return // nothing changed
xrf.interactive.objects.map( (o) => {
let newState = o.name == mesh.name ? state : false
diff --git a/src/3rd/js/three/xrf/src/non-euclidian.js b/src/3rd/js/three/xrf/src/non-euclidian.js
index fb3c41a..1138cd9 100644
--- a/src/3rd/js/three/xrf/src/non-euclidian.js
+++ b/src/3rd/js/three/xrf/src/non-euclidian.js
@@ -102,7 +102,7 @@ xrf.portalNonEuclidian = function(opts){
// trigger href upon camera collide
if( mesh.userData.XRF.href ){
- raycaster.far = 0.3
+ raycaster.far = 0.35
let cam = xrf.camera.getCam ? xrf.camera.getCam() : camera
cam.getWorldPosition(cameraPosition)
cam.getWorldDirection(cameraDirection)
@@ -110,7 +110,7 @@ xrf.portalNonEuclidian = function(opts){
intersects = raycaster.intersectObjects([mesh], false)
if (intersects.length > 0 && !mesh.portal.teleporting ){
mesh.portal.teleporting = true
- mesh.userData.XRF.href.exec()
+ mesh.userData.XRF.href.exec({nocommit:true})
setTimeout( () => mesh.portal.teleporting = false, 500) // dont flip back and forth
}
}
diff --git a/src/xrfragment/Filter.hx b/src/xrfragment/Filter.hx
index f23e68d..5eb62f0 100644
--- a/src/xrfragment/Filter.hx
+++ b/src/xrfragment/Filter.hx
@@ -52,11 +52,11 @@ class Filter {
private var str:String = "";
private var q:haxe.DynamicAccess = {}; // 1. create an associative array/object to store filter-arguments as objects
- private var isProp:EReg = ~/^.*=[><=]?/; // 1. detect object id's & properties `foo=1` and `foo` (reference regex= `~/^.*=[><=]?/` )
+ private var isProp:EReg = ~/^.*=[><=]?/; // 1. detect object id's & properties `foo=1` and `foo` (reference regex= `~/^.*=[><=]?/` )
private var isExclude:EReg = ~/^-/; // 1. detect excluders like `-foo`,`-foo=1`,`-.foo`,`-/foo` (reference regex= `/^-/` )
private var isRoot:EReg = ~/^[-]?\//; // 1. detect root selectors like `/foo` (reference regex= `/^[-]?\//` )
private var isNumber:EReg = ~/^[0-9\.]+$/; // 1. detect number values like `foo=1` (reference regex= `/^[0-9\.]+$/` )
- private var operators:EReg = ~/(^-|\*$)/; // 1. detect operators so you can easily strip keys (reference regex= `/(^-|\*$)/` )
+ private var operators:EReg = ~/(^-|\*$|\/)/; // 1. detect operators so you can easily strip keys (reference regex= `/(^-|\*$)/` )
private var isSelectorExclude:EReg = ~/^-/; // 1. detect exclude keys like `-foo` (reference regex= `/^-/` )
public function new(str:String){
diff --git a/src/xrfragment/Parser.hx b/src/xrfragment/Parser.hx
index 97d0080..8e01751 100644
--- a/src/xrfragment/Parser.hx
+++ b/src/xrfragment/Parser.hx
@@ -9,7 +9,7 @@ import xrfragment.XRF;
class Parser {
public static var error:String = "";
public static var debug:Bool = false;
- public static var keyClean:EReg = ~/(\*$|^-)/g;
+ public static var keyClean:EReg = ~/(\*$|^-|\/)/g;
@:keep
public static function parse(key:String,value:String,store:haxe.DynamicAccess,?index:Int):Bool {
@@ -65,7 +65,7 @@ class Parser {
trace("⚠ fragment '"+key+"' has incompatible value ("+value+")");// 1. don't add to store if value-type is incorrect
return false;
}
- store.set(key, v ); // 1. if valid, add to store
+ store.set( keyClean.replace(key,''), v); // 1. if valid, add to store
if( debug ) trace("✔ "+key+": "+v.string);
}else{ // 1. expose (but mark) non-offical fragments too
if( Std.isOfType(value, String) ) v.guessType(v,value);