Skip to content

Commit

Permalink
electron
Browse files Browse the repository at this point in the history
  • Loading branch information
Elevista committed Jan 31, 2019
1 parent 11b7d3f commit afac10c
Show file tree
Hide file tree
Showing 12 changed files with 3,104 additions and 1,272 deletions.
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ node_modules
.vscode
.tscache
.idea
build
www/**
!www/favicon.ico
!www/index.html
104 changes: 104 additions & 0 deletions electron/Frame.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
<template>
<div class="frame" :class="{focus,menu}" tabindex="0">
<div class="title" @mousedown="menu&&$el.focus()">
<i></i>
<span class="name">Minsweeper</span>
<button class="min" @click="win.minimize()"></button>
<button class="max" disabled></button>
<button class="close" @click="win.close()"></button>
</div>
<App class="app" @changeLevel="resize" @menu="menu=$event"/>
</div>
</template>
<script>
import App from '../app/app.vue'
import { remote } from 'electron'
export default {
name: 'Frame',
components: { App },
data () { return { focus: true, menu: false } },
computed: { win: () => remote.getCurrentWindow() },
beforeMount () {
this.win.removeAllListeners('blur')
this.win.removeAllListeners('focus')
this.win.addListener('blur', () => { this.focus = false })
this.win.addListener('focus', () => { this.focus = true })
},
async mounted () {
this.win.setTitle('Minsweeper')
await this.resize()
this.win.show()
},
methods: {
test (evt) {
console.log(evt)
},
async resize () {
await this.$nextTick()
const { offsetWidth, offsetHeight } = this.$el
this.win.setResizable(true)
this.win.setSize(offsetWidth + 2, offsetHeight + 2) // margin: 1px
this.win.setResizable(false)
}
}
}
</script>
<style scoped>
.app{width: auto;display: inline-block;}
.frame-border{display: inline-block;border:solid 1px silver;border-right-color: #000;border-bottom-color: #000;}
.frame{
display:inline-block;
padding:1px;
border: outset 1px #eee;
user-select: none;
box-shadow: -1px -1px 0 1px silver, 1px 1px 0 2px #000;
margin:1px;
}
.frame:not(.menu) .title {-webkit-app-region: drag;}
.title{
height: 16px;
background: #0000a8;
color:white;
padding: 1px 2px;
display: flex;
flex-direction: row;
align-items: start;
}
.frame:not(.focus) .title{
background: #87888f;
color:#c0c7c8;
}
.rbborder{ padding-right: 1px;padding-bottom: 1px; padding:1px;box-shadow: -1px -1px 0 #000 inset}
.title i{width:16px;height:16px;background: url('icons/16x16.png') no-repeat 0 0;display: inline-block; }
.title span {display: flex;}
.title button{
outline: none;
-webkit-app-region: none;
height: 11px;
width: 13px;
padding:0;
background: url('icons/title_btns.png') no-repeat 0 0;
background-color: silver;
border: outset 1px #eee;
box-shadow: 0px 1px 0 0px #000, 1px 0px 0 0px #000, 1px 1px 0 0px #000;
box-sizing: content-box;
margin: 1px 1px 1px 0;
z-index: 1000;
}
.title button:active{border: inset 1px #eee;}
.title .name{
flex:1;
font-family: Tahoma;
padding: 1px 2px;
font-size: 11px;
letter-spacing: 1px;
}
.title button.max{background-position: -13px 0;}
.title button.close{background-position: -26px 0;margin-left:2px}
</style>
<style>
html{overflow: hidden;}
:focus {outline:none;}
</style>
35 changes: 35 additions & 0 deletions electron/dev.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
const webpack = require('webpack')
const WebpackDevServer = require('webpack-dev-server')
const webpackHotMiddleware = require('webpack-hot-middleware')
const [ , rendererConfig ] = require('./webpack.config')(null, { mode: 'development' })
const electron = require('electron')
const electronDebug = require('electron-debug')
const path = require('path')

function Deferred () { this.promise = new Promise((resolve, reject) => Object.assign(this, { resolve, reject })) }

async function devServer () {
const compiler = webpack(rendererConfig)
const hotMiddleware = webpackHotMiddleware(compiler)

const deferred = new Deferred()
const server = new WebpackDevServer(compiler, {
contentBase: path.join(__dirname, '../www'),
before (app) {
app.use(hotMiddleware)
deferred.resolve()
}
})
server.listen(9080)
await deferred.promise
}
async function run () {
await devServer()
electronDebug({ showDevTools: true })
const { default: installExtension, VUEJS_DEVTOOLS } = require('electron-devtools-installer')
await new Promise(resolve => electron.app.on('ready', resolve))
await installExtension(VUEJS_DEVTOOLS)
require('./main')
}

run().catch(err => console.error(err))
Binary file added electron/icons/16x16.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added electron/icons/256x256.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added electron/icons/32x32.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added electron/icons/title_btns.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
21 changes: 21 additions & 0 deletions electron/main.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
const { app, BrowserWindow } = require('electron')
const production = process.env.NODE_ENV === 'production'
const renderer = production ? `file://${__dirname}/index.html` : `http://localhost:9080`
const iconPath = production ? require('./icons/256x256.png') : './icons/256x256.png'
const icon = require('path').join(__dirname, iconPath)

function createWindow () {
const win = new BrowserWindow({
useContentSize: true,
title: 'Minesweeper',
icon,
show: false,
frame: false,
resizable: false
})
win.setMenu(null)
win.loadURL(renderer)
}

app.isReady() ? createWindow() : app.on('ready', createWindow)
app.on('window-all-closed', () => app.quit())
8 changes: 8 additions & 0 deletions electron/renderer.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
import Frame from './Frame.vue'
import Vue from 'vue'
import '../app/util/filters.mjs'
import _ from 'lodash'
import { lodashMixin } from '../app/util/util.mjs'

_.mixin(lodashMixin)
new Vue({ el: 'app', render: h => h(Frame) }) // eslint-disable-line no-new
35 changes: 35 additions & 0 deletions electron/webpack.config.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
const path = require('path')
const baseConf = require('../webpack.config.base')
const defConf = require('../webpack.config')
const webpack = require('webpack')

module.exports = function (env, { mode = 'development' } = {}) {
const production = mode === 'production'
const configs = {
main: Object.assign(baseConf('electron'), {
mode,
target: 'electron-main',
entry: path.join(__dirname, 'main.js'),
devtool: production ? false : 'inline-source-map',
output: {
filename: 'main.js',
libraryTarget: 'commonjs2',
path: path.resolve(__dirname, '../www/')
},
node: { __dirname: !production, __filename: !production }
}),
renderer: Object.assign(defConf(env, { mode }), {
mode,
target: 'electron-renderer',
entry: [path.join(__dirname, 'renderer.js')],
node: { __dirname: !production, __filename: !production }
})
}
if (mode === 'production') {
Object.values(configs).forEach(c => c.plugins.push(new webpack.DefinePlugin({ 'process.env.NODE_ENV': '"production"' })))
} else {
configs.renderer.entry.push('webpack-hot-middleware/client?noInfo=true&reload=true')
configs.renderer.plugins.push(new webpack.HotModuleReplacementPlugin())
}
return Object.values(configs)
}
Loading

0 comments on commit afac10c

Please sign in to comment.