feat: created example url for tracking links page

This commit is contained in:
Leyla Becker 2026-02-18 12:00:43 -06:00
parent 672a4ee7fb
commit d4c62539c5

View file

@ -2,7 +2,209 @@
parts of a url:
<!-- insert custom html that shows the parts of a url but color coded with a legend at the bottom, when a component is hovered it should highlight its corresponding legend item, use aria by labels to link together legend items and sections with their url part -->
<style>
.url-container {
margin: 1em 0;
}
.url-example {
font-family: monospace;
font-size: 1.2em;
padding: 1em;
background: var(--code-background, #f5f5f5);
border: 1px solid var(--border-color, #ddd);
border-radius: 8px;
margin-bottom: 1em;
overflow-x: auto;
white-space: nowrap;
}
.url-example span,
.url-legend-item {
transition: opacity 0.2s;
cursor: pointer;
}
.url-legend {
display: flex;
flex-direction: column;
gap: 0.75em;
padding: 1em;
background: var(--code-background, #f5f5f5);
border: 1px solid var(--border-color, #ddd);
border-radius: 8px;
}
.url-legend-item {
display: flex;
align-items: flex-start;
gap: 0.5em;
}
.url-legend-item .url-legend-label {
font-weight: 600;
min-width: 8em;
}
.url-legend-item .url-legend-desc {
color: #666;
font-size: 0.9em;
}
.url-legend-color {
width: 1em;
height: 1em;
border-radius: 3px;
flex-shrink: 0;
margin-top: 0.2em;
}
.url-part-protocol { color: #db2777; }
.url-legend-protocol { background: #db2777; }
.url-part-subdomain { color: #0891b2; }
.url-legend-subdomain { background: #0891b2; }
.url-part-domain { color: #2563eb; }
.url-legend-domain { background: #2563eb; }
.url-part-tld { color: #16a34a; }
.url-legend-tld { background: #16a34a; }
.url-part-port { color: #ca8a04; }
.url-legend-port { background: #ca8a04; }
.url-part-path { color: #ea580c; }
.url-legend-path { background: #ea580c; }
.url-part-query { color: #dc2626; }
.url-legend-query { background: #dc2626; }
.url-part-fragment { color: #9333ea; }
.url-legend-fragment { background: #9333ea; }
/* Cross-highlighting using :has() - no JavaScript needed */
.url-container:has([data-part]:hover) [data-part] { opacity: 0.4; }
/* Keep hovered element visible but without glow */
.url-container [data-part]:hover { opacity: 1 !important; }
/* Highlight style with neutral glow */
.url-highlight {
opacity: 1 !important;
background: rgba(0, 0, 0, 0.08);
box-shadow: 0 0 8px 4px rgba(0, 0, 0, 0.12);
border-radius: 4px;
}
/* When hovering URL parts, highlight matching legend items */
.url-container:has(.url-example [data-part="protocol"]:hover) .url-legend [data-part="protocol"],
.url-container:has(.url-example [data-part="subdomain"]:hover) .url-legend [data-part="subdomain"],
.url-container:has(.url-example [data-part="domain"]:hover) .url-legend [data-part="domain"],
.url-container:has(.url-example [data-part="tld"]:hover) .url-legend [data-part="tld"],
.url-container:has(.url-example [data-part="port"]:hover) .url-legend [data-part="port"],
.url-container:has(.url-example [data-part="path"]:hover) .url-legend [data-part="path"],
.url-container:has(.url-example [data-part="query"]:hover) .url-legend [data-part="query"],
.url-container:has(.url-example [data-part="fragment"]:hover) .url-legend [data-part="fragment"] {
opacity: 1 !important;
padding: 0.5em 0.75em;
margin: -0.5em -0.75em;
border-radius: 0.5em;
box-shadow:
inset 0 0 0.5em 0.25em rgba(0, 0, 0, 0.06),
0 0 0.75rem 0.5rem rgba(0, 0, 0, 0.06),
0 0 1.25rem 1rem rgba(0, 0, 0, 0.04),
0 0 2rem 1.5rem rgba(0, 0, 0, 0.02);
}
/* When hovering legend items, highlight matching URL parts */
.url-container:has(.url-legend [data-part="protocol"]:hover) .url-example [data-part="protocol"],
.url-container:has(.url-legend [data-part="subdomain"]:hover) .url-example [data-part="subdomain"],
.url-container:has(.url-legend [data-part="domain"]:hover) .url-example [data-part="domain"],
.url-container:has(.url-legend [data-part="tld"]:hover) .url-example [data-part="tld"],
.url-container:has(.url-legend [data-part="port"]:hover) .url-example [data-part="port"],
.url-container:has(.url-legend [data-part="path"]:hover) .url-example [data-part="path"],
.url-container:has(.url-legend [data-part="query"]:hover) .url-example [data-part="query"],
.url-container:has(.url-legend [data-part="fragment"]:hover) .url-example [data-part="fragment"] {
opacity: 1 !important;
border-radius: 0.25em;
box-shadow:
inset 0 0 0.5em 0.25em rgba(0, 0, 0, 0.06),
0 0 0.75rem 0.5rem rgba(0, 0, 0, 0.06),
0 0 1.25rem 1rem rgba(0, 0, 0, 0.04),
0 0 2rem 1.5rem rgba(0, 0, 0, 0.02);
}
</style>
<div class="url-container">
<div class="url-example" role="figure" aria-labelledby="url-example-caption">
<span class="url-part-protocol" aria-describedby="legend-protocol" data-part="protocol">https://</span><span class="url-part-subdomain" aria-describedby="legend-subdomain" data-part="subdomain">www.</span><span class="url-part-domain" aria-describedby="legend-domain" data-part="domain">example</span><span class="url-part-tld" aria-describedby="legend-tld" data-part="tld">.com</span><span class="url-part-port" aria-describedby="legend-port" data-part="port">:443</span><span class="url-part-path" aria-describedby="legend-path" data-part="path">/products/shoes</span><span class="url-part-query" aria-describedby="legend-query" data-part="query">?utm_source=facebook&utm_campaign=summer_sale&fbclid=abc123</span><span class="url-part-fragment" aria-describedby="legend-fragment" data-part="fragment">#reviews</span>
</div>
<div class="url-legend" role="list" aria-label="URL component legend">
<div class="url-legend-item" role="listitem" id="legend-protocol" data-part="protocol">
<span class="url-legend-color url-legend-protocol" aria-hidden="true"></span>
<span class="url-legend-label">Protocol</span>
<span class="url-legend-desc">How to communicate with the server (https is encrypted, http is not)</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-subdomain" data-part="subdomain">
<span class="url-legend-color url-legend-subdomain" aria-hidden="true"></span>
<span class="url-legend-label">Subdomain</span>
<span class="url-legend-desc">A subdivision of the main domain, often used for different services</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-domain" data-part="domain">
<span class="url-legend-color url-legend-domain" aria-hidden="true"></span>
<span class="url-legend-label">Domain</span>
<span class="url-legend-desc">The human-readable name that identifies the website</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-tld" data-part="tld">
<span class="url-legend-color url-legend-tld" aria-hidden="true"></span>
<span class="url-legend-label">TLD</span>
<span class="url-legend-desc">Top-Level Domain, the suffix like .com, .org, or .net</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-port" data-part="port">
<span class="url-legend-color url-legend-port" aria-hidden="true"></span>
<span class="url-legend-label">Port</span>
<span class="url-legend-desc">Network port number (443 is default for HTTPS, 80 for HTTP)</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-path" data-part="path">
<span class="url-legend-color url-legend-path" aria-hidden="true"></span>
<span class="url-legend-label">Path</span>
<span class="url-legend-desc">The specific page or resource location on the server</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-query" data-part="query">
<span class="url-legend-color url-legend-query" aria-hidden="true"></span>
<span class="url-legend-label">Query Params</span>
<span class="url-legend-desc">Key-value pairs that pass data to the page  often used for tracking</span>
</div>
<div class="url-legend-item" role="listitem" id="legend-fragment" data-part="fragment">
<span class="url-legend-color url-legend-fragment" aria-hidden="true"></span>
<span class="url-legend-label">Fragment</span>
<span class="url-legend-desc">Links to a specific section within the page (not sent to server)</span>
</div>
</div>
</div>
<script>
(function() {
const urlExample = document.querySelector('.url-example');
const legendItems = document.querySelectorAll('.url-legend-item[data-part]');
legendItems.forEach(item => {
item.addEventListener('mouseenter', () => {
const part = item.dataset.part;
const urlPart = document.querySelector(`.url-example [data-part="${part}"]`);
if (urlPart && urlExample) {
const containerRect = urlExample.getBoundingClientRect();
const partRect = urlPart.getBoundingClientRect();
const partCenter = partRect.left - containerRect.left + urlExample.scrollLeft + (partRect.width / 2);
const scrollTarget = partCenter - (containerRect.width / 2);
urlExample.scrollTo({ left: scrollTarget, behavior: 'smooth' });
}
});
});
})();
</script>
explain what each part does