diff --git a/public/css/styles.css b/public/css/styles.css
index 69e82e79..22aa2915 100644
--- a/public/css/styles.css
+++ b/public/css/styles.css
@@ -21,9 +21,13 @@ body {
a {
text-decoration: none;
- color: var(--link)
+ color: var(--link);
+}
+a:not([href]), a[href=""] {
+ /* link is missing href */
+ text-decoration: wavy underline;
+ color: #f00;
}
-
a:hover {
text-decoration: underline;
}
@@ -49,4 +53,4 @@ main {
.cm-editor {
max-height: 100vh;
-}
\ No newline at end of file
+}
diff --git a/sample/bundleCulling/meta.ts b/sample/bundleCulling/meta.ts
index 1b40f8cf..a3324774 100644
--- a/sample/bundleCulling/meta.ts
+++ b/sample/bundleCulling/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Bundle Culling',
- description: `A demonstration of using frustum culling with render bundles through indirect instanced draw calls.
-
-Source at
-`,
+ description: `A demonstration of using frustum culling with render bundles through indirect instanced draw calls.`,
filename: __DIRNAME__,
- url: 'https://toji.github.io/webgpu-bundle-culling/',
+ external: {
+ url: 'https://toji.github.io/webgpu-bundle-culling/',
+ sourceURL: 'https://github.com/toji/webgpu-bundle-culling',
+ },
sources: [],
};
diff --git a/sample/clusteredShading/meta.ts b/sample/clusteredShading/meta.ts
index d2cf8830..9a3adbe6 100644
--- a/sample/clusteredShading/meta.ts
+++ b/sample/clusteredShading/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Clustered Shading',
- description: `Shows a simple clustered forward shading renderer.
-
-Source at
-`,
+ description: `Shows a simple clustered forward shading renderer.`,
filename: __DIRNAME__,
- url: 'https://toji.github.io/webgpu-clustered-shading/',
+ external: {
+ url: 'https://toji.github.io/webgpu-clustered-shading/',
+ sourceURL: 'https://github.com/toji/webgpu-clustered-shading',
+ },
sources: [],
};
diff --git a/sample/marchingCubes/meta.ts b/sample/marchingCubes/meta.ts
index 9ef87886..25319982 100644
--- a/sample/marchingCubes/meta.ts
+++ b/sample/marchingCubes/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Marching Cubes',
- description: `This example demonstrates how to dynamically generate procedural meshes using a signed distance field and a multi-pass marching cubes algorithm on the GPU.
-
-Source at
-`,
+ description: `This example demonstrates how to dynamically generate procedural meshes using a signed distance field and a multi-pass marching cubes algorithm on the GPU.`,
filename: __DIRNAME__,
- url: 'https://tcoppex.github.io/webgpu-marchingcubes/',
+ external: {
+ url: 'https://tcoppex.github.io/webgpu-marchingcubes/',
+ sourceURL: 'https://github.com/tcoppex/webgpu-marchingcubes',
+ },
sources: [],
};
diff --git a/sample/metaballs/meta.ts b/sample/metaballs/meta.ts
index e0b01b20..2b12c8ea 100644
--- a/sample/metaballs/meta.ts
+++ b/sample/metaballs/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Metaballs',
- description: `This example shows an implementation of metaballs with WebGPU.
-
-Source at https://github.com/toji/webgpu-metaballs/
-`,
+ description: `This example shows an implementation of metaballs with WebGPU.`,
filename: __DIRNAME__,
- url: 'https://toji.github.io/webgpu-metaballs/',
+ external: {
+ url: 'https://toji.github.io/webgpu-metaballs/',
+ sourceURL: 'https://github.com/toji/webgpu-metaballs',
+ },
sources: [],
};
diff --git a/sample/pristineGrid/meta.ts b/sample/pristineGrid/meta.ts
index c4014fb9..8dce8e62 100644
--- a/sample/pristineGrid/meta.ts
+++ b/sample/pristineGrid/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Pristine Grid',
- description: `A simple WebGPU implementation of the "Pristine Grid" technique described in this wonderful little blog post:
-
-Source at
-`,
+ description: `A simple WebGPU implementation of the "Pristine Grid" technique described in this wonderful little blog post: `,
filename: __DIRNAME__,
- url: 'https://toji.github.io/pristine-grid-webgpu/',
+ external: {
+ url: 'https://toji.github.io/pristine-grid-webgpu/',
+ sourceURL: 'https://github.com/toji/pristine-grid-webgpu',
+ },
sources: [],
};
diff --git a/sample/spookyball/meta.ts b/sample/spookyball/meta.ts
index c238830b..587bc2bb 100644
--- a/sample/spookyball/meta.ts
+++ b/sample/spookyball/meta.ts
@@ -1,10 +1,10 @@
export default {
name: 'Spookyball',
- description: `This example shows a simple game made with WebGPU.
-
-Source at
-`,
+ description: `This example shows a simple game made with WebGPU.`,
filename: __DIRNAME__,
- url: 'https://spookyball.com',
+ external: {
+ url: 'https://spookyball.com',
+ sourceURL: 'https://github.com/toji/spookyball',
+ },
sources: [],
};
diff --git a/src/main.ts b/src/main.ts
index fe8deea1..1043eb65 100644
--- a/src/main.ts
+++ b/src/main.ts
@@ -27,6 +27,7 @@ function getElem(
const sampleListElem = getElem('#samplelist');
const sampleElem = getElem('#sample');
const githubElem = getElem('#src') as HTMLAnchorElement;
+const standaloneElem = getElem('#standalone') as HTMLAnchorElement;
const introElem = getElem('#intro');
const codeTabsElem = getElem('#codeTabs');
const sourcesElem = getElem('#sources');
@@ -183,7 +184,7 @@ function setSampleIFrame(
descriptionElem.innerHTML = '';
currentSampleInfo = sampleInfo;
- const { name, description, filename, url, sources } = sampleInfo || {
+ const { name, description, filename, external, sources } = sampleInfo || {
name: '',
description: '',
filename: '',
@@ -197,17 +198,18 @@ function setSampleIFrame(
// Replace the iframe because changing src adds to the user's history.
sampleContainerElem.innerHTML = '';
if (filename) {
- const src = url || `${filename}${search}`;
+ const src = external ? external.url : `${filename}${search}`;
sampleContainerElem.appendChild(el('iframe', { src }));
sampleContainerElem.style.height = sources.length > 0 ? '600px' : '100%';
- if (url) {
- // If it's remote example, hide the github link and assume it's in the description.
- githubElem.style.display = 'none';
+ if (external) {
+ // For remote samples, get the source URL from the metadata.
+ githubElem.href = external.sourceURL;
+ standaloneElem.href = external.url;
} else {
- // It's a local sample so show the github link.
- githubElem.style.display = '';
+ // For local samples, generate a link to the source in this repo.
githubElem.href = `https://github.com/webgpu/webgpu-samples/tree/main/${filename}`;
+ standaloneElem.href = filename;
}
// hide intro and show sample
@@ -294,7 +296,9 @@ for (const { title, description, samples } of pageCategories) {
...Object.entries(samples).map(([key, sampleInfo]) =>
el('li', {}, [
el('a', {
- href: sampleInfo.filename,
+ href: sampleInfo.external
+ ? sampleInfo.external.url
+ : sampleInfo.filename,
...(!sampleInfo.openInNewTab && {
onClick: (e: PointerEvent) => {
setSampleIFrameURL(e, sampleInfo);
diff --git a/src/samples.ts b/src/samples.ts
index 3c5d390c..8f2c400d 100644
--- a/src/samples.ts
+++ b/src/samples.ts
@@ -52,7 +52,7 @@ export type SampleInfo = {
description: string;
openInNewTab?: boolean;
filename: string; // used if sample is local
- url?: string; // used if sample is remote
+ external?: { url: string; sourceURL: string }; // used if sample is remote
sources: SourceInfo[];
};