electron@7.2.4实现打印功能

一、background.js,项目入口配置文件


import { app, protocol, BrowserWindow, ipcMain } from 'electron'

/*
* 
* 省略多数默认配置
* 
* */


/*
* 打印
* */

//在主线程下,通过ipcMain对象监听渲染线程传过来的getPrinterList事件
ipcMain.on('getPrinterList', (event) => {
  //主线程获取打印机列表
  const list = win.webContents.getPrinters();

  //通过webContents发送事件到渲染线程,同时将打印机列表也传过去
  win.webContents.send('getPrinterList', list);
});


二、printerDiff.vue,打印组件,在components里面创建

<template>
  <div class="container">
    <webview id="printWebview" ref="printWebview" :src="fullPath" nodeintegration/>
    <printDialog :dialog-visible="dialogVisible" @cancel="handlePrintDialogCancel" @select-print="printSelectAfter"/>
  </div>
</template>
<script>
  const {ipcRenderer} = window.require('electron')
  import path from 'path'
  import printDialog from '@/components/PrintDialog.vue'
  import { Message } from 'element-ui'


  export default {
    name: 'Pinter',
    components: {
      printDialog
    },
    props: {
      // HtmlData: {
      //   type: String,
      //   default: '',
      // },
    },
    data () {
      return {
        printList: [],
        dialogVisible: false,
        printDeviceName: '',
        fullPath: path.join(__static, 'print.html'),
        messageBox: null,
        htmlData: ''
      }
    },

    mounted () {
      const webview = this.$refs.printWebview
      webview.addEventListener('ipc-message', async event => {
        if (event.channel === 'webview-print-do') {
          await webview.print({
              silent: true,
              printBackground: true,
              deviceName: this.printDeviceName
          })
        }
      })

    },
    methods: {
      print (val) {
        this.htmlData = val
        this.getPrintListHandle()
      },
      // 获取打印机列表
      getPrintListHandle () {
        // 改用ipc异步方式获取列表,解决打印列数量多的时候导致卡死的问题
        ipcRenderer.send('getPrinterList')
        ipcRenderer.once('getPrinterList', (event, data) => {
          // 过滤可用打印机
          this.printList = data.filter(element => element.status === 0)
          // 1.判断是否有打印服务
          if (this.printList.length <= 0) {
            Message.info('打印服务异常,请尝试重启电脑')
            this.$emit('cancel')
          }
          else {
            this.dialogVisible = true
//            this.checkPrinter()
          }
        })
      },
      // 2.判断打印机状态
      checkPrinter () {
        // 本地获取打印机
        const printerName = this.$util.getLocalStorage('printForm')
        const printer = this.printList.find(device => device.name === printerName)
        // 有打印机设备并且状态正常直接打印
        if (printer && printer.status === 0) {
          this.printDeviceName = printerName
          this.printRender()
        }
        else if (printerName === '') {
          Message.info('请先设置其他打印机')
          this.dialogVisible = true
          this.$emit('cancel')
        }
        else {
          Message.info('当前打印机不可用,请重新设置')
          this.dialogVisible = true
        }
      },

      handlePrintDialogCancel () {
        this.$emit('cancel')
        this.dialogVisible = false
      },
      printSelectAfter (val) {
        this.dialogVisible = false
        this.$util.setLocalStorage('printForm', val.name)
        this.printDeviceName = val.name
        this.printRender()
      },
      printRender (html) {
        Message.info('打印中,请稍后')
        console.log(this.printDeviceName);
        console.log(this.htmlData);
        // 获取<webview>节点
        const webview = this.$refs.printWebview
        // 发送信息到<webview>里的页面
        webview.send('webview-print-render', {
          printName: this.printDeviceName,
          html: this.htmlData
        })
      }
    }
  }
</script>
<style scoped>
  .container {
    position: fixed;
    right: -500px;
  }
</style>

__static无法使用的时候,.eslintrc.js文件添加

globals: {
__static: true
}

module.exports = {
  root: true,
  env: {
    node: true
  },
  'extends': [
    'plugin:vue/essential',
    'eslint:recommended'
  ],
  rules: {
    'no-unused-vars': 'off',
    'no-console': 'off',
    'no-debugger': process.env.NODE_ENV === 'production' ? 'error' : 'off'
  },
  parserOptions: {
    parser: 'babel-eslint'
  },
  globals: {
    __static: true
  },
}

不能直接使用require,需要使用

window.require(‘electron’)

注意

一定要这样写,不要像大部分网络案例写回调,写回调将会报错
webview.print({
silent: true,
printBackground: true,
deviceName: this.printDeviceName
})

添加回调报错

在这里插入图片描述


三、PrintDialog.vue,打印机列表组件,在components里面创建

this.$util.getLocalStorage(‘printForm’)是获取缓存里面打印机名称,自定义封装的方法,具体写法随意
<template>
  <div>
    <el-dialog width="300px" :visible="dialogVisible" :append-to-body="true" :show-close="false" title="打印机设置">
      <el-table :data="printList" highlight-current-row border @current-change="handleCurrentChange">
        <el-table-column label="打印机名称">
          <template slot-scope="scope">
            {{ scope.row.name }}
            <!--<el-tag v-if="scope.row.name==printName" type="primary" disable-transitions>默认</el-tag>-->
          </template>
        </el-table-column>
        <div slot="empty">
          暂无可用打印机
        </div>
      </el-table>
      <div class="buttonStyle">
        <el-button @click="$emit('cancel')">取消</el-button>
        <el-button type="primary" @click="checkPrinter">确认</el-button>
      </div>
    </el-dialog>
  </div>
</template>
<script>

  const {ipcRenderer} = window.require('electron')
  import { Message } from 'element-ui'

  export default {
    name: '',
    props: {
      dialogVisible: {
        type: Boolean,
        default: false
      }
    },
    data () {
      return {
        rowData: null,
        printList: [],
      }
    },
    computed: {
      printName(){
        return this.$util.getLocalStorage('printForm')
      }
    },
    watch: {
      dialogVisible: {
        immediate: true,
        handler: 'getPrintListHandle'
      },
    },
    methods: {
      // 获取打印机列表
      getPrintListHandle (dialogVisible) {
        if (!dialogVisible) {
          return
        }

        // 改用ipc异步方式获取列表,解决打印列数量多的时候导致卡死的问题
        ipcRenderer.send('getPrinterList')
        ipcRenderer.once('getPrinterList', (event, data) => {
          // 过滤可用打印机
          this.printList = data.filter(element => element.status === 0)
        })
      },
      handleCurrentChange (row) {
        this.rowData = row
      },
      // 取消
      cancel () {
        this.dialogVisible = false
      },
      checkPrinter () {
        // 本地获取打印机
        const printerName = this.$util.getLocalStorage('printForm')
        const printer = this.printList.find(device => device.name === printerName)
        // 有打印机设备并且状态正常直接打印
        if (printer && printer.status === 0) {
          this.selectPrint()
        }
        else if (printerName === '') {
          Message.info('请先设置其他打印机')
        }
        else {
          Message.info('当前打印机不可用,请重新设置')
        }
      },
      selectPrint () {
        if (this.rowData) {
          this.$util.setLocalStorage('printForm', this.rowData.name)
          this.$emit('select-print', this.rowData)
        }
        else {
          Message.info('您还没有选择打印机')
        }
      },
    }
  }
</script>

<style scoped>
  .buttonStyle {
    text-align: right;
    margin-top: 20px;
  }
</style>


四、Login.vue,页面

<template>
  <div>

    <printerDiff ref="printRef" :html-data="htmlData"></printerDiff>

  </div>

</template>

<script>
  import printerDiff from '@/components/printerDiff.vue'
  import { Message } from 'element-ui'
  const path = window.require('path')


  export default {
    name: 'Login',
    data () {
      return {
        printList: [],
        fullPath: path.join(__static, 'print.html'),
        printDeviceName: '',
        htmlData: '我是小仙女',
      }
    },

    methods: {
     // 获取打印机列表
     doPrint() {
       if(this.$util.getLocalStorage('printForm') == null){
         // 改用ipc异步方式获取列表,解决打印列数量多的时候导致卡死的问题
         ipcRenderer.send('getPrinterList')
         ipcRenderer.once('getPrinterList', (event, data) => {
           // 过滤可用打印机
           this.printList = data.filter(element => element.status === 0)
           // 1.判断是否有打印服务
           if (this.printList.length <= 0) {
             Message.error('打印服务异常,请尝试重启电脑')
           } else {
             this.$util.setLocalStorage('printForm', this.printList[0].name)
             this.$refs.printRef.print(this.htmlData)
           }
         })
       } else {
         this.$refs.printRef.print(this.htmlData)
       }
     },

    },
    components: {
      printerDiff
    }
  }
</script>

<style lang="scss" scoped>
  

</style>


五、在public目录创建print.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8"/>
    <meta name="viewport" content="width=device-width, initial-scale=1.0"/>
    <meta http-equiv="X-UA-Compatible" content="ie=edge"/>
    <title>Document</title>
    <style>
        body,
        html {
            padding: 0;
            margin: 0;
            font-size: 30px;
        }

        @page {
            margin: 0px;
        }

        .title {
            font-size: 16px;
            padding: 10px 0;
            border-bottom: 1px solid #333333;
        }
    </style>
</head>

<body id="bd"></body>

<script>
  const {ipcRenderer} = window.require('electron')
  ipcRenderer.on('webview-print-render', (event, info) => {
    let obj = ''
    obj += `<div class="title">${info.html}</div>`
    // 执行渲染
    document.getElementById('bd').innerHTML = obj
    ipcRenderer.sendToHost('webview-print-do')
  })
</script>
</html>

  • 3
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 3
    评论
实现Vue3 + Vite + Electron打印功能,你可以按照以下步骤进行。 1. 安装Electron 在项目中安装Electron,你可以使用npm命令进行安装: ``` npm install electron --save-dev ``` 2. 创建Electron应用程序 在应用程序的主目录中创建一个名为main.js的文件,并在其中创建一个Electron应用程序: ```javascript const { app, BrowserWindow } = require('electron') function createWindow () { const win = new BrowserWindow({ width: 800, height: 600, webPreferences: { nodeIntegration: true } }) win.loadURL('http://localhost:3000') win.webContents.on('did-finish-load', () => { win.webContents.print() }) } app.on('ready', createWindow) ``` 在这个示例中,我们创建了一个Electron窗口,并在窗口加载完成时执行打印操作。 3. 打印Vue3组件 在Vue3组件中,你可以使用window.print()方法来实现打印功能。例如,在一个名为PrintButton.vue的组件中: ```html <template> <button @click="print">打印</button> </template> <script> export default { methods: { print() { window.print() } } } </script> ``` 在这个示例中,我们在组件中创建了一个打印按钮,并在按钮点击时执行打印操作。 4. 运行应用程序 现在,你可以在终端运行Electron应用程序,并访问http://localhost:3000来测试打印功能: ``` electron . ``` 如果一切正常,你应该能够在Electron窗口中看到你的Vue3应用程序,并且能够通过按钮打印内容。 这就是使用Vue3 + Vite + Electron实现打印功能的基本步骤。当然,你还可以根据自己的需求进行更多的定制和优化。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值