Vue 3+Vite+Eectron从入门到实战系列之(五)一后台管理登录页
前面已经讲了不少基础知识,这篇开始,我们进行实操,做个后台管理系统,打包成多端的,可安装的桌面app!!其中,登录,退出的提示信息用系统的提示,不使用elemengplus的弹窗提示!!

实现效果

核心代码实现
- login.vue文件
<template><div class="login-form animated puffIn"><div class="login-form__left"></div><div class="login-form__right"><h2>荣耀科技财务管理系统</h2><el-form:model="loginForm"ref="loginFormRef"size="large"show-messagelabel-position="top"label-width="100px":rules="rules"status-icon><el-form-item label="用户名:" prop="username"><el-inputv-model="loginForm.username"placeholder="请输入用户名"></el-input></el-form-item><el-form-item label="密码:" prop="password"><el-inputtype="password"v-model="loginForm.password"placeholder="请输入密码"></el-input></el-form-item><el-form-item><el-buttonclass="login-btn"type="primary"@keydown.enter="handleKeyDownLogin"@click.native.prevent="handleLogin">登录</el-button></el-form-item><el-form-item><el-buttonclass="registry-btn"type="success"@click.native.prevent="handleRegister">注册</el-button></el-form-item><el-form-item><div class="login-ctrl"><el-checkboxlabel="记住我"v-model="loginForm.checked"></el-checkbox><el-link type="primary">忘记密码?</el-link></div></el-form-item></el-form></div></div>
</template><script setup>
import { ref, reactive, toRaw, onMounted, onUnmounted } from 'vue'
import userStore from '@/store/user'
import { useRouter } from 'vue-router'const loginFormRef = ref(null)
const router = useRouter()
const sysUser = userStore()
const rules = reactive({username: [{ required: true, message: '用户名不能为空', trigger: 'blur' },{ min: 3, max: 5, message: '用户名长度必须是3到5位', trigger: 'blur' }],password: [{required: true,message: '密码不能为空',trigger: 'change'},{ min: 6, max: 6, message: '用户名长度必须是6位', trigger: 'blur' }]
})
const loginForm = ref({username: '',password: '',checked: false
})const handleKeyDownLogin = (e) => {if (e.keyCode === 13) {handleLogin()}
}onMounted(() => {window.addEventListener('keydown', handleKeyDownLogin)
})
onUnmounted(() => {window.removeEventListener('keydown', handleKeyDownLogin)
})const handleLogin = async () => {const status = await loginFormRef.value.validate()if (status) {const data = toRaw(loginForm.value)const isLogin = await sysUser.sysLogin(data)// 跳转到首页if (isLogin) {router.push('/')} else {window.electronAPI.loginError()}} else {}
}
const handleRegister = () => {console.log('register')window.electronAPI.register()
}
</script><style scoped lang="scss">
.login-form {padding: 0 20px 0 0;border: 1px solid #f7f7f7;border-radius: 20px;box-shadow: 0 0 30px #c1c1c1;background: rgba(255, 255, 255, 0.5);position: absolute;top: 20%;right: 300px;display: flex;&__left {width: 480px;height: 500px;background: url(../../assets/images/bg1.png) no-repeat center center;background-size: 100% 100%;}&__right {width: 480px;height: 500px;padding: 20px;box-sizing: border-box;h2 {text-align: center;margin-bottom: 30px;font-size: 32px;font-weight: bold;color: #333;}.login-ctrl {display: flex;justify-content: space-between;width: 100%;}.el-button {width: 100%;}.login-btn {background: linear-gradient(147deg,#8ec5fc 13.33%,#1a2cab 46.22%,#610cb3 87.97%);border: none;}}
}
</style>
- pinia的配置
import { createPinia } from "pinia";
const pinia = createPinia();export default pinia;
登录退出功能的store
import { defineStore } from 'pinia'
const userStore = defineStore('user', {state: () => ({userInfo: {name: 'admin',avatar: '',roles: ['admin'],introduction: 'I am a super administrator'},token: window.localStorage.getItem('token')}),getters: {username() {return this.userInfo.name}},actions: {setToken(token) {this.token = token},setUserInfo(userInfo) {this.userInfo = userInfo},sysLogin(data) {return new Promise((resolve, reject) => {if (data.username === 'admin' && data.password === '123456') {window.electronAPI.loginSuccess(data)// 登录成功后,将token存入本地this.setToken(data.username)window.localStorage.setItem('token', data.username)resolve(true)} else {window.electronAPI.loginError()}})},sysLogout() {return new Promise((resolve, reject) => {window.electronAPI.logout()this.setToken('')window.localStorage.removeItem('token')resolve(true)})}}
})
export default userStore
菜单收起展开的store
import { defineStore } from "pinia";
const useSysStore = defineStore("sys", {state: () => ({collapse: false,}),getters: {isCollapse() {return this.collapse;},},actions: {toggleCollapse() {console.log(this.collapse);this.collapse = !this.collapse;},},
});
export default useSysStore;
打包
npm run ele:build
打包文件里面安装到本地即可以使用

注意事项
- win11的弹窗是正常显示

如果电脑系统是win10,很可能弹不出右下角的系统弹窗,是系统处于安全角度的考虑,但是mac和win11是没有问题的,这里贴出解决方案。
electron在win10不弹窗的bug
相关文章:
Vue 3+Vite+Eectron从入门到实战系列之(五)一后台管理登录页
前面已经讲了不少基础知识,这篇开始,我们进行实操,做个后台管理系统,打包成多端的,可安装的桌面app!!其中,登录,退出的提示信息用系统的提示,不使用elemengplus的弹窗提示!ÿ…...
Docker 网络代理配置及防火墙设置指南
Docker 网络代理配置及防火墙设置指南 背景 在某些环境中,服务器无法直接访问外网,需要通过网络代理进行连接。虽然我们通常会在 /etc/environment 或 /etc/profile 等系统配置文件中直接配置代理,但 Docker 命令无法使用这些配置。例如&am…...
基于PostGIS(Postgres)+Node.js实现的xyz瓦片地图服务器
背景介绍 前两天研究GeoServer发布存储在PostGIS中栅格数据,最终目的是想在PostGIS中存储金字塔瓦片,用GeoServer发布,但是最后经过研究不改GeoServer源码的情况下,好像只支持将大图tif存在PostGIS数据库中进行发布,金…...
浙大数据结构慕课课后题(06-图3 六度空间)
题目要求: 输入格式: 输入第1行给出两个正整数,分别表示社交网络图的结点数N(1<N≤103,表示人数)、边数M(≤33N,表示社交关系数)。随后的M行对应M条边,每行给出一对正…...
Windows File Recovery卡在99%怎么解决?实用指南!
为什么会出现“Windows File Recovery卡在99%”的问题? Windows File Recovery(Windows文件恢复)是微软设计的命令行应用程序。它可以帮助用户从健康/损坏/格式化的存储设备中恢复已删除/丢失的文件。 通过输入相关命令,设置源/…...
数据结构之数组
写在前面 看下数组。 1:巴拉巴拉 数组是一种线性数据结构,使用连续的内存空间来存储数据,存储的数据要求有相同的数据类型,并且每个元素占用的内存空间相同。获取元素速度非常快,为O(1)常量时间复杂度,所…...
springboot集成sensitive-word实现敏感词过滤
文章目录 敏感词过滤方案一:正则表达式方案二:基于DFA算法的敏感词过滤工具框架-sensitive-wordspringboot集成sensitive-word步骤一:引入pom步骤二:自定义配置步骤三:自定义敏感词白名单步骤四:核心方法测…...
C++ 之动手写 Reactor 服务器模型(一):网络编程基础复习总结
基础 IP 地址可以在网络环境中唯一标识一台主机。 端口号可以在主机中唯一标识一个进程。 所以在网络环境中唯一标识一个进程可以使用 IP 地址与端口号 Port 。 字节序 TCP/IP协议规定,网络数据流应采用大端字节序。 大端:低地址存高位,…...
qt 在vs2022 报错记录
1,qt.network.ssl: QSslSocket::connectToHostEncrypted: TLS initialization failed 需要把SSL 相关的库加入进去,如ssleay32.dll,libeay32.dll。 2,在一个文件中已定义,编译器在链接时,在多处报 已在.*…...
【人工智能】TensorFlow和机器学习概述
一、TensorFlow概述 TensorFlow是由Google Brain团队开发的开源机器学习库,用于各种复杂的数学计算,特别是在深度学习领域。以下是对TensorFlow的详细概述: 1. 核心概念 张量(Tensor):TensorFlow中的基本…...
SQLALchemy 的介绍
SQLALchemy 的介绍 基本概述主要特点使用场景安装与配置安装 SQLAlchemy配置 SQLAlchemy示例:使用 SQLite 数据库连接到其他数据库 结论 总结 SQLAlchemy是Python编程语言下的一款开源软件,它提供了SQL工具包及对象关系映射(ORM)工…...
Java虚拟机:运行时内存结构
大家好,我是栗筝i,这篇文章是我的 “栗筝i 的 Java 技术栈” 专栏的第 035 篇文章,在 “栗筝i 的 Java 技术栈” 这个专栏中我会持续为大家更新 Java 技术相关全套技术栈内容。专栏的主要目标是已经有一定 Java 开发经验,并希望进…...
微信小程序子组件调用父组件的方法
来源:通义千文2.5 步骤 1: 定义父组件中的方法 首先,在父组件中定义一个方法(如 handleClick),并准备一个用于接收子组件传来的数据的方法。 父组件(Parent.wxml) html<!-- parent.wxml …...
【数据结构】TreeMap和TreeSet
目录 前言TreeMap实现的接口内部类常用方法 TreeSet实现的接口常用方法 前言 Map和set是一种专门用来进行搜索的容器或者数据结构,其搜索的效率与其具体的实例化子类有关。 一般把搜索的数据称为关键字(Key), 和关键字对应的称为…...
前端react集成OIDC
文章目录 OpenID Connect (OIDC)3种 授权模式 【服务端】express 集成OIDC【前端】react 集成OIDCoidc-client-js库 原生集成react-oidc-context 库非组件获取user信息 OAuth 2.0 协议主要用于资源授权。 OpenID Connect (OIDC) https://openid.net/specs/openid-connect-core…...
JavaWeb—XML_Tomcat10_HTTP
一、XML XML是EXtensible MarkupLanguage的缩写,翻译过来就是可扩展标记语言。所以很明显,XML和HTML一样都是标记语言,也就是说它们的基本语法都是标签。 可扩展:三个字表面上的意思是XML允许自定义格式。但这不代表你可以随便写; 在XML基…...
中介者模式在Java中的实现:设计模式精解
中介者模式在Java中的实现:设计模式精解 中介者模式(Mediator Pattern)是一种行为型设计模式,用于定义一个中介者对象,以封装一系列对象之间的交互,从而使对象之间的交互不再直接发生,减少了系…...
PyQt编程快速上手
Python GUI安装 GUI就是图形用户界面的意思,在Python中使用PyQt可以快速搭建自己的应用,使得自己的程序看上去更加高大上,学会GUI编程可以使得自己的软件有可视化的结果。 如果你想用Python快速制作界面,可以安装PyQt:…...
Docker Swarm管理
Docker Swarm管理 前置知识点 Docker Swarm 是 Docker 公司 2014年出品的基于 Docker 的集群管理调度工具,能够将多台主机构建成一个Docker集群,并结合Overlay网络实现容器调度的互访 用户可以只通过 Swarm API 来管理多个主机上的 Docker Swarm 群集包…...
Python | Leetcode Python题解之第335题路径交叉
题目: 题解: class Solution:def isSelfCrossing(self, distance: List[int]) -> bool:n len(distance)# 处理第 1 种情况i 0while i < n and (i < 2 or distance[i] > distance[i - 2]):i 1if i n:return False# 处理第 j 次移动的情况…...
synchronized 学习
学习源: https://www.bilibili.com/video/BV1aJ411V763?spm_id_from333.788.videopod.episodes&vd_source32e1c41a9370911ab06d12fbc36c4ebc 1.应用场景 不超卖,也要考虑性能问题(场景) 2.常见面试问题: sync出…...
TDengine 快速体验(Docker 镜像方式)
简介 TDengine 可以通过安装包、Docker 镜像 及云服务快速体验 TDengine 的功能,本节首先介绍如何通过 Docker 快速体验 TDengine,然后介绍如何在 Docker 环境下体验 TDengine 的写入和查询功能。如果你不熟悉 Docker,请使用 安装包的方式快…...
day52 ResNet18 CBAM
在深度学习的旅程中,我们不断探索如何提升模型的性能。今天,我将分享我在 ResNet18 模型中插入 CBAM(Convolutional Block Attention Module)模块,并采用分阶段微调策略的实践过程。通过这个过程,我不仅提升…...
uni-app学习笔记二十二---使用vite.config.js全局导入常用依赖
在前面的练习中,每个页面需要使用ref,onShow等生命周期钩子函数时都需要像下面这样导入 import {onMounted, ref} from "vue" 如果不想每个页面都导入,需要使用node.js命令npm安装unplugin-auto-import npm install unplugin-au…...
系统设计 --- MongoDB亿级数据查询优化策略
系统设计 --- MongoDB亿级数据查询分表策略 背景Solution --- 分表 背景 使用audit log实现Audi Trail功能 Audit Trail范围: 六个月数据量: 每秒5-7条audi log,共计7千万 – 1亿条数据需要实现全文检索按照时间倒序因为license问题,不能使用ELK只能使用…...
Mac软件卸载指南,简单易懂!
刚和Adobe分手,它却总在Library里给你写"回忆录"?卸载的Final Cut Pro像电子幽灵般阴魂不散?总是会有残留文件,别慌!这份Mac软件卸载指南,将用最硬核的方式教你"数字分手术"࿰…...
DBAPI如何优雅的获取单条数据
API如何优雅的获取单条数据 案例一 对于查询类API,查询的是单条数据,比如根据主键ID查询用户信息,sql如下: select id, name, age from user where id #{id}API默认返回的数据格式是多条的,如下: {&qu…...
CMake 从 GitHub 下载第三方库并使用
有时我们希望直接使用 GitHub 上的开源库,而不想手动下载、编译和安装。 可以利用 CMake 提供的 FetchContent 模块来实现自动下载、构建和链接第三方库。 FetchContent 命令官方文档✅ 示例代码 我们将以 fmt 这个流行的格式化库为例,演示如何: 使用 FetchContent 从 GitH…...
【7色560页】职场可视化逻辑图高级数据分析PPT模版
7种色调职场工作汇报PPT,橙蓝、黑红、红蓝、蓝橙灰、浅蓝、浅绿、深蓝七种色调模版 【7色560页】职场可视化逻辑图高级数据分析PPT模版:职场可视化逻辑图分析PPT模版https://pan.quark.cn/s/78aeabbd92d1...
《C++ 模板》
目录 函数模板 类模板 非类型模板参数 模板特化 函数模板特化 类模板的特化 模板,就像一个模具,里面可以将不同类型的材料做成一个形状,其分为函数模板和类模板。 函数模板 函数模板可以简化函数重载的代码。格式:templa…...
