拓冰建站拓冰建站
首页 / 资讯中心 / 正文

用事件驱动编程从零构建打字速度游戏:Web-Dev-For-Beginners 实战指南

用事件驱动编程从零构建打字速度游戏Web-Dev-For-Beginners 实战指南【免费下载链接】Web-Dev-For-Beginners24 Lessons, 12 Weeks, Get Started as a Web Developer项目地址: https://gitcode.com/GitHub_Trending/we/Web-Dev-For-Beginners本指南以 Web-Dev-For-Beginners 课程第 4 模块《Event-Driven Programming - Build a Typing Game》为核心带你理解浏览器如何通过事件与 JavaScript 通信并亲手实现一个实时校验输入、逐词高亮、统计完成时间的打字速度游戏。读完本文你将掌握addEventListener()事件监听、DOM 动态更新、输入校验与计时逻辑的组合运用并能独立完成可运行的完整项目。事件驱动编程网页活起来的核心机制思考你常用的应用或网站是什么让它们显得鲜活、响应灵敏关键在于对用户操作的即时反应——每一次点击、滑动或按键都会产生一个事件event这正是 Web 开发魔力的来源。Web 编程与普通脚本最大的不同在于不可预知性我们永远不知道用户何时会点击按钮、何时开始打字——可能立即发生可能等五分钟也可能根本不发生。因此我们不能像写菜谱那样自上而下地编写代码而是要写一段耐心等待的代码事件未发生时它安静待命事件一旦触发便立刻响应。这与 19 世纪电报员守在机器旁等待消息到来的工作方式异曲同工。什么是事件简单说事件就是发生了某件事点击按钮是事件、输入一个字母是事件、移动鼠标也是事件。事件驱动编程Event-Driven Programming让我们为代码建立监听-响应机制其核心构件是事件监听器Event Listener。可以把事件监听器想象成代码的门铃安装门铃用addEventListener()告诉它要听什么声音例如click或keypress指定门铃响起时执行的逻辑自定义函数事件监听器的四个关键特性监听特定的用户动作如点击、按键、鼠标移动执行事件发生时你编写的自定义代码响应用户的交互营造无缝体验处理同一元素上的多个事件通过不同的监听器NOTE创建事件监听器的方式有很多种——可以使用匿名函数也可以创建具名函数可以使用element.click handler之类的快捷写法也可以使用addEventListener()。本练习聚焦addEventListener()与匿名函数因为这是 Web 开发者最常用的技术而且它最灵活适用于所有事件类型事件名可以作为参数传入。常见事件一览浏览器提供数十种可监听的事件页面上用户几乎任何操作都会触发事件。幸运的是日常应用通常只需要其中一小部分。以下是几个常用事件包含我们游戏中用到的两种事件描述常见用途click用户点击了某元素按钮、链接、可交互元素contextmenu用户点击鼠标右键自定义右键菜单select用户选中了文本文本编辑、复制操作input用户输入了文本表单校验、实时搜索理解这些事件类型时要注意用户与页面上特定元素交互时触发事件事件对象event object提供了用户动作的详细信息事件支持你构建响应式、可交互的 Web 应用事件行为在不同浏览器和设备间保持一致游戏整体设计从需求到流程我们将创建一个打字速度游戏检验玩家也是开发者最重要的基本功之一的键入技能。有趣的是今天仍在使用的 QWERTY 键盘布局诞生于 1870 年代的打字机时代而良好的打字能力对今天的程序员依旧价值连城。游戏的整体流程如下游戏运行机制玩家点击开始按钮后启动显示一句随机名言逐词实时追踪玩家的输入进度高亮当前单词引导玩家注意力出现输入错误时提供即时的视觉反馈整句输入完成时计算并显示总用时项目文件结构保持简洁整个游戏只需要三个文件——这也是驱动大部分 Web 应用的三件套index.html页面结构、script.js全部游戏逻辑、style.css视觉样式。打开终端创建项目目录# Linux 或 macOS mkdir typing-game cd typing-game # Windows md typing-game cd typing-game命令作用新建名为typing-game的目录、自动进入该目录、为游戏开发准备好干净的工作区。接着用 VS Code 打开目录code .最后在编辑器里新建上述三个文件index.html负责游戏结构与内容、script.js承载所有游戏逻辑与事件监听器、style.css定义视觉外观。参考本仓库的完整可运行实现位于 4-typing-game/solution/包含index.html、index.js、index.css三个文件可直接对照学习。构建用户界面HTML如同设计飞船控制面板我们需要把所有玩家需要的元素放在最顺手的位置。分析一个打字游戏的需求需要以下 UI 元素UI 元素用途HTML 元素名言展示区显示要输入的文字p且idquote消息区显示状态与完成消息p且idmessage文本输入框玩家输入名言的位置input且idtyped-value开始按钮开始游戏button且idstartUI 结构设计要点从上到下逻辑化组织内容、为每个元素分配唯一 ID 以便 JavaScript 定位、建立清晰的视觉层级、使用语义化 HTML 保证可访问性。新建index.html添加如下 HTML!-- inside index.html -- html head titleTyping game/title link relstylesheet hrefstyle.css /head body h1Typing game!/h1 pPractice your typing skills with a quote from Sherlock Holmes. Click **start** to begin!/p p idquote/p !-- This will display our quote -- p idmessage/p !-- This will display any status messages -- div input typetext aria-labelcurrent word idtyped-value / !-- The textbox for typing -- button typebutton idstartStart/button !-- To start the game -- /div script srcscript.js/script /body /html这段 HTML 结构的作用在head中链接CSS 样式表创建清晰的标题与用户指引建立带特定 ID 的占位段落供动态内容填充包含带可访问性属性aria-label的输入框提供触发游戏的开始按钮在末尾加载JavaScript 文件以获得最佳性能仓库中的 4-typing-game/solution/index.html 在此基础上做了增强引入了 Font Awesome 图标、视觉隐藏但仍保留给屏幕阅读器的labelclasshidden-label、输入框占位符placeholderType here...以及实时日期时间显示体现了可访问性与用户体验的进阶实践。启动应用使用 Live Server开发中频繁测试能尽早发现问题、实时看到进展。VS Code 的 Live Server 扩展既能在本地托管应用又能在每次保存时自动刷新浏览器。安装步骤如下通过链接进入扩展页面点击Install安装——浏览器会提示打开 VS Code 并引导完成安装部分情况可能需要重启 VS Code安装完成后按Ctrl-Shift-PmacOS 为Cmd-Shift-P打开命令面板——它提供所有 VS Code 命令的快速访问入口支持边输入边搜索输入并执行Live Server: Open with Live ServerLive Server 的作用启动本地开发服务器、保存文件时自动刷新浏览器、默认在localhost:5500提供服务。打开浏览器访问https://localhost:5500你应该能看到刚创建的页面。接下来添加功能。添加样式CSS从 1980 年代起研究者就发现即时的视觉反馈能显著提升用户表现并减少错误——这正是我们要实现的。游戏必须让玩家一目了然知道当前该输入哪个词输错时能立刻察觉。新建style.css添加如下样式/* inside style.css */ .highlight { background-color: yellow; } .error { background-color: lightcoral; border: red; }这两个 CSS 类的作用highlight用黄色背景高亮当前单词提供清晰的视觉引导error用浅珊瑚色背景提示输入错误在不打断打字流程的前提下提供即时反馈使用对比色保证可访问性与清晰的视觉传达✅ 关于布局你可以完全自由发挥花点时间让页面更美观更换字体、给标题上色、调整元素尺寸。仓库解决方案 4-typing-game/solution/index.css 展示了一套完整的增强样式渐变背景linear-gradient(135deg, #f9fafb, #e3f2ef)、带左边框与圆角的引用展示卡片#quote、输入框聚焦时的发光效果input#typed-value:focus的box-shadow、开始按钮的悬浮位移动画button#start:hover的transform: translateY(-2px)以及针对窄屏的media (max-width: 600px)响应式规则——值得逐一对照实践。编写游戏逻辑JavaScriptHTML 与 CSS 搭好了躯壳JavaScript 则是让游戏真正动起来的引擎。整个实现分三步推进步骤目的你将学到创建常量准备名言数组与 DOM 引用变量管理与 DOM 选择开始游戏的事件监听器处理游戏初始化事件处理与 UI 更新打字输入的事件监听器实时处理用户输入输入校验与动态反馈这种结构化方式能帮助你把代码组织成逻辑清晰的模块、增量构建功能以便调试、理解应用各部分如何协同工作、为未来项目沉淀可复用模式。新建script.js。第一步创建常量就像任务控制中心在发射前调试好全部监测系统先把所有资源准备到位既能避免后续到处查找也能防止拼写错误。需要准备的数据数据类型用途示例名言数组存放游戏所有可选名言[Quote 1, Quote 2, ...]单词数组将当前名言拆分为单词[When, you, have, ...]单词索引追踪玩家正在输入的单词0, 1, 2, 3...开始时间计算用时进行计分Date.now()还需要对 UI 元素的引用文本输入框typed-value、名言展示区quote、消息区message。// inside script.js // all of our quotes const quotes [ When you have eliminated the impossible, whatever remains, however improbable, must be the truth., There is nothing more deceptive than an obvious fact., I ought to know by this time that when a fact appears to be opposed to a long train of deductions it invariably proves to be capable of bearing some other interpretation., I never make exceptions. An exception disproves the rule., What one man can invent another can discover., Nothing clears up a case so much as stating it to another person., Education never ends, Watson. It is a series of lessons, with the greatest for the last., ]; // store the list of words and the index of the word the player is currently typing let words []; let wordIndex 0; // the starting time let startTime Date.now(); // page elements const quoteElement document.getElementById(quote); const messageElement document.getElementById(message); const typedValueElement document.getElementById(typed-value);这段初始化代码的作用用const存放名言数组——名言不会改变用let初始化追踪变量——这些值会在游戏过程中更新用document.getElementById()捕获DOM 元素引用保证高效访问用清晰、描述性的变量名搭建全部游戏功能的基础把相关数据与元素逻辑化组织便于后续维护✅ 你可以向数组中加入更多名言。Pro Tip随时可以用document.getElementById()获取元素。由于我们会频繁引用这些元素最好用常量封装以避免字符串字面量的拼写错误。Vue.js、React 等框架能帮你更好地集中管理代码。常量方式还能获得 IDE 的自动补全与错误检查支持并在元素 ID 变更时更容易重构。第二步添加开始逻辑当用户点击start我们需要随机选择名言、设置用户界面、为当前单词与计时建立追踪。在script.js末尾追加// at the end of script.js document.getElementById(start).addEventListener(click, () { // get a quote const quoteIndex Math.floor(Math.random() * quotes.length); const quote quotes[quoteIndex]; // Put the quote into an array of words words quote.split( ); // reset the word index for tracking wordIndex 0; // UI updates // Create an array of span elements so we can set a class const spanWords words.map(function(word) { return span${word} /span}); // Convert into string and set as innerHTML on quote display quoteElement.innerHTML spanWords.join(); // Highlight the first word quoteElement.childNodes[0].className highlight; // Clear any prior messages messageElement.innerText ; // Setup the textbox // Clear the textbox typedValueElement.value ; // set focus typedValueElement.focus(); // set the event handler // Start the timer startTime new Date().getTime(); });按逻辑段拆解这段代码 单词追踪设置用Math.floor()与Math.random()随机选取名言保证每次不同用split( )将名言转换为单词数组将wordIndex重置为 0——玩家从第一个单词开始为一轮新游戏准备好游戏状态 UI 设置与显示创建span元素数组把每个单词包裹起来以便单独设置样式拼接span 元素为单个字符串高效更新 DOM给第一个单词添加highlightCSS 类实现高亮清除上一局的游戏消息获得干净起点⌨️ 文本框准备清空输入框中的既有文本聚焦文本框让玩家可以立即开始输入准备好新游戏会话的输入区域⏱️ 计时器初始化用new Date().getTime()记录当前时间戳为精确计算打字速度与完成时间提供基础启动本局游戏的性能追踪第三步添加打字逻辑这是游戏的心脏每敲入一个字符代码都会检查输入内容、给出反馈并决定下一步走向——类似 1970 年代 WordStar 等早期文字处理器为打字员提供的实时反馈。在script.js末尾继续追加// at the end of script.js typedValueElement.addEventListener(input, () { // Get the current word const currentWord words[wordIndex]; // get the current value const typedValue typedValueElement.value; if (typedValue currentWord wordIndex words.length - 1) { // end of sentence // Display success const elapsedTime new Date().getTime() - startTime; const message CONGRATULATIONS! You finished in ${elapsedTime / 1000} seconds.; messageElement.innerText message; } else if (typedValue.endsWith( ) typedValue.trim() currentWord) { // end of word // clear the typedValueElement for the new word typedValueElement.value ; // move to the next word wordIndex; // reset the class name for all elements in quote for (const wordElement of quoteElement.childNodes) { wordElement.className ; } // highlight the new word quoteElement.childNodes[wordIndex].className highlight; } else if (currentWord.startsWith(typedValue)) { // currently correct // highlight the next word typedValueElement.className ; } else { // error state typedValueElement.className error; } });理解打字逻辑的瀑布式判断这个函数采用瀑布waterfall方式按从最具体到最通用的顺序依次检查条件 场景一整句完成检查输入值是否等于当前单词且处于最后一个单词用当前时间减开始时间计算用时除以 1,000 将毫秒转换为秒显示包含完成时间的祝贺消息✅ 场景二单词完成输入以空格结尾时判定单词完成验证trim()后的输入与当前单词完全一致typedValue.endsWith( ) typedValue.trim() currentWord的复合条件确保玩家确实按下了空格键确认清空输入框以输入下一个单词递增wordIndex推进到下一词移除所有元素的类并高亮新单词更新视觉高亮 场景三正在输入且正确验证当前单词以已输入内容开头currentWord.startsWith(typedValue)移除错误样式表明当前输入正确不打断输入允许继续打字❌ 场景四错误状态输入内容与预期单词开头不匹配时触发应用errorCSS 类提供即时视觉反馈帮助玩家快速发现并纠正错误源码印证仓库中的解决方案 4-typing-game/solution/index.js 对同一逻辑做了 ES6 重构可作为对照学习的范本使用document.querySelector()统一选择元素用getRandomQuote()、renderQuote()、highlightWord()等具名工具函数取代匿名函数用[...quoteElement.children].forEach(...)与classList.toggle(highlight, i index)更安全地切换高亮类在完成时设置typedValueElement.disabled true禁用输入框这正是课后挑战中UI 状态管理的参考实现并用Date.now()与toFixed(2)格式化完成时间。对比两种写法能同时理解最小实现与工程化重构两种风格。测试你的应用现在进入测试阶段如果一开始没有完美运行完全正常——即使经验丰富的开发者也会经常发现 bug这是开发过程的一部分。点击start然后开始打字吧需要测试的要点验证点击 Start 会显示随机名言确认输入时当前单词高亮正确检查错误输入时会出现错误样式测试完成单词后高亮会正确推进验证完成整句名言后显示带用时的完成消息常用调试技巧打开浏览器控制台F12检查JavaScript 错误确认所有文件名完全匹配注意大小写敏感确保Live Server 正在运行并正常刷新测试不同名言以验证随机选择逻辑进阶挑战GitHub Copilot Agent 挑战 使用 Agent 模式完成以下挑战练习高级事件处理、数据分析与动态 UI 更新任务为打字游戏实现一个难度调节系统追踪玩家的打字速度每分钟字数 WPM与准确率百分比自动在三档难度间切换Easy简单名言、Medium当前名言、Hard带标点的复杂名言在 UI 上显示当前难度等级与玩家统计数据实现连击计数器——连续 3 次良好表现后提升难度添加视觉反馈颜色、动画标识难度变化需要补充相应的 HTML 元素、CSS 样式与 JavaScript 函数包含合理的错误处理并使用适当的 ARIA 标签保证可访问性。 核心挑战扩展游戏功能功能描述练习的技能输入控制完成后禁用input事件监听器点击按钮时重新启用事件管理与状态控制UI 状态管理完成名言后禁用文本框DOM 属性操作模态对话框用模态对话框显示成功消息高级 UI 模式与可访问性最高分系统用localStorage存储最高分浏览器存储 API 与数据持久化实现提示查阅localStorage.setItem()与localStorage.getItem()实现持久化存储练习动态添加与移除事件监听器探索 HTMLdialog元素或 CSS 模态模式禁用/启用表单控件时考虑可访问性提示解决方案 4-typing-game/solution/index.js 中typedValueElement.disabled true一行即为UI 状态管理挑战的直接参考。学习路线从 5 分钟到一个月⚡ 接下来 5 分钟用不同名言测试游戏确保运行顺畅尝试修改 CSS——换掉高亮与错误颜色边玩边打开浏览器 DevToolsF12观察 Console挑战自己尽快完成一句名言⏰ 这一小时往数组里加更多名言比如来自你喜欢的书籍或电影实现挑战部分的 localStorage 最高分系统添加每局结束后的每分钟字数WPM计算器为正确输入、错误与完成添加音效 这一周构建多人对战版本创建不同难度级别变化名言复杂度添加进度条显示名言完成度实现带个人统计追踪的用户账户设计自定义主题供用户选择️ 这一个月创建包含指法教学的分级打字课程构建分析功能展示哪些字母或单词最容易出错支持不同语言与键盘布局集成教育 API 从文学数据库拉取名言发布增强版打字游戏供他人使用回顾与自学浏览器为开发者提供了大量可用事件通读这份清单思考每个事件的适用场景下拉菜单、实时校验的表单、响应点击的游戏——你看到的每一个交互背后都是事件驱动编程的力量。课后作业完成本课后通过 4-typing-game/typing-game/assignment.md 中的作业Create a new keyboard game检验学习成果设计并构建一个你自己的键盘游戏要求包含至少 3 个不同的键盘事件监听器、即时的视觉反馈、完整的游戏逻辑计分/关卡/进度机制以及清晰的用户界面说明。可参考的创意方向包括节奏游戏、像素画创作器、拼词游戏、贪吃蛇、音乐合成器或编程术语专项打字等评分标准涵盖功能完整性、代码质量、用户体验与创意性四个维度。【免费下载链接】Web-Dev-For-Beginners24 Lessons, 12 Weeks, Get Started as a Web Developer项目地址: https://gitcode.com/GitHub_Trending/we/Web-Dev-For-Beginners创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
分享:

看完干货,该让你的企业上线了

免费需求沟通 · 48 小时内出具建站方案 · 河南本地可上门