diff --git a/main.go b/main.go index a5324f8..8397356 100644 --- a/main.go +++ b/main.go @@ -52,8 +52,8 @@ func main() { app.Get("/", func(c *fiber.Ctx) error { return c.Render("index", fiber.Map{}) }) - app.Get("/end", func(c *fiber.Ctx) error { - return c.Render("end", fiber.Map{}) + app.Get("/results", func(c *fiber.Ctx) error { + return c.Render("results", fiber.Map{}) }) app.Get("/:qid", func(c *fiber.Ctx) error { qID, err := c.ParamsInt("qid") @@ -71,7 +71,7 @@ func main() { return err } - nextURL := prefix + "/end" + nextURL := prefix + "/results" reachedEnd := true if idx+1 < len(questions.Questions) { nextURL = fmt.Sprintf("%v/%d", prefix, idx+2) diff --git a/public/scripts/controllers/yourscore.js b/public/scripts/controllers/yourscore.js index 53dfcd5..dba36be 100644 --- a/public/scripts/controllers/yourscore.js +++ b/public/scripts/controllers/yourscore.js @@ -2,9 +2,11 @@ import { Controller } from "https://unpkg.com/@hotwired/stimulus/dist/stimulus.j import { gameState } from "./gamestate.js"; const ANIMATION_DURATION = 1500.0; +const MAX_QUESTIONS = 10; +const CIRCLE_RADIUS = 50; export default class extends Controller { - static targets = ['path', 'count']; + static targets = ['path', 'pathBack', 'count', 'postScore', 'rank']; connect() { this._startT = 0; @@ -13,41 +15,41 @@ export default class extends Controller { } _startAnimating(t) { - this._finalScore = 3; + this._finalScore = 10; this._startT = t; - this._finalArcPostition = 360 * this._finalScore / 10; - this._updateCounterEvery = ANIMATION_DURATION / this._finalScore; - this._updateCounterAt = 0; + this._finalArcPostition = 360 * this._finalScore / MAX_QUESTIONS; this._currentlyDisplayedScore = 0; - this.countTarget.innerText = "0"; + this.countTarget.innerText = "0%"; requestAnimationFrame(this._animateFrame.bind(this)); } _animateFrame(t) { let tt = t - this._startT; + let tScaled = tt / ANIMATION_DURATION; if (tt >= ANIMATION_DURATION) { - if (this._finalArcPostition == 360) { - this.pathTarget.setAttribute("d", this._describeCircle(50, 50, 45)); + this.pathTarget.setAttribute("d", this._describeCircle(CIRCLE_RADIUS, CIRCLE_RADIUS, CIRCLE_RADIUS - 5)); } else { - this.pathTarget.setAttribute("d", this._describeArc(50, 50, 45, 0, this._finalArcPostition)); + this.pathTarget.setAttribute("d", this._describeArc(CIRCLE_RADIUS, CIRCLE_RADIUS, CIRCLE_RADIUS - 5, 0, this._finalArcPostition)); } - this.countTarget.innerText = this._finalScore.toString(); + let scoreToDisplay = (this._finalScore * 100 / MAX_QUESTIONS) | 0; + this.countTarget.innerText = `${scoreToDisplay}%`; + window.setTimeout(() => this._showPostStore(), 1); return; } let arcT = Math.sin(tt / ANIMATION_DURATION * Math.PI / 2.0); - this.pathTarget.setAttribute("d", this._describeArc(50, 50, 45, 0, this._finalArcPostition * arcT)); + this.pathTarget.setAttribute("d", this._describeArc(CIRCLE_RADIUS, CIRCLE_RADIUS, CIRCLE_RADIUS - 5, 0, this._finalArcPostition * arcT)); - if (tt >= this._updateCounterAt) { - this._currentlyDisplayedScore++; - this.countTarget.innerText = this._currentlyDisplayedScore.toString(); - this._updateCounterAt += this._updateCounterEvery; + let scoreToDisplay = (arcT * this._finalScore * 100 / MAX_QUESTIONS) | 0; + if (scoreToDisplay != this._currentlyDisplayedScore) { + this._currentlyDisplayedScore = scoreToDisplay; + this.countTarget.innerText = `${scoreToDisplay}%`; } requestAnimationFrame(this._animateFrame.bind(this)); @@ -87,4 +89,9 @@ export default class extends Controller { return d; } + _showPostStore() { + this.rankTarget.innerText = "Developer"; + + this.postScoreTarget.classList.remove("hidden"); + } } \ No newline at end of file diff --git a/public/style.css b/public/style.css index a31d0af..ff9a432 100644 --- a/public/style.css +++ b/public/style.css @@ -1,3 +1,7 @@ +:root { + --score-color: green; +} + div.offscreen { position: fixed; left: -100px; @@ -85,6 +89,65 @@ input[type=radio] { display: none !important; } +.vspacer { + height: 2em; +} + +/** + * Your score + */ +div.score-wrapper { + text-align: center; +} + +div.yourscore { + margin-inline: auto; + position: relative; + text-align: left; + + width: 250px; + height: 250px; +} + +div.yourscore svg { + position: absolute; + + width: 100%; + height: 100%; + z-index: -10; +} + +div.yourscore svg path { + stroke: #ccc; +} + +div.yourscore svg path.score { + stroke: var(--score-color); +} + + +div.yourscore .counter { + position: absolute; + font-size: 4em; + + top: calc(50% - 0.75em); + left: 0; + width: 100%; + text-align: center; + color: var(--score-color); + + z-index: 10; +} + +div.post-score { + margin-block-start: 2em; +} + +div.rank { + font-size: 1.5em; + text-align: center; +} + /** * Page transition */ diff --git a/views/end.html b/views/end.html deleted file mode 100644 index f76a0f0..0000000 --- a/views/end.html +++ /dev/null @@ -1,12 +0,0 @@ -
You reached the end
- -Your final score is
+