@codady/utils 0.0.38 → 0.0.40
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +37 -0
- package/dist/utils.cjs.js +576 -24
- package/dist/utils.cjs.min.js +3 -3
- package/dist/utils.esm.js +576 -24
- package/dist/utils.esm.min.js +3 -3
- package/dist/utils.umd.js +576 -24
- package/dist/utils.umd.min.js +3 -3
- package/dist.zip +0 -0
- package/examples/ajax-download.html +94 -0
- package/examples/ajax-get.html +59 -0
- package/examples/ajax-hook.html +55 -0
- package/examples/ajax-method.html +36 -0
- package/examples/ajax-post.html +37 -0
- package/examples/ajax-signal.html +91 -0
- package/examples/ajax-timeout.html +85 -0
- package/examples/buildUrl.html +99 -0
- package/examples/getUrlHash.html +71 -0
- package/examples/stringToEncodings-collision-test-registry.html +117 -0
- package/examples/stringToEncodings-collision-test.html +71 -0
- package/examples/stringToEncodings.html +138 -0
- package/examples/unicodeToEncodings.html +195 -0
- package/modules.js +17 -1
- package/modules.ts +17 -1
- package/package.json +1 -1
- package/src/ajax.js +380 -0
- package/src/ajax.ts +470 -0
- package/src/buildUrl.js +64 -0
- package/src/buildUrl.ts +86 -0
- package/src/capitalize.js +19 -0
- package/src/capitalize.ts +20 -0
- package/src/cleanQueryString.js +19 -0
- package/src/cleanQueryString.ts +20 -0
- package/src/getBodyHTML.js +53 -0
- package/src/getBodyHTML.ts +61 -0
- package/src/getEl.js +1 -1
- package/src/getEl.ts +6 -5
- package/src/getEls.js +1 -1
- package/src/getEls.ts +5 -5
- package/src/getUrlHash.js +37 -0
- package/src/getUrlHash.ts +39 -0
- package/src/isEmpty.js +24 -23
- package/src/isEmpty.ts +26 -23
- package/src/sliceStrEnd.js +63 -0
- package/src/sliceStrEnd.ts +60 -0
- package/src/stringToEncodings.js +56 -0
- package/src/stringToEncodings.ts +110 -0
- package/src/unicodeToEncodings.js +51 -0
- package/src/unicodeToEncodings.ts +55 -0
- package/src/arrayMutableMethods - /345/211/257/346/234/254.js" +0 -5
- package/src/comma - /345/211/257/346/234/254.js" +0 -2
- package/src/deepCloneToJSON - /345/211/257/346/234/254.js" +0 -47
- package/src/deepMergeMaps - /345/211/257/346/234/254.js" +0 -78
- package/src/escapeHTML - /345/211/257/346/234/254.js" +0 -29
- package/src/getDataType - /345/211/257/346/234/254.js" +0 -38
- package/src/isEmpty - /345/211/257/346/234/254.js" +0 -45
- package/src/mapMutableMethods - /345/211/257/346/234/254.js" +0 -5
- package/src/setMutableMethods - /345/211/257/346/234/254.js" +0 -5
- package/src/wrapMap - /345/211/257/346/234/254.js" +0 -119
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8">
|
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
6
|
+
<title>URL Builder Demo</title>
|
|
7
|
+
<style>
|
|
8
|
+
body {
|
|
9
|
+
font-family: Arial, sans-serif;
|
|
10
|
+
margin: 20px;
|
|
11
|
+
}
|
|
12
|
+
.section {
|
|
13
|
+
margin-bottom: 20px;
|
|
14
|
+
}
|
|
15
|
+
label {
|
|
16
|
+
font-weight: bold;
|
|
17
|
+
}
|
|
18
|
+
input, button {
|
|
19
|
+
padding: 5px;
|
|
20
|
+
margin: 5px 0;
|
|
21
|
+
font-size: 16px;
|
|
22
|
+
}
|
|
23
|
+
pre {
|
|
24
|
+
background-color: #f4f4f4;
|
|
25
|
+
padding: 10px;
|
|
26
|
+
border-radius: 5px;
|
|
27
|
+
border: 1px solid #ddd;
|
|
28
|
+
font-family: monospace;
|
|
29
|
+
}
|
|
30
|
+
</style>
|
|
31
|
+
</head>
|
|
32
|
+
<body>
|
|
33
|
+
<h1>URL Builder Demo</h1>
|
|
34
|
+
|
|
35
|
+
<div class="section">
|
|
36
|
+
<label for="baseUrl">Base URL:</label>
|
|
37
|
+
<input type="text" id="baseUrl" value="/api/data" placeholder="Enter Base URL">
|
|
38
|
+
</div>
|
|
39
|
+
|
|
40
|
+
<div class="section">
|
|
41
|
+
<label for="data">Data (Query Params):</label>
|
|
42
|
+
<input type="text" id="data" value="key=value&name=John" placeholder="Enter query params (key=value)">
|
|
43
|
+
</div>
|
|
44
|
+
|
|
45
|
+
<div class="section">
|
|
46
|
+
<label for="cacheBustKey">Cache Bust Key:</label>
|
|
47
|
+
<input type="text" id="cacheBustKey" value="_cache" placeholder="Enter cache-bust key">
|
|
48
|
+
</div>
|
|
49
|
+
|
|
50
|
+
<div class="section">
|
|
51
|
+
<label for="appendCacheBust">Append Cache Bust:</label>
|
|
52
|
+
<input type="checkbox" id="appendCacheBust" checked>
|
|
53
|
+
</div>
|
|
54
|
+
|
|
55
|
+
<div class="section">
|
|
56
|
+
<label for="hash">Hash Fragment:</label>
|
|
57
|
+
<input type="text" id="hash" value="#section" placeholder="Enter hash fragment (e.g. #section)">
|
|
58
|
+
</div>
|
|
59
|
+
|
|
60
|
+
<div class="section">
|
|
61
|
+
<button onclick="generateUrl()">Generate URL</button>
|
|
62
|
+
</div>
|
|
63
|
+
|
|
64
|
+
<div class="section">
|
|
65
|
+
<h3>Generated URL:</h3>
|
|
66
|
+
<pre id="resultUrl"></pre>
|
|
67
|
+
</div>
|
|
68
|
+
|
|
69
|
+
<script src="../dist/utils.umd.js"></script>
|
|
70
|
+
|
|
71
|
+
<script>
|
|
72
|
+
// The buildUrl function (as provided)
|
|
73
|
+
|
|
74
|
+
// Function to generate and display the URL
|
|
75
|
+
function generateUrl() {
|
|
76
|
+
const baseUrl = document.getElementById('baseUrl').value;
|
|
77
|
+
const data = document.getElementById('data').value;
|
|
78
|
+
const cacheBustKey = document.getElementById('cacheBustKey').value;
|
|
79
|
+
const appendCacheBust = document.getElementById('appendCacheBust').checked;
|
|
80
|
+
const hash = document.getElementById('hash').value;
|
|
81
|
+
|
|
82
|
+
// If there is data, convert it into an object or URLSearchParams
|
|
83
|
+
|
|
84
|
+
|
|
85
|
+
// Call buildUrl with the current form data
|
|
86
|
+
const url = utils.buildUrl({
|
|
87
|
+
url: baseUrl + hash, // Include the hash if present
|
|
88
|
+
data, // Data can be a string, object, or URLSearchParams
|
|
89
|
+
cacheBustKey: cacheBustKey,
|
|
90
|
+
appendCacheBust: appendCacheBust
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
// Display the result
|
|
94
|
+
document.getElementById('resultUrl').textContent = url;
|
|
95
|
+
console.log(url)
|
|
96
|
+
}
|
|
97
|
+
</script>
|
|
98
|
+
</body>
|
|
99
|
+
</html>
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8">
|
|
5
|
+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
|
6
|
+
<title>getUrlHash Function Demo</title>
|
|
7
|
+
<style>
|
|
8
|
+
body { font-family: sans-serif; line-height: 1.6; padding: 20px; max-width: 800px; margin: 0 auto; background: #f4f7f6; }
|
|
9
|
+
.container { background: white; padding: 20px; border-radius: 8px; box-shadow: 0 2px 10px rgba(0,0,0,0.1); }
|
|
10
|
+
code { background: #eee; padding: 2px 5px; border-radius: 4px; color: #d63384; }
|
|
11
|
+
table { width: 100%; border-collapse: collapse; margin-top: 20px; }
|
|
12
|
+
th, td { text-align: left; padding: 12px; border-bottom: 1px solid #ddd; }
|
|
13
|
+
th { background: #f8f9fa; }
|
|
14
|
+
.hash-tag { font-weight: bold; color: #007bff; }
|
|
15
|
+
.empty { color: #999; font-style: italic; }
|
|
16
|
+
.note { margin-top: 20px; font-size: 0.9em; color: #666; border-left: 4px solid #007bff; padding-left: 15px; }
|
|
17
|
+
</style>
|
|
18
|
+
</head>
|
|
19
|
+
<body>
|
|
20
|
+
|
|
21
|
+
<div class="container">
|
|
22
|
+
<h2>URL Hash Extractor Demo</h2>
|
|
23
|
+
<p>This demo tests the <code>getUrlHash</code> function using <code>new URL()</code> logic.</p>
|
|
24
|
+
|
|
25
|
+
<table>
|
|
26
|
+
<thead>
|
|
27
|
+
<tr>
|
|
28
|
+
<th>Test Input URL</th>
|
|
29
|
+
<th>Extracted Hash</th>
|
|
30
|
+
</tr>
|
|
31
|
+
</thead>
|
|
32
|
+
<tbody id="resultsTable">
|
|
33
|
+
</tbody>
|
|
34
|
+
</table>
|
|
35
|
+
|
|
36
|
+
<div class="note">
|
|
37
|
+
<strong>Check the Network Tab:</strong> Open your browser's Developer Tools (F12) and go to the "Network" tab. You will see that <strong>no requests</strong> are made to these URLs during parsing.
|
|
38
|
+
</div>
|
|
39
|
+
</div>
|
|
40
|
+
|
|
41
|
+
<script src="../dist/utils.umd.js" type="text/javascript" charset="utf-8"></script>
|
|
42
|
+
<script>
|
|
43
|
+
|
|
44
|
+
// Array of test cases including absolute, relative, and non-standard paths
|
|
45
|
+
const testCases = [
|
|
46
|
+
"https://example.com/page.html#section1",
|
|
47
|
+
"../../src/index.html#hello",
|
|
48
|
+
"/about#team",
|
|
49
|
+
"api/data?id=123#debug-info",
|
|
50
|
+
"https://google.com/search?q=ajax#top",
|
|
51
|
+
"#just-hash",
|
|
52
|
+
"no-hash-here.html"
|
|
53
|
+
];
|
|
54
|
+
|
|
55
|
+
const tableBody = document.getElementById('resultsTable');
|
|
56
|
+
|
|
57
|
+
testCases.forEach(testUrl => {
|
|
58
|
+
const hash = utils.getUrlHash(testUrl);
|
|
59
|
+
const row = document.createElement('tr');
|
|
60
|
+
|
|
61
|
+
row.innerHTML = `
|
|
62
|
+
<td><code>${testUrl}</code></td>
|
|
63
|
+
<td><span class="${hash ? 'hash-tag' : 'empty'}">${hash || '(empty)'}</span></td>
|
|
64
|
+
`;
|
|
65
|
+
|
|
66
|
+
tableBody.appendChild(row);
|
|
67
|
+
});
|
|
68
|
+
</script>
|
|
69
|
+
|
|
70
|
+
</body>
|
|
71
|
+
</html>
|
|
@@ -0,0 +1,117 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8" />
|
|
5
|
+
<title>Unicode Collision Tester (Hash vs Registry)</title>
|
|
6
|
+
<style>
|
|
7
|
+
body { font-family: system-ui, sans-serif; padding: 20px; }
|
|
8
|
+
input, button { padding: 6px 10px; font-size: 14px; }
|
|
9
|
+
pre { background: #f7f7f7; padding: 10px; max-height: 260px; overflow: auto; }
|
|
10
|
+
.stat { margin-top: 12px; font-weight: bold; }
|
|
11
|
+
.grid { display: grid; grid-template-columns: 1fr 1fr; gap: 20px; margin-top: 16px; }
|
|
12
|
+
h3 { margin-bottom: 6px; }
|
|
13
|
+
</style>
|
|
14
|
+
</head>
|
|
15
|
+
<body>
|
|
16
|
+
|
|
17
|
+
<h2>Unicode Collision Tester — Hash vs Registry</h2>
|
|
18
|
+
|
|
19
|
+
<label>Test Count:</label>
|
|
20
|
+
<input id="count" type="number" value="20000" min="1" step="1000" />
|
|
21
|
+
<button onclick="runTest()">Run Test</button>
|
|
22
|
+
|
|
23
|
+
<div class="grid">
|
|
24
|
+
<div>
|
|
25
|
+
<h3>Hash-only Mode (No Registry)</h3>
|
|
26
|
+
<div class="stat" id="statsHash"></div>
|
|
27
|
+
<pre id="logHash"></pre>
|
|
28
|
+
</div>
|
|
29
|
+
|
|
30
|
+
<div>
|
|
31
|
+
<h3>Registry Mode (Zero Collision)</h3>
|
|
32
|
+
<div class="stat" id="statsRegistry"></div>
|
|
33
|
+
<pre id="logRegistry"></pre>
|
|
34
|
+
</div>
|
|
35
|
+
</div>
|
|
36
|
+
|
|
37
|
+
<script src="../dist/utils.umd.js"></script>
|
|
38
|
+
|
|
39
|
+
<script>
|
|
40
|
+
|
|
41
|
+
// =======================================
|
|
42
|
+
// Collision Tester
|
|
43
|
+
// =======================================
|
|
44
|
+
|
|
45
|
+
function runTest() {
|
|
46
|
+
const count = Number(document.getElementById("count").value);
|
|
47
|
+
|
|
48
|
+
const usedHash = new Map(); // codePoint -> name
|
|
49
|
+
const collisionsHash = [];
|
|
50
|
+
|
|
51
|
+
const registry = new Map();
|
|
52
|
+
const usedRegistry = new Map();
|
|
53
|
+
const collisionsRegistry = [];
|
|
54
|
+
|
|
55
|
+
console.time("Hash Mode");
|
|
56
|
+
for (let i = 0; i < count; i++) {
|
|
57
|
+
const name = `icon-${i.toString().padStart(6, "0")}`;
|
|
58
|
+
const result = utils.stringToEncodings(name);
|
|
59
|
+
|
|
60
|
+
if (usedHash.has(result.codePoint)) {
|
|
61
|
+
collisionsHash.push({
|
|
62
|
+
name,
|
|
63
|
+
collidesWith: usedHash.get(result.codePoint),
|
|
64
|
+
unicode: result.unicode
|
|
65
|
+
});
|
|
66
|
+
} else {
|
|
67
|
+
usedHash.set(result.codePoint, name);
|
|
68
|
+
}
|
|
69
|
+
}
|
|
70
|
+
console.timeEnd("Hash Mode");
|
|
71
|
+
|
|
72
|
+
console.time("Registry Mode");
|
|
73
|
+
for (let i = 0; i < count; i++) {
|
|
74
|
+
const name = `icon-${i.toString().padStart(6, "0")}`;
|
|
75
|
+
const result = utils.stringToEncodings(name, { registryMap: registry });
|
|
76
|
+
|
|
77
|
+
if (usedRegistry.has(result.codePoint)) {
|
|
78
|
+
collisionsRegistry.push({
|
|
79
|
+
name,
|
|
80
|
+
collidesWith: usedRegistry.get(result.codePoint),
|
|
81
|
+
unicode: result.unicode
|
|
82
|
+
});
|
|
83
|
+
} else {
|
|
84
|
+
usedRegistry.set(result.codePoint, name);
|
|
85
|
+
}
|
|
86
|
+
}
|
|
87
|
+
console.timeEnd("Registry Mode");
|
|
88
|
+
|
|
89
|
+
const rateHash = (collisionsHash.length / count * 100).toFixed(4);
|
|
90
|
+
const rateRegistry = (collisionsRegistry.length / count * 100).toFixed(4);
|
|
91
|
+
|
|
92
|
+
document.getElementById("statsHash").textContent =
|
|
93
|
+
`Total: ${count} | Unique Unicode: ${usedHash.size} | Collisions: ${collisionsHash.length} | Collision Rate: ${rateHash}%`;
|
|
94
|
+
|
|
95
|
+
document.getElementById("statsRegistry").textContent =
|
|
96
|
+
`Total: ${count} | Unique Unicode: ${usedRegistry.size} | Collisions: ${collisionsRegistry.length} | Collision Rate: ${rateRegistry}%`;
|
|
97
|
+
|
|
98
|
+
document.getElementById("logHash").textContent =
|
|
99
|
+
collisionsHash.length
|
|
100
|
+
? collisionsHash.slice(0, 100).map(c =>
|
|
101
|
+
`${c.name} ↔ ${c.collidesWith} → ${c.unicode}`
|
|
102
|
+
).join("\n")
|
|
103
|
+
: "No collisions 🎉";
|
|
104
|
+
|
|
105
|
+
document.getElementById("logRegistry").textContent =
|
|
106
|
+
collisionsRegistry.length
|
|
107
|
+
? collisionsRegistry.slice(0, 20).map(c =>
|
|
108
|
+
`${c.name} ↔ ${c.collidesWith} → ${c.unicode}`
|
|
109
|
+
).join("\n")
|
|
110
|
+
: "Zero collisions ✅ (Expected)";
|
|
111
|
+
|
|
112
|
+
console.log(registry)
|
|
113
|
+
}
|
|
114
|
+
</script>
|
|
115
|
+
|
|
116
|
+
</body>
|
|
117
|
+
</html>
|
|
@@ -0,0 +1,71 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8" />
|
|
5
|
+
<title>Unicode Collision Tester (utils.stringToEncodings)</title>
|
|
6
|
+
<style>
|
|
7
|
+
body { font-family: system-ui, sans-serif; padding: 20px; }
|
|
8
|
+
input, button { padding: 6px 10px; font-size: 14px; }
|
|
9
|
+
pre { background: #f7f7f7; padding: 10px; max-height: 300px; overflow: auto; }
|
|
10
|
+
.stat { margin-top: 12px; font-weight: bold; }
|
|
11
|
+
</style>
|
|
12
|
+
</head>
|
|
13
|
+
<body>
|
|
14
|
+
|
|
15
|
+
<h2>Unicode Collision Tester (PUA Plane 15–16)</h2>
|
|
16
|
+
|
|
17
|
+
<label>Test Count:</label>
|
|
18
|
+
<input id="count" type="number" value="10000" min="1" step="1000" />
|
|
19
|
+
<button onclick="runTest()">Run Test</button>
|
|
20
|
+
|
|
21
|
+
<div class="stat" id="stats"></div>
|
|
22
|
+
<pre id="log"></pre>
|
|
23
|
+
|
|
24
|
+
<script src="../dist/utils.umd.js"></script>
|
|
25
|
+
|
|
26
|
+
<script>
|
|
27
|
+
|
|
28
|
+
// ==============================
|
|
29
|
+
// Collision Tester
|
|
30
|
+
// ==============================
|
|
31
|
+
|
|
32
|
+
function runTest() {
|
|
33
|
+
const count = Number(document.getElementById("count").value);
|
|
34
|
+
const used = new Map(); // codePoint -> name
|
|
35
|
+
const collisions = [];
|
|
36
|
+
|
|
37
|
+
console.time("Test Time");
|
|
38
|
+
|
|
39
|
+
for (let i = 0; i < count; i++) {
|
|
40
|
+
const name = `icon-${i.toString().padStart(6, "0")}`;
|
|
41
|
+
const result = utils.stringToEncodings(name);
|
|
42
|
+
|
|
43
|
+
if (used.has(result.codePoint)) {
|
|
44
|
+
collisions.push({
|
|
45
|
+
name,
|
|
46
|
+
collidesWith: used.get(result.codePoint),
|
|
47
|
+
unicode: result.unicode
|
|
48
|
+
});
|
|
49
|
+
} else {
|
|
50
|
+
used.set(result.codePoint, name);
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
console.timeEnd("Test Time");
|
|
55
|
+
|
|
56
|
+
const collisionRate = (collisions.length / count * 100).toFixed(4);
|
|
57
|
+
|
|
58
|
+
document.getElementById("stats").textContent =
|
|
59
|
+
`Total: ${count} | Unique Unicode: ${used.size} | Collisions: ${collisions.length} | Collision Rate: ${collisionRate}%`;
|
|
60
|
+
|
|
61
|
+
const log = document.getElementById("log");
|
|
62
|
+
log.textContent = collisions.length
|
|
63
|
+
? collisions.slice(0, 100).map(c =>
|
|
64
|
+
`${c.name} ↔ ${c.collidesWith} → ${c.unicode}`
|
|
65
|
+
).join("\n")
|
|
66
|
+
: "No collisions detected 🎉";
|
|
67
|
+
}
|
|
68
|
+
</script>
|
|
69
|
+
|
|
70
|
+
</body>
|
|
71
|
+
</html>
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
<head>
|
|
4
|
+
<meta charset="UTF-8" />
|
|
5
|
+
<title>utils.stringToEncodings Demo (Hash + Registry Mode)</title>
|
|
6
|
+
<style>
|
|
7
|
+
body {
|
|
8
|
+
font-family: system-ui, -apple-system, Segoe UI, Roboto, Ubuntu, Cantarell;
|
|
9
|
+
background: #0f172a;
|
|
10
|
+
color: #e5e7eb;
|
|
11
|
+
padding: 24px;
|
|
12
|
+
}
|
|
13
|
+
input, textarea {
|
|
14
|
+
width: 100%;
|
|
15
|
+
padding: 10px;
|
|
16
|
+
margin-top: 6px;
|
|
17
|
+
border-radius: 8px;
|
|
18
|
+
border: 1px solid #334155;
|
|
19
|
+
background: #020617;
|
|
20
|
+
color: white;
|
|
21
|
+
}
|
|
22
|
+
button {
|
|
23
|
+
padding: 10px 16px;
|
|
24
|
+
border-radius: 8px;
|
|
25
|
+
border: none;
|
|
26
|
+
background: #38bdf8;
|
|
27
|
+
color: black;
|
|
28
|
+
font-weight: 600;
|
|
29
|
+
cursor: pointer;
|
|
30
|
+
margin-top: 12px;
|
|
31
|
+
}
|
|
32
|
+
table {
|
|
33
|
+
width: 100%;
|
|
34
|
+
border-collapse: collapse;
|
|
35
|
+
margin-top: 16px;
|
|
36
|
+
}
|
|
37
|
+
th, td {
|
|
38
|
+
text-align: left;
|
|
39
|
+
padding: 10px;
|
|
40
|
+
border-bottom: 1px solid #334155;
|
|
41
|
+
font-family: monospace;
|
|
42
|
+
}
|
|
43
|
+
.badge {
|
|
44
|
+
padding: 2px 8px;
|
|
45
|
+
border-radius: 6px;
|
|
46
|
+
font-size: 12px;
|
|
47
|
+
}
|
|
48
|
+
.ok { background: #22c55e; color: black; }
|
|
49
|
+
.warn { background: #f59e0b; color: black; }
|
|
50
|
+
</style>
|
|
51
|
+
</head>
|
|
52
|
+
<body>
|
|
53
|
+
|
|
54
|
+
<h2>utils.stringToEncodings Demo</h2>
|
|
55
|
+
|
|
56
|
+
<label>Input String</label>
|
|
57
|
+
<input id="input" value="arrowUpSolid" />
|
|
58
|
+
|
|
59
|
+
<label style="margin-top:12px;">
|
|
60
|
+
<input type="checkbox" id="useRegistry" checked />
|
|
61
|
+
Enable Registry Mode (Zero Collision)
|
|
62
|
+
</label>
|
|
63
|
+
|
|
64
|
+
<label style="margin-top:12px;">Batch Input (one per line)</label>
|
|
65
|
+
<textarea id="batch" rows="6">arrowUpSolid
|
|
66
|
+
arrowDownSolid
|
|
67
|
+
homeOutline
|
|
68
|
+
settingsGear
|
|
69
|
+
userCircle</textarea>
|
|
70
|
+
|
|
71
|
+
<button onclick="run()">Generate</button>
|
|
72
|
+
|
|
73
|
+
<p id="stats"></p>
|
|
74
|
+
|
|
75
|
+
<table id="output">
|
|
76
|
+
<thead>
|
|
77
|
+
<tr>
|
|
78
|
+
<th>Name</th>
|
|
79
|
+
<th>Unicode</th>
|
|
80
|
+
<th>Hex</th>
|
|
81
|
+
<th>HTML Dec</th>
|
|
82
|
+
<th>HTML Hex</th>
|
|
83
|
+
<th>Hash</th>
|
|
84
|
+
<th>Collision</th>
|
|
85
|
+
</tr>
|
|
86
|
+
</thead>
|
|
87
|
+
<tbody></tbody>
|
|
88
|
+
</table>
|
|
89
|
+
|
|
90
|
+
<script src="../dist/utils.umd.js"></script>
|
|
91
|
+
|
|
92
|
+
<script>
|
|
93
|
+
// ------------------------------
|
|
94
|
+
// Registry (persistent in session)
|
|
95
|
+
// ------------------------------
|
|
96
|
+
const registry = new Map();
|
|
97
|
+
|
|
98
|
+
// ------------------------------
|
|
99
|
+
// UI Handler
|
|
100
|
+
// ------------------------------
|
|
101
|
+
function run() {
|
|
102
|
+
const input = document.getElementById("input").value.trim();
|
|
103
|
+
const batchLines = document.getElementById("batch").value.split("\n").map(s => s.trim()).filter(Boolean);
|
|
104
|
+
const useRegistry = document.getElementById("useRegistry").checked;
|
|
105
|
+
|
|
106
|
+
const list = [input, ...batchLines].filter(Boolean);
|
|
107
|
+
|
|
108
|
+
const tbody = document.querySelector("#output tbody");
|
|
109
|
+
tbody.innerHTML = "";
|
|
110
|
+
|
|
111
|
+
list.forEach(name => {
|
|
112
|
+
const result = utils.stringToEncodings(name, useRegistry ? { registryMap: registry } : {});
|
|
113
|
+
const tr = document.createElement("tr");
|
|
114
|
+
|
|
115
|
+
tr.innerHTML = `
|
|
116
|
+
<td>${name}</td>
|
|
117
|
+
<td>${result.unicode}</td>
|
|
118
|
+
<td>${result.hex}</td>
|
|
119
|
+
<td><code>${utils.escapeHTML(result.htmlDec)}</code></td>
|
|
120
|
+
<td><code>${utils.escapeHTML(result.htmlHex)}</code></td>
|
|
121
|
+
<td title="${result.hash}">${result.hash.slice(0,20)}...</td>
|
|
122
|
+
<td>
|
|
123
|
+
<span class="badge ${result.collision ? "warn" : "ok"}">
|
|
124
|
+
${result.collision ? "Collision" : "OK"}
|
|
125
|
+
</span>
|
|
126
|
+
</td>
|
|
127
|
+
`;
|
|
128
|
+
|
|
129
|
+
tbody.appendChild(tr);
|
|
130
|
+
});
|
|
131
|
+
|
|
132
|
+
document.getElementById("stats").textContent =
|
|
133
|
+
`Registry Size: ${registry.size} entries`;
|
|
134
|
+
}
|
|
135
|
+
</script>
|
|
136
|
+
|
|
137
|
+
</body>
|
|
138
|
+
</html>
|
|
@@ -0,0 +1,195 @@
|
|
|
1
|
+
<!DOCTYPE html>
|
|
2
|
+
<html lang="en">
|
|
3
|
+
|
|
4
|
+
<head>
|
|
5
|
+
<meta charset="UTF-8" />
|
|
6
|
+
<title>Unicode Encoding Parser Demo</title>
|
|
7
|
+
<style>
|
|
8
|
+
body {
|
|
9
|
+
font-family: system-ui, -apple-system, Segoe UI, Roboto, sans-serif;
|
|
10
|
+
background: #0f172a;
|
|
11
|
+
color: #e5e7eb;
|
|
12
|
+
padding: 24px;
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
h1 {
|
|
16
|
+
font-size: 20px;
|
|
17
|
+
margin-bottom: 12px;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
.examples {
|
|
21
|
+
display: flex;
|
|
22
|
+
flex-wrap: wrap;
|
|
23
|
+
gap: 8px;
|
|
24
|
+
margin-bottom: 12px;
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
button {
|
|
28
|
+
background: #020617;
|
|
29
|
+
border: 1px solid #334155;
|
|
30
|
+
color: #e5e7eb;
|
|
31
|
+
padding: 6px 10px;
|
|
32
|
+
border-radius: 8px;
|
|
33
|
+
cursor: pointer;
|
|
34
|
+
font-size: 14px;
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
button:hover {
|
|
38
|
+
border-color: #38bdf8;
|
|
39
|
+
color: #38bdf8;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
input {
|
|
43
|
+
width: 100%;
|
|
44
|
+
padding: 10px;
|
|
45
|
+
font-size: 16px;
|
|
46
|
+
border-radius: 8px;
|
|
47
|
+
border: 1px solid #334155;
|
|
48
|
+
background: #020617;
|
|
49
|
+
color: #fff;
|
|
50
|
+
outline: none;
|
|
51
|
+
margin-bottom: 10px;
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
input:focus {
|
|
55
|
+
border-color: #38bdf8;
|
|
56
|
+
}
|
|
57
|
+
|
|
58
|
+
.hint {
|
|
59
|
+
font-size: 13px;
|
|
60
|
+
color: #94a3b8;
|
|
61
|
+
margin-bottom: 10px;
|
|
62
|
+
}
|
|
63
|
+
|
|
64
|
+
table {
|
|
65
|
+
width: 100%;
|
|
66
|
+
margin-top: 12px;
|
|
67
|
+
border-collapse: collapse;
|
|
68
|
+
background: #020617;
|
|
69
|
+
border-radius: 12px;
|
|
70
|
+
overflow: hidden;
|
|
71
|
+
}
|
|
72
|
+
|
|
73
|
+
th,
|
|
74
|
+
td {
|
|
75
|
+
padding: 10px 12px;
|
|
76
|
+
border-bottom: 1px solid #1e293b;
|
|
77
|
+
text-align: left;
|
|
78
|
+
}
|
|
79
|
+
|
|
80
|
+
th {
|
|
81
|
+
width: 200px;
|
|
82
|
+
color: #93c5fd;
|
|
83
|
+
}
|
|
84
|
+
|
|
85
|
+
code {
|
|
86
|
+
background: #020617;
|
|
87
|
+
padding: 2px 6px;
|
|
88
|
+
border-radius: 6px;
|
|
89
|
+
color: #fbbf24;
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
.preview {
|
|
93
|
+
font-size: 48px;
|
|
94
|
+
margin-top: 12px;
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
.error {
|
|
98
|
+
color: #f87171;
|
|
99
|
+
margin-top: 8px;
|
|
100
|
+
}
|
|
101
|
+
</style>
|
|
102
|
+
</head>
|
|
103
|
+
|
|
104
|
+
<body>
|
|
105
|
+
|
|
106
|
+
<h1>Unicode → Encoding Parser Demo</h1>
|
|
107
|
+
|
|
108
|
+
<div class="examples">
|
|
109
|
+
<button onclick="setExample('U+1F600')">😀 Emoji (U+1F600)</button>
|
|
110
|
+
<button onclick="setExample('U+E001')">PUA Example (U+E001)</button>
|
|
111
|
+
<button onclick="setExample('F123')">Hex Example (F123)</button>
|
|
112
|
+
<button onclick="setExample('61731')">Decimal Example (61731)</button>
|
|
113
|
+
<button onclick="setExample('0x1F680')">Rocket (0x1F680)</button>
|
|
114
|
+
<button onclick="setExample('❤️')">Heart Emoji</button>
|
|
115
|
+
</div>
|
|
116
|
+
|
|
117
|
+
<input id="input" placeholder="Enter Unicode: U+F123 | F123 | 0xF123 | 61731 | 😀" />
|
|
118
|
+
|
|
119
|
+
<div class="hint">
|
|
120
|
+
Supported formats: <code>U+F123</code>, <code>F123</code>, <code>0xF123</code>, <code>61731</code>, <code>😀</code>
|
|
121
|
+
</div>
|
|
122
|
+
|
|
123
|
+
<div id="error" class="error"></div>
|
|
124
|
+
|
|
125
|
+
<table id="output" style="display:none;">
|
|
126
|
+
<tr>
|
|
127
|
+
<th>Unicode</th>
|
|
128
|
+
<td><code id="unicode"></code></td>
|
|
129
|
+
</tr>
|
|
130
|
+
<tr>
|
|
131
|
+
<th>Hex</th>
|
|
132
|
+
<td><code id="hex"></code></td>
|
|
133
|
+
</tr>
|
|
134
|
+
<tr>
|
|
135
|
+
<th>Code Point (Dec)</th>
|
|
136
|
+
<td><code id="codePoint"></code></td>
|
|
137
|
+
</tr>
|
|
138
|
+
<tr>
|
|
139
|
+
<th>HTML Decimal</th>
|
|
140
|
+
<td><code id="htmlDec"></code></td>
|
|
141
|
+
</tr>
|
|
142
|
+
<tr>
|
|
143
|
+
<th>HTML Hex</th>
|
|
144
|
+
<td><code id="htmlHex"></code></td>
|
|
145
|
+
</tr>
|
|
146
|
+
</table>
|
|
147
|
+
|
|
148
|
+
<div class="preview" id="preview"></div>
|
|
149
|
+
<script src="../dist/utils.umd.js"></script>
|
|
150
|
+
|
|
151
|
+
<script>
|
|
152
|
+
function setExample(value) {
|
|
153
|
+
const input = document.getElementById("input");
|
|
154
|
+
input.value = value;
|
|
155
|
+
input.dispatchEvent(new Event("input"));
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
const input = document.getElementById("input");
|
|
159
|
+
const error = document.getElementById("error");
|
|
160
|
+
const output = document.getElementById("output");
|
|
161
|
+
|
|
162
|
+
input.addEventListener("input", () => {
|
|
163
|
+
const value = input.value.trim();
|
|
164
|
+
|
|
165
|
+
if (!value) {
|
|
166
|
+
output.style.display = "none";
|
|
167
|
+
error.textContent = "";
|
|
168
|
+
document.getElementById("preview").textContent = "";
|
|
169
|
+
return;
|
|
170
|
+
}
|
|
171
|
+
|
|
172
|
+
try {
|
|
173
|
+
const result = utils.unicodeToEncodings(value);
|
|
174
|
+
|
|
175
|
+
document.getElementById("unicode").textContent = result.unicode;
|
|
176
|
+
document.getElementById("hex").textContent = result.hex;
|
|
177
|
+
document.getElementById("codePoint").textContent = result.codePoint;
|
|
178
|
+
document.getElementById("htmlDec").textContent = result.htmlDec;
|
|
179
|
+
document.getElementById("htmlHex").textContent = result.htmlHex;
|
|
180
|
+
document.getElementById("preview").textContent = result.char;
|
|
181
|
+
|
|
182
|
+
output.style.display = "table";
|
|
183
|
+
error.textContent = "";
|
|
184
|
+
}
|
|
185
|
+
catch (e) {
|
|
186
|
+
output.style.display = "none";
|
|
187
|
+
document.getElementById("preview").textContent = "";
|
|
188
|
+
error.textContent = e.message;
|
|
189
|
+
}
|
|
190
|
+
});
|
|
191
|
+
</script>
|
|
192
|
+
|
|
193
|
+
</body>
|
|
194
|
+
|
|
195
|
+
</html>
|