2021.07.23 補充:
留言區裡有人詢問能不能開了一個,就關閉前一個的功能,今日程式碼加上此功能。
2020.07.23 補充:
看到留言區裡有人問有沒有預設開啟的方法,程式碼做了點調整,只要在 .title-box 中加入data-expanded="true"
,預設就會開啟囉~
從jQuery到原生JS
手風琴,英文單字是Accordion,但在很多套件上有時又稱Collapse。本篇筆記就用中文的手風琴比較好理解。
很久以前,有用jQuery寫了一個手風琴的功能,放在codePen上後看到有人點愛心跟Fork,覺得有趣:Collapse/Accordion plugin
今年開始在工作時逼自己寫原生的JS(Vanilla JavaScript),今天趁著意外的假日,試著把手風琴用原生JS寫了一個出來。寫完後發現,其實沒幾行就可以完成,也有了一點小小的成就感。
本篇就是開發過程的一個筆記,最後也會附上原始碼。這段先附上最後會完成的Demo:
https://letswritetw.github.io/augurio-collapse-accordion/
HTML
HTML的架構用最簡單的,最外面先包一層div,裡面每一組的項目用.callopse
包。一個.collapse
就是一組,一組裡有.title-box
、.contents-box
,一個是頭,一個是會被隱藏的內容。
CSS
樣式的部份就簡單寫,因為之後要套到每個頁面時,每個頁面會有自己的設計。
針對手風琴打開、關閉時,寫了一個會變換「+」、「-」符號的轉變效果,主要是用2個span
去刻成2條線,一條轉直的,當 .contents-box
被打開時再轉回横的。
以下範例code為了好閱讀,改用SASS:
JavaScript
JS的部份,寫了2個部份:
- 先抓每個
.contents-box
的高度,存在data-height
裡,然後把高度設為0。 - 監聽每一個
.title-box
的點擊事件,如果.title-box
有.active
,那就把同一層的.contents-box
高度寫回去。
之所以會有把高度寫回去的動作,而不是去改display none/block,是為了讓手風琴打開/關閉時會有jQuery slideUp、slideDown的效果。
而如果只是單純的寫height 0/100%,那即使寫了 transition: height
,也一樣不會有slideUp、slideDown的樣子,一定要給指定的高度才行,所以才會有第一步的抓原始高度到 data-height
裡,讓 .title-box
被點擊時可以抓到原有的高度。
原始碼下載
本筆記原始碼的部份,August整理放到Github上了。
https://github.com/letswritetw/augurio-collapse-accordion


想請問如果第一個collapse要預設每次點進來都是開的,點選title-box後才會收合,是有辦法做到的嗎?謝謝~
請問一下,.title-box 被點擊時,加入 .active,這個部分有時候點到.tltle的文字與.icons的span會無法做動,請問有辦法解決嗎? 感謝!!
您好,請問一下,如果滑鼠點選第一個選單時,選單內容打開了。
滑鼠再點選第二選單時,要如何讓第一個打開的選單內容”關閉”呢?
也就是一次,只要打開一個選單就好了!
能否指點一二呢!
請問若要將已點開的選單再按一次.title-box就收合,要新增哪個部份呢?