UCPCOGAI/promptchallenge
0
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, viewport-fit=cover" />6 <meta name="color-scheme" content="light" />7 <title>UCPCOG Prompt Proficiency Challenge</title>8 <style>9 :root{10 --navy:#0B1F3A;11 --blue:#1F4E79;12 --green:#4F7D5A;13 --light:#F4F6F8;14 --border:#D6DEE6;15 --gold:#B7791F;16 --red:#B91C1C;17 --success:#15803D;18 --white:#FFFFFF;19 --text:#182230;20 --muted:#5D6B7C;21 --shadow:0 12px 32px rgba(11,31,58,.10);22 --radius:16px;23 --max:1180px;24 }25 26 *{box-sizing:border-box}27 [hidden]{display:none!important}28 html{scroll-behavior:smooth}29 body{30 margin:0;31 font-family:system-ui,-apple-system,BlinkMacSystemFont,"Segoe UI",Roboto,Arial,sans-serif;32 color:var(--text);33 background:linear-gradient(180deg,#eef3f8 0,#f8fafc 280px,#eef3f8 100%);34 min-height:100vh;35 }36 button,input,select,textarea{font:inherit}37 button{cursor:pointer}38 button:focus-visible,input:focus-visible,.option:focus-visible{39 outline:3px solid rgba(31,78,121,.35);40 outline-offset:2px;41 }42 43 .topbar{44 background:linear-gradient(135deg,var(--navy),#0f315d);45 color:white;46 padding:18px 20px;47 box-shadow:0 4px 18px rgba(11,31,58,.22);48 }49 .topbar-inner{50 max-width:var(--max);51 margin:auto;52 display:flex;53 align-items:center;54 gap:14px;55 justify-content:space-between;56 }57 .brand{display:flex;align-items:center;gap:14px;min-width:0}58 .brand-mark{59 width:48px;height:48px;border:2px solid #9dd8c0;border-radius:14px;60 display:grid;place-items:center;font-weight:800;color:#9dd8c0;flex:none;61 }62 .brand h1{font-size:clamp(1.2rem,2.7vw,1.75rem);margin:0;line-height:1.1}63 .brand p{margin:4px 0 0;color:#cfe0ef;font-size:.94rem}64 .privacy-chip{65 font-size:.82rem;color:#d7e6f2;border:1px solid rgba(255,255,255,.28);66 border-radius:999px;padding:8px 12px;white-space:nowrap;67 }68 69 .app{max-width:var(--max);margin:26px auto;padding:0 18px 42px}70 .panel{71 background:var(--white);border:1px solid var(--border);border-radius:var(--radius);72 box-shadow:var(--shadow);73 }74 .screen{display:none}75 .screen.active{display:block}76 .hero{padding:clamp(28px,5vw,56px);overflow:hidden;position:relative}77 .hero::after{78 content:"";position:absolute;right:-90px;top:-120px;width:330px;height:330px;79 border-radius:50%;background:radial-gradient(circle,rgba(79,125,90,.16),rgba(79,125,90,0) 68%);80 pointer-events:none;81 }82 .hero-grid{display:grid;grid-template-columns:1.35fr .85fr;gap:34px;align-items:start;position:relative;z-index:1}83 .hero h2{font-size:clamp(2rem,5vw,3.6rem);line-height:1.04;margin:0 0 18px;color:var(--navy);letter-spacing:-.035em}84 .hero .lead{font-size:clamp(1rem,2vw,1.23rem);line-height:1.65;color:#344257;max-width:760px}85 .hero-actions{display:flex;gap:12px;flex-wrap:wrap;margin-top:28px}86 .btn{87 border:1px solid transparent;border-radius:10px;padding:12px 18px;font-weight:750;88 min-height:46px;display:inline-flex;align-items:center;justify-content:center;gap:8px;89 transition:.18s transform,.18s background,.18s border-color;90 }91 .btn:hover{transform:translateY(-1px)}92 .btn-primary{background:var(--success);color:white}93 .btn-primary:hover{background:#116b34}94 .btn-secondary{background:white;color:var(--blue);border-color:#b7c7d9}95 .btn-danger{background:white;color:var(--red);border-color:#e5b9b9}96 .btn-ghost{background:transparent;color:var(--blue);border-color:transparent}97 .btn[disabled]{opacity:.45;cursor:not-allowed;transform:none}98 .info-card{background:#f7fafc;border:1px solid var(--border);border-radius:14px;padding:20px}99 .info-card h3{margin:0 0 10px;color:var(--navy)}100 .feature-list{display:grid;gap:12px;margin:0;padding:0;list-style:none}101 .feature-list li{display:flex;gap:10px;line-height:1.45}102 .check{width:22px;height:22px;border-radius:50%;background:#e7f5ec;color:var(--success);display:grid;place-items:center;flex:none;font-weight:900}103 .notice{margin-top:18px;padding:14px 16px;border-left:4px solid var(--blue);background:#edf4fb;color:#2b4259;border-radius:8px}104 105 .setup{padding:32px}106 .setup h2{margin:0 0 8px;color:var(--navy)}107 .setup p{color:var(--muted);line-height:1.6}108 .rating-row{display:flex;gap:10px;flex-wrap:wrap;margin:18px 0}109 .rating-btn{110 width:52px;height:52px;border:1px solid var(--border);background:white;border-radius:50%;111 font-weight:800;color:var(--navy);112 }113 .rating-btn.selected{background:var(--success);color:white;border-color:var(--success)}114 .scale-labels{display:flex;justify-content:space-between;color:var(--muted);font-size:.86rem;max-width:350px}115 116 .quiz-shell{display:grid;grid-template-columns:270px 1fr;gap:18px}117 .sidebar{padding:20px;align-self:start;position:sticky;top:18px}118 .eyebrow{font-size:.72rem;letter-spacing:.09em;text-transform:uppercase;font-weight:850;color:var(--blue)}119 .progress-title{font-size:1.15rem;margin:6px 0 12px;color:var(--navy)}120 .progress-track{height:10px;background:#e4e9ef;border-radius:999px;overflow:hidden}121 .progress-fill{height:100%;background:linear-gradient(90deg,var(--green),var(--success));width:0;transition:width .25s ease}122 .progress-copy{font-size:.84rem;color:var(--muted);margin-top:8px}123 .domain-list{margin-top:22px;border-top:1px solid var(--border);padding-top:18px;display:grid;gap:12px}124 .domain-item{display:grid;grid-template-columns:1fr auto;gap:8px;align-items:center;font-size:.88rem}125 .domain-dot{width:9px;height:9px;background:var(--border);border-radius:50%;display:inline-block;margin-right:7px}126 .domain-item.active .domain-dot{background:var(--success)}127 .side-note{margin-top:18px;padding-top:18px;border-top:1px solid var(--border);font-size:.82rem;color:var(--muted);line-height:1.5}128 .question-card{padding:clamp(22px,4vw,38px)}129 .question-head{display:flex;justify-content:space-between;gap:16px;align-items:start}130 .question-head h2{margin:6px 0 0;color:var(--navy);font-size:clamp(1.35rem,3vw,2rem)}131 .points{background:#e9f5ec;color:var(--success);border:1px solid #b9d9c3;padding:7px 10px;border-radius:8px;font-weight:800;font-size:.82rem;white-space:nowrap}132 .scenario{margin:24px 0 10px;color:var(--blue);font-weight:850}133 .prompt-text{line-height:1.65;font-size:1.03rem;margin:0 0 18px}134 .instruction{font-weight:750;margin:22px 0 12px}135 .options{display:grid;gap:12px}136 .option{137 display:flex;gap:12px;align-items:flex-start;border:1px solid #cbd6e2;border-radius:12px;138 padding:14px;background:white;transition:.15s border,.15s background,.15s transform;139 }140 .option:hover{border-color:#86a9c8;transform:translateY(-1px)}141 .option.selected{border-color:var(--success);background:#f2faf4}142 .option input{margin-top:4px;accent-color:var(--success);width:18px;height:18px;flex:none}143 .option-letter{144 width:28px;height:28px;display:grid;place-items:center;border:1px solid var(--border);145 border-radius:50%;font-weight:850;color:var(--navy);flex:none;146 }147 .option-content{line-height:1.55}148 .option-content strong{display:block;margin-bottom:3px}149 .builder-preview{150 margin-top:18px;padding:16px;border:1px dashed #9cb2c8;border-radius:10px;background:#f8fbfe;151 color:#29394d;line-height:1.6;white-space:pre-wrap;152 }153 .order-list{display:grid;gap:10px}154 .order-row{155 border:1px solid var(--border);border-radius:10px;padding:11px 12px;display:grid;156 grid-template-columns:38px 1fr auto;gap:10px;align-items:center;background:white;157 }158 .order-num{width:30px;height:30px;border-radius:50%;background:#edf3f8;color:var(--blue);display:grid;place-items:center;font-weight:850}159 .move-buttons{display:flex;gap:6px}160 .move-buttons button{width:38px;height:38px;border:1px solid var(--border);background:white;border-radius:8px;color:var(--blue);font-weight:900}161 .confidence-box{margin-top:24px;padding:18px;background:#f7fafc;border:1px solid var(--border);border-radius:12px}162 .confidence-box h3{font-size:.95rem;margin:0 0 10px;color:var(--navy)}163 .confidence-scale{display:flex;gap:8px;flex-wrap:wrap}164 .confidence-scale button{165 width:44px;height:44px;border-radius:50%;border:1px solid var(--border);background:white;font-weight:800;166 }167 .confidence-scale button.selected{background:var(--blue);color:white;border-color:var(--blue)}168 .quiz-nav{169 display:flex;justify-content:space-between;gap:12px;margin-top:28px;padding-top:20px;border-top:1px solid var(--border)170 }171 172 .estimate{padding:32px}173 .estimate h2{margin-top:0;color:var(--navy)}174 .estimate input[type=range]{width:100%;accent-color:var(--success)}175 .estimate-value{font-size:2.4rem;font-weight:900;color:var(--success);margin:14px 0}176 177 .results{overflow:hidden}178 .results-head{179 background:linear-gradient(135deg,var(--navy),#0f315d);color:white;padding:20px 24px;180 display:flex;justify-content:space-between;align-items:center;gap:14px;flex-wrap:wrap;181 }182 .results-head h2{margin:0}183 .results-actions{display:flex;gap:8px;flex-wrap:wrap}184 .results-actions .btn{color:white;border-color:rgba(255,255,255,.38);background:transparent}185 .results-grid{display:grid;grid-template-columns:260px 1fr;gap:18px;padding:18px;background:#f4f7fa}186 .score-column{display:grid;gap:14px}187 .score-card{background:white;border:1px solid var(--border);border-radius:12px;padding:18px;text-align:center}188 .score-card h3{font-size:.78rem;letter-spacing:.05em;text-transform:uppercase;color:var(--blue);margin:0 0 8px}189 .score-number{font-size:3rem;line-height:1;font-weight:900;color:var(--success)}190 .score-level{font-weight:850;color:var(--success);margin-top:8px}191 .score-copy{font-size:.88rem;color:var(--muted);line-height:1.5}192 .calibration-label{font-size:1.05rem;font-weight:850;margin-top:8px}193 .calibration-label.over{color:#d06600}.calibration-label.under{color:var(--blue)}.calibration-label.good{color:var(--success)}194 .results-main{display:grid;gap:14px}195 .result-card{background:white;border:1px solid var(--border);border-radius:12px;padding:18px}196 .result-card h3{margin:0 0 14px;color:var(--navy);font-size:1rem}197 .bar-row{display:grid;grid-template-columns:220px 1fr 70px;gap:10px;align-items:center;margin:12px 0}198 .bar-track{height:10px;background:#e7ebf0;border-radius:999px;overflow:hidden}199 .bar-fill{height:100%;border-radius:999px;background:var(--success)}200 .bar-fill.mid{background:var(--gold)}.bar-fill.low{background:var(--red)}201 .two-col{display:grid;grid-template-columns:1fr 1fr;gap:14px}202 .plain-list{margin:0;padding-left:20px;line-height:1.7}203 .recommendation-grid{display:grid;gap:10px}204 .rec{205 padding:14px;border-left:4px solid var(--blue);background:#f7fafc;border-radius:8px;206 }207 .rec strong{display:block;color:var(--navy);margin-bottom:4px}208 .model-prompt{209 white-space:pre-wrap;background:#f7fafc;border:1px solid var(--border);padding:14px;border-radius:10px;210 line-height:1.55;font-family:ui-monospace,SFMono-Regular,Consolas,monospace;font-size:.88rem;211 }212 .result-footer{213 display:flex;gap:10px;flex-wrap:wrap;justify-content:center;padding:18px;border-top:1px solid var(--border);background:white;214 }215 216 .review{padding:28px}217 .review h2{margin-top:0;color:var(--navy)}218 .review-list{display:grid;gap:14px}219 .review-item{border:1px solid var(--border);border-radius:12px;padding:16px;background:white}220 .review-item.correct{border-left:5px solid var(--success)}221 .review-item.incorrect{border-left:5px solid var(--gold)}222 .review-item h3{margin:0 0 8px;color:var(--navy);font-size:1rem}223 .review-item p{line-height:1.55;color:#344257}224 .review-answer{font-size:.9rem;background:#f7fafc;border-radius:8px;padding:10px;margin-top:8px}225 226 .toast{227 position:fixed;left:50%;bottom:24px;transform:translateX(-50%) translateY(120px);228 background:var(--navy);color:white;padding:12px 18px;border-radius:999px;box-shadow:var(--shadow);229 opacity:0;transition:.25s;z-index:1000;font-weight:700;230 }231 .toast.show{transform:translateX(-50%) translateY(0);opacity:1}232 233 .mobile-progress{display:none}234 235 @media(max-width:900px){236 .hero-grid,.results-grid{grid-template-columns:1fr}237 .quiz-shell{grid-template-columns:1fr}238 .sidebar{display:none}239 .mobile-progress{240 display:block;position:sticky;top:0;z-index:20;background:white;border:1px solid var(--border);241 border-radius:12px;padding:12px 14px;margin-bottom:12px;box-shadow:0 6px 16px rgba(11,31,58,.08)242 }243 .mobile-progress-row{display:flex;justify-content:space-between;font-size:.86rem;margin-bottom:8px;font-weight:750;color:var(--navy)}244 .bar-row{grid-template-columns:1fr}245 .bar-score{font-size:.84rem;color:var(--muted)}246 .two-col{grid-template-columns:1fr}247 }248 @media(max-width:620px){249 .app{padding:0 10px 92px;margin-top:12px}250 .topbar{padding:14px 12px}251 .brand-mark{width:40px;height:40px}252 .brand p,.privacy-chip{display:none}253 .hero,.setup,.question-card,.estimate,.review{padding:20px}254 .hero-grid{gap:18px}255 .question-head{display:block}256 .points{display:inline-block;margin-top:10px}257 .quiz-nav{258 position:sticky;bottom:0;background:white;margin-left:-20px;margin-right:-20px;margin-bottom:-20px;259 padding:12px 20px calc(12px + env(safe-area-inset-bottom));box-shadow:0 -8px 20px rgba(11,31,58,.09);z-index:15;260 }261 .quiz-nav .btn{flex:1}262 .results-head{padding:18px}263 .results-grid{padding:10px}264 .results-actions{width:100%}265 .results-actions .btn{flex:1}266 .option{padding:12px}267 .order-row{grid-template-columns:34px 1fr}268 .move-buttons{grid-column:2}269 }270 271 @media(prefers-reduced-motion:reduce){272 *{scroll-behavior:auto!important;transition:none!important;animation:none!important}273 }274 275 @media print{276 body{background:white}277 .topbar,.results-actions,.result-footer,.toast{display:none!important}278 .app{max-width:none;margin:0;padding:0}279 .screen{display:none!important}280 #resultsScreen{display:block!important}281 .results{box-shadow:none;border:none}282 .results-head{background:white;color:black;border-bottom:2px solid #333}283 .results-grid{display:block;background:white;padding:0}284 .score-column,.results-main{display:block}285 .score-card,.result-card{break-inside:avoid;margin:10px 0}286 }287 </style>288</head>289<body>290 <header class="topbar">291 <div class="topbar-inner">292 <div class="brand">293 <div class="brand-mark" aria-hidden="true">AI</div>294 <div>295 <h1>UCPCOG Prompt Proficiency Challenge</h1>296 <p>Test. Learn. Improve your AI prompting.</p>297 </div>298 </div>299 <div class="privacy-chip">Runs entirely in your browser</div>300 </div>301 </header>302 303 <main class="app">304 <section id="introScreen" class="screen active panel hero">305 <div class="hero-grid">306 <div>307 <h2>How strong are your prompting skills, really?</h2>308 <p class="lead">309 This diagnostic measures how well you define tasks, ground AI in authoritative sources,310 control outputs, verify evidence, recognize public-sector risk, and design repeatable workflows.311 </p>312 <div class="hero-actions">313 <button class="btn btn-primary" id="startBtn">Start the assessment</button>314 <button class="btn btn-secondary" id="resumeBtn" hidden>Resume saved progress</button>315 </div>316 <div class="notice">317 This is a developmental assessment, not a disciplinary evaluation. It takes about 10 to 15 minutes.318 </div>319 </div>320 <aside class="info-card">321 <h3>What this assessment includes</h3>322 <ul class="feature-list">323 <li><span class="check">โ</span><span>15 applied public-sector scenarios</span></li>324 <li><span class="check">โ</span><span>Six prompt proficiency domains</span></li>325 <li><span class="check">โ</span><span>Confidence calibration</span></li>326 <li><span class="check">โ</span><span>Personalized improvement guidance</span></li>327 <li><span class="check">โ</span><span>Targeted retry of missed questions</span></li>328 </ul>329 <div class="notice" style="margin-bottom:0">330 Your responses stay on this device unless you choose to print or export them.331 </div>332 </aside>333 </div>334 </section>335 336 <section id="setupScreen" class="screen panel setup">337 <span class="eyebrow">Before you begin</span>338 <h2>Rate your current prompting ability</h2>339 <p>340 Select the rating that best reflects your current ability to use AI prompts professionally.341 This response is not scored. It is used to compare confidence with demonstrated performance.342 </p>343 <div class="rating-row" id="selfRating" role="radiogroup" aria-label="Self-assessed prompting ability">344 <button class="rating-btn" data-value="1" aria-label="1, beginner">1</button>345 <button class="rating-btn" data-value="2" aria-label="2">2</button>346 <button class="rating-btn" data-value="3" aria-label="3">3</button>347 <button class="rating-btn" data-value="4" aria-label="4">4</button>348 <button class="rating-btn" data-value="5" aria-label="5, highly proficient">5</button>349 </div>350 <div class="scale-labels"><span>Beginner</span><span>Highly proficient</span></div>351 <div class="hero-actions">352 <button class="btn btn-secondary" id="setupBackBtn">Back</button>353 <button class="btn btn-primary" id="beginQuizBtn" disabled>Begin questions</button>354 </div>355 </section>356 357 <section id="quizScreen" class="screen">358 <div class="mobile-progress panel">359 <div class="mobile-progress-row">360 <span id="mobileQuestionLabel">Question 1 of 15</span>361 <span id="mobilePercent">0%</span>362 </div>363 <div class="progress-track"><div class="progress-fill" id="mobileProgressFill"></div></div>364 </div>365 366 <div class="quiz-shell">367 <aside class="panel sidebar">368 <div class="eyebrow">Progress</div>369 <div class="progress-title" id="questionLabel">Question 1 of 15</div>370 <div class="progress-track"><div class="progress-fill" id="progressFill"></div></div>371 <div class="progress-copy" id="progressCopy">0% complete</div>372 373 <div class="domain-list" id="domainList"></div>374 375 <div class="side-note">376 Responses are saved locally so you can recover from an accidental refresh.377 </div>378 </aside>379 380 <article class="panel question-card">381 <div class="question-head">382 <div>383 <span class="eyebrow" id="questionDomain"></span>384 <h2 id="questionTitle"></h2>385 </div>386 <span class="points" id="questionPoints"></span>387 </div>388 389 <div class="scenario">Scenario</div>390 <p class="prompt-text" id="questionScenario"></p>391 <p class="instruction" id="questionInstruction"></p>392 393 <div id="answerArea"></div>394 395 <div class="confidence-box">396 <h3>How confident are you in this answer?</h3>397 <div class="confidence-scale" id="confidenceScale" role="radiogroup" aria-label="Confidence in this answer">398 <button data-value="1" aria-label="1, not confident">1</button>399 <button data-value="2" aria-label="2">2</button>400 <button data-value="3" aria-label="3">3</button>401 <button data-value="4" aria-label="4">4</button>402 <button data-value="5" aria-label="5, very confident">5</button>403 </div>404 </div>405 406 <div class="quiz-nav">407 <button class="btn btn-secondary" id="prevBtn">Back</button>408 <button class="btn btn-primary" id="nextBtn" disabled>Continue</button>409 </div>410 </article>411 </div>412 </section>413 414 <section id="estimateScreen" class="screen panel estimate">415 <span class="eyebrow">One final estimate</span>416 <h2>What score do you think you earned?</h2>417 <p>418 Move the slider to estimate your score. This is not scored. It helps measure confidence calibration.419 </p>420 <div class="estimate-value"><span id="estimateValue">70</span>/100</div>421 <input id="estimateSlider" type="range" min="0" max="100" value="70" step="1" aria-label="Estimated assessment score" />422 <div class="hero-actions">423 <button class="btn btn-secondary" id="estimateBackBtn">Back</button>424 <button class="btn btn-primary" id="showResultsBtn">Show my results</button>425 </div>426 </section>427 428 <section id="resultsScreen" class="screen panel results">429 <div class="results-head">430 <div>431 <h2>Your Results</h2>432 <div id="resultsSubtitle">Assessment complete</div>433 </div>434 <div class="results-actions">435 <button class="btn" id="printBtn">Print results</button>436 <button class="btn" id="exportBtn">Export results</button>437 </div>438 </div>439 440 <div class="results-grid">441 <aside class="score-column">442 <div class="score-card">443 <h3>Your score</h3>444 <div><span class="score-number" id="overallScore">0</span> / 100</div>445 <div class="score-level" id="proficiencyLevel"></div>446 <p class="score-copy" id="proficiencyCopy"></p>447 </div>448 449 <div class="score-card">450 <h3>Confidence calibration</h3>451 <div class="calibration-label" id="calibrationLabel"></div>452 <p class="score-copy" id="calibrationCopy"></p>453 </div>454 455 <div class="score-card">456 <h3>Score range</h3>457 <p class="score-copy" style="text-align:left;line-height:1.8">458 <strong>90โ100</strong> Prompt Architect<br>459 <strong>75โ89</strong> Workflow Designer<br>460 <strong>60โ74</strong> Structured Practitioner<br>461 <strong>40โ59</strong> Effective Drafter<br>462 <strong>0โ39</strong> Foundational User463 </p>464 </div>465 </aside>466 467 <div class="results-main">468 <section class="result-card">469 <h3>Competency breakdown</h3>470 <div id="domainBars"></div>471 </section>472 473 <div class="two-col">474 <section class="result-card">475 <h3>Strongest capabilities</h3>476 <ul class="plain-list" id="strengthList"></ul>477 </section>478 <section class="result-card">479 <h3>Priority improvement areas</h3>480 <ol class="plain-list" id="priorityList"></ol>481 </section>482 </div>483 484 <section class="result-card">485 <h3>Recommended next steps</h3>486 <div class="recommendation-grid" id="recommendations"></div>487 </section>488 489 <section class="result-card">490 <h3>Copy and use this stronger prompt pattern</h3>491 <div class="model-prompt" id="modelPrompt"></div>492 <div class="hero-actions" style="margin-top:12px">493 <button class="btn btn-primary" id="copyPromptBtn">Copy prompt</button>494 </div>495 </section>496 </div>497 </div>498 499 <div class="result-footer">500 <button class="btn btn-secondary" id="reviewBtn">Review all questions</button>501 <button class="btn btn-secondary" id="retryBtn">Retry missed questions</button>502 <button class="btn btn-primary" id="retakeBtn">Retake full assessment</button>503 <button class="btn btn-danger" id="clearBtn">Clear my data</button>504 </div>505 </section>506 507 <section id="reviewScreen" class="screen panel review">508 <span class="eyebrow">Guided review</span>509 <h2>Question-by-question feedback</h2>510 <p>Review what you selected, the correct reasoning, and the improvement principle for each scenario.</p>511 <div class="review-list" id="reviewList"></div>512 <div class="hero-actions">513 <button class="btn btn-secondary" id="reviewBackBtn">Back to results</button>514 </div>515 </section>516 </main>517 518 <div class="toast" id="toast" role="status" aria-live="polite"></div>519 520<script>521const DOMAINS = {522 clarity: {523 label: "Task & Objective Clarity",524 weight: 15,525 short: "Task clarity",526 rec: "State the decision, audience, purpose, and required outcome before asking AI to draft."527 },528 grounding: {529 label: "Context & Source Grounding",530 weight: 20,531 short: "Source grounding",532 rec: "Identify authoritative sources, limit the model to those materials, and require page or section references."533 },534 control: {535 label: "Constraints & Output Control",536 weight: 15,537 short: "Output control",538 rec: "Specify structure, length, tone, exclusions, and what the model must not assume."539 },540 verification: {541 label: "Verification & Evidence",542 weight: 20,543 short: "Verification",544 rec: "Require citations, uncertainty labels, factual checks, and human review before official use."545 },546 risk: {547 label: "Data & Public-Sector Risk",548 weight: 15,549 short: "Risk awareness",550 rec: "Use approved platforms, classify information, protect sensitive data, and retain human authority over consequential decisions."551 },552 workflow: {553 label: "Workflow & Reuse",554 weight: 15,555 short: "Workflow design",556 rec: "Design repeatable steps with source intake, drafting, verification, approval, and records retention."557 }558};559 560const QUESTIONS = [561 {562 id:"q1", domain:"clarity", type:"choice", points:5,563 title:"Best Prompt Selection",564 scenario:"You need to prepare a board summary of a 60-page federal grant notice.",565 instruction:"Which prompt is most likely to produce a reliable, usable result?",566 options:[567 "Summarize this grant notice.",568 "Summarize the grant notice and tell me whether we should apply.",569 "Using only the attached grant notice, prepare a structured board summary. Identify eligible applicants, eligible activities, funding limits, match requirements, deadlines, evaluation criteria, reporting obligations, and unresolved questions. Cite the page or section supporting each finding. Do not determine whether we should apply."570 ],571 correct:2,572 rationale:"The strongest prompt defines the audience, requested fields, source boundary, citation requirement, and a limit on unsupported recommendations.",573 principle:"A strong prompt defines the actual deliverable and prevents the model from making a decision that belongs to staff or leadership."574 },575 {576 id:"q2", domain:"grounding", type:"multi", points:5,577 title:"Identify the Missing Controls",578 scenario:"A staff member writes: โPrepare a legal summary of the new rule for our managers. Keep it under 500 words.โ",579 instruction:"Select every important control that is missing.",580 options:[581 "Identify the authoritative rule or source documents",582 "Require citations to the relevant provisions",583 "Define the intended management audience",584 "Tell the AI to write in a more confident tone",585 "Require unresolved legal questions to be flagged for counsel"586 ],587 correct:[0,1,2,4],588 rationale:"A legal summary needs authoritative sources, citations, a defined audience, and escalation of unresolved legal issues. More confidence would increase risk.",589 principle:"High-stakes work needs source control, role clarity, and explicit escalation."590 },591 {592 id:"q3", domain:"control", type:"builder", points:5,593 title:"Repair a Weak Prompt",594 scenario:"The original prompt is: โWrite a memo about our budget.โ",595 instruction:"Select the components that materially improve control over the output.",596 base:"Write a memo about our budget.",597 options:[598 {label:"Identify the audience and decision the memo supports", text:"Prepare the memo for the governing board and explain the decision requiring board direction."},599 {label:"Name the source materials", text:"Use only the attached adopted budget, current expenditure report, and finance director notes."},600 {label:"Require a defined structure", text:"Use sections for current position, major variances, risks, decisions, and unresolved questions."},601 {label:"Ask for persuasive language regardless of evidence", text:"Make the financial position sound positive even if the sources are mixed."},602 {label:"Prohibit unsupported assumptions", text:"Do not invent causes, forecasts, or explanations not supported by the supplied records."}603 ],604 correct:[0,1,2,4],605 rationale:"The strongest repair defines audience, sources, structure, and prohibited assumptions. It does not ask the AI to distort evidence.",606 principle:"Output control depends on explicit structure and clear boundaries."607 },608 {609 id:"q4", domain:"verification", type:"multi", points:5,610 title:"Evaluate the AI Output",611 scenario:"An AI-generated briefing cites a 2025 federal report, states that costs fell by 37%, and recommends immediate adoption. The source file contains no 37% figure and no adoption recommendation.",612 instruction:"Select every problem that must be addressed.",613 options:[614 "Unsupported statistic",615 "Recommendation exceeds the evidence",616 "The response should be longer",617 "Citation must be checked against the actual source",618 "The response uses professional language"619 ],620 correct:[0,1,3],621 rationale:"The statistic is unsupported, the recommendation exceeds the evidence, and the citation must be verified. Length and tone are not the core problems.",622 principle:"A polished answer can still be wrong. Verify every material claim."623 },624 {625 id:"q5", domain:"risk", type:"choice", points:5,626 title:"Classify a Sensitive Data Use",627 scenario:"A staff member wants to upload caregiver case notes containing names, addresses, diagnoses, and benefit information into a personal AI account to create summaries.",628 instruction:"What is the correct classification?",629 options:[630 "Approved low-risk use",631 "Acceptable after removing names only",632 "Prohibited in the proposed environment and subject to approved-platform and data-governance review",633 "Acceptable when the staff member deletes the chat afterward"634 ],635 correct:2,636 rationale:"The proposed environment is not approved for sensitive case information. Removing names alone may not adequately de-identify the records.",637 principle:"Platform approval, data classification, and authorization matter more than convenience."638 },639 {640 id:"q6", domain:"workflow", type:"order", points:5,641 title:"Sequence a Controlled AI Workflow",642 scenario:"A department is creating an AI-assisted policy briefing for official use.",643 instruction:"Place the workflow stages in the best order.",644 items:[645 "Generate the initial draft",646 "Verify facts, citations, and calculations",647 "Define the required decision and output",648 "Retain the final record",649 "Identify authoritative source materials",650 "Obtain authorized approval",651 "Apply professional judgment and revise",652 "Establish data restrictions and approved tools"653 ],654 correct:[2,4,7,0,1,6,5,3],655 rationale:"A controlled workflow defines the objective and sources before drafting, then verifies, applies judgment, obtains approval, and retains the final record.",656 principle:"Prompting is one stage in a larger accountable workflow."657 },658 {659 id:"q7", domain:"grounding", type:"choice", points:5,660 title:"Ground a Meeting Summary",661 scenario:"You need a summary of a three-hour regional board meeting.",662 instruction:"Which instruction best controls the evidence?",663 options:[664 "Use your general knowledge to add context where the transcript is unclear.",665 "Use only the transcript and approved agenda. Distinguish motions, votes, staff reports, public comments, and unresolved items. Mark inaudible or uncertain passages rather than guessing.",666 "Create a polished summary and fill in missing details so it reads smoothly."667 ],668 correct:1,669 rationale:"The correct instruction limits sources, defines categories, and directs the model to label uncertainty rather than fabricate missing details.",670 principle:"Source grounding includes rules for handling gaps and ambiguity."671 },672 {673 id:"q8", domain:"clarity", type:"multi", points:5,674 title:"Diagnose an Ambiguous Request",675 scenario:"A manager asks AI: โHelp us improve transportation.โ",676 instruction:"Which clarifications are needed before a useful prompt can be written?",677 options:[678 "What transportation problem is being addressed",679 "Which population or geography is affected",680 "What decision or deliverable is required",681 "Which evidence or datasets are available",682 "Which font the AI prefers"683 ],684 correct:[0,1,2,3],685 rationale:"The request lacks a defined problem, population, deliverable, and evidence base. Font preference is irrelevant at this stage.",686 principle:"A vague task cannot be repaired by adding more words. The underlying objective must be clarified."687 },688 {689 id:"q9", domain:"verification", type:"choice", points:5,690 title:"Handle a Citation You Cannot Confirm",691 scenario:"An AI response provides a convincing quotation and citation, but the cited passage cannot be found in the source.",692 instruction:"What should happen next?",693 options:[694 "Use the quotation because the citation looks authoritative",695 "Remove or correct the claim, document the verification failure, and review other citations",696 "Ask the AI to make the quotation shorter",697 "Replace the citation with the agency homepage"698 ],699 correct:1,700 rationale:"An unverified quotation must not be used. One citation failure also justifies checking the rest of the output.",701 principle:"Citation formatting is not proof. Verification requires checking the underlying source."702 },703 {704 id:"q10", domain:"risk", type:"choice", points:5,705 title:"Protect Consequential Decisions",706 scenario:"A procurement team wants AI to score vendor proposals and automatically select the winning bidder.",707 instruction:"Which approach is most appropriate?",708 options:[709 "Allow the AI to make the final selection if the scoring rubric is uploaded",710 "Use AI only for administrative support or documented decision support, with authorized human evaluators retaining final scoring and selection responsibility",711 "Let the lowest-cost model make the decision",712 "Use a personal AI account because procurement documents are already public"713 ],714 correct:1,715 rationale:"Procurement selection is consequential. AI may support analysis, but authorized humans must retain responsibility and the process must be documented and auditable.",716 principle:"AI should not receive unreviewed authority over consequential public decisions."717 },718 {719 id:"q11", domain:"workflow", type:"builder", points:5,720 title:"Build a Reusable Prompt Pattern",721 scenario:"A planning department repeatedly summarizes development applications for internal review.",722 instruction:"Select the components that make the prompt reusable and governable.",723 base:"Summarize this development application.",724 options:[725 {label:"Use a standard input checklist",text:"Confirm that the application, site plan, zoning information, staff comments, and applicable ordinance sections are present."},726 {label:"Use a standard output structure",text:"Return project facts, applicable standards, potential conflicts, missing information, and questions for professional review."},727 {label:"Require source references",text:"Cite the application page, map layer, or ordinance section supporting each material finding."},728 {label:"Allow the AI to approve routine applications",text:"Approve the application automatically when no conflict is found."},729 {label:"Define the review point",text:"Label all conclusions as preliminary until reviewed by authorized planning staff."}730 ],731 correct:[0,1,2,4],732 rationale:"Reusable prompts need standard inputs, outputs, citations, and a clear human review point. Approval authority should not be delegated to the prompt.",733 principle:"A prompt becomes a workflow when inputs, outputs, controls, and review points are standardized."734 },735 {736 id:"q12", domain:"verification", type:"choice", points:5,737 title:"Use Uncertainty Correctly",738 scenario:"The source documents conflict about the project deadline.",739 instruction:"Which instruction produces the most reliable response?",740 options:[741 "Choose the deadline that appears most often.",742 "Identify each conflicting deadline, cite its source, explain that the conflict cannot be resolved from the supplied materials, and flag it for human confirmation.",743 "Use the later deadline to reduce risk.",744 "Omit the deadline."745 ],746 correct:1,747 rationale:"The AI should surface the conflict, cite each source, and escalate the unresolved issue rather than selecting a date without authority.",748 principle:"Reliability includes knowing when not to resolve uncertainty."749 },750 {751 id:"q13", domain:"grounding", type:"multi", points:5,752 title:"Create a Trustworthy Knowledge Base",753 scenario:"A COG wants an internal AI assistant to answer questions about policies and procedures.",754 instruction:"Select the practices that improve grounding and maintainability.",755 options:[756 "Use approved, current policy documents",757 "Assign document owners and review dates",758 "Mix current and superseded policies without labels",759 "Preserve version and effective-date metadata",760 "Require answers to cite the controlling document"761 ],762 correct:[0,1,3,4],763 rationale:"A trustworthy knowledge base depends on approved sources, ownership, version control, review dates, and citations.",764 principle:"Institutional knowledge systems require information governance, not just document upload."765 },766 {767 id:"q14", domain:"workflow", type:"order", points:5,768 title:"Prepare Public Communications",769 scenario:"Staff are using AI to draft a public notice about a service change.",770 instruction:"Place the stages in the safest operational order.",771 items:[772 "Draft the notice with AI",773 "Publish through the authorized channel",774 "Confirm the approved policy decision and effective date",775 "Obtain communications approval",776 "Identify the affected audience and required notice elements",777 "Retain the approved final version",778 "Check facts, dates, accessibility, and plain-language requirements",779 "Complete legal or program review when required"780 ],781 correct:[2,4,0,6,7,3,1,5],782 rationale:"The organization must confirm the decision and requirements before drafting, then review, approve, publish, and retain the final record.",783 principle:"Public communications require approved facts and an authorized release process."784 },785 {786 id:"q15", domain:"control", type:"multi", points:10,787 title:"Capstone: Design the Board Briefing",788 scenario:"A COG employee must prepare a board briefing about a federal grant using a 75-page notice, internal project notes, and preliminary budget estimates.",789 instruction:"Select every element that belongs in the final prompt and workflow.",790 options:[791 "Identify the board decision the briefing must support",792 "Limit factual grant findings to the official funding notice",793 "Clearly distinguish internal estimates from federal requirements",794 "Require page or section citations for material grant claims",795 "Ask AI to decide whether the board should authorize the application",796 "Flag missing information and unresolved eligibility questions",797 "Require finance and program review before board distribution",798 "Upload confidential personnel records to provide more context"799 ],800 correct:[0,1,2,3,5,6],801 rationale:"The capstone requires a defined decision, source boundaries, separation of estimates from requirements, citations, uncertainty handling, and human review. AI should not make the board decision or receive unrelated confidential records.",802 principle:"Professional prompting integrates objective clarity, source control, evidence, risk boundaries, and review authority."803 }804];805 806const state = {807 screen:"intro",808 selfRating:null,809 current:0,810 activeQuestionIds:QUESTIONS.map(q=>q.id),811 answers:{},812 confidence:{},813 estimate:70,814 retryMode:false,815 originalScore:null,816 lastResults:null817};818 819const els = {};820[821 "introScreen","setupScreen","quizScreen","estimateScreen","resultsScreen","reviewScreen",822 "startBtn","resumeBtn","setupBackBtn","beginQuizBtn","selfRating","questionLabel","progressFill",823 "progressCopy","domainList","questionDomain","questionTitle","questionPoints","questionScenario",824 "questionInstruction","answerArea","confidenceScale","prevBtn","nextBtn","mobileQuestionLabel",825 "mobilePercent","mobileProgressFill","estimateValue","estimateSlider","estimateBackBtn","showResultsBtn",826 "overallScore","proficiencyLevel","proficiencyCopy","calibrationLabel","calibrationCopy","domainBars",827 "strengthList","priorityList","recommendations","modelPrompt","copyPromptBtn","printBtn","exportBtn",828 "reviewBtn","retryBtn","retakeBtn","clearBtn","reviewList","reviewBackBtn","toast","resultsSubtitle"829].forEach(id=>els[id]=document.getElementById(id));830 831function showScreen(name){832 document.querySelectorAll(".screen").forEach(s=>s.classList.remove("active"));833 const map={intro:els.introScreen,setup:els.setupScreen,quiz:els.quizScreen,estimate:els.estimateScreen,results:els.resultsScreen,review:els.reviewScreen};834 map[name].classList.add("active");835 state.screen=name;836 saveState();837 window.scrollTo({top:0,behavior:"smooth"});838}839 840function saveState(){841 localStorage.setItem("promptProficiencyState", JSON.stringify({842 selfRating:state.selfRating,843 current:state.current,844 activeQuestionIds:state.activeQuestionIds,845 answers:state.answers,846 confidence:state.confidence,847 estimate:state.estimate,848 retryMode:state.retryMode,849 originalScore:state.originalScore,850 lastResults:state.lastResults851 }));852}853 854function loadState(){855 const raw=localStorage.getItem("promptProficiencyState");856 if(!raw) return false;857 try{858 const saved=JSON.parse(raw);859 Object.assign(state,saved);860 return true;861 }catch(e){return false}862}863 864function resetState(full=true){865 state.selfRating=null;866 state.current=0;867 state.activeQuestionIds=QUESTIONS.map(q=>q.id);868 state.answers={};869 state.confidence={};870 state.estimate=70;871 state.retryMode=false;872 state.originalScore=null;873 state.lastResults=null;874 if(full) localStorage.removeItem("promptProficiencyState");875}876 877function activeQuestions(){878 return state.activeQuestionIds.map(id=>QUESTIONS.find(q=>q.id===id));879}880 881function currentQuestion(){ return activeQuestions()[state.current]; }882 883function renderDomainList(){884 const q=currentQuestion();885 els.domainList.innerHTML = Object.entries(DOMAINS).map(([key,d])=>`886 <div class="domain-item ${q && q.domain===key ? "active":""}">887 <span><span class="domain-dot"></span>${d.short}</span>888 <span>${d.weight}%</span>889 </div>890 `).join("");891}892 893function answerIsComplete(q){894 const a=state.answers[q.id];895 if(q.type==="choice") return Number.isInteger(a);896 if(q.type==="multi" || q.type==="builder") return Array.isArray(a) && a.length>0;897 if(q.type==="order") return Array.isArray(a) && a.length===q.items.length;898 return false;899}900 901function renderQuestion(){902 const list=activeQuestions();903 const q=list[state.current];904 const progress=state.current/list.length*100;905 const label=`Question ${state.current+1} of ${list.length}`;906 els.questionLabel.textContent=label;907 els.mobileQuestionLabel.textContent=label;908 els.progressFill.style.width=`${progress}%`;909 els.mobileProgressFill.style.width=`${progress}%`;910 els.progressCopy.textContent=`${Math.round(progress)}% complete`;911 els.mobilePercent.textContent=`${Math.round(progress)}%`;912 els.questionDomain.textContent=DOMAINS[q.domain].label;913 els.questionTitle.textContent=q.title;914 els.questionPoints.textContent=`${q.points} points`;915 els.questionScenario.textContent=q.scenario;916 els.questionInstruction.textContent=q.instruction;917 renderDomainList();918 renderAnswer(q);919 renderConfidence(q);920 els.prevBtn.disabled=state.current===0 && !state.retryMode;921 els.nextBtn.textContent=state.current===list.length-1 ? "Finish questions" : "Continue";922 updateNextButton();923}924 925function renderAnswer(q){926 if(q.type==="choice"){927 const selected=state.answers[q.id];928 els.answerArea.innerHTML=`<div class="options">${q.options.map((o,i)=>`929 <label class="option ${selected===i?"selected":""}" tabindex="0">930 <input type="radio" name="answer" value="${i}" ${selected===i?"checked":""}>931 <span class="option-letter">${String.fromCharCode(65+i)}</span>932 <span class="option-content">${o}</span>933 </label>`).join("")}</div>`;934 els.answerArea.querySelectorAll("input").forEach(input=>input.addEventListener("change",e=>{935 state.answers[q.id]=Number(e.target.value); saveState(); renderAnswer(q); updateNextButton();936 }));937 }938 939 if(q.type==="multi"){940 const selected=state.answers[q.id]||[];941 els.answerArea.innerHTML=`<div class="options">${q.options.map((o,i)=>`942 <label class="option ${selected.includes(i)?"selected":""}" tabindex="0">943 <input type="checkbox" value="${i}" ${selected.includes(i)?"checked":""}>944 <span class="option-content">${o}</span>945 </label>`).join("")}</div>`;946 els.answerArea.querySelectorAll("input").forEach(input=>input.addEventListener("change",e=>{947 const value=Number(e.target.value);948 const arr=new Set(state.answers[q.id]||[]);949 e.target.checked?arr.add(value):arr.delete(value);950 state.answers[q.id]=[...arr].sort((a,b)=>a-b);951 saveState(); renderAnswer(q); updateNextButton();952 }));953 }954 955 if(q.type==="builder"){956 const selected=state.answers[q.id]||[];957 const preview=[q.base,...selected.map(i=>q.options[i].text)].join("\n\n");958 els.answerArea.innerHTML=`<div class="options">${q.options.map((o,i)=>`959 <label class="option ${selected.includes(i)?"selected":""}" tabindex="0">960 <input type="checkbox" value="${i}" ${selected.includes(i)?"checked":""}>961 <span class="option-content"><strong>${o.label}</strong>${o.text}</span>962 </label>`).join("")}</div>963 <div class="builder-preview" aria-live="polite"><strong>Prompt preview</strong>\n\n${escapeHtml(preview)}</div>`;964 els.answerArea.querySelectorAll("input").forEach(input=>input.addEventListener("change",e=>{965 const value=Number(e.target.value);966 const arr=new Set(state.answers[q.id]||[]);967 e.target.checked?arr.add(value):arr.delete(value);968 state.answers[q.id]=[...arr].sort((a,b)=>a-b);969 saveState(); renderAnswer(q); updateNextButton();970 }));971 }972 973 if(q.type==="order"){974 if(!Array.isArray(state.answers[q.id])){975 state.answers[q.id]=q.items.map((_,i)=>i);976 }977 const order=state.answers[q.id];978 els.answerArea.innerHTML=`<div class="order-list">${order.map((itemIndex,pos)=>`979 <div class="order-row">980 <div class="order-num">${pos+1}</div>981 <div>${q.items[itemIndex]}</div>982 <div class="move-buttons">983 <button type="button" data-pos="${pos}" data-dir="-1" aria-label="Move item up" ${pos===0?"disabled":""}>โ</button>984 <button type="button" data-pos="${pos}" data-dir="1" aria-label="Move item down" ${pos===order.length-1?"disabled":""}>โ</button>985 </div>986 </div>`).join("")}</div>`;987 els.answerArea.querySelectorAll(".move-buttons button").forEach(btn=>btn.addEventListener("click",()=>{988 const pos=Number(btn.dataset.pos), dir=Number(btn.dataset.dir), target=pos+dir;989 [order[pos],order[target]]=[order[target],order[pos]];990 state.answers[q.id]=order; saveState(); renderAnswer(q); updateNextButton();991 }));992 }993}994 995function renderConfidence(q){996 const selected=state.confidence[q.id];997 els.confidenceScale.querySelectorAll("button").forEach(btn=>{998 btn.classList.toggle("selected",Number(btn.dataset.value)===selected);999 });1000}1001 1002function updateNextButton(){1003 const q=currentQuestion();1004 els.nextBtn.disabled=!(answerIsComplete(q) && Number.isInteger(state.confidence[q.id]));1005}1006 1007function escapeHtml(str){1008 return String(str).replace(/[&<>"']/g,m=>({"&":"&","<":"<",">":">",'"':""","'":"'"}[m]));1009}1010 1011function scoreQuestion(q,answer){1012 if(q.type==="choice") return answer===q.correct ? q.points : 0;1013 if(q.type==="multi" || q.type==="builder"){1014 const correct=new Set(q.correct), selected=new Set(answer||[]);1015 let hits=0, wrong=0;1016 selected.forEach(v=>correct.has(v)?hits++:wrong++);1017 const raw=(hits-wrong)/correct.size;1018 return Math.max(0,Math.min(q.points,q.points*raw));1019 }1020 if(q.type==="order"){1021 const arr=answer||[];1022 let correctPositions=0;1023 q.correct.forEach((v,i)=>{if(arr[i]===v) correctPositions++});1024 return q.points*(correctPositions/q.correct.length);1025 }1026 return 0;1027}1028 1029function computeResults(questionSet=QUESTIONS){1030 const domainRaw={};1031 Object.keys(DOMAINS).forEach(k=>domainRaw[k]={earned:0,max:0});1032 let totalEarned=0,totalMax=0;1033 const missed=[];1034 questionSet.forEach(q=>{1035 const earned=scoreQuestion(q,state.answers[q.id]);1036 domainRaw[q.domain].earned+=earned;1037 domainRaw[q.domain].max+=q.points;1038 totalEarned+=earned; totalMax+=q.points;1039 if(earned<q.points*.75) missed.push(q.id);1040 });1041 const domainScores={};1042 Object.entries(domainRaw).forEach(([k,v])=>{1043 domainScores[k]=v.max?Math.round(v.earned/v.max*100):null;1044 });1045 let weighted=0,weightUsed=0;1046 Object.entries(DOMAINS).forEach(([k,d])=>{1047 if(domainScores[k]!==null){weighted+=domainScores[k]*d.weight;weightUsed+=d.weight}1048 });1049 const overall=Math.round(weighted/weightUsed);1050 const confidenceValues=questionSet.map(q=>state.confidence[q.id]).filter(Number.isFinite);1051 const confidencePct=confidenceValues.length?Math.round(((confidenceValues.reduce((a,b)=>a+b,0)/confidenceValues.length)-1)/4*100):0;1052 const estimate=Number(state.estimate)||0;1053 const gap=Math.round(((confidencePct+estimate)/2)-overall);1054 return {overall,domainScores,missed,confidencePct,estimate,gap,totalEarned,totalMax};1055}1056 1057function proficiency(score){1058 if(score>=90) return ["Prompt Architect","You consistently integrate objectives, sources, constraints, verification, risk controls, and workflow sequencing."];1059 if(score>=75) return ["Workflow Designer","You can structure complex prompts, control evidence, and design repeatable AI-supported processes."];1060 if(score>=60) return ["Structured Practitioner","You have a solid foundation. Focus on the lowest-scoring domains to improve reliability."];1061 if(score>=40) return ["Effective Drafter","You can produce useful drafts, but stronger grounding, verification, and controls are needed."];1062 return ["Foundational User","Focus first on task clarity, authoritative sources, output constraints, and human verification."];1063}1064 1065function calibration(gap){1066 if(gap>15) return ["Overconfidence risk","Your confidence was materially higher than your demonstrated performance. Strengthen structured prompting and verification before moving into higher-risk workflows.","over"];1067 if(gap>7) return ["Slightly overconfident","Your confidence was somewhat higher than your demonstrated performance. Use the improvement priorities below to tighten your approach.","over"];1068 if(gap<-15) return ["Underconfident capability","Your demonstrated ability was substantially stronger than your confidence estimate.","under"];1069 if(gap<-7) return ["Slightly underconfident","Your demonstrated ability was stronger than your confidence estimate.","under"];1070 return ["Well calibrated","Your confidence closely matched your demonstrated proficiency.","good"];1071}1072 1073function renderResults(){1074 const results=computeResults(QUESTIONS);1075 state.lastResults=results;1076 saveState();1077 const [level,copy]=proficiency(results.overall);1078 const [calLabel,calCopy,calClass]=calibration(results.gap);1079 1080 els.overallScore.textContent=results.overall;1081 els.proficiencyLevel.textContent=level;1082 els.proficiencyCopy.textContent=copy;1083 els.calibrationLabel.textContent=calLabel;1084 els.calibrationLabel.className=`calibration-label ${calClass}`;1085 els.calibrationCopy.textContent=calCopy;1086 els.resultsSubtitle.textContent=state.retryMode && state.originalScore!==null1087 ? `Targeted retry complete. Original score: ${state.originalScore}.`1088 : "Assessment complete.";1089 1090 const ranked=Object.entries(results.domainScores)1091 .filter(([,v])=>v!==null)1092 .sort((a,b)=>b[1]-a[1]);1093 1094 els.domainBars.innerHTML=ranked.map(([key,score])=>`1095 <div class="bar-row">1096 <div>${DOMAINS[key].label}</div>1097 <div class="bar-track"><div class="bar-fill ${score<50?"low":score<70?"mid":""}" style="width:${score}%"></div></div>1098 <div class="bar-score">${score} / 100</div>1099 </div>1100 `).join("");1101 1102 const strengths=ranked.slice(0,3);1103 const priorities=[...ranked].reverse().slice(0,3);1104 els.strengthList.innerHTML=strengths.map(([k,s])=>`<li>${DOMAINS[k].label} (${s}%)</li>`).join("");1105 els.priorityList.innerHTML=priorities.map(([k,s])=>`<li>${DOMAINS[k].label} (${s}%)</li>`).join("");1106 els.recommendations.innerHTML=priorities.map(([k,s])=>`1107 <div class="rec"><strong>${DOMAINS[k].label}</strong>${DOMAINS[k].rec}</div>1108 `).join("");1109 1110 els.modelPrompt.textContent=buildModelPrompt(priorities.map(([k])=>k));1111 els.retryBtn.disabled=results.missed.length===0;1112}1113 1114function buildModelPrompt(weakDomains){1115 const lines=[1116 "Using only the attached authoritative source documents, prepare a structured briefing for the governing board.",1117 "",1118 "State the decision or purpose the briefing supports. Distinguish verified facts, internal estimates, professional judgments, and unresolved questions.",1119 "",1120 "Cite the page or section supporting each material factual statement. Clearly label information that cannot be verified from the supplied sources.",1121 "",1122 "Do not invent facts, statistics, legal conclusions, causes, forecasts, or recommendations that are not supported by the provided material.",1123 "",1124 "Format the response with:",1125 "1. Executive summary",1126 "2. Key findings",1127 "3. Operational implications",1128 "4. Risks and uncertainties",1129 "5. Questions requiring human review",1130 "6. Source citations",1131 "",1132 "The output remains a draft until reviewed and approved by authorized staff."1133 ];1134 if(weakDomains.includes("risk")) lines.push("\nDo not include or infer sensitive personal information. Use only an approved AI environment.");1135 if(weakDomains.includes("workflow")) lines.push("\nAfter drafting, provide a verification checklist and identify the required review and approval points.");1136 if(weakDomains.includes("control")) lines.push("\nKeep the briefing concise, use plain language, and do not exceed 900 words.");1137 return lines.join("\n");1138}1139 1140function renderReview(){1141 els.reviewList.innerHTML=QUESTIONS.map((q,i)=>{1142 const earned=scoreQuestion(q,state.answers[q.id]);1143 const ok=earned>=q.points*.75;1144 return `<article class="review-item ${ok?"correct":"incorrect"}">1145 <h3>${i+1}. ${q.title} โ ${ok?"Proficient response":"Review recommended"}</h3>1146 <p>${q.rationale}</p>1147 <div class="review-answer"><strong>Improvement principle:</strong> ${q.principle}</div>1148 </article>`;1149 }).join("");1150}1151 1152function nextQuestion(){1153 if(state.current<activeQuestions().length-1){1154 state.current++; saveState(); renderQuestion(); window.scrollTo({top:0,behavior:"smooth"});1155 }else{1156 state.estimate=70;1157 els.estimateSlider.value=70;1158 els.estimateValue.textContent=70;1159 showScreen("estimate");1160 }1161}1162 1163function startFullAssessment(){1164 resetState(false);1165 state.activeQuestionIds=QUESTIONS.map(q=>q.id);1166 showScreen("setup");1167}1168 1169function beginRetry(){1170 const results=state.lastResults || computeResults(QUESTIONS);1171 if(!results.missed.length) return;1172 state.originalScore=results.overall;1173 state.retryMode=true;1174 state.activeQuestionIds=results.missed;1175 state.current=0;1176 state.activeQuestionIds.forEach(id=>{1177 delete state.answers[id];1178 delete state.confidence[id];1179 });1180 showScreen("quiz");1181 renderQuestion();1182}1183 1184function exportResults(){1185 const r=state.lastResults||computeResults(QUESTIONS);1186 const lines=[1187 "UCPCOG Prompt Proficiency Challenge Results",1188 `Overall score: ${r.overall}/100`,1189 `Proficiency level: ${proficiency(r.overall)[0]}`,1190 `Confidence calibration: ${calibration(r.gap)[0]}`,1191 "",1192 "Competency scores:"1193 ];1194 Object.entries(r.domainScores).forEach(([k,v])=>lines.push(`- ${DOMAINS[k].label}: ${v}%`));1195 lines.push("","Priority recommendations:");1196 Object.entries(r.domainScores).sort((a,b)=>a[1]-b[1]).slice(0,3).forEach(([k])=>lines.push(`- ${DOMAINS[k].rec}`));1197 const blob=new Blob([lines.join("\n")],{type:"text/plain"});1198 const url=URL.createObjectURL(blob);1199 const a=document.createElement("a");1200 a.href=url;a.download="prompt-proficiency-results.txt";a.click();