[純前端]打造自己的OKR管理軟件

OKR(Objectives and Key Results)即目標(biāo)與關(guān)鍵成果法,可以理解為對(duì)目標(biāo)完成情況的一種管理方法。
一般需要列出當(dāng)前周期的目標(biāo),然后列舉一些關(guān)鍵結(jié)果來衡量目標(biāo)的完成情況。
我個(gè)人的情況是,以每?jī)蓚€(gè)月為一個(gè)周期設(shè)定自己的目標(biāo)。最初都是用markdown記錄,每次列出表格,寫下目標(biāo),結(jié)果,進(jìn)度,最后給自己算分?jǐn)?shù)。

然而這個(gè)算分的過程每次都得重新計(jì)算,十分麻煩,而且表格也得手工維護(hù),總之就是麻煩。于是就有了寫個(gè)軟件管理的想法。
正好自己主要是做后端,所以想學(xué)習(xí)下前端知識(shí),于是把這款軟件定位在web應(yīng)用上。

1. 產(chǎn)品設(shè)計(jì)
先給自己寫了個(gè)簡(jiǎn)單的PRD(產(chǎn)品需求文檔),大概自己能看懂就ok,理了理思路。傳送門:https://github.com/GooZy/ot/blob/master/PRD.md
2. 環(huán)境配置
安裝npm,獲取npm(https://www.npmjs.com/get-npm)
安裝vue,官方安裝方法(https://cn.vuejs.org/v2/guide/installation.html#NPM)
用IDEA(https://www.jetbrains.com/idea/)作為IDE
3. 新建項(xiàng)目
使用命令"vue ui
"
開啟圖形界面,新建項(xiàng)目,有個(gè)默認(rèn)初始化git選項(xiàng),按照喜好可要可不要

“預(yù)設(shè)”選項(xiàng),選擇“手動(dòng)”,然后勾上這些包"vuex
"
和"router
"
,不選包"linter
"

之后勾選使用html5歷史模式(https://router.vuejs.org/zh/guide/essentials/history-mode.html#html5-history-%E6%A8%A1%E5%BC%8F)

進(jìn)入項(xiàng)目web管理頁(yè)面后,添加element-ui
模塊

項(xiàng)目建立后導(dǎo)入到IDEA,就可以開始編寫代碼了。
4. 難點(diǎn)記錄
這一部分只挑一些重點(diǎn)來說,剩余的可以參考git倉(cāng)庫(kù)代碼:https://github.com/GooZy/ot
主要用了兩個(gè)頁(yè)面,App.vue
作為整個(gè)門面,保持不變,主要用于展示OKR的可選月份,圖中紅色圈出的部分即是。Home.vue
承接OKR的展示部分,為圖中的非紅色部分。

月份展示
提前算好月份列表,默認(rèn)顯示當(dāng)前雙月的目標(biāo)。這里用v-model指定默認(rèn)打開的tab。詳細(xì)參考:官方文檔-tabs(https://element.eleme.io/#/zh-CN/component/tabs)
注意<router-view>
別放在循環(huán)里面,這樣會(huì)產(chǎn)生多個(gè),實(shí)際上我們只需要一個(gè)。

數(shù)據(jù)傳遞
當(dāng)點(diǎn)擊月份標(biāo)簽的時(shí)候,使用$router.push
把月份信息傳遞到Home.vue
。這里有個(gè)點(diǎn)要注意,push
方法在推送的URL和當(dāng)前URL相同時(shí),會(huì)在控制臺(tái)報(bào)錯(cuò)。這里加了個(gè)catch忽略掉報(bào)錯(cuò)。
this.$router.push({path: '/okr/', query: {'month': tab.label}}).catch(() => {});
由于使用的是同一個(gè)Home.vue
,所以靠query詞來區(qū)分頁(yè)面。改寫router/index.js
來映射到Home.vue
const routes = [ ?{ ? ?path: '/okr/*', ? ?name: 'home', component: Home ?}];
Home.vue考慮
本來只用了<el-table>
,后來發(fā)現(xiàn)需要標(biāo)題,所以在外面嵌套了<el-card>
,最終布局是:

固定最后一行百分比
為了保證最后百分比總和為100%,就打算固定最后一行為不可更改的形式。
這里用了一個(gè)字典存是否可以修改hitBox: {}
,key是目標(biāo)+行號(hào)+列名
,可以唯一確定一個(gè)單元格。

v-slot用于獲取父組件的數(shù)據(jù),使其可以傳遞下來,具體參考:編譯作用域(https://cn.vuejs.org/v2/guide/components-slots.html#%E7%BC%96%E8%AF%91%E4%BD%9C%E7%94%A8%E5%9F%9F)
數(shù)據(jù)刷新
有兩種情況頁(yè)面需要刷新。一個(gè)是當(dāng)雙擊單元格時(shí),此時(shí)要顯示單元格成編輯框,所以必須刷新頁(yè)面。另一個(gè)是數(shù)據(jù)變動(dòng)時(shí),此時(shí)需要刷新頁(yè)面。所以要特別注意hitBox
,在第一種情況下,不需要刷新,否則單元格又變回原樣。
// 同樣的頁(yè)面,不需要初始化的數(shù)據(jù)
if (!isOldPage) {
this.hitBox = {};
this.editData = false;
}
數(shù)據(jù)直接用localstorage存,使用方式就是k-v,將結(jié)構(gòu)化數(shù)據(jù)序列化后使用即可。
let tableData = localStorage.getItem(this.month);tableData = JSON.parse(tableData);
5. 部署到github pages
官方說的很明白:https://cli.vuejs.org/zh/guide/deployment.html#github-pages
部署完之后就可以愉快地使用啦~
6. 效果
項(xiàng)目github地址:https://github.com/GooZy/ot
部署頁(yè)面:https://goozy.github.io/ot/
參考資料
VUE+Element UI實(shí)現(xiàn)簡(jiǎn)單的表格行內(nèi)編輯效果(https://www.jianshu.com/p/79f39f2c1382)
Vue結(jié)合Element-UI實(shí)現(xiàn)單元格編輯、刪除等操作(https://blog.csdn.net/yhflyl/article/details/88689304)
PS:代碼全糊掉了=。=,想更好閱讀體驗(yàn)的,建議看我個(gè)人博客吧。https://goozy.github.io/post/make-your-own-okr-management-software/