Commit 45b10b9d authored by Ori Pomerantz's avatar Ori Pomerantz

feat(docs/op-stack): Initial version

Basically a copy paste of the current site
parent ae9f35d9
# The Optimism Community Hub
[![Discord](https://img.shields.io/discord/667044843901681675.svg?color=768AD4&label=discord&logo=https%3A%2F%2Fdiscordapp.com%2Fassets%2F8c9701b98ad4372b58f13fd9f65f966e.svg)](https://discord-gateway.optimism.io)
[![Twitter Follow](https://img.shields.io/twitter/follow/optimismPBC.svg?label=optimismPBC&style=social)](https://twitter.com/optimismPBC)
Optimism is a Layer 2 platform for Ethereum.
Optimism is, in a nutshell, an application inside of Ethereum that executes transactions more efficiently than Ethereum itself. It's based on the concept of the [Optimistic Rollup](https://research.paradigm.xyz/rollups), a construction that allows us to "optimistically" publish transaction results without actually executing those transactions on Ethereum (most of the time). Optimism makes transactions cheaper, faster, and smarter.
Please note that this repository is undergoing rapid development.
------
This is the source for the [community hub](https://community.optimism.io/).
# Usage
## Serve Locally
```shell
yarn dev
```
Then navigate to http://localhost:8080.
If that link doesn't work, double check the output of `yarn dev`.
You might already be serving something on port 8080 and the site may be on port 8081.
## Build for Production
```shell
yarn build
```
You probably don't need to run this command, but now you know.
{
"name": "optimism-hub",
"version": "0.0.2",
"description": "The Optimism Community Hub",
"main": "index.js",
"scripts": {
"dev": "vuepress dev src",
"build": "vuepress build src"
},
"license": "MIT",
"devDependencies": {
"@vuepress/plugin-medium-zoom": "^1.8.2",
"@vuepress/plugin-pwa": "^1.9.7",
"vuepress": "^1.8.2",
"vuepress-plugin-plausible-analytics": "^0.2.1",
"vuepress-theme-hope": "^1.22.0"
},
"dependencies": {
"check-md": "^1.0.2"
}
}
const { description } = require('../../package')
const path = require('path')
module.exports = {
title: 'OPStack Docs',
description: description,
head: [
['link', { rel: 'manifest', href: '/manifest.json' }],
['meta', { name: 'theme-color', content: '#3eaf7c' }],
['meta', { name: 'apple-mobile-web-app-capable', content: 'yes' }],
['meta', { name: 'apple-mobile-web-app-status-bar-style', content: 'black' }],
['link', { rel: "icon", type: "image/png", sizes: "32x32", href: "/assets/logos/favicon.png"}],
],
// cache: false,
theme: path.resolve(__dirname, './theme'),
themeConfig: {
contributor: false,
hostname: 'https://community.optimism.io',
logo: '/assets/logos/logo.png',
docsDir: 'src',
docsRepo: 'https://github.com/ethereum-optimism/opstack-docs',
docsBranch: 'main',
lastUpdated: false,
darkmode: 'disable',
themeColor: false,
blog: false,
iconPrefix: 'far fa-',
pageInfo: false,
pwa: {
cacheHTML: false,
},
activeHash: {
offset: -200,
},
algolia: {
appId: '8LQU4WGQXA',
apiKey: '2c1a86142192f96dab9a5066ad0c1d50',
indexName: 'optimism'
},
nav: [
/* When you update here, don't forget to update the tiles
in src/README.md */
{
text: 'How Optimism Works',
link: '/docs/protocol/',
},
{
text: 'Support',
link: '/docs/biz/'
},
{
text: 'Security',
link: '/docs/security-model/',
},
{
text: 'Dev Docs',
link: '/docs/developers/',
},
{
text: "Governance",
link: "/docs/governance/"
},
{
text: 'Contribute',
link: '/docs/contribute/',
},
{
text: 'Community',
items: [
{
icon: 'discord',
iconPrefix: 'fab fa-',
iconClass: 'color-discord',
text: 'Discord',
link: 'https://discord.optimism.io',
},
{
icon: 'github',
iconPrefix: 'fab fa-',
iconClass: 'color-github',
text: 'GitHub',
link: 'https://github.com/ethereum-optimism/optimism',
},
{
icon: 'twitter',
iconPrefix: 'fab fa-',
iconClass: 'color-twitter',
text: 'Twitter',
link: 'https://twitter.com/optimismFND',
},
{
icon: 'twitch',
iconPrefix: 'fab fa-',
iconClass: 'color-twitch',
text: 'Twitch',
link: 'https://www.twitch.tv/optimismpbc'
},
{
icon: 'medium',
iconPrefix: 'fab fa-',
iconClass: 'color-medium',
text: 'Blog',
link: 'https://optimismpbc.medium.com/'
},
{
icon: 'computer-classic',
iconClass: 'color-ecosystem',
text: 'Ecosystem',
link: 'https://www.optimism.io/apps/all',
},
{
icon: 'globe',
iconClass: 'color-optimism',
text: 'optimism.io',
link: 'https://www.optimism.io/',
}
]
}
],
searchPlaceholder: 'Search the docs',
sidebar: {
'/docs/governance/': [
[
'/docs/governance/',
'What is the Optimism Collective?'
],
[
'https://www.optimism.io/vision',
'The Optimistic Vision'
],
{
title: "OP Holders",
children: [
'/docs/governance/howto-delegate.md',
'/docs/governance/economics.md',
'/docs/governance/allocations.md',
'/docs/governance/airdrop-1.md'
],
collapsable: true,
},
{
title: "Delegates",
children: [
'/docs/governance/delegate.md',
'/docs/governance/existing-delegate.md',
'/docs/governance/delegate-info.md',
],
collapsable: true,
},
{
title: "Proposal Submitters",
children: [
'/docs/governance/proposals.md',
[
'https://gov.optimism.io/tags/c/proposals/38/passed',
'Passed Proposals'
]
],
collapsable: true,
},
{
title: "Token House Governance",
children: [
'/docs/governance/token-house.md',
'/docs/governance/token-house-history.md',
'/docs/governance/gov-fund.md',
[
"https://docs.google.com/spreadsheets/d/1Ul8iMTsOFUKUmqz6MK0zpgt8Ki8tFtoWKGlwXj-Op34",
"Governance Fund Tracker"
],
[
'https://gov.optimism.io/t/working-constitution-of-the-optimism-collective/55',
"Working Constitution"
],
[
'https://github.com/ethereum-optimism/OPerating-manual/blob/main/manual.md',
'Operating Manual'
]
],
collapsable: true,
},
{
title: "Citizen House Governance",
children: [
'/docs/governance/citizens-house.md',
'/docs/governance/citizenship.md',
'/docs/governance/retropgf-2.md',
],
collapsable: true
},
[
'https://calendar.google.com/calendar/u/0?cid=Y19mbm10Z3VoNm5vbzZxZ2JuaTJncGVyaWQ0a0Bncm91cC5jYWxlbmRhci5nb29nbGUuY29t',
'Governance Calendar'
],
'/docs/governance/attestation-station.md'
],
'/docs/security-model/': [
'/docs/security-model/optimism-security-model.md',
'/docs/security-model/bounties.md',
[
'https://medium.com/ethereum-optimism/our-pragmatic-path-to-decentralization-cb5805ca43c1',
'Decentralizing Optimism'
]
],
'/docs/protocol/': [
{
title: 'How Optimism Works',
children: [
'/docs/protocol/1-design-philosophy.md',
'/docs/protocol/2-rollup-protocol.md',
],
collapsable: false,
},
{
title: 'Protocol Specs',
children: [
'/docs/protocol/protocol-2.0.md',
'/docs/protocol/compressed-ctc.md'
],
collapsable: false,
}
],
'/docs/developers/': [
'/docs/developers/releases.md',
{
title: 'Building on Optimism',
children: [
'/docs/developers/build/using-tools.md',
'/docs/developers/build/transaction-fees.md',
'/docs/developers/build/system-contracts.md',
'/docs/developers/build/dev-node.md',
'/docs/developers/build/run-a-node.md',
'/docs/developers/build/differences.md',
'/docs/developers/build/json-rpc.md',
'/docs/developers/build/testing-dapps.md',
'/docs/developers/build/cheap-dapp.md'
],
},
{
title: 'Bridging L1 and L2',
children: [
'/docs/developers/bridge/basics.md',
'/docs/developers/bridge/standard-bridge.md',
'/docs/developers/bridge/messaging.md',
'/docs/developers/bridge/comm-strategies.md'
],
collapsable: true,
},
'/docs/developers/known-issues.md',
{
title: "Useful Tools",
children: [
'/docs/useful-tools/networks.md',
'/docs/useful-tools/debugging.md',
'/docs/useful-tools/faucets.md',
'/docs/useful-tools/monitoring.md',
'/docs/useful-tools/explorers.md',
'/docs/useful-tools/providers.md',
'/docs/useful-tools/oracles.md',
'/docs/useful-tools/meta-tx.md',
['https://www.optimism.io/apps/tools', 'Third Party Tools'],
],
},
{
title: "SDK",
children: [
'/docs/sdk/js-client.md',
[
'https://github.com/ethereum-optimism/optimism/tree/develop/packages/contracts/docs',
'Optimism Contracts'
],
'/docs/sdk/alchemy-sdk.md'
]
},
'/docs/developers/media.md',
{
title: "OP Stack: Bedrock",
children: [
'/docs/developers/bedrock/explainer.md',
'/docs/developers/bedrock/differences.md',
'/docs/developers/bedrock/public-testnets.md',
'/docs/developers/bedrock/node-operator-guide.md',
'/docs/developers/bedrock/upgrade-guide.md',
'/docs/developers/bedrock/metrics.md'
]
}
],
}
},
plugins: [
"@vuepress/pwa",
[
'@vuepress/plugin-medium-zoom',
{
// When an image is inside a link, it means we don't to expand it
// when clicked
selector: ':not(a) > img'
}
],
"plausible-analytics"
]
}
module.exports.themeConfig.sidebar["/docs/useful-tools/"] = module.exports.themeConfig.sidebar["/docs/developers/"]
export default ({ router }) => {
router.addRoutes([
{ path: '/docs/', redirect: '/' },
])
}
{
"name": "OP Docs",
"short_name": "OP Docs",
"description": "The official OP Docs",
"icons": [
{
"src": "/assets/logos/icon-192x192.png",
"sizes": "192x192",
"type": "image/png"
},
{
"src": "/assets/logos/icon-256x256.png",
"sizes": "256x256",
"type": "image/png"
},
{
"src": "/assets/logos/icon-384x384.png",
"sizes": "384x384",
"type": "image/png"
},
{
"src": "/assets/logos/icon-512x512.png",
"sizes": "512x512",
"type": "image/png"
},
{
"src": "/assets/logos/icon-1020x1020.png",
"sizes": "any",
"type": "image/png"
}
],
"start_url": "/index.html",
"display": "standalone",
"background_color": "#ffffff",
"theme_color": "#ff0420"
}
@import url('https://fonts.googleapis.com/css2?family=Open+Sans:wght@400;600&display=swap');
@import url('https://fonts.googleapis.com/css2?family=Rubik:ital,wght@0,400;0,600;0,700;1,600;1,700&display=swap');
@import 'https://pro.fontawesome.com/releases/v5.15.4/css/all.css';
main, body, html {
font-family: 'Open Sans', sans-serif;
}
p {
font-size: 16px;
line-height: 24px;
}
aside.sidebar {
background-color: #F1F4F9;
border-right: none;
}
p.sidebar-heading {
color: #323A43 !important;
font-family: 'Open Sans', sans-serif;
font-weight: 600;
font-size: 14px !important;
line-height: 24px !important;
min-height: 36px;
margin-left: 32px;
padding: 8px 16px !important;
width: calc(100% - 64px) !important;
border-radius: 8px;
}
a.sidebar-link {
font-family: 'Open Sans', sans-serif;
font-size: 14px !important;
line-height: 24px !important;
min-height: 36px;
margin-left: 32px;
padding: 8px 16px !important;
width: calc(100% - 64px) !important;
border-radius: 8px;
}
section.sidebar-group a.sidebar-link {
margin-left: 44px;
width: calc(100% - 64px) !important;
}
.sidebar-links:not(.sidebar-group-items) > li > a.sidebar-link {
font-weight: 600 !important;
color: #323A43 !important;
}
.sidebar-links:not(.sidebar-group-items) > li > a.sidebar-link.active {
border-left-color: #F1F4F9 !important;
background-color: #FFDBDF !important;
color: #FF0420 !important;
}
a.sidebar-link.active {
border-left-color: #F1F4F9 !important;
background-color: #FFDBDF !important;
color: #FF0420 !important;
}
h1 {
font-size: 50px;
}
h2 {
font-size: 40px;
}
h3 {
font-size: 28px;
}
h4 {
font-size: 20px;
}
h1 {
font-family: 'Rubik', sans-serif;
font-weight: 700;
font-style: italic;
border-bottom: none;
color: #202327 !important;
}
h2, h3, h4 {
font-family: 'Rubik', sans-serif;
border-bottom: none;
font-weight: 400;
}
#search-form {
@media (min-width $MQNormal) {
margin-left: 2rem;
}
}
.search-box {
@media (min-width $MQNormal) {
order: 1;
margin-right: 0;
margin-left: 1rem;
.suggestions {
left: auto !important;
right: 0 !important;
}
}
input {
border-color: #CBD5E0 !important;
border-radius: 100px !important;
background-color: #FFFFFF !important;
}
}
header.navbar {
border-bottom: none;
box-shadow: 0px 6px 8px -6px rgba(20, 23, 26, 0.06), 0px 8px 16px -6px rgba(20, 23, 26, 0.04);
--bgcolor-blur: hsla(0,0%,100%,0.9);
}
span.site-name {
display: none !important;
}
a.nav-link,
div.nav-item span.title {
font-weight: 600;
}
a.nav-link:not(.router-link-active),
div.nav-item span.title {
color: #68778D;
}
.theme-default-content:not(.custom) > p {
text-align: inherit !important;
}
.sidebar {
box-shadow: none !important;
}
div.hero-info {
color: white;
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
display: flex;
align-items: center;
}
div.hero-info .description {
display: none;
}
div.hero-info #main-title {
color: white !important;
}
header.hero > img {
border-radius: 16px;
max-height: none !important;
}
header.hero {
margin-top: 20px;
position: relative;
justify-content: space-between !important;
}
.home .features {
border-top: none !important;
justify-content: space-between !important;
margin: 0 !important;
padding-top: 0.5rem !important;
}
.home .features h2 {
font-family: 'Open Sans', sans-serif;
font-style: normal;
font-size: 16px !important;
font-weight: 600 !important;
color: #202327 !important;
}
.home .features p {
font-family: 'Open Sans', sans-serif;
font-size: 14px !important;
color: #68778D !important;
}
.home .features .icon-container {
height: 44px;
width: 44px;
background-color: #FFF0F1;
border-radius: 8px;
display: flex;
justify-content: center;
align-items: center;
color: #FF0420;
}
.home .features .feature {
background-color: #FFFFFF !important;
box-shadow: 0px 6px 8px -6px rgba(20, 23, 26, 0.12), 0px 8px 16px -6px rgba(20, 23, 26, 0.08);
border-radius: 16px !important;
margin: 0 !important;
margin-bottom: 2rem !important;
padding: 1.5rem !important;
}
.features-header {
margin-top: 30px;
margin-bottom: 0px;
}
div.theme-container:not(.has-sidebar) {
background-color: #F1F4F9;
}
.anchor-header {
color: #202327;
font-weight: 600;
font-size: 14px;
font-height: 20px;
margin-bottom: 10px;
}
.anchor-support {
margin-top: 20px;
}
.anchor-support-links i {
width: 20px;
text-align: center;
margin-right: 5px;
}
.anchor-support-links a {
color: #68778D;
}
.anchor-support-links a div {
height: 30px;
font-size: 14px;
}
.anchor-support-links a:hover {
color: #FF0420;
}
#anchor {
width: 15rem !important;
}
#anchor .anchor {
line-height: 27.2px !important;
}
#anchor .anchor div {
color: #68778D !important;
}
#anchor .anchor.active div {
font-weight: 600 !important;
}
.theme-default-content code {
top: 1px;
line-height: 22.4px !important;
vertical-align: middle !important;
}
.nav-dropdown svg.icon.outbound {
display: none;
}
.nav-dropdown .dropdown-item i {
width: 20px;
}
.color-discord {
color: #5865F2;
}
.color-github {
color: #121212;
}
.color-twitter {
color: #1DA1F2;
}
.color-twitch {
color: #6441A5;
}
.color-medium {
color: #000000;
}
.color-optimism {
color: #FF0420;
}
.color-ecosystem {
color: #ea94db;
}
$textColor = #000000
$accentColor = #f01a37
$backgroundColor = #272934
$lightBackgroundColor = #f3f3f3
$sidebarWidth = 320px
import Vue from "vue";
import type { AlgoliaOption } from "@mr-hope/vuepress-types";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, {
placeholder: string;
}, {
initialize(userOptions: AlgoliaOption, lang: string): void;
update(options: AlgoliaOption, lang: string): void;
}, unknown, {
options: AlgoliaOption;
}>;
export default _default;
import Vue from "vue";
export default Vue.extend({
name: "AlgoliaSearchDropdown",
props: {
options: { type: Object, required: true },
},
data: () => ({
placeholder: "",
}),
watch: {
$lang(newValue) {
this.update(this.options, newValue);
},
options(newValue) {
this.update(newValue, this.$lang);
},
},
mounted() {
this.initialize(this.options, this.$lang);
this.placeholder =
this.$site.themeConfig.searchPlaceholder || "";
},
methods: {
initialize(userOptions, lang) {
void Promise.all([
import(
/* webpackChunkName: "docsearch" */ "docsearch.js/dist/cdn/docsearch.min.js"),
import(
/* webpackChunkName: "docsearch" */ "docsearch.js/dist/cdn/docsearch.min.css"),
]).then(([docsearch]) => {
// eslint-disable-next-line
docsearch.default(Object.assign(Object.assign({}, userOptions), { inputSelector: "#algolia-search-input",
// #697 Make docsearch work well at i18n mode.
algoliaOptions: {
facetFilters: [`lang:${lang}`].concat(
// eslint-disable-next-line
userOptions.facetFilters || []),
}, handleSelected: (_input, _event, suggestion) => {
const { pathname, hash } = new URL(suggestion.url);
const routepath = pathname.replace(this.$site.base, "/");
if (this.$router.getRoutes().some((route) => route.path === routepath))
void this.$router.push(`${routepath}${decodeURIComponent(hash)}`);
else
window.open(suggestion.url);
} }));
});
},
update(options, lang) {
this.$el.innerHTML =
'<input id="algolia-search-input" class="search-query">';
this.initialize(options, lang);
},
},
});
//# sourceMappingURL=Dropdown.js.map
\ No newline at end of file
{"version":3,"file":"Dropdown.js","sourceRoot":"","sources":["Dropdown.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AAKtB,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,uBAAuB;IAE7B,KAAK,EAAE;QACL,OAAO,EAAE,EAAE,IAAI,EAAE,MAAiC,EAAE,QAAQ,EAAE,IAAI,EAAE;KACrE;IAED,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC;QACX,WAAW,EAAE,EAAE;KAChB,CAAC;IAEF,KAAK,EAAE;QACL,KAAK,CAAC,QAAgB;YACpB,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,OAAO,EAAE,QAAQ,CAAC,CAAC;QACtC,CAAC;QAED,OAAO,CAAC,QAAuB;YAC7B,IAAI,CAAC,MAAM,CAAC,QAAQ,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC;QACpC,CAAC;KACF;IAED,OAAO;QACL,IAAI,CAAC,UAAU,CAAC,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC;QAC1C,IAAI,CAAC,WAAW;YACb,IAAI,CAAC,KAAK,CAAC,WAAW,CAAC,iBAA4B,IAAI,EAAE,CAAC;IAC/D,CAAC;IAED,OAAO,EAAE;QACP,UAAU,CAAC,WAA0B,EAAE,IAAY;YACjD,KAAK,OAAO,CAAC,GAAG,CAAC;gBACf,MAAM;gBACJ,mCAAmC,CAAC,wCAAwC,CAC7E;gBACD,MAAM;gBACJ,mCAAmC,CAAC,yCAAyC,CAC9E;aACF,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,SAAS,CAAC,EAAE,EAAE;gBACtB,2BAA2B;gBAC1B,SAAiB,CAAC,OAAO,iCACrB,WAAW,KACd,aAAa,EAAE,uBAAuB;oBACtC,8CAA8C;oBAC9C,cAAc,EAAE;wBACd,YAAY,EAAE,CAAC,QAAQ,IAAI,EAAE,CAAC,CAAC,MAAM;wBACnC,2BAA2B;wBACzB,WAAmB,CAAC,YAAyB,IAAI,EAAE,CACtD;qBACF,EACD,cAAc,EAAE,CACd,MAAwB,EACxB,MAAa,EACb,UAA2B,EAC3B,EAAE;wBACF,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE,GAAG,IAAI,GAAG,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;wBACnD,MAAM,SAAS,GAAG,QAAQ,CAAC,OAAO,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,EAAE,GAAG,CAAC,CAAC;wBAEzD,IACE,IAAI,CAAC,OAAO,CAAC,SAAS,EAAE,CAAC,IAAI,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,KAAK,CAAC,IAAI,KAAK,SAAS,CAAC;4BAElE,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,SAAS,GAAG,kBAAkB,CAAC,IAAI,CAAC,EAAE,CAAC,CAAC;;4BAC/D,MAAM,CAAC,IAAI,CAAC,UAAU,CAAC,GAAG,CAAC,CAAC;oBACnC,CAAC,IACD,CAAC;YACL,CAAC,CAAC,CAAC;QACL,CAAC;QAED,MAAM,CAAC,OAAsB,EAAE,IAAY;YACzC,IAAI,CAAC,GAAG,CAAC,SAAS;gBAChB,wDAAwD,CAAC;YAC3D,IAAI,CAAC,UAAU,CAAC,OAAO,EAAE,IAAI,CAAC,CAAC;QACjC,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<form
id="search-form"
class="algolia-search-wrapper search-box"
role="search"
>
<label class="sr-only" for="algolia-search-input">Algolia search</label>
<input
id="algolia-search-input"
class="search-query"
:placeholder="placeholder"
/>
</form>
</template>
<script src="./Dropdown" />
<style lang="stylus">
.algolia-search-wrapper
& > span
vertical-align middle
.algolia-autocomplete
line-height normal
.ds-dropdown-menu
min-width 515px !important
margin 6px 0 0
padding 4px
border 1px solid var(--light-grey)
border-radius 4px
background var(--bgcolor)
font-size 16px
text-align left
@media (max-width $MQMobile)
min-width calc(100vw - 4rem) !important
max-width calc(100vw - 4rem) !important
&:before
border-color var(--light-grey)
[class*=ds-dataset-]
padding 0
border none
background var(--bgcolor)
.ds-suggestions
margin-top 0
.ds-suggestion
border-bottom 1px solid var(--border-color)
.algolia-docsearch-suggestion--highlight
color var(--accent-color)
.algolia-docsearch-suggestion
padding 0
border-color var(--border-color)
background var(--bgcolor)
color var(--text-color)
.algolia-docsearch-suggestion--category-header
padding 5px 10px
margin-top 0
background var(--accent-color)
color var(--white)
font-weight 600
.algolia-docsearch-suggestion--highlight
background rgba(255, 255, 255, 0.6)
.algolia-docsearch-suggestion--wrapper
padding 0
@media (max-width $MQMobile)
padding 5px 7px 5px 5px !important
.algolia-docsearch-suggestion--title
margin-bottom 0
color var(--text-color)
font-weight 600
.algolia-docsearch-suggestion--subcategory-column
vertical-align top
padding 5px 7px 5px 5px
border-color var(--border-color)
background var(--bgcolor)
color var(--text-color)
@media (min-width $MQMobile)
display table-cell
float none
width 150px
min-width 150px
@media (max-width $MQMobile)
padding 0 !important
background white !important
&:after
display none
.algolia-docsearch-suggestion--subcategory-column-text
color #555
&:after
@media (max-width $MQMobile)
display inline-block
vertical-align middle
content ' > '
width 5px
margin -3px 3px 0
font-size 10px
line-height 14.4px
.algolia-docsearch-suggestion--content
@media (min-width $MQMobile)
display table-cell
float none
vertical-align top
width 100%
.algolia-docsearch-footer
border-color var(--border-color)
.ds-cursor .algolia-docsearch-suggestion--content
background var(--grey3)
color var(--text-color)
</style>
import Vue from "vue";
import type { AlgoliaOption } from "@mr-hope/vuepress-types";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
initialize(userOptions: AlgoliaOption, _lang: string): void;
resolveRoutePathFromUrl(absoluteUrl: string): string;
update(options: AlgoliaOption, lang: string): void;
}, unknown, {
options: AlgoliaOption;
}>;
export default _default;
import { createElement } from "preact";
import Vue from "vue";
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore: docsearch type issue
import docsearch from "@docsearch/js";
export default Vue.extend({
name: "AlgoliaSearchFull",
props: {
options: { type: Object, required: true },
},
watch: {
$lang(newValue) {
this.update(this.options, newValue);
},
options(newValue) {
this.update(newValue, this.$lang);
},
},
mounted() {
this.initialize(this.options, this.$lang);
},
methods: {
// eslint-disable-next-line @typescript-eslint/no-unused-vars
initialize(userOptions, _lang) {
// eslint-disable-next-line
docsearch(Object.assign(Object.assign({ container: "#docsearch", placeholder: this.$site.themeConfig.searchPlaceholder || "" }, userOptions), { searchParameters: userOptions.searchParameters || {},
// transform full url to route path
transformItems: (items) => items.map((item) => (Object.assign(Object.assign({}, item), {
// the `item.url` is full url with protocol and hostname
// so we have to transform it to vue-router path
url: this.resolveRoutePathFromUrl(item.url) }))),
// render the hit component with custom `onClick` handler
hitComponent: ({ hit, children }) => createElement("a", {
href: hit.url,
onClick: (event) => {
// We rely on the native link scrolling when user is
// already on the right anchor because Vue Router doesn’t
// support duplicated history entries.
if (this.$route.fullPath === hit.url)
return;
const fullPath = `${window.location.origin}${hit.url}`;
const { pathname: hitPathname } = new URL(fullPath);
// If the hits goes to another page, we prevent the native link behavior
// to leverage the Vue Router loading feature.
if (this.$route.path !== hitPathname)
event.preventDefault();
if (this.$router
.getRoutes()
.some((route) => route.path.replace(/index\.html$/, "") === hitPathname))
void this.$router.push(hit.url);
else
window.open(fullPath);
},
}, children), navigator: {
navigate: ({ itemUrl }) => {
const fullPath = `${window.location.origin}${itemUrl}`;
const { pathname: hitPathname } = new URL(fullPath);
// Vue Router doesn’t handle same-page navigation so we use
// the native browser location API for anchor navigation.
if (this.$route.path === hitPathname)
window.location.assign(fullPath);
else if (this.$router
.getRoutes()
.some((route) => route.path === hitPathname))
void this.$router.push(itemUrl);
else
window.open(fullPath);
},
navigateNewTab({ itemUrl }) {
window.open(itemUrl);
},
navigateNewWindow({ itemUrl }) {
window.open(itemUrl);
},
} }));
},
resolveRoutePathFromUrl(absoluteUrl) {
const { pathname, hash } = new URL(absoluteUrl);
return `${pathname.replace(this.$site.base, "/")}${hash}`;
},
update(options, lang) {
this.$el.innerHTML = '<div id="docsearch"></div>';
this.initialize(options, lang);
},
},
});
//# sourceMappingURL=Full.js.map
\ No newline at end of file
{"version":3,"file":"Full.js","sourceRoot":"","sources":["Full.ts"],"names":[],"mappings":"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"}
\ No newline at end of file
import Vue from "vue";
import { SidebarHeader } from "@theme/utils/sidebar";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, {}, {}, {}, {
items: SidebarHeader[];
}>;
export default _default;
import Vue from "vue";
import { isActive } from "@theme/utils/path";
const renderLink = (h, { text, link, level }) => h("RouterLink", {
props: {
to: link,
activeClass: "",
exactActiveClass: "",
},
class: {
"anchor-link": true,
[level ? `heading${level}` : ""]: level,
},
}, [h("div", {}, [text])]);
const renderChildren = (h, { children, route }) => h("ul", { class: "anchor-list" }, children.map((child) => {
const active = isActive(route, `${route.path}#${child.slug}`);
return h("li", { class: { anchor: true, active } }, [
renderLink(h, {
text: child.title,
link: `${route.path}#${child.slug}`,
level: child.level,
}),
]);
}));
export default Vue.extend({
name: "Anchor",
functional: true,
props: {
items: {
type: Array,
default: () => [],
},
},
render(h, { props, parent: { $page, $route } }) {
return h("div", { attrs: { class: "anchor-place-holder" } }, [
h("aside", { attrs: { id: "anchor" } }, [
($page.headers && $page.headers.length)
? h("div", { class: "anchor-header" }, [
"On this page"
])
: null,
h("div", { class: "anchor-wrapper" }, [
props.items.length
? renderChildren(h, {
children: props.items,
route: $route,
})
: $page.headers
? renderChildren(h, {
children: $page.headers,
route: $route,
})
: null,
]),
($page.headers && $page.headers.length)
? h("div", [
h("div", { class: "anchor-header anchor-support" }, [
"Support"
]),
h("div", { class: "anchor-support-links" }, [
h("a", { attrs: { href: "https://discord.optimism.io", target: "_blank" } }, [
h("div", [
h("i", { attrs: { class: "fab fa-discord" } }),
" Discord community"
])
]),
h("a", { attrs: { href: "https://optimismpbc.typeform.com/get-in-touch", target: "_blank" } }, [
h("div", [
h("i", { attrs: { class: "far fa-comment-dots" } }),
" Get support for going live"
])
]),
h("a", { attrs: { href: "https://github.com/ethereum-optimism/optimism/issues", target: "_blank" } }, [
h("div", [
h("i", { attrs: { class: "fab fa-github" } }),
" Make an issue on GitHub"
])
]),
h("a", { attrs: { href: "https://github.com/ethereum-optimism/optimism/contribute", target: "_blank" } }, [
h("div", [
h("i", { attrs: { class: "far fa-hands-helping" } }),
" Contribute to Optimism"
])
]),
])
])
: null
]),
]);
},
});
//# sourceMappingURL=Anchor.js.map
\ No newline at end of file
{"version":3,"file":"Anchor.js","sourceRoot":"","sources":["Anchor.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AAEtB,OAAO,EAAE,QAAQ,EAAE,MAAM,mBAAmB,CAAC;AAW7C,MAAM,UAAU,GAAG,CACjB,CAAgB,EAChB,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAc,EAC1B,EAAE,CACT,CAAC,CACC,YAAY,EACZ;IACE,KAAK,EAAE;QACL,EAAE,EAAE,IAAI;QACR,WAAW,EAAE,EAAE;QACf,gBAAgB,EAAE,EAAE;KACrB;IACD,KAAK,EAAE;QACL,aAAa,EAAE,IAAI;QACnB,CAAC,KAAK,CAAC,CAAC,CAAC,UAAU,KAAK,EAAE,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,KAAK;KACxC;CACF,EACD,CAAC,CAAC,CAAC,KAAK,EAAE,EAAE,EAAE,CAAC,IAAI,CAAC,CAAC,CAAC,CACvB,CAAC;AAOJ,MAAM,cAAc,GAAG,CACrB,CAAgB,EAChB,EAAE,QAAQ,EAAE,KAAK,EAAyB,EACnC,EAAE,CACT,CAAC,CACC,IAAI,EACJ,EAAE,KAAK,EAAE,aAAa,EAAE,EACxB,QAAQ,CAAC,GAAG,CAAC,CAAC,KAAoB,EAAE,EAAE;IACpC,MAAM,MAAM,GAAG,QAAQ,CAAC,KAAK,EAAE,GAAG,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC;IAE9D,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE,KAAK,EAAE,EAAE,MAAM,EAAE,IAAI,EAAE,MAAM,EAAE,EAAE,EAAE;QAClD,UAAU,CAAC,CAAC,EAAE;YACZ,IAAI,EAAE,KAAK,CAAC,KAAK;YACjB,IAAI,EAAE,GAAG,KAAK,CAAC,IAAI,IAAI,KAAK,CAAC,IAAI,EAAE;YACnC,KAAK,EAAE,KAAK,CAAC,KAAK;SACnB,CAAC;KACH,CAAC,CAAC;AACL,CAAC,CAAC,CACH,CAAC;AAEJ,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,QAAQ;IAEd,UAAU,EAAE,IAAI;IAEhB,KAAK,EAAE;QACL,KAAK,EAAE;YACL,IAAI,EAAE,KAAkC;YACxC,OAAO,EAAE,GAAG,EAAE,CAAC,EAAE;SAClB;KACF;IAED,MAAM,CAAC,CAAC,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,EAAE,KAAK,EAAE,MAAM,EAAE,EAAE;QAC5C,OAAO,CAAC,CAAC,KAAK,EAAE,EAAE,KAAK,EAAE,EAAE,KAAK,EAAE,qBAAqB,EAAE,EAAE,EAAE;YAC3D,CAAC,CAAC,OAAO,EAAE,EAAE,KAAK,EAAE,EAAE,EAAE,EAAE,QAAQ,EAAE,EAAE,EAAE;gBACtC,CAAC,CAAC,KAAK,EAAE,EAAE,KAAK,EAAE,gBAAgB,EAAE,EAAE;oBACpC,KAAK,CAAC,KAAK,CAAC,MAAM;wBAChB,CAAC,CAAC,cAAc,CAAC,CAAC,EAAE;4BAChB,QAAQ,EAAE,KAAK,CAAC,KAAK;4BACrB,KAAK,EAAE,MAAM;yBACd,CAAC;wBACJ,CAAC,CAAC,KAAK,CAAC,OAAO;4BACf,CAAC,CAAC,cAAc,CAAC,CAAC,EAAE;gCAChB,QAAQ,EAAE,KAAK,CAAC,OAAO;gCACvB,KAAK,EAAE,MAAM;6BACd,CAAC;4BACJ,CAAC,CAAC,IAAI;iBACT,CAAC;aACH,CAAC;SACH,CAAC,CAAC;IACL,CAAC;CACF,CAAC,CAAC"}
\ No newline at end of file
<script src="./Anchor" />
<style lang="stylus">
$headings = 2 3 4 5 6
.anchor-place-holder
position sticky
top: ($navbarHeight + 2rem)
max-width $contentWidth
margin 0 auto
padding 0 2.5rem
z-index 99
@media (max-width $MQNarrow)
padding 0 1.5rem
& + .theme-default-content:not(.custom)
padding-top 0
#anchor
display none
position absolute
left calc(100% + 0.5rem)
min-width 10rem
max-width 15rem
max-height 85vh
overflow-y scroll
@media (min-width $MQWide)
.has-anchor &
display block
&::-webkit-scrollbar-track-piece
background transparent
&::-webkit-scrollbar
width 3px
&::-webkit-scrollbar-thumb:vertical
background #ddd
.theme-dark &
background #333
.anchor-wrapper
position relative
padding-left 8px
&::before
content ' '
position absolute
top 0
left 0px
bottom 0
width 2px
background var(--border-color)
z-index -1
> .anchor-list
margin 0
.anchor-list
padding-left 0
.anchor
position relative
box-sizing border-box
padding 1px 8px
list-style none
line-height 1.5
&::before
content ' '
position absolute
z-index 2
top 0
bottom 0
left -8px
width 2px
background transparent
&:hover
.anchor-link
color var(--accent-color)
&.active
.anchor-link
color var(--accent-color)
&::before
background var(--accent-color)
.anchor-link
display inline-block
vertical-align middle
position relative
max-width 100%
color var(--light-grey)
> div
text-overflow ellipsis
white-space nowrap
overflow hidden
for $heading in $headings
&.heading{$heading}
padding-left ($heading * 8 - 16) px
font-size: (16 - $heading)px
</style>
import Vue from "vue";
import type { PageComputed } from "@mr-hope/vuepress-types";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, unknown, {
author: string;
time: string;
tags: string[];
readingTimeContent: string;
readingTime: string;
authorText: string;
timeText: string;
tagText: string;
readingTimeText: string;
}, {
article: PageComputed;
}>;
export default _default;
import Vue from "vue";
import { capitalize } from "@mr-hope/vuepress-shared";
import AuthorIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/AuthorIcon.vue";
import CalendarIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/CalendarIcon.vue";
import CategoryInfo from "@mr-hope/vuepress-plugin-comment/lib/client/CategoryInfo.vue";
import TagInfo from "@mr-hope/vuepress-plugin-comment/lib/client/TagInfo.vue";
import TimerIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/TimerIcon.vue";
export default Vue.extend({
name: "ArticleInfo",
components: {
AuthorIcon,
CalendarIcon,
CategoryInfo,
TagInfo,
TimerIcon,
},
props: {
article: { type: Object, required: true },
},
computed: {
author() {
return (this.article.frontmatter.author ||
(this.$themeConfig.author && this.article.frontmatter.author !== false
? this.$themeConfig.author
: ""));
},
time() {
const { date, time = date } = this.article.frontmatter;
if (typeof time === "string") {
if (time.indexOf("T") !== -1) {
const [dateString, temp] = time.split("T");
const [times] = temp.split(".");
return `${dateString} ${times === "00:00:00" ? "" : times}`;
}
return time;
}
return this.article.createTime || "";
},
tags() {
const { tag, tags = tag } = this.article.frontmatter;
if (typeof tags === "string")
return [capitalize(tags)];
if (Array.isArray(tags))
return tags.map((item) => capitalize(item));
return [];
},
readingTimeContent() {
return `PT${Math.max(Math.round(this.$page.readingTime.minutes), 1)}M`;
},
readingTime() {
const { minute, time } = READING_TIME_I18N[this.$localePath || "/"];
return this.article.readingTime.minutes < 1
? minute
: time.replace("$time", Math.round(this.article.readingTime.minutes).toString());
},
authorText() {
return PAGE_INFO_I18N[this.$localePath || "/"].author;
},
timeText() {
return PAGE_INFO_I18N[this.$localePath || "/"].time;
},
tagText() {
return PAGE_INFO_I18N[this.$localePath || "/"].tag;
},
readingTimeText() {
return PAGE_INFO_I18N[this.$localePath || "/"].readingTime;
},
},
});
//# sourceMappingURL=ArticleInfo.js.map
\ No newline at end of file
{"version":3,"file":"ArticleInfo.js","sourceRoot":"","sources":["ArticleInfo.ts"],"names":[],"mappings":"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"}
\ No newline at end of file
<template>
<div v-if="author || time" class="article-info">
<!-- Author -->
<span v-if="author" :aria-label="authorText" data-balloon-pos="down">
<AuthorIcon />
<span property="author" v-text="author" />
</span>
<!-- Writing Date -->
<span
v-if="time"
class="time"
:aria-label="timeText"
data-balloon-pos="down"
>
<CalendarIcon />
<span property="datePublished" v-text="time" />
</span>
<CategoryInfo
v-if="article.frontmatter.category"
:category="article.frontmatter.category"
/>
<TagInfo v-if="tags.length !== 0" :tags="tags" />
<!-- Reading time -->
<span
v-if="readingTime"
class="read-time-info"
:aria-label="readingTimeText"
data-balloon-pos="down"
>
<TimerIcon />
<span v-text="readingTime" />
<meta property="timeRequired" :content="readingTimeContent" />
</span>
</div>
</template>
<script src="./ArticleInfo" />
<style lang="stylus">
$articleInfoTextSize ?= 14px
.article-info
color var(--dark-grey)
font-size $articleInfoTextSize
font-family Arial, Helvetica, sans-serif
& > span
display inline-block
margin-right 0.5em
line-height 1.8
@media (max-width $MQMobileNarrow)
margin-right 0.3em
font-size 0.86rem
&::after
--balloon-font-size 8px
padding 0.3em 0.6em !important
svg
position relative
bottom -0.125em
.tags-wrapper
display inline-block
.icon
width 1em
height 1em
</style>
import Vue from "vue";
import type { PageComputed } from "@mr-hope/vuepress-types";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, unknown, {
isEncrypted: boolean;
excerpt: string;
}, {
article: PageComputed;
}>;
export default _default;
import Vue from "vue";
import ArticleInfo from "@theme/components/Blog/ArticleInfo.vue";
import LockIcon from "@theme/icons/LockIcon.vue";
import PresentationIcon from "@theme/icons/PresentationIcon.vue";
import StickyIcon from "@theme/icons/StickyIcon.vue";
import { getPathMatchedKeys } from "@theme/utils/encrypt";
export default Vue.extend({
name: "ArticleItem",
components: { ArticleInfo, LockIcon, StickyIcon, PresentationIcon },
props: {
article: { type: Object, required: true },
},
computed: {
isEncrypted() {
return (getPathMatchedKeys(this.$themeConfig.encrypt, this.article.path)
.length !== 0 || Boolean(this.article.frontmatter.password));
},
excerpt() {
if (this.article.excerpt)
return this.article.excerpt;
return (this.article.frontmatter.description ||
this.article.frontmatter.summary ||
"");
},
},
});
//# sourceMappingURL=ArticleItem.js.map
\ No newline at end of file
{"version":3,"file":"ArticleItem.js","sourceRoot":"","sources":["ArticleItem.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,QAAQ,MAAM,2BAA2B,CAAC;AACjD,OAAO,gBAAgB,MAAM,mCAAmC,CAAC;AACjE,OAAO,UAAU,MAAM,6BAA6B,CAAC;AACrD,OAAO,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAK1D,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,aAAa;IAEnB,UAAU,EAAE,EAAE,WAAW,EAAE,QAAQ,EAAE,UAAU,EAAE,gBAAgB,EAAE;IAEnE,KAAK,EAAE;QACL,OAAO,EAAE,EAAE,IAAI,EAAE,MAAgC,EAAE,QAAQ,EAAE,IAAI,EAAE;KACpE;IAED,QAAQ,EAAE;QACR,WAAW;YACT,OAAO,CACL,kBAAkB,CAAC,IAAI,CAAC,YAAY,CAAC,OAAO,EAAE,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC;iBAC7D,MAAM,KAAK,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,OAAO,CAAC,WAAW,CAAC,QAAQ,CAAC,CAC9D,CAAC;QACJ,CAAC;QAED,OAAO;YACL,IAAI,IAAI,CAAC,OAAO,CAAC,OAAO;gBAAE,OAAO,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC;YAEtD,OAAO,CACL,IAAI,CAAC,OAAO,CAAC,WAAW,CAAC,WAAW;gBACpC,IAAI,CAAC,OAAO,CAAC,WAAW,CAAC,OAAO;gBAChC,EAAE,CACH,CAAC;QACJ,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<article class="article" vocab="https://schema.org/" typeof="Article">
<StickyIcon v-if="article.frontmatter.sticky" />
<header class="title" @click="$router.push(article.path)">
<LockIcon v-if="isEncrypted" />
<PresentationIcon v-if="article.frontmatter.layout === 'Slide'" />
<span property="headline">{{ article.title }}</span>
<meta
v-if="article.frontmatter.image"
property="image"
:content="$withBase(article.frontmatter.image)"
/>
</header>
<!-- eslint-disable-next-line vue/no-v-html -->
<div v-if="excerpt" class="excerpt" v-html="excerpt" />
<hr class="hr" />
<ArticleInfo :article="article" />
</article>
</template>
<script src="./ArticleItem" />
<style lang="stylus">
.article
position relative
box-sizing border-box
width 100%
margin 0 auto 20px
padding 16px 20px
background var(--bgcolor)
border-radius 6px
text-align left
box-shadow 0 1px 3px 0 var(--card-shadow-color)
@media (max-width $MQMobileNarrow)
border-radius 0
&:last-child
margin-bottom 0
&:hover
box-shadow 0 2px 6px 0 var(--card-shadow-color)
.sticky-icon
position absolute
top 0
right 0
width 40px
height 40px
fill var(--accent-color)
.sticky-text
fill var(--white)
.title
display inline-block
position relative
font-size 1.28rem
line-height 36px
&::after
content ''
position absolute
width 100%
height 2px
bottom 0
left 0
background var(--accent-color)
visibility hidden
transform scaleX(0)
transition transform 0.3s ease-in-out
&:hover
cursor pointer
&::after
visibility visible
transform scaleX(1)
.lock-icon, .presentation-icon
position relative
bottom -0.125em
display inline-block
vertical-align baseline
width 20px
height 20px
color var(--accent-color)
.excerpt
overflow hidden
line-height 1.7
h1
display none
& + p
margin-top 0.5em
p
&:first-child
margin-top 0.5em
&:last-child
margin-bottom 0.5em
// code block fix
pre
line-height 1.4
padding 1.25rem 1.5rem
margin 0.85rem 0
// line number fix
.line-numbers-mode
pre
padding-left ($lineNumbersWrapperWidth + 1) rem
// hide code demo
.code-demo-wrapper
display none
</style>
import Vue from "vue";
import type { BlogOptions } from "@theme/types";
import type { PageComputed } from "@mr-hope/vuepress-types";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, {
currentPage: number;
articleList: PageComputed[];
}, {
getArticleList(): PageComputed[];
}, {
blogConfig: BlogOptions;
articlePerPage: number;
filter: ((page: PageComputed) => boolean) | undefined;
$articles: PageComputed[];
articles: PageComputed[];
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import ArticleItem from "@theme/components/Blog/ArticleItem.vue";
import EmptyIcon from "@theme/icons/EmptyIcon.vue";
import MyTransition from "@theme/components/MyTransition.vue";
import { filterArticle, sortArticle } from "@theme/utils/article";
import { getPathMatchedKeys } from "@theme/utils/encrypt";
export default Vue.extend({
name: "ArticleList",
components: { ArticleItem, EmptyIcon, MyTransition },
data: () => ({
currentPage: 1,
articleList: [],
}),
computed: {
blogConfig() {
return this.$themeConfig.blog || {};
},
articlePerPage() {
return this.blogConfig.perPage || 10;
},
filter() {
const { path } = this.$route;
return path.includes("/article")
? (page) => page.frontmatter.layout !== "Slide"
: path.includes("/star")
? (page) => Boolean(page.frontmatter.star || page.frontmatter.sticky)
: path.includes("/encrypt")
? (page) => getPathMatchedKeys(this.$themeConfig.encrypt, page.path).length !==
0 || Boolean(page.frontmatter.password)
: path.includes("/slide")
? (page) => page.frontmatter.layout === "Slide"
: undefined;
},
$articles() {
// filter then sort
return sortArticle(filterArticle(this.$site.pages, this.filter), "sticky");
},
/** Articles in this page */
articles() {
return this.articleList.slice((this.currentPage - 1) * this.articlePerPage, this.currentPage * this.articlePerPage);
},
},
watch: {
// update article list when route is changed
$route(to, from) {
if (to.path !== from.path) {
this.articleList = this.getArticleList();
// reset page to 1
this.currentPage = 1;
}
},
currentPage() {
// list top border distance
const distance = document.querySelector("#article-list").getBoundingClientRect().top + window.scrollY;
setTimeout(() => {
window.scrollTo(0, distance);
}, 100);
},
},
mounted() {
this.articleList = this.getArticleList();
},
methods: {
getArticleList() {
try {
return this.$pagination
? // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
this.$pagination._matchedPages
: this.$articles;
}
catch (err) {
return this.$articles;
}
},
},
});
//# sourceMappingURL=ArticleList.js.map
\ No newline at end of file
{"version":3,"file":"ArticleList.js","sourceRoot":"","sources":["ArticleList.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,SAAS,MAAM,4BAA4B,CAAC;AACnD,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,EAAE,aAAa,EAAE,WAAW,EAAE,MAAM,sBAAsB,CAAC;AAClE,OAAO,EAAE,kBAAkB,EAAE,MAAM,sBAAsB,CAAC;AAM1D,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,aAAa;IAEnB,UAAU,EAAE,EAAE,WAAW,EAAE,SAAS,EAAE,YAAY,EAAE;IAEpD,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC;QACX,WAAW,EAAE,CAAC;QACd,WAAW,EAAE,EAAoB;KAClC,CAAC;IAEF,QAAQ,EAAE;QACR,UAAU;YACR,OAAO,IAAI,CAAC,YAAY,CAAC,IAAI,IAAI,EAAE,CAAC;QACtC,CAAC;QAED,cAAc;YACZ,OAAO,IAAI,CAAC,UAAU,CAAC,OAAO,IAAI,EAAE,CAAC;QACvC,CAAC;QAED,MAAM;YACJ,MAAM,EAAE,IAAI,EAAE,GAAG,IAAI,CAAC,MAAM,CAAC;YAE7B,OAAO,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC;gBAC9B,CAAC,CAAC,CAAC,IAAkB,EAAW,EAAE,CAAC,IAAI,CAAC,WAAW,CAAC,MAAM,KAAK,OAAO;gBACtE,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,OAAO,CAAC;oBACxB,CAAC,CAAC,CAAC,IAAkB,EAAW,EAAE,CAC9B,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,IAAI,IAAI,IAAI,CAAC,WAAW,CAAC,MAAM,CAAC;oBAC7D,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,UAAU,CAAC;wBAC3B,CAAC,CAAC,CAAC,IAAkB,EAAW,EAAE,CAC9B,kBAAkB,CAAC,IAAI,CAAC,YAAY,CAAC,OAAO,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC,MAAM;4BAC7D,CAAC,IAAI,OAAO,CAAC,IAAI,CAAC,WAAW,CAAC,QAAQ,CAAC;wBAC7C,CAAC,CAAC,IAAI,CAAC,QAAQ,CAAC,QAAQ,CAAC;4BACzB,CAAC,CAAC,CAAC,IAAkB,EAAW,EAAE,CAAC,IAAI,CAAC,WAAW,CAAC,MAAM,KAAK,OAAO;4BACtE,CAAC,CAAC,SAAS,CAAC;QAChB,CAAC;QAED,SAAS;YACP,mBAAmB;YACnB,OAAO,WAAW,CAChB,aAAa,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,EAAE,IAAI,CAAC,MAAM,CAAC,EAC5C,QAAQ,CACT,CAAC;QACJ,CAAC;QAED,4BAA4B;QAC5B,QAAQ;YACN,OAAO,IAAI,CAAC,WAAW,CAAC,KAAK,CAC3B,CAAC,IAAI,CAAC,WAAW,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,cAAc,EAC5C,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,cAAc,CACvC,CAAC;QACJ,CAAC;KACF;IAED,KAAK,EAAE;QACL,4CAA4C;QAC5C,MAAM,CAAC,EAAS,EAAE,IAAW;YAC3B,IAAI,EAAE,CAAC,IAAI,KAAK,IAAI,CAAC,IAAI,EAAE;gBACzB,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,cAAc,EAAE,CAAC;gBACzC,kBAAkB;gBAClB,IAAI,CAAC,WAAW,GAAG,CAAC,CAAC;aACtB;QACH,CAAC;QAED,WAAW;YACT,2BAA2B;YAC3B,MAAM,QAAQ,GAEV,QAAQ,CAAC,aAAa,CAAC,eAAe,CACvC,CAAC,qBAAqB,EAAE,CAAC,GAAG,GAAG,MAAM,CAAC,OAAO,CAAC;YAEjD,UAAU,CAAC,GAAG,EAAE;gBACd,MAAM,CAAC,QAAQ,CAAC,CAAC,EAAE,QAAQ,CAAC,CAAC;YAC/B,CAAC,EAAE,GAAG,CAAC,CAAC;QACV,CAAC;KACF;IAED,OAAO;QACL,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,cAAc,EAAE,CAAC;IAC3C,CAAC;IAED,OAAO,EAAE;QACP,cAAc;YACZ,IAAI;gBACF,OAAO,IAAI,CAAC,WAAW;oBACrB,CAAC,CAAC,sEAAsE;wBACrE,IAAI,CAAC,WAAW,CAAC,aAAgC;oBACpD,CAAC,CAAC,IAAI,CAAC,SAAS,CAAC;aACpB;YAAC,OAAO,GAAG,EAAE;gBACZ,OAAO,IAAI,CAAC,SAAS,CAAC;aACvB;QACH,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div id="article-list" class="article-wrapper">
<EmptyIcon v-if="!articles.length" class="empty" />
<MyTransition
v-for="(article, index) in articles"
:key="article.path"
:delay="index * 0.04"
>
<ArticleItem :article="article" />
</MyTransition>
<Pagination
v-model="currentPage"
:per-page="articlePerPage"
:total="articleList.length"
/>
</div>
</template>
<script src="./ArticleList" />
<style lang="stylus">
.article-wrapper
margin-top -0.5rem - $navbarHeight
padding-top: $navbarHeight + 0.5rem
text-align center
@media (max-width $MQMobile)
margin-top -0.5rem - $navbarMobileHeight
padding-top: $navbarMobileHeight + 0.5rem
.empty
max-width 560px
margin 0 auto
text-align center
</style>
import Vue from "vue";
interface ArticleTypeItem {
text: string;
path: string;
}
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
navigate(path: string): void;
}, {
types: ArticleTypeItem[];
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
import { navigate } from "@theme/utils/navigate";
export default Vue.extend({
name: "ArticleType",
computed: {
types() {
const blogI18n = this.$themeLocaleConfig.blog || getDefaultLocale().blog;
return [
{ text: blogI18n.allText, path: "/article/" },
{ text: blogI18n.star, path: "/star/" },
{ text: blogI18n.slides, path: "/slide/" },
{ text: blogI18n.encrypt, path: "/encrypt/" },
];
},
},
methods: {
navigate(path) {
navigate(path, this.$router, this.$route);
},
},
});
//# sourceMappingURL=ArticleType.js.map
\ No newline at end of file
{"version":3,"file":"ArticleType.js","sourceRoot":"","sources":["ArticleType.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAOjD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,aAAa;IAEnB,QAAQ,EAAE;QACR,KAAK;YACH,MAAM,QAAQ,GAAG,IAAI,CAAC,kBAAkB,CAAC,IAAI,IAAI,gBAAgB,EAAE,CAAC,IAAI,CAAC;YAEzE,OAAO;gBACL,EAAE,IAAI,EAAE,QAAQ,CAAC,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE;gBAC7C,EAAE,IAAI,EAAE,QAAQ,CAAC,IAAI,EAAE,IAAI,EAAE,QAAQ,EAAE;gBACvC,EAAE,IAAI,EAAE,QAAQ,CAAC,MAAM,EAAE,IAAI,EAAE,SAAS,EAAE;gBAC1C,EAAE,IAAI,EAAE,QAAQ,CAAC,OAAO,EAAE,IAAI,EAAE,WAAW,EAAE;aAC9C,CAAC;QACJ,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,IAAY;YACnB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5C,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<ul class="article-type-wrapper">
<li
v-for="type in types"
:key="type.text"
class="article-type"
:class="{ active: type.path === $route.path }"
role="navigation"
@click="navigate(type.path)"
>
<span>{{ type.text }}</span>
</li>
</ul>
</template>
<script src="./ArticleType" />
<style lang="stylus">
.article-type-wrapper
position relative
padding-left 0
font-size 18px
font-family Arial, Helvetica, sans-serif
font-weight 600
display flex
justify-content center
align-items center
list-style none
z-index 2
@media (max-width $MQMobileNarrow)
font-size 16px
.article-type
position relative
vertical-align middle
margin 0.3em 0.8em
line-height 1.2
cursor pointer
&::after
position absolute
content ' '
left 50%
right 50%
bottom -6px
height 2px
background var(--accent-color)
border-radius 1px
visibility hidden
transition left 0.2s ease-in-out, right 0.2s ease-in-out
span
transition all 0.3s ease-in-out
&.active
position relative
span
display inline-block
color var(--accent-color)
transform scale(1.1, 1.1)
&:hover, &.active
&::after
left calc(50% - 8px)
right calc(50% - 8px)
visibility visible
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, {
defaultHeroImage: string;
}, unknown, {
heroImageStyle: Record<string, string>;
bgImageStyle: Record<string, string>;
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import MyTransition from "@theme/components/MyTransition.vue";
import defaultHeroImage from "@theme/assets/hero.jpg";
export default Vue.extend({
name: "BlogHero",
components: { MyTransition },
data: () => ({ defaultHeroImage }),
computed: {
heroImageStyle() {
const defaultStyle = {
maxHeight: "180px",
margin: this.$frontmatter.showTitle === false
? "6rem auto 1.5rem"
: "1rem auto",
};
return Object.assign(Object.assign({}, defaultStyle), this.$frontmatter.heroImageStyle);
},
bgImageStyle() {
const defaultBgImageStyle = {
height: "350px",
textAlign: "center",
overflow: "hidden",
};
const { bgImageStyle = {} } = this.$frontmatter;
return Object.assign(Object.assign({}, defaultBgImageStyle), bgImageStyle);
},
},
});
//# sourceMappingURL=BlogHero.js.map
\ No newline at end of file
{"version":3,"file":"BlogHero.js","sourceRoot":"","sources":["BlogHero.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,gBAAgB,MAAM,wBAAwB,CAAC;AAEtD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE,EAAE,YAAY,EAAE;IAE5B,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC,EAAE,gBAAgB,EAAE,CAAC;IAElC,QAAQ,EAAE;QACR,cAAc;YACZ,MAAM,YAAY,GAAG;gBACnB,SAAS,EAAE,OAAO;gBAClB,MAAM,EACJ,IAAI,CAAC,YAAY,CAAC,SAAS,KAAK,KAAK;oBACnC,CAAC,CAAC,kBAAkB;oBACpB,CAAC,CAAC,WAAW;aAClB,CAAC;YAEF,uCACK,YAAY,GACX,IAAI,CAAC,YAAY,CAAC,cAAyC,EAC/D;QACJ,CAAC;QAED,YAAY;YACV,MAAM,mBAAmB,GAA2B;gBAClD,MAAM,EAAE,OAAO;gBACf,SAAS,EAAE,QAAQ;gBACnB,QAAQ,EAAE,QAAQ;aACnB,CAAC;YACF,MAAM,EAAE,YAAY,GAAG,EAAE,EAAE,GAAG,IAAI,CAAC,YAAY,CAAC;YAEhD,uCACK,mBAAmB,GAClB,YAAuC,EAC3C;QACJ,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div
v-if="$frontmatter.hero !== false"
class="blog-hero"
:class="{ full: $frontmatter.heroFullScreen }"
:style="{ ...bgImageStyle }"
>
<div
class="mask"
:style="{
background: `url(${
$frontmatter.bgImage
? $withBase($frontmatter.bgImage)
: defaultHeroImage
}) center/cover no-repeat`,
}"
/>
<MyTransition :delay="0.04">
<img
v-if="$frontmatter.heroImage"
class="hero-logo"
:style="heroImageStyle || {}"
:src="$withBase($frontmatter.heroImage)"
alt="hero"
/>
</MyTransition>
<MyTransition :delay="0.08">
<h1 v-if="$frontmatter.showTitle !== false">
{{ $frontmatter.heroText || $title || "Hope" }}
</h1>
</MyTransition>
<MyTransition :delay="0.12">
<p v-if="$description" class="description" v-text="$description" />
</MyTransition>
</div>
</template>
<script src="./BlogHero" />
<style lang="stylus">
.blog-hero
position relative
color #eee
margin-bottom 16px
height 450px
display flex
flex-direction column
justify-content center
@media (max-width $MQMobile)
height 350px
margin 0 -1.5rem 16px
@media (max-width $MQMobileNarrow)
margin 0 0 16px
&.full
height 'calc(100vh - %s)' % $navbarHeight !important
@media (max-width $MQMobile)
height 'calc(100vh - %s)' % $navbarMobileHeight !important
.mask
background-position-y top !important
.mask
position absolute
top 0
bottom 0
left 0
right 0
&:after
display block
content ' '
background var(--light-grey)
position absolute
top 0
bottom 0
left 0
right 0
z-index 1
opacity 0.2
& > :not(.mask)
position relative
z-index 2
h1
margin 0.5rem auto
font-size 36px
@media (max-width $MQNarrow)
font-size 30px
@media (max-width $MQMobile)
font-size 36px
@media (max-width $MQMobileNarrow)
font-size 30px
.hero-logo + h1
margin 0 auto
.description
margin 1.2rem auto 0
font-size 20px
@media (max-width $MQNarrow)
font-size 18px
@media (max-width $MQMobile)
font-size 20px
@media (max-width $MQMobileNarrow)
font-size 18px
</style>
import Vue from "vue";
/**
* 项目配置
*
* Project Configuration
*/
export interface ProjectOptions {
/**
* 项目类型
*
* Type of project
*/
type: "article" | "book" | "link" | "project";
/**
* 项目名称
*
* Project name
*/
name: string;
/**
* 项目描述
*
* Project desription
*/
desc?: string;
/**
* 项目封面,应为绝对路径
*
* Cover for the project, must be an absolute path
*/
cover?: string;
/**
* 项目链接
*
* Link of the project
*/
link: string;
}
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, unknown, unknown, Record<never, any>>;
export default _default;
import Vue from "vue";
import ArticleList from "@theme/components/Blog/ArticleList.vue";
import BlogHero from "@theme/components/Blog/BlogHero.vue";
import BlogInfo from "@BlogInfo";
import MyTransition from "@theme/components/MyTransition.vue";
import ProjectList from "@theme/components/Blog/ProjectList.vue";
export default Vue.extend({
name: "BlogHome",
components: {
ArticleList,
BlogHero,
BlogInfo,
MyTransition,
ProjectList,
},
});
//# sourceMappingURL=BlogHome.js.map
\ No newline at end of file
{"version":3,"file":"BlogHome.js","sourceRoot":"","sources":["BlogHome.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,QAAQ,MAAM,qCAAqC,CAAC;AAC3D,OAAO,QAAQ,MAAM,WAAW,CAAC;AACjC,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,WAAW,MAAM,wCAAwC,CAAC;AAwCjE,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE;QACV,WAAW;QACX,QAAQ;QACR,QAAQ;QACR,YAAY;QACZ,WAAW;KACZ;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="page blog">
<BlogHero />
<div class="blog-page-wrapper">
<main class="blog-home">
<MyTransition :delay="0.16">
<ProjectList />
</MyTransition>
<MyTransition :delay="0.24">
<ArticleList :key="$route.path" />
</MyTransition>
</main>
<MyTransition :delay="0.16">
<BlogInfo />
</MyTransition>
</div>
<MyTransition :delay="0.28">
<Content :key="$route.path" class="theme-default-content" custom />
</MyTransition>
</div>
</template>
<script src="./BlogHome" />
<style lang="stylus">
.page.blog
box-sizing content-box
min-height 100vh
padding-top $navbarHeight
padding-bottom 2rem
margin 0px auto
background var(--bgcolor-light)
@media (max-width $MQMobile)
padding $navbarMobileHeight 1.5rem 2rem
@media (max-width $MQMobileNarrow)
padding-left 0
padding-right 0
.blog-page-wrapper
display flex
justify-content center
align-items flex-start
margin 0 auto
@media (min-width $MQMobile)
padding 0 1rem
@media (min-width $MQNarrow)
padding 0 2rem
@media (min-width $MQWide)
padding 0
.blog-home
max-width 780px
overflow hidden
flex 1
@media (min-width $MQMobile)
margin 0 15px
.theme-default-content:empty
padding 0
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, unknown, unknown, Record<never, any>>;
export default _default;
import Vue from "vue";
import BlogInfoList from "@theme/components/Blog/BlogInfoList.vue";
import BloggerInfo from "@theme/components/Blog/BloggerInfo.vue";
import MyTransition from "@theme/components/MyTransition.vue";
export default Vue.extend({
name: "BlogInfo",
components: { BlogInfoList, BloggerInfo, MyTransition },
});
//# sourceMappingURL=BlogInfo.js.map
\ No newline at end of file
{"version":3,"file":"BlogInfo.js","sourceRoot":"","sources":["BlogInfo.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,YAAY,MAAM,yCAAyC,CAAC;AACnE,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAE9D,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE,EAAE,YAAY,EAAE,WAAW,EAAE,YAAY,EAAE;CACxD,CAAC,CAAC"}
\ No newline at end of file
<template>
<aside class="blog-info-wrapper">
<MyTransition>
<BloggerInfo />
</MyTransition>
<MyTransition :delay="0.04">
<BlogInfoList />
</MyTransition>
</aside>
</template>
<script src="./BlogInfo" />
<style lang="stylus">
.blog-info-wrapper
.sidebar &
.blogger-info
display none
.page &
position sticky
box-sizing border-box
top ($navbarHeight + 1rem)
flex 0 0 300px
height auto
margin-bottom 12px
transition all 0.3s
@media (max-width $MQMobile)
display none
.blogger-info
margin-bottom 16px
padding 8px 0
border-radius 8px
box-shadow 0 1px 3px 0 var(--card-shadow-color)
&:hover
box-shadow 0 2px 6px 0 var(--card-shadow-color)
</style>
import ArticleIcon from "@theme/icons/ArticleIcon.vue";
declare const _default: import("vue/types/vue").ExtendedVue<{
$starArticles: import("@mr-hope/vuepress-types").PageComputed[];
} & Record<never, any> & ArticleIcon, {
active: string;
}, {
setActive(name: string): void;
navigate(path: string): void;
}, {
i18n: {
article: string;
articleList: string;
category: string;
tag: string;
timeline: string;
timelineText: string;
allText: string;
intro: string;
star: string;
slides: string;
encrypt: string;
};
articleNumber: number;
}, Record<never, any>>;
export default _default;
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
import ArticleIcon from "@theme/icons/ArticleIcon.vue";
import CategoryIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/CategoryIcon.vue";
import TagIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/TagIcon.vue";
import TimeIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/TimeIcon.vue";
import ArticleList from "@theme/components/Blog/ArticleList.vue";
import CategoryList from "@theme/components/Blog/CategoryList.vue";
import MyTransition from "@theme/components/MyTransition.vue";
import TagList from "@theme/components/Blog/TagList.vue";
import Timeline from "@theme/components/Blog/Timeline.vue";
import TimelineList from "@theme/components/Blog/TimelineList.vue";
import { filterArticle } from "@theme/utils/article";
import { starMixin } from "@theme/mixins/star";
export default starMixin.extend({
name: "BlogInfo",
components: {
ArticleIcon,
ArticleList,
CategoryIcon,
CategoryList,
MyTransition,
TagIcon,
TagList,
TimeIcon,
Timeline,
TimelineList,
},
data: () => ({
active: "category",
}),
computed: {
i18n() {
return this.$themeLocaleConfig.blog || getDefaultLocale().blog;
},
articleNumber() {
return filterArticle(this.$site.pages).length;
},
},
methods: {
setActive(name) {
this.active = name;
},
navigate(path) {
if (this.$route.path !== path)
void this.$router.push(path);
},
},
});
//# sourceMappingURL=BlogInfoList.js.map
\ No newline at end of file
{"version":3,"file":"BlogInfoList.js","sourceRoot":"","sources":["BlogInfoList.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,WAAW,MAAM,8BAA8B,CAAC;AACvD,OAAO,YAAY,MAAM,oEAAoE,CAAC;AAC9F,OAAO,OAAO,MAAM,+DAA+D,CAAC;AACpF,OAAO,QAAQ,MAAM,gEAAgE,CAAC;AACtF,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,YAAY,MAAM,yCAAyC,CAAC;AACnE,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,OAAO,MAAM,oCAAoC,CAAC;AACzD,OAAO,QAAQ,MAAM,qCAAqC,CAAC;AAC3D,OAAO,YAAY,MAAM,yCAAyC,CAAC;AACnE,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,SAAS,EAAE,MAAM,oBAAoB,CAAC;AAI/C,eAAe,SAAS,CAAC,MAAM,CAAC;IAC9B,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE;QACV,WAAW;QACX,WAAW;QACX,YAAY;QACZ,YAAY;QACZ,YAAY;QACZ,OAAO;QACP,OAAO;QACP,QAAQ;QACR,QAAQ;QACR,YAAY;KACb;IAED,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC;QACX,MAAM,EAAE,UAAU;KACnB,CAAC;IAEF,QAAQ,EAAE;QACR,IAAI;YACF,OAAO,IAAI,CAAC,kBAAkB,CAAC,IAAI,IAAI,gBAAgB,EAAE,CAAC,IAAI,CAAC;QACjE,CAAC;QAED,aAAa;YACX,OAAO,aAAa,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC;QAChD,CAAC;KACF;IAED,OAAO,EAAE;QACP,SAAS,CAAC,IAAY;YACpB,IAAI,CAAC,MAAM,GAAG,IAAI,CAAC;QACrB,CAAC;QAED,QAAQ,CAAC,IAAY;YACnB,IAAI,IAAI,CAAC,MAAM,CAAC,IAAI,KAAK,IAAI;gBAAE,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC9D,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="blog-info-list">
<div class="switch-wrapper">
<button class="switch-button" @click="setActive('article')">
<div
class="icon-wapper"
:class="{ active: active === 'article' }"
:aria-label="i18n.article"
data-balloon-pos="up"
>
<ArticleIcon />
</div>
</button>
<button class="switch-button" @click="setActive('category')">
<div
class="icon-wapper"
:class="{ active: active === 'category' }"
:aria-label="i18n.category"
data-balloon-pos="up"
>
<CategoryIcon />
</div>
</button>
<button class="switch-button" @click="setActive('tag')">
<div
class="icon-wapper"
:class="{ active: active === 'tag' }"
:aria-label="i18n.tag"
data-balloon-pos="up"
>
<TagIcon />
</div>
</button>
<button class="switch-button" @click="setActive('timeline')">
<div
class="icon-wapper"
:class="{ active: active === 'timeline' }"
:aria-label="i18n.timeline"
data-balloon-pos="up"
>
<TimeIcon />
</div>
</button>
</div>
<!-- Article -->
<MyTransition v-if="active === 'article'">
<div class="sticky-article-wrapper">
<div class="title" @click="navigate('/article/')">
<ArticleIcon />
<span class="num">{{ articleNumber }}</span>
{{ i18n.article }}
</div>
<hr />
<ul class="sticky-article-list">
<MyTransition
v-for="(article, index) in $starArticles"
:key="article.path"
:delay="(index + 1) * 0.08"
>
<li
class="sticky-article"
@click="navigate(article.path)"
v-text="article.title"
/>
</MyTransition>
</ul>
</div>
</MyTransition>
<!-- Category -->
<MyTransition v-if="active === 'category'">
<div class="category-wrapper">
<div
v-if="$category.list.length !== 0"
class="title"
@click="navigate('/category/')"
>
<CategoryIcon />
<span class="num">{{ $category.list.length }}</span>
{{ i18n.category }}
</div>
<hr />
<MyTransition :delay="0.04">
<CategoryList />
</MyTransition>
</div>
</MyTransition>
<!-- Tags -->
<MyTransition v-if="active === 'tag'">
<div class="tag-wrapper">
<div
v-if="$tag.list.length !== 0"
class="title"
@click="navigate('/tag/')"
>
<TagIcon />
<span class="num">{{ $tag.list.length }}</span>
{{ i18n.tag }}
</div>
<hr />
<MyTransition :delay="0.04">
<TagList />
</MyTransition>
</div>
</MyTransition>
<!-- Timeline -->
<MyTransition v-if="active === 'timeline'">
<TimelineList />
</MyTransition>
</div>
</template>
<script src="./BlogInfoList" />
<style lang="stylus">
@require '~@mr-hope/vuepress-shared/styles/reset'
.blog-info-list
margin 8px auto
padding 8px 16px
.page &
background var(--bgcolor)
border-radius 6px
box-shadow 0 1px 3px 0 var(--card-shadow-color)
&:hover
box-shadow 0 2px 6px 0 var(--card-shadow-color)
.switch-wrapper
display flex
justify-content center
margin-bottom 8px
.switch-button
button()
width 44px
height 44px
margin 0 8px
padding 4px
color var(--grey3)
&:focus
outline none
.icon-wapper
width 20px
height 20px
padding 8px
border-radius 50%
background rgba(127, 127, 127, 0.15)
.theme-dark &
background rgba(255, 255, 255, 0.15)
&:hover
cursor pointer
&.active
.theme-light &
background var(--accent-color-l10)
.theme-dark &
background var(--accent-color-d10)
.icon
width 100%
height 100%
.sticky-article-wrapper, .category-wrapper, .tag-wrapper
padding 8px 0
.title
cursor pointer
.icon
position relative
bottom -0.125rem
width 16px
height 16px
margin 0 6px
.num
position relative
margin 0 2px
font-size 22px
.sticky-article-wrapper
.sticky-article-list
margin 8px auto
.sticky-article
padding 12px 8px 4px
border-bottom 1px dashed var(--grey14)
&:hover
cursor pointer
color var(--accent-color)
.category-wrapper
.category-list-wrapper
margin 8px auto
.tag-wrapper
.tag-list-wrapper
margin 8px auto
.page &
.timeline-list-wrapper
.content
max-height 60vh
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, unknown, {
showArticles: boolean;
componentName: string;
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import ArticleList from "@theme/components/Blog/ArticleList.vue";
import ArticleType from "@theme/components/Blog/ArticleType.vue";
import BlogInfo from "@BlogInfo";
import CategoryList from "@theme/components/Blog/CategoryList.vue";
import MyTransition from "@theme/components/MyTransition.vue";
import TagList from "@theme/components/Blog/TagList.vue";
import Timeline from "@theme/components/Blog/Timeline.vue";
import TimelineList from "@theme/components/Blog/TimelineList.vue";
export default Vue.extend({
name: "BlogPage",
components: {
ArticleList,
ArticleType,
BlogInfo,
CategoryList,
MyTransition,
TagList,
Timeline,
TimelineList,
},
computed: {
showArticles() {
const { path } = this.$route;
return !path.includes("/timeline");
},
componentName() {
const pathName = this.$route.path.split("/")[1];
if (["category", "tag"].includes(pathName))
return `${pathName}List`;
else if (pathName === "timeline")
return pathName;
return "articleType";
},
},
});
//# sourceMappingURL=BlogPage.js.map
\ No newline at end of file
{"version":3,"file":"BlogPage.js","sourceRoot":"","sources":["BlogPage.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,WAAW,MAAM,wCAAwC,CAAC;AACjE,OAAO,QAAQ,MAAM,WAAW,CAAC;AACjC,OAAO,YAAY,MAAM,yCAAyC,CAAC;AACnE,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,OAAO,MAAM,oCAAoC,CAAC;AACzD,OAAO,QAAQ,MAAM,qCAAqC,CAAC;AAC3D,OAAO,YAAY,MAAM,yCAAyC,CAAC;AAEnE,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE;QACV,WAAW;QACX,WAAW;QACX,QAAQ;QACR,YAAY;QACZ,YAAY;QACZ,OAAO;QACP,QAAQ;QACR,YAAY;KACb;IAED,QAAQ,EAAE;QACR,YAAY;YACV,MAAM,EAAE,IAAI,EAAE,GAAG,IAAI,CAAC,MAAM,CAAC;YAE7B,OAAO,CAAC,IAAI,CAAC,QAAQ,CAAC,WAAW,CAAC,CAAC;QACrC,CAAC;QAED,aAAa;YACX,MAAM,QAAQ,GAAG,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC;YAEhD,IAAI,CAAC,UAAU,EAAE,KAAK,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC;gBAAE,OAAO,GAAG,QAAQ,MAAM,CAAC;iBAChE,IAAI,QAAQ,KAAK,UAAU;gBAAE,OAAO,QAAQ,CAAC;YAElD,OAAO,aAAa,CAAC;QACvB,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<main class="blog-page">
<MyTransition>
<component :is="componentName" v-if="componentName" />
</MyTransition>
<MyTransition :delay="0.24">
<ArticleList v-if="showArticles" :key="$route.path" />
</MyTransition>
</main>
</template>
<script src="./BlogPage" />
<style lang="stylus">
.blog-page
max-width 780px
flex 1
@media (min-width $MQMobile)
margin 0 15px
.article-title
font-size 1.8rem
margin 10px 15px
</style>
import MediaLinks from "@theme/components/MediaLinks.vue";
import type { BlogOptions } from "@theme/types";
declare const _default: import("vue/types/vue").ExtendedVue<{
$timelineItems: import("@mr-hope/vuepress-types").PageComputed[];
$timeline: import("@theme/mixins/timeline").TimelineItem[];
} & Record<never, any> & MediaLinks, unknown, {
navigate(url: string): void;
jumpIntro(): void;
}, {
blogConfig: BlogOptions;
bloggerName: string;
bloggerAvatar: string;
hasIntro: boolean;
hintAttr: string;
i18n: {
article: string;
articleList: string;
category: string;
tag: string;
timeline: string;
timelineText: string;
allText: string;
intro: string;
star: string;
slides: string;
encrypt: string;
};
articleNumber: number;
}, Record<never, any>>;
export default _default;
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
import MediaLinks from "@theme/components/MediaLinks.vue";
import { timelineMixin } from "@theme/mixins/timeline";
import { filterArticle } from "@theme/utils/article";
import { navigate } from "@theme/utils/navigate";
export default timelineMixin.extend({
name: "BloggerInfo",
components: { MediaLinks },
computed: {
blogConfig() {
return this.$themeConfig.blog || {};
},
bloggerName() {
return (this.blogConfig.name ||
this.$themeConfig.author ||
this.$site.title ||
"");
},
bloggerAvatar() {
return this.blogConfig.avatar || this.$themeConfig.logo || "";
},
hasIntro() {
return Boolean(this.blogConfig.intro);
},
hintAttr() {
return this.hasIntro ? "aria-label" : "";
},
i18n() {
return this.$themeLocaleConfig.blog || getDefaultLocale().blog;
},
articleNumber() {
return filterArticle(this.$site.pages).length;
},
},
methods: {
navigate(url) {
navigate(url, this.$router, this.$route);
},
jumpIntro() {
if (this.hasIntro)
navigate(this.blogConfig.intro, this.$router, this.$route);
},
},
});
//# sourceMappingURL=BloggerInfo.js.map
\ No newline at end of file
{"version":3,"file":"BloggerInfo.js","sourceRoot":"","sources":["BloggerInfo.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,UAAU,MAAM,kCAAkC,CAAC;AAC1D,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACvD,OAAO,EAAE,aAAa,EAAE,MAAM,sBAAsB,CAAC;AACrD,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAKjD,eAAe,aAAa,CAAC,MAAM,CAAC;IAClC,IAAI,EAAE,aAAa;IAEnB,UAAU,EAAE,EAAE,UAAU,EAAE;IAE1B,QAAQ,EAAE;QACR,UAAU;YACR,OAAO,IAAI,CAAC,YAAY,CAAC,IAAI,IAAI,EAAE,CAAC;QACtC,CAAC;QAED,WAAW;YACT,OAAO,CACL,IAAI,CAAC,UAAU,CAAC,IAAI;gBACpB,IAAI,CAAC,YAAY,CAAC,MAAM;gBACxB,IAAI,CAAC,KAAK,CAAC,KAAK;gBAChB,EAAE,CACH,CAAC;QACJ,CAAC;QAED,aAAa;YACX,OAAO,IAAI,CAAC,UAAU,CAAC,MAAM,IAAI,IAAI,CAAC,YAAY,CAAC,IAAI,IAAI,EAAE,CAAC;QAChE,CAAC;QAED,QAAQ;YACN,OAAO,OAAO,CAAC,IAAI,CAAC,UAAU,CAAC,KAAK,CAAC,CAAC;QACxC,CAAC;QAED,QAAQ;YACN,OAAO,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,YAAY,CAAC,CAAC,CAAC,EAAE,CAAC;QAC3C,CAAC;QAED,IAAI;YACF,OAAO,IAAI,CAAC,kBAAkB,CAAC,IAAI,IAAI,gBAAgB,EAAE,CAAC,IAAI,CAAC;QACjE,CAAC;QAED,aAAa;YACX,OAAO,aAAa,CAAC,IAAI,CAAC,KAAK,CAAC,KAAK,CAAC,CAAC,MAAM,CAAC;QAChD,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,GAAW;YAClB,QAAQ,CAAC,GAAG,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC3C,CAAC;QAED,SAAS;YACP,IAAI,IAAI,CAAC,QAAQ;gBACf,QAAQ,CAAC,IAAI,CAAC,UAAU,CAAC,KAAe,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QACzE,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="blogger-info" vocab="https://schema.org/" typeof="Person">
<div
class="blogger"
:class="{ hasIntro }"
:[hintAttr]="hasIntro ? i18n.intro : ''"
:data-balloon-pos="hasIntro ? 'down' : ''"
role="navigation"
@click="jumpIntro"
>
<img
v-if="bloggerAvatar"
class="avatar"
:class="{ round: blogConfig.roundAvatar !== false }"
property="image"
alt="Blogger Avatar"
:src="$withBase(bloggerAvatar)"
/>
<div
v-if="bloggerName"
class="name"
property="name"
v-text="bloggerName"
/>
<meta
v-if="hasIntro"
property="url"
:content="$withBase(blogConfig.intro)"
/>
</div>
<div class="num-wrapper">
<div @click="navigate('/article/')">
<div class="num">{{ articleNumber }}</div>
<div>{{ i18n.article }}</div>
</div>
<div @click="navigate('/category/')">
<div class="num">{{ $category.list.length }}</div>
<div>{{ i18n.category }}</div>
</div>
<div @click="navigate('/tag/')">
<div class="num">{{ $tag.list.length }}</div>
<div>{{ i18n.tag }}</div>
</div>
<div @click="navigate('/timeline/')">
<div class="num">{{ $timelineItems.length }}</div>
<div>{{ i18n.timeline }}</div>
</div>
</div>
<MediaLinks />
</div>
</template>
<script src="./BloggerInfo" />
<style lang="stylus">
.blogger-info
.page &
background var(--bgcolor)
.blogger
padding 8px 0
text-align center
&.hasIntro
cursor pointer
.avatar
width 128px
height 128px
margin 0 auto
&.round
border-radius 50%
.name
margin 16px auto
font-size 22px
.num-wrapper
display flex
margin 0 auto 16px
width 80%
> div
width 25%
text-align center
font-size 13px
cursor pointer
&:hover
color var(--accent-color)
.num
position relative
margin-bottom 8px
font-weight 600
font-size 20px
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
capitalize: (word: string) => string;
clickCategory(path: string): void;
}, unknown, Record<never, any>>;
export default _default;
import Vue from "vue";
import { capitalize } from "@mr-hope/vuepress-shared";
import { navigate } from "@theme/utils/navigate";
export default Vue.extend({
name: "CategoryList",
methods: {
capitalize,
clickCategory(path) {
navigate(path, this.$router, this.$route);
},
},
});
//# sourceMappingURL=CategoryList.js.map
\ No newline at end of file
{"version":3,"file":"CategoryList.js","sourceRoot":"","sources":["CategoryList.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,EAAE,UAAU,EAAE,MAAM,0BAA0B,CAAC;AACtD,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAEjD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,cAAc;IAEpB,OAAO,EAAE;QACP,UAAU;QAEV,aAAa,CAAC,IAAY;YACxB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5C,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<ul class="category-list-wrapper">
<li
v-for="(category, index) in $category.list"
:key="category.path"
class="category"
:class="{
active: category.path === $route.path,
[`category${index % 9}`]: true,
}"
@click="clickCategory(category.path)"
>
{{ capitalize(category.name) }}
<span class="category-num">{{ category.pages.length }}</span>
</li>
</ul>
</template>
<script src="./CategoryList" />
<style lang="stylus">
$categoryListTextSize ?= 14px
.category-list-wrapper
position relative
z-index 2
padding-left 0
font-size $categoryListTextSize
font-family Arial, Helvetica, sans-serif
list-style none
.category
display inline-block
vertical-align middle
margin 0.3rem 0.6rem 0.8rem
padding 0.4rem 0.8rem
border-radius 0.25rem
box-shadow 0 1px 4px 0 var(--card-shadow-color)
color var(--dark-grey)
cursor pointer
overflow hidden
transition background-color 0.3s, color 0.3s
@media (max-width $MQMobileNarrow)
font-size 0.9rem
.category-num
display inline-block
min-width 1rem
height 1.2rem
margin-left 0.2em
padding 0 0.1rem
border-radius 0.6rem
color var(--white)
font-family sans-serif
font-size 0.7rem
line-height 1.2rem
text-align center
@require '~@mr-hope/vuepress-shared/styles/colors.styl'
for $color, $index in $colors
.category-list-wrapper .category{$index}
&, .theme-light &
background lighten($color, 90%)
&:hover
background lighten($color, 75%)
&.active
background var(--accent-color)
color var(--white)
.category-num
color var(--accent-color)
background var(--bgcolor-light)
.theme-dark &
background darken($color, 75%)
&:hover
background darken($color, 60%)
&.active
background var(--accent-color-d10)
color var(--white)
.category-num
background $color
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
navigate(link: string): void;
}, unknown, Record<never, any>>;
export default _default;
import Vue from "vue";
import ArticleIcon from "@theme/icons/ArticleIcon.vue";
import BookIcon from "@theme/icons/BookIcon.vue";
import LinkIcon from "@theme/icons/LinkIcon.vue";
import ProjectIcon from "@theme/icons/ProjectIcon.vue";
import { navigate } from "@theme/utils/navigate";
export default Vue.extend({
name: "ProjectList",
components: { ArticleIcon, BookIcon, LinkIcon, ProjectIcon },
methods: {
navigate(link) {
navigate(link, this.$router, this.$route);
},
},
});
//# sourceMappingURL=ProjectList.js.map
\ No newline at end of file
{"version":3,"file":"ProjectList.js","sourceRoot":"","sources":["ProjectList.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,WAAW,MAAM,8BAA8B,CAAC;AACvD,OAAO,QAAQ,MAAM,2BAA2B,CAAC;AACjD,OAAO,QAAQ,MAAM,2BAA2B,CAAC;AACjD,OAAO,WAAW,MAAM,8BAA8B,CAAC;AACvD,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAEjD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,aAAa;IAEnB,UAAU,EAAE,EAAE,WAAW,EAAE,QAAQ,EAAE,QAAQ,EAAE,WAAW,EAAE;IAE5D,OAAO,EAAE;QACP,QAAQ,CAAC,IAAY;YACnB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5C,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="project-list">
<div
v-for="(project, index) in $frontmatter.project || []"
:key="project.name"
class="project"
:class="`project${index % 9}`"
@click="navigate(project.link)"
>
<div
v-if="project.cover"
class="cover"
:style="`background: url(${$withBase(
project.cover
)}) center/cover no-repeat;`"
/>
<component :is="`${project.type}-icon`" />
<div class="name">{{ project.name }}</div>
<div class="desc">{{ project.desc }}</div>
</div>
</div>
</template>
<script src="./ProjectList" />
<style lang="stylus">
.project-list
position relative
display flex
justify-content flex-start
align-content stretch
align-items stretch
flex-wrap wrap
font-family sans-serif
margin-bottom 12px
z-index 2
.project
position relative
width calc(50% - 40px)
background-color var(--grey14)
border-radius 8px
margin 6px 8px
padding 12px
transition background-color 0.3s, transform 0.3s
@media (min-width $MQNarrow)
width calc(33% - 40px)
@media (min-width $MQWide)
width calc(25% - 40px)
&:hover
cursor pointer
transform scale(0.98, 0.98)
.cover
content ''
opacity 0.5
top 0
left 0
bottom 0
right 0
position absolute
z-index 1
.icon
position relative
z-index 2
float right
width 20px
height 20px
.name
position relative
z-index 2
color var(--grey3)
font-size 16px
font-weight 500
.desc
position relative
z-index 2
margin 6px 0
color var(--dark-grey)
font-size 13px
@require '~@mr-hope/vuepress-shared/styles/colors.styl'
for $color, $index in $colors
.project-list .project{$index}
&, .theme-light &
background lighten($color, 90%)
&:hover
background lighten($color, 75%)
.theme-dark &
background darken($color, 75%)
&:hover
background darken($color, 60%)
</style>
import Vue from "vue";
interface TagOption {
name: string;
path: string;
}
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
isActive(name: string): boolean;
clickTag(path: string): void;
}, {
tagList: TagOption[];
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
import { navigate } from "@theme/utils/navigate";
export default Vue.extend({
name: "TagList",
computed: {
tagList() {
return [
{
name:
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
this.$themeLocaleConfig.blog.allText ||
getDefaultLocale().blog.allText,
path: "/tag/",
},
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
...this.$tag.list,
];
},
},
methods: {
isActive(name) {
return (name ===
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
((this.$currentTag && this.$currentTag.key) ||
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
this.$themeLocaleConfig.blog.allText ||
getDefaultLocale().blog.allText));
},
clickTag(path) {
navigate(path, this.$router, this.$route);
},
},
});
//# sourceMappingURL=TagList.js.map
\ No newline at end of file
{"version":3,"file":"TagList.js","sourceRoot":"","sources":["TagList.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAC5D,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAOjD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,SAAS;IAEf,QAAQ,EAAE;QACR,OAAO;YACL,OAAO;gBACL;oBACE,IAAI;oBACF,oEAAoE;oBACpE,IAAI,CAAC,kBAAkB,CAAC,IAAK,CAAC,OAAO;wBACrC,gBAAgB,EAAE,CAAC,IAAI,CAAC,OAAO;oBACjC,IAAI,EAAE,OAAO;iBACd;gBACD,sEAAsE;gBACtE,GAAI,IAAI,CAAC,IAAI,CAAC,IAAoB;aACnC,CAAC;QACJ,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,IAAY;YACnB,OAAO,CACL,IAAI;gBACJ,sEAAsE;gBACtE,CAAC,CAAC,IAAI,CAAC,WAAW,IAAI,IAAI,CAAC,WAAW,CAAC,GAAG,CAAC;oBACzC,oEAAoE;oBACpE,IAAI,CAAC,kBAAkB,CAAC,IAAK,CAAC,OAAO;oBACrC,gBAAgB,EAAE,CAAC,IAAI,CAAC,OAAO,CAAC,CACnC,CAAC;QACJ,CAAC;QAED,QAAQ,CAAC,IAAY;YACnB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5C,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<ul class="tag-list-wrapper">
<li
v-for="(tag, index) in tagList"
:key="tag.path"
class="tag"
:class="{ active: isActive(tag.name), [`tag${index % 9}`]: true }"
@click="clickTag(tag.path)"
>
<div class="tag-name">{{ tag.name }}</div>
</li>
</ul>
</template>
<script src="./TagList" />
<style lang="stylus">
.tag-list-wrapper
position relative
z-index 2
padding-left 0
font-family Arial, Helvetica, sans-serif
list-style none
display flex
flex-wrap wrap
justify-content space-evenly
.tag
display inline-block
position relative
vertical-align middle
min-width 24px
margin 4px 6px
padding 3px 8px
border-radius 8px
box-shadow 0 1px 6px 0 var(--box-shadow-color)
color var(--white)
font-size 12px
text-align center
overflow hidden
cursor pointer
transition background-color 0.3s, transform 0.3s
&:hover
cursor pointer
&.active
transform scale(1.1, 1.1)
@require '~@mr-hope/vuepress-shared/styles/colors.styl'
for $color, $index in $colors
.tag-list-wrapper .tag{$index}
.theme-light &, &
background lighten($color, 10%)
&:hover, &.active
background darken($color, 5%)
.theme-dark &
background darken($color, 5%)
&:hover, &.active
background lighten($color, 10%)
</style>
import Anchor from "@theme/components/Anchor.vue";
import type { SidebarHeader } from "@theme/utils/groupHeader";
declare const _default: import("vue/types/vue").ExtendedVue<{
$timelineItems: import("@mr-hope/vuepress-types").PageComputed[];
$timeline: import("@theme/mixins/timeline").TimelineItem[];
} & Record<never, any> & Anchor, unknown, {
navigate(url: string): void;
}, {
hint: string;
anchorConfig: SidebarHeader[];
}, Record<never, any>>;
export default _default;
import Anchor from "@theme/components/Anchor.vue";
import MyTransition from "@theme/components/MyTransition.vue";
import { timelineMixin } from "@theme/mixins/timeline";
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
export default timelineMixin.extend({
name: "Timeline",
components: { Anchor, MyTransition },
computed: {
hint() {
return ((this.$themeConfig.blog && this.$themeConfig.blog.timeline) ||
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
this.$themeLocaleConfig.blog.timelineText ||
getDefaultLocale().blog.timelineText);
},
anchorConfig() {
return this.$timeline.map((item) => ({
title: item.year.toString(),
level: 2,
slug: item.year.toString(),
}));
},
},
methods: {
navigate(url) {
void this.$router.push(url);
},
},
});
//# sourceMappingURL=Timeline.js.map
\ No newline at end of file
{"version":3,"file":"Timeline.js","sourceRoot":"","sources":["Timeline.ts"],"names":[],"mappings":"AAAA,OAAO,MAAM,MAAM,8BAA8B,CAAC;AAClD,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACvD,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAI5D,eAAe,aAAa,CAAC,MAAM,CAAC;IAClC,IAAI,EAAE,UAAU;IAEhB,UAAU,EAAE,EAAE,MAAM,EAAE,YAAY,EAAE;IAEpC,QAAQ,EAAE;QACR,IAAI;YACF,OAAO,CACL,CAAC,IAAI,CAAC,YAAY,CAAC,IAAI,IAAI,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,QAAQ,CAAC;gBAC3D,oEAAoE;gBACpE,IAAI,CAAC,kBAAkB,CAAC,IAAK,CAAC,YAAY;gBAC1C,gBAAgB,EAAE,CAAC,IAAI,CAAC,YAAY,CACrC,CAAC;QACJ,CAAC;QAED,YAAY;YACV,OAAO,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,CAAC;gBACnC,KAAK,EAAE,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE;gBAC3B,KAAK,EAAE,CAAC;gBACR,IAAI,EAAE,IAAI,CAAC,IAAI,CAAC,QAAQ,EAAE;aAC3B,CAAC,CAAC,CAAC;QACN,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,GAAW;YAClB,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAC9B,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="timeline-wrapper">
<ul class="timeline-content">
<MyTransition>
<li class="desc">{{ hint }}</li>
</MyTransition>
<Anchor :items="anchorConfig" />
<MyTransition
v-for="(item, index) in $timeline"
:key="index"
:delay="0.08 * (index + 1)"
>
<li>
<h3 :id="item.year" class="year">
<span>{{ item.year }}</span>
</h3>
<ul class="year-wrapper">
<li
v-for="(article, articleIndex) in item.articles"
:key="articleIndex"
>
<span class="date">{{ article.frontmatter.parsedDate }}</span>
<span class="title" @click="navigate(article.path)">
{{ article.title }}
</span>
</li>
</ul>
</li>
</MyTransition>
</ul>
</div>
</template>
<script src="./Timeline" />
<style lang="stylus">
.timeline-wrapper
max-width 740px
margin 0 auto
padding 40px 0
--dot-color #fff
--dot-bar-color #eaecef
--dot-border-color #ddd
.theme-dark &
--dot-color #444
--dot-bar-color #333
--dot-border-color #555
#anchor
left unset
right 0
min-width 0
.anchor-wrapper
position relative
z-index 10
.timeline-content
box-sizing border-box
position relative
padding-left 76px
list-style none
&::after
content ' '
position absolute
top 14px
left 64px
z-index -1
width 4px
height calc(100% - 38px)
margin-left -2px
background var(--dot-bar-color)
.desc
position relative
color var(--text-color)
font-size 18px
@media (min-width $MQNormal)
font-size 20px
&:before
content ' '
position absolute
z-index 2
left -12px
top 50%
width 8px
height 8px
margin-left -6px
margin-top -6px
background var(--dot-color)
border 2px solid var(--dot-border-color)
border-radius 50%
.year
margin-top 0.5rem - $navbarHeight
margin-bottom 0.5rem
padding-top: ($navbarHeight + 3rem)
color var(--text-color)
font-size 26px
font-weight 700
span
position relative
&:before
content ' '
position absolute
z-index 2
left -12px
top 50%
width 8px
height 8px
margin-left -6px
margin-top -6px
background var(--dot-color)
border 2px solid var(--dot-border-color)
border-radius 50%
.year-wrapper
padding-left 0 !important
li
position relative
display flex
padding 30px 0 10px
border-bottom 1px dashed var(--border-color)
list-style none
&:hover
cursor pointer
.date
font-size 16px
transition font-size 0.3s ease-out
&::before
background-color var(--bgcolor)
border-color var(--accent-color)
.title
color var(--accent-color)
font-size 18px
transition font-size 0.3s ease-out
.date
position absolute
right calc(100% + 24px)
text-align right
width 40px
font-size 14px
line-height 30px
&::before
content ' '
position absolute
z-index 2
right -16px
top 50%
width 6px
height 6px
margin-left -6px
margin-top -6px
background var(--dot-color)
border 2px solid var(--dot-border-color)
border-radius 50%
.title
position relative
font-size 16px
line-height 30px
@media (max-width $MQMobile)
.timeline-wrapper
margin 0 1.2rem
</style>
D
import MyTransition from "@theme/components/MyTransition.vue";
declare const _default: import("vue/types/vue").ExtendedVue<{
$timelineItems: import("@mr-hope/vuepress-types").PageComputed[];
$timeline: import("@theme/mixins/timeline").TimelineItem[];
} & Record<never, any> & MyTransition, unknown, {
navigate(url: string): void;
}, {
hint: string;
}, Record<never, any>>;
export default _default;
import MyTransition from "@theme/components/MyTransition.vue";
import TimeIcon from "@mr-hope/vuepress-plugin-comment/lib/client/icons/TimeIcon.vue";
import { timelineMixin } from "@theme/mixins/timeline";
import { getDefaultLocale } from "@mr-hope/vuepress-shared";
export default timelineMixin.extend({
name: "TimelineList",
components: { MyTransition, TimeIcon },
computed: {
hint() {
return (
// eslint-disable-next-line @typescript-eslint/no-non-null-assertion
this.$themeLocaleConfig.blog.timeline ||
getDefaultLocale().blog.timeline);
},
},
methods: {
navigate(url) {
void this.$router.push(url);
},
},
});
//# sourceMappingURL=TimelineList.js.map
\ No newline at end of file
{"version":3,"file":"TimelineList.js","sourceRoot":"","sources":["TimelineList.ts"],"names":[],"mappings":"AAAA,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,QAAQ,MAAM,gEAAgE,CAAC;AACtF,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACvD,OAAO,EAAE,gBAAgB,EAAE,MAAM,0BAA0B,CAAC;AAE5D,eAAe,aAAa,CAAC,MAAM,CAAC;IAClC,IAAI,EAAE,cAAc;IAEpB,UAAU,EAAE,EAAE,YAAY,EAAE,QAAQ,EAAE;IAEtC,QAAQ,EAAE;QACR,IAAI;YACF,OAAO;YACL,oEAAoE;YACpE,IAAI,CAAC,kBAAkB,CAAC,IAAK,CAAC,QAAQ;gBACtC,gBAAgB,EAAE,CAAC,IAAI,CAAC,QAAQ,CACjC,CAAC;QACJ,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,GAAW;YAClB,KAAK,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;QAC9B,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<div class="timeline-list-wrapper">
<div class="title" @click="navigate('/timeline/')">
<TimeIcon />
<span class="num">{{ $timelineItems.length }}</span>
{{ hint }}
</div>
<hr />
<div class="content">
<ul class="timeline-list">
<MyTransition
v-for="(item, index) in $timeline"
:key="index"
:delay="0.08 * (index + 1)"
>
<li>
<h3 class="year">{{ item.year }}</h3>
<ul class="year-wrapper">
<li
v-for="(article, articleIndex) in item.articles"
:key="articleIndex"
>
<span class="date">{{ article.frontmatter.parsedDate }}</span>
<span class="timeline-title" @click="navigate(article.path)">
{{ article.title }}
</span>
</li>
</ul>
</li>
</MyTransition>
</ul>
</div>
</div>
</template>
<script src="./TimelineList" />
<style lang="stylus">
.timeline-list-wrapper
padding 8px 0
--dot-color #fff
--dot-bar-color #eaecef
--dot-border-color #ddd
.theme-dark &
--dot-color #444
--dot-bar-color #333
--dot-border-color #555
.title
cursor pointer
.icon
position relative
bottom -0.125rem
width 16px
height 16px
margin 0 6px
.num
position relative
margin 0 2px
font-size 22px
.content
overflow-y scroll
max-height 80vh
&::-webkit-scrollbar-track-piece
background transparent
.timeline-list
position relative
margin 0 8px
box-sizing border-box
list-style none
&::after
content ' '
position absolute
top 14px
left 0
z-index -1
margin-left -2px
width 4px
height calc(100% - 14px)
background var(--dot-bar-color)
.year
position relative
margin 20px 0 0px
color var(--text-color)
font-size 20px
font-weight 700
&:before
content ' '
position absolute
z-index 2
left -20px
top 50%
margin-left -4px
margin-top -4px
width 8px
height 8px
background var(--dot-color)
border 1px solid var(--dot-border-color)
border-radius 50%
.year-wrapper
padding-left 0 !important
li
position relative
display flex
padding 12px 0 4px
list-style none
border-bottom 1px dashed var(--border-color)
&:hover
.date
color var(--accent-color)
&::before
background var(--accent-color)
border-color var(--dot-color)
.title
color var(--accent-color)
.date
width 36px
line-height 32px
display inline-block
vertical-align bottom
font-size 12px
&::before
content ' '
position absolute
left -19px
top 24px
width 6px
height 6px
margin-left -4px
background var(--dot-color)
border-radius 50%
border 1px solid var(--dot-border-color)
z-index 2
.timeline-title
line-height 32px
font-size 14px
cursor pointer
</style>
import Vue from "vue";
declare const _default: import("vue/types/vue").ExtendedVue<Vue, {
location: string;
}, unknown, {
copyright: string;
}, {
html: string;
lang: string;
}>;
export default _default;
import Vue from "vue";
export default Vue.extend({
name: "Clipboard",
props: {
html: { type: String, default: "" },
lang: { type: String, default: "en-US" },
},
data: () => ({
location: "",
}),
computed: {
copyright() {
const { author } = this.$themeConfig;
const content = {
"zh-CN": `${this.html}\n-----\n${author ? `著作权归${author}所有。\n` : ""}链接: ${this.location}`,
"en-US": `${this.html}\n-----\n${author ? `Copyright by ${author}.\n` : ""}Link: ${this.location}`,
"vi-VN": `${this.html}\n-----\n${author ? `bản quyền bởi ${author}.\n` : ""}Liên kết: ${this.location}`,
};
return content[this.lang];
},
},
created() {
if (typeof window !== "undefined")
this.location = window.location.toString();
},
});
//# sourceMappingURL=Clipboard.js.map
\ No newline at end of file
{"version":3,"file":"Clipboard.js","sourceRoot":"","sources":["Clipboard.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AAEtB,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,WAAW;IAEjB,KAAK,EAAE;QACL,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,EAAE,EAAE;QACnC,IAAI,EAAE,EAAE,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,EAAE;KACzC;IAED,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC;QACX,QAAQ,EAAE,EAAE;KACb,CAAC;IAEF,QAAQ,EAAE;QACR,SAAS;YACP,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC,YAAY,CAAC;YACrC,MAAM,OAAO,GAA2B;gBACtC,OAAO,EAAE,GAAG,IAAI,CAAC,IAAI,YACnB,MAAM,CAAC,CAAC,CAAC,OAAO,MAAM,OAAO,CAAC,CAAC,CAAC,EAClC,OAAO,IAAI,CAAC,QAAQ,EAAE;gBACtB,OAAO,EAAE,GAAG,IAAI,CAAC,IAAI,YACnB,MAAM,CAAC,CAAC,CAAC,gBAAgB,MAAM,KAAK,CAAC,CAAC,CAAC,EACzC,SAAS,IAAI,CAAC,QAAQ,EAAE;gBACxB,OAAO,EAAE,GAAG,IAAI,CAAC,IAAI,YACnB,MAAM,CAAC,CAAC,CAAC,iBAAiB,MAAM,KAAK,CAAC,CAAC,CAAC,EAC1C,aAAa,IAAI,CAAC,QAAQ,EAAE;aAC7B,CAAC;YAEF,OAAO,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QAC5B,CAAC;KACF;IAED,OAAO;QACL,IAAI,OAAO,MAAM,KAAK,WAAW;YAC/B,IAAI,CAAC,QAAQ,GAAG,MAAM,CAAC,QAAQ,CAAC,QAAQ,EAAE,CAAC;IAC/C,CAAC;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<!-- eslint-disable-next-line vue/no-v-html -->
<div v-html="copyright" />
</template>
<script src="./Clipboard" />
import Navbar from "@theme/components/Navbar/Navbar.vue";
import type { SidebarItem, SidebarHeader } from "@theme/utils/sidebar";
declare const _default: import("vue/types/vue").ExtendedVue<{
globalEncryptPassword: string;
} & {
checkGlobalPassword(globalPassword: string): void;
} & {
isGlobalEncrypted: boolean;
} & Record<never, any> & {
encryptOptions: import("../types").EncryptOptions;
} & Navbar, {
isSidebarOpen: boolean;
hideNavbar: boolean;
touchStart: {
clientX: number;
clientY: number;
};
}, {
/** Get scroll distance */
getScrollTop(): number;
toggleSidebar(to: boolean): void;
onTouchStart(event: TouchEvent): void;
onTouchEnd(event: TouchEvent): void;
getHeader(items: SidebarItem[]): SidebarHeader[];
}, {
enableNavbar: boolean;
enableSidebar: boolean;
sidebarItems: SidebarItem[];
pageClasses: unknown;
headers: SidebarHeader[];
enableAnchor: boolean;
}, {
navbar: boolean;
sidebar: boolean;
}>;
export default _default;
import { getSidebarItems } from "@theme/utils/sidebar";
import { globalEncryptMixin } from "@theme/mixins/globalEncrypt";
import Navbar from "@theme/components/Navbar/Navbar.vue";
import PageFooter from "@theme/components/PageFooter.vue";
import Password from "@theme/components/Password.vue";
import Sidebar from "@theme/components/Sidebar/Sidebar.vue";
import throttle from "lodash.throttle";
export default globalEncryptMixin.extend({
name: "Common",
components: {
Navbar,
PageFooter,
Password,
Sidebar,
},
props: {
navbar: { type: Boolean, default: true },
sidebar: { type: Boolean, default: true },
},
data: () => ({
isSidebarOpen: false,
hideNavbar: false,
touchStart: {
clientX: 0,
clientY: 0,
},
}),
computed: {
enableNavbar() {
if (this.navbar === false)
return false;
const { frontmatter } = this.$page;
if (frontmatter.navbar === false || this.$themeConfig.navbar === false)
return false;
return Boolean(this.$title ||
this.$themeConfig.logo ||
this.$themeConfig.repo ||
this.$themeConfig.nav ||
this.$themeLocaleConfig.nav);
},
enableSidebar() {
if (this.sidebar === false)
return false;
return (!this.$frontmatter.home &&
this.$frontmatter.sidebar !== false &&
this.sidebarItems.length !== 0);
},
sidebarItems() {
if (this.sidebar === false)
return [];
return getSidebarItems(this.$page, this.$site, this.$localePath);
},
pageClasses() {
const userPageClass = this.$page.frontmatter.pageClass;
return [
{
"has-navbar": this.enableNavbar,
"has-sidebar": this.enableSidebar,
"has-anchor": this.enableAnchor,
"hide-navbar": this.hideNavbar,
"sidebar-open": this.isSidebarOpen,
},
userPageClass,
];
},
headers() {
return this.getHeader(this.sidebarItems);
},
enableAnchor() {
return (this.$frontmatter.anchorDisplay ||
(this.$themeConfig.anchorDisplay !== false &&
this.$frontmatter.anchorDisplay !== false));
},
},
mounted() {
let lastDistance = 0;
this.$router.afterEach(() => {
this.isSidebarOpen = false;
});
window.addEventListener("scroll", throttle(() => {
const distance = this.getScrollTop();
// scroll down
if (lastDistance < distance && distance > 58) {
if (!this.isSidebarOpen)
this.hideNavbar = true;
// scroll up
}
else
this.hideNavbar = false;
lastDistance = distance;
}, 300));
},
methods: {
/** Get scroll distance */
getScrollTop() {
return (window.pageYOffset ||
document.documentElement.scrollTop ||
document.body.scrollTop ||
0);
},
toggleSidebar(to) {
this.isSidebarOpen = typeof to === "boolean" ? to : !this.isSidebarOpen;
this.$emit("toggle-sidebar", this.isSidebarOpen);
},
// Side swipe
onTouchStart(event) {
this.touchStart = {
clientX: event.changedTouches[0].clientX,
clientY: event.changedTouches[0].clientY,
};
},
onTouchEnd(event) {
const dx = event.changedTouches[0].clientX - this.touchStart.clientX;
const dy = event.changedTouches[0].clientY - this.touchStart.clientY;
if (Math.abs(dx) > Math.abs(dy) && Math.abs(dx) > 40)
if (dx > 0 && this.touchStart.clientX <= 80)
this.toggleSidebar(true);
else
this.toggleSidebar(false);
},
getHeader(items) {
for (let i = 0; i < items.length; i++) {
const item = items[i];
if (item.type === "group") {
const matching = this.getHeader(item.children);
if (matching.length !== 0)
return matching;
}
else if (item.type === "page" &&
item.headers &&
item.path === this.$route.path)
return item.headers;
}
return [];
},
},
});
//# sourceMappingURL=Common.js.map
\ No newline at end of file
{"version":3,"file":"Common.js","sourceRoot":"","sources":["Common.ts"],"names":[],"mappings":"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"}
\ No newline at end of file
<template>
<div
class="theme-container"
:class="pageClasses"
@touchstart="onTouchStart"
@touchend="onTouchEnd"
>
<Password v-if="isGlobalEncrypted" @password-verify="checkGlobalPassword" />
<!-- Content -->
<template v-else>
<Navbar v-if="enableNavbar" @toggle-sidebar="toggleSidebar">
<template #start>
<slot name="navbar-start" />
</template>
<template #center>
<slot name="navbar-center" />
</template>
<template #end>
<slot name="navbar-end" />
</template>
</Navbar>
<div class="sidebar-mask" @click="toggleSidebar(false)" />
<Sidebar :items="sidebarItems" @toggle-sidebar="toggleSidebar">
<template #top>
<slot name="sidebar-top" />
</template>
<template #center>
<slot name="sidebar-center" />
</template>
<template #bottom>
<slot name="sidebar-bottom" />
</template>
</Sidebar>
<slot :sidebar-items="sidebarItems" :headers="headers" />
<PageFooter :key="$route.path" />
</template>
</div>
</template>
<script src="./Common" />
<style lang="stylus">
.theme-container
min-height 100vh
.sidebar-mask
position fixed
z-index 9
top 0
left 0
width 100vw
height 100vh
display none
.theme-container.sidebar-open &
display block
</style>
import Vue from "vue";
interface ActionConfig {
text: string;
link: string;
}
declare const _default: import("vue/types/vue").ExtendedVue<Vue, unknown, {
navigate(link: string): void;
}, {
actionLinks: ActionConfig[];
}, Record<never, any>>;
export default _default;
import Vue from "vue";
import MyTransition from "@theme/components/MyTransition.vue";
import NavLink from "@theme/components/Navbar/NavLink.vue";
import { navigate } from "@theme/utils/navigate";
export default Vue.extend({
name: "Home",
components: { MyTransition, NavLink },
computed: {
actionLinks() {
const { action } = this.$frontmatter;
if (Array.isArray(action))
return action;
return [action];
},
},
methods: {
navigate(link) {
navigate(link, this.$router, this.$route);
},
},
});
//# sourceMappingURL=Home.js.map
\ No newline at end of file
{"version":3,"file":"Home.js","sourceRoot":"","sources":["Home.ts"],"names":[],"mappings":"AAAA,OAAO,GAAG,MAAM,KAAK,CAAC;AACtB,OAAO,YAAY,MAAM,oCAAoC,CAAC;AAC9D,OAAO,OAAO,MAAM,sCAAsC,CAAC;AAC3D,OAAO,EAAE,QAAQ,EAAE,MAAM,uBAAuB,CAAC;AAOjD,eAAe,GAAG,CAAC,MAAM,CAAC;IACxB,IAAI,EAAE,MAAM;IAEZ,UAAU,EAAE,EAAE,YAAY,EAAE,OAAO,EAAE;IAErC,QAAQ,EAAE;QACR,WAAW;YACT,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC,YAAY,CAAC;YACrC,IAAI,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC;gBAAE,OAAO,MAAwB,CAAC;YAC3D,OAAO,CAAC,MAAM,CAAmB,CAAC;QACpC,CAAC;KACF;IAED,OAAO,EAAE;QACP,QAAQ,CAAC,IAAY;YACnB,QAAQ,CAAC,IAAI,EAAE,IAAI,CAAC,OAAO,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAC5C,CAAC;KACF;CACF,CAAC,CAAC"}
\ No newline at end of file
<template>
<main
:aria-labelledby="$frontmatter.heroText !== null ? 'main-title' : null"
class="home"
>
<header class="hero">
<MyTransition>
<img
v-if="$frontmatter.heroImage"
key="light"
:class="{ light: Boolean($frontmatter.darkHeroImage) }"
:src="$withBase($frontmatter.heroImage)"
:alt="$frontmatter.heroAlt || 'HomeLogo'"
/>
</MyTransition>
<MyTransition>
<img
v-if="$frontmatter.darkHeroImage"
key="dark"
class="dark"
:src="$withBase($frontmatter.darkHeroImage)"
:alt="$frontmatter.heroAlt || 'HomeLogo'"
/>
</MyTransition>
<div class="hero-info">
<MyTransition :delay="0.04">
<h1
v-if="$frontmatter.heroText !== false"
id="main-title"
v-text="$frontmatter.heroText || $title || 'Hello'"
/>
</MyTransition>
<MyTransition :delay="0.08">
<p
class="description"
v-text="
$frontmatter.tagline ||
$description ||
'Welcome to your VuePress site'
"
/>
</MyTransition>
<MyTransition :delay="0.12">
<p v-if="$frontmatter.action" class="action">
<NavLink
v-for="action in actionLinks"
:key="action.text"
:item="action"
class="action-button"
:class="action.type || ''"
/>
</p>
</MyTransition>
</div>
</header>
<MyTransition :delay="0.16">
<div>
<h2 class="features-header">Resources</h2>
<div
v-if="$frontmatter.features && $frontmatter.features.length"
class="features"
>
<template v-for="(feature, index) in $frontmatter.features">
<div
v-if="feature.link"
:key="index"
class="feature link"
:class="`feature${index % 9}`"
tabindex="0"
role="navigation"
@click="navigate(feature.link)"
>
<div class="icon-container">
<i :class="`far fa-${feature.icon}`"></i>
</div>
<h2>{{ feature.title }}</h2>
<p>{{ feature.details }}</p>
</div>
<div
v-else
:key="index"
class="feature"
:class="`feature${index % 9}`"
>
<h2>{{ feature.title }}</h2>
<p>{{ feature.details }}</p>
</div>
</template>
</div>
</div>
</MyTransition>
<MyTransition :delay="0.24">
<Content class="theme-default-content custom" />
</MyTransition>
</main>
</template>
<script src="./Home" />
<style lang="stylus">
.home
display block
max-width $homePageWidth
min-height 100vh - $navbarHeight
padding $navbarHeight 2rem 0
margin 0px auto
overflow-x hidden
@media (max-width $MQNarrow)
min-height 100vh - $navbarMobileHeight
padding-top $navbarMobileHeight
@media (max-width $MQMobileNarrow)
padding-left 1.5rem
padding-right 1.5rem
.hero
text-align center
@media (min-width $MQNarrow)
display flex
justify-content space-evenly
align-items center
text-align left
img
display block
max-width 100%
max-height 320px
margin 0
@media (max-width $MQNarrow)
max-height 280px
margin 3rem auto 1.5rem
@media (max-width $MQMobile)
max-height 240px
margin 2rem auto 1.2rem
@media (max-width $MQMobileNarrow)
max-height 210px
margin 1.5rem auto 1rem
.theme-light &
&.light
display block
&.dark
display none
.theme-dark &
&.light
display none
&.dark
display block
h1
font-size 3rem
@media (max-width $MQMobile)
font-size 2.5rem
@media (max-width $MQMobileNarrow)
font-size 2rem
h1, .description, .action
margin 1.8rem auto
@media (max-width $MQMobile)
margin 1.5rem auto
@media (max-width $MQMobileNarrow)
margin 1.2rem auto
.description
max-width 35rem
color var(--text-color-l40)
font-size 1.6rem
line-height 1.3
@media (max-width $MQMobile)
font-size 1.4rem
@media (max-width $MQMobileNarrow)
font-size 1.2rem
.action-button
display inline-block
margin 0.6rem 0.8rem
padding 1rem 1.5rem
border 2px solid var(--accent-color)
border-radius 2rem
color var(--accent-color)
font-size 1.2rem
transition background 0.1s ease
overflow hidden
@media (max-width $MQMobile)
padding 0.8rem 1.2rem
font-size 1.1rem
@media (max-width $MQMobileNarrow)
font-size 1rem
&:hover
color var(--white)
background-color var(--accent-color)
&.primary
color var(--white)
background-color var(--accent-color)
&:hover
border-color var(--accent-color-l10)
background-color var(--accent-color-l10)
.theme-dark &
&:hover
border-color var(--accent-color-d10)
background-color var(--accent-color-d10)
.features
display flex
flex-wrap wrap
justify-content center
align-items stretch
align-content stretch
margin 0 -2rem
padding 1.2rem 0
border-top 1px solid var(--border-color)
@media (max-width $MQMobileNarrow)
margin 0 -1.5rem
.feature
display flex
flex-direction column
justify-content center
flex-basis calc(33% - 4rem)
margin 0.5rem
padding 0 1.5rem
border-radius 0.5rem
transition transform 0.3s, box-shadow 0.3s
overflow hidden
@media (max-width $MQNarrow)
flex-basis calc(50% - 4rem)
@media (max-width $MQMobile)
font-size 0.95rem
@media (max-width $MQMobileNarrow)
flex-basis calc(100%)
font-size 0.9rem
margin 0.5rem 0
border-radius 0
&.link
cursor pointer
&:hover
box-shadow 0 2px 12px 0 var(--card-shadow-color)
h2
margin-bottom 0.25rem
border-bottom none
color var(--text-color-l10)
font-size 1.25rem
font-weight 500
@media (max-width $MQMobileNarrow)
font-size 1.2rem
p
margin-top 0
color var(--text-color-l25)
{$contentClass}
padding-bottom 1.5rem
@require '~@mr-hope/vuepress-shared/styles/colors.styl'
for $color, $index in $colors
.home .features .feature{$index}
&, .theme-light &
background lighten($color, 90%)
.theme-dark &
background darken($color, 75%)
</style>
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
This diff is collapsed.
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment