2023 F2E 鐵人賽心得

2023 因為換工作的緣故,接觸了 svelte 和 angular,為了磨練自己,決定用這兩個我沒那麼熟悉的技術開發,今年的時間比較充裕,一個關卡有 10 天的開發時間,前幾年都只有一週真的爆肝,因此這次比賽的勞累度我認為會比以往低不少(事後證明我錯了 😂

第一關  —  立法委員的形象官網

使用技術:svelteKit + tailwindcss + GSAP

這關不難,就是考驗切版功力,好久沒有出現這麼親民的關卡了(?,剛好很久沒有切版可以溫習一下,用 tailwindcss 開發就是舒服,config 設定好,切版咻咻咻一下就完成了,即便我已經快一年都沒碰 tailwindcss,靠 vscode 的 tailwindcss IntelliSense 的語法提示還是很快就找回手感了,tailwindcss 切版真的快,但是如果有程式碼潔癖的人看到那一大串的 css 應該有點焦慮

這次的開發有兩個新的嘗試

  1. 用 css 寫數字跳動效果,不禁讚嘆 css 真的越來越強大了,連數字跳動的效果都能夠實現,有興趣的可以看看這個codepen的實作細節,感嘆自己已經快追不上 css 的腳步了
  2. 使用原生的 html dialog element 寫彈窗,不得不說還蠻方便的,就不需要自己造輪子,相當省事,雖然彈窗的彈出效果生硬了一點,這部分應該是可以調整,但我就沒有深入研究了

第一次用 svelte 寫 side project,不得不說 svelte 寫起來真的很簡潔,比 vue 還簡潔,個人覺得學習曲線比 vue 還低,可以說是框架的明日之星,但也因為 svelte 很年輕,所以坑自然也是不少,歡迎大家有空一起來踩坑 😂 然後也嘗試使用 svelte kit 開發(類似 next js 的 SSR framework),但因為 server side rendering 的緣故,遇到不少問題,搞了有點久還好最後都有解決,在 SSR 裡面處理 windows 物件都要特別小心,如果執行環境不是 browser 直接噴錯

最終成品:喵立翰 立委競選官網

第二關  —  全台總統開票地圖

nrwl nx + angular + material + d3.js

剛好遇到 angular 出 17 版,就決定用最新最潮的版本,ngIf、ngFor 等語法改版後不得不說真的跟 svelte 的語法好像 😂,但我自己是蠻喜歡的啦,在效能上也有明顯的提升,關於 angular 17 有那些更新可以參考這篇文章

不得不說專案初始的一些設定就花了我不少的時間,作為一個 angular 初心者, 不知道該怎麼修改 angular material 的 default theme,不知道可以在哪裡初始化資料,真的是一萬個不知道,就只能靠自己慢慢摸索了

要繪製台灣開票地圖,首先要先有圖資,先到內政地理圖資服務中心下載縣市、鄉鎮、村里的圖資,把 shp 檔案下來再丟到mapshaper上面轉成 TopoJSON 就搞定了,最頭痛的還是開票資料,這部分的資料沒有 json 可以下載只有 csv,異想天開想說能不能用 csv 轉 json 直接拿來用,結果轉換出來的資料格式跟我期望的差非常多,只好採用土炮方式,抓中選會開票 api 的資料,然後寫個 function 把圖資和開票兩邊的資料 merge,縣市還好,鄉鎮還行,村里直接讓我的 macbook pro m1 當機,一個 json 檔案 57 萬行真的不是開玩笑,想不到 json 的殺傷力這麼大(?

接下來要用 d3 畫出台灣的地圖,不得不說 d3 真的是大魔王,我覺得官方文件沒有寫得很好上手,爬文又會找到很久以前的資料,殊不知用法早就不一樣了,花了點時間看了這本書(D3.js 資料視覺化實用攻略)惡補一下,總算有比較理解 d3 的語法了

先來釐清開票地圖想要基本功能有:

  1. 畫出台灣的各個行政區
  2. 行政區會依照得票率顯示對應顏色的層級,得票率越高,區塊顏色越深
  3. 可以點按行政區,地圖會跟著 zoom in,層級為縣市 -> 鄉鎮 ->村里
  4. 能夠按左上角的返回按鈕返回到上一個層級

以上需求感覺很簡單,但卻寫得我暈頭轉向,不是不小心清空所有的區域不然就是重複畫線,而且點擊的順序不一樣,會觸發的 bug 也不一樣 😂,但寫著寫的就發現一件事情

現有的圖資存在兩個問題

  1. 點到高雄市就會讓地圖的整個視角拉超遠

一開始以為是 zoom function 沒有寫好,但很詭異的是就高雄市有問題,後來發現罪魁禍首是那個離台灣有點遙遠的東沙群島,在畫面上小到幾乎看不到,因為 zoom 會把視角拉近到可以看到完整的縣市區域,就會連帶地把那些小島的顯示範圍也包含進來,因此就會出現一種很詭異的現象,明明我要從全台的視角切換到高雄市的視角反而變得超遠,其實這樣的顯示結果是正確的,只是不符合我們的預期,解決方式就是把那個小島直接刪掉,基隆的右上角也需要處理一下

2. 金門和馬祖的位置有點尷尬

由於金門和馬祖都離台灣本島有點距離,如果想要完整看到離島和本島的話視角一定會拉遠,變成台灣本島特別小,但我的期望是希望本島可以盡可能的放滿整個畫面,先採取暴力一點的作法,scale 設定大一點,縮放到以本島看的清楚為主,金門馬祖看不到就算了(喂,但想想這做法也不是很理想,結果如下

觀察一下天下雜誌和關鍵評論的地圖作法,都是把金門和馬祖挪到澎湖的正上方,這樣台灣本島既不會太小也能夠看到金門,真的是一石二鳥之計,本來還期待政府有沒有提供這種特規版本的圖資,但結果是沒有,想不到居然還是逃不過要編輯圖資這一步,爬文看到蠻多人用 QGIS 這個應用程式編輯的,只好乖乖下載 QGIS,開始學習怎麼使用 QGIS,花了一點時間看 youtube 教學,學習要怎麼搬移區域,怎麼刪除不要的區域,怎麼輸出等等(文章最後有影片教學連結,然後再把編輯完的結果 export 成 geojson,再丟到 mapshaper 轉成 TopoJSON,過程當然也是一波三折,轉換出來的圖資跟自己預期的不一樣就只能重做,做完縣市還有鄉鎮等著你,做完鄉鎮還有村里等著你… 果不其然在編輯的村里的時候瘋狂轉彩球,還好我的電腦有扛得住,超怕死當要再來一次

最終成品:2020 總統大選開票地圖

完賽心得

比賽期間,我推掉所有飯局,請大家不要約我出去玩,我就是要當個無情的比賽機器 😂,假日和平日下班後的時間全部投入在比賽,有時候寫扣寫到忘我回過神來已經是午夜時分了,不得不說真的很累,但我還蠻享受那個過程的,雖然開發的過程中挫折滿滿,為什麼地圖畫不出來?為什麼視角會大偏移?為什麽我更新資料畫面沒有重新渲染?諸如此類的問題一大堆,但做出來真的很有成就感,也謝謝自己願意堅持到最後,12 月終於可以回歸正常的生活了(?

QGIS Reference