这些小活动你都参加了吗?快来围观一下吧!>>
电子产品世界 » 论坛首页 » DIY与开源设计 » 电子DIY » 【FRDM-MCXW72|Zephyr】微信小程序对接温湿度计

共1条 1/1 1 跳转至

【FRDM-MCXW72|Zephyr】微信小程序对接温湿度计

高工
2026-05-23 21:47:30     打赏

        之前预留了ESS服务,就是为了实现和小程序的对接,事实证明,和大模型说了使用标准的ess对接。一步就直接生成了最终的代码。

账号注册

     注册方法很简单,直接打开微信公众平台,打开后点击小程序,会弹到小程序页面,在这个页面中点击前往注册便可执行对应的注册流程。

工具安装

      这一步可以直接在注册账号后按照指引安装工具,也可以直接跑微软的Misrosoft Store直接搜索微信开发者工具安装。

工程创建

     打开微信开发者工具软件(首次打开需登录,拿注册开发者账号的微信登录即可)后,点击左上角的项目,之后选择新建项目,便会弹出新建项目的弹窗(见下图)

1.jpg

        在新建项目界面中,选择好工程的保存路径,选用注册时对应的appid(软件登陆时就已经绑定了,直接选择即可),后端服务选择不使用云服务,模板选择 JS-基础模板,之后点击创建便可生成工程,建好后的工程目录结构如下:

├── app.js
├── app.json
├── app.wxss
└── pages
    └── index
        ├── index.js
        ├── index.json
        ├── index.wxml
        └── index.wxss

代码修改

     这部分我是直接丢给大模型生成的,也就说了这么一句话:我想做这样的微信小程序,基于小程序的JS框架。界面上,有一个选择框和一个确认按钮,选择框可以显示手机搜索到的支持BLE ESS(标准实现,非私有协议)的温湿度计列表,确认按钮则执行连接和断开此设备。连上后,界面中出现两个显示框,一个显示传感器传来的温度信息,一个显示传感器传过来的湿度信息,帮忙实现一下

app.json

配置全局参数

{
  "pages": [
    "pages/index/index"
  ],
  "window": {
    "navigationBarTitleText": "BLE ESS温湿度计",
    "navigationBarTextStyle": "white",
    "navigationBarBackgroundColor": "#007AFF"
  },
  "requiredBackgroundModes": ["bluetooth"],
  "permission": {
    "scope.bluetooth": {
      "desc": "用于搜索并连接BLE温湿度设备"
    }
  },
  "lazyCodeLoading": "requiredComponents"
}

app.js

App({
  onLaunch() {
    console.log("小程序启动")
  }
})

app.wxss

        用于设置全局样式

page {
  background: #f5f5f5;
  padding: 10rpx;
}

pages/index/index.json

      用于配置页面信息,个人理解就是这个子页面的名称

{
  "navigationBarTitleText": "ESS温湿度"
}

pages/index/index.wxml

      界面显示的内容和显示规则

<!-- 设备选择 -->
<view class="card">
  <text class="label">选择ESS设备:</text>
  <picker bindchange="onDeviceSelect" value="{{selectedIndex}}" range="{{deviceNames}}">
    <view class="picker-box">
      {{deviceNames[selectedIndex] || '点击搜索设备'}}
    </view>
  </picker>
</view>

<!-- 按钮 -->
<view class="btn-group">
  <button type="primary" bindtap="startSearch" disabled="{{isConnecting}}">搜索BLE设备</button>
  <button type="{{connected ? 'warn' : 'primary'}}" bindtap="connectOrDisconnect" disabled="{{!hasSelected}}">
    {{connected ? '断开连接' : '连接设备'}}
  </button>
</view>

<!-- 温湿度显示(连接成功才显示) -->
<view class="data-card" wx:if="{{connected}}">
  <view class="data-item">
    <text>温度</text>
    <text class="value">{{temperature}} ℃</text>
  </view>
  <view class="data-item">
    <text>湿度</text>
    <text class="value">{{humidity}} %RH</text>
  </view>
</view>

pages/index/index.wxss

      说明各控件的样式

.card {
  background: white;
  border-radius: 16rpx;
  padding: 30rpx;
  margin: 20rpx;
}

.label {
  font-size: 30rpx;
  color: #333;
  margin-bottom: 20rpx;
  display: block;
}

.picker-box {
  background: #f2f2f2;
  padding: 24rpx;
  border-radius: 12rpx;
  font-size: 28rpx;
  text-align: center;
}

.btn-group {
  display: flex;
  gap: 20rpx;
  margin: 20rpx;
}

button {
  flex: 1;
  border-radius: 12rpx;
}

.data-card {
  background: white;
  border-radius: 16rpx;
  padding: 40rpx 30rpx;
  margin: 30rpx 20rpx;
}

.data-item {
  display: flex;
  justify-content: space-between;
  font-size: 36rpx;
  margin: 20rpx 0;
}

.value {
  color: #007AFF;
  font-weight: bold;
}

pages/index/index.js

      核心功能实现,具体的搜索设备,数据更新逻辑等都是在这部分实现的

Page({
  data: {
    devices: [],             // 设备列表
    deviceNames: [],         // 选择框显示名称
    selectedIndex: 0,        // 选中下标
    connected: false,        // 是否连接
    hasSelected: false,      // 是否选了设备
    deviceId: '',            // 连接的设备ID
    temperature: '---',      // 温度
    humidity: '---',         // 湿度

    // BLE ESS 标准UUID(官方固定,不用改)
    ESS_SERVICE_UUID: '0000181A-0000-1000-8000-00805F9B34FB',
    TEMP_CHAR_UUID: '00002A6E-0000-1000-8000-00805F9B34FB',
    HUMI_CHAR_UUID: '00002A6F-0000-1000-8000-00805F9B34FB'
  },

  onLoad() {
    this.initBluetooth()
  },

  // 初始化蓝牙
  initBluetooth() {
    wx.openBluetoothAdapter({
      fail: () => {
        wx.showToast({ title: '请开启蓝牙', icon: 'error' })
      }
    })
  },

  // 搜索 BLE ESS 设备
  startSearch() {
    if (this.data.connected) {
      wx.showToast({ title: '请先断开', icon: 'none' })
      return
    }

    wx.showToast({ title: '搜索中...', icon: 'loading' })
    this.setData({ devices: [], deviceNames: [] })

    // 只搜索 ESS 服务
    wx.startBluetoothDevicesDiscovery({
      services: [this.data.ESS_SERVICE_UUID],
      allowDuplicatesKey: false,
      success: () => {
        wx.onBluetoothDeviceFound((res) => {
          const dev = res.devices[0]
          if (dev.name && dev.name.trim() !== '') {
            this.addDevice(dev)
          }
        })

        // 5秒后自动停止
        setTimeout(() => {
          wx.stopBluetoothDevicesDiscovery()
          wx.showToast({ title: '搜索完成' })
        }, 5000)
      }
    })
  },

  // 添加设备到列表
  addDevice(device) {
    const { devices } = this.data
    const exist = devices.some(item => item.deviceId === device.deviceId)
    if (!exist) {
      devices.push(device)
      const names = devices.map(d => d.name)
      this.setData({ devices, deviceNames: names })
    }
  },

  // 选择设备
  onDeviceSelect(e) {
    const idx = e.detail.value
    this.setData({
      selectedIndex: idx,
      hasSelected: true
    })
  },

  // 连接 / 断开
  connectOrDisconnect() {
    const { connected, devices, selectedIndex } = this.data
    if (devices.length === 0) return

    const device = devices[selectedIndex]
    connected ? this.disconnect() : this.connect(device)
  },

  // 连接设备
  connect(device) {
    wx.showLoading({ title: '连接中...' })

    wx.createBLEConnection({
      deviceId: device.deviceId,
      success: () => {
        this.setData({
          connected: true,
          deviceId: device.deviceId
        })
        wx.hideLoading()
        wx.showToast({ title: '连接成功' })
        this.startListenESS()
      },
      fail: () => {
        wx.hideLoading()
        wx.showToast({ title: '连接失败', icon: 'error' })
      }
    })
  },

  // 断开连接
  disconnect() {
    wx.closeBLEConnection({
      deviceId: this.data.deviceId,
      success: () => {
        this.setData({
          connected: false,
          temperature: '---',
          humidity: '---'
        })
        wx.showToast({ title: '已断开' })
      }
    })
  },

  // 订阅标准ESS温湿度
  startListenESS() {
    const { deviceId, ESS_SERVICE_UUID, TEMP_CHAR_UUID, HUMI_CHAR_UUID } = this.data

    // 打开通知
    wx.notifyBLECharacteristicValueChange({
      deviceId, serviceId: ESS_SERVICE_UUID, characteristicId: TEMP_CHAR_UUID, state: true
    })
    wx.notifyBLECharacteristicValueChange({
      deviceId, serviceId: ESS_SERVICE_UUID, characteristicId: HUMI_CHAR_UUID, state: true
    })

    // 接收数据
    wx.onBLECharacteristicValueChange((res) => {
      const buf = new DataView(res.value)

      // 温度:int16,单位 0.01℃
      if (res.characteristicId === TEMP_CHAR_UUID) {
        const temp = buf.getInt16(0, true) / 100
        this.setData({ temperature: temp.toFixed(1) })
      }

      // 湿度:uint16,单位 0.01%RH
      if (res.characteristicId === HUMI_CHAR_UUID) {
        const humi = buf.getUint16(0, true) / 100
        this.setData({ humidity: humi.toFixed(1) })
      }
    })
  }
})

最终效果

1.jpg

      点击界面顶部的真机调试,编译后会二维码,此时用注册的微信扫描二维码

1.gif

最后

     如果要把这部分代码直接公开使用,其实就是按照开发者指南的方法把APPID更换成正式的appid,之后点击界面右侧的上传即可进行后续操作。不过发布小程序涉及的内容还挺多,主要是一些法规之类的东东,因此暂时就不去折腾他了,等后续真正有需求时再去研究个人发布应用需要怎么操作。





关键词: FRDM-MCXW72     Zephyr     微信     程序         

共1条 1/1 1 跳转至

回复

匿名不能发帖!请先 [ 登陆 注册 ]