Nodejs 我用 Electron 做了一个图片上传的工具——PicGo

发布于 1周前 作者 ionicwang 来自 nodejs/Nestjs

Nodejs 我用 Electron 做了一个图片上传的工具——PicGo

前言

作为一个比较常用 markdown 写文章、博客的人,在 markdown 里插入图片对我而言一直一个比较繁琐的活。以前每周写电影推荐的时候,我要在 markdown 里插入一张电影海报,我需要如下的操作:

  1. 打开豆瓣的网站,选一张满意的海报,下载
  2. 打开七牛的网站,登录,点点点,找到上传,上传
  3. 关闭上传窗口,找到地址,复制地址,再关闭七牛
  4. 粘贴到 markdown 里

每次都需要繁琐的打开网页进行一些必要而枯燥的操作。这样很麻烦。在用过 mac 上一款很不错的小工具应用 iPic 后我非常喜欢它的简洁操作。不过它免费版本并不支持七牛图床。所以我就想着,能不能自己写一个类似的工具呢?结合自己的使用习惯再顺便加点功能。

于是我就开始自己的图片上传工具的开发了。它叫做PicGo

技术选型

最早最早我想着用 swift 来写一个原生的应用,主要想着能做出体积友良、性能优秀的应用。不过鉴于 swift 迭代的太快,很多教程都已经不适合了。并且 swift 网上的教程对我这个小前端来说着实要学的东西不少。我只是想做个方便自己的工具而已,一切以方便自己作为大前提。作为一个前端工程师,我决定采用electron来开发。同时因为我是 Vue 的粉丝,一并就使用了electron-vue作为我的 electron 开发脚手架。不得不说,electron-vue提供的脚手架做的真的很用心,而且我自己要做修改加配置什么的也很方便。日后做跨平台支持的话也比较容易。

需求分析

由于用过 iPic,很多它的一些操作模式我觉得特别值得借鉴。比如我想要个简单的拖拽就能实现上传,我想要能够上传我剪贴板的图片,我想要是实现上传成功后自动复制链接到剪贴板,这样我就可以直接编辑了。

那么这样一来,我编辑文章只需要如下操作:

  • 找到要上传的图片,使用这个工具直接上传
  • 上传成功后自动复制地址到剪贴板,在 markdown 里直接粘贴

一下子省去了很多原本繁琐的操作!

功能展示

前前后后,用每天的闲暇时间从 0 开始学习 electron 框架,到 Travis-ci 构建出第一个可用的版本,大概花了一个月的时间。基本实现了我自己当初的目标,极大提升了我自己的文章写作体验。

操作演示

精致设计

macOS 系统下,支持拖拽至 menubar 图标实现上传。menubar app 窗口显示最新上传的 5 张图片以及剪贴板里的图片。点击图片自动将上传的链接复制到剪贴板。

便捷管理

查看你的上传记录,重复使用更方便。支持点击图片大图查看。支持删除图片(仅本地记录),让界面更加干净。

可选图床

目前支持微博图床和七牛图床。未来将支持更多。方便不同图床的上传需求。

多样链接

支持 4 种剪贴板链接格式,让你的文本编辑游刃有余。

后续工作

目前 PicGo 还是一个很年轻的项目,bug 肯定是不少的,功能方面也有所欠缺。所以还需要不断地完善。我希望大家在使用的过程中有什么意见或者建议都可以在项目仓库里的issues里提出来~

  • 目前暂不支持 Windows 和 linux,未来将会逐步支持。
  • 未来将支持更多的图床。如果可能,可以支持自定义的图床(只要设定好协议)
  • 将集成系统服务,提供一键上传的全局快捷键
  • 提升用户体验,修 bug

最后

希望这是一个能够提升你文章编辑体验的工具。如果你想学习 electron 开发,我也会在不久之后写几篇文章用于记录我是如何开发PicGo这个 electron 应用的。如果你喜欢它,欢迎给这个项目点个 Star。另外,它是开源免费的,如果你觉得它对你有所帮助,也可以考虑给我打赏一杯喝咖啡的钱~

支付宝:

微信:


3 回复

上传的时候,一直显示服务器错误,这是为什么

非常棒的选择!使用 Electron 和 Node.js 来开发一个图片上传工具(PicGo)是一个非常实用的项目。下面是一个简单的示例代码,展示了如何在 Electron 应用中实现图片上传功能。

首先,你需要安装 Electron 和一些必要的依赖:

npm install electron
npm install express multer --save

然后,你可以创建一个基本的 Electron 应用,并设置一个简单的服务器来处理文件上传。以下是一个简单的 main.js 文件示例:

const { app, BrowserWindow } = require('electron');
const path = require('path');
const express = require('express');
const multer = require('multer');

let mainWindow;

function createWindow() {
  mainWindow = new BrowserWindow({
    width: 800,
    height: 600,
    webPreferences: {
      preload: path.join(__dirname, 'preload.js')
    }
  });

  mainWindow.loadFile('index.html');
}

app.whenReady().then(createWindow);

app.on('window-all-closed', () => {
  if (process.platform !== 'darwin') {
    app.quit();
  }
});

app.on('activate', () => {
  if (BrowserWindow.getAllWindows().length === 0) {
    createWindow();
  }
});

// 简单的文件上传服务器
const appServer = express();
const storage = multer.diskStorage({
  destination: (req, file, cb) => {
    cb(null, 'uploads/');
  },
  filename: (req, file, cb) => {
    cb(null, file.fieldname + '-' + Date.now() + path.extname(file.originalname));
  }
});

const upload = multer({ storage: storage });

appServer.post('/upload', upload.single('image'), (req, res) => {
  res.send('File uploaded successfully');
});

appServer.listen(3000, () => {
  console.log('Server started on port 3000');
});

希望这能帮助你开始!

回到顶部