跳到主要内容位置
Hello! 我是张旭乾

致力于帮助你以最直观、最快速的方式学会前端开发,并希望我的个人经历对你有所启发。点击查看最新技术视频教程、实战课程、技术博客、前端资源导航、以及我的想法和生活点滴

“峰华前端工程师”账号创作者/《JavaScript 基础语法详解》作者

最新视频

什么是 Node.js

Node.js 是一个可以运行在服务器端的 JavaScript 运行环境,并且是开源和跨平台的。我们在网页中使用的 JavaScript 是浏览器提供的运行环境,是运行在客户端,也就是用户的电脑上的。

Node.js 则把 Chrome 的 V8 JS 引擎独立了出来,脱离了浏览器,这样就可以使用 JavaScript 开发服务端应用了。

全栈开发

因为 Node.js 同样使用 JavaScript 语言,那么我们可以只学习一种语言,就可以开发多端应用,变成全栈工程师,减少了学习成本。

热门程度

在 stackoverflow 2024 年的开发者调查中显示,Node.js 是最热门的服务端开发技术:

stackoverflow 2024 年的开发者调查 Node.js

而 JavaScript 则是适用人数最多的语言:

JavaScript 排行

并且 Node.js Foundation 报告世界 500 强中有 98% 都或多或少的使用了 Node.js。

Node.js 在 500 强使用情况

谁、何时开发了 Node.js

Node.js 是由 Ryan Dahl 开发的,于 2009 年发布。开发 Node.js 目的是为了解决 Apache 这个热门服务器在处理大量并发连接时的性能,同时减少资源消耗。

Event Driven 架构

Node.js 采用了事件驱动,非阻塞 I/O 的架构模式,并且使用单线程结合 Event Loop 的方式来执行代码。不需要维护线程池,减少了内存的消耗,提高了性能,适合实时应用的开发,例如股票交易应用,也适合大数据应用的开发。

模块化

Node.js 对 JS 本身的一大影响就是支持了模块化,把处理不同逻辑的代码放到不同的文件中,形成模块,然后在其他文件中可以进行引入并使用,这样就方便的封装和复用。

// math.mjs
export function add(a, b) {
  return a + b;
}

export function subtract(a, b) {
  return a - b;
}
// app.mjs
import { add, subtract } from './math.mjs';

console.log(add(5, 3)); // 输出: 8
console.log(subtract(10, 4)); // 输出: 6

API

在使用客户端 JavaScript 时,浏览器提供了 Window、Document 等 API 让我们能够操作浏览器窗口和网页等,而 Node.js 也提供了一组 API 让我们更方便的编写服务端应用,例如 File 文件读写,HTTP 服务器,OS 操作系统工具,等等。

示例

要使用 Node.js,我们可以在它的官网下载对应操作系统的安装包,它分为稳定版和最新版,稳定版更新周期稍慢,官方支持周期长,最新版更新周期快能体验新的特性,可以根据自己的需求进行下载。

这里,我们有一个简单的 Node.js HTTP API 使用示例,用于处理一个 GET 请求,并返回响应结果:

  • 代码从 node:http 模块中导入了 createServer 函数来创建服务器。
  • 之后调用 createServer,在里边处理了请求和响应,无论什么请求都返回 200 响应码和 Hello World 文本。
  • 最后调用 createServer 返回的实例中的 listen 方法,来启动服务器并监听本地 3000 端口。
// server.mjs
import { createServer } from 'node:http';

const server = createServer((req, res) => {
  res.writeHead(200, { 'Content-Type': 'text/plain' });
  res.end('Hello World!\n');
});

// 启动服务器到本地 3000 端口
server.listen(3000, '127.0.0.1', () => {
  console.log('Listening on 127.0.0.1:3000');
});

// 运行 `node server.mjs` 来启动服务器

使用 node server.mjs 运行服务器之后,在浏览器访问 http://localhost:3000就可以看到返回的 Hello World!结果了。

小结

好了,这个就是 Node.js 的介绍,你学会了吗?如果有帮助请三连并关注,想学更多的开发知识,可以在评论区留言,感谢观看!

3 分钟了解 Node.js

我们在使用 React 处理表单给服务器发送数据的时候,需要分别手动处理 Loading 加载,error 错误,和服务器请求,这样的 state 比较分散,代码不容易维护:

function CommentForm() {
  const [comments, setComments] = useState([]);
  const [isPending, setIsPending] = useState(false);
  const [error, setError] = useState(null);

  async function handleFormSubmit(e) {
    e.preventDefault();
    setIsPending(true);
    const formData = new FormData(e.target);
    const comment = formData.get("comment");
    try {
      const result = await submitComment(comment);
      setComments((comments) => [...comments, result]);
      setIsPending(false);
    } catch (error) {
      setError(error);
    }
  }

React 19 出了一个新 Hooks, useActionState 可以让我们集中管理 loading、error 和服务器的请求,它:

  • 接收一个 async 的函数作为参数,在里边我们可以编写表单的提交操作。
  • 这个函数又接收两个参数,一个是表单之前的状态,一个是React 帮我们包装好的表单对象,基于浏览器的 FormData API,它包含各个表单控件的用户输入。
  • 之后在里边我们可以访问表单数据并提交到服务器。
  • 函数的返回值会作为 useActionState 的返回值之一,一般用于返回错误。
  • 最后 useActionState 还接收第二个参数,作为表单状态的初始值。
  • useActionState 会返回一个数组,它里边有我们 async 函数的返回值,用于给表单 action 属性绑定的事件处理函数,还有一个加载状态。

这样定义好之后,我们就可以在 JSX 中使用了:

const [error, submitCommentAction, isPending] = useActionState(
  async (previousState, formData) => {
    const comment = formData.get("comment");
    const result = await submitComment(comment);
    setComments((comments) => [...comments, result]);
    return null;
  },
  null
);

<form action={submitCommentAction}>
  <textarea
    name="comment"
    placeholder="写个评论吧..."
    cols={40}
    rows={4}
  />
  <button type="submit" disabled={isPending}>
    发布评论
  </button>
</form>
{error && <p className="error">{error}</p>}
<ul className="comments-list">
  {comments.map((comment, index) => (
    <li key={index}>
      <p>评论:{comment}</p>
    </li>
  ))}
</ul>

在表单提交后,React 现在还会帮我们自动清空表单控件的里的输入,只要这些输入框是非受控组件。

乐观 UI

另外,表单处理还有另外一种常见的需求,就是乐观 UI,在提交数据后,先更新 UI,随后再处理服务器数据,这样能先给用户反馈,提高程序响应性。

React 19 提供了 useOptimistic Hooks 来实现乐观 UI,我们可以:

  • 使用它包装一下表单本身的状态。
  • 它会返回和 useState 类似的两个结果,一个是乐观状态值,一个是修改乐观状态的函数。
  • 之后我们在表单处理函数里,调用修改乐观状态的函数就可以了,可以在发送服务器数据之前。
  • 最后在 JSX 中,使用乐观数据展示就可以了。
const [optimisticComments, setOptimisticComents] = useOptimistic(comments);

const [error, submitCommentAction, isPending] = useActionState(
    async (previousState, formData) => {
      const comment = formData.get("comment");
      setOptimisticComents((optComments) => [...optComments, comment]);
      const result = await submitComment(comment);
      setComments((comments) => [...comments, result]);
      return null;
    },
    null
  );

<ul className="comments-list">
  {optimisticComments.map((comment, index) => (
    <li key={index}>
      <p>评论:{comment}</p>
    </li>
  ))}
</ul>

访问上层表单状态

有时候表单组件的嵌套比较复杂,每个表单控件可能都是一个独立的组件,这样在获取表单状态的时候,需要多次传递 props,很不方便,这个时候 React 19 提供了 useFormStatus hooks,只要是 form 元素下层的组件,都可以访问表单的状态,例如加载状态、数据和错误等等,调用 useFormStatus 会返回包含这些信息的对象,例如我们可以在按钮中访问表单的加载状态,然后根据它来判断是否禁用按钮,之后父组件也不用再传递props了:

function SubmitButton() {
  const { pending } = useFormStatus();

  return (
    <button type="submit" disabled={pending}>
      发布评论
    </button>
  );
}

 <form action={submitCommentAction}>
  <!-- ... -->
  <SubmitButton />
</form>

小结

好了,这个就是 React 19 表单处理的新方式,以及相关的 hooks,你学会了吗?如果有帮助请三连并关注,想学更多的开发知识,可以在评论区留言,感谢观看!

React 19 表单处理新方式-新Hooks

我们在使用 CSS 实现动画的时候,是以时间为基础的。keyframes 里的百分比,会根据 animation 属性中指定的时间来分配:

.someElement {
  animation: aniamte 1s linear;
}

@keyframes animate {
  0%{}    /* 0s */
  25%{}
  50%{}   /* 1s */
  100%{}  /* 2s */
}

现在,CSS 出了一个新特性,让我们可以按滚动来实现动画,这就是 CSS 滚动驱动动画。

滚动的方式有两种:

  • 一种是以距离最近的父组件的滚动条的滚动,keyframes 百分比根据滚动条的位置计算。
  • 另一种是按元素自身出现的位置来执行动画,就是说元素从底部滚动出来,到上方滚动出去的过程,keyframes 的百分比根据元素位置进行计算。

利用 CSS 滚动驱动动画可以实现:

  • 视差效果
  • 全屏阅读进度
  • 幻灯片
  • reveal 出现动画

配置 CSS 滚动动画

那要使用 CSS 滚动驱动动画,我们需要配置 animation-timeline 属性来指定滚动方式,使用 scroll() 函数可以按最近父元素的滚动条实现动画。scroll() 函数接收两个参数:

  • 第一个参数是根据哪个元素的滚动执行动画,它可以取 3 个值:
    • neareast - 最近的有滚动条的父元素,这个是默认值
    • root - 根元素的滚动条,也就是最顶级的
    • self - 元素自身的滚动条
  • 第二个参数指定方向,可以指定:
    • block - 块级方向,这是默认的
    • inline - 行级方向
    • y - 纵向
    • x - 横向
    • 所以有 block 和 inline 是因为当文字是横向书写的,那么 block 相当于 y,inline 相当与 x,而竖写的文字则 block 相当与 x,inline 相当于 y,这样会比较灵活。
animation-timeline: scroll(root block); 
/* nearest, root, self */
/* block inline y x */

然后再定义动画 keyframes 并使用 animation 属性指定动画即可,要注意的是这里 animation 就不能指定时间了:

@keyframes move200 {
  0% {
    translate: 0 0;
  }
  100% {
    translate: 0 -200px;
  }
}

.someElement {
  animation: move200 linear;
}

如果要按元素位置来执行动画,可以使用 view() 函数,view 也接收两个参数:

  • 第一个参数也是指定方向,可以取同样的 block、inline、y和x
  • 第二个参数指定 offset,即元素滚动执行动画的区间,不指定则是整个滚动区域,可以指定两个值指定开始和结束区域。
animation-timeline: view(block 50% 10%);

使用 view() 实现动画,还可以指定 animation-range 属性,来定义元素自身出现在什么位置开始动画,在什么位置结束动画,它可以取的值有:

  • entry - 元素上边界开始进入到滚动的可视区域中到完全进入结束
  • exit - 元素开始离开滚动可视区域到完全离开结束
  • entry-crossing - 元素从进入开始到完全进入之间
  • exit-crossing - 元素离开开始到完全离开之间
  • cover - 元素上边界进入到滚动区域,到下边界完全离开。
  • contain - 元素完全在滚动区域之中。

可以分别指定开始和结束区间,每个关键字后面可以跟上百分比偏移,例如:animation-range: entry 0% entry 100% 表示元素进入动画,从上边界进入开始,到下边界与浏览器底部相交结束,如果开始和结束的关键字相同,偏移为 0% 到 100%,可以只写关键字,例如这里可以简写为 entry:

animation-range: entry 0% entry 100%
animation-range: entry

这张图描述了 animation-range 各个值的范围,这些关键字指定的区域会有重合,可以看情况选择最贴近动画执行过程的。

兼容性

目前 CSS 滚动驱动动画在 Chrome 和 Edge 浏览器中实现了,其他浏览器兼容情况可以参考 can i use 网站:

CSS 滚动驱动动画兼容性

示例

我们来看两个具体的例子,第一个例子实现了两个图片视差滚动的效果,使用 scroll() 根据根元素的滚动执行动画,第一个图片的动画使用了 translate () 属性来加速它的上移。

第二个例子利用了 view() 实现了图片的进入特效,在它进入时放大、透明度设置为 0,然后完全进入并到 50% 的位置时还原为正常状态,这样就有了一个从放大到缩小的动画。

小结

好了,这个就是 CSS 滚动驱动动画的介绍,你学会了吗?如果有帮助请三连并关注,想学更多的开发知识,可以在评论区留言,感谢观看!

2 分钟学会纯 CSS 滚动动画:根据滚动条或元素位置执行动画

HTMX 是一个主打增强 HTML 功能的前端框架,通过给 HTML 添加自定义的属性,让任何元素都可以发送 Ajax 请求,实现 CSS 过渡、Web Socket 和服务端事件响应等常见的 Web 端功能,而不需要我们编写额外的 JS 代码。

这个设计哲学就符合了 HTML 的 Hypertext 特性,也就是使用纯文本的方式来编写网页内容。

htmx 的包体积很小,只有 14k,但用它可以实现常见的前端应用:例如网站、单页应用、实时应用等等。

要使用 htmx,只需要引入它的库即可:

<script src="https://unpkg.com/htmx.org@1.9.10"></script>

发送 HTTP 请求

要发送 HTTP 请求,可以给触发的元素添加 hx-get、hx-post 等属性,分别发送 GET、POST 请求,HTMX 默认会在鼠标点击的时候触发:

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  >
  加载 Todos
</button>

之后通过 hx-target 指定要替换的页面元素,一般通过 id 来查找:

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  hx-target="#todo-list"
>

更新页面

之后我们可以定义一个要显示请求数据的 HTML 元素,并指定 ID 属性:

<div id="todo-list"></div>

这样服务端返回的数据就会放到这里边。htmx 建议后端直接返回 HTML 内容,这样可以拿来就用。

htmx 默认会把数据放到元素内部,我们可以通过 hx-swap 来指定其它的替换方式,默认是innerHTML:

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  hx-target="#todo-list"
  hx-swap="innerHTML"
>

也可以指定其他值:

outerHTML:替换整个元素。

afterBegin: 在元素内部开头插入

beforeBegin:在元素外部上方插入

beforeEnd:在元素内部结尾插入

afterend:在元素外部下方插入

delete: 删除元素

none:不添加内容

加载状态

要显示加载状态,可以给元素设置 htmx-indicator class,htmx 会自动控制它的显示与隐藏:

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  hx-target="#todo-list"
  hx-swap="innerHTML"
  >
  加载 Todos <span class="htmx-indicator">...</span>
</button>

自定义事件触发

如果要修改htmx默认的鼠标点击触发事件,可以配置 hx-trigger,例如在鼠标移上去时触发事件

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  hx-target="#todo-list"
  hx-swap="innerHTML"
  hx-trigger="mouseenter"
>
  加载 Todos <span class="htmx-indicator">...</span>
</button>

事件 Modifiers

htmx 也支持给事件添加修饰符,配置延迟,或者事件是不是之触发一次:

<button
  hx-get="https://jsonplaceholder.typicode.com/todos"
  hx-target="#todo-list"
  hx-swap="innerHTML"
  hx-trigger="mouseenter delay:1s once"
>
  加载 Todos <span class="htmx-indicator">...</span>
</button>

使用 Extensions(handlebars)

htmx 支持 Extensions 扩展来实现更多功能,如果后端返回 JSON 格式数据,可以利用 client-side-templates 插件,配合 handlebars 模板引擎来渲染:

<script src="https://unpkg.com/htmx.org/dist/ext/client-side-templates.js"></script>
<script src="https://cdn.jsdelivr.net/npm/handlebars@latest/dist/handlebars.js"></script>

通过 script 引入相关的库后,在需要使用插件的元素外层元素中:

  • 添加 hx-ext 属性,值为插件名。
  • 然后配置 handlebars-array-template 值为自定义的模板 id,这个用于处理服务端返回数组 JSON 数据,如果是单个对象,可以把属性名中的 array去掉。
  • 之后使用 template 定义模板,id指定为 handlebars-array-template 中配置的,之后在里边编写模板即可。
  • 最后 id 为 todo-list 的 div 会用模板中的格式进行展示。
<div hx-ext="client-side-templates">
  <button
    hx-get="https://jsonplaceholder.typicode.com/todos"
    hx-target="#todo-list"
    hx-swap="innerHTML"
    handlebars-array-template="todo-list-template"
    hx-trigger="mouseenter delay:1s once"
  >
    加载 Todos <span class="htmx-indicator">...</span>
  </button>
  <div id="todo-list"></div>
  <template id="todo-list-template">
    <ul>
      {{#each this}}
      <li>{{title}}</li>
      {{/each}}
    </ul>
  </template>
</div>

演示

看一下最终演示代码,从 jsonplaceholder 获取 todos 列表后,获取 json 数据,然后通过 handlebars 渲染所有的 todo title 也就是标题属性的内容。

小结

好了,这个就是 htmx 的介绍,你学会了吗?如果有帮助请三连并关注,想学更多的开发知识,可以在评论区留言,感谢观看!

3分钟了解 HTMX

最新博客 

当我想用 CSS 写一个新 CSS Logo 的时候...

张旭乾
软件工程师 / B站UP主

按照小伙伴们的请求,我用 CSS 写了一个新的 CSS Logo。

一开始,我想从它的官方库里找找,看看有没有直接用 CSS 写好的源码,发现没有,就找了最容易查看细节的 SVG 的文件。

把它导入 figma 之后,发现啥用也没有,我以为能直接看背景矩形的圆角,发现无论是这个背景还是 CSS 文字都是路径,没办法直接测量圆角。

然后我又想看一下 CSS 与边框的距离,发现这些数字也不是挺精确...大概 34px 吧,不知道是不是软件的问题,算啦,就简单粗略的还原一下吧。圆角的问题,这里我直接覆盖一个新的矩形,调一下透明度,然后调整圆角,直到和 logo 的圆角看起来一致就好了,大概 68px,这里注意一下,CSS 最后一个 S 的弧度和这个圆角似乎也保持了一致。再看宽度和高度是 440px。背景紫色是 #663399,这个官方仓库也写明了。

升级 Docusaurus 到 3.6,打包速度只需 5 秒钟

张旭乾
软件工程师 / B站UP主

这几天我把 Docusaurus 升级到了 3.6,主要是因为这个版本引入了 Rspack 和 SWC 等库,把打包速度提升了好几倍。以前打包大概要一两分钟,现在只需要五六秒就搞定了!

新的打包库, Rspadck, SWC, Lightning CSS

升级过程其实很简单,就是在 package.json 里把版本号改成最新的 3.6.1(当下最新版)。

CSS 动画完全指南

张旭乾
软件工程师 / B站UP主

随着现代网页设计的发展,CSS 动画已逐渐成为构建用户体验良好、互动性强的网站的关键。相比于静态的页面布局,动画能为用户带来更丰富的视觉体验,也能帮助网页更好地传达信息。

那么,为什么要用 CSS 动画呢?简单来说,CSS 动画可以通过视觉效果引导用户注意页面上的重要内容,例如按钮、链接、图标等,使用户的交互体验更加直观、自然。通过适当的动画设计,页面可以显得更具活力和吸引力,提高用户的留存率与参与度。

CSS 动画在网页中的应用也变得越来越重要。无论是加载动画、鼠标悬停效果,还是页面滚动时的动态内容展示,CSS 动画都能够轻松实现。再由于 CSS 动画轻量和高效的特性,我们可以在不影响页面性能的前提下,增强网站的互动性与用户体验。

这篇文章将详细介绍 CSS 动画的基础知识、关键技巧和常见应用,帮助初学者全面掌握 CSS 动画的使用方法,使大家能够轻松地为网页添加动态效果,提升网页开发和设计的专业性以及吸引力。

什么是CSS动画?

CSS 动画是通过定义一系列关键帧或过渡效果,使网页中的元素在指定时间内发生变化的一种技术。它能让网页元素平滑地改变属性,例如位置、大小、颜色、透明度等。

在现代网页设计中,CSS 动画有多种用途,常见的包括:

  • 加载动画:帮助用户了解页面正在加载,可以缓解因为等待而带来的焦虑感。
  • 交互效果:如按钮悬停、点击效果等,当用户与页面交互时,动画可以反馈出响应状态,提升用户的互动体验。
  • 滚动效果:在页面滚动时展示的动画内容,使得页面不再是静态的、单一的文本和图片,增加了视觉层次感。

10 个 CSS 1 行代码技巧

张旭乾
软件工程师 / B站UP主

在前端开发过程中,利用 CSS 一行代码技巧可以解决一些常见问题,提高编码效率,使样式设置更加简洁。本文将分享 10 个 CSS 一行代码技巧。

1. 居中对齐

居中对齐是 CSS 中的常见需求。通过一行 CSS 代码,可以实现元素的水平垂直居中。

display: grid; place-items: center;

12个 JavaScript 一行代码技巧

张旭乾
软件工程师 / B站UP主

JavaScript 是一种功能强大的编程语言,我们可以通过使用一行代码实现很多功能。在日常开发中,我们经常会遇到需要快速实现某些功能的情况。下面让我们一起看看 12个有用的 JavaScript 一行代码技巧。

1. 生成随机颜色

JavaScript 中可以通过以下方式快速生成一个随机颜色:

let randomColor = "#" + Math.floor(Math.random()*16777215).toString(16);

这行代码会生成一个六位的十六进制数,可以用作 CSS 颜色值。

2. 获取 URL 参数

如果你想获取 URL 参数,可以通过以下一行代码实现:

Vite 和 Webpack 的比较与区别

张旭乾
软件工程师 / B站UP主

前言

在现代前端开发中,打包工具已经成为不可或缺的一部分。它们可以将多个文件合并为一个或多个文件,使前端应用的加载和运行速度更快。目前,Vite 和 Webpack 是最受欢迎的打包工具之一。本文将介绍它们之间的比较和区别,以帮助你选择适合自己项目的工具。

什么是 Vite?

Vite 是一种新型的前端构建工具,旨在提高开发过程中的开发体验和构建速度。它支持所有的现代前端框架,如 Vue、React、Angular等,以及原生的 HTML/CSS/JS 应用。

Vite 的核心理念是“快速开发”。它采用了一种新的开发方式,即在开发过程中不需要事先打包应用程序,而是在应用程序运行时即时编译和构建。这种方式使得开发者可以更快地编写代码,而无需等待长时间的编译和构建过程。

什么是 Webpack?

Webpack 是一个广泛使用的打包工具,为现代 Web 应用程序提供了强大的静态资源管理功能。Webpack 可以将多个文件打包成一个或多个文件,并使它们在浏览器中快速加载。Webpack 是一个高度可配置的工具,因此可以根据项目的需要进行定制。

Webpack 的核心理念是“模块化”。它支持使用各种语言和框架编写模块,并将它们打包成可在浏览器中使用的 JavaScript 文件。Webpack 还提供了强大的插件系统,可以扩展其功能。

如何使用 JSX 编写 React 组件

张旭乾
软件工程师 / B站UP主

在 React 中,我们通常使用 JSX 来编写组件。JSX 是一种类似 HTML 的语法,它可以帮助我们更方便地编写组件,并且可以使代码更加易读和易于维护。在本文中,我们将介绍如何使用 JSX 编写 React 组件,并且将介绍 JSX 与 HTML 的区别、渲染列表、条件渲染、注册事件和传递 Props 相关知识。

React 框架简介

React 是一个由 Facebook 开发的用于构建用户界面的 JavaScript 库。它采用组件化的开发模式,使得开发者可以将一个 Web 应用程序拆分成多个组件,每个组件负责不同的功能,从而使得开发、测试和维护变得更加容易。

React 的主要特点是高效、可重用和灵活。它采用了 Virtual DOM 技术,可以最小化 DOM 操作,从而提高性能。另外,React 还拥有丰富的生态系统,包括 React Router、Redux、React Native 等等,可以帮助开发者更加高效地构建 Web 应用程序、移动应用程序和桌面应用程序等等。

10 种方法使用 CSS 水平居中一个元素

张旭乾
软件工程师 / B站UP主

我们在前端开发中,经常会有居中某个元素的需求。因为 CSS 对于居中的方式有多种多样,在不同场景下有不同的效果,需要特别记住它们的应用场景才能够正常的居中元素。那么这篇文章,我们就看一下在 CSS 中,水平居中一个元素的不同方法和技巧,帮助你在前端开发中更加游刃有余。

使用 text-align 居中行内元素

text-align 不仅可以居中文本,还可以居中行内元素(如文本或图片)。把父元素的 'text-align' 设置为 center,然后把子元素的 display 属性设置为 inline 就可以了。

.parent-element {
text-align: center;
}

配置 Vite alias 别名导入,避免冗长的相对路径

张旭乾
软件工程师 / B站UP主

在开发大型 Vue 项目的时候,有的组件会嵌套的很深,如果需要引入外层其他目录的组件,需要编写很长一段相对路径。假如有如下组件目录结构:

/Layout/Header/NavBar.vue
/Base/BaseLink.vue

如果在 NavBar 中引入 BaseLink 组件,需要使用下面的路径进行导入:

NavBar.vue
<script>
import BaseLink from '../../Base/BaseLink.vue';
</script>

这里使用了两个 ../ 才访问到 Base 目录,如果这个时候,我们给 ../../ 设置一个别名,例如 @,那么就可以使导入路径更简洁,变成:

@/Base/BaseLink.vue

Vite 支持设置路径别名,来支持这种形式的导入。

Vue3 表单提交事件处理

张旭乾
软件工程师 / B站UP主

这篇文章我们看一下对于表单整体的提交事件应该如何处理,并引入一个事件修饰符的概念。 我们继续使用上篇文章的项目示例,这里我把 html 中,class 为 form 的 div 改成了 form 元素,CSS 的样式也作了对应的调整。

<div class="form">
->
<form></form>
</div>

现在,我们在 form 元素的结束标签之前,添加一个 button 按钮元素,作为表单的提交按钮,点击它表单就会提交。

<textarea id="intro" rows="10" v-model="intro"></textarea>
<!-- 在这里添加 -->
<button type="submit">提交</button>