使用 electron 实现类似新版 QQ 的登录界面效果(阴影、背景动画、窗体3D翻转)

yizhihongxing

使用 Electron 实现类似新版 QQ 的登录界面效果,需要注意以下几点:

1. 创建 Electron 项目

使用命令行创建一个新的 Electron 项目,进入项目文件夹后安装必要的依赖:

# 初始化项目
npm init
# 安装 electron
npm install electron --save
# 安装 jquery 和 bootstrap
npm install jquery bootstrap --save

为了实现窗体的旋转效果,我们使用 CSS 3D Transform 这个特性。这里我们还需要引入一个元素,使得窗体可以进行翻转。我使用的是 Flipster,一个 jQuery 插件。安装 Flipster:

npm install flipster --save

2. 编写登录窗口的 HTML 和 CSS

在项目的根目录下,创建一个名为 index.html 的文件,并添加下面的 html 代码:

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>QQ Login</title>
    <!-- 引入 bootstrap 样式文件 -->
    <link rel="stylesheet" href="./node_modules/bootstrap/dist/css/bootstrap.min.css">
    <!-- 引入 flipster 样式文件 -->
    <link rel="stylesheet" href="./node_modules/flipster/dist/jquery.flipster.min.css">
    <!-- 引入自己的样式文件 -->
    <link rel="stylesheet" href="./src/style.css">
</head>
<body>
    <div class="container">
        <div class="login-form-wrapper">
            <form class="login-form">
                <h3>Please Login</h3>
                <div class="form-group">
                    <input type="text" placeholder="Username" class="form-control">
                </div>
                <div class="form-group">
                    <input type="password" placeholder="Password" class="form-control">
                </div>
                <button type="submit" class="btn btn-primary">Login</button>
            </form>
            <!-- 构建翻转窗体 -->
            <ul id="flipster-wrapper">
                <li><img src="./res/1.jpg"></li>
                <li><img src="./res/2.jpg"></li>
                <li><img src="./res/3.jpg"></li>
                <li><img src="./res/4.jpg"></li>
            </ul>
        </div>
    </div>
    <!-- 引入 jQuery -->
    <script src="./node_modules/jquery/dist/jquery.min.js"></script>
    <!-- 引入 bootstrap.js -->
    <script src="./node_modules/bootstrap/dist/js/bootstrap.min.js"></script>
    <!-- 引入 flipster.js -->
    <script src="./node_modules/flipster/dist/jquery.flipster.min.js"></script>
    <!-- 引入自己的脚本文件 -->
    <script src="./src/main.js"></script>
</body>
</html>

接下来在项目的根目录下,创建一个名为 style.css 的样式文件,并添加下列代码:

body {
    margin: 0;
    background-color: #f3f3f3;
    font-family: 'Roboto', sans-serif;
}

.container {
    background-color: transparent;
    height: 100%;
    display: flex;
    justify-content: center;
    align-items: center;
}

.login-form-wrapper {
    position: absolute;
    width: 450px;
    height: 400px;
    background-color: #fff;
    box-shadow: 0 2px 8px rgba(102, 119, 136, 0.1);
    border-radius: 3px;
    overflow: hidden;
}

.login-form-wrapper .login-form {
    padding: 30px;
}

.login-form-wrapper h3 {
    margin-top: 0;
    margin-bottom: 20px;
    font-size: 24px;
    font-weight: 400;
    color: #333;
}

.form-group {
    margin-bottom: 20px;
}

.form-control {
    box-shadow: none;
    border-radius: 2px;
    border-color: #dcdcdc;
    height: 50px;
    font-size: 16px;
}

.btn-primary {
    background-color: #007bff;
    border-color: #007bff;
    padding: 12px 18px;
    font-size: 16px;
    border-radius: 2px;
}

.btn-primary:hover {
    background-color: #0069d9;
}

/* 翻转窗体相关 */
#flipster-wrapper {
    margin: 70px auto 0;
}

#flipster-wrapper li {
    margin-bottom: 20px;
    border-radius: 2px;
    box-shadow: 0 2px 4px rgba(0,0,0,0.1);
}

#flipster-wrapper img {
    display: block;
    width: 100%;
    border-radius: 2px;
}

3. 编写 Electron 主进程代码和渲染进程代码

需要注意的是,我们需要使用 这个标签来开启和禁用部分 Electron 特性来达到最佳的运行效果。

在根目录下,创建一个名为 main.js 的文件,添加如下代码:

const { app, BrowserWindow } = require('electron')

let mainWindow = null

app.on('ready', function() {
    mainWindow = new BrowserWindow({
        width: 450,
        height: 400,
        frame: false, // 隐藏默认窗口栏
        resizable: false, // 禁止窗口大小缩放
        transparent: true, // 窗口透明
        show: false, // 创建窗口时先不显示
        webPreferences: {
            nodeIntegration: true // 开启 Node.js
        }
    })

    // 加载 HTML 文件
    mainWindow.loadFile('./index.html')

    // 当最初的 html 文件加载完成时触发
    mainWindow.once('ready-to-show', () => {
        mainWindow.show() // 显示窗口
    })

    // 监听渲染器进程发来的 ipc 消息
    const { ipcMain } = require('electron')
    ipcMain.on('window-close', () => {
        if (mainWindow !== null) {
            mainWindow.close()
        }
    })
})

在根目录下,创建一个名为 renderer.js 的文件,添加如下代码:

$(function () {
    // 初始化 flipster
    $('#flipster-wrapper').flipster({
        style: 'carousel',
        spacing: -0.5,
        buttons: true,
        nav: false,
        start: 1,
        loop: true
    })

    // 窗口拖动
    var _electron = require('electron')
    var remote = _electron.remote
    var win = remote.getCurrentWindow()
    var drag = document.querySelector('.login-form-wrapper')

    drag.addEventListener('mousedown', function (e) {
        if (e.button !== 0) {
            return
        }

        win.setIgnoreMouseEvents(true)
        var mousePos = null

        document.addEventListener('mousemove', moveCallback, true)
        document.addEventListener('mouseup', mouseupCallback, true)

        function moveCallback (e) {
            e.preventDefault()

            var pos
            if (mousePos === null) {
                mousePos = {
                    x: e.screenX,
                    y: e.screenY
                }
            } else {
                pos = {
                    x: e.screenX - mousePos.x,
                    y: e.screenY - mousePos.y
                }

                win.setPosition(remote.screen.getCursorScreenPoint().x - pos.x, remote.screen.getCursorScreenPoint().y - pos.y)
            }

            mousePos = {
                x: e.screenX,
                y: e.screenY
            }
        }

        function mouseupCallback () {
            win.setIgnoreMouseEvents(false)
            document.removeEventListener('mousemove', moveCallback, true)
            document.removeEventListener('mouseup', mouseupCallback, true)
        }
    })
})

4. 编写菜单和 ipc 监听器

const { Menu, MenuItem } = require('electron')
const { app, BrowserWindow, ipcMain } = require('electron')

app.on('ready', function() {
    const mainWindow = new BrowserWindow({
        width: 700,
        height: 500,
        webPreferences: {
            nodeIntegration: true
        }
    })

    mainWindow.loadFile('index.html')

    mainWindow.webContents.on('did-finish-load', () => {
        const menu = Menu.buildFromTemplate([
            {
                label: 'File',
                submenu: [
                    {
                        label: 'Close',
                        accelerator: 'CmdOrCtrl+W',
                        click() {
                            mainWindow.close()
                        }
                    }
                ]
            },
            {
                label: 'Edit',
                submenu: [
                    {
                        label: 'Undo',
                        accelerator: 'CmdOrCtrl+Z',
                        selector: 'undo:'
                    },
                    {
                        label: 'Redo',
                        accelerator: 'Shift+CmdOrCtrl+Z',
                        selector: 'redo:'
                    },
                    {
                        type: 'separator'
                    },
                    {
                        label: 'Copy',
                        accelerator: 'CmdOrCtrl+C',
                        selector: 'copy:'
                    },
                    {
                        label: 'Cut',
                        accelerator: 'CmdOrCtrl+X',
                        selector: 'cut:'
                    },
                    {
                        label: 'Paste',
                        accelerator: 'CmdOrCtrl+V',
                        selector: 'paste:'
                    },
                    {
                        label: 'Select All',
                        accelerator: 'CmdOrCtrl+A',
                        selector: 'selectAll:'
                    }
                ]
            }
        ])

        ipcMain.on('show-context-menu', (event) => {
            event.preventDefault()
            menu.popup({ window: mainWindow })
        })

        mainWindow.webContents.on('context-menu', (event) => {
            event.preventDefault()
            ipcMain.emit('show-context-menu', event)
        })
    })
})

5. 运行

最后,打开终端,进入项目根目录下,运行以下命令启动应用:

npm start

应用启动后,可以看到类似 QQ 登录界面的效果,窗体可以旋转,同时支持菜单和 ipc 监听器。

示例1: 参考代码

示例2: 参考代码

本站文章如无特殊说明,均为本站原创,如若转载,请注明出处:使用 electron 实现类似新版 QQ 的登录界面效果(阴影、背景动画、窗体3D翻转) - Python技术站

(0)
上一篇 2023年6月11日
下一篇 2023年6月11日

相关文章

  • HTML设计模式日常学习笔记整理

    HTML设计模式日常学习笔记整理 什么是HTML设计模式? HTML设计模式是用于解耦HTML和CSS的一种技术。通过将网页设计划分为多个模块,每个模块负责不同的功能和样式,从而达到可复用性和可维护性的目的。同时,这种技术能够增加代码的可读性,便于多人协作开发和代码重构。 实践攻略 第一步:制定设计方案 在进行HTML设计模式开发前,需要先进行设计方案的制定…

    css 2023年6月10日
    00
  • 使用Vite处理css less及postcss示例详解

    使用Vite处理css、less及postcss示例详解 在前端开发中,我们常常需要处理各种css预处理器,并采用postcss工具进行后处理。Vite工具可以方便地处理这些过程,本篇攻略将详细介绍如何使用Vite处理css、less及postcss。 步骤一:安装Vite 首先需要安装Node.js和npm,然后在终端输入以下命令安装Vite: npm i…

    css 2023年6月9日
    00
  • CSS3之2D与3D变换的实现方法

    CSS3之2D与3D变换的实现方法 CSS3提供了非常丰富的2D和3D变换API,可以实现在网页中呈现出立体感和动态效果。本文将详细讲解CSS3 2D和3D变换的实现方法。 2D变换 CSS3提供了4种基本的2D变换:旋转(rotate)、缩放(scale)、倾斜(skew)和移动(translate)。下面将对每种变换进行详细讲解。 rotate rota…

    css 2023年6月10日
    00
  • 浅谈webpack4.x 入门(一篇足矣)

    浅谈webpack4.x 入门(一篇足矣)是一个webpack入门教程,主要讲解了webpack的基本概念和使用方式。下面是详细的攻略: 什么是webpack Webpack是一个打包工具,它可以将多个模块打包成一个文件,并且支持代码分割和模块化。在Web应用程序开发中,使用Webpack可以提高应用程序的性能和可维护性,同时也可以简化开发流程。 webpa…

    css 2023年6月9日
    00
  • Bootstrap 实现表格样式、表单布局的实例代码

    下面是关于“Bootstrap 实现表格样式、表单布局的实例代码”的攻略: Bootstrap 表格样式 Bootstrap 提供了多种表格样式,使用 table 类即可。如下是一个漂亮的、具有不同表格样式的 HTML 表格: <table class="table table-bordered table-hover table-strip…

    css 2023年6月10日
    00
  • vue项目引入百度地图BMapGL鼠标绘制和BMap辅助工具

    下面将详细说明如何在Vue项目中引入百度地图BMapGL鼠标绘制和BMap辅助工具。 步骤一:安装依赖 首先,需要在项目中安装百度地图JavaScript API,具体代码如下所示: npm install bmapgl –save 步骤二:引入百度地图相关的JS和CSS文件 在Vue项目中,可以在index.html文件中引入: <!DOCTYPE…

    css 2023年6月10日
    00
  • vue-element换肤所有主题色和基础色均可实现自主配置

    实现vue-element-admin换肤功能一般分为以下几个步骤: 安装依赖 npm install –save-dev style-resources-loader 配置less变量及全局样式 在src/styles/variables.scss中定义仪表盘样式,如下: @import ‘~element-theme-chalk/src/index’;…

    css 2023年6月9日
    00
  • jQuery插件animateSlide制作多点滑动幻灯片

    让我详细讲解一下“jQuery插件animateSlide制作多点滑动幻灯片”的完整攻略。 1. 准备工作 要制作一个jQuery插件animateSlide,需要先准备好以下工作: 安装jQuery库文件; 安装jQuery UI库文件; 编写html结构; 编写CSS样式; 编写JS代码。 2. 编写html结构 先来看一下一个基础的html结构: &l…

    css 2023年6月9日
    00
合作推广
合作推广
分享本页
返回顶部