diff --git a/.docker/entrypoint.sh b/.docker/entrypoint.sh index 77c697aa..efe40476 100755 --- a/.docker/entrypoint.sh +++ b/.docker/entrypoint.sh @@ -1,10 +1,8 @@ #! /bin/bash # print folder contents for debugging -echo "Contents:" -echo "" +printf "\n\nContents:\n\n" ls -echo "" # run cite process python3 _cite/cite.py diff --git a/.github/DISCUSSION_TEMPLATE/general.yaml b/.github/DISCUSSION_TEMPLATE/general.yaml new file mode 100644 index 00000000..66b2c499 --- /dev/null +++ b/.github/DISCUSSION_TEMPLATE/general.yaml @@ -0,0 +1,35 @@ +body: + - type: checkboxes + attributes: + label: Checks + options: + - label: I have searched **[the docs](https://greene-lab.gitbook.io/lab-website-template-docs)**, [existing issues](https://github.com/greenelab/lab-website-template/issues), and [existing discussions](https://github.com/greenelab/lab-website-template/discussions) for answers first. + required: true + + - type: input + id: repo + attributes: + label: Link to your website repo + description: "In almost all cases, **we cannot help you if you don't provide this**." + placeholder: ex. https://github.com/greenelab/greenelab.com + validations: + required: true + + - type: input + id: version + attributes: + label: Version of Lab Website Template you are using + description: See your `CITATION.cff` file. + placeholder: ex. 1.0.0 + validations: + required: true + + - type: textarea + id: description + attributes: + label: Description + description: | + Describe your issue in as much detail as possible. For example: What happened? What did you expect to happen? How can we reproduce the problem? What browser are you seeing the problem in? + placeholder: Description + validations: + required: true diff --git a/.github/DISCUSSION_TEMPLATE/q-a.yaml b/.github/DISCUSSION_TEMPLATE/q-a.yaml new file mode 100644 index 00000000..66b2c499 --- /dev/null +++ b/.github/DISCUSSION_TEMPLATE/q-a.yaml @@ -0,0 +1,35 @@ +body: + - type: checkboxes + attributes: + label: Checks + options: + - label: I have searched **[the docs](https://greene-lab.gitbook.io/lab-website-template-docs)**, [existing issues](https://github.com/greenelab/lab-website-template/issues), and [existing discussions](https://github.com/greenelab/lab-website-template/discussions) for answers first. + required: true + + - type: input + id: repo + attributes: + label: Link to your website repo + description: "In almost all cases, **we cannot help you if you don't provide this**." + placeholder: ex. https://github.com/greenelab/greenelab.com + validations: + required: true + + - type: input + id: version + attributes: + label: Version of Lab Website Template you are using + description: See your `CITATION.cff` file. + placeholder: ex. 1.0.0 + validations: + required: true + + - type: textarea + id: description + attributes: + label: Description + description: | + Describe your issue in as much detail as possible. For example: What happened? What did you expect to happen? How can we reproduce the problem? What browser are you seeing the problem in? + placeholder: Description + validations: + required: true diff --git a/.github/ISSUE_TEMPLATE/config.yml b/.github/ISSUE_TEMPLATE/config.yml new file mode 100644 index 00000000..7d0b7de5 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/config.yml @@ -0,0 +1,8 @@ +blank_issues_enabled: true +contact_links: + - name: ๐Ÿ’ฌ Start a discussion + url: https://github.com/greenelab/lab-website-template/discussions + about: I need help, I have a question, or other discussion. + - name: ๐Ÿ“š Docs issue + url: https://github.com/greenelab/lab-website-template-docs/issues + about: I have a question or issue related to the template documentation. diff --git a/.github/ISSUE_TEMPLATE/issue.yaml b/.github/ISSUE_TEMPLATE/issue.yaml new file mode 100644 index 00000000..d8125550 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/issue.yaml @@ -0,0 +1,38 @@ +name: ๐Ÿž Create an issue +description: I think I've discovered a bug, I want to request a feature/change, or other issue. + +body: + - type: checkboxes + attributes: + label: Checks + options: + - label: I have searched **[the docs](https://greene-lab.gitbook.io/lab-website-template-docs)**, [existing issues](https://github.com/greenelab/lab-website-template/issues), and [existing discussions](https://github.com/greenelab/lab-website-template/discussions) for answers first. + required: true + + - type: input + id: repo + attributes: + label: Link to your website repo + description: "In almost all cases, **we cannot help you if you don't provide this**." + placeholder: ex. https://github.com/greenelab/greenelab.com + validations: + required: true + + - type: input + id: version + attributes: + label: Version of Lab Website Template you are using + description: See your `CITATION.cff` file. + placeholder: ex. 1.0.0 + validations: + required: true + + - type: textarea + id: description + attributes: + label: Description + description: | + Describe your issue in as much detail as possible. For example: What happened? What did you expect to happen? How can we reproduce the problem? What browser are you seeing the problem in? + placeholder: Description + validations: + required: true diff --git a/.github/pull_request_template.md b/.github/pull_request_template.md index 00a0e711..6aaf76bd 100644 --- a/.github/pull_request_template.md +++ b/.github/pull_request_template.md @@ -1,4 +1,13 @@ -This website is based on the Lab Website Template. -See its documentation for working with this site: +STOP!!! -https://greene-lab.gitbook.io/lab-website-template-docs +You are about to open this pull request against THE TEMPLATE ITSELF. You probably meant to open it against your own website repo. + +--- + +FOR THE TEMPLATE MAINTAINER(S) + +New template version checklist: + +- [ ] I have updated CITATION and CHANGELOG as appropriate. +- [ ] I have updated lab-website-template-docs as appropriate. +- [ ] I have checked the testbed as appropriate. diff --git a/.github/user_pull_request_template.md b/.github/user_pull_request_template.md new file mode 100644 index 00000000..00a0e711 --- /dev/null +++ b/.github/user_pull_request_template.md @@ -0,0 +1,4 @@ +This website is based on the Lab Website Template. +See its documentation for working with this site: + +https://greene-lab.gitbook.io/lab-website-template-docs diff --git a/.github/workflows/build-preview.yaml b/.github/workflows/build-preview.yaml index 52842860..3ef04044 100644 --- a/.github/workflows/build-preview.yaml +++ b/.github/workflows/build-preview.yaml @@ -22,28 +22,29 @@ jobs: steps: # for debugging - - name: Print contexts - uses: crazy-max/ghaction-dump-context@v1 + - uses: crazy-max/ghaction-dump-context@v2 - name: Checkout branch contents - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: repository: ${{ github.event.pull_request.head.repo.full_name }} ref: ${{ github.head_ref }} - name: Install Ruby packages if: github.event.action != 'closed' - uses: ruby/setup-ruby@v1 + uses: ruby/setup-ruby@v1.172.0 with: - ruby-version: "3.0" + ruby-version: "3.1" bundler-cache: true - name: Get Pages url if: github.event.action != 'closed' id: pages - uses: actions/configure-pages@v2 - with: - enablement: false + uses: actions/configure-pages@v4 + + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 - name: Build preview version of site if: github.event.action != 'closed' @@ -51,7 +52,7 @@ jobs: JEKYLL_ENV=production bundle exec jekyll build --baseurl "${{ steps.pages.outputs.base_path || '' }}/${{ env.PREVIEWS_FOLDER }}/pr-${{ github.event.number }}" - name: Commit preview to Pages branch - uses: rossjrw/pr-preview-action@v1 + uses: rossjrw/pr-preview-action@v1.4.7 with: source-dir: _site umbrella-dir: ${{ env.PREVIEWS_FOLDER }} diff --git a/.github/workflows/build-site.yaml b/.github/workflows/build-site.yaml index 9b71767f..6194c83b 100644 --- a/.github/workflows/build-site.yaml +++ b/.github/workflows/build-site.yaml @@ -21,30 +21,35 @@ jobs: steps: # for debugging - - name: Print contexts - uses: crazy-max/ghaction-dump-context@v1 + - uses: crazy-max/ghaction-dump-context@v2 - name: Checkout branch contents - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Install Ruby packages - uses: ruby/setup-ruby@v1 + uses: ruby/setup-ruby@v1.172.0 with: - ruby-version: "3.0" + ruby-version: "3.1" bundler-cache: true - name: Get Pages url id: pages - uses: actions/configure-pages@v2 - with: - enablement: false + uses: actions/configure-pages@v4 + + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 + + - name: Set root url + run: | + printf "\n\nurl: ${{ steps.pages.outputs.origin }}" >> _config.yaml - name: Build live version of site run: | JEKYLL_ENV=production bundle exec jekyll build --baseurl "${{ steps.pages.outputs.base_path || '' }}" - name: Commit live site to Pages branch - uses: JamesIves/github-pages-deploy-action@v4 + uses: JamesIves/github-pages-deploy-action@v4.5.0 with: folder: _site clean-exclude: ${{ env.PREVIEWS_FOLDER }} diff --git a/.github/workflows/first-time-setup.yaml b/.github/workflows/first-time-setup.yaml index bf227f7d..415e2842 100644 --- a/.github/workflows/first-time-setup.yaml +++ b/.github/workflows/first-time-setup.yaml @@ -14,21 +14,24 @@ jobs: steps: # for debugging - - name: Print contexts - uses: crazy-max/ghaction-dump-context@v1 + - uses: crazy-max/ghaction-dump-context@v2 - name: Create Pages branch - uses: peterjgrainger/action-create-branch@v2.4.0 + uses: peterjgrainger/action-create-branch@v3.0.0 env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} with: branch: "gh-pages" - name: Checkout Pages branch - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: ref: gh-pages + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 + # clean slate, as if starting from orphan branch - name: Clear Pages branch run: rm -rf * .github .docker .gitignore @@ -38,16 +41,16 @@ jobs: run: touch .nojekyll - name: Make placeholder homepage - run: echo "Placeholder homepage" > index.html + run: printf "Placeholder homepage" > index.html - name: Commit changes to Pages branch - uses: stefanzweifel/git-auto-commit-action@v4 + uses: stefanzweifel/git-auto-commit-action@v5 with: branch: gh-pages commit_message: "Clear branch" - name: Checkout main branch - uses: actions/checkout@v3 + uses: actions/checkout@v4 - name: Remove files user doesn't need run: | @@ -55,23 +58,24 @@ jobs: CHANGELOG.md \ testbed.md \ .github/ISSUE_TEMPLATE \ + .github/DISCUSSION_TEMPLATE \ .github/workflows/versioning.yaml \ .github/pull_request_template.md \ - + - name: Rename files run: | - mv .github/user_pull_request_template.md .github/pull_request_template.md + mv -f .github/user_pull_request_template.md .github/pull_request_template.md - name: Set vars for personalization run: | user="${{ github.repository_owner }}" description="An engaging 1-3 sentence description of your lab." - echo "USER=${user}" >> $GITHUB_ENV - echo "DESCRIPTION=${description}" >> $GITHUB_ENV + printf "USER=${user}" >> $GITHUB_ENV + printf "DESCRIPTION=${description}" >> $GITHUB_ENV - name: Personalize readme for user run: | - echo " + printf " # ${{ env.USER }}'s Website Visit **[website url](#)** ๐Ÿš€ @@ -80,7 +84,7 @@ jobs: " > README.md - name: Personalize Jekyll config for user - uses: actions/github-script@v6 + uses: actions/github-script@v7 with: script: | const { readFileSync, writeFileSync } = require("fs"); @@ -97,7 +101,7 @@ jobs: writeFileSync(file, contents); - name: Personalize homepage for user - uses: actions/github-script@v6 + uses: actions/github-script@v7 with: script: | const { readFileSync, writeFileSync } = require("fs"); @@ -109,6 +113,6 @@ jobs: writeFileSync(file, contents); - name: Commit changed files - uses: stefanzweifel/git-auto-commit-action@v4 + uses: stefanzweifel/git-auto-commit-action@v5 with: commit_message: "Setup repo" diff --git a/.github/workflows/update-citations.yaml b/.github/workflows/update-citations.yaml index 2bafb552..f6ff6ec2 100644 --- a/.github/workflows/update-citations.yaml +++ b/.github/workflows/update-citations.yaml @@ -29,17 +29,16 @@ jobs: steps: # for debugging - - name: Print contexts - uses: crazy-max/ghaction-dump-context@v1 + - uses: crazy-max/ghaction-dump-context@v2 - name: Checkout branch contents - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: repository: ${{ github.event.pull_request.head.repo.full_name }} ref: ${{ github.head_ref }} - name: Setup Python - uses: actions/setup-python@v4 + uses: actions/setup-python@v5 with: python-version: "3.11" cache: "pip" @@ -49,13 +48,17 @@ jobs: run: | python -m pip install --upgrade --requirement ./_cite/requirements.txt + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 + - name: Build updated citations run: python _cite/cite.py timeout-minutes: 15 - name: Check if citations changed id: changed - uses: tj-actions/verify-changed-files@v13 + uses: tj-actions/verify-changed-files@v18 with: files: | _data/citations.yaml @@ -64,7 +67,7 @@ jobs: if: | steps.changed.outputs.files_changed == 'true' && inputs.open-pr != true - uses: stefanzweifel/git-auto-commit-action@v4 + uses: stefanzweifel/git-auto-commit-action@v5 with: commit_message: "Update citations" @@ -72,7 +75,7 @@ jobs: if: | steps.changed.outputs.files_changed == 'true' && inputs.open-pr == true - uses: peter-evans/create-pull-request@v4 + uses: peter-evans/create-pull-request@v6 with: branch: citation-update title: Periodic citation update diff --git a/.github/workflows/update-url.yaml b/.github/workflows/update-url.yaml index 9ccd9a3e..b3573a54 100644 --- a/.github/workflows/update-url.yaml +++ b/.github/workflows/update-url.yaml @@ -20,21 +20,22 @@ jobs: steps: # for debugging - - name: Print contexts - uses: crazy-max/ghaction-dump-context@v1 + - uses: crazy-max/ghaction-dump-context@v2 - name: Get Pages url id: pages - uses: actions/configure-pages@v2 - with: - enablement: false + uses: actions/configure-pages@v4 - name: Checkout branch contents - uses: actions/checkout@v3 + uses: actions/checkout@v4 + + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 # update link to site in readme - name: Update readme - uses: actions/github-script@v6 + uses: actions/github-script@v7 with: script: | const { readFileSync, writeFileSync } = require("fs"); @@ -53,14 +54,14 @@ jobs: - name: Check if readme changed id: changed - uses: tj-actions/verify-changed-files@v13 + uses: tj-actions/verify-changed-files@v18 with: files: | README.md - name: Commit changed files if: steps.changed.outputs.files_changed == 'true' - uses: stefanzweifel/git-auto-commit-action@v4 + uses: stefanzweifel/git-auto-commit-action@v5 with: commit_message: "Update url" diff --git a/.github/workflows/versioning.yaml b/.github/workflows/versioning.yaml new file mode 100644 index 00000000..e148f366 --- /dev/null +++ b/.github/workflows/versioning.yaml @@ -0,0 +1,135 @@ +name: versioning +run-name: versioning tasks + +on: + pull_request: + branches: + - main + push: + branches: + - main + +permissions: + contents: write + +jobs: + pull-request: + # only run on template itself, not user instance of template + if: | + github.repository == 'greenelab/lab-website-template' && + github.event_name == 'pull_request' + runs-on: ubuntu-latest + steps: + # for debugging + - uses: crazy-max/ghaction-dump-context@v2 + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 + + - name: Checkout base branch contents + uses: actions/checkout@v4 + with: + ref: main + path: base + + - name: Checkout pr branch contents + uses: actions/checkout@v4 + with: + path: pr + + - name: Install packages + run: npm install yaml semver + + - name: Check version, date, changelog + uses: actions/github-script@v7 + with: + script: | + const { readFileSync } = require("fs"); + const { lte, valid } = require("semver"); + const { parse } = require("yaml"); + + // load and parse file contents + const { version: oldVersion, "date-released": oldDate } = parse( + readFileSync("base/CITATION.cff").toString() + ); + const { version: newVersion, "date-released": newDate } = parse( + readFileSync("pr/CITATION.cff").toString() + ); + const changelog = readFileSync("pr/CHANGELOG.md") + .toString() + .split(/^## /m) + .map((section) => { + const [heading, ...body] = section.split("\n"); + return [heading.trim(), body.join("\n").trim()]; + }); + + // check version + if (!valid(newVersion)) throw Error("Version not valid"); + if (lte(newVersion, oldVersion)) throw Error("Version not updated"); + + // check date + if (new Date(newDate).toISOString().split("T")[0] !== newDate) + throw Error("Date not valid"); + if (new Date(newDate) <= new Date(oldDate)) throw Error("Date not updated"); + + // check changelog + const newSection = changelog.find( + ([heading, body]) => + heading.includes(newVersion) && heading.includes(newDate) && body + ); + if (!newSection) throw Error("Changelog not updated or not valid"); + + push: + # only run on template itself, not user instance of template + if: | + github.repository == 'greenelab/lab-website-template' && + github.event_name == 'push' + runs-on: ubuntu-latest + steps: + # for debugging + - uses: crazy-max/ghaction-dump-context@v2 + + - name: Checkout branch contents + uses: actions/checkout@v4 + + - name: Install packages + run: npm install yaml semver + + # for debugging + - if: runner.debug == '1' + uses: mxschmitt/action-tmate@v3 + + - name: Get version and body + id: version + uses: actions/github-script@v7 + with: + script: | + const { readFileSync } = require("fs"); + const { parse } = require("yaml"); + + // load and parse file contents + const { version, "date-released": date } = parse( + readFileSync("CITATION.cff").toString() + ); + const changelog = readFileSync("CHANGELOG.md") + .toString() + .split(/^## /m) + .map((section) => { + const [heading, ...body] = section.split("\n"); + return [heading.trim(), body.join("\n").trim()]; + }); + + // find changelog body for version + const [, body = ""] = + changelog.find( + ([heading]) => heading.includes(version) && heading.includes(date) + ) || []; + + return { version, body }; + + - name: Create GitHub release + uses: ncipollo/release-action@v1.14.0 + with: + commit: ${{ github.ref }} + tag: v${{ fromJson(steps.version.outputs.result).version }} + name: v${{ fromJson(steps.version.outputs.result).version }} + body: ${{ fromJson(steps.version.outputs.result).body }} diff --git a/CHANGELOG.md b/CHANGELOG.md new file mode 100644 index 00000000..fb1f988e --- /dev/null +++ b/CHANGELOG.md @@ -0,0 +1,152 @@ +# Changelog + +Reference: common-changelog.org + +## 1.2.1 - 2024-04-01 + +### Changed + +- Minor bug fixes in cite process and sitemap generation. + +## 1.2.0 - 2024-03-08 + +### Changed + +- Update all GitHub Actions to fix "Node v16 deprecated" warnings. +- Sources that Manubot doesn't know how to cite (e.g. wosuid:12345) are now ignored by default if they're from metasources. +- Fix bug where passing tags to tags component manually doesn't work. +- Fix bug in citation (and other) components when `lookup` is blank. +- Fix nested tables bug. +- Dark mode tweaks. +- Various CSS tweaks and fixes. + +### Added + +- Add `image` param to support blog post thumbnails. +- Add `html-proofer` plugin that checks for broken images/links/etc. +- Add `remove` flag to remove a source from a metasource. + +## 1.1.6 - 2023-10-06 + +### Changed + +- Use latest minor versions of Python packages in auto-cite script. + +## 1.1.5 - 2023-05-19 + +### Changed + +- Fix ORCID plugin bug and other cite process tweaks. + +## 1.1.4 - 2023-04-28 + +### Changed + +- Fix ORCID plugin and other cite process bugs. + +## 1.1.3 - 2023-04-20 + +### Changed + +- Fix first-time-setup mv bug. +- Fix citation, float, and portrait component CSS. +- Filter and trim citation info fields. + +## 1.1.2 - 2023-04-11 + +### Changed + +- Fix first-time-setup rm bug. + +## 1.1.1 - 2023-04-06 + +### Changed + +- Change member profile page from col layout to float. +- Fix first time setup. Preserve config formatting and comments. +- Improve Docker cite process behavior. +- Fix post excerpt component start/end markers and special search attr chars. +- Fix misc CSS. + +### Added + +- Add show-title and show-subtitle site config options. +- Include site subtitle in description meta tag. +- Add user pull request template. +- Add title and link fallbacks to citation component. + +## 1.1.0 - 2023-03-17 + +Add alert component, Docker support, accessibility fixes. + +### Changed + +- Fix Lighthouse accessibility issues. +- De-href components when link isn't provided (no hand cursor icon on hover or nav on click). +- In search script, limit highlights by total count instead of char length. +- Grid and link style tweaks. +- Take ORCID icon from Font Awesome. +- Misc bug fixes in tags script, float component. + +### Added + +- Add Docker configuration and scripts for local previewing. +- Add alert component and types. +- Role icon in portrait component hoisted to top left. + +## 1.0.0 - 2023-02-28 + +First official release. + +High-level comparison with pre-releases: + +- Simpler configuration. +- More automation, less setup. +- More customization and flexibility. +- Redesigned components. +- New docs. +- Complete rewrite. +- Culmination of years of feedback. + +### Changed + +- Template is no longer limited to GitHub Pages white-listed Jekyll plugins. Any plugins possible. +- Pull request previews happen right within GitHub instead of needing Netlify. +- Better versioning. `CITATION.cff` file now source of truth for version, and tags/releases enforced. +- Citation-related files in `/_data` must now be named prefixed with the cite plugin they are to be run with, e.g. `sources-2020.yaml` or `orcid-students.yaml`. +- Folder renames for clarity and for better separation of template and user content: `/auto-cite` โ†’ `/_cite`, `/css` โ†’ `/_styles`, `/js` โ†’ `/_scripts`. +- Rename "Tools" page to "Projects" to be more clear and general purpose. +- Rename `extra-links` to `buttons` in `sources.yaml` files. +- Rename `theme.scss` to `-theme.scss`. +- Rename/repurpose components: link โ†’ button, two-col โ†’ cols, gallery โ†’ grid. +- Combine "link" and "role" data lists into single `types.yaml` map. +- Redesign components, change parameters and behavior. +- Update Font Awesome icon names from v5 to v6. +- Change placeholder text, images, and other images. +- Use CSS variables instead of Sass variables. +- Simplify caching method in cite process. +- Simplify Liquid code by including custom Ruby plugins. +- Simplify styles and scripts. + +### Added + +- New docs at greene-lab.gitbook.io/lab-website-template-docs. +- Add automations for first time setup and URL change. +- Write PubMed and Google Scholar automatic citation plugins. +- Automatic citations through GitHub Actions should now work from (most) forks. +- Add optional description and type params for citations. +- Add periodic cite process run that opens a pull request. +- List component filters can now accept arbitrary regex. +- Add light/dark mode toggle. +- Pre-install selection of useful Jekyll plugins, namely Jekyll Spaceship. +- Add author portrait and updated date for blog posts. +- Add richer metadata for SEO. +- Google Fonts link determined automatically from theme file. + +### Removed + +- Remove options from `_config.yaml` to simplify configuration: `baseurl`, `auto-cite`, `logo`. +- Remove `/favicons` folder, hardcode files for logo, icon, and share in `/images`. +- Remove `palettes.scss` and `mixins.scss`. +- Remove banner component (same thing can be achieved with full width section and figure components). +- Remove role component. Combine with portrait component. diff --git a/CITATION.cff b/CITATION.cff index 22d406ce..4b875d47 100644 --- a/CITATION.cff +++ b/CITATION.cff @@ -1,8 +1,8 @@ # citation metadata for the template itself title: "Lab Website Template" -version: 1.1.6 -date-released: 2023-10-06 +version: 1.2.1 +date-released: 2024-04-01 url: "https://github.com/greenelab/lab-website-template" authors: - family-names: "Rubinetti" diff --git a/Gemfile b/Gemfile index b39f041e..cbdd53f2 100644 --- a/Gemfile +++ b/Gemfile @@ -4,6 +4,8 @@ source "https://rubygems.org" gem "jekyll", "~> 4.3" gem "webrick", "~> 1.7" +gem "html-proofer", "~> 5.0" + # plugins group :jekyll_plugins do gem "jekyll-spaceship" diff --git a/Gemfile.lock b/Gemfile.lock index d719aa93..ee2cb121 100644 --- a/Gemfile.lock +++ b/Gemfile.lock @@ -1,23 +1,50 @@ GEM remote: https://rubygems.org/ specs: + Ascii85 (1.1.0) addressable (2.8.1) public_suffix (>= 2.0.2, < 6.0) + afm (0.2.2) + async (2.8.1) + console (~> 1.10) + fiber-annotation + io-event (~> 1.1) + timers (~> 4.1) colorator (1.1.0) concurrent-ruby (1.2.2) + console (1.23.4) + fiber-annotation + fiber-local + json em-websocket (0.5.3) eventmachine (>= 0.12.9) http_parser.rb (~> 0) + ethon (0.16.0) + ffi (>= 1.15.0) eventmachine (1.2.7) ffi (1.15.5) ffi (1.15.5-x64-mingw-ucrt) + fiber-annotation (0.2.0) + fiber-local (1.0.0) forwardable-extended (2.6.0) gemoji (3.0.1) + google-protobuf (3.22.0) google-protobuf (3.22.0-arm64-darwin) google-protobuf (3.22.0-x64-mingw-ucrt) + hashery (2.1.2) + html-proofer (5.0.8) + addressable (~> 2.3) + async (~> 2.1) + nokogiri (~> 1.13) + pdf-reader (~> 2.11) + rainbow (~> 3.0) + typhoeus (~> 1.3) + yell (~> 2.0) + zeitwerk (~> 2.5) http_parser.rb (0.8.0) i18n (1.12.0) concurrent-ruby (~> 1.0) + io-event (1.4.4) jekyll (4.3.2) addressable (~> 2.4) colorator (~> 1.0) @@ -52,6 +79,7 @@ GEM rainbow (~> 3.0) jekyll-watch (2.2.1) listen (~> 3.0) + json (2.7.1) kramdown (2.4.0) rexml kramdown-parser-gfm (1.1.0) @@ -69,24 +97,41 @@ GEM racc (~> 1.4) pathutil (0.16.2) forwardable-extended (~> 2.6) + pdf-reader (2.12.0) + Ascii85 (~> 1.0) + afm (~> 0.2.1) + hashery (~> 2.0) + ruby-rc4 + ttfunk posix-spawn (0.3.15) public_suffix (5.0.1) racc (1.6.2) rainbow (3.1.1) + rake (13.1.0) rb-fsevent (0.11.2) rb-inotify (0.10.1) ffi (~> 1.0) rexml (3.2.5) rouge (3.30.0) + ruby-rc4 (0.1.5) safe_yaml (1.0.5) + sass-embedded (1.58.3) + google-protobuf (~> 3.21) + rake (>= 10.0.0) sass-embedded (1.58.3-arm64-darwin) google-protobuf (~> 3.21) sass-embedded (1.58.3-x64-mingw-ucrt) google-protobuf (~> 3.21) terminal-table (3.0.2) unicode-display_width (>= 1.1.1, < 3) + timers (4.3.5) + ttfunk (1.7.0) + typhoeus (1.4.1) + ethon (>= 0.9.0) unicode-display_width (2.4.2) webrick (1.8.1) + yell (2.2.2) + zeitwerk (2.6.13) PLATFORMS aarch64-linux @@ -99,6 +144,7 @@ PLATFORMS x86_64-linux DEPENDENCIES + html-proofer (~> 5.0) jekyll (~> 4.3) jekyll-feed jekyll-last-modified-at @@ -108,4 +154,4 @@ DEPENDENCIES webrick (~> 1.7) BUNDLED WITH - 2.4.7 + 2.5.6 diff --git a/_cite/cite.py b/_cite/cite.py index 5f8d135a..6cd5befc 100644 --- a/_cite/cite.py +++ b/_cite/cite.py @@ -124,6 +124,10 @@ for index, source in enumerate(sources): log(f"Processing source {index + 1} of {len(sources)}, {label(source)}") + # if explicitly flagged, remove/ignore entry + if get_safe(source, "remove", False) == True: + continue + # new citation data for source citation = {} @@ -148,7 +152,7 @@ else: log(e, 3, "WARNING") # discard source from citations - # continue + continue # preserve fields from input source, overriding existing fields citation.update(source) diff --git a/_cite/util.py b/_cite/util.py index 466a7d56..904ff332 100644 --- a/_cite/util.py +++ b/_cite/util.py @@ -7,7 +7,7 @@ import yaml from yaml.loader import SafeLoader from pathlib import Path -from datetime import datetime +from datetime import date, datetime from rich import print from diskcache import Cache @@ -88,15 +88,17 @@ def list_of_dicts(data): return isinstance(data, list) and all(isinstance(entry, dict) for entry in data) -def format_date(date): +def format_date(_date): """ format date as YYYY-MM-DD, or no date if malformed """ - if isinstance(date, int): - return datetime.fromtimestamp(date // 1000.0).strftime("%Y-%m-%d") + if isinstance(_date, int): + return datetime.fromtimestamp(_date // 1000.0).strftime("%Y-%m-%d") + if isinstance(_date, (date, datetime)): + return _date.strftime("%Y-%m-%d") try: - return datetime.strptime(date, "%Y-%m-%d").strftime("%Y-%m-%d") + return datetime.strptime(_date, "%Y-%m-%d").strftime("%Y-%m-%d") except Exception: return "" diff --git a/_includes/card.html b/_includes/card.html index feb325cb..600cc971 100644 --- a/_includes/card.html +++ b/_includes/card.html @@ -35,7 +35,9 @@ {% endif %} {% if include.description %} - {{ include.description | markdownify }} +

+ {{ include.description | markdownify | remove: "

" | remove: "

" }} +

{% endif %} {% if include.tags or include.repo %} diff --git a/_includes/citation.html b/_includes/citation.html index ea62b17e..3eb8b2b4 100644 --- a/_includes/citation.html +++ b/_includes/citation.html @@ -1,96 +1,109 @@ -{% assign citation = site.data.citations - | where_exp: "citation", - "citation.id == include.lookup or citation.title contains include.lookup" - | first - | default: include -%} +{% if include.lookup %} + {% assign citation = site.data.citations + | where_exp: "citation", + "citation.id == include.lookup or citation.title contains include.lookup" + | first + %} +{% else %} + {% assign citation = include %} +{% endif %} -
- {% if include.style == "rich" %} - - {{ citation.title | default: +
+ {% if include.style == "rich" %} + - - {% endif %} + {{ citation.title | default: + + {% endif %} -
- {% assign type = site.data.types[citation.type] %} - {% include icon.html icon=type.icon %} +
+ {% assign type = site.data.types[citation.type] %} + {% include icon.html icon=type.icon %} - - {{ citation.title | default: "[no title info]" }} - + + {{ citation.title | default: "[no title info]" }} + -
10 %} - data-tooltip="{{ citation.authors | join: ", " }} " - {% endif %} - tabindex="0" - > - {{ - citation.authors - | join: "," - | split: "," - | array_carve: 5 - | join: ", " - | default: "[no author info]" - }} -
+
10 %} + data-tooltip="{{ citation.authors | join: ", " }} " + {% endif %} + tabindex="0" + > + {{ + citation.authors + | join: "," + | split: "," + | array_carve: 5 + | join: ", " + | markdownify + | remove: "

" | remove: "

" + | default: "[no author info]" + }} +
-
- {{ citation.publisher | default: "[no publisher info]" }} -   ยท   - {{ citation.date | default: "[no date info]" | date: "%d %b %Y" }} -   ยท   - {{ citation.id | default: "[no id info]" }} -
+
+ + {{- citation.publisher | default: "[no publisher info]" -}} + +  ยท  + + {{- citation.date | default: "[no date info]" | date: "%d %b %Y" -}} + +  ยท  + + {{- citation.id | default: "[no id info]" -}} + +
- {% if include.style == "rich" %} - {% if citation.description %} -
- {{ - citation.description - | markdownify - | remove: "

" - | remove: "

" - }} -
- {% endif %} + {% if include.style == "rich" %} + {% if citation.description %} +
+ {{ + citation.description + | markdownify + | remove: "

" + | remove: "

" + }} +
+ {% endif %} - {% if citation.buttons.size > 0 %} -
- {% for button in citation.buttons %} - {% - include button.html - type=button.type - icon=button.icon - text=button.text - link=button.link - style="bare" - %} - {% endfor %} -
- {% endif %} + {% if citation.buttons.size > 0 %} +
+ {% for button in citation.buttons %} + {% + include button.html + type=button.type + icon=button.icon + text=button.text + link=button.link + style="bare" + %} + {% endfor %} +
+ {% endif %} - {% if citation.tags.size > 0 or citation.repo %} - {% include tags.html tags=citation.tags repo=citation.repo %} + {% if citation.tags.size > 0 or citation.repo %} + {% include tags.html tags=citation.tags repo=citation.repo %} + {% endif %} {% endif %} - {% endif %} +
diff --git a/_includes/content.html b/_includes/content.html index 44c59d88..f9d01c89 100644 --- a/_includes/content.html +++ b/_includes/content.html @@ -2,17 +2,11 @@ modify main content of page: - add section breaks - attach section properties - - wrap each table in div to allow for scrolling - filter out blank sections --> {% assign content = include.content %} -{% assign content = content - | regex_replace: "(.*?)
", - "
\1
" -%} - {% assign sections = content | split: "" | array_filter %} {% for section in sections %} diff --git a/_includes/fonts.html b/_includes/fonts.html index 8fe3b65d..153709b2 100644 --- a/_includes/fonts.html +++ b/_includes/fonts.html @@ -5,13 +5,13 @@ -{% assign fontawesome = "https://use.fontawesome.com/releases/v6.3.0/css/all.css" %} +{% assign fontawesome = "https://use.fontawesome.com/releases/v6.5.0/css/all.css" %} + rel="stylesheet" + media="none" + onload="this.removeAttribute('media'); this.onload = null;" +/> diff --git a/_includes/header.html b/_includes/header.html index 967078ce..4dbdac0e 100644 --- a/_includes/header.html +++ b/_includes/header.html @@ -27,12 +27,12 @@ {% endif %} {% if site.logo-text != false %} - + {% if site.title and site.show-title != false %} - {{ site.title }} + {{ site.title }} {% endif %} {% if site.subtitle and site.show-subtitle != false %} - {{ site.subtitle }} + {{ site.subtitle }} {% endif %} {% endif %} diff --git a/_includes/meta.html b/_includes/meta.html index dabae072..1336e305 100644 --- a/_includes/meta.html +++ b/_includes/meta.html @@ -24,7 +24,9 @@ {{ site.subtitle }}. {{ description }} {%- endcapture %} {% endif %} -{% assign url = site.location %} +{% capture url -%} + {{ site.url }}{{ site.baseurl }} +{%- endcapture %} {% assign png = "images/icon.png" | file_exists %} {% assign jpg = "images/icon.jpg" | file_exists %} diff --git a/_includes/portrait.html b/_includes/portrait.html index dade824f..3b77f3d1 100644 --- a/_includes/portrait.html +++ b/_includes/portrait.html @@ -1,8 +1,11 @@ -{% assign member = site.members - | where_exp: "member", "member.slug == include.lookup" - | first - | default: include -%} +{% if include.lookup %} + {% assign member = site.members + | where_exp: "member", "member.slug == include.lookup" + | first + %} +{% else %} + {% assign member = include %} +{% endif %}
- {% assign url = post.url %} - {% assign title = post.title %} - {{ title }} +
+
+ {% assign url = post.url %} + {% assign title = post.title %} + {% assign image = post.image %} - {% - include post-info.html - author=post.author - published=post.date - updated=post.last_modified_at - tags=post.tags - %} + {% if image %} + + {{ title | default: + + {% endif %} - {% assign excerpt = post.content - | default: "" - | regex_scan: "(.*)", true - | default: post.excerpt - | default: "" - | strip_html - %} - {% assign search = post.content - | strip_html - | strip_newlines - | regex_strip - %} -

- {{ excerpt }} -

+
+ {{ title }} + + {% + include post-info.html + author=post.author + published=post.date + updated=post.last_modified_at + tags=post.tags + %} + + {% assign excerpt = post.content + | default: "" + | regex_scan: "(.*)", true + | default: post.excerpt + | default: "" + | strip_html + %} + {% assign search = post.content + | strip_html + | strip_newlines + | regex_strip + %} +

+ {{ excerpt }} +

+
+
diff --git a/_layouts/post.html b/_layouts/post.html index 9b1641a9..09fd57b0 100644 --- a/_layouts/post.html +++ b/_layouts/post.html @@ -2,6 +2,8 @@ layout: default --- +{% include section.html background=page.image %} +

{{ page.title }}

{% diff --git a/_members/jane-smith.md b/_members/jane-smith.md new file mode 100644 index 00000000..f4cae896 --- /dev/null +++ b/_members/jane-smith.md @@ -0,0 +1,19 @@ +--- +name: Jane Smith +image: images/photo.jpg +role: pi +aliases: + - J. Smith + - J Smith +links: + home-page: https://janesmith.com + orcid: 0000-0001-8713-9213 +--- + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +Faucibus purus in massa tempor nec feugiat nisl pretium fusce. +Elit at imperdiet dui accumsan. +Duis tristique sollicitudin nibh sit amet commodo nulla facilisi. +Vitae elementum curabitur vitae nunc sed velit dignissim sodales. +Lacinia at quis risus sed vulputate odio ut. +Magna eget est lorem ipsum. diff --git a/_members/john-doe.md b/_members/john-doe.md new file mode 100644 index 00000000..0e441c6d --- /dev/null +++ b/_members/john-doe.md @@ -0,0 +1,10 @@ +--- +name: John Doe +image: images/photo.jpg +role: phd +group: alum +links: + github: john-doe +--- + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. diff --git a/_members/sarah-johnson.md b/_members/sarah-johnson.md new file mode 100644 index 00000000..b0d97b44 --- /dev/null +++ b/_members/sarah-johnson.md @@ -0,0 +1,11 @@ +--- +name: Sarah Johnson +image: images/photo.jpg +description: Lead Programmer +role: programmer +links: + email: sarah.johnson@gmail.com + twitter: sarahjohnson +--- + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. diff --git a/_plugins/misc.rb b/_plugins/misc.rb index 6b4cb0fc..fe19bd8f 100644 --- a/_plugins/misc.rb +++ b/_plugins/misc.rb @@ -1,4 +1,5 @@ require 'liquid' +require 'html-proofer' module Jekyll module MiscFilters @@ -14,7 +15,7 @@ def object_items(object) elsif object.is_a?(Array) return object end - return [] + return object end # filter a list of hashes by comma-sep'd field:value pairs @@ -54,6 +55,33 @@ def google_fonts(css) return url end end + + # based on https://github.com/episource/jekyll-html-proofer + module HtmlProofer + priority = Jekyll::Hooks::PRIORITY_MAP[:high] + 1000 + + Jekyll::Hooks.register(:site, :post_write, priority: priority) do |site| + if not site.config["proofer"] == false + options = { + allow_missing_href: true, + enforce_https: false, + ignore_files: [/.*testbed.html/], + ignore_urls: [ + /fonts\.gstatic\.com/, + /localhost:/, + /0\.0\.0\.0:/, + ], + } + + begin + HTMLProofer.check_directory(site.dest, options).run + rescue Exception => error + STDERR.puts error + # raise error + end + end + end + end end Liquid::Template.register_filter(Jekyll::MiscFilters) diff --git a/_posts/2023-02-23-example-post-3.md b/_posts/2023-02-23-example-post-3.md index c7b1038d..0aa5a153 100644 --- a/_posts/2023-02-23-example-post-3.md +++ b/_posts/2023-02-23-example-post-3.md @@ -1,5 +1,6 @@ --- title: Example post 3 +image: images/photo.jpg author: john-doe tags: biology, medicine --- diff --git a/_scripts/anchors.js b/_scripts/anchors.js index 904edf9c..58daabcb 100644 --- a/_scripts/anchors.js +++ b/_scripts/anchors.js @@ -6,7 +6,7 @@ const onLoad = () => { // for each heading const headings = document.querySelectorAll( - "h1[id], h2[id], h3[id], h4[id]" + "h1[id], h2[id], h3[id], h4[id], h5[id], h6[id]" ); for (const heading of headings) { // create anchor link diff --git a/_scripts/dark-mode.js b/_scripts/dark-mode.js index b0124d94..b75b25eb 100644 --- a/_scripts/dark-mode.js +++ b/_scripts/dark-mode.js @@ -3,12 +3,9 @@ */ { - // save/load user's dark mode preference from local storage - const loadDark = () => window.localStorage.getItem("dark-mode") === "true"; - const saveDark = (value) => window.localStorage.setItem("dark-mode", value); - - // immediately load saved mode before page renders - document.documentElement.dataset.dark = loadDark(); + // immediately load saved (or default) mode before page renders + document.documentElement.dataset.dark = + window.localStorage.getItem("dark-mode") ?? "false"; const onLoad = () => { // update toggle button to match loaded mode @@ -23,6 +20,6 @@ window.onDarkToggleChange = (event) => { const value = event.target.checked; document.documentElement.dataset.dark = value; - saveDark(value); + window.localStorage.setItem("dark-mode", value); }; } diff --git a/_scripts/table-wrap.js b/_scripts/table-wrap.js new file mode 100644 index 00000000..4c5bddd8 --- /dev/null +++ b/_scripts/table-wrap.js @@ -0,0 +1,25 @@ +/* + put a wrapper around each table to allow scrolling. +*/ + +{ + const onLoad = () => { + // for each top-level table + const tables = document.querySelectorAll("table:not(table table)"); + for (const table of tables) { + // create wrapper with scroll + const wrapper = document.createElement("div"); + wrapper.style.overflowX = "auto"; + + // undo css force-text-wrap + table.style.overflowWrap = "normal"; + + // add wrapper around table + table.parentNode.insertBefore(wrapper, table); + wrapper.appendChild(table); + } + }; + + // after page loads + window.addEventListener("load", onLoad); +} diff --git a/_styles/-theme.scss b/_styles/-theme.scss index 6ceff0f0..0caecc61 100644 --- a/_styles/-theme.scss +++ b/_styles/-theme.scss @@ -3,23 +3,25 @@ // colors [data-dark="false"] { - --primary: #0ea5e9; + --primary: #0795d9; --secondary: #7dd3fc; --text: #000000; --background: #ffffff; --background-alt: #fafafa; --light-gray: #e0e0e0; --gray: #808080; + --dark-gray: #404040; --overlay: #00000020; } [data-dark="true"] { - --primary: #0ea5e9; + --primary: #0795d9; --secondary: #075985; --text: #ffffff; --background: #181818; --background-alt: #1c1c1c; --light-gray: #404040; --gray: #808080; + --dark-gray: #b0b0b0; --overlay: #ffffff10; } @@ -31,7 +33,6 @@ --code: "Roboto Mono", monospace; // font sizes - --medium: 1rem; --large: 1.2rem; --xl: 1.4rem; --xxl: 1.6rem; @@ -44,8 +45,10 @@ // text line spacing --spacing: 2; + --compact: 1.5; // effects --rounded: 3px; --shadow: 0 0 10px 0 var(--overlay); + --transition: 0.2s ease; } diff --git a/_styles/alert.scss b/_styles/alert.scss index c789ad80..6e77eec2 100644 --- a/_styles/alert.scss +++ b/_styles/alert.scss @@ -28,10 +28,10 @@ font-size: var(--large); } -.alert-content > *:first-child { +.alert-content > :first-child { margin-top: 0; } -.alert-content > *:last-child { +.alert-content > :last-child { margin-bottom: 0; } diff --git a/_styles/all.scss b/_styles/all.scss index 3cceebd5..a8aeeaaa 100644 --- a/_styles/all.scss +++ b/_styles/all.scss @@ -1,7 +1,11 @@ --- --- -* { +*, +::before, +::after { box-sizing: border-box; - transition: none 0.2s; + -moz-text-size-adjust: none; + -webkit-text-size-adjust: none; + text-size-adjust: none; } diff --git a/_styles/anchor.scss b/_styles/anchor.scss index 96c1a87b..65c18d8d 100644 --- a/_styles/anchor.scss +++ b/_styles/anchor.scss @@ -11,10 +11,10 @@ opacity: 0; font-size: 0.75em; text-decoration: none; - transition-property: opacity, color; + transition: opacity var(--transition), color var(--transition); } -*:hover > .anchor, +:hover > .anchor, .anchor:focus { opacity: 1; } diff --git a/_styles/body.scss b/_styles/body.scss index ef748976..91ecffcf 100644 --- a/_styles/body.scss +++ b/_styles/body.scss @@ -1,18 +1,15 @@ --- --- -html, body { + display: flex; + flex-direction: column; margin: 0; padding: 0; min-height: 100vh; background: var(--background); color: var(--text); font-family: var(--body); -} - -body { - display: flex; - flex-direction: column; text-align: center; + line-height: var(--compact); } diff --git a/_styles/button.scss b/_styles/button.scss index 7b4122e4..ed497f00 100644 --- a/_styles/button.scss +++ b/_styles/button.scss @@ -22,14 +22,13 @@ button { background: var(--primary); color: var(--background); text-align: center; + font: inherit; font-family: var(--heading); font-weight: var(--semi-bold); - line-height: 1; text-decoration: none; vertical-align: middle; - -webkit-appearance: none; appearance: none; - transition-property: background, color; + transition: background var(--transition), color var(--transition); } .button:hover { diff --git a/_styles/card.scss b/_styles/card.scss index 57fe20df..d95888e4 100644 --- a/_styles/card.scss +++ b/_styles/card.scss @@ -37,9 +37,8 @@ padding: 20px; } -.card-text > *, -.card-text > .tags { - margin: 0; +.card-text > * { + margin: 0 !important; } .card-title { @@ -48,6 +47,6 @@ } .card-subtitle { - margin-top: -15px; + margin-top: -10px !important; font-style: italic; } diff --git a/_styles/citation.scss b/_styles/citation.scss index 0bcda445..dc6c95e2 100644 --- a/_styles/citation.scss +++ b/_styles/citation.scss @@ -4,9 +4,13 @@ $thumb-size: 180px; $wrap: 800px; +.citation-container { + container-type: inline-size; +} + .citation { display: flex; - margin: 15px 0; + margin: 20px 0; border-radius: var(--rounded); background: var(--background); overflow: hidden; @@ -32,7 +36,7 @@ $wrap: 800px; position: relative; display: inline-flex; flex-wrap: wrap; - gap: 15px; + gap: 10px; max-width: 100%; height: min-content; padding: 20px; @@ -47,7 +51,6 @@ $wrap: 800px; .citation-details, .citation-description { width: 100%; - line-height: calc(var(--spacing) - 0.4); } .citation-title { @@ -64,6 +67,10 @@ $wrap: 800px; z-index: -1; } +.citation-publisher { + text-transform: capitalize; +} + .citation-description { color: var(--gray); } @@ -84,7 +91,7 @@ $wrap: 800px; margin: 0; } -@media (max-width: $wrap) { +@container (max-width: #{$wrap}) { .citation { flex-direction: column; } diff --git a/_styles/code.scss b/_styles/code.scss index 79ada5e0..4a50657e 100644 --- a/_styles/code.scss +++ b/_styles/code.scss @@ -13,7 +13,6 @@ code.highlighter-rouge { padding: 2px 6px; background: var(--light-gray); border-radius: var(--rounded); - line-height: calc(var(--spacing) - 0.2); } // code block @@ -24,7 +23,6 @@ div.highlighter-rouge { overflow-x: auto; overflow-y: auto; text-align: left; - line-height: calc(var(--spacing) - 0.4); div.highlight { display: contents; diff --git a/_styles/cols.scss b/_styles/cols.scss index 7f5e9110..a3500b3c 100644 --- a/_styles/cols.scss +++ b/_styles/cols.scss @@ -18,11 +18,11 @@ $one: 500px; min-height: 0; } -.cols > div > *:first-child { +.cols > div > :first-child { margin-top: 0 !important; } -.cols > div > *:last-child { +.cols > div > :last-child { margin-bottom: 0 !important; } diff --git a/_styles/dark-toggle.scss b/_styles/dark-toggle.scss index 66d5906f..ade9c05d 100644 --- a/_styles/dark-toggle.scss +++ b/_styles/dark-toggle.scss @@ -8,9 +8,8 @@ margin: 0; border-radius: 999px; background: var(--primary); - -webkit-appearance: none; appearance: none; - transition-property: background; + transition: background var(--transition); } .dark-toggle:after { @@ -23,7 +22,7 @@ font-family: "Font Awesome 6 Free"; font-weight: 900; transform: translate(-50%, -50%); - transition: left 0.2s; + transition: left var(--transition); } .dark-toggle:checked:after { diff --git a/_styles/feature.scss b/_styles/feature.scss index f3042529..3d2a53f9 100644 --- a/_styles/feature.scss +++ b/_styles/feature.scss @@ -47,7 +47,7 @@ $wrap: 800px; } .feature-image { - width: unset; + width: 100%; max-width: calc($wrap / 2); } } diff --git a/_styles/grid.scss b/_styles/grid.scss index 21a3a337..8ff6d2eb 100644 --- a/_styles/grid.scss +++ b/_styles/grid.scss @@ -49,6 +49,6 @@ $one: 500px; } } -.grid > *:where(h1, h2, h3, h4) { +.grid > :where(h1, h2, h3, h4, h5, h6) { display: none; } diff --git a/_styles/header.scss b/_styles/header.scss index 4d251992..045e2935 100644 --- a/_styles/header.scss +++ b/_styles/header.scss @@ -46,7 +46,7 @@ header a { height: 100%; } -.title { +.title-text { display: flex; justify-content: flex-start; align-items: baseline; @@ -57,13 +57,11 @@ header a { text-align: left; } -// main title -.title > *:first-child { +.title { font-size: var(--large); } -// subtitle -.title > *:last-child { +.subtitle { opacity: 0.65; font-weight: var(--thin); } @@ -75,9 +73,8 @@ header a { height: 30px; margin: 0; color: var(--text); - -webkit-appearance: none; appearance: none; - transition-property: background; + transition: background var(--transition); } .nav-toggle:after { @@ -153,17 +150,17 @@ header[data-big] { height: $logo-big; } - .title { + .title-text { flex-direction: column; align-items: center; text-align: center; } - .title > *:first-child { + .title { font-size: var(--xxl); } - .title > *:last-child { + .subtitle { font-size: var(--large); } } diff --git a/_styles/heading.scss b/_styles/heading.scss index e02dc47c..2ea35a42 100644 --- a/_styles/heading.scss +++ b/_styles/heading.scss @@ -4,45 +4,47 @@ h1, h2, h3, -h4 { +h4, +h5, +h6 { + margin: 40px 0 20px 0; font-family: var(--heading); - line-height: calc(var(--spacing) - 0.2); + font-weight: var(--semi-bold); + text-align: left; + letter-spacing: 1px; } h1 { - margin: 40px 0 20px 0; - font-size: var(--xxl); + font-size: 1.6rem; font-weight: var(--regular); - letter-spacing: 1px; text-transform: uppercase; - text-align: left; + text-align: center; } h2 { - margin: 40px 0 20px 0; + font-size: 1.6rem; padding-bottom: 5px; border-bottom: solid 1px var(--light-gray); - font-size: var(--xl); font-weight: var(--regular); - letter-spacing: 1px; - text-align: left; } h3 { - margin: 40px 0 20px 0; - font-size: var(--large); - font-weight: var(--semi-bold); - text-align: left; + font-size: 1.5rem; } h4 { - margin: 40px 0 20px 0; - font-size: var(--medium); - font-weight: var(--semi-bold); - text-align: left; + font-size: 1.3rem; +} + +h5 { + font-size: 1.15rem; +} + +h6 { + font-size: 1rem; } -:where(h1, h2, h3, h4) > .icon { +:where(h1, h2, h3, h4, h5, h6) > .icon { margin-right: 1em; color: var(--light-gray); } diff --git a/_styles/link.scss b/_styles/link.scss index 7d1fb844..41230d38 100644 --- a/_styles/link.scss +++ b/_styles/link.scss @@ -3,7 +3,7 @@ a { color: var(--primary); - transition-property: color; + transition: color var(--transition); overflow-wrap: break-word; } diff --git a/_styles/list.scss b/_styles/list.scss index e90094fe..d769a6a3 100644 --- a/_styles/list.scss +++ b/_styles/list.scss @@ -16,4 +16,9 @@ li { padding-left: 10px; text-align: justify; line-height: var(--spacing); + + ul, + ol { + margin: 0; + } } diff --git a/_styles/portrait.scss b/_styles/portrait.scss index 50849f35..fa0c0396 100644 --- a/_styles/portrait.scss +++ b/_styles/portrait.scss @@ -48,7 +48,6 @@ .portrait-text { display: flex; flex-direction: column; - line-height: calc(var(--spacing) - 0.4); } .portrait-name { @@ -63,7 +62,7 @@ display: flex; justify-content: center; align-items: center; - width: 20%; + width: calc(20px + 10%); aspect-ratio: 1 / 1; border-radius: 999px; background: var(--background); diff --git a/_styles/post-excerpt.scss b/_styles/post-excerpt.scss index 6e57a105..27c7a1dc 100644 --- a/_styles/post-excerpt.scss +++ b/_styles/post-excerpt.scss @@ -1,31 +1,69 @@ --- --- +$thumb-size: 200px; +$wrap: 800px; + +.post-excerpt-container { + container-type: inline-size; +} + .post-excerpt { display: flex; - flex-wrap: wrap; - gap: 20px; margin: 20px 0; - padding: 20px 30px; border-radius: var(--rounded); background: var(--background); - text-align: left; + overflow: hidden; box-shadow: var(--shadow); } -.post-excerpt > * { +.post-excerpt-image { + position: relative; + width: $thumb-size; + flex-shrink: 0; + // box-shadow: var(--shadow); +} + +.post-excerpt-image img { + position: absolute; + inset: 0; + width: 100%; + height: 100%; + object-fit: cover; +} + +.post-excerpt-text { + display: flex; + flex-wrap: wrap; + gap: 20px; + padding: 20px 30px; + text-align: left; +} + +.post-excerpt-text > * { margin: 0 !important; } -.post-excerpt > a:first-child { +.post-excerpt-text > a:first-child { width: 100%; font-weight: var(--semi-bold); } -.post-excerpt > div { +.post-excerpt-text > div { justify-content: flex-start; } -.post-excerpt > p { +.post-excerpt-text > p { width: 100%; } + +@container (max-width: #{$wrap}) { + .post-excerpt { + flex-direction: column; + } + + .post-excerpt-image { + width: unset; + height: $thumb-size; + } +} diff --git a/_styles/post-info.scss b/_styles/post-info.scss index 4c8eaaab..65c86cbc 100644 --- a/_styles/post-info.scss +++ b/_styles/post-info.scss @@ -8,7 +8,7 @@ flex-wrap: wrap; gap: 20px; margin: 20px 0; - color: var(--gray); + color: var(--dark-gray); } .post-info .portrait { diff --git a/_styles/post-nav.scss b/_styles/post-nav.scss index 2fba2fc2..40b5dd17 100644 --- a/_styles/post-nav.scss +++ b/_styles/post-nav.scss @@ -9,22 +9,21 @@ $wrap: 600px; align-items: flex-start; gap: 10px; color: var(--gray); - line-height: calc(var(--spacing) - 0.4); } -.post-nav > *:first-child { +.post-nav > :first-child { text-align: left; } -.post-nav > *:last-child { +.post-nav > :last-child { text-align: right; } -.post-nav > *:first-child .icon { +.post-nav > :first-child .icon { margin-right: 0.5em; } -.post-nav > *:last-child .icon { +.post-nav > :last-child .icon { margin-left: 0.5em; } diff --git a/_styles/quote.scss b/_styles/quote.scss index e6dcb45d..68b2f3a4 100644 --- a/_styles/quote.scss +++ b/_styles/quote.scss @@ -7,10 +7,10 @@ blockquote { border-left: solid 4px var(--light-gray); } -blockquote > *:first-child { +blockquote > :first-child { margin-top: 0; } -blockquote > *:last-child { +blockquote > :last-child { margin-bottom: 0; } diff --git a/_styles/section.scss b/_styles/section.scss index bc3e5646..332deb65 100644 --- a/_styles/section.scss +++ b/_styles/section.scss @@ -6,7 +6,7 @@ $padding: 40px; section { padding: $padding max($padding, calc((100% - $page) / 2)); - transition-property: background, color; + transition: background var(--transition), color var(--transition); } section[data-size="wide"] { diff --git a/_styles/table.scss b/_styles/table.scss index c5736ef0..995c7002 100644 --- a/_styles/table.scss +++ b/_styles/table.scss @@ -1,14 +1,10 @@ --- --- -.table-wrapper { - margin: 40px 0; - overflow-x: auto; -} - table { - margin: 0 auto; + margin: 40px auto; border-collapse: collapse; + overflow-wrap: anywhere; } th { diff --git a/_styles/tags.scss b/_styles/tags.scss index 932b7ed8..4e98207f 100644 --- a/_styles/tags.scss +++ b/_styles/tags.scss @@ -2,7 +2,7 @@ --- .tags { - display: inline-flex; + display: flex; justify-content: center; align-items: center; flex-wrap: wrap; @@ -22,7 +22,7 @@ overflow: hidden; text-overflow: ellipsis; white-space: nowrap; - transition-property: background, color; + transition: background var(--transition), color var(--transition); } .tag:hover { diff --git a/_styles/textbox.scss b/_styles/textbox.scss index 07bc0128..6d33cedc 100644 --- a/_styles/textbox.scss +++ b/_styles/textbox.scss @@ -12,7 +12,6 @@ input[type="text"] { color: var(--text); font-family: inherit; font-size: inherit; - -webkit-appearance: none; appearance: none; box-shadow: var(--shadow); } diff --git a/testbed.md b/testbed.md new file mode 100644 index 00000000..6b343a5e --- /dev/null +++ b/testbed.md @@ -0,0 +1,437 @@ +--- +title: Testbed +header: https://upload.wikimedia.org/wikipedia/commons/thumb/e/ea/Van_Gogh_-_Starry_Night_-_Google_Art_Project.jpg/1024px-Van_Gogh_-_Starry_Night_-_Google_Art_Project.jpg +footer: https://upload.wikimedia.org/wikipedia/commons/thumb/e/ea/Van_Gogh_-_Starry_Night_-_Google_Art_Project.jpg/1024px-Van_Gogh_-_Starry_Night_-_Google_Art_Project.jpg +header-dark: false +footer-dark: false +--- + +# Testbed + +{% include section.html %} + +# Basic formatting + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. +Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. +Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum. + +[External link](https://some-website.org/) + +[Internal link](team) + +_italic text_ + +**bold text** + +~~strike-through text~~ + +
+
+Text with extra blank lines above and below +
+
+ +- list item a +- list item b +- list item c + +1. ordered list item 1 +1. ordered list item 2 +1. ordered list item 3 + + + +1. top level list item + - nested list item + 1. even deeper nested list item + +Plain image: + +![plain image](/images/photo.jpg) + +# Heading 1 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +## Heading 2 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +### Heading 3 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +#### Heading 4 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +##### Heading 5 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +###### Heading 6 + +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. + +--- + +| TABLE | Game 1 | Game 2 | Game 3 | Total | +| :---- | :----: | :----: | :----: | ----: | +| Anna | 144 | 123 | 218 | 485 | +| Bill | 90 | 175 | 120 | 385 | +| Cara | 102 | 214 | 233 | 549 | + +> It was the best of times it was the worst of times. +> It was the age of wisdom, it was the age of foolishness. +> It was the spring of hope, it was the winter of despair. + +```javascript +// some code with syntax highlighting +const popup = document.querySelector("#popup"); +popup.style.width = "100%"; +popup.innerText = + "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua."; +``` + +This sentence has `inline code`, useful for making references to variables, packages, versions, etc. within a sentence. + +Lorem ipsum dolor sit amet. +{:.left} +Consectetur adipiscing elit. +{:.center} +Sed do eiusmod tempor incididunt. +{:.right} + +{% include section.html %} + +# Jekyll Spaceship + +| Stage | Direct Products | ATP Yields | +| -----------------: | --------------: | ---------: | +| Glycolysis | 2 ATP | | +| ^^ | 2 NADH | 3--5 ATP | +| Pyruvaye oxidation | 2 NADH | 5 ATP | +| Citric acid cycle | 2 ATP | | +| ^^ | 6 NADH | 15 ATP | +| ^^ | 2 FADH | 3 ATP | +| 30--32 ATP | | | + +$ a \* b = c ^ b $ + +$ 2^{\frac{n-1}{3}} $ + +$ \int_a^b f(x)\,dx. $ + +```mermaid! +pie title Pets adopted by volunteers + "Dogs" : 386 + "Cats" : 85 + "Rats" : 35 +``` + +{% include section.html %} + +# Components + +## Section + +{% include section.html background="images/background.jpg" %} + +Section, `background` + +{% include section.html dark=true %} + +Section, `dark=true` + +{% include section.html background="images/background.jpg" dark=true %} + +Section, `background` `dark=true` + +{% include section.html size="wide" %} + +Section, `size=wide` + +{% include section.html size="full" %} + +Section, `size=full` w/ figure + +{% include figure.html image="https://images.rawpixel.com/image_1000/cHJpdmF0ZS9sci9pbWFnZXMvd2Vic2l0ZS8yMDIyLTA1L2ZsMjYyODgwODcyMjYtaW1hZ2VfMS1rb3k1Zzkxay5qcGc.jpg" link="team" width="100%" %} + +{% include section.html %} + +## Figure + +{% include figure.html image="images/icon.png" %} +{% include figure.html image="images/icon.png" caption="_Lorem_ **ipsum**." %} +{% include figure.html image="images/icon.png" caption="_Lorem_ **ipsum**. `px` width" width="400px" %} +{% include figure.html image="images/icon.png" caption="_Lorem_ **ipsum**. `%` width" link="team" width="50%" %} +{% include figure.html image="images/icon.png" caption="_Lorem_ **ipsum**. `px` height" link="team" height="200px" %} +{% include figure.html image="images/fallback.svg" caption="_Lorem_ **ipsum**. `px` width, svg" link="team" width="400px" %} +{% include figure.html image="images/fallback.svg" caption="_Lorem_ **ipsum**. `%` width, svg" link="team" width="50%" %} +{% include figure.html image="images/fallback.svg" caption="_Lorem_ **ipsum**. `px` height, svg" link="team" height="200px" %} + +{% include section.html %} + +## Button + +{% include button.html type="github" %} +{% include button.html type="github" style="bare" %} +{% include button.html type="github" icon="fa-brands fa-youtube" text="Override Text" tooltip="Override tooltip" %} +{% include button.html type="github" text="" style="bare" %} +{% include button.html type="github" text="" link="github-handle" %} + +{% include section.html %} + +## Icon + +{% include icon.html icon="fa-solid fa-bacteria" %} +{% include icon.html icon="fa-solid fa-virus" %} +{% include icon.html icon="fa-solid fa-flask" %} +{% include icon.html icon="manubot.svg" %} + +{% include icon.html icon="fa-brands fa-github" %} Lorem +{% include icon.html icon="fa-solid fa-microscope" %} Ipsum +{% include icon.html icon="manubot.svg" %} Dolor + +{% include section.html %} + +## Feature + +{% capture text %} +_Lorem_ **ipsum** dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture%} +{% include feature.html image="images/icon.png" link="team" title="Title" text=text %} +{% include feature.html image="images/icon.png" title="Title" text=text flip=true %} +{% include feature.html link="team" %} + +{% include section.html %} + +## List + +### List citations + +{% include list.html data="citations" component="citation" %} + +--- + +### List projects + +{% include list.html data="projects" component="card" %} + +--- + +### List team members + +{% include list.html data="members" component="portrait" %} + +--- + +### List blog posts + +{% include list.html data="posts" component="post-excerpt" %} + +{% include section.html %} + +## Citation + +{% include citation.html lookup="doi:10.1016/j.csbj.2020.05.017" %} +{% include citation.html lookup="Open collaborative writing" style="rich" %} +{% include citation.html title="Manual title" authors="Manual authors" %} + +{% include section.html %} + +## Card + +{% include card.html image="images/icon.png" link="https://nasa.gov/" title="A Large Card" subtitle="A cool card" description="A cool description" tooltip="A cool tooltip" tags="manual tag" repo="greenelab/lab-website-template" %} +{% include card.html image="images/icon.png" title="A Small Card" subtitle="A cool card" description="_Lorem_ **ipsum**" tooltip="A cool tooltip" tags="manual tag" repo="greenelab/lab-website-template" style="small" %} + +{% include section.html %} + +## Portrait + +{% include portrait.html lookup="jane-smith" %} +{% include portrait.html lookup="john-doe" style="small" %} +{% include portrait.html name="Manual name" style="small" %} +{% include portrait.html style="small" %} + +{% include section.html %} + +## Post Excerpt + +{% include post-excerpt.html lookup="example-post-1" %} +{% include post-excerpt.html title="Manual title" author="Manual author" date="2020-02-20" last_modified_at="" %} + +{% include section.html %} + +## Alert + +{% capture lorem %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture %} +{% capture content %}**Tip** {{ lorem }}{% endcapture %} +{% include alert.html type="tip" content=content %} +{% capture content %}**Help** {{ lorem }}{% endcapture %} +{% include alert.html type="help" content=content %} +{% capture content %}**Info** {{ lorem }}{% endcapture %} +{% include alert.html type="info" content=content %} +{% capture content %}**Success** {{ lorem }}{% endcapture %} +{% include alert.html type="success" content=content %} +{% capture content %}**Warning** {{ lorem }}{% endcapture %} +{% include alert.html type="warning" content=content %} +{% capture content %}**Error** {{ lorem }}{% endcapture %} +{% include alert.html type="error" content=content %} + +{% include section.html %} + +## Tags + +{% include tags.html tags="ovarian cancer, dataset, gene expression" repo="greenelab/lab-website-template" link="blog" %} + +{% include section.html %} + +## Float + +### Figures + +{% capture content %} +{% include figure.html image="images/icon.png" caption="Caption" width="200px" %} +{% endcapture %} +{% include float.html content=content %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum. +{% include float.html clear=true %} + +### Code + +{% capture content %} + +```javascript +const test = "Lorem ipsum dolor sit amet, consectetur adipiscing elit."; +``` + +{% endcapture %} +{% include float.html content=content flip=true %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Nulla facilisi etiam dignissim diam quis. Id aliquet lectus proin nibh nisl condimentum id venenatis a. Tristique magna sit amet purus gravida quis blandit turpis cursus. Ultrices eros in cursus turpis massa tincidunt dui ut ornare. A cras semper auctor neque vitae tempus quam pellentesque nec. At tellus at urna condimentum mattis pellentesque. Ipsum consequat nisl vel pretium. Ultrices mi tempus imperdiet nulla malesuada pellentesque elit eget gravida. Integer vitae justo eget magna fermentum iaculis eu non diam. Mus mauris vitae ultricies leo integer malesuada nunc vel. Leo integer malesuada nunc vel risus. Ornare arcu odio ut sem nulla pharetra. Purus semper eget duis at tellus at urna condimentum. Enim neque volutpat ac tincidunt vitae semper quis lectus. + +{% include section.html %} + +## Grid + +### Regular + +With Markdown images + +{% capture content %} +![image](https://journals.plos.org/ploscompbiol/article/figure/image?size=inline&id=info:doi/10.1371/journal.pcbi.1007128.g001&rev=2) + +![image](https://ars.els-cdn.com/content/image/1-s2.0-S2001037020302804-gr1.jpg) + +![image](https://iiif.elifesciences.org/lax:32822%2Felife-32822-fig8-v3.tif/full/863,/0/default.webp) + +![image]({{ "/images/icon.png" | relative_url }}) + +![image]({{ "/images/icon.png" | relative_url }}) + +![image]({{ "/images/icon.png" | relative_url }}) +{% endcapture %} +{% include grid.html content=content %} + +### Square + +With figure components + +{% capture content %} +{% include figure.html image="https://journals.plos.org/ploscompbiol/article/figure/image?size=inline&id=info:doi/10.1371/journal.pcbi.1007128.g001&rev=2" %} +{% include figure.html image="https://ars.els-cdn.com/content/image/1-s2.0-S2001037020302804-gr1.jpg" %} +{% include figure.html image="https://iiif.elifesciences.org/lax:32822%2Felife-32822-fig8-v3.tif/full/863,/0/default.webp" %} +{% include figure.html image="images/icon.png" %} +{% include figure.html image="images/icon.png" %} +{% include figure.html image="images/icon.png" %} +{% endcapture %} +{% include grid.html style="square" content=content %} + +### Grid of citations + +{% capture content %} +{% include list.html data="citations" component="citation" style="rich" %} +{% endcapture %} +{% include grid.html content=content %} + +### Grid of blog posts + +{% capture content %} +{% include list.html data="posts" component="post-excerpt" %} +{% endcapture %} +{% include grid.html content=content %} + +{% include section.html %} + +## Cols + +### Text + +{% capture col1 %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture %} +{% capture col2 %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Nulla facilisi etiam dignissim diam quis. Id aliquet lectus proin nibh nisl condimentum id venenatis a. +{% endcapture %} +{% capture col3 %} +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Nulla facilisi etiam dignissim diam quis. Id aliquet lectus proin nibh nisl condimentum id venenatis a. Tristique magna sit amet purus gravida quis blandit turpis cursus. Ultrices eros in cursus turpis massa tincidunt dui ut ornare. A cras semper auctor neque vitae tempus quam pellentesque nec. At tellus at urna condimentum mattis pellentesque. Ipsum consequat nisl vel pretium. Ultrices mi tempus imperdiet nulla malesuada pellentesque elit eget gravida. Integer vitae justo eget magna fermentum iaculis eu non diam. Mus mauris vitae ultricies leo integer malesuada nunc vel. Leo integer malesuada nunc vel risus. Ornare arcu odio ut sem nulla pharetra. Purus semper eget duis at tellus at urna condimentum. Enim neque volutpat ac tincidunt vitae semper quis lectus. +{% endcapture %} +{% include cols.html col1=col1 col2=col2 col3=col3 %} + +### Images + +{% capture col1 %} +{% include figure.html image="images/icon.png" caption="Fig. 1a" %} +Lorem _ipsum_ dolor **sit** amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture %} +{% capture col2 %} +{% include figure.html image="images/icon.png" caption="Fig. 1b" %} +Lorem _ipsum_ dolor **sit** amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture %} +{% capture col3 %} +{% include figure.html image="images/icon.png" caption="Fig. 1c" %} +Lorem _ipsum_ dolor **sit** amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. +{% endcapture %} +{% include cols.html col1=col1 col2=col2 col3=col3 %} + +### Code + +{% capture col1 %} + +```javascript +const test = "Lorem ipsum dolor sit amet"; +``` + +{% endcapture %} +{% capture col2 %} + +```javascript +const test = "Lorem ipsum dolor sit amet"; +``` + +{% endcapture %} +{% capture col3 %} + +```javascript +const test = "Lorem ipsum dolor sit amet"; +``` + +{% endcapture %} +{% include cols.html col1=col1 col2=col2 col3=col3 %} + +{% include section.html %} + +## Search + +{% include search-box.html %} +{% include search-info.html %} + +{% include section.html %} + +## Site Search + +{% include site-search.html %}