diff --git a/client/src/components/EntryCard.tsx b/client/src/components/EntryCard.tsx
index 0ae793c..47c27d1 100644
--- a/client/src/components/EntryCard.tsx
+++ b/client/src/components/EntryCard.tsx
@@ -1,38 +1,9 @@
import { useState } from 'react';
import { Entry } from '../hooks/useJudging';
+import { PlayIcon, VideoIcon, CodeIcon } from './Icons';
import MetricChip from './MetricChip';
import './EntryCard.css';
-function PlayIcon() {
- return (
-
- );
-}
-
-function VideoIcon() {
- return (
-
- );
-}
-
-function CodeIcon() {
- return (
-
- );
-}
-
function renderBold(text: string) {
const parts = text.split(/\*\*(.+?)\*\*/g);
return parts.map((part, i) => (i % 2 === 1 ? {part} : part));
diff --git a/client/src/components/Icons.tsx b/client/src/components/Icons.tsx
new file mode 100644
index 0000000..84593b2
--- /dev/null
+++ b/client/src/components/Icons.tsx
@@ -0,0 +1,29 @@
+export function PlayIcon() {
+ return (
+
+ );
+}
+
+export function VideoIcon() {
+ return (
+
+ );
+}
+
+export function CodeIcon() {
+ return (
+
+ );
+}
diff --git a/client/src/pages/Results.css b/client/src/pages/Results.css
index 60903d7..379ff35 100644
--- a/client/src/pages/Results.css
+++ b/client/src/pages/Results.css
@@ -274,6 +274,50 @@
transform: translateY(-1px);
}
+.results-action-link {
+ display: inline-flex;
+ flex-direction: column;
+ align-items: flex-start;
+ justify-content: center;
+ gap: 2px;
+ font-size: 13px;
+ font-weight: 600;
+ letter-spacing: 0.04em;
+ text-decoration: none;
+ padding: 8px 12px;
+ align-self: stretch;
+ border-radius: 6px;
+ transition: all 0.2s ease;
+}
+
+.results-video-link {
+ color: #c084fc;
+ background: #c084fc12;
+ border: 1px solid #c084fc30;
+}
+
+.results-video-link:hover {
+ color: #d8b4fe;
+ background: #c084fc20;
+ border-color: #c084fc60;
+ box-shadow: 0 0 12px #c084fc25;
+ transform: translateY(-1px);
+}
+
+.results-code-link {
+ color: #60a5fa;
+ background: #60a5fa12;
+ border: 1px solid #60a5fa30;
+}
+
+.results-code-link:hover {
+ color: #93c5fd;
+ background: #60a5fa20;
+ border-color: #60a5fa60;
+ box-shadow: 0 0 12px #60a5fa25;
+ transform: translateY(-1px);
+}
+
/* ─── Nav ─── */
.results-nav {
diff --git a/client/src/pages/Results.tsx b/client/src/pages/Results.tsx
index 09b5a1c..edbcef4 100644
--- a/client/src/pages/Results.tsx
+++ b/client/src/pages/Results.tsx
@@ -2,22 +2,10 @@ import { useEffect, useState } from 'react';
import { useParams, Link, Navigate } from 'react-router-dom';
import { formatJamTitle } from '../utils/jam';
import { Entry } from '../hooks/useJudging';
+import { PlayIcon, VideoIcon, CodeIcon } from '../components/Icons';
import MetricChip from '../components/MetricChip';
import './Results.css';
-
-function PlayIcon() {
- return (
-
- );
-}
-
interface RankedEntry {
entry: Entry;
weight: number;
@@ -121,6 +109,18 @@ export default function Results() {
Play Now
)}
+ {r.entry.video_url && (
+
+
+ Watch Demo
+
+ )}
+ {r.entry.repo_url && (
+
+
+ View Code
+
+ )}