用 Electron-Vue 开发的协助程序员的开发工具 IT-Tools - V2EX
V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
爱意满满的作品展示区。
TsaiKoga
V2EX    分享创造

用 Electron-Vue 开发的协助程序员的开发工具 IT-Tools

  •  1
     
  •   TsaiKoga 2019-03-27 09:40:16 +08:00 3037 次点击
    这是一个创建于 2393 天前的主题,其中的信息可能已经有所发展或是发生改变。

    这是由 Electron & Vue.js 编写的,为程序员服务的编程工具

    目前提供了四个版块:

    • 正则表达式
    • 时间戳转化
    • 颜色盒子
    • Json 转化

    在这几个模块中,可以发现使用组件化的好处,处理多个组件之间各种数据变化非常方便!

    IT-Tools

    项目地址:

    Github 地址:https://github.com/TsaiKoga/it-tools

    求 Star

    感兴趣的朋友可以 star 或 fork,或是给我你的宝贵意见,互相学习一下


    下面介绍一下我写 正则表达式内容,写的不好,望见谅...

    electron-vue

    克隆项目,从 electron-vue 克隆项目,然后开始编写代码;

    https://github.com/SimulatedGREG/electron-vue.git 

    通过"正则表达式"这个模块,来了解 Vue 组件通信;

    electron-vue 一开始已经为你生成一些文件页面,我们可以按照他的方法创建我们自己的页面;

    创建路由:

    src/renderer/router/index.js 文件中添加路由:

    export default new Router({ routes: [ { path: '/', name: 'landing-page', component: require('@/components/LandingPage').default }, { path: '/regex-page', name: 'regex-page', component: require('@/components/RegexPage').default } ] }); 

    这里我们的 url 为 /regex-page,并且 require 了 RegexPage 组件,这个组件要放置在 components 目录下,所以我创建了文件:src/renderer/components/RegexPage.vue

    编写组件:

    可以通过复制 LandingPage.vue 组件,将它改成新组件即可:

    要实现这个页面,头部两个输入框,输入后都能与下面的 textarea 内容进行比较处理,得出结论;

    这个用 组件化 vue 比纯粹用 js jquery 的 dom 操作要方便太多了;

    通过 template 包裹写成 vue 组件:

    <template> <div id="regex-page">     <div class="regex-inner" v-show="currentTab === 'Home'">     <div class="regex-top">       <div class="regex-top-label">         <label>Your regular expression:</label>       </div>       <div class="regex-top-fields">         <div class="regex-diagonal">/</div>         <div class="regex-diagnoal-input">           <input type="text" name="regex-exp" @input='execRegex' :value='regexExp' />         </div>         <div class="regex-diagonal">/</div>         <div>           <input type="text" name="regex-opt" @input="execRegex" :value="regexOpt" />         </div>       </div>      </div>      <div class="regex-bottom">       <div class="regex-content">         <label>Your test string: </label>         <textarea class="regex-textarea" name="regex-content" @input="execRegex" :value='regexCont'></textarea>       </div>       <div class="result-content result-init" v-if="regexResult['status'] == 0">         {{ regexResult['content'] }}       </div>       <div class="result-content result-match" v-if="regexResult['status'] == 1">         <div>           <div class="regex-match-btn">             <label>Match Result:</label>             <a href="Javascript:void(0)" class="clean-fields" @click="cleanAllFields">Clean Fields</a>           </div>           <div class="result-item">             <span v-for="(cont, indx) in regexResult['matchedContext']" :class="indx%2 !== 0 ? 'match' : null">{{ cont }}</span>           </div>         </div>         <ul v-if="regexResult['content'].length > 0">           <label>Match Groups:</label>           <div class="match-groups">             <li v-for="(itemGroup, index) in regexResult['content']">               <div class="group-item">               <label>Match Group {{ index + 1 }}:</label>               <ul>                 <li v-if="i !== 0" v-for="(item, i) in itemGroup">{{ i }}: {{ item }}</li>               </ul>               </div>             </li>           </div>         </ul>         </div>         <div class="result-content result-not-match" v-if="regexResult['status'] == -1">           {{ regexResult['content'] }}         </div>       </div>     </div> </div> </template> <script> import { mapState, mapActions } from 'vuex' export default { name: 'regex-page', computed: { ...mapState('Regex', { regexExp: state => state.regexExp, regexOpt: state => state.regexOpt, regexCont: state => state.regexCont, regexResult: state => state.regexResult}) }, methods: { ...mapActions('Regex', [ 'setNav', 'cleanFields', 'regexMatch' ]), cleanllFields () { this.cleanFields() }, execRegex (event) { this.regexMatch(event) }, updateNav (title, index) { this.setNav({ title: title, index: index }) } } } </script> <style lang="scss" scoped> * { } </style> 

    至于,输入框之间的交互,我使用 vuex 来实现他们之间数据的传递;

    使用 Vuex 管理状态: 一、创建 store 目录,并创建 modules 目录用来管理不同的命名空间的 State, Actions, Mutations 创建 src/renderer/store/modules/Regex.js 文件:

    const state = { regexExp: '', regexOpt: '', regexCont: '', regexResult: { status: 0, content: "Here's result." } } const mutatiOns= { REGEX_MATCH (state, target) { if (target.name === 'regex-exp') { state.regexExp = target.value } if (target.name === 'regex-opt') { state.regexOpt = target.value } if (target.name === 'regex-content') { state.regexCOnt= target.value } ... } const actiOns= { cleanFields ({ commit }) { commit('CLEAN_FIELDS') }, regexMatch ({ commit }, payload) { commit('REGEX_MATCH', payload.target) } } export default { state, mutations, actions } 

    state 给默认状态;

    mutations 更改对应 state ;

    actions 用于写异步来改变状态或提交 mutations 的更改;

    state 的方法被我写在 computed,这样组件中可以使用;

    在 methods 方法中使用 mapActions,并定义其他方法来调用这些 action ;

    二、main.js 加入 store 容器

    import App from './App' import router from './router' import store from './store' if (!process.env.IS_WEB) Vue.use(require('vue-electron')) Vue.http = Vue.prototype.$http = axios Vue.config.productiOnTip= false new Vue({ components: { App }, router, store, template: '<App/>' }).$mount('#app') 

    三、组件中通过 computed 或 data 使用 State,通过 methods 触发 Actions 方法

    import { mapState, mapActions } from 'vuex' export default { name: 'regex-page', computed: { ...mapState('Regex', { regexExp: state => state.regexExp, regexOpt: state => state.regexOpt, regexCont: state => state.regexCont, regexResult: state => state.regexResult}) }, methods: { ...mapActions('Regex', [ 'setNav', 'cleanFields', 'regexMatch' ]), cleanAllFields () { this.cleanFields() }, execRegex (event) { this.regexMatch(event) }, updateNav (title, index) { this.setNav({ title: title, index: index }) } } } 

    在组件文件中引用了

    mapState, mapActions 方法,他可以获取这个 store 里的 state 和 action 方法,

    不过要注意命名空间的使用,此处使用了 Regex 作为命名空间,所以要在 mapState 和 mapActions 中加 命名空间;

    命名空间定义文件在:src/renderer/store/modules/index.js 文件;

    const files = require.context('.', false, /\.js$/) const modules = {} files.keys().forEach(key => { if (key === './index.js') return modules[key.replace(/(\.\/|\.js)/g, '')] = files(key).default modules[key.replace(/(\.\/|\.js)/g, '')]['namespaced'] = true }) export default modules 

    但是直接 (‘ Regex ’, [regexExp: state => state.regexExp]) 是无法使用的,必须在 module 中声明 namespaced: true 才可以;

    … mapActions() 是将里面的对象 扁平化 到 外面的对象中;

    直接 mapActions 只是打开了方法,还未执行:

    删除 createSharedMutations() 的方法后,action 生效;

    绑定到组件上

    <input type="text" name="regex-exp" @input='execRegex' value='regexExp' /> 

    生成桌面应用

    运行命令:

    npm run build:mas # 生成 mac 应用 npm run build:linux # 生成 linux 应用 npm run build:win32 # 生成 windows 应用 

    可以在 /build 目录中看到生成的应用目录

    9 条回复    2019-04-05 16:33:54 +08:00
    oldarm
        1
    oldarm  
       2019-03-27 09:52:48 +08:00
    不错
    jevonszmx
        2
    jevonszmx  
       2019-03-27 09:56:25 +08:00
    哈哈,我也用 Electron+vue 写了一个自己用,https://github.com/jevonszmx/webtool,UI 是使用的 bootstrap,不过目前支持的功能比你多。


    ![截图]( )

    ![截图]( )

    ![截图]( )

    ![截图]( )

    希望有人继续一起完善。
    jevonszmx
        3
    jevonszmx  
       2019-03-27 09:57:38 +08:00
    额,V2 解析链接出错了,把后面的,UI 也加上了,实际地址是: https://github.com/jevonszmx/webtool
    TsaiKoga
        4
    TsaiKoga  
    OP
       2019-03-27 10:40:30 +08:00
    @jevonszmx 额,我的转化都是自己写的,提示比较多
    azh7138m
        5
    azh7138m  
       2019-03-27 15:27:19 +08:00
    @jevonszmx md5 加密很厉害啊,那怎么解密呢?
    kosmosr
        6
    kosmosr  
       2019-03-27 18:39:18 +08:00 via Android
    有个工具叫 uTools 也很好用也是集成了很多小插件,推荐一波 https://u.tools
    TsaiKoga
        7
    TsaiKoga  
    OP
       2019-03-28 09:35:35 +08:00
    大家不要光顾着收藏,麻烦 star 一个: https://github.com/TsaiKoga/it-tools
    Chingim
        8
    Chingim  
       2019-03-28 19:32:57 +08:00 via Android
    纯粹是页面展示的功能,为什么非得打包一个 electron ?
    TsaiKoga
        9
    TsaiKoga  
    OP
       2019-04-05 16:33:54 +08:00
    关于     帮助文档     自助推广系统     博客     API     FAQ     Solana     5416 人在线   最高记录 6679       Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 35ms UTC 09:15 PVG 17:15 LAX 02:15 JFK 05:15
    Do have faith in what you're doing.
    ubao snddm index pchome yahoo rakuten mypaper meadowduck bidyahoo youbao zxmzxm asda bnvcg cvbfg dfscv mmhjk xxddc yybgb zznbn ccubao uaitu acv GXCV ET GDG YH FG BCVB FJFH CBRE CBC GDG ET54 WRWR RWER WREW WRWER RWER SDG EW SF DSFSF fbbs ubao fhd dfg ewr dg df ewwr ewwr et ruyut utut dfg fgd gdfgt etg dfgt dfgd ert4 gd fgg wr 235 wer3 we vsdf sdf gdf ert xcv sdf rwer hfd dfg cvb rwf afb dfh jgh bmn lgh rty gfds cxv xcv xcs vdas fdf fgd cv sdf tert sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf sdf shasha9178 shasha9178 shasha9178 shasha9178 shasha9178 liflif2 liflif2 liflif2 liflif2 liflif2 liblib3 liblib3 liblib3 liblib3 liblib3 zhazha444 zhazha444 zhazha444 zhazha444 zhazha444 dende5 dende denden denden2 denden21 fenfen9 fenf619 fen619 fenfe9 fe619 sdf sdf sdf sdf sdf zhazh90 zhazh0 zhaa50 zha90 zh590 zho zhoz zhozh zhozho zhozho2 lislis lls95 lili95 lils5 liss9 sdf0ty987 sdft876 sdft9876 sdf09876 sd0t9876 sdf0ty98 sdf0976 sdf0ty986 sdf0ty96 sdf0t76 sdf0876 df0ty98 sf0t876 sd0ty76 sdy76 sdf76 sdf0t76 sdf0ty9 sdf0ty98 sdf0ty987 sdf0ty98 sdf6676 sdf876 sd876 sd876 sdf6 sdf6 sdf9876 sdf0t sdf06 sdf0ty9776 sdf0ty9776 sdf0ty76 sdf8876 sdf0t sd6 sdf06 s688876 sd688 sdf86