当前位置: 首页 > news >正文

【小程序 - 加强】自定义组件、使用npm包、全局数据共享、分包_05

目录

一、自定义组件

1. 组件的创建与引用

1.1 创建组件

1.2 引用组件

1.2.1 局部引用组件

1.2.2 全局引用组件

1.2.3 全局引用 VS 局部引用

1.2.4 组件和页面的区别

2. 样式

2.1 组件样式隔离

2.2 组件样式隔离的注意点

2.3 修改组件的样式隔离选项

2.4 styleIsolation 的可选值

3. 数据、方法和属性

3.1 data 数据

3.2 methods方法

3.3 properties 属性

3.4 data 和 properties 的区别

3.5 使用 setData 修改 properties 的值

4. 数据监听器

4.1 什么是数据监听器

4.2 数据监听器的基本用法

4.3 监听对象属性的变化

5. 数据监听器 - 案例

1. 案例效果

2. 渲染 UI 结构

3. 定义 button 的事件处理函数

4. 监听对象中指定属性的变化

5. 监听对象中所有属性的变化

6. 纯数据字段

6.1 什么是纯数据字段

6.2 使用规则

6.3 使用纯数据字段改造数据监听器案例

7. 组件的生命周期

7.1 组件全部的生命周期函数

7.2 组件主要的生命周期函数

7.3 lifetimes 节点

8. 组件所在页面的生命周期

8.1 什么是组件所在页面的生命周期

8.2 pageLifetimes 节点

8.3 生成随机的 RGB 颜色值

9. 插槽

9.1 什么是插槽

9.2. 单个插槽

9.3 启用多个插槽

9.4 定义多个插槽

9.5 使用多个插槽

10. 父子组件之间的通信

10.1 父子组件之间通信的 3 种方式

10.1.1 属性绑定

10.1.2 事件绑定

10.1.3 获取组件实例

11. behaviors

11.1 什么是 behaviors

11.2 behaviors 的工作方式

11.3 创建 behavior

11.4 导入并使用 behavior

11.5 behavior 中所有可用的节点

11.6 同名字段的覆盖和组合规则*

💠 自定义组件小结

二、使用npm包

1. 小程序对 npm 的支持与限制

2. Vant Weapp

2.1 什么是 Vant Weapp

2.2 安装 Vant 组件库

2.3. 使用 Vant 组件

2.4 定制全局主题样式

3. API Promise化

3.1 基于回调函数的异步 API 的缺点

3.2 什么是 API Promise 化

3.3 实现 API Promise 化

3.4 调用 Promise 化之后的异步 API

三、全局数据共享

1. 什么是全局数据共享

2. 小程序中的全局数据共享方案

2.1 MobX

2.1.1 安装 MobX 相关的包

2.1.2 创建 MobX 的 Store 实例

2.1.3 将 Store 中的成员绑定到页面中

2.1.4 在页面上使用 Store 中的成员

2.1.5 将 Store 中的成员绑定到组件中

2.1.6 在组件中使用 Store 中的成员

四、分包

1. 基础概念

1.1 什么是分包

1.2 分包的好处

1.3 分包前项目的构成

1.4 分包后项目的构成

1.5 分包的加载规则

1.6 分包的体积

2. 使用分包

2.1 配置方法

2.2 打包原则

2.3 引用原则

3. 独立分包

3.1 什么是独立分包

3.2 独立分包和普通分包的区别

3.3 独立分包的应用场景

3.4 独立分包的配置方法

3.5 引用原则

4. 分包预下载

4.1 什么是分包预下载

4.2 配置分包的预下载

4.3 分包预下载的限制

💠 案例 - 自定义 tabBar

💠 小结一下


一、自定义组件

1. 组件的创建与引用

1.1 创建组件

①在项目的根目录中,鼠标右键,创建 components -> test 件夹

②在新建的 components -> test 文件夹上,鼠标右键,点击“ 新建 Component 

③键入组件的名称之后回车,会自动生成组件对应的 4 个文件,后缀名分别为 .js,.json, .wxml 和 .wxss

注意:为了保证目录结构的清晰,建议把不同的组件,存放到单独目录中,例如:

1.2 引用组件

组件的引用方式分为“局部引用”和“全局引用”,顾名思义: 

● 局部引用:组件只能在当前被引用的页面内使用

● 全局引用:组件可以在每个小程序页面中使用

1.2.1 局部引用组件

在页面的 .json 配置文件中引用组件的方式,叫做“局部引用”。示例代码如下:

1.2.2 全局引用组件

app.json 全局配置文件中引用组件的方式,叫做“全局引用”。示例代码如下:

1.2.3 全局引用 VS 局部引用

根据组件的使用频率范围,来选择合适的引用方式:

● 如果某组件在多个页面中经常被用到,建议进行“全局引用”

● 如果某组件只在特定的页面中被用到,建议进行“局部引用”

1.2.4 组件和页面的区别

从表面来看,组件和页面都是由 .js.json.wxml .wxss 这四个文件组成的。但是,组件和页面的 .js .json 文件有明显的不同:

● 组件的 .json 文件中需要声明 "component": true 属性

● 组件的 .js 文件中调用的是 Component() 函数

● 组件的事件处理函数需要定义到 methods 节点中

2. 样式

2.1 组件样式隔离

默认情况下,自定义组件的样式只对当前组件生效,不会影响到组件之外的 UI 结构,如图所示:

组件 A 的样式不会影响组件 C 的样式

组件 A 的样式不会影响小程序页面的样式

小程序页面的样式不会影响组件 A C 的样式

好处:

① 防止外界的样式影响组件内部的样式

② 防止组件的样式破坏外界的样式

2.2 组件样式隔离的注意点

● app.wxss 中的全局样式对组件无效

● 只有 class 选择器会有样式隔离效果,id 选择器、属性选择器、标签选择器不受样式隔离的影响

建议:在组件引用组件的页面中建议使用 class 选择器,不要使用 id、属性、标签选择器

2.3 修改组件的样式隔离选项

默认情况下,自定义组件的样式隔离特性能够防止组件内外样式互相干扰的问题。但有时,我们希望在外界能够控制组件内部的样式,此时,可以通过 styleIsolation 修改组件的样式隔离选项,用法如下:

2.4 styleIsolation 的可选值

可选值

默认值

描述

isolated

表示启用样式隔离,在自定义组件内外,使用 class 指定的样式将不会相互影响

apply-shared

表示页面 wxss 样式将影响到自定义组件,但自定义组件 wxss 中指定的样式不会影响页面

shared

表示页面 wxss 样式将影响到自定义组件,自定义组件 wxss 中指定的样式也会影响页面和其他设置了 apply-shared shared 的自定义组件

3. 数据、方法和属性

3.1 data 数据

在小程序组件中,用于组件模板渲染私有数据,需要定义到 data 节点中,示例如下:

3.2 methods方法

在小程序组件中,事件处理函数自定义方法需要定义到 methods 节点中,示例代码如下:

3.3 properties 属性

在小程序组件中,properties 是组件的对外属性,用来接收外界传递到组件中的数据,示例代码如下:

3.4 data properties 的区别

在小程序的组件中,properties 属性和 data 数据的用法相同,它们都是可读可写的,只不过:

● data 更倾向于存储组件的私有数据

● properties 更倾向于存储外界传递到组件中的数据

3.5 使用 setData 修改 properties 的值

由于 data 数据properties 属性在本质上没有任何区别,因此 properties 属性的值也可以用于页面渲染,或使用 setData properties 中的属性重新赋值,示例代码如下:

4. 数据监听器

4.1 什么是数据监听器

数据监听器用于监听和响应任何属性和数据字段的变化,从而执行特定的操作。它的作用类似于 vue 中的 watch 侦听器。在小程序组件中,数据监听器的基本语法格式如下:

4.2 数据监听器的基本用法

组件的 UI 结构如下:

组件的 .js 文件代码如下:

4.3 监听对象属性的变化

数据监听器支持监听对象中单个多个属性的变化,示例语法如下:

5. 数据监听器 - 案例

1. 案例效果

2. 渲染 UI 结构

3. 定义 button 的事件处理函数

4. 监听对象中指定属性的变化

5. 监听对象中所有属性的变化

如果某个对象中需要被监听的属性太多,为了方便,可以使用通配符 ** 监听对象中所有属性的变化,示例代码如下:

6. 纯数据字段

6.1 什么是纯数据字段

概念:纯数据字段指的是那些不用于界面渲染的 data 字段

应用场景:例如有些情况下,某些 data 中的字段既不会展示在界面上也不会传递给其他组件,仅仅在当前组件内部使用。带有这种特性的 data 字段适合被设置为纯数据字段。

好处:纯数据字段有助于提升页面更新的性能

6.2 使用规则

Component 构造器的 options 节点中,指定 pureDataPattern 为一个正则表达式,字段名符合这个正则表达式的字段将成为纯数据字段,示例代码如下:

6.3 使用纯数据字段改造数据监听器案例

7. 组件的生命周期

7.1 组件全部的生命周期函数

小程序组件可用的全部生命周期如下表所示:

生命周期函数

参数

描述说明

created

在组件实例刚刚被创建时执行

attached

在组件实例进入页面节点树时执行

ready

在组件在视图层布局完成后执行

moved

在组件实例被移动到节点树另一个位置时执行

detached

在组件实例被从页面节点树移除时执行

error

Object Error

每当组件方法抛出错误时执行

注:关于组件生命周期函数执行的时机说明

✔ created

在执行created生命周期函数时,证明组件刚被创建好,但是这个组件还没有被放到小程序页面中进行渲染(显示),此时我们能做的事情是比较少的

✔ attached

组件创建好以后,紧接着就需要把创建好的组件放进页面节点树里,那么组件刚一被放进节点树的时候,此时就会执行attached生命周期函数

✔ ready

在执行attached期间,组件只是刚被放进页面的UI结构中,但是这个组件还未被渲染,接下来就是组件在页面上来被真正的渲染出来,当组件被渲染完成以后会执行组件的ready生命周期函数,所以ready生命周期函数执行的时机就是在组件刚被渲染完成之后

7.2 组件主要的生命周期函数

在小程序组件中,最重要的生命周期函数有 3 个,分别是 createdattacheddetached。它们各自的特点如下:

组件实例刚被创建好的时候,created 生命周期函数会被触发

● 此时还不能调用 setData

● 通常在这个生命周期函数中,只应该用于给组件的 this 添加一些自定义的属性字段

在组件完全初始化完毕、进入页面节点树后attached 生命周期函数会被触发

● 此时, this.data 已被初始化完毕

● 这个生命周期很有用,绝大多数初始化的工作可以在这个时机进行(例如发请求获取初始数据)

在组件离开页面节点树后detached 生命周期函数会被触发

● 退出一个页面时,会触发页面内每个自定义组件的 detached 生命周期函数

● 此时适合做一些清理性质的工作

7.3 lifetimes 节点

在小程序组件中,生命周期函数可以直接定义在 Component 构造器的第一级参数中,可以在 lifetimes 字段内进行声明(这是推荐的方式,其优先级最高)。示例代码如下:

8. 组件所在页面的生命周期

8.1 什么是组件所在页面的生命周期

有时,自定义组件的行为依赖于页面状态的变化,此时就需要用到组件所在页面的生命周期

也就是说,在组件的js文件中,可以监听页面状态的变化即可以监听组件所在页面的生命周期,然后去执行一些操作

例如:每当触发页面的 show 生命周期函数的时候,我们希望能够重新生成一个随机的 RGB 颜色值。

下面我们来看一下,在组件里面都可以访问页面的哪些生命周期函数

在自定义组件中,组件所在页面的生命周期函数有如下 3 个,分别是:

生命周期函数

参数

描述

show

组件所在的页面被展示时执行

hide

组件所在的页面被隐藏时执行

resize

Object Size

组件所在的页面尺寸变化时执行

8.2 pageLifetimes 节点

组件所在页面的生命周期函数,需要定义在 pageLifetimes 节点中,示例代码如下:

8.3 生成随机的 RGB 颜色值

9. 插槽

9.1 什么是插槽

在自定义组件的 wxml 结构中,可以提供一个 <slot> 节点(插槽),用于承载组件使用者提供的 wxml 结构

9.2. 单个插槽

在小程序中,默认每个自定义组件中只允许使用一个 <slot> 进行占位,这种个数上的限制叫做单个插槽。

9.3 启用多个插槽

在小程序的自定义组件中,需要使用多 <slot> 插槽时,可以在组件的 .js 文件中,通过如下方式进行启用。

9.4 定义多个插槽

可以在组件的 .wxml 中使用多个 <slot> 标签,以不同的 name 来区分不同的插槽。示例代码如下:

9.5 使用多个插槽

在使用带有多个插槽的自定义组件时,需要用 slot 属性来将节点插入到不同的 <slot> 中。示例代码如下:

10. 父子组件之间的通信

10.1 父子组件之间通信的 3 种方式

① 属性绑定

● 用于父组件向子组件的指定属性设置数据,仅能设置 JSON 兼容的数据

② 事件绑定

● 用于子组件向父组件传递数据,可以传递任意数据

③ 获取组件实例

● 父组件还可以通过 this.selectComponent() 获取子组件实例对象

● 这样就可以直接访问子组件的任意数据和方法

10.1.1 属性绑定

属性绑定用于实现父向子传值,而且只能传递普通类型的数据,无法将方法传递给子组件父组件的示例代码如下:

子组件在 properties 节点中声明对应的属性并使用。示例代码如下:

10.1.2 事件绑定

事件绑定用于实现子向父传值,可以传递任何类型的数据。使用步骤如下:

父组件js 中,定义一个函数,这个函数即将通过自定义事件的形式,传递给子组件

父组件wxml 中,通过自定义事件的形式,将步骤 1 中定义的函数引用,传递给子组件

子组件js 中,通过调用 this.triggerEvent('自定义事件名称', { /* 参数对象 */ }) ,将数据发送到父组件

父组件js 中,通过 e.detail 获取到子组件传递过来的数据

步骤1父组件js 中,定义一个函数,这个函数即将通过自定义事件的形式,传递给子组件。

步骤2:在父组件wxml 中,通过自定义事件的形式,将步骤 1 中定义的函数引用,传递给子组件。

步骤3:在子组件js 中,通过调用 this.triggerEvent(自定义事件名称’, { /* 参数对象 */ }) ,将数据发送到父组件。

步骤4:在父组件js 中,通过 e.detail 获取到子组件传递过来的数据。

10.1.3 获取组件实例

可在父组件里调用 this.selectComponent("idclass选择器") ,获取子组件的实例对象,从而直接访问子组件的任意数据和方法。调用时需要传入一个选择器,例如 this.selectComponent(".my-component")

11. behaviors

11.1 什么是 behaviors

behaviors 是小程序中,用于实现组件间代码共享的特性,类似于 Vue.js 中的 “mixins”

11.2 behaviors 的工作方式

每个 behavior 可以包含一组属性数据生命周期函数方法。组件引用它时,它的属性、数据和方法会被合并到组件中

每个组件可以引用多个 behaviorbehavior 也可以引用其它 behavior

11.3 创建 behavior

调用 Behavior(Object object) 方法即可创建一个共享的 behavior 实例对象,供所有的组件使用:

11.4 导入并使用 behavior

在组件中,使用 require() 方法导入需要的 behavior挂载后即可访问 behavior 中的数据或方法,示例代码如下:

11.5 behavior 中所有可用的节点

可用的节点

类型

是否必填

描述

properties

Object Map

同组件的属性

data

Object

同组件的数据

methods

Object

同自定义组件的方法

behaviors

String Array

引入其它的 behavior

created

Function

生命周期函数

attached

Function

生命周期函数

ready

Function

生命周期函数

moved

Function

生命周期函数

detached

Function

生命周期函数

11.6 同名字段的覆盖和组合规则*

组件和它引用的 behavior 可以包含同名的字段,此时可以参考如下 3 种同名时的处理规则:

同名的数据字段 (data)

同名的属性 (properties) 或方法 (methods)

同名的生命周期函数

关于详细的覆盖和组合规则,大家可以参考微信小程序官方文档给出的说明:

behaviors | 微信开放文档

💠 自定义组件小结

能够创建并引用组件

全局引用、局部引用、usingComponents

能够知道如何修改组件的样式隔离选项

options -> styleIsolation isolated, apply-shared, shared

能够知道如何定义和使用数据监听器

observers

能够知道如何定义和使用纯数据字段

options -> pureDataPattern

能够知道实现组件父子通信有哪3种方式

属性绑定、事件绑定this.selectComponent(' idclass选择器')

能够知道如何定义和使用behaviors

调用 Behavior() 构造器方法 

二、使用npm包

1. 小程序对 npm 的支持与限制

从小程序基础库版本 2.2.1 或以上、及开发者工具 1.02.1808300 或以上开始,小程序支持使用 npm 安装第三方包。

目前,小程序中已经支持使用 npm 安装第三方包,从而来提高小程序的开发效率。但是,在小程序中使用 npm 包有如下 3 个限制:

不支持依赖于 Node.js 内置库的包

某些npm包依赖于nodejs里的核心模块,如依赖于fs模块的包等,这些包就无法在小程序里使用,因为小程序并没有提供nidejs这样一个运行环境。

不支持依赖于浏览器内置对象的包

比如,jQuery,因为jQuery依赖于浏览器的window等这些内置对象。但是小程序并不提供像浏览器里这些内置对象,所以说依赖于浏览器内置对象的包,也无法在小程序中正常的运行。

不支持依赖于 C++ 插件的包

比如,npm上一些负责加密的包,它会依赖于C++的插件来提高加密的性能,但是小程序中不提供C++的运行环境,所以说在小程序也不支持依赖于 C++ 插件的包

总结:虽然 npm 上的包有千千万,但是能供小程序使用的包却“为数不多”。

2. Vant Weapp

2.1 什么是 Vant Weapp

Vant Weapp 是有赞前端团队开源的一套小程序 UI 组件库,助力开发者快速搭建小程序应用。它所使用的是 MIT 开源许可协议,对商业使用比较友好。

◼️ 官方文档地址 Vant Weapp - 轻量、可靠的小程序 UI 组件库

扫描下方的小程序二维码,体验组件库示例:

2.2 安装 Vant 组件库

在小程序项目中,安装 Vant 组件库主要分为如下 3 步:

通过 npm 安装(建议指定版本为@1.3.3

安装之前,需要在小程序根目录中打开命令行工具,使用 npm init -y 初始化一个package.json包管理文件。

构建 npm

修改 app.json

详细的操作步骤,大家可以参考 Vant 官方提供的快速上手教程:

https://youzan.github.io/vant-weapp/#/quickstart#an-zhuang

2.3. 使用 Vant 组件

安装完 Vant 组件库之后,可以在 app.json usingComponents 节点中引入需要的组件,即可在 wxml 中直接使用组件。示例代码如下:

2.4 定制全局主题样式

Vant Weapp 使用 CSS 变量来实现定制主题。 关于 CSS 变量的基本用法,请参考 MDN 文档:使用 CSS 自定义属性(变量) - CSS:层叠样式表 | MDN

app.wxss 中,写入 CSS 变量,即可对全局生效:

所有可用的颜色变量,请参考 Vant 官方提供的配置文件:https://github.com/youzan/vant-weapp/blob/dev/packages/common/style/var.less

注:page标签是小程序每个页面的根节点,所以说我们可以拿page标签定义样式变量,这样小程序每个页面都可以访问到这些CSS变量

3. API Promise化

3.1 基于回调函数的异步 API 的缺点

默认情况下,小程序官方提供的异步 API 都是基于回调函数实现的,例如,网络请求的 API 需要按照如下的方式调用:

缺点:容易造成回调地狱的问题,代码的可读性维护性差!

3.2 什么是 API Promise 化

API Promise,指的是通过额外的配置,将官方提供的、基于回调函数的异步 API升级改造为基于 Promise 的异步 API,从而提高代码的可读性、维护性,避免回调地狱的问题。

3.3 实现 API Promise 化

在小程序中,实现 API Promise 化主要依赖于 miniprogram-api-promise 这个第三方的 npm 包。它的安装和使用步骤如下:

3.4 调用 Promise 化之后的异步 API

三、全局数据共享

1. 什么是全局数据共享

全局数据共享(又叫做:状态管理)是为了解决组件之间数据共享的问题。

开发中常用的全局数据共享方案有:VuexReduxMobX 等。

2. 小程序中的全局数据共享方案

在小程序中,可使用 mobx-miniprogram 配合 mobx-miniprogram-bindings 实现全局数据共享。其中:

● mobx-miniprogram 用来创建 Store 实例对象

● mobx-miniprogram-bindings 用来Store 中的共享数据或方法绑定到组件页面

2.1 MobX
2.1.1 安装 MobX 相关的包

在项目中运行如下的命令,安装 MobX 相关的包:

注意:MobX 相关的包安装完毕之后,记得删除 miniprogram_npm 目录后,重新构建 npm

2.1.2 创建 MobX Store 实例

2.1.3 Store 中的成员绑定到页面

2.1.4 在页面上使用 Store 中的成员

2.1.5 Store 中的成员绑定到组件

2.1.6 在组件中使用 Store 中的成员

四、分包

1. 基础概念

1.1 什么是分包

分包指的是把一个完整的小程序项目,按照需求划分为不同的子包,在构建时打包成不同的分包,用户在使用时按需进行加载

1.2 分包的好处

对小程序进行分包的好处主要有以下两点:

● 可以优化小程序首次启动的下载时间

默认情况下,小程序不会对项目进行分包,所有的页面都是打包到一起的,用户在首次启动时,小程序需要把整个项目下载下来才能运行,此时项目体积会比较打,因此会导致首次启动小程序的下载时间比较长。如果采用分包的话,可以先把首页下载下来,于是就可提高小程序首次启动的下载时间。

● 在多团队共同开发时可以更好的解耦协作

比如,我们可以按照功能的不同,将小程序划分为不同的子包,由不同的人负责不同的功能,每个人负责一个分包的开发,开发效率会更高一些。

1.3 分包前项目的构成

分包前,小程序项目中所有的页面资源都被打包到了一起,导致整个项目体积过大,影响小程序首次启动的下载时间

1.4 分包后项目的构成

分包后,小程序项目由 1 个主包 + 多个分包组成:

● 主包:一般只包含项目的启动页面TabBar 页面、以及所有分包都需要用到的一些公共资源

● 分包:只包含和当前分包有关的页面和私有资源

1.5 分包的加载规则

在小程序启动时,默认会下载主包启动主包内页面

● tabBar 页面需要放到主包中

当用户进入分包内某个页面时,客户端会把对应分包下载下来,下载完成后再进行展示

● 非 tabBar 页面可以按照功能的不同,划分为不同的分包之后,进行按需下载

1.6 分包的体积

目前,小程序分包的大小有以下两个限制:

●  整个小程序所有分包大小不超过 20M(主包 + 所有分包)

● 单个分包/主包大小不能超过 2M

2. 使用分包

2.1 配置方法

2.2 打包原则

① 小程序会按 subpackages 的配置进行分包,subpackages 之外的目录将被打包到主包中

② 主包也可以有自己的 pages(即最外层的 pages 字段)

③ tabBar 页面必须在主包内

④ 分包之间不能互相嵌套

2.3 引用原则

主包无法引用分包内的私有资源

分包之间不能相互引用私有资源

分包可以引用主包内的公共资源

3. 独立分包

3.1 什么是独立分包

独立分包本质上也是分包,只不过它比较特殊,可以独立于主包和其他分包而单独运行

3.2 独立分包和普通分包的区别

最主要的区别:是否依赖于主包才能运行

● 普通分包必须依赖于主包才能运行

● 独立分包可以在不下载主包的情况下,独立运行

3.3 独立分包的应用场景

开发者可以按需,将某些具有一定功能独立性的页面配置到独立分包中。原因如下:

● 当小程序从普通的分包页面启动时,需要首先下载主包

● 而独立分包不依赖主包即可运行,可以很大程度上提升分包页面的启动速度

注意:一个小程序中可以有多个独立分包。

3.4 独立分包的配置方法

3.5 引用原则

独立分包和普通分包以及主包之间,是相互隔绝的,不能相互引用彼此的资源!例如:

① 主包无法引用独立分包内的私有资源

② 独立分包之间,不能相互引用私有资源

③ 独立分包和普通分包之间,不能相互引用私有资源

④ 特别注意:独立分包中不能引用主包内的公共资源普通分包可以

4. 分包预下载

4.1 什么是分包预下载

分包预下载指的是:在进入小程序的某个页面时,由框架自动预下载可能需要的分包,从而提升进入后续分包页面时的启动速度。

4.2 配置分包的预下载

预下载分包的行为,会在进入指定的页面时触发。在 app.json 中,使用 preloadRule 节点定义分包的预下载规则,示例代码如下:

4.3 分包预下载的限制

同一个分包中的页面享有共同的预下载大小限额 2M,例如:

💠 案例 - 自定义 tabBar

✔ 案例效果

在此案例中,用到的主要知识点如下:

● 自定义组件

● Vant 组件库

● MobX 数据共享

● 组件样式隔离

● 组件数据监听器

● 组件的 behaviors

● Vant 样式覆盖

✔ 实现步骤

自定义 tabBar 分为 3 大步骤,分别是:

配置信息

添加 tabBar 代码文件

编写 tabBar 代码

详细步骤,可以参考小程序官方给出的文档:自定义 tabBar | 微信开放

主要代码如下: 

* app.json

{"pages": ["pages/home/home","pages/message/message","pages/contact/contact"],"window": {"backgroundTextStyle": "light","navigationBarBackgroundColor": "#13A7A0","navigationBarTitleText": "WeChat","navigationBarTextStyle": "black"},"tabBar": {"custom": true,"list": [{"pagePath": "pages/home/home","text": "首页","iconPath": "/images/tabs/home.png","selectedIconPath": "/images/tabs/home-active.png"},{"pagePath": "pages/message/message","text": "消息","iconPath": "/images/tabs/message.png","selectedIconPath": "/images/tabs/message-active.png"},{"pagePath": "pages/contact/contact","text": "联系我们","iconPath": "/images/tabs/contact.png","selectedIconPath": "/images/tabs/contact-active.png"}]},"sitemapLocation": "sitemap.json","usingComponents": {"van-button": "@vant/weapp/button/index","my-numbers": "./components/numbers/numbers","van-tabbar": "@vant/weapp/tabbar/index","van-tabbar-item": "@vant/weapp/tabbar-item/index"}
}

* custom-tab-bar/index.wxml

<!--custom-tab-bar/index.wxml-->
<!-- <text>这是自定义的TabBar</text> --><!-- {{active}}属性绑定,该值来自于组件脚本文件index.js中从store映射过来的activeTabBarIndex值即active: 'activeTabBarIndex' -->
<!-- Tabbar 标签栏组件中的Tabbar属性active-color	选中标签的颜色,默认#7d7e80 -->
<van-tabbar active="{{active}}" bind:change="onChange" active-color="#13A7A0">
<!-- 按需渲染数字徽标—— item.info ? item.info : '' ——使用三元表达式判断哪个tabbar上有徽标info属性 --><van-tabbar-item wx:for="{{list}}" wx:key="index" info="{{item.info ? item.info : ''}}"><image slot="icon" src="{{item.iconPath}}" mode="aspectFit" style="width: 25px; height: 25px;" /><image slot="icon-active" src="{{item.selectedIconPath}}" mode="aspectFit" style="width: 25px; height: 25px;" />{{item.text}}</van-tabbar-item>
</van-tabbar>

* custom-tab-bar/index.wxml

// custom-tab-bar/index.js
// storeBindingsBehavior 起到一个桥梁作用:将store里的数据或成员映射到当前组件里,来进行使用
import { storeBindingsBehavior } from 'mobx-miniprogram-bindings'
// store 数据源
import { store } from '../store/store'Component({options: {// 在自定义组件中使用 Vant Weapp 组件时,如果想要在页面的样式文件中覆盖组件的样式需开启// 样式覆盖:https://youzan.github.io/vant-weapp/#/custom-style#jie-chu-yang-shi-ge-chistyleIsolation: 'shared'},behaviors: [storeBindingsBehavior], // 通过 storeBindingsBehavior 来实现自栋动绑定// 声明一个配置对象storeBindings: {// 数据源:指定要绑定的数据源store,// 字段数据:指定要绑定的字段数据fields: {sum: 'sum',active: 'activeTabBarIndex'},// 方法:指定要绑定的方法actions: {updateActive: 'updateActiveTabBarIndex'},},// 数据监听器observers: {// 监听sum获取sum的最新值val'sum': function (val) {this.setData({'list[1].info': val})}},/*** 组件的属性列表*/properties: {},/*** 组件的初始数据*/data: {// 把active抽离到store里进行公共存储并命名为activeTabBarIndex,所以这里就不需要再定义了,直接使用从store映射过来的activeTabBarIndex即active: 'activeTabBarIndex'// active: 0,"list": [{"pagePath": "/pages/home/home","text": "首页","iconPath": "/images/tabs/home.png","selectedIconPath": "/images/tabs/home-active.png"},{"pagePath": "/pages/message/message","text": "消息","iconPath": "/images/tabs/message.png","selectedIconPath": "/images/tabs/message-active.png",info: 0},{"pagePath": "/pages/contact/contact","text": "联系我们","iconPath": "/images/tabs/contact.png","selectedIconPath": "/images/tabs/contact-active.png"}]},/*** 组件的方法列表*/methods: {onChange(event) {// event.detail 的值为当前选中项的索引// 因为我们把在index.js文件中data里定义的active放在了store里,这里并未定义active,所以this.setData({ active: event.detail })就不使用了,直接使用从store里映射过来的action方法即可// this.setData({ active: event.detail })this.updateActive(event.detail)// 切换tab页面实现跳转wx.switchTab({url: this.data.list[event.detail].pagePath,})},}
})

* custom-tab-bar/index.wxss

/* custom-tab-bar/index.wxss *//* vant的Tabbar 标签栏组件图标跟文字之间margin过大,显示Tabbar徽标时越过当前Tabbar的范围,需要重置为0 */
/* 在自定义组件中使用 Vant Weapp 组件时,如果想要在页面的样式文件中覆盖组件的样式需要在组件的js文件中开启styleIsolation: 'shared' 配置项,如不开启,无法覆盖,样式不生效*/
/*  样式覆盖:https://youzan.github.io/vant-weapp/#/custom-style#jie-chu-yang-shi-ge-chi */
.van-tabbar-item {--tabbar-item-margin-bottom: 0; 
}

* store/store.js

// 在这个 JS 文件中,专门来创建 Store 的实例对象
// 分析:按需导入mobx-miniprogram包的成员:observable 和 action 方法
import { observable, action } from 'mobx-miniprogram'// observable方法用来创建 Store 的实例对象 
// 分析:调用observable()方法得到一个实例对象,并按需导出,外界在使用时,导入store实例即可使用其中的数据与方法
export const store = observable({// 数据字段numA: 1,numB: 2,activeTabBarIndex: 0,// 计算属性// 分析:计算属性sum前的修饰符get表示当前计算属性的值是只读的 ——你只能获取它的值,无法为它重新赋值。因为计算属性的值不需要被重新赋值,它的值是依赖数据字段的变化自动进行计算的get sum() { return this.numA + this.numB},// actions 函数,专门来修改 store 中数据的值// 分析:声明一些action方法如updateNum1、updateNum2,同时分别为他们指定一个function函数,只不过这个函数需要被action方法包裹起来,即在外面我们需要先调用action方法,在action方法内部传一个function,通过这个function来修改store内数据的值,外界传过来的参数,可以在function的形参里面进行接收,比如外界传了一个步长值step,接下来可以根据这个step让numA进行自增updateNum1: action(function (step) { // 外界传参可以使用action方法内function的形参接收this.numA += step}),updateNum2: action(function (step) {this.numB += step}),updateActiveTabBarIndex: action(function (index) {this.activeTabBarIndex = index})
})

pages/message/message.wxml

<!--pages/message/message.wxml-->
<text>pages/message/message.wxml</text><view>~~~~~~</view><view>{{numA}} + {{numB}} = {{sum}}</view>
<van-button type="primary" bindtap="btnHandler1" data-step="{{1}}">numA + 1</van-button>
<van-button type="danger" bindtap="btnHandler1" data-step="{{-1}}">numA - 1</van-button>

pages/message/message.js

// pages/message/message.js
import { createStoreBindings } from 'mobx-miniprogram-bindings'
import { store } from '../../store/store'Page({/*** 页面的初始数据*/data: {},/*** 生命周期函数--监听页面加载*/onLoad(options) {// this指代当前页面实例  配置对象包含3个属性:数据源store、字段fields、方法actions// 分析:调用createStoreBindings()方法,传递一个this(当前页面实例)和一个配置对象,就可以将store里面对应的字段或对应的方法绑定到当前页面的实例身上,该方法的最终返回值挂载到页面上作为当前页面的一个自定义属性而存在,这个属性值storeBindings,作用是当当前页面被卸载时可以在卸载处理函数中做请理性的工作this.storeBindings = createStoreBindings(this, {// 数据源,将来会将store里面对应的属性或方法绑定到当前页面实例上store,// 数据字段,需要将哪些字段绑定到当前页面上来进行使用fields: ['numA', 'numB', 'sum'], // 可以为空数组,默认// 方法,需要将哪些方法绑定到当前页面上来进行使用actions: ['updateNum1'] // 可以为空数组,默认})},btnHandler1(e) {// console.log(e)// 在事件处理函数中,调用从store映射过来的updateNum1()方法this.updateNum1(e.target.dataset.step)},/*** 生命周期函数--监听页面初次渲染完成*/onReady() {},/*** 生命周期函数--监听页面显示*/onShow() {},/*** 生命周期函数--监听页面隐藏*/onHide() {},/*** 生命周期函数--监听页面卸载*/onUnload() {this.storeBindings.detroyStoreBindings()},/*** 页面相关事件处理函数--监听用户下拉动作*/onPullDownRefresh() {},/*** 页面上拉触底事件的处理函数*/onReachBottom() {},/*** 用户点击右上角分享*/onShareAppMessage() {}
})

💠 小结一下

① 能够知道如何安装和配置 vant-weapp 组件库

● 参考 Vant 的官方文档

② 能够知道如何使用 MobX 实现全局数据共享

● 安装包、创建 Store参考官方文档进行使用

③ 能够知道如何对小程序的 API 进行 Promise

● 安装包、app.js 中进行配置

④ 能够知道如何实现自定义 tabBar 的效果

Vant 组件库 + 自定义组件 + 全局数据共享


【前文回顾】👉 小程序 - 基础| 页面导航、页面事件、生命周期、WXS脚本_04 

相关文章:

【小程序 - 加强】自定义组件、使用npm包、全局数据共享、分包_05

目录 一、自定义组件 1. 组件的创建与引用 1.1 创建组件 1.2 引用组件 1.2.1 局部引用组件 1.2.2 全局引用组件 1.2.3 全局引用 VS 局部引用 1.2.4 组件和页面的区别 2. 样式 2.1 组件样式隔离 2.2 组件样式隔离的注意点 2.3 修改组件的样式隔离选项 2.4 styleIso…...

Vue.js3学习篇--Vue模板应用

目录 一,模板基础 1.模板插值 &#xff08;1&#xff09;基础插值 &#xff08;2&#xff09;HTML代码插值 &#xff08;3&#xff09;标签属性插值 2.模板指令 &#xff08;1&#xff09;定义 &#xff08;2&#xff09;指令参数 二.条件渲染 1.使用v-if指令渲染 2.使…...

【软考】5.2 传输介质/通信方式/IP地址/子网划分

《传输介质》 双绞线&#xff1a;网线&#xff1b;传输距离在100m以内 无屏蔽双绞线&#xff1a;UTP&#xff1b;可靠性相对较低屏蔽双绞线&#xff1a;STP&#xff1b;屏蔽怕干扰&#xff1b;可靠性相对较高&#xff1b;一般用于对传输可靠性要求很高的场合 网线&#xff1a…...

软件测试银行项目网上支付接口调用测试实例

公司最近有一个网站商城项目要开始开发了&#xff0c;这几天老板和几个同事一起开着需求会议&#xff0c; 讨论了接下来的业务规划和需求策略&#xff0c;等技术需求一下来还要讨论技术需求&#xff0c; 确认后再慢慢的进入开发阶段&#xff0c;趁着闲暇时间新造的人想总结一…...

w806 adc 中断扫描通道采集

用到了该芯片adc 扫描4个adc 通道&#xff0c;官方的死循环等待非常浪费时间&#xff0c;这里改用adc 中断采集方式&#xff0c;记录一下 int32_t adcFilterSum[4]{0}; int32_t detec_adc_value[4]{0};//mV int16_t detec_convt_ok[4]{0};/*is OK*/ ADC_HandleTypeDef hadc;vo…...

使用CSS的Positions布局打造响应式网页

在当今移动互联网的时代&#xff0c;响应式网页设计已经成为了一个必备的技能。通过使用CSS Positions布局&#xff0c;我们可以轻松地实现一个响应式的网页&#xff0c;使网页能够在不同的屏幕尺寸下自动适应。本文将介绍如何使用CSS Positions布局来打造一个响应式网页&#…...

模型训练环境相关(CUDA、PyTorch)

模型训练环境相关&#xff08;CUDA、PyTorch&#xff09; 1. 查看当前 GPU 所能支持的最高版本的 CUDA2. 如何判断是否安装了 CUDA3. 安装 PyTorch3.1 创建虚拟环境3.2 激活并进入虚拟环境3.3 安装 PyTorch 1. 查看当前 GPU 所能支持的最高版本的 CUDA 打开 NVIDIA 控制面板&a…...

链动2+1模式:社交电商行业的新型商业模式与营销手段

链动21模式是近年来在社交电商行业中崭露头角的一种新型商业模式和营销手段。在经历了多年的发展之后&#xff0c;社交电商行业已经进入了一个竞争激烈、用户获取成本高昂的阶段。在这个阶段&#xff0c;如何迅速吸引用户并增加他们的留存率和复购率成为了亟待解决的问题。 为了…...

竞赛选题 深度学习 opencv python 实现中国交通标志识别

文章目录 0 前言1 yolov5实现中国交通标志检测2.算法原理2.1 算法简介2.2网络架构2.3 关键代码 3 数据集处理3.1 VOC格式介绍3.2 将中国交通标志检测数据集CCTSDB数据转换成VOC数据格式3.3 手动标注数据集 4 模型训练5 实现效果5.1 视频效果 6 最后 0 前言 &#x1f525; 优质…...

LuatOS-SOC接口文档(air780E)-- fskv - kv数据库,掉电不丢数据

示例 -- 本库的目标是替代fdb库 -- 1. 兼容fdb的函数 -- 2. 使用fdb的flash空间,启用时也会替代fdb库 -- 3. 功能上与EEPROM是类似的 fskv.init() fskv.set("wendal", 1234) log.info("fskv", "wendal", fskv.get("wendal"))--[[ fs…...

一篇文章教你Pytest快速入门和基础讲解,一定要看!

前言 目前有两种纯测试的测试框架&#xff0c;pytest和unittestunittest应该是广为人知&#xff0c;而且也是老框架了&#xff0c;很多人都用来做自动化&#xff0c;无论是UI还是接口pytest是基于unittest开发的另一款更高级更好用的单元测试框架出去面试也好&#xff0c;跟别…...

SpringBoot项目:Cannot find declaration to go to

SpringBoot项目get,set方法总报Cannot find declaration to go to 搜了很多答案&#xff0c;没解决 后来仔细一想&#xff0c;原来是我的idea软件重装了&#xff0c;lombok插件没重新安装导致。 安装步骤&#xff1a; 1、下载地址&#xff1a;https://plugins.jetbrains.com…...

【高并发】多线程和高并发提纲

文章目录 三大源头两个主要问题三大解决方案 最近正在面试&#xff0c;对多线程和高并发相关问题整理了一个简单的提纲。 个人感觉这三大部分由底向上&#xff0c;足够引出对并发编程中大部分问题的讨论~ 三大源头 线程切换带来的原子性问题。 原子操作&#xff1a;利用CPU提…...

vue.js处理数组对象中某个字段是否变为两个字段

一、场景&#xff1a; 产品要求做一个时间步骤条&#xff0c;使用目前后端已返回的数据进行操作实现。时间步骤条要求日期和时间分开显示且相同日期只显示第一个日期。 图左边为实现效果&#xff0c;右边为后台返回的接口。接口中current字段表示当前到达第几步&#xff0c;从…...

从零开始的C++(补充三的内容)

auto:在编译阶段根据数据的类型确认auto所代表的类型&#xff0c;并将auto换成对应的类型。 特点&#xff1a; 1、auto所能代表的类型必须是在编译阶段就能确认的。 2、auto修饰的变量必须初始化&#xff0c;否则编译器无法判断auto的实际类型。 3、auto会根据第一个数据来…...

微信小程序通过createSelectorQuery获取元素 高度,宽度与界面距离

小程序官方有提供给我们一个 const query wx.createSelectorQuery() 函数 我们可以先编写这样一段代码 wxml <view><button bindtap"getDom">点击查看</button><view class "textIn" style "height: 100px;width: 30px;&quo…...

MySQL-事务

MySQL-事务 1.什么是事务 举例&#xff1a;想象炒菜的过程。 洗菜切菜炒菜装盘 我相信缺少任何任何一个步骤&#xff0c;都不完美&#xff01;&#xff01;&#xff01;可以将炒菜的过程理解为一个事务&#xff0c;是一组操作的集合&#xff0c;而MySQL中的事务也是如此。但…...

自动定时删除磁盘文件的脚本(从文件日期最早的开始删)

#!/bin/bash# 指定的挂载点 MOUNTPOINT"/media/vm/MyDisk512GB"# 设置磁盘大小的限制 (例如&#xff1a;800G) LIMIT$((800 * 1024 * 1024)) # 单位是KB# 获取挂载点的已使用空间 USED_SPACE$(df -kP "$MOUNTPOINT" | tail -1 | awk {print $3})echo &quo…...

拆解CPU的基本结构和运行原理

CPU的基本结构 CPU是一个计算系统的核心 南北桥芯片将CPU与外设连接起来 CPU执行流程 CPU的电路基础 组合电路基本原理 时序电路基本原理 多核成为主流 汇编语言和寄存器 中断的基本原理 中断的产生 中断服务程序 CPU 做为计算机的总司令官&#xff0c;它管理着计算…...

Docker安装——Ubuntu (Jammy 22.04)

一、为什么要用 Ubuntu&#xff1f;(centos和ubuntu有什么区别&#xff09; 使用lsb_release命令&#xff1a;lsb_release -a &#xff0c;即可查看ubantu的版本&#xff0c;但是为什么要使用ubantu 呢&#xff1f; 区别&#xff1a;1、centos基于EHEL开发&#xff0c;而ubunt…...

Fast DDS之Transport

目录 transport层负责为DDS用户数据收发和服务发现提供通信。包含UDP&#xff0c;TCP&#xff0c;SHM。...

爱普生L125X_L325X系列打印机Wi-Fi配置方法(Smart Panel)

准备工作&#xff1a; 手机需要下载“Epson Smart Panel”APP&#xff1b; 配置无线&#xff08;Wi-Fi&#xff09;方法 说明&#xff1a;SSID名称&#xff08;Wi-Fi名&#xff09;不能包含中文字符,路由器需要选择2.4GHz频段; 1. 打开“Epson Smart Panel”软件&#xff0…...

【回顾一下Docker的基本用法】

文章目录 回顾一下Docker的基本用法1.初识Docker1.1.什么是Docker1.1.1.应用部署的环境问题1.1.2.Docker解决依赖兼容问题1.1.3.Docker解决操作系统环境差异1.1.4.小结 1.2.Docker和虚拟机的区别1.3.Docker架构1.3.1.镜像和容器1.3.2.DockerHub1.3.3.Docker架构1.3.4.小结 1.4.…...

【Python】Python基础知识

【Python】Python基础知识 关键字 查看Python关键字&#xff1a; >python >>>import keyword >>>keyword.kwlist 注释 注释有两方面作用&#xff1a; &#xff08;1&#xff09;提高程序的可读性&#xff08;最重要的作用&#xff09;&#xff1b…...

【计算机视觉 05】YOLO论文讲解:V1-V7

https://ai.deepshare.net/live_pc/l_63243a65e4b050af23b79338 Part1.目标检测与YOLO系列 1. 目标检测任务及发展脉络 2. YOLO的发展史 Anchors Base原理&#xff1a; Part2.YOLOV1-V3 3. YOLO V1的网络结构 4. YOLO V3的网络结构与实验结果 Part3.YOLO的进化 5. YOLO V4的网络…...

git全局与单仓库的密码管理

概要 在使用git时&#xff0c;有默认的全局配置&#xff0c;每个仓库也有自己的配置&#xff0c;在使用时常常傻傻分不清楚&#xff0c;现在进行一个简单的整理记录。 一般情况下全局配置中的git账号和邮箱通常设置成自己的&#xff0c;其他仓库再根据项目需要进行单独配置&a…...

IDEA的使用(一) (IntelliJ IDEA 2022.1.3版本)

目录 1. IDEA项目结构 2. 模块的导入操作 2.1 正规操作 2.2 取巧操作 2.3 出现乱码 2.4 模块改名 3. 代码模板的使用 后缀补全&#xff08;Postfix Completion&#xff09;、实时模板&#xff08;Live Templates&#xff09;菜单里面什么介绍都有&#xff0c;可以自学&a…...

javaee SpringMVC文件上传 项目结构

引入依赖 <?xml version"1.0" encoding"UTF-8"?><project xmlns"http://maven.apache.org/POM/4.0.0" xmlns:xsi"http://www.w3.org/2001/XMLSchema-instance"xsi:schemaLocation"http://maven.apache.org/POM/4.0.0…...

JavaScript DOM 函数大全详解(使用最新的 JS 语法)

JavaScript DOM 函数大全详解&#xff08;使用最新的 JS 语法&#xff09; JavaScript 的 Document Object Model&#xff08;DOM&#xff09;是用于操作网页内容的编程接口。在最新的 JavaScript 语法下&#xff0c;我们有很多方便和高效的方法来处理 DOM。下面是一些常用 DO…...

Stm32_标准库_8_ADC_光敏传感器_测量具体光照强度

ADC简介 测量方式 采用二分法比较数据 IO通道 ADC基本结构及配置路线 获取数字变量需要用到用到光敏电阻的AO口&#xff0c;AO端口接在PA0引脚即可 测得的模拟数据与实际光照强度之间的关系为 光照强度 100 - 模拟量 / 40;代码&#xff1a; 完整朴素代码&#xff1a; #in…...

基于SSM的固定资产管理系统的设计与实现

末尾获取源码 开发语言&#xff1a;Java Java开发工具&#xff1a;JDK1.8 后端框架&#xff1a;SSM 前端&#xff1a;采用JSP技术开发 数据库&#xff1a;MySQL5.7和Navicat管理工具结合 服务器&#xff1a;Tomcat8.5 开发软件&#xff1a;IDEA / Eclipse 是否Maven项目&#x…...

Leetcode---364场周赛

题目列表 2864. 最大二进制奇数 2865. 美丽塔 I 2866. 美丽塔 II 2867. 统计树中的合法路径数目 一、最大二进制奇数 这题只要你对二进制有了解(学编程的不会不了解二进制吧)&#xff0c;应该问题不大&#xff0c;这题要求最大奇数&#xff0c;1.奇数&#xff1a;只要保证…...

使用 Powershell 检索不理解的命令

使用 Powershell 检索不理解的命令 尝试使用 Powershell 完成 Powershell 的命令行 使用 Powershell 时&#xff0c;有时您会忘记某个 cmdlet 或想要了解哪些 cmdlet 可用。在这种情况下&#xff0c;最好在互联网上查找&#xff0c;但您也可以使用 Powershell 函数来完成。 以…...

基于 FPGA 的机器博弈五子棋游戏

基于 FPGA 的机器博弈五子棋游戏 一,设计目的 五子棋是一种深受大众喜爱的游戏,其规则简单,变化多端,非常富有趣味性 和消遣性。棋类游戏在具备娱乐性、益智性的同时也因为其载体大多是手机, 电脑等移动互联网设备导致现代社会低头族等现象更加严重,危害青少年的身 体健康…...

uCOSIII实时操作系统 三 移植

目录 uCOSIII简介&#xff1a; 准备工作&#xff1a; 准备基础工程&#xff1a; UCOSIII工程源码&#xff1a; UCOSIII移植&#xff1a; 向基础工程中添加相应的文件夹 向工程中添加分组 常见问题&#xff1a; 下载验证&#xff1a; uCOSIII简介&#xff1a; UCOS-I…...

机器学习之SGD, Batch, and Mini Batch的简单介绍

文章目录 总述SGD(Stochastic Gradient Descent)(随机梯度下降&#xff09;Batch &#xff08;批量&#xff09;mini Batch (迷你批量&#xff09; 总述 SGD, Batch, and Mini Batch是可用于神经网络的监督学习计算权重更新的方案&#xff0c;即∆wij。 SGD(Stochastic Gradi…...

Windows电脑上的多开器与分布式存储系统的关系

Windows电脑上的多开器和分布式存储系统是两个不同的概念&#xff0c;二者之间没有直接的关系。 多开器是一种软件&#xff0c;它可以在Windows电脑上让用户同时运行多个同一应用程序的实例。多开器通常用于游戏玩家和应用程序测试人员等需要同时运行多个实例的用户。 分布式…...

积分球可以用于什么光谱光学检测

积分球是光测量的主要工具之一。积分球可以同时捕获一个光源发出的所有辐射。 1.光源测量 积分球可以用于测量光源的光通量、色温、光效等参数。通过将光源放置在积分球的入口处&#xff0c;球内的光线经过多次反射后形成均匀的照度分布&#xff0c;然后使用光度计或光谱仪对光…...

【力扣面试题】URL化

&#x1f451;专栏内容&#xff1a;力扣刷题⛪个人主页&#xff1a;子夜的星的主页&#x1f495;座右铭&#xff1a;前路未远&#xff0c;步履不停 目录 一、题目描述二、题目分析1、使用String内部方法2、使用StringBuilder 一、题目描述 题目链接&#xff1a;URL化 编写一种…...

计算机网络基础(二):物理层、数据链路层及网络层

一、物理层 1.物理层 物理层面的通信标准可以概括划分为与网络基础设施有关的标准和与被传输物理信号有关的标准两类。 网络基础设施的标准&#xff1a;鉴于物理层面的消息互通也是物理层应该兑现的服务&#xff0c;因此物理层的标准还会包括针脚的用途、线缆的材料与设计等…...

小白自学—网络安全(黑客技术)笔记

目录 一、自学网络安全学习的误区和陷阱 二、学习网络安全的一些前期准备 三、网络安全学习路线 四、学习资料的推荐 想自学网络安全&#xff08;黑客技术&#xff09;首先你得了解什么是网络安全&#xff01;什么是黑客&#xff01; 网络安全可以基于攻击和防御视角来分类…...

2.2.3 vim操作合集

1 vim VIM 是 Linux 系统上一款文本编辑器,学习 VIM 最好的文档,应该是阅读学习 VIM 的帮助文档,可以使用本地的帮助文件(vim--->:help),或者使用在线帮助文档。同时针对vim的使用,相应的相书籍也很多,如下 2 vim操作模式 命令模式:默认模式,该模式下可以移动光标…...

解决 Jenkins 性能缓慢的问题~转

解决 Jenkins 性能缓慢的问题 Docker中文社区 ​​ 计算机技术与软件专业技术资格持证人 2 人赞同了该文章 没有什么比缓慢的持续集成系统更令人沮丧的了。它减慢了反馈循环并阻止代码快速投入生产。虽然像使用性能更好的服务器可以为您争取时间&#xff0c;但您最终必须投资…...

Matrix卡顿优化之IdleHandlerLagTracer源码分析

前言 IdleHandler是Android系统为开发者提供的一种在消息队列空闲时运行任务的机制&#xff0c;通过IdleHandler执行的任务优先级低于主线程优先级&#xff0c;会在主线程任务执行完成后再执行&#xff0c;所以适用于一些实时性要求不高的任务&#xff0c;通常用于Android启动…...

(ubuntu)Docker 安装linux 详情过程

文章目录 前言Docker 安装linux第一步&#xff1a;使用dokcker 拉取镜像&#xff1a;第二步&#xff1a;创建本地目录&#xff08;用于挂载&#xff09;第三步&#xff1a;&#xff08;上传配置文件&#xff09;修改配置文件第四步&#xff1a;创建docker容器第五步: 测试本地连…...

ArcMap:第二届全国大学生GIS技能大赛(广西师范学院)详解-上午题

目录 01 题目 1.1 第一小题 1.2 第二小题 1.3 第三小题 1.4 数据展示 02 思路和实操 2.1 第一问思路 2.2 第一问操作过程 2.2.1 地理配准 2.2.2 镶嵌 2.2.2.1 第一种镶嵌方法 2.2.2.2 第二种镶嵌方法 2.2.3 裁剪 2.2.4 DEM信息提取 2.2.5 分类 2.3 第二问思路 …...

Blender 导出 fbx 到虚幻引擎中丢失材质!!!(使用Blender导出内嵌材质的fbx即可解决)

目录 0 引言1 Blender导出内嵌纹理的fbx模型 0 引言 我在Blender处理了一些fbx模型后再次导出到UE中就经常出现&#xff0c;材质空白的情况&#xff08;如下图所示&#xff09;&#xff0c;今天终于找到问题原因&#xff0c;记录下来&#xff0c;让大家避免踩坑。 其实原因很简…...

C++交换a和b的方法

以下是用C编写的交换a和b的六种方法&#xff1a; 1. 方法一&#xff1a;使用临时变量 #include <iostream>int main() {int a 5;int b 10;std::cout << "Before swapping: a " << a << ", b " << b << std::end…...

3D孪生场景搭建:模拟仿真

前面几期文章介绍如何使用NSDT 编辑器 搭建3D应用场景&#xff0c;本期介绍下孪生场景中一个一个非常重要的功能&#xff1a;模拟仿真。 1、什么是模拟仿真 模拟仿真是一种用于描述、分析和模拟现实世界中系统、过程或事件的计算机模型和程序。仿真通过输入各种参数和条件&am…...

美国各流域边界下载,并利用arcgis提取与处理

一、边界数据的下载 一般使用最普遍的流域边界数据是从HydroSHEDS官网下载: HydroBASINS代表一系列矢量多边形图层&#xff0c;以全球尺度呈现次级流域边界。该产品的目标是提供一种无缝的全球覆盖&#xff0c;其中包含了不同尺度&#xff08;从数十到数百万平方千米&#xf…...