HarmonyOS鸿蒙Next中有个网络地址其中为需要打印的小票如何使用webview打印

HarmonyOS鸿蒙Next中有个网络地址其中为需要打印的小票如何使用webview打印 现有一个后端获取的网络地址 这个地址为一个html页面 使用webview 然后打印没有蓝牙打印机

如何使这个html地址内容通过蓝牙打印机打印出来

9 回复

【背景知识】

  • connection.startBluetoothDiscovery 是经典蓝牙扫描,ble.startBLEScan 是低功耗蓝牙扫描。ble 的 startBLEScan 是只能扫描到 ble 设备,如果想要扫描到系统设置中的所有设备,需要去调用 connection.startbluetoothdiscovery
  • 基于串口通信协议(Serial Port Profile,SPP)实现设备间连接和传输数据的开发:连接和传输数据

【解决方案】

离线状态下,可以通过蓝牙扫描连接打印机进行打印。主要操作步骤如下:

  • 在 module.json5 文件中申请蓝牙权限:
{
  "name": "ohos.permission.ACCESS_BLUETOOTH",
  "reason": "$string:module_desc",
  "usedScene": {
    "abilities": [
      "FormAbility"
    ],
    "when": "inuse"
  }
}
  • 使用 connection.startbluetoothdiscovery 扫描打印机蓝牙并进行连接,参考示例如下:
import connection from '@ohos.bluetooth.connection';
import { BusinessError } from '@ohos.base';
import { promptAction } from '@kit.ArkUI';
import abilityAccessCtrl, { Permissions } from '@ohos.abilityAccessCtrl';
import common from '@ohos.app.ability.common';

interface Device {
  name?: string
  deviceId?: string
}

@Entry
@Component
struct Index {
  private context = this as common.UIAbilityContext
  @State findList: Device[] = []

  aboutToAppear(): void {
    const permissions: Array<Permissions> = ['ohos.permission.ACCESS_BLUETOOTH'];
    let atManager: abilityAccessCtrl.AtManager = abilityAccessCtrl.createAtManager();
    atManager.requestPermissionsFromUser(this.context, permissions).then((data) => {
      // 授权成功
    }).catch((err: BusinessError) => {
      console.error(`Failed to request permissions from user. Code is ${err.code}, message is ${err.message}`);
    })
  }

  build() {
    Flex({ direction: FlexDirection.Column }) {
      Row() {
        Button("扫描蓝牙").onClick(() => {
          // 开启扫描
          try {
            connection.startBluetoothDiscovery();
            console.info('startBleScan success')
            promptAction.showToast({
              message: "已打开"
            })
          } catch (err) {
            promptAction.showToast({
              message: "蓝牙开关未打开"
            })
          }
          // 接收扫描结果
          connection.on('bluetoothDeviceFind', (data: string[]) => {
            console.log('data: ' + JSON.stringify(data) + connection.getRemoteDeviceName(data[0]))
            if (!this.findList.find(item => item.deviceId === data[0])) {
              this.findList.push({
                name: connection.getRemoteDeviceName(data[0]),
                deviceId: data[0]
              })
            }
          });
        })

        Button("停止扫描").onClick(() => {
          try {
            // 关闭扫描
            connection.stopBluetoothDiscovery();
            console.info('stopBleScan success');
            promptAction.showToast({
              message: "停止扫描"
            })
          } catch (err) {
            promptAction.showToast({
              message: "蓝牙已关闭"
            })
          }
        })

        Button("清空").onClick(() => {
          this.findList = []
        })
      }

      List() {
        ForEach(this.findList, (item: Device) => {
          ListItem() {
            Flex({ alignItems: ItemAlign.Center, justifyContent: FlexAlign.SpaceBetween }) {
              Column() {
                Text(`设备名称:${item?.name}`)
                Text(`设备id:${item?.deviceId}`).fontColor("#ffcbcbcb").fontSize(12)
              }
              .alignItems(HorizontalAlign.Start)

              Row({ space: 5 }) {
                Button("链接").width(60).height(20).fontSize(12).onClick(() => {
                  try {
                    // 实际的地址可由扫描流程获取
                    connection.pairDevice(item.deviceId, () => {
                      promptAction.showToast({
                        message: "配对成功"
                      })
                    });
                  } catch (err) {
                    console.error('errCode: ' + (err as BusinessError).code + ', errMessage: ' +
                    (err as BusinessError).message);
                  }
                })
              }
            }
            .height(50)
            .backgroundColor("#fff")
            .width("100%")
            .borderRadius(10)
            .padding(6)
          }
          .padding(4)
        })
      }
      .height(200)
      .width("100%")
      .flexGrow(1)
      .flexShrink(1)
      .flexBasis(1)
    }
    .padding(10).width('100%').height('100%').backgroundColor("#ffcdcdcd")
  }
}
  • 使用 socket 模块继续进行后续的数据传输等功能,参考官网文档:连接和传输数据

【总结】

在离线场景下,可以使用 connect 连接模块和外设配对、连接成功,再使用 socket 模块继续进行后续的数据传输等功能,实现设备间的通信。

更多关于HarmonyOS鸿蒙Next中有个网络地址其中为需要打印的小票如何使用webview打印的实战系列教程也可以访问 https://www.itying.com/category-93-b0.html


在module.json5中添加网络访问和打印权限:

{
  "requestPermissions": [
    { "name": "ohos.permission.INTERNET" },
    { "name": "ohos.permission.PRINT" }
  ]
}

通过WebviewController加载远程HTML页面:

import { webview } from '@kit.ArkWeb';
@Component
struct WebComponent {
  controller: webview.WebviewController = new webview.WebviewController();
  
  build() {
    Column() {
      Web({ 
        src: 'https://your-html-page-url.com', // 填入后端获取的网络地址
        controller: this.controller 
      })
    }
  }
}

在HTML页面中通过W3C标准接口触发打印:

<button onclick="window.print()">打印小票</button>

目前是获取照片通过蓝牙打印机打印 但是传递的arraybuffer 打印机打印的照片不显示 显示一堆乱码

可以参考应用侧通过调用createWebPrintDocumentAdapter 创建打印适配器,通过将适配器传入打印的 print 接口调起打印:通过调用应用侧接口拉起打印

这种无法选中蓝牙打印机打印 只能通过wifi来打印,

直接在HTML中调用window.print() 就可以拉起打印服务。

这样就无法选蓝牙打印机了 只能选普通打印机 打印小票的打印机一般都是蓝牙的,

在HarmonyOS Next中,使用WebView打印小票可通过WebPrintManager实现。首先配置WebPrintManager,设置打印参数如纸张尺寸、边距等。然后通过WebView的loadUrl()加载网络地址,调用WebPrintManager的print()方法触发打印。注意确保网络地址返回的内容格式适合打印,并提前在设备上配置好打印机。需要声明ohos.permission.PRINT权限。

在HarmonyOS Next中通过WebView实现蓝牙打印的解决方案:

  1. 核心思路:
  • 使用WebView加载HTML内容
  • 通过Canvas将HTML内容转换为图片
  • 调用蓝牙打印API打印图片
  1. 关键实现步骤:
// 1. 加载WebView
webView.load(htmlUrl);

// 2. 获取WebView内容并转换为Canvas
const canvas = new Canvas();
webView.captureAsImage(canvas);

// 3. 初始化蓝牙打印
const printManager = print.createPrintManager();
const printer = printManager.getBluetoothPrinter(deviceId);

// 4. 打印配置
const printConfig = {
    paperSize: '80mm', // 小票常用宽度
    orientation: 'portrait'
};

// 5. 执行打印
printer.print(canvas.toPixelMap(), printConfig)
    .then(() => {
        console.log('打印成功');
    })
    .catch(err => {
        console.error('打印失败:', err);
    });
  1. 注意事项:
  • 需要先配对蓝牙打印机
  • 确保HTML内容适配小票宽度(通常80mm)
  • 可能需要处理HTML中的样式,避免在小票上显示不全
  • 需要申请ohos.permission.PRINT权限
  1. 兼容性处理:
  • 对于复杂HTML内容,建议先简化布局
  • 长内容需要分页处理
  • 测试不同蓝牙打印机的兼容性

这种方法不需要直接操作WebView的打印接口,而是通过中间图像转换的方式实现蓝牙打印。

回到顶部