refactoring outer structure
authorThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Sun, 28 Jun 2026 11:47:06 +0000 (11:47 +0000)
committerThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Sun, 28 Jun 2026 11:47:06 +0000 (11:47 +0000)
16 files changed:
developer/authored/Manuscript.copy/Core/RT-Style_make.js [new file with mode: 0644]
developer/authored/Manuscript.copy/Core/block_visibility_during_layout.js [deleted file]
developer/authored/Manuscript.copy/Core/document_loaded.js [deleted file]
developer/authored/Manuscript.copy/Core/loader.js [deleted file]
developer/authored/Manuscript.copy/Core/stage_manager.js [new file with mode: 0644]
developer/authored/Manuscript.copy/Core/theme_make.js [new file with mode: 0644]
developer/authored/Manuscript.copy/Document/RT-Style_locator.js
developer/authored/Manuscript.copy/Document/RT-style.js [deleted file]
developer/authored/Manuscript.copy/Document/manual.html
developer/authored/Manuscript.copy/Element/theme_selector.js
developer/authored/Manuscript.copy/Layout/article_tech_ref.js
developer/authored/Manuscript.copy/Locator/direct.js
developer/authored/Manuscript.copy/Theme/golden_wheat.js
developer/authored/Manuscript.copy/Theme/inverse_wheat.js
developer/authored/Manuscript.copy/Theme/manifest.js [new file with mode: 0644]
developer/authored/Manuscript.copy/Theme/wheat.js

diff --git a/developer/authored/Manuscript.copy/Core/RT-Style_make.js b/developer/authored/Manuscript.copy/Core/RT-Style_make.js
new file mode 100644 (file)
index 0000000..ea53313
--- /dev/null
@@ -0,0 +1,214 @@
+// Core/loader.js
+
+window.RT = window.RT || {};
+window.RT.Element = [];
+window.RT.Module = window.RT.Module || new Set();
+
+
+
+// 2. Establish the Debug System
+window.RT.debug = {
+  active_tokens: new Set([
+    'scroll'
+  ]),
+
+  log: function(token, message) {
+    if (this.active_tokens.has(token)) {
+      console.log(`[RT:${token}]`, message);
+    }
+  },
+
+  warn: function(token, message) {
+    if (this.active_tokens.has(token)) {
+      console.warn(`[RT:${token}]`, message);
+    }
+  },
+  
+  error: function(token, message) {
+    console.error(`[RT:${token}] CRITICAL:`, message);
+  },
+  
+  enable: function(token) { this.active_tokens.add(token); console.log(`Enabled: ${token}`); },
+  disable: function(token) { this.active_tokens.delete(token); console.log(`Disabled: ${token}`); }
+};
+
+// 3. Establish the Utilities
+window.RT.utility = {
+
+  string: {
+    to_roman: function(num) {
+      if (num < 1) return num.toString();
+      const lookup = {M:1000, CM:900, D:500, CD:400, C:100, XC:90, L:50, XL:40, X:10, IX:9, V:5, IV:4, I:1};
+      let roman = '';
+      for (let i in lookup) {
+        while (num >= lookup[i]) {
+          roman += i;
+          num -= lookup[i];
+        }
+      }
+      return roman;
+    },
+
+    strip_common_indent: function(text, tag_indent = '') {
+      const raw_lines = text.split('\n');
+      const content_lines = raw_lines.filter(line => line.trim().length > 0);
+      let common_indent = '';
+
+      if (content_lines.length > 0) {
+        const first_match = content_lines[0].match(/^\s*/);
+        common_indent = first_match ? first_match[0] : '';
+
+        for (let i = 1; i < content_lines.length; i++) {
+          const line = content_lines[i];
+          let j = 0;
+          while (j < common_indent.length && j < line.length && common_indent[j] === line[j]) {
+            j++;
+          }
+          common_indent = common_indent.substring(0, j);
+          if (common_indent.length === 0) break;
+        }
+      }
+
+      let final_string = '';
+      if (common_indent.length > 0 && common_indent.startsWith(tag_indent)) {
+         const cleaned_lines = raw_lines.map(line => {
+            return line.startsWith(common_indent) ? line.replace(common_indent, '') : line;
+         });
+         
+         if (cleaned_lines.length > 0 && cleaned_lines[0].length === 0) {
+           cleaned_lines.shift();
+         }
+         if (cleaned_lines.length > 0 && cleaned_lines[cleaned_lines.length - 1].trim().length === 0) {
+            cleaned_lines.pop();
+         }
+         final_string = cleaned_lines.join('\n');
+      } else {
+         final_string = text.trim();
+      }
+
+      return final_string;
+    }
+  },
+
+  dom: {
+    measure_outer_height: function(el) {
+      const wasInDOM = el.parentNode !== null;
+      if (!wasInDOM) document.body.appendChild(el);
+      const rect = el.getBoundingClientRect();
+      const style = window.getComputedStyle(el);
+      const margin = parseFloat(style.marginTop) + parseFloat(style.marginBottom);
+      if (!wasInDOM) el.remove();
+      return (rect.height || 0) + (margin || 0);
+    },
+
+    is_block_content: function(element) {
+      return element.textContent.trim().includes('\n');
+    }
+  },
+
+  font: {
+    measure_ink_ratio: function(target_font, ref_font = null) {
+      const debug = window.RT.debug;
+      debug.log('layout', `Measuring ink ratio for ${target_font}`);
+
+      const canvas = document.createElement('canvas');
+      const ctx = canvas.getContext('2d');
+
+      if (!ref_font) {
+        const bodyStyle = window.getComputedStyle(document.body);
+        ref_font = bodyStyle.fontFamily;
+      }
+
+      const get_metrics = (font) => {
+        ctx.font = '100px ' + font; 
+        const metrics = ctx.measureText('M');
+        return {
+          ascent: metrics.actualBoundingBoxAscent, 
+          descent: metrics.actualBoundingBoxDescent 
+        };
+      };
+
+      const ref_m = get_metrics(ref_font);
+      const target_m = get_metrics(target_font);
+      
+      const ratio = ref_m.ascent / target_m.ascent;
+
+      return { 
+        ratio: ratio,
+        baseline_diff: ref_m.descent - target_m.descent 
+      };
+    }
+  },
+
+  color: {
+    extract_l: function(color_string) {
+      const str = String(color_string).trim();
+      
+      if (!str.startsWith('oklch')) {
+        console.error(`[RT:color] Invalid format: Expected oklch color string, received '${str}'`);
+        return 0; 
+      }
+
+      const match = str.match(/oklch\(\s*([\d.]+%?)/);
+      if (!match) {
+        console.error(`[RT:color] Parsing error: Could not extract lightness from '${str}'`);
+        return 0;
+      }
+
+      const l_value = match[1];
+      return l_value.includes('%') ? parseFloat(l_value) / 100 : parseFloat(l_value);
+    },
+
+    is_high_contrast: function(bg_color, text_color) {
+      const bg_l = this.extract_l(bg_color);
+      const text_l = this.extract_l(text_color);
+      return Math.abs(text_l - bg_l) >= 0.7;
+    },
+
+    is_readable: function(bg_color, text_color) {
+      const bg_l = this.extract_l(bg_color);
+      const text_l = this.extract_l(text_color);
+      return Math.abs(text_l - bg_l) >= 0.5;
+    },
+    
+    is_light: function(color_string) {
+      return this.extract_l(color_string) > 0.75;
+    },
+
+    is_gray: function(color_string) {
+      const l = this.extract_l(color_string);
+      return l >= 0.25 && l <= 0.75;
+    },
+
+    is_dark: function(color_string) {
+      return this.extract_l(color_string) < 0.25;
+    }
+  }
+
+};
+
+window.RT.theme_preference = function(author_pref, default_color = "#FF00FF") {
+  const reader_pref = localStorage.getItem('RT-Style·theme_preference');
+  const theme_to_load = reader_pref ? reader_pref : author_pref;
+  
+  window.RT.theme('load', theme_to_load, default_color);
+};
+
+
+window.RT.load = function(module_path) {
+  if (window.RT.Module.has(module_path)) {
+    return;
+  }
+  window.RT.Module.add(module_path);
+
+  let resolved_path = window.RT.dirpr_library + '/' + module_path;
+  if (!resolved_path.endsWith('.js')) {
+    resolved_path = resolved_path + '.js';
+  }
+
+  document.write('<script src="' + resolved_path + '"></script>');
+};
+
+window.RT.load('Core/stage_manager');
+window.RT.load('Core/theme_make');
+window.RT.load('Theme/manifest.js')
diff --git a/developer/authored/Manuscript.copy/Core/block_visibility_during_layout.js b/developer/authored/Manuscript.copy/Core/block_visibility_during_layout.js
deleted file mode 100644 (file)
index 8513f01..0000000
+++ /dev/null
@@ -1,19 +0,0 @@
-// block_visibility_during_layout.js
-
-// 1. Hide the document immediately upon execution in the <head>
-document.documentElement.style.visibility = "hidden";
-
-// 2. Define the restoration function
-const restore_visibility = function() {
-    document.documentElement.style.visibility = "";
-    document.removeEventListener("RT_layout_complete", restore_visibility);
-    window.removeEventListener("load", restore_visibility);
-};
-
-// 3. Listen for a specific completion signal from the layout engine
-document.addEventListener("RT_layout_complete", restore_visibility);
-
-// 4. Structural Safety Net: If the layout engine fails or is never loaded, 
-//    restore visibility on the final window 'load' event so the page doesn't remain blank.
-window.addEventListener("load", restore_visibility);
-
diff --git a/developer/authored/Manuscript.copy/Core/document_loaded.js b/developer/authored/Manuscript.copy/Core/document_loaded.js
deleted file mode 100644 (file)
index e12641d..0000000
+++ /dev/null
@@ -1,24 +0,0 @@
-window.RT = window.RT || {};
-
-window.RT.document_loaded = function(layout_callback) {
-  const debug = window.RT.debug || { log: function(){} };
-  debug.log('lifecycle', 'Processing registered elements.');
-
-  if (window.RT.theme) {
-    window.RT.theme();
-  }
-  
-  if (window.RT.Element && Array.isArray(window.RT.Element)) {
-    window.RT.Element.forEach(function(element_fn) {
-      if (typeof element_fn === 'function') {
-        element_fn();
-      }
-    });
-  }
-
-  if (window.MathJax && MathJax.Hub && MathJax.Hub.Queue) {
-    MathJax.Hub.Queue(["Typeset", MathJax.Hub], layout_callback);
-  } else {
-    layout_callback();
-  }
-};
diff --git a/developer/authored/Manuscript.copy/Core/loader.js b/developer/authored/Manuscript.copy/Core/loader.js
deleted file mode 100644 (file)
index 171e6d3..0000000
+++ /dev/null
@@ -1,312 +0,0 @@
-// Core/loader.js
-
-window.RT = window.RT || {};
-window.RT.Element = [];
-window.RT.Module = window.RT.Module || new Set();
-
-// 1. Establish the Generic Theme Dictionary
-//  e.g. RT.theme( 'read', 'content_main')
-window.RT.theme = (function() {
-  const dictionary = {
-    meta: { 
-      is_dark: false, 
-      name: "" 
-    },
-    surface: { 
-      0: "", 1: "", 2: "", 3: "", 
-      input: "", code: "", select: "" 
-    },
-    content: { 
-      main: "", muted: "", subtle: "", inverse: "" 
-    },
-    brand: { 
-      primary: "", secondary: "", tertiary: "", link: "" 
-    },
-    border: { 
-      faint: "", regular: "", strong: "" 
-    },
-    state: { 
-      success: "", warning: "", error: "", info: "" 
-    },
-    syntax: { 
-      keyword: "", string: "", func: "", comment: "" 
-    },
-    page: { 
-      width: "", min_height: "", padding: "", margin: "", 
-      bg_color: "", border_color: "", text_color: "", shadow: "" 
-    }
-  };
-
-  function resolve_path(path_array) {
-    let current = dictionary;
-    for (let i = 0; i < path_array.length - 1; i++) {
-      const step = path_array[i];
-      if (current[step] === undefined) return null;
-      current = current[step];
-    }
-    return { container: current, key: path_array[path_array.length - 1] };
-  }
-
-  function check_completion(obj, path_string) {
-    for (const key in obj) {
-      if (typeof obj[key] === 'object' && obj[key] !== null) {
-        if (!check_completion(obj[key], path_string + key + '.')) {
-          return false;
-        }
-      } else {
-        if (obj[key] === "") {
-          window.RT.debug.error('theme', 'is_defined check failed at missing key: ' + path_string + key);
-          return false;
-        }
-      }
-    }
-    return true;
-  }
-
-  return function(command, ...args) {
-
-    // e.g. RT.theme('read','page','width')
-    if (command === 'read') {
-      const target = resolve_path(args);
-      if (target && target.container.hasOwnProperty(target.key)) {
-        return target.container[target.key];
-      }
-      window.RT.debug.error('theme', 'Read attempt on unknown path: ' + args.join('.'));
-      return null;
-    } 
-    
-    if (command === 'write') {
-      if (args.length < 2) {
-        window.RT.debug.error('theme', 'Write command expects a path and a value.');
-        return;
-      }
-      const value = args.pop();
-      const target = resolve_path(args);
-      
-      if (target && target.container.hasOwnProperty(target.key)) {
-        target.container[target.key] = value;
-      } else {
-        window.RT.debug.error('theme', 'Write attempt on unknown path rejected: ' + args.join('.'));
-      }
-      return;
-    }
-
-    if (command === 'is_defined') {
-      if (args.length === 0) {
-        return check_completion(dictionary, '');
-      }
-      
-      for (let i = 0; i < args.length; i++) {
-        const path_array = args[i];
-        if (!Array.isArray(path_array)) {
-           window.RT.debug.error('theme', 'is_defined arguments must be path arrays. Received: ' + path_array);
-           return false;
-        }
-        const target = resolve_path(path_array);
-        if (!target || !target.container.hasOwnProperty(target.key) || target.container[target.key] === "") {
-           window.RT.debug.error('theme', 'is_defined check failed at: ' + path_array.join('.'));
-           return false;
-        }
-      }
-      return true;
-    }
-    
-    window.RT.debug.error('theme', 'Invalid command passed to theme dictionary: ' + command);
-  };
-})();
-
-
-// 2. Establish the Debug System
-window.RT.debug = {
-  active_tokens: new Set([
-    'scroll'
-  ]),
-
-  log: function(token, message) {
-    if (this.active_tokens.has(token)) {
-      console.log(`[RT:${token}]`, message);
-    }
-  },
-
-  warn: function(token, message) {
-    if (this.active_tokens.has(token)) {
-      console.warn(`[RT:${token}]`, message);
-    }
-  },
-  
-  error: function(token, message) {
-    console.error(`[RT:${token}] CRITICAL:`, message);
-  },
-  
-  enable: function(token) { this.active_tokens.add(token); console.log(`Enabled: ${token}`); },
-  disable: function(token) { this.active_tokens.delete(token); console.log(`Disabled: ${token}`); }
-};
-
-// 3. Establish the Utilities
-window.RT.utility = {
-
-  string: {
-    to_roman: function(num) {
-      if (num < 1) return num.toString();
-      const lookup = {M:1000, CM:900, D:500, CD:400, C:100, XC:90, L:50, XL:40, X:10, IX:9, V:5, IV:4, I:1};
-      let roman = '';
-      for (let i in lookup) {
-        while (num >= lookup[i]) {
-          roman += i;
-          num -= lookup[i];
-        }
-      }
-      return roman;
-    },
-
-    strip_common_indent: function(text, tag_indent = '') {
-      const raw_lines = text.split('\n');
-      const content_lines = raw_lines.filter(line => line.trim().length > 0);
-      let common_indent = '';
-
-      if (content_lines.length > 0) {
-        const first_match = content_lines[0].match(/^\s*/);
-        common_indent = first_match ? first_match[0] : '';
-
-        for (let i = 1; i < content_lines.length; i++) {
-          const line = content_lines[i];
-          let j = 0;
-          while (j < common_indent.length && j < line.length && common_indent[j] === line[j]) {
-            j++;
-          }
-          common_indent = common_indent.substring(0, j);
-          if (common_indent.length === 0) break;
-        }
-      }
-
-      let final_string = '';
-      if (common_indent.length > 0 && common_indent.startsWith(tag_indent)) {
-         const cleaned_lines = raw_lines.map(line => {
-            return line.startsWith(common_indent) ? line.replace(common_indent, '') : line;
-         });
-         
-         if (cleaned_lines.length > 0 && cleaned_lines[0].length === 0) {
-           cleaned_lines.shift();
-         }
-         if (cleaned_lines.length > 0 && cleaned_lines[cleaned_lines.length - 1].trim().length === 0) {
-            cleaned_lines.pop();
-         }
-         final_string = cleaned_lines.join('\n');
-      } else {
-         final_string = text.trim();
-      }
-
-      return final_string;
-    }
-  },
-
-  dom: {
-    measure_outer_height: function(el) {
-      const wasInDOM = el.parentNode !== null;
-      if (!wasInDOM) document.body.appendChild(el);
-      const rect = el.getBoundingClientRect();
-      const style = window.getComputedStyle(el);
-      const margin = parseFloat(style.marginTop) + parseFloat(style.marginBottom);
-      if (!wasInDOM) el.remove();
-      return (rect.height || 0) + (margin || 0);
-    },
-
-    is_block_content: function(element) {
-      return element.textContent.trim().includes('\n');
-    }
-  },
-
-  font: {
-    measure_ink_ratio: function(target_font, ref_font = null) {
-      const debug = window.RT.debug;
-      debug.log('layout', `Measuring ink ratio for ${target_font}`);
-
-      const canvas = document.createElement('canvas');
-      const ctx = canvas.getContext('2d');
-
-      if (!ref_font) {
-        const bodyStyle = window.getComputedStyle(document.body);
-        ref_font = bodyStyle.fontFamily;
-      }
-
-      const get_metrics = (font) => {
-        ctx.font = '100px ' + font; 
-        const metrics = ctx.measureText('M');
-        return {
-          ascent: metrics.actualBoundingBoxAscent, 
-          descent: metrics.actualBoundingBoxDescent 
-        };
-      };
-
-      const ref_m = get_metrics(ref_font);
-      const target_m = get_metrics(target_font);
-      
-      const ratio = ref_m.ascent / target_m.ascent;
-
-      return { 
-        ratio: ratio,
-        baseline_diff: ref_m.descent - target_m.descent 
-      };
-    }
-  },
-
-  color: {
-    extract_l: function(color_string) {
-      const str = String(color_string).trim();
-      
-      if (!str.startsWith('oklch')) {
-        console.error(`[RT:color] Invalid format: Expected oklch color string, received '${str}'`);
-        return 0; 
-      }
-
-      const match = str.match(/oklch\(\s*([\d.]+%?)/);
-      if (!match) {
-        console.error(`[RT:color] Parsing error: Could not extract lightness from '${str}'`);
-        return 0;
-      }
-
-      const l_value = match[1];
-      return l_value.includes('%') ? parseFloat(l_value) / 100 : parseFloat(l_value);
-    },
-
-    is_high_contrast: function(bg_color, text_color) {
-      const bg_l = this.extract_l(bg_color);
-      const text_l = this.extract_l(text_color);
-      return Math.abs(text_l - bg_l) >= 0.7;
-    },
-
-    is_readable: function(bg_color, text_color) {
-      const bg_l = this.extract_l(bg_color);
-      const text_l = this.extract_l(text_color);
-      return Math.abs(text_l - bg_l) >= 0.5;
-    },
-    
-    is_light: function(color_string) {
-      return this.extract_l(color_string) > 0.75;
-    },
-
-    is_gray: function(color_string) {
-      const l = this.extract_l(color_string);
-      return l >= 0.25 && l <= 0.75;
-    },
-
-    is_dark: function(color_string) {
-      return this.extract_l(color_string) < 0.25;
-    }
-  }
-
-};
-
-window.RT.load = function(module_path) {
-  if (window.RT.Module.has(module_path)) {
-    return;
-  }
-  window.RT.Module.add(module_path);
-
-  let resolved_path = window.RT.dirpr_library + '/' + module_path;
-  if (!resolved_path.endsWith('.js')) {
-    resolved_path = resolved_path + '.js';
-  }
-
-  document.write('<script src="' + resolved_path + '"></script>');
-};
diff --git a/developer/authored/Manuscript.copy/Core/stage_manager.js b/developer/authored/Manuscript.copy/Core/stage_manager.js
new file mode 100644 (file)
index 0000000..e1057cb
--- /dev/null
@@ -0,0 +1,143 @@
+// Core/document_loaded.js
+
+window.RT = window.RT || {};
+window.RT.Element = window.RT.Element || [];
+window.RT.Module = window.RT.Module || new Set();
+
+(function(){
+  const debug = window.RT.debug || { log: function(){} };
+  
+  let target_y = 0;
+  let is_reload = false;
+  let is_layout_locked = false;
+  let scroll_timer;
+
+  function lock_layout() {
+    is_layout_locked = true;
+    document.documentElement.style.visibility = "hidden";
+  }
+
+  function unlock_layout() {
+    if (!is_layout_locked) return;
+    is_layout_locked = false;
+    
+    document.documentElement.style.visibility = "";
+    window.removeEventListener("load", unlock_layout);
+    document.dispatchEvent(new Event("RT_layout_complete"));
+  }
+
+  function configure_history(){
+    if ('scrollRestoration' in history) {
+      history.scrollRestoration = 'manual';
+    }
+  }
+
+  function capture_scroll_target(){
+    const raw_target = sessionStorage.getItem('RT_saved_y');
+    target_y = raw_target !== null ? parseInt(raw_target ,10) : 0;
+    
+    if (window.performance) {
+      const nav_entries = performance.getEntriesByType("navigation");
+      if (nav_entries.length > 0) {
+        is_reload = (nav_entries[0].type === "reload");
+      } else if (performance.navigation) {
+        is_reload = (performance.navigation.type === 1);
+      }
+    }
+  }
+
+  function enforce_scroll(target ,use_hash ,attempts){
+    if (attempts > 15) {
+      unlock_layout();
+      return;
+    }
+
+    if (use_hash) {
+      const hash_target = document.getElementById(window.location.hash.substring(1));
+      if (hash_target) {
+        hash_target.scrollIntoView();
+      }
+    } else {
+      window.scrollTo(0 ,target);
+    }
+
+    let is_successful = use_hash ? true : (Math.abs(window.scrollY - target) < 5 || target === 0);
+    if (is_successful && document.body.scrollHeight > 1000) { 
+       setTimeout(() => {
+         if (!use_hash && Math.abs(window.scrollY - target) >= 5) {
+             enforce_scroll(target ,use_hash ,attempts + 1);
+         } else {
+             unlock_layout();
+         }
+       }, 100);
+    } else {
+       setTimeout(() => enforce_scroll(target ,use_hash ,attempts + 1) ,50);
+    }
+  }
+
+  function bind_window_events(){
+    window.addEventListener('scroll' ,() => {
+      if (is_layout_locked) return;
+      clearTimeout(scroll_timer);
+      scroll_timer = setTimeout(() => {
+        sessionStorage.setItem('RT_saved_y' ,window.scrollY);
+      }, 200);
+    }, { passive: true });
+    
+    window.addEventListener('beforeunload' ,() => {
+      lock_layout();
+    });
+  }
+
+  function execute_pagination_and_scroll(){
+    debug.log('scroll' ,`Pagination layout starting.`);
+    if(window.RT.paginate_by_element) window.RT.paginate_by_element();
+    if(window.RT.page) window.RT.page();
+    
+    let final_target = target_y;
+    let use_hash = false;
+    if (window.location.hash && !is_reload) {
+        const hash_target = document.getElementById(window.location.hash.substring(1));
+        if (hash_target) {
+            use_hash = true;
+        }
+    }
+
+    enforce_scroll(final_target ,use_hash ,0);
+  }
+
+  function process_elements_and_layout() {
+    debug.log('lifecycle', 'Processing registered elements.');
+
+    if (window.RT.theme) {
+      window.RT.theme();
+    }
+    
+    if (window.RT.Element && Array.isArray(window.RT.Element)) {
+      while (window.RT.Element.length > 0) {
+        const element_fn = window.RT.Element.shift();
+        if (typeof element_fn === 'function') {
+          element_fn();
+        }
+      }
+    }
+
+    if (window.MathJax && MathJax.Hub && MathJax.Hub.Queue) {
+      MathJax.Hub.Queue(["Typeset", MathJax.Hub], execute_pagination_and_scroll);
+    } else {
+      execute_pagination_and_scroll();
+    }
+  }
+
+  // Initial Execution
+  lock_layout();
+  configure_history();
+  capture_scroll_target();
+  bind_window_events();
+  
+  document.addEventListener('DOMContentLoaded', process_elements_and_layout);
+
+  // Structural Safety Net: restore visibility on load if layout engine hangs
+  window.addEventListener("load", unlock_layout);
+  
+})();
diff --git a/developer/authored/Manuscript.copy/Core/theme_make.js b/developer/authored/Manuscript.copy/Core/theme_make.js
new file mode 100644 (file)
index 0000000..eea792a
--- /dev/null
@@ -0,0 +1,101 @@
+// 1. Establish the Generic Theme Dictionary
+//  e.g. RT.theme( 'read', 'content_main')
+// Establish the global theme library
+window.RT.theme_library = window.RT.theme_library || {};
+
+window.RT.theme = (function() {
+  const dictionary = {
+    meta: { is_dark: false, name: "" },
+    surface: { 0: "", 1: "", 2: "", 3: "", input: "", code: "", select: "" },
+    content: { main: "", muted: "", subtle: "", inverse: "" },
+    brand: { primary: "", secondary: "", tertiary: "", link: "" },
+    border: { faint: "", regular: "", strong: "" },
+    state: { success: "", warning: "", error: "", info: "" },
+    syntax: { keyword: "", string: "", func: "", comment: "" },
+    page: { width: "", min_height: "", padding: "", margin: "", bg_color: "", border_color: "", text_color: "", shadow: "" }
+  };
+
+  function resolve_path(path_array) {
+    let current = dictionary;
+    for (let i = 0; i < path_array.length - 1; i++) {
+      const step = path_array[i];
+      if (current[step] === undefined) return null;
+      current = current[step];
+    }
+    return { container: current, key: path_array[path_array.length - 1] };
+  }
+
+  function apply_and_validate_theme(new_theme, fallback_color) {
+    const debug = window.RT.debug || { error: function(){} };
+
+    // Pass 1: Walk the structure of the active dictionary
+    function walk_current(curr, source, path) {
+      for (const key in curr) {
+        const current_path = path ? path + "." + key : key;
+        if (typeof curr[key] === 'object' && curr[key] !== null) {
+          walk_current(curr[key], source[key] || {}, current_path);
+        } else {
+          if (source[key] !== undefined && source[key] !== "") {
+            curr[key] = source[key];
+          } else {
+            debug.error('theme', `Missing key in loaded theme: ${current_path}. Assigning fallback.`);
+            curr[key] = fallback_color;
+          }
+        }
+      }
+    }
+
+    // Pass 2: Walk the structure of the incoming theme dictionary
+    function walk_new(source, curr, path) {
+      for (const key in source) {
+        const current_path = path ? path + "." + key : key;
+        if (typeof source[key] === 'object' && source[key] !== null) {
+          if (curr[key] === undefined) {
+            debug.error('theme', `Unexpected structure in loaded theme: ${current_path} is an object.`);
+          } else {
+            walk_new(source[key], curr[key] || {}, current_path);
+          }
+        } else {
+          if (curr[key] === undefined) {
+            debug.error('theme', `Unexpected key in loaded theme: ${current_path}.`);
+          }
+        }
+      }
+    }
+
+    walk_current(dictionary, new_theme, "");
+    walk_new(new_theme, dictionary, "");
+  }
+
+  return function(command, ...args) {
+    if (command === 'read') {
+      const target = resolve_path(args);
+      return (target && target.container.hasOwnProperty(target.key)) ? target.container[target.key] : null;
+    } 
+    
+    if (command === 'write') {
+      if (args.length < 2) return;
+      const value = args.pop();
+      const target = resolve_path(args);
+      if (target && target.container.hasOwnProperty(target.key)) {
+        target.container[target.key] = value;
+      }
+      return;
+    }
+
+    if (command === 'load') {
+      const theme_name = args[0];
+      const fallback = args[1] || "#FF00FF";
+
+      if (!window.RT.theme_library.hasOwnProperty(theme_name)) {
+        window.RT.debug.error('theme', `Load aborted: Theme '${theme_name}' is not in the theme_library.`);
+        return false;
+      }
+
+      apply_and_validate_theme(window.RT.theme_library[theme_name], fallback);
+      return true;
+    }
+
+    window.RT.debug.error('theme', 'Invalid command passed to theme dictionary: ' + command);
+  };
+})();
index 0fac1e3..b8dd367 100644 (file)
 window.RT = window.RT || {};
 
 (function() {
-  // We are the style library, so ...
   window.RT.dirpr_library = "..";
-  
-  // 1. Inject the loader script
-  document.write('<script src="' + window.RT.dirpr_library + '/Core/loader.js"><\/script>');
+  document.write('<script src="' + window.RT.dirpr_library + '/Core/RT-Style_make.js"><\/script>');
   
   // 2. Inject a secondary script block for the core dependencies
   document.write(
     '<script>' +
-    'window.RT.load("Core/utility");' +
-    'window.RT.load("Core/block_visibility_during_layout");' +
-    'window.RT.load("Theme");' +
     'window.RT.load("Element/theme_selector");' +
     '<\/script>'
   );
diff --git a/developer/authored/Manuscript.copy/Document/RT-style.js b/developer/authored/Manuscript.copy/Document/RT-style.js
deleted file mode 100644 (file)
index dcd7ff2..0000000
+++ /dev/null
@@ -1,20 +0,0 @@
-// for documents in RT-style/Manuscript/document
-window.RT = window.RT || {};
-
-(function() {
-  // We are the style library, so ...
-  window.RT.dirpr_library = "..";
-  
-  // 1. Inject the loader script
-  document.write('<script src="' + window.RT.dirpr_library + '/Core/loader.js"><\/script>');
-  
-  // 2. Inject a secondary script block for the core dependencies
-  document.write(
-    '<script>' +
-    'window.RT.load("Core/utility");' +
-    'window.RT.load("Core/block_visibility_during_layout");' +
-    'window.RT.load("Theme");' +
-    'window.RT.load("Element/theme_selector");' +
-    '<\/script>'
-  );
-})();
index 9545d07..a2d9afe 100644 (file)
@@ -3,16 +3,14 @@
   <head>
     <meta charset="UTF-8">
     <title>RT Style System: Reference Manual</title>
-    
     <script src="RT-Style_locator.js"></script>
     <script>
+      window.RT.theme_preference('golden_wheat');
       window.RT.load('Layout/article_tech_ref');
     </script>
-
   </head>
   <body>
     <RT·theme-selector></RT·theme-selector>
-
     <RT·article>
 
       <RT·title 
index 3e94b49..39b4829 100644 (file)
@@ -1,11 +1,13 @@
+// Element/theme_selector.js
+
 window.RT = window.RT || {};
+window.RT.Element = window.RT.Element || [];
 
-window.RT.theme_selector = function(){
-  document.querySelectorAll('rt·theme-selector').forEach( (el) => {
-    let current_theme = localStorage.getItem('RT_theme_preference');
-    if(!current_theme){
-      current_theme = 'dark_gold';
-    }
+window.RT.Element.push(function build_theme_selector() {
+  document.querySelectorAll('rt·theme-selector').forEach((el) => {
+    
+    const active_theme = window.RT.theme('read', 'meta', 'name');
+    const available_themes = Object.keys(window.RT.theme_library || {});
     
     const container = document.createElement('div');
     container.style.position = 'fixed';
@@ -18,23 +20,31 @@ window.RT.theme_selector = function(){
     container.style.color = 'white';
     container.style.fontFamily = 'sans-serif';
 
-    container.innerHTML = `
-      <b>Theme Selection</b><br>
-      <label>
-        <input type="radio" name="RT·theme" value="dark_gold" ${current_theme === 'dark_gold' ? 'checked' : ''}> Dark Gold
-      </label><br>
-      <label>
-        <input type="radio" name="RT·theme" value="light_gold" ${current_theme === 'light_gold' ? 'checked' : ''}> Light Gold
-      </label>
-    `;
+    let html_content = `<b>Theme Selection</b><br>`;
+    
+    if (available_themes.length === 0) {
+      html_content += `<small>No themes found in library.</small>`;
+    } else {
+      available_themes.forEach(theme_name => {
+        const is_checked = active_theme === theme_name ? 'checked' : '';
+        html_content += `
+          <label>
+            <input type="radio" name="RT·theme" value="${theme_name}" ${is_checked}> ${theme_name}
+          </label><br>
+        `;
+      });
+    }
+
+    container.innerHTML = html_content;
 
-    container.addEventListener( 'change' ,(e) => {
+    container.addEventListener('change', (e) => {
       if(e.target.name === 'RT·theme') {
-        localStorage.setItem('RT_theme_preference' ,e.target.value);
-        location.reload();
+        localStorage.setItem('RT-Style·theme_preference', e.target.value);
+        // Reloading applies the new preference via theme_preference() in the <head>
+        location.reload(); 
       }
     });
 
     el.replaceWith(container);
   });
-};
+});
index ffc9420..d015b0d 100644 (file)
 (function(){
   const RT = window.RT = window.RT || {};
-  const debug = RT.debug || { log: function(){} };
 
-  let target_y = 0;
-  let is_reload = false;
-  let is_layout_locked = true;
-  let scroll_timer;
-
-  function configure_history(){
-    if ('scrollRestoration' in history) {
-      history.scrollRestoration = 'manual';
-    }
-  }
-
-  function capture_scroll_target(){
-    const raw_target = sessionStorage.getItem('RT_saved_y');
-    target_y = raw_target !== null ? parseInt(raw_target ,10) : 0;
-    
-    if (window.performance) {
-      const nav_entries = performance.getEntriesByType("navigation");
-      if (nav_entries.length > 0) {
-        is_reload = (nav_entries[0].type === "reload");
-      } else if (performance.navigation) {
-        is_reload = (performance.navigation.type === 1);
-      }
-    }
-  }
-
-  function load_elements(){
-    // The specific elements requested by the layout
-    RT.load('Element/counter');
-    RT.load('Element/chapter');
-    RT.load('Element/endnote');
-    RT.load('Element/math');
-    RT.load('Element/code');
-    RT.load('Element/term');
-    RT.load('Element/TOC');
-    RT.load('Element/title');
-    RT.load('Element/symbol');
-    RT.load('Element/constraint');
-    RT.load('Element/crossref');
-
-    RT.load('Layout/paginate_by_element');
-    RT.load('Layout/page_fixed_glow');
-  }
-
-  function apply_style_rule(selector ,rules){
-    document.querySelectorAll(selector).forEach( (el) => {
-      for (let prop in rules) {
-        if (typeof rules[prop] === 'string' && rules[prop].indexOf('!important') !== -1) {
-          const kebab_prop = prop.replace(/[A-Z]/g ,m => "-" + m.toLowerCase());
-          const value = rules[prop].replace(' !important' ,'');
-          el.style.setProperty(kebab_prop ,value ,'important');
-        } else {
-          el.style[prop] = rules[prop];
+  // 1. The Explicit Element Roster 
+  const required_elements = [
+    'counter',
+    'chapter',
+    'endnote',
+    'math',
+    'code',
+    'term',
+    'TOC',
+    'title',
+    'symbol',
+    'constraint',
+    'crossref'
+  ];
+
+  // Trigger file loading immediately
+  required_elements.forEach(name => RT.load('Element/' + name));
+  
+  // 2. The Extracted Styling Function
+  function apply_article_styles() {
+    const t = function(...path) { return window.RT.theme('read', ...path); };
+
+    const surface_0 = t('surface', '0');
+    const surface_code = t('surface', 'code');
+    const content_main = t('content', 'main');
+    const brand_primary = t('brand', 'primary');
+    const brand_secondary = t('brand', 'secondary');
+    const brand_tertiary = t('brand', 'tertiary');
+    const is_dark = t('meta', 'is_dark');
+
+    const font_weight = is_dark === false ? "600" : "400";
+
+    const apply = function(selector, rules) {
+      document.querySelectorAll(selector).forEach(el => {
+        for (let p in rules) {
+          if (typeof rules[p] === 'string' && rules[p].includes('!important')) {
+            el.style.setProperty(p.replace(/[A-Z]/g, m => "-" + m.toLowerCase()), rules[p].replace(' !important', ''), 'important');
+          } else {
+            el.style[p] = rules[p];
+          }
         }
-      }
-    });
-  }
-
-  function apply_style(){
-    // Note: This will be updated to read from window.RT.theme('read', ...) 
-    // in the next iteration.
-    RT.config = RT.config || {};
-    RT.config.article = {
-      font_family: "'Noto Sans JP', Arial, sans-serif"
-      ,line_height: "1.8"       
-      ,font_size: "16px"        
-      ,font_weight: "400"
-      ,max_width: "46.875rem" 
-      ,margin: "0 auto"
+      });
     };
-    
-    if( RT.config.theme && RT.config.theme.meta_is_dark === false ){
-      RT.config.article.font_weight = "600";
-    }
 
-    window.RT.config.page = window.RT.config.page || {};
-    window.RT.config.page.height_limit = 900; 
-
-    const conf = RT.config.article;
-
-    apply_style_rule('body, html, RT·article' ,{ overflowAnchor: "none !important" });
-    apply_style_rule('RT·article', {
+    // Apply base geometry
+    apply('body, html, RT·article', { overflowAnchor: "none !important" });
+    apply('RT·article', {
       display: "block",
-      fontFamily: conf.font_family,
-      fontSize: conf.font_size,
-      lineHeight: conf.line_height,
-      fontWeight: conf.font_weight,
-      maxWidth: conf.max_width + " !important",
-      margin: conf.margin,
-      backgroundColor: RT.config.theme.surface_0,
-      color: RT.config.theme.content_main,
+      fontFamily: "'Noto Sans JP', Arial, sans-serif",
+      fontSize: "16px",
+      lineHeight: "1.8",
+      fontWeight: font_weight,
+      maxWidth: "46.875rem !important",
+      margin: "0 auto",
+      backgroundColor: surface_0,
+      color: content_main,
       boxSizing: "border-box !important"
     });
     
-    apply_style_rule('RT·article:not(:has(RT·page))' ,{ padding: "3rem !important" });
-    apply_style_rule('RT·article:has(RT·page)' ,{ padding: "0 !important" });
-    apply_style_rule('RT·article RT·page' ,{
-      position: "relative",
-      display: "block",
-      padding: "3rem",
-      margin: "1.25rem auto",
-      backgroundColor: RT.config.theme.surface_0,
-      boxShadow: `0 0 0.625rem ${RT.config.theme.brand_primary}`
+    apply('RT·article:not(:has(RT·page))', { padding: "3rem !important" });
+    apply('RT·article:has(RT·page)', { padding: "0 !important" });
+    apply('RT·article RT·page', {
+      position: "relative", display: "block", padding: "3rem",
+      margin: "1.25rem auto", backgroundColor: surface_0,
+      boxShadow: `0 0 0.625rem ${brand_primary}`
     });
 
-    apply_style_rule('RT·article h1' ,{ fontSize: "1.5rem", textAlign: "center", color: RT.config.theme.brand_primary, fontWeight: "500", marginTop: "1.5rem", lineHeight: "1.15" });
-    apply_style_rule('RT·article h2' ,{ fontSize: "1.25rem", color: RT.config.theme.brand_secondary, textAlign: "left", marginTop: "2rem", marginLeft: "0" });
-    apply_style_rule('RT·article h3' ,{ fontSize: "1.125rem", color: RT.config.theme.brand_tertiary, textAlign: "left", marginTop: "1.5rem", marginLeft: "4ch" });
-    apply_style_rule('RT·article h4' ,{ fontSize: "1.05rem", color: RT.config.theme.content_main, fontWeight: "600", textAlign: "left", marginTop: "1.25rem", marginLeft: "8ch" });
-    apply_style_rule('RT·article p, RT·article ul, RT·article ol' ,{ color: RT.config.theme.content_main, textAlign: "justify", marginBottom: "1rem", marginLeft: "0" });
-    apply_style_rule('RT·article li' ,{ marginBottom: "0.5rem" });
-    apply_style_rule('RT·article RT·code' ,{ fontFamily: "'Courier New', Courier, monospace", backgroundColor: RT.config.theme.surface_code, padding: "0.125rem 0.25rem", color: RT.config.theme.content_main });
-    apply_style_rule('RT·article img' ,{ maxWidth: "100%", height: "auto", display: "block", margin: "1.5rem auto" });
+    // Apply specific element scales
+    const element_styles = [
+      [ 'RT·article h1', { 
+          fontSize:   "1.5rem", 
+          textAlign:  "center", 
+          color:      brand_primary, 
+          fontWeight: "500", 
+          marginTop:  "1.5rem", 
+          lineHeight: "1.15" 
+      }],
+      
+      [ 'RT·article h2', { 
+          fontSize:   "1.25rem", 
+          color:      brand_secondary, 
+          textAlign:  "left", 
+          marginTop:  "2rem", 
+          marginLeft: "0" 
+      }],
+      
+      [ 'RT·article h3', { 
+          fontSize:   "1.125rem", 
+          color:      brand_tertiary, 
+          textAlign:  "left", 
+          marginTop:  "1.5rem", 
+          marginLeft: "4ch" 
+      }],
+      
+      [ 'RT·article h4', { 
+          fontSize:   "1.05rem", 
+          color:      content_main, 
+          fontWeight: "600", 
+          textAlign:  "left", 
+          marginTop:  "1.25rem", 
+          marginLeft: "8ch" 
+      }],
+      
+      [ 'RT·article p, RT·article ul, RT·article ol', { 
+          color:        content_main, 
+          textAlign:    "justify", 
+          marginBottom: "1rem", 
+          marginLeft:   "0" 
+      }],
+      
+      [ 'RT·article li', { 
+          marginBottom: "0.5rem" 
+      }],
+      
+      [ 'RT·article RT·code', { 
+          fontFamily:      "'Courier New', Courier, monospace", 
+          backgroundColor: surface_code, 
+          padding:         "0.125rem 0.25rem", 
+          color:           content_main 
+      }],
+      
+      [ 'RT·article img', { 
+          maxWidth: "100%", 
+          height:   "auto", 
+          display:  "block", 
+          margin:   "1.5rem auto" 
+      }]
+    ];
+
+    element_styles.forEach(rule => apply(rule[0], rule[1]));
   }
 
-  function execute_pagination_and_scroll(){
-    debug.log('scroll' ,`8. Pagination layout starting.`);
-    if(RT.paginate_by_element) RT.paginate_by_element();
-    if(RT.page) RT.page();
+  // 3. The Core Layout Entry Function
+  function article_tech_ref(){
     
-    let final_target = target_y;
-    let use_hash = false;
-    if (window.location.hash && !is_reload) {
-        const hash_target = document.getElementById(window.location.hash.substring(1));
-        if (hash_target) {
-            use_hash = true;
-        }
-    }
-
-    enforce_scroll(final_target ,use_hash ,0);
-  }
-
-  function enforce_scroll(target ,use_hash ,attempts){
-    if (attempts > 15) {
-      unlock_layout();
-      return;
-    }
-
-    if (use_hash) {
-      const hash_target = document.getElementById(window.location.hash.substring(1));
-      if (hash_target) {
-        hash_target.scrollIntoView();
+    // Execute the extracted style generator first
+    apply_article_styles();
+
+    // Dynamically enqueue the semantic processors
+    required_elements.forEach(name => {
+      if (typeof RT[name] === 'function') {
+        RT.Element.push(RT[name]);
+      } else {
+        RT.debug.warn('layout', 'Required element function missing: RT.' + name);
       }
-    } else {
-      window.scrollTo(0 ,target);
-    }
-
-    let is_successful = use_hash ? true : (Math.abs(window.scrollY - target) < 5 || target === 0);
-    if (is_successful && document.body.scrollHeight > 1000) { 
-       setTimeout(() => {
-         if (!use_hash && Math.abs(window.scrollY - target) >= 5) {
-             enforce_scroll(target ,use_hash ,attempts + 1);
-         } else {
-             unlock_layout();
-         }
-       }, 100);
-    } else {
-       setTimeout(() => enforce_scroll(target ,use_hash ,attempts + 1) ,50);
-    }
-  }
-
-  function unlock_layout(){
-    if (!is_layout_locked) return;
-    is_layout_locked = false;
-    document.dispatchEvent(new Event("RT_layout_complete"));
-  }
-
-  function bind_window_events(){
-    window.addEventListener('scroll' ,() => {
-      if (is_layout_locked) return;
-      clearTimeout(scroll_timer);
-      scroll_timer = setTimeout(() => {
-        sessionStorage.setItem('RT_saved_y' ,window.scrollY);
-      }, 200);
-    }, { passive: true });
-    
-    window.addEventListener('beforeunload' ,() => {
-      is_layout_locked = true;
     });
   }
 
-  // Execution Outline
-  configure_history();
-  capture_scroll_target();
-  load_elements();
-  bind_window_events();
-  
-  document.addEventListener('DOMContentLoaded', () => {
-    apply_style();             
-    
-    if (window.RT.document_loaded) {
-      window.RT.document_loaded(execute_pagination_and_scroll);
-    } else {
-      execute_pagination_and_scroll();
-    }
-  });
+  // 4. Register the layout function immediately upon parsing
+  RT.Element = RT.Element || [];
+  RT.Element.push(article_tech_ref);
 
 })();
index 2f93eb7..f9457a5 100644 (file)
@@ -31,9 +31,7 @@ window.RT = window.RT || {};
   
   document.write(
     '<script>' +
-    'window.RT.load("Core/utility");' +
     'window.RT.load("Core/block_visibility_during_layout");' +
-    'window.RT.load("Theme");' +
     'window.RT.load("Element/theme_selector");' +
     '<\/script>'
   );
index acc509f..8ccaa16 100644 (file)
@@ -1,98 +1,57 @@
-/*
-  Theme: Golden Wheat (Light) - "Spanish Gold Edition"
-  Standard: Theme 1.0
-  Description: Light Parchment background with Oxblood Red ink.
-*/
-(function(){
-  const RT = window.RT = window.RT || {};
-  
-  RT.theme = function(){
-    const dictionary = {
-       meta_is_dark: false
-      ,meta_name:    "Golden Wheat (Yellow)"
-
-      // --- SURFACES ---
-      ,surface_0:       "oklch(0.95 0.02 90)"
-      ,surface_1:       "oklch(0.92 0.02 90)"
-      ,surface_2:       "oklch(0.97 0.01 90)"
-      ,surface_3:       "oklch(0.99 0 0)"
-      ,surface_input:   "oklch(0.94 0.01 90)"
-      ,surface_code:    "oklch(0.90 0.02 90)"
-      ,surface_select:  "oklch(0.85 0.05 25)"
-
-      // --- CONTENT ---
-      ,content_main:    "oklch(0.20 0.02 25)"
-      ,content_muted:   "oklch(0.35 0.03 25)"
-      ,content_subtle:  "oklch(0.55 0.02 25)"
-      ,content_inverse: "oklch(0.92 0.02 90)"
-
-      // --- BRAND & ACTION ---
-      ,brand_primary:   "oklch(0.40 0.15 25)"
-      ,brand_secondary: "oklch(0.45 0.14 25)"
-      ,brand_tertiary:  "oklch(0.50 0.12 25)"
-      ,brand_link:      "oklch(0.40 0.16 25)"
-
-      // --- BORDERS ---
-      ,border_faint:    "oklch(0.85 0.02 90)"
-      ,border_default:  "oklch(0.75 0.03 90)"
-      ,border_strong:   "oklch(0.50 0.08 25)"
-
-      // --- STATE & FEEDBACK ---
-      ,state_success:   "oklch(0.45 0.10 130)"
-      ,state_warning:   "oklch(0.55 0.15 45)"
-      ,state_error:     "oklch(0.45 0.15 25)"
-      ,state_info:      "oklch(0.50 0.12 240)"
-
-      // --- SYNTAX ---
-      ,syntax_keyword:  "oklch(0.45 0.15 25)"
-      ,syntax_string:   "oklch(0.40 0.10 130)"
-      ,syntax_func:     "oklch(0.45 0.12 35)"
-      ,syntax_comment:  "oklch(0.60 0.02 90)"
-    };
-
-    // 1. Populate the Dictionary
-    for (const [key, value] of Object.entries(dictionary)) {
-      window.RT.theme('write', key, value);
-    }
-
-    // 2. Structural Safety Net
-    if (!window.RT.theme('is_defined')) {
-      window.RT.debug.error('theme', `Theme '${dictionary.meta_name}' failed structural completeness check. Missing keys detected.`);
-    }
-
-    // 3. Global Pseudo Elements
-    const style_id = 'rt-global-overrides';
-    if (!document.getElementById(style_id)) {
-      const style = document.createElement('style');
-      style.id = style_id;
-      
-      const [select_bg, select_fg, scroll_bg, scroll_thumb, scroll_hover, content_main] = 
-        window.RT.theme('read', 'surface_select', 'brand_primary', 'surface_0', 'border_default', 'brand_secondary', 'content_main');
-
-      style.textContent = `
-        ::selection { background: ${select_bg}; color: ${select_fg}; }
-        ::-moz-selection { background: ${select_bg}; color: ${select_fg}; }
-        
-        ::-webkit-scrollbar { width: 12px; }
-        ::-webkit-scrollbar-track { background: ${scroll_bg}; }
-        ::-webkit-scrollbar-thumb { 
-           background: ${scroll_thumb};
-           border: 2px solid ${scroll_bg};
-           border-radius: 8px; 
-        }
-        ::-webkit-scrollbar-thumb:hover { background: ${scroll_hover}; }
-
-        rt-article p, rt-article li {
-           text-shadow: 0px 0px 0.5px rgba(0,0,0, 0.2);
-        }
-
-        .MathJax, .MathJax_Display, .mjx-chtml {
-            color: ${content_main} !important;
-            fill: ${content_main} !important;
-            stroke: ${content_main} !important;
-        }
-      `;
-      document.head.appendChild(style);
+// Theme/golden_wheat.js
+
+window.RT = window.RT || {};
+window.RT.theme_library = window.RT.theme_library || {};
+
+window.RT.theme_library['golden_wheat'] = {
+  meta: {
+    is_dark: false,
+    name: "Golden Wheat (Yellow)"
+  },
+  surface: {
+    0: "oklch(0.95 0.02 90)",
+    1: "oklch(0.92 0.02 90)",
+    2: "oklch(0.97 0.01 90)",
+    3: "oklch(0.99 0 0)",
+    input: "oklch(0.94 0.01 90)",
+    code: "oklch(0.90 0.02 90)",
+    select: "oklch(0.85 0.05 25)"
+  },
+  content: {
+    main: "oklch(0.20 0.02 25)",
+    muted: "oklch(0.35 0.03 25)",
+    subtle: "oklch(0.55 0.02 25)",
+    inverse: "oklch(0.92 0.02 90)"
+  },
+  brand: {
+    primary: "oklch(0.40 0.15 25)",
+    secondary: "oklch(0.45 0.14 25)",
+    tertiary: "oklch(0.50 0.12 25)",
+    link: "oklch(0.40 0.16 25)"
+  },
+  border: {
+    faint: "oklch(0.85 0.02 90)",
+    regular: "oklch(0.75 0.03 90)",
+    strong: "oklch(0.50 0.08 25)"
+  },
+  state: {
+    success: "oklch(0.45 0.10 130)",
+    warning: "oklch(0.55 0.15 45)",
+    error: "oklch(0.45 0.15 25)",
+    info: "oklch(0.50 0.12 240)"
+  },
+  syntax: {
+    keyword: "oklch(0.45 0.15 25)",
+    string: "oklch(0.40 0.10 130)",
+    func: "oklch(0.45 0.12 35)",
+    comment: "oklch(0.60 0.02 90)"
+  },
+  custom_css: `
+    rt-article p, rt-article li { text-shadow: 0px 0px 0.5px rgba(0,0,0, 0.2); }
+    .MathJax, .MathJax_Display, .mjx-chtml {
+        color: oklch(0.20 0.02 25) !important;
+        fill: oklch(0.20 0.02 25) !important;
+        stroke: oklch(0.20 0.02 25) !important;
     }
-  };
-})();
+  `
+};
index 53c356d..c4acc80 100644 (file)
@@ -1,90 +1,52 @@
-/*
-  Theme: Inverse Wheat (Dark)
-  Standard: Theme 1.0
-  Description: High contrast Amber on Deep Charcoal.
-*/
-(function(){
-  const RT = window.RT = window.RT || {};
-  
-  RT.theme = function(){
-    const dictionary = {
-       meta_is_dark: true
-      ,meta_name:    "Inverse Wheat"
-
-      // --- SURFACES ---
-      ,surface_0:       "oklch(0.15 0 0)"
-      ,surface_1:       "oklch(0.18 0 0)"
-      ,surface_2:       "oklch(0.21 0 0)"
-      ,surface_3:       "oklch(0.24 0 0)"
-      ,surface_input:   "oklch(0.19 0 0)"
-      ,surface_code:    "oklch(0.17 0 0)"
-      ,surface_select:  "oklch(0.30 0.05 80)"
-
-      // --- CONTENT ---
-      ,content_main:    "oklch(0.85 0.05 90)"
-      ,content_muted:   "oklch(0.70 0.03 90)"
-      ,content_subtle:  "oklch(0.50 0.02 90)"
-      ,content_inverse: "oklch(0.15 0 0)"
-
-      // --- BRAND & ACTION ---
-      ,brand_primary:   "oklch(0.75 0.15 80)"
-      ,brand_secondary: "oklch(0.65 0.12 70)"
-      ,brand_tertiary:  "oklch(0.60 0.10 60)"
-      ,brand_link:      "oklch(0.75 0.15 85)"
-
-      // --- BORDERS ---
-      ,border_faint:    "oklch(0.25 0.01 90)"
-      ,border_default:  "oklch(0.35 0.02 90)"
-      ,border_strong:   "oklch(0.45 0.03 90)"
-
-      // --- STATE & FEEDBACK ---
-      ,state_success:   "oklch(0.60 0.12 130)"
-      ,state_warning:   "oklch(0.65 0.15 50)"
-      ,state_error:     "oklch(0.55 0.15 25)"
-      ,state_info:      "oklch(0.60 0.10 240)"
-
-      // --- SYNTAX ---
-      ,syntax_keyword:  "oklch(0.70 0.15 50)"
-      ,syntax_string:   "oklch(0.75 0.10 130)"
-      ,syntax_func:     "oklch(0.80 0.12 85)"
-      ,syntax_comment:  "oklch(0.55 0.02 90)"
-    };
-
-    // 1. Populate the Dictionary
-    for (const [key, value] of Object.entries(dictionary)) {
-      window.RT.theme('write', key, value);
-    }
-
-    // 2. Structural Safety Net
-    if (!window.RT.theme('is_defined')) {
-      window.RT.debug.error('theme', `Theme '${dictionary.meta_name}' failed structural completeness check. Missing keys detected.`);
-    }
-
-    // 3. Global Pseudo Elements
-    const style_id = 'rt-global-overrides';
-    if (!document.getElementById(style_id)) {
-      const style = document.createElement('style');
-      style.id = style_id;
-      
-      const [select_bg, select_fg, scroll_bg, scroll_thumb, scroll_hover] = 
-        window.RT.theme('read', 'surface_select', 'brand_primary', 'surface_0', 'border_default', 'brand_secondary');
-
-      style.textContent = `
-        ::selection { background: ${select_bg}; color: ${select_fg}; }
-        ::-moz-selection { background: ${select_bg}; color: ${select_fg}; }
-        
-        ::-webkit-scrollbar { width: 12px; }
-        ::-webkit-scrollbar-track { background: ${scroll_bg}; }
-        ::-webkit-scrollbar-thumb { 
-           background: ${scroll_thumb};
-           border: 2px solid ${scroll_bg};
-           border-radius: 8px; 
-        }
-        ::-webkit-scrollbar-thumb:hover { background: ${scroll_hover}; }
-
-        img.rt-diagram { filter: invert(1) hue-rotate(180deg); }
-      `;
-      document.head.appendChild(style);
-    }
-  };
-})();
+// Theme/inverse_wheat.js
+
+window.RT = window.RT || {};
+window.RT.theme_library = window.RT.theme_library || {};
+
+window.RT.theme_library['inverse_wheat'] = {
+  meta: {
+    is_dark: true,
+    name: "Inverse Wheat"
+  },
+  surface: {
+    0: "oklch(0.15 0 0)",
+    1: "oklch(0.18 0 0)",
+    2: "oklch(0.21 0 0)",
+    3: "oklch(0.24 0 0)",
+    input: "oklch(0.19 0 0)",
+    code: "oklch(0.17 0 0)",
+    select: "oklch(0.30 0.05 80)"
+  },
+  content: {
+    main: "oklch(0.85 0.05 90)",
+    muted: "oklch(0.70 0.03 90)",
+    subtle: "oklch(0.50 0.02 90)",
+    inverse: "oklch(0.15 0 0)"
+  },
+  brand: {
+    primary: "oklch(0.75 0.15 80)",
+    secondary: "oklch(0.65 0.12 70)",
+    tertiary: "oklch(0.60 0.10 60)",
+    link: "oklch(0.75 0.15 85)"
+  },
+  border: {
+    faint: "oklch(0.25 0.01 90)",
+    regular: "oklch(0.35 0.02 90)",
+    strong: "oklch(0.45 0.03 90)"
+  },
+  state: {
+    success: "oklch(0.60 0.12 130)",
+    warning: "oklch(0.65 0.15 50)",
+    error: "oklch(0.55 0.15 25)",
+    info: "oklch(0.60 0.10 240)"
+  },
+  syntax: {
+    keyword: "oklch(0.70 0.15 50)",
+    string: "oklch(0.75 0.10 130)",
+    func: "oklch(0.80 0.12 85)",
+    comment: "oklch(0.55 0.02 90)"
+  },
+  custom_css: `
+    img.rt-diagram { filter: invert(1) hue-rotate(180deg); }
+  `
+};
diff --git a/developer/authored/Manuscript.copy/Theme/manifest.js b/developer/authored/Manuscript.copy/Theme/manifest.js
new file mode 100644 (file)
index 0000000..3900800
--- /dev/null
@@ -0,0 +1,16 @@
+// Theme/manifest.js
+
+window.RT = window.RT || {};
+
+(function() {
+  const themes = [
+    'inverse_wheat',
+    'golden_wheat',
+    'wheat'
+  ];
+
+  themes.forEach(theme_name => {
+    window.RT.load('Theme/' + theme_name);
+  });
+})();
+
index 2571cd8..8a1e751 100644 (file)
@@ -1,88 +1,50 @@
-/*
-  Theme: Classic Wheat (Light)
-  Standard: Theme 1.0
-  Description: Warm paper tones with Burnt Orange accents.
-*/
-(function(){
-  const RT = window.RT = window.RT || {};
-  
-  RT.theme_light = function(){
-    const dictionary = {
-       meta_is_dark: false
-      ,meta_name:    "Classic Wheat"
-
-      // --- SURFACES ---
-      ,surface_0:       "oklch(0.95 0.02 80)"
-      ,surface_1:       "oklch(0.92 0.02 80)"
-      ,surface_2:       "oklch(0.97 0.01 80)"
-      ,surface_3:       "oklch(0.99 0 0)"
-      ,surface_input:   "oklch(0.96 0.01 80)"
-      ,surface_code:    "oklch(0.92 0.01 80)"
-      ,surface_select:  "oklch(0.88 0.06 80)"
-
-      // --- CONTENT ---
-      ,content_main:    "oklch(0.25 0.02 60)"
-      ,content_muted:   "oklch(0.45 0.03 60)"
-      ,content_subtle:  "oklch(0.65 0.02 60)"
-      ,content_inverse: "oklch(0.94 0.02 80)"
-
-      // --- BRAND & ACTION ---
-      ,brand_primary:   "oklch(0.50 0.15 50)"
-      ,brand_secondary: "oklch(0.55 0.12 60)"
-      ,brand_tertiary:  "oklch(0.60 0.10 45)"
-      ,brand_link:      "oklch(0.50 0.16 50)"
-
-      // --- BORDERS ---
-      ,border_faint:    "oklch(0.85 0.02 80)"
-      ,border_default:  "oklch(0.75 0.02 80)"
-      ,border_strong:   "oklch(0.55 0.04 80)"
-
-      // --- STATE & FEEDBACK ---
-      ,state_success:   "oklch(0.50 0.10 130)"
-      ,state_warning:   "oklch(0.60 0.15 50)"
-      ,state_error:     "oklch(0.50 0.15 25)"
-      ,state_info:      "oklch(0.55 0.10 240)"
-
-      // --- SYNTAX ---
-      ,syntax_keyword:  "oklch(0.50 0.14 50)"
-      ,syntax_string:   "oklch(0.45 0.10 130)"
-      ,syntax_func:     "oklch(0.50 0.10 320)"
-      ,syntax_comment:  "oklch(0.65 0.02 80)"
-    };
-
-    // 1. Populate the Dictionary
-    for (const [key, value] of Object.entries(dictionary)) {
-      window.RT.theme('write', key, value);
-    }
-
-    // 2. Structural Safety Net
-    if (!window.RT.theme('is_defined')) {
-      window.RT.debug.error('theme', `Theme '${dictionary.meta_name}' failed structural completeness check. Missing keys detected.`);
-    }
-
-    // 3. Global Pseudo Elements
-    const style_id = 'rt-global-overrides';
-    if (!document.getElementById(style_id)) {
-      const style = document.createElement('style');
-      style.id = style_id;
-      
-      const [select_bg, select_fg, scroll_bg, scroll_thumb, scroll_hover] = 
-        window.RT.theme('read', 'surface_select', 'brand_primary', 'surface_0', 'border_default', 'brand_secondary');
-
-      style.textContent = `
-        ::selection { background: ${select_bg}; color: ${select_fg}; }
-        ::-moz-selection { background: ${select_bg}; color: ${select_fg}; }
-        
-        ::-webkit-scrollbar { width: 12px; }
-        ::-webkit-scrollbar-track { background: ${scroll_bg}; }
-        ::-webkit-scrollbar-thumb { 
-           background: ${scroll_thumb};
-           border: 2px solid ${scroll_bg};
-           border-radius: 8px; 
-        }
-        ::-webkit-scrollbar-thumb:hover { background: ${scroll_hover}; }
-      `;
-      document.head.appendChild(style);
-    }
-  };
-})();
+// Theme/wheat.js
+
+window.RT = window.RT || {};
+window.RT.theme_library = window.RT.theme_library || {};
+
+window.RT.theme_library['wheat'] = {
+  meta: {
+    is_dark: false,
+    name: "Classic Wheat"
+  },
+  surface: {
+    0: "oklch(0.95 0.02 80)",
+    1: "oklch(0.92 0.02 80)",
+    2: "oklch(0.97 0.01 80)",
+    3: "oklch(0.99 0 0)",
+    input: "oklch(0.96 0.01 80)",
+    code: "oklch(0.92 0.01 80)",
+    select: "oklch(0.88 0.06 80)"
+  },
+  content: {
+    main: "oklch(0.25 0.02 60)",
+    muted: "oklch(0.45 0.03 60)",
+    subtle: "oklch(0.65 0.02 60)",
+    inverse: "oklch(0.94 0.02 80)"
+  },
+  brand: {
+    primary: "oklch(0.50 0.15 50)",
+    secondary: "oklch(0.55 0.12 60)",
+    tertiary: "oklch(0.60 0.10 45)",
+    link: "oklch(0.50 0.16 50)"
+  },
+  border: {
+    faint: "oklch(0.85 0.02 80)",
+    regular: "oklch(0.75 0.02 80)",
+    strong: "oklch(0.55 0.04 80)"
+  },
+  state: {
+    success: "oklch(0.50 0.10 130)",
+    warning: "oklch(0.60 0.15 50)",
+    error: "oklch(0.50 0.15 25)",
+    info: "oklch(0.55 0.10 240)"
+  },
+  syntax: {
+    keyword: "oklch(0.50 0.14 50)",
+    string: "oklch(0.45 0.10 130)",
+    func: "oklch(0.50 0.10 320)",
+    comment: "oklch(0.65 0.02 80)"
+  },
+  custom_css: ``
+};