chore(engine): switch to eleventy
This commit is contained in:
parent
4443bea122
commit
65fd0a0dd8
114 changed files with 4493 additions and 8239 deletions
|
@ -23,7 +23,7 @@ steps:
|
|||
hosts:
|
||||
from_secret: deploy_host
|
||||
target: /var/www/rulebook.kobold.city
|
||||
source: dist/*
|
||||
source: _site/*
|
||||
user:
|
||||
from_secret: deploy_user
|
||||
key:
|
||||
|
|
|
@ -1,15 +0,0 @@
|
|||
/* eslint-env node */
|
||||
require('@rushstack/eslint-patch/modern-module-resolution')
|
||||
|
||||
module.exports = {
|
||||
root: true,
|
||||
'extends': [
|
||||
'plugin:vue/vue3-essential',
|
||||
'eslint:recommended',
|
||||
'@vue/eslint-config-typescript',
|
||||
'@vue/eslint-config-prettier'
|
||||
],
|
||||
parserOptions: {
|
||||
ecmaVersion: 'latest'
|
||||
}
|
||||
}
|
45
.gitignore
vendored
45
.gitignore
vendored
|
@ -1,28 +1,25 @@
|
|||
# Logs
|
||||
logs
|
||||
*.log
|
||||
npm-debug.log*
|
||||
yarn-debug.log*
|
||||
yarn-error.log*
|
||||
pnpm-debug.log*
|
||||
lerna-debug.log*
|
||||
# Generated files
|
||||
package/generated*
|
||||
|
||||
node_modules
|
||||
.DS_Store
|
||||
dist
|
||||
dist-ssr
|
||||
coverage
|
||||
*.local
|
||||
# Ignore installed npm modules
|
||||
node_modules/
|
||||
|
||||
/cypress/videos/
|
||||
/cypress/screenshots/
|
||||
# Ignore build tool output, e.g. code coverage
|
||||
.nyc_output/
|
||||
coverage/
|
||||
|
||||
# Editor directories and files
|
||||
.vscode/*
|
||||
!.vscode/extensions.json
|
||||
# Ignore API documentation
|
||||
api-docs/
|
||||
|
||||
# Ignore folders from source code editors
|
||||
.vscode
|
||||
.idea
|
||||
*.suo
|
||||
*.ntvs*
|
||||
*.njsproj
|
||||
*.sln
|
||||
*.sw?
|
||||
|
||||
# Ignore eleventy output when doing manual tests
|
||||
_site/
|
||||
|
||||
package-lock.json
|
||||
|
||||
# Ignore test files
|
||||
.cache
|
||||
test/stubs-layout-cache/_includes/*.js
|
|
@ -1 +0,0 @@
|
|||
{}
|
3
.vscode/extensions.json
vendored
3
.vscode/extensions.json
vendored
|
@ -1,3 +0,0 @@
|
|||
{
|
||||
"recommendations": ["Vue.volar", "Vue.vscode-typescript-vue-plugin"]
|
||||
}
|
26
CHANGELOG.md
26
CHANGELOG.md
|
@ -5,31 +5,23 @@ Tout les changements notables au projet sont consignés dans ce fichier, afin de
|
|||
Ce format est basé sur la norme [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
||||
et ce projet adhère au [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
||||
|
||||
## En cours
|
||||
## En cours - Pélican 0.3.0 (beta 1)
|
||||
|
||||
### Erratum 3
|
||||
|
||||
Avec cette version sort la première version adaptée à Rulebook 3 de Erratum, mon JDR de fantasy urbaine. Cette version fait une adaptation aux règles de rulebook 3 et profite des nouvelles possibilités offertes par la nouvelle itérations des règles de bases. Le livre de règle de Erratum a également été simplifié pour ne contenir que les règles de ce dernier.
|
||||
Refonte global du site en Eleventy, et simplification des règles pour n'être plus qu'une base.
|
||||
|
||||
### Ajoutés
|
||||
|
||||
- Ajout règles sur les dieux
|
||||
- Ajout d'une différenciation entre magies communes et rares
|
||||
- Ajout des postures alter
|
||||
TBD
|
||||
|
||||
### Modifiés
|
||||
|
||||
- Adaptation générales aux règles de rulebook
|
||||
- Amélioration des vertues
|
||||
- Déplacement dans un site externe du lore
|
||||
- Division des signes et magies en plusieurs page pour profiter de la place supplémentaire
|
||||
- Modification des signes pour utiliser le nouveau système de classe
|
||||
- Rééquilibrage global des signes
|
||||
- Refonte du verseau pour être basé sur les flux plus que le temps
|
||||
- Refonte signes doublés
|
||||
- Revue de la liste des heraults
|
||||
TBD
|
||||
|
||||
### Pélican 0.2.0 (alpha 2)
|
||||
### Supprimés
|
||||
|
||||
- [site] Retrait de tout les éléments spécifiques à un JDR en particulier.
|
||||
|
||||
## Pélican 0.2.0 (alpha 2)
|
||||
|
||||
Refonte global du site en vueJS
|
||||
|
||||
|
|
11
_data/metadata.js
Normal file
11
_data/metadata.js
Normal file
|
@ -0,0 +1,11 @@
|
|||
module.exports = {
|
||||
title: "Système D100 Pélican",
|
||||
url: "https://pelicanjdr.kazhnuz.space/",
|
||||
language: "fr",
|
||||
description: "Une base de JDR basé sur le système D100",
|
||||
author: {
|
||||
name: "Kazhnuz",
|
||||
email: "kazhnuz@kobold.cafe",
|
||||
url: "https://kazhnuz.space/"
|
||||
}
|
||||
}
|
18
_includes/layouts/base.njk
Normal file
18
_includes/layouts/base.njk
Normal file
|
@ -0,0 +1,18 @@
|
|||
---
|
||||
layout: layouts/parent.njk
|
||||
---
|
||||
|
||||
<h1>{{ eleventyNavigation.key }}</h1>
|
||||
|
||||
<aside>
|
||||
<div id="more-info">
|
||||
<h2>Sommaire</h2>
|
||||
{{ content | toc | safe }}
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<main id="skip">
|
||||
<div>
|
||||
{{ content | safe }}
|
||||
</div>
|
||||
</main>
|
8
_includes/layouts/home.njk
Normal file
8
_includes/layouts/home.njk
Normal file
|
@ -0,0 +1,8 @@
|
|||
---
|
||||
layout: layouts/parent.njk
|
||||
---
|
||||
<main id="skip">
|
||||
<div>
|
||||
{{ content | safe }}
|
||||
</div>
|
||||
</main>
|
45
_includes/layouts/parent.njk
Normal file
45
_includes/layouts/parent.njk
Normal file
|
@ -0,0 +1,45 @@
|
|||
<!doctype html>
|
||||
<html lang="{{ metadata.language }}">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>{{ title or metadata.title }}</title>
|
||||
<meta name="description" content="{{ description or metadata.description }}">
|
||||
|
||||
{#- Atom and JSON feeds included by default #}
|
||||
<link rel="alternate" href="/feed/feed.xml" type="application/atom+xml" title="{{ metadata.title }}">
|
||||
<link rel="alternate" href="/feed/feed.json" type="application/json" title="{{ metadata.title }}">
|
||||
<link rel="icon" type="image/x-icon" href="/favicon.svg">
|
||||
|
||||
{#- Uncomment this if you’d like folks to know that you used Eleventy to build your site! #}
|
||||
<meta name="generator" content="{{ eleventy.generator }}">
|
||||
|
||||
{%- css %}{% include "public/css/index.css" %}{% endcss %}
|
||||
<style>{% getBundle "css" %}</style>
|
||||
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<svg class="d-none" alt="">
|
||||
<symbol id="icon-bars" viewBox="0 0 32 32">
|
||||
<path d="M30 24v3c0 .6-.4 1-1 1h-26c-.6 0-1-.4-1-1v-3c0-.6.4-1 1-1h26c.6 0 1 .4 1 1zM30 15v3c0 .6-.4 1-1 1h-26c-.6 0-1-.4-1-1v-3c0-.6.4-1 1-1h26c.6 0 1 .4 1 1zM30 6v3c0 .6-.4 1-1 1h-26c-.6 0-1-.4-1-1v-3c0-.6.4-1 1-1h26c.6 0 1 .4 1 1z"></path>
|
||||
</symbol>
|
||||
</svg>
|
||||
|
||||
<a href="#skip" class="visually-hidden">Skip to main content</a>
|
||||
<nav id="sidebar">
|
||||
{{ collections.all | eleventyNavigation | eleventyNavigationToHtml({anchorClass: "itemLink",activeAnchorClass: "active",activeListItemClass: "active",activeKey: eleventyNavigation.key, listClass: "nav", listItemClass: "item"}) | safe }}
|
||||
</nav>
|
||||
|
||||
<div class="wrapper">
|
||||
{{ content | safe }}
|
||||
|
||||
<footer><a href="https://quarante-douze.net/"><img src="/img/qdouze.gif" alt="" /><span class="visually-hidden">Site hébergé par Fanstuff Garden.</span></a> <a href="https://creativecommons.org/licenses/by-sa/4.0/"><img src="/img/cc-by-sa.png" alt="" /><span class="visually-hidden">Tout le contenu de cette page est sous licence Creatve Common Attribution - Partage à l'identique.</span></a></footer>
|
||||
</div>
|
||||
|
||||
|
||||
<button id="mobile-button" class="menu-button"><svg class="icon icon-bars" alt=""><use xlink:href="#icon-bars"></use></svg> <span class="sr-only">Afficher le menu</span></button>
|
||||
|
||||
<script src="/js/mobile-sidebar.js"></script>
|
||||
</body>
|
||||
</html>
|
28
_includes/layouts/post.njk
Normal file
28
_includes/layouts/post.njk
Normal file
|
@ -0,0 +1,28 @@
|
|||
---
|
||||
layout: layouts/parent.njk
|
||||
---
|
||||
{# Only include the syntax highlighter CSS on blog posts #}
|
||||
{%- css %}{% include "node_modules/prismjs/themes/prism-okaidia.css" %}{% endcss %}
|
||||
{%- css %}{% include "public/css/prism-diff.css" %}{%- endcss %}
|
||||
<h1>{{ title }}</h1>
|
||||
|
||||
<ul class="post-metadata">
|
||||
<li><time datetime="{{ page.date | htmlDateString }}">{{ page.date | readableDate }}</time></li>
|
||||
{%- for tag in tags | filterTagList %}
|
||||
{%- set tagUrl %}/tags/{{ tag | slugify }}/{% endset %}
|
||||
<li><a href="{{ tagUrl }}" class="post-tag">{{ tag }}</a>{%- if not loop.last %}, {% endif %}</li>
|
||||
{%- endfor %}
|
||||
</ul>
|
||||
|
||||
{{ content | safe }}
|
||||
|
||||
{%- if collections.posts %}
|
||||
{%- set previousPost = collections.posts | getPreviousCollectionItem %}
|
||||
{%- set nextPost = collections.posts | getNextCollectionItem %}
|
||||
{%- if nextPost or previousPost %}
|
||||
<ul class="links-nextprev">
|
||||
{%- if previousPost %}<li>Previous: <a href="{{ previousPost.url }}">{{ previousPost.data.title }}</a></li>{% endif %}
|
||||
{%- if nextPost %}<li>Next: <a href="{{ nextPost.url }}">{{ nextPost.data.title }}</a></li>{% endif %}
|
||||
</ul>
|
||||
{%- endif %}
|
||||
{%- endif %}
|
9
_includes/postslist.njk
Normal file
9
_includes/postslist.njk
Normal file
|
@ -0,0 +1,9 @@
|
|||
{%- css %}.postlist { counter-reset: start-from {{ (postslistCounter or postslist.length) + 1 }} }{% endcss %}
|
||||
<ol reversed class="postlist">
|
||||
{% for post in postslist | reverse %}
|
||||
<li class="postlist-item{% if post.url == url %} postlist-item-active{% endif %}">
|
||||
<a href="{{ post.url }}" class="postlist-link">{% if post.data.title %}{{ post.data.title }}{% else %}<code>{{ post.url }}</code>{% endif %}</a>
|
||||
<time class="postlist-date" datetime="{{ post.date | htmlDateString }}">{{ post.date | readableDate("LLLL yyyy") }}</time>
|
||||
</li>
|
||||
{% endfor %}
|
||||
</ol>
|
4
_includes/websites.md
Normal file
4
_includes/websites.md
Normal file
|
@ -0,0 +1,4 @@
|
|||
- Réseau
|
||||
- [Press Garden](https://press.fanstuff.garden)
|
||||
- <a href="https://piaille.fr/@breezemedia" rel="me">Breeze Media (fedi)</a>
|
||||
- <a href="https://bsky.app/profile/breezemedia.bsky.social" rel="me">Breeze Media (bsky)</a>
|
|
@ -1,3 +1,10 @@
|
|||
---
|
||||
layout: layouts/home.njk
|
||||
eleventyNavigation:
|
||||
key: Accueil
|
||||
order: 0
|
||||
---
|
||||
|
||||
# Bienvenue sur le site de Pélican
|
||||
|
||||
Pélican est un système générique de jeu de rôle basé sur le système D100, ayant pour objectif de créer un système de jeu de rôle simple mais efficace, se basant sur les dés les plus générique d’un rôliste. Il ne s'agit cependant que d'une base de système, à partir de laquelle vous pourrez construire des systèmes adaptés à votre univers et vos concepts.
|
50
eleventy.config.drafts.js
Normal file
50
eleventy.config.drafts.js
Normal file
|
@ -0,0 +1,50 @@
|
|||
function eleventyComputedPermalink() {
|
||||
// When using `addGlobalData` and you *want* to return a function, you must nest functions like this.
|
||||
// `addGlobalData` acts like a global data file and runs the top level function it receives.
|
||||
return (data) => {
|
||||
// Always skip during non-watch/serve builds
|
||||
if(data.draft && !process.env.BUILD_DRAFTS) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return data.permalink;
|
||||
}
|
||||
};
|
||||
|
||||
function eleventyComputedExcludeFromCollections() {
|
||||
// When using `addGlobalData` and you *want* to return a function, you must nest functions like this.
|
||||
// `addGlobalData` acts like a global data file and runs the top level function it receives.
|
||||
return (data) => {
|
||||
// Always exclude from non-watch/serve builds
|
||||
if(data.draft && !process.env.BUILD_DRAFTS) {
|
||||
return true;
|
||||
}
|
||||
|
||||
return data.eleventyExcludeFromCollections;
|
||||
}
|
||||
};
|
||||
|
||||
module.exports.eleventyComputedPermalink = eleventyComputedPermalink;
|
||||
module.exports.eleventyComputedExcludeFromCollections = eleventyComputedExcludeFromCollections;
|
||||
|
||||
module.exports = eleventyConfig => {
|
||||
eleventyConfig.addGlobalData("eleventyComputed.permalink", eleventyComputedPermalink);
|
||||
eleventyConfig.addGlobalData("eleventyComputed.eleventyExcludeFromCollections", eleventyComputedExcludeFromCollections);
|
||||
|
||||
let logged = false;
|
||||
eleventyConfig.on("eleventy.before", ({runMode}) => {
|
||||
let text = "Excluding";
|
||||
// Only show drafts in serve/watch modes
|
||||
if(runMode === "serve" || runMode === "watch") {
|
||||
process.env.BUILD_DRAFTS = true;
|
||||
text = "Including";
|
||||
}
|
||||
|
||||
// Only log once.
|
||||
if(!logged) {
|
||||
console.log( `[11ty/eleventy-base-blog] ${text} drafts.` );
|
||||
}
|
||||
|
||||
logged = true;
|
||||
});
|
||||
}
|
34
eleventy.config.images.js
Normal file
34
eleventy.config.images.js
Normal file
|
@ -0,0 +1,34 @@
|
|||
const path = require("path");
|
||||
const eleventyImage = require("@11ty/eleventy-img");
|
||||
|
||||
module.exports = eleventyConfig => {
|
||||
function relativeToInputPath(inputPath, relativeFilePath) {
|
||||
let split = inputPath.split("/");
|
||||
split.pop();
|
||||
|
||||
return path.resolve(split.join(path.sep), relativeFilePath);
|
||||
}
|
||||
|
||||
// Eleventy Image shortcode
|
||||
// https://www.11ty.dev/docs/plugins/image/
|
||||
eleventyConfig.addAsyncShortcode("image", async function imageShortcode(src, alt, widths, sizes) {
|
||||
// Full list of formats here: https://www.11ty.dev/docs/plugins/image/#output-formats
|
||||
// Warning: Avif can be resource-intensive so take care!
|
||||
let formats = ["avif", "webp", "auto"];
|
||||
let file = relativeToInputPath(this.page.inputPath, src);
|
||||
let metadata = await eleventyImage(file, {
|
||||
widths: widths || ["auto"],
|
||||
formats,
|
||||
outputDir: path.join(eleventyConfig.dir.output, "img"), // Advanced usage note: `eleventyConfig.dir` works here because we’re using addPlugin.
|
||||
});
|
||||
|
||||
// TODO loading=eager and fetchpriority=high
|
||||
let imageAttributes = {
|
||||
alt,
|
||||
sizes,
|
||||
loading: "lazy",
|
||||
decoding: "async",
|
||||
};
|
||||
return eleventyImage.generateHTML(metadata, imageAttributes);
|
||||
});
|
||||
};
|
146
eleventy.config.js
Normal file
146
eleventy.config.js
Normal file
|
@ -0,0 +1,146 @@
|
|||
const { DateTime } = require("luxon");
|
||||
const markdownItAnchor = require("markdown-it-anchor");
|
||||
|
||||
const pluginRss = require("@11ty/eleventy-plugin-rss");
|
||||
const pluginSyntaxHighlight = require("@11ty/eleventy-plugin-syntaxhighlight");
|
||||
const pluginBundle = require("@11ty/eleventy-plugin-bundle");
|
||||
const pluginNavigation = require("@11ty/eleventy-navigation");
|
||||
const { EleventyRenderPlugin } = require("@11ty/eleventy");
|
||||
const { EleventyHtmlBasePlugin } = require("@11ty/eleventy");
|
||||
|
||||
const pluginDrafts = require("./eleventy.config.drafts.js");
|
||||
const pluginImages = require("./eleventy.config.images.js");
|
||||
const pluginTOC = require('eleventy-plugin-toc');
|
||||
|
||||
module.exports = function(eleventyConfig) {
|
||||
// Copy the contents of the `public` folder to the output folder
|
||||
// For example, `./public/css/` ends up in `_site/css/`
|
||||
eleventyConfig.addPassthroughCopy({
|
||||
"./public/": "/",
|
||||
"./node_modules/prismjs/themes/prism-okaidia.css": "/css/prism-okaidia.css"
|
||||
});
|
||||
|
||||
// Run Eleventy when these files change:
|
||||
// https://www.11ty.dev/docs/watch-serve/#add-your-own-watch-targets
|
||||
|
||||
// Watch content images for the image pipeline.
|
||||
eleventyConfig.addWatchTarget("content/**/*.{svg,webp,png,jpeg}");
|
||||
|
||||
// App plugins
|
||||
eleventyConfig.addPlugin(pluginDrafts);
|
||||
eleventyConfig.addPlugin(pluginImages);
|
||||
|
||||
// Official plugins
|
||||
eleventyConfig.addPlugin(pluginRss);
|
||||
eleventyConfig.addPlugin(pluginSyntaxHighlight, {
|
||||
preAttributes: { tabindex: 0 }
|
||||
});
|
||||
eleventyConfig.addPlugin(pluginNavigation);
|
||||
eleventyConfig.addPlugin(EleventyHtmlBasePlugin);
|
||||
eleventyConfig.addPlugin(EleventyRenderPlugin);
|
||||
eleventyConfig.addPlugin(pluginBundle);
|
||||
eleventyConfig.addPlugin(pluginTOC, {
|
||||
tags: ['h2'],
|
||||
wrapper: 'div'
|
||||
});
|
||||
|
||||
// Filters
|
||||
eleventyConfig.addFilter("readableDate", (dateObj, format, zone) => {
|
||||
// Formatting tokens for Luxon: https://moment.github.io/luxon/#/formatting?id=table-of-tokens
|
||||
return DateTime.fromJSDate(dateObj, { zone: zone || "utc" }).toFormat(format || "dd LLLL yyyy");
|
||||
});
|
||||
|
||||
eleventyConfig.addFilter('htmlDateString', (dateObj) => {
|
||||
// dateObj input: https://html.spec.whatwg.org/multipage/common-microsyntaxes.html#valid-date-string
|
||||
return DateTime.fromJSDate(dateObj, {zone: 'utc'}).toFormat('yyyy-LL-dd');
|
||||
});
|
||||
|
||||
// Get the first `n` elements of a collection.
|
||||
eleventyConfig.addFilter("head", (array, n) => {
|
||||
if(!Array.isArray(array) || array.length === 0) {
|
||||
return [];
|
||||
}
|
||||
if( n < 0 ) {
|
||||
return array.slice(n);
|
||||
}
|
||||
|
||||
return array.slice(0, n);
|
||||
});
|
||||
|
||||
// Return the smallest number argument
|
||||
eleventyConfig.addFilter("min", (...numbers) => {
|
||||
return Math.min.apply(null, numbers);
|
||||
});
|
||||
|
||||
// Return all the tags used in a collection
|
||||
eleventyConfig.addFilter("getAllTags", collection => {
|
||||
let tagSet = new Set();
|
||||
for(let item of collection) {
|
||||
(item.data.tags || []).forEach(tag => tagSet.add(tag));
|
||||
}
|
||||
return Array.from(tagSet);
|
||||
});
|
||||
|
||||
eleventyConfig.addFilter("filterTagList", function filterTagList(tags) {
|
||||
return (tags || []).filter(tag => ["all", "nav", "post", "posts"].indexOf(tag) === -1);
|
||||
});
|
||||
|
||||
// Customize Markdown library settings:
|
||||
eleventyConfig.amendLibrary("md", mdLib => {
|
||||
mdLib.use(markdownItAnchor, {
|
||||
permalink: markdownItAnchor.permalink.ariaHidden({
|
||||
placement: "after",
|
||||
class: "header-anchor",
|
||||
symbol: "#",
|
||||
ariaHidden: false,
|
||||
}),
|
||||
level: [1,2,3,4],
|
||||
slugify: eleventyConfig.getFilter("slugify")
|
||||
});
|
||||
});
|
||||
|
||||
// Features to make your build faster (when you need them)
|
||||
|
||||
// If your passthrough copy gets heavy and cumbersome, add this line
|
||||
// to emulate the file copy on the dev server. Learn more:
|
||||
// https://www.11ty.dev/docs/copy/#emulate-passthrough-copy-during-serve
|
||||
|
||||
// eleventyConfig.setServerPassthroughCopyBehavior("passthrough");
|
||||
|
||||
return {
|
||||
// Control which files Eleventy will process
|
||||
// e.g.: *.md, *.njk, *.html, *.liquid
|
||||
templateFormats: [
|
||||
"md",
|
||||
"njk",
|
||||
"html",
|
||||
"liquid",
|
||||
],
|
||||
|
||||
// Pre-process *.md files with: (default: `liquid`)
|
||||
markdownTemplateEngine: "njk",
|
||||
|
||||
// Pre-process *.html files with: (default: `liquid`)
|
||||
htmlTemplateEngine: "njk",
|
||||
|
||||
// These are all optional:
|
||||
dir: {
|
||||
input: "content", // default: "."
|
||||
includes: "../_includes", // default: "_includes"
|
||||
data: "../_data", // default: "_data"
|
||||
output: "_site"
|
||||
},
|
||||
|
||||
// -----------------------------------------------------------------
|
||||
// Optional items:
|
||||
// -----------------------------------------------------------------
|
||||
|
||||
// If your site deploys to a subdirectory, change `pathPrefix`.
|
||||
// Read more: https://www.11ty.dev/docs/config/#deploy-to-a-subdirectory-with-a-path-prefix
|
||||
|
||||
// When paired with the HTML <base> plugin https://www.11ty.dev/docs/plugins/html-base/
|
||||
// it will transform any absolute URLs in your HTML to include this
|
||||
// folder name and does **not** affect where things go in the output folder.
|
||||
pathPrefix: "/",
|
||||
};
|
||||
};
|
1
env.d.ts
vendored
1
env.d.ts
vendored
|
@ -1 +0,0 @@
|
|||
/// <reference types="vite/client" />
|
13
index.html
13
index.html
|
@ -1,13 +0,0 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="fr">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<link rel="icon" href="/favicon.ico">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>Bienvenue sur Pélican</title>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
<script type="module" src="/src/main.ts"></script>
|
||||
</body>
|
||||
</html>
|
5464
package-lock.json
generated
5464
package-lock.json
generated
File diff suppressed because it is too large
Load diff
65
package.json
65
package.json
|
@ -1,39 +1,40 @@
|
|||
{
|
||||
"name": "pelican-jdr",
|
||||
"version": "0.0.0",
|
||||
"private": true,
|
||||
"version": "0.2.0",
|
||||
"description": "Un systeme de jdr sous forme d'un site 11ty",
|
||||
"scripts": {
|
||||
"dev": "vite",
|
||||
"build": "run-p type-check build-only",
|
||||
"preview": "vite preview",
|
||||
"build-only": "vite build",
|
||||
"type-check": "vue-tsc --noEmit",
|
||||
"lint": "eslint . --ext .vue,.js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix --ignore-path .gitignore"
|
||||
"build": "npx @11ty/eleventy",
|
||||
"build-ghpages": "npx @11ty/eleventy --pathprefix=/eleventy-base-blog/",
|
||||
"start": "npx @11ty/eleventy --serve --quiet",
|
||||
"debug": "DEBUG=Eleventy* npx @11ty/eleventy",
|
||||
"debugstart": "DEBUG=Eleventy* npx @11ty/eleventy --serve --quiet",
|
||||
"benchmark": "DEBUG=Eleventy:Benchmark* npx @11ty/eleventy"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "git://git.kobold.cafe/jdr-et-univers/pelicanjdr"
|
||||
},
|
||||
"author": {
|
||||
"name": "Kazhnuz",
|
||||
"email": "kazhnuz@kobold.cafe",
|
||||
"url": "https://kazhnuz.space"
|
||||
},
|
||||
"license": "CC BY-SA",
|
||||
"engines": {
|
||||
"node": ">=14"
|
||||
},
|
||||
"homepage": "https://pelicanjdr.kazhnuz.space",
|
||||
"devDependencies": {
|
||||
"@11ty/eleventy": "^2.0.1",
|
||||
"@11ty/eleventy-img": "^3.1.0",
|
||||
"@11ty/eleventy-navigation": "^0.3.5",
|
||||
"@11ty/eleventy-plugin-bundle": "^1.0.4",
|
||||
"@11ty/eleventy-plugin-rss": "^1.2.0",
|
||||
"@11ty/eleventy-plugin-syntaxhighlight": "^5.0.0",
|
||||
"luxon": "^3.3.0",
|
||||
"markdown-it-anchor": "^8.6.7"
|
||||
},
|
||||
"dependencies": {
|
||||
"@types/lodash": "^4.14.191",
|
||||
"@types/marked": "^4.0.8",
|
||||
"axios": "^1.3.2",
|
||||
"lodash": "^4.17.21",
|
||||
"marked": "^4.2.12",
|
||||
"pinia": "^2.0.28",
|
||||
"sass": "^1.58.0",
|
||||
"vue": "^3.2.45",
|
||||
"vue-router": "^4.1.6"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@rushstack/eslint-patch": "^1.1.4",
|
||||
"@types/node": "^18.11.12",
|
||||
"@vitejs/plugin-vue": "^4.0.0",
|
||||
"@vue/eslint-config-prettier": "^7.0.0",
|
||||
"@vue/eslint-config-typescript": "^11.0.0",
|
||||
"@vue/tsconfig": "^0.1.3",
|
||||
"eslint": "^8.22.0",
|
||||
"eslint-plugin-vue": "^9.3.0",
|
||||
"npm-run-all": "^4.1.5",
|
||||
"prettier": "^2.7.1",
|
||||
"typescript": "~4.7.4",
|
||||
"vite": "^4.0.0",
|
||||
"vue-tsc": "^1.0.12"
|
||||
"eleventy-plugin-toc": "^1.1.5"
|
||||
}
|
||||
}
|
||||
|
|
412
public/css/index.css
Normal file
412
public/css/index.css
Normal file
|
@ -0,0 +1,412 @@
|
|||
:root {
|
||||
--color-gray-20: #e0e0e0;
|
||||
--color-gray-50: #C0C0C0;
|
||||
--color-gray-90: #002b36;
|
||||
--sidebar-width: 280px;
|
||||
--main-width: 800px;
|
||||
|
||||
/* --text-color is assigned to --color-gray-_ above */
|
||||
--text-color-link: #4c2512;
|
||||
--text-color-link-active: #4c2512;
|
||||
--text-color-link-visited: #4c2512;
|
||||
--text-color-title: #66350F;
|
||||
|
||||
--background-color: #FDF7E7;
|
||||
--background-menu: #002b36;
|
||||
|
||||
--text-color: var(--color-gray-90);
|
||||
|
||||
--font-family: Inter,
|
||||
-apple-system,
|
||||
BlinkMacSystemFont,
|
||||
'Segoe UI',
|
||||
Cantarell,
|
||||
Roboto,
|
||||
Oxygen,
|
||||
Ubuntu,
|
||||
'Fira Sans',
|
||||
'Droid Sans',
|
||||
'Helvetica Neue',
|
||||
sans-serif;
|
||||
--font-family-monospace: Consolas, Menlo, Monaco, Andale Mono WT, Andale Mono, Lucida Console, Lucida Sans Typewriter, DejaVu Sans Mono, Bitstream Vera Sans Mono, Liberation Mono, Nimbus Mono L, Courier New, Courier, monospace;
|
||||
--font-family-logo: serif;
|
||||
--font-family-title:serif;
|
||||
}
|
||||
|
||||
* {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
html,
|
||||
body {
|
||||
margin: 0 auto;
|
||||
min-height:100%;
|
||||
font-family: var(--font-family);
|
||||
color: var(--text-color);
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
body {
|
||||
padding: 24px;
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
max-width: var(--main-width);
|
||||
margin: auto;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
html {
|
||||
overflow-y: scroll;
|
||||
background-color: var(--background-color);
|
||||
}
|
||||
|
||||
/* https://www.a11yproject.com/posts/how-to-hide-content/ */
|
||||
.visually-hidden {
|
||||
clip: rect(0 0 0 0);
|
||||
clip-path: inset(50%);
|
||||
height: 1px;
|
||||
overflow: hidden;
|
||||
position: absolute;
|
||||
white-space: nowrap;
|
||||
width: 1px;
|
||||
}
|
||||
|
||||
a[href] {
|
||||
color: var(--text-color-link);
|
||||
text-decoration: underline dashed 1px;
|
||||
border-radius: 0.1rem;
|
||||
text-decoration: underline dashed 1px;
|
||||
text-underline-offset: 0.1rem;
|
||||
}
|
||||
a[href]:visited {
|
||||
color: var(--text-color-link-visited);
|
||||
}
|
||||
a[href]:hover,
|
||||
a[href]:active {
|
||||
color: var(--text-color-link-active);
|
||||
background-color: rgba(0,0,0,0.1);
|
||||
text-decoration: none;
|
||||
}
|
||||
|
||||
blockquote {
|
||||
opacity: 75%;
|
||||
border-left: 3px solid currentColor;
|
||||
padding-left: 12px;
|
||||
}
|
||||
|
||||
/* Direct Links / Markdown Headers */
|
||||
.header-anchor {
|
||||
text-decoration: none;
|
||||
font-style: normal;
|
||||
font-size: 1em;
|
||||
margin-left: .1em;
|
||||
}
|
||||
a[href].header-anchor,
|
||||
a[href].header-anchor:visited {
|
||||
color: transparent;
|
||||
}
|
||||
a[href].header-anchor:focus,
|
||||
a[href].header-anchor:hover {
|
||||
text-decoration: underline;
|
||||
}
|
||||
a[href].header-anchor:focus,
|
||||
:hover > a[href].header-anchor {
|
||||
color: #aaa;
|
||||
}
|
||||
|
||||
header {
|
||||
background:center center url("/img/back.jpg");
|
||||
background-repeat: no-repeat;
|
||||
background-size: cover;
|
||||
border-radius:3px;
|
||||
height:240px;
|
||||
box-shadow: 0px 1px 3px 0px rgba(0, 0, 0, 0.8);
|
||||
display:flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
h1 {
|
||||
color: var(--text-color-title);
|
||||
font-family: var(--font-family-title);
|
||||
font-size: 3rem;
|
||||
line-height: 1;
|
||||
}
|
||||
|
||||
header h1 {
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
header h1 a[href] {
|
||||
font-size:5.5rem;
|
||||
text-shadow: -2px -2px 0 #000,
|
||||
0 -2px 0 #000,
|
||||
2px -2px 0 #000,
|
||||
2px 0 0 #000,
|
||||
2px 2px 0 #000,
|
||||
0 2px 0 #000,
|
||||
-2px 2px 0 #000,
|
||||
-2px 0 0 #000,
|
||||
.05em .1em 0 #000;
|
||||
font-weight: 900;
|
||||
color:white!important;
|
||||
text-decoration: none;
|
||||
text-transform: uppercase;
|
||||
display: block;
|
||||
line-height: 1;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
.quadrillage {
|
||||
display:grid;
|
||||
grid-template-columns : 1fr 1fr;
|
||||
column-gap: 1rem;
|
||||
}
|
||||
|
||||
#sidebar {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
border-right: 1px solid black;
|
||||
background-color: var(--background-menu);
|
||||
padding:12px;
|
||||
height:100%;
|
||||
box-shadow: 1px 0px 1px 0px rgba(0,0,0,0.4);
|
||||
}
|
||||
|
||||
#sidebar.shown {
|
||||
left: 0;
|
||||
}
|
||||
|
||||
#sidebar > ul > li {
|
||||
margin:0;
|
||||
padding:3px;
|
||||
}
|
||||
|
||||
main {
|
||||
line-height:1.5rem;
|
||||
margin: auto;
|
||||
}
|
||||
|
||||
main img {
|
||||
display: block;
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
margin: auto;
|
||||
}
|
||||
|
||||
.card,
|
||||
#sidebar ul>li,
|
||||
#links ul>li {
|
||||
background-color: var(--background-menu);
|
||||
}
|
||||
|
||||
#sidebar ul > li,
|
||||
#links ul > li {
|
||||
list-style: none;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
|
||||
#more-info ol > li,
|
||||
#more-info ul > li {
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
#sidebar ul > li li,
|
||||
#links ul>li li,
|
||||
#more-info li {
|
||||
border-radius:0px;
|
||||
padding:0px;
|
||||
margin:0px;
|
||||
font-weight: normal;
|
||||
border:0;
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
ul.nav,
|
||||
#sidebar ul li ul,
|
||||
#links ul li ul,
|
||||
#more-info ol {
|
||||
padding:0;
|
||||
margin:0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
#sidebar ul li a,
|
||||
#more-info ol li a {
|
||||
display:block;
|
||||
width:100%;
|
||||
text-decoration:dashed;
|
||||
color: white;
|
||||
border-radius:3px;
|
||||
padding:6px;
|
||||
}
|
||||
|
||||
#more-info ol li a {
|
||||
color: var(--text-color);
|
||||
}
|
||||
|
||||
#links ul li > p {
|
||||
padding: 3px;
|
||||
margin:0;
|
||||
}
|
||||
|
||||
#more-info h2 {
|
||||
padding: 3px;
|
||||
margin: 0;
|
||||
font-size: 1rem;
|
||||
}
|
||||
|
||||
#sidebar ul li li a,
|
||||
#links ul li li a,
|
||||
#more-info ol li a {
|
||||
padding-left:18px;
|
||||
}
|
||||
|
||||
#sidebar ul li a.active,
|
||||
#sidebar ul li a:hover {
|
||||
background-color: rgba(255, 255, 255, 0.3);
|
||||
}
|
||||
|
||||
|
||||
#more-info ol li a:hover,
|
||||
#more-info ol li a.active {
|
||||
background-color:rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
aside {
|
||||
position: absolute;
|
||||
top: 1px;
|
||||
right: -264px;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
#more-info {
|
||||
position: sticky;
|
||||
top:12px;
|
||||
border-left: 3px solid var(--text-color-title);
|
||||
padding: 6px;
|
||||
}
|
||||
|
||||
#sidebar {
|
||||
min-width:var(--sidebar-width);
|
||||
width:var(--sidebar-width);
|
||||
z-index:10;
|
||||
}
|
||||
|
||||
#more-info {
|
||||
min-width: 240px;
|
||||
width: 240px;
|
||||
}
|
||||
|
||||
footer {
|
||||
text-align:right;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
iframe {
|
||||
border: none;
|
||||
}
|
||||
|
||||
.menu-button {
|
||||
display: none;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1400px) {
|
||||
.wrapper {
|
||||
margin-left: var(--sidebar-width);
|
||||
position: relative;
|
||||
}
|
||||
|
||||
aside {
|
||||
position: static !important;
|
||||
}
|
||||
|
||||
#more-info {
|
||||
position: static;
|
||||
border-left: 3px solid #e03131;
|
||||
padding: 6px;
|
||||
}
|
||||
}
|
||||
|
||||
.d-none {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.icon {
|
||||
display: inline-block;
|
||||
width: 1em;
|
||||
height: 1em;
|
||||
stroke-width: 0;
|
||||
stroke: currentColor;
|
||||
fill: currentColor;
|
||||
color: currentColor;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.sr-only {
|
||||
position: absolute;
|
||||
width: 1px;
|
||||
height: 1px;
|
||||
padding: 0;
|
||||
margin: -1px;
|
||||
overflow: hidden;
|
||||
clip: rect(0, 0, 0, 0);
|
||||
border: 0;
|
||||
opacity: 0;
|
||||
transition-delay: .8s;
|
||||
transition-property: opacity;
|
||||
transition-duration: 0.2s;
|
||||
}
|
||||
|
||||
@media screen and (max-width: 1000px) {
|
||||
#sidebar {
|
||||
left: calc(-1* var(--sidebar-width));
|
||||
}
|
||||
|
||||
.wrapper {
|
||||
margin: .5rem;
|
||||
}
|
||||
|
||||
.menu-button {
|
||||
position: fixed;
|
||||
bottom: 24px;
|
||||
right: 24px;
|
||||
background-color: rgba(0, 0, 0, 0.4);
|
||||
color: white;
|
||||
padding: 0.75em;
|
||||
border: none;
|
||||
font-size: 1.2rem;
|
||||
display: flex;
|
||||
align-content: center;
|
||||
justify-content: center;
|
||||
aspect-ratio: 1;
|
||||
border-radius: 999px;
|
||||
z-index: 12;
|
||||
}
|
||||
|
||||
.menu-button:hover {
|
||||
background-color: var(--text-color-link);
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 600px) {
|
||||
header h1 a[href] {
|
||||
font-size: 5rem;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 460px) {
|
||||
header h1 a[href] {
|
||||
font-size: 4.5rem;
|
||||
}
|
||||
}
|
||||
|
||||
@media screen and (max-width: 390px) {
|
||||
header h1 a[href] {
|
||||
font-size: 4rem;
|
||||
}
|
||||
}
|
10
public/js/mobile-sidebar.js
Normal file
10
public/js/mobile-sidebar.js
Normal file
|
@ -0,0 +1,10 @@
|
|||
document.getElementById('mobile-button').addEventListener('click', function () {
|
||||
const sidebar = document.getElementById('sidebar');
|
||||
if (!sidebar.classList.contains('shown')) {
|
||||
sidebar.classList.remove('hidden');
|
||||
sidebar.classList.add('shown');
|
||||
} else {
|
||||
sidebar.classList.remove('shown');
|
||||
sidebar.classList.add('hidden');
|
||||
}
|
||||
});
|
32
src/App.vue
32
src/App.vue
|
@ -1,32 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { RouterView } from "vue-router";
|
||||
import TopBar from "./components/layout/TopBar.vue";
|
||||
import SideBar from "./components/layout/SideBar.vue";
|
||||
import TableOfContent from "./components/layout/TableOfContent.vue";
|
||||
import { useConfigStore } from "./stores/config";
|
||||
import { onMounted, ref } from "vue";
|
||||
import axios from "axios";
|
||||
|
||||
const store = useConfigStore();
|
||||
const loaded = ref(false);
|
||||
|
||||
onMounted(() => {
|
||||
axios.get(`/pelican.json`).then((response) => {
|
||||
store.setConfig(response.data);
|
||||
loaded.value = true;
|
||||
});
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<TopBar id="topbar" />
|
||||
<div id="wrapper">
|
||||
<SideBar />
|
||||
<div id="page">
|
||||
<div id="content" class="pt-1">
|
||||
<RouterView v-if="loaded" />
|
||||
</div>
|
||||
</div>
|
||||
<TableOfContent />
|
||||
</div>
|
||||
</template>
|
|
@ -1,74 +0,0 @@
|
|||
/* color palette from <https://github.com/vuejs/theme> */
|
||||
:root {
|
||||
--vt-c-white: #ffffff;
|
||||
--vt-c-white-soft: #f8f8f8;
|
||||
--vt-c-white-mute: #f2f2f2;
|
||||
|
||||
--vt-c-black: #181818;
|
||||
--vt-c-black-soft: #222222;
|
||||
--vt-c-black-mute: #282828;
|
||||
|
||||
--vt-c-indigo: #2c3e50;
|
||||
|
||||
--vt-c-divider-light-1: rgba(60, 60, 60, 0.29);
|
||||
--vt-c-divider-light-2: rgba(60, 60, 60, 0.12);
|
||||
--vt-c-divider-dark-1: rgba(84, 84, 84, 0.65);
|
||||
--vt-c-divider-dark-2: rgba(84, 84, 84, 0.48);
|
||||
|
||||
--vt-c-text-light-1: var(--vt-c-indigo);
|
||||
--vt-c-text-light-2: rgba(60, 60, 60, 0.66);
|
||||
--vt-c-text-dark-1: var(--vt-c-white);
|
||||
--vt-c-text-dark-2: rgba(235, 235, 235, 0.64);
|
||||
}
|
||||
|
||||
/* semantic color variables for this project */
|
||||
:root {
|
||||
--color-background: var(--vt-c-white);
|
||||
--color-background-soft: var(--vt-c-white-soft);
|
||||
--color-background-mute: var(--vt-c-white-mute);
|
||||
|
||||
--color-border: var(--vt-c-divider-light-2);
|
||||
--color-border-hover: var(--vt-c-divider-light-1);
|
||||
|
||||
--color-heading: var(--vt-c-text-light-1);
|
||||
--color-text: var(--vt-c-text-light-1);
|
||||
|
||||
--section-gap: 160px;
|
||||
}
|
||||
|
||||
@media (prefers-color-scheme: dark) {
|
||||
:root {
|
||||
--color-background: var(--vt-c-black);
|
||||
--color-background-soft: var(--vt-c-black-soft);
|
||||
--color-background-mute: var(--vt-c-black-mute);
|
||||
|
||||
--color-border: var(--vt-c-divider-dark-2);
|
||||
--color-border-hover: var(--vt-c-divider-dark-1);
|
||||
|
||||
--color-heading: var(--vt-c-text-dark-1);
|
||||
--color-text: var(--vt-c-text-dark-2);
|
||||
}
|
||||
}
|
||||
|
||||
*,
|
||||
*::before,
|
||||
*::after {
|
||||
box-sizing: border-box;
|
||||
margin: 0;
|
||||
position: relative;
|
||||
font-weight: normal;
|
||||
}
|
||||
|
||||
body {
|
||||
min-height: 100vh;
|
||||
color: var(--color-text);
|
||||
background: var(--color-background);
|
||||
transition: color 0.5s, background-color 0.5s;
|
||||
line-height: 1.6;
|
||||
font-family: Inter, -apple-system, BlinkMacSystemFont, 'Segoe UI', Roboto, Oxygen, Ubuntu,
|
||||
Cantarell, 'Fira Sans', 'Droid Sans', 'Helvetica Neue', sans-serif;
|
||||
font-size: 15px;
|
||||
text-rendering: optimizeLegibility;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
|
@ -1 +0,0 @@
|
|||
<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 261.76 226.69" xmlns:v="https://vecta.io/nano"><path d="M161.096.001l-30.225 52.351L100.647.001H-.005l130.877 226.688L261.749.001z" fill="#41b883"/><path d="M161.096.001l-30.225 52.351L100.647.001H52.346l78.526 136.01L209.398.001z" fill="#34495e"/></svg>
|
Before Width: | Height: | Size: 308 B |
|
@ -1,35 +0,0 @@
|
|||
@import './base.css';
|
||||
|
||||
#app {
|
||||
max-width: 1280px;
|
||||
margin: 0 auto;
|
||||
padding: 2rem;
|
||||
|
||||
font-weight: normal;
|
||||
}
|
||||
|
||||
a,
|
||||
.green {
|
||||
text-decoration: none;
|
||||
color: hsla(160, 100%, 37%, 1);
|
||||
transition: 0.4s;
|
||||
}
|
||||
|
||||
@media (hover: hover) {
|
||||
a:hover {
|
||||
background-color: hsla(160, 100%, 37%, 0.2);
|
||||
}
|
||||
}
|
||||
|
||||
@media (min-width: 1024px) {
|
||||
body {
|
||||
display: flex;
|
||||
place-items: center;
|
||||
}
|
||||
|
||||
#app {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr 1fr;
|
||||
padding: 0 2rem;
|
||||
}
|
||||
}
|
|
@ -1,52 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted, onBeforeUpdate } from "vue";
|
||||
|
||||
import axios from "axios";
|
||||
import MarkdownRender from "./markdown/MarkdownRender.vue";
|
||||
|
||||
const props = defineProps<{
|
||||
path: string;
|
||||
order?: number;
|
||||
}>();
|
||||
|
||||
const loadedPage = ref("");
|
||||
const markdown = ref("");
|
||||
|
||||
function refresh() {
|
||||
const markdownFileUrl = `/${props.path}.md`;
|
||||
if (loadedPage.value === markdownFileUrl) {
|
||||
return;
|
||||
}
|
||||
loadedPage.value = markdownFileUrl;
|
||||
console.log(`Chargement de l'URL ${markdownFileUrl}`);
|
||||
axios
|
||||
.get(markdownFileUrl)
|
||||
.then((response) => {
|
||||
markdown.value = response.data;
|
||||
})
|
||||
.catch(
|
||||
() =>
|
||||
(markdown.value =
|
||||
"# 404 Not Found \n \n La page recherchée n'a pas pu être trouvée")
|
||||
);
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
refresh();
|
||||
});
|
||||
|
||||
onBeforeUpdate(() => {
|
||||
refresh();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<article>
|
||||
<MarkdownRender
|
||||
:markdown="markdown"
|
||||
:order="order"
|
||||
v-if="markdown !== ''"
|
||||
></MarkdownRender>
|
||||
<slot></slot>
|
||||
</article>
|
||||
</template>
|
|
@ -1,36 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { useConfigStore } from "@/stores/config";
|
||||
import { computed } from "vue";
|
||||
|
||||
const store = useConfigStore();
|
||||
|
||||
const sidebar = computed(() => {
|
||||
return store.getSidebar() ?? [{ title: "", id: 0, links: [] }];
|
||||
});
|
||||
|
||||
const linkBase = computed(() => {
|
||||
if (store.isJdrLoaded()) {
|
||||
return `jdr/${store.currentJdr}`;
|
||||
} else {
|
||||
return `jdr`;
|
||||
}
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<aside id="sidebar" class="bg-dark fg-light menu">
|
||||
<h1 class="title-5 fg-light">Navigation</h1>
|
||||
<ul v-for="item in sidebar" :key="item.id">
|
||||
<div class="menu-divider" v-if="item.title">{{ item.title }}</div>
|
||||
<li v-for="(link, index) in item.links" :key="index">
|
||||
<router-link
|
||||
:to="`/${linkBase}/${link.path}`"
|
||||
class="menu-item"
|
||||
:replace="true"
|
||||
v-if="!link.isHidden"
|
||||
>{{ link.title }}</router-link
|
||||
>
|
||||
</li>
|
||||
</ul>
|
||||
</aside>
|
||||
</template>
|
|
@ -1,22 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { useTocStore } from "../../stores/toc";
|
||||
import { computed } from "vue";
|
||||
|
||||
const toc = useTocStore();
|
||||
const tocList = computed(() => {
|
||||
return toc.getToc();
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="card" id="toc" v-if="tocList.length > 1">
|
||||
<div class="card-header bg-primary">Sommaire</div>
|
||||
<ul class="menu fg-dark">
|
||||
<li v-for="(tocLine, index) in tocList" :key="index">
|
||||
<router-link :to="`#${tocLine.anchor}`"
|
||||
><span v-html="tocLine.text"></span
|
||||
></router-link>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</template>
|
|
@ -1,27 +0,0 @@
|
|||
<template>
|
||||
<header class="bg-primary" id="topbar">
|
||||
<div class="menu toolbar fg-light d-block d-flex-sm">
|
||||
<ul>
|
||||
<li><router-link to="/" class="menu-item">Home</router-link></li>
|
||||
<li>
|
||||
<router-link to="/about" class="menu-item">À propos</router-link>
|
||||
</li>
|
||||
</ul>
|
||||
<ul class="f-end">
|
||||
<li>
|
||||
<router-link to="/fiches" class="menu-item">Fiches</router-link>
|
||||
</li>
|
||||
<li>
|
||||
<a
|
||||
href="https://git.kobold.cafe/pelican/pelican-jdr"
|
||||
class="menu-item"
|
||||
>Sources</a
|
||||
>
|
||||
</li>
|
||||
<li>
|
||||
<a href="https://kazhnuz.space" class="menu-item">Retour</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</header>
|
||||
</template>
|
|
@ -1,122 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { ref, onMounted, onBeforeUpdate, watch } from "vue";
|
||||
import { marked } from "marked";
|
||||
import { useTocStore } from "../../stores/toc";
|
||||
|
||||
import { useRoute } from "vue-router";
|
||||
import { useConfigStore } from "@/stores/config";
|
||||
|
||||
const props = defineProps<{
|
||||
markdown: string;
|
||||
order?: number;
|
||||
}>();
|
||||
|
||||
const htmlContent = ref("");
|
||||
|
||||
var specialQuote: Map<string, { class: string; text: string }> = new Map();
|
||||
specialQuote.set("NOTE", { class: "info", text: "Information :" });
|
||||
specialQuote.set("SUCCESS", { class: "success", text: "Success :" });
|
||||
specialQuote.set("WARNING", { class: "warning", text: "Warning :" });
|
||||
specialQuote.set("DANGER", { class: "danger", text: "Danger :" });
|
||||
|
||||
var renderer = new marked.Renderer();
|
||||
|
||||
const toc = useTocStore();
|
||||
const config = useConfigStore();
|
||||
const route = useRoute();
|
||||
var tocNbr = 1;
|
||||
|
||||
renderer.heading = function (text, level, raw) {
|
||||
var anchor = "#" + raw.toLowerCase().replace(/[^\w]+/g, "-");
|
||||
if (level === 2) {
|
||||
toc.addTocLine(route.path, {
|
||||
anchor: anchor,
|
||||
order: (props.order ?? 1) * 100 + tocNbr,
|
||||
text: text,
|
||||
});
|
||||
tocNbr++;
|
||||
}
|
||||
return `<h${level} id="${anchor}">${text}</h${level}>\n`;
|
||||
};
|
||||
|
||||
renderer.blockquote = function (quote) {
|
||||
var bqClass = "";
|
||||
var newQuote = quote;
|
||||
for (const [key, quoteData] of specialQuote) {
|
||||
if (quote.includes(`[!${key}]`)) {
|
||||
bqClass = `bg-${quoteData?.class}`;
|
||||
newQuote = newQuote.replace(
|
||||
`[!${key}]`,
|
||||
`<strong>${quoteData?.text}</strong>`
|
||||
);
|
||||
}
|
||||
}
|
||||
newQuote = newQuote.replace("\n", "<br />");
|
||||
return `<blockquote class="${bqClass}">${newQuote}</blockquote>`;
|
||||
};
|
||||
|
||||
const variable = {
|
||||
name: "variable",
|
||||
level: "inline", // Is this a block-level or inline-level tokenizer?
|
||||
start(src: string) {
|
||||
return src.match(/{{/)?.index;
|
||||
}, // Hint to Marked.js to stop and check for a match
|
||||
tokenizer(
|
||||
src: string
|
||||
): { type: string; raw: string; [index: string]: any } | undefined {
|
||||
const rule = /\{\{([A-Za-z0-9_]+)\}\}/; // Regex for the complete token, anchor to string start
|
||||
const match = rule.exec(src);
|
||||
if (match) {
|
||||
return {
|
||||
// Token to generate
|
||||
type: "variable", // Should match "name" above
|
||||
raw: match[0], // Text to consume from the source
|
||||
["varName"]: match[1],
|
||||
};
|
||||
}
|
||||
},
|
||||
renderer(token: { type: string; raw: string; [index: string]: any }): string {
|
||||
const varName = token["varName"] as string | null;
|
||||
const value = `${config.getVar(varName ?? "")}`;
|
||||
return value;
|
||||
},
|
||||
};
|
||||
|
||||
marked.setOptions({
|
||||
renderer: renderer,
|
||||
});
|
||||
marked.use({ extensions: [variable] });
|
||||
|
||||
function render() {
|
||||
tocNbr = 1;
|
||||
if (htmlContent.value === "") {
|
||||
htmlContent.value = marked.parse(props.markdown);
|
||||
}
|
||||
}
|
||||
|
||||
function forceRender(markdown: string) {
|
||||
htmlContent.value = marked.parse(markdown);
|
||||
}
|
||||
|
||||
onMounted(() => {
|
||||
render();
|
||||
});
|
||||
|
||||
onBeforeUpdate(() => {
|
||||
render();
|
||||
});
|
||||
|
||||
watch(
|
||||
() => props.markdown,
|
||||
(newMd) => {
|
||||
forceRender(newMd);
|
||||
}
|
||||
);
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<article>
|
||||
<div v-html="htmlContent" class="markdown"></div>
|
||||
<slot></slot>
|
||||
</article>
|
||||
</template>
|
|
@ -1,50 +0,0 @@
|
|||
<script lang="ts" setup>
|
||||
import { ref, onMounted } from "vue";
|
||||
import type { TableField, TableItem } from "@/utils/tables/types";
|
||||
import type { PropType } from "vue";
|
||||
import axios from "axios";
|
||||
import TableRenderer from "./TableRenderer.vue";
|
||||
|
||||
const props = defineProps({
|
||||
fields: {
|
||||
type: Array as PropType<TableField[]>,
|
||||
default: () => [],
|
||||
},
|
||||
files: {
|
||||
type: Array as PropType<string[]>,
|
||||
default: () => [],
|
||||
},
|
||||
category: {
|
||||
type: String,
|
||||
default: "",
|
||||
},
|
||||
});
|
||||
|
||||
const toLoad = ref(1);
|
||||
const items = ref([] as TableItem[]);
|
||||
|
||||
onMounted(() => {
|
||||
setTimeout(() => {
|
||||
refresh();
|
||||
}, 100);
|
||||
});
|
||||
|
||||
function refresh() {
|
||||
toLoad.value = props.files.length;
|
||||
for (const file of props.files) {
|
||||
const listItems = `/jdr/${props.category}/${file}.json`;
|
||||
axios.get(listItems).then((response) => {
|
||||
toLoad.value = toLoad.value - 1;
|
||||
items.value = items.value.concat(response.data);
|
||||
});
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<TableRenderer
|
||||
:fields="fields"
|
||||
:items="items"
|
||||
v-if="toLoad === 0"
|
||||
></TableRenderer>
|
||||
</template>
|
|
@ -1,141 +0,0 @@
|
|||
<script lang="ts" setup>
|
||||
import { computed, reactive, onMounted } from "vue";
|
||||
import PaginatedFilteredTable from "@/utils/tables/PaginatedFilteredTable";
|
||||
import type { TableField, TableItem } from "@/utils/tables/types";
|
||||
import type { PropType } from "vue";
|
||||
import PageList from "./pagination/PageList.vue";
|
||||
import TagList from "./TagList.vue";
|
||||
|
||||
const props = defineProps({
|
||||
fields: {
|
||||
type: Array as PropType<TableField[]>,
|
||||
default: () => [],
|
||||
},
|
||||
items: {
|
||||
type: Array as PropType<TableItem[]>,
|
||||
default: () => [],
|
||||
},
|
||||
});
|
||||
|
||||
const DEFAULT_MAX_ITEM_BY_PAGE = 10;
|
||||
|
||||
const table = reactive(new PaginatedFilteredTable(DEFAULT_MAX_ITEM_BY_PAGE));
|
||||
|
||||
const filtersFieldMap = computed(() => {
|
||||
return table?.filteredTable?.filtersFieldMap;
|
||||
});
|
||||
|
||||
const displayedFieldKeys = computed(() => {
|
||||
return table?.filteredTable?.table.displayedFieldKeys;
|
||||
});
|
||||
|
||||
const paginatedList = computed(() => {
|
||||
return table?.items;
|
||||
});
|
||||
|
||||
onMounted(() => {
|
||||
table.fields = props.fields;
|
||||
table.addItems(props.items);
|
||||
table.currentPage = 0;
|
||||
});
|
||||
|
||||
function switchFilter(filterSet: string | number, filterName: string | number) {
|
||||
table.switchFilter(filterSet as string, filterName as string);
|
||||
}
|
||||
|
||||
function removeFilter(filterSet: string | number) {
|
||||
table.removeAllFilters(filterSet as string);
|
||||
}
|
||||
|
||||
const currentPage = computed(() => {
|
||||
return table?.currentPage;
|
||||
});
|
||||
|
||||
const getTotalPage = computed(() => {
|
||||
return table?.pageNumber;
|
||||
});
|
||||
|
||||
function goTo(page: number) {
|
||||
table.currentPage = page - 1;
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="d-flex f-between">
|
||||
<div>
|
||||
<input
|
||||
v-model="table.textSearch"
|
||||
class="btn-small"
|
||||
placeholder="Rechercher"
|
||||
/>
|
||||
</div>
|
||||
<div class="d-flex f-end">
|
||||
<TagList
|
||||
:filtersFieldMap="filtersFieldMap"
|
||||
@remove-filter="removeFilter"
|
||||
@switch-filter="switchFilter"
|
||||
></TagList>
|
||||
</div>
|
||||
</div>
|
||||
<table class="mb-0 table-auto">
|
||||
<thead>
|
||||
<tr>
|
||||
<th v-for="field in fields" :key="field.key">
|
||||
{{ field.label }}
|
||||
</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
<tr v-for="(item, index) of paginatedList" :key="index">
|
||||
<td v-for="(key, index2) in displayedFieldKeys" :key="index2">
|
||||
{{ item[key] }}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="d-flex f-between">
|
||||
<div>
|
||||
<span>Lignes par page </span>
|
||||
<select
|
||||
class="btn-small btn-outline"
|
||||
v-model.number="table.pageLenght"
|
||||
@change="table.currentPage = 0"
|
||||
>
|
||||
<option>5</option>
|
||||
<option>10</option>
|
||||
<option>15</option>
|
||||
<option>25</option>
|
||||
<option>50</option>
|
||||
</select>
|
||||
</div>
|
||||
<PageList
|
||||
:current-page="currentPage + 1"
|
||||
:page-nbr="getTotalPage + 1"
|
||||
@set-page="goTo"
|
||||
></PageList>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.small-text {
|
||||
font-size: 0.8rem;
|
||||
padding-bottom: 0.5rem;
|
||||
}
|
||||
|
||||
table:not(:last-child) {
|
||||
font-size: 0.8rem;
|
||||
margin-bottom: 0.5rem;
|
||||
}
|
||||
|
||||
.pages {
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
input,
|
||||
.btn-outline {
|
||||
border: 1px solid rgba(0, 0, 0, 0.2);
|
||||
margin-bottom: 0.5rem;
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
}
|
||||
</style>
|
|
@ -1,112 +0,0 @@
|
|||
<script lang="ts" setup>
|
||||
import type { FilterFieldsMap } from "@/utils/tables/types";
|
||||
import { ref, defineProps, computed } from "vue";
|
||||
|
||||
const props = defineProps<{
|
||||
filtersFieldMap: FilterFieldsMap;
|
||||
}>();
|
||||
|
||||
const emit = defineEmits(["switchFilter", "removeFilter"]);
|
||||
|
||||
const computedFieldMap = computed(() => {
|
||||
return props.filtersFieldMap ?? [];
|
||||
});
|
||||
|
||||
const haveElement = computed(() => {
|
||||
// eslint-disable-next-line @typescript-eslint/no-unused-vars
|
||||
for (const _key in props.filtersFieldMap) {
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
});
|
||||
|
||||
const tagNumber = computed(() => {
|
||||
var i = 0;
|
||||
for (const key in props.filtersFieldMap) {
|
||||
const filters = props.filtersFieldMap[key].filters;
|
||||
for (const key2 in filters) {
|
||||
if (filters[key2] === true) {
|
||||
i++;
|
||||
}
|
||||
}
|
||||
}
|
||||
return i;
|
||||
});
|
||||
|
||||
const showPopover = ref(false);
|
||||
|
||||
function switchFilter(filterSet: string | number, filterName: string | number) {
|
||||
emit("switchFilter", filterSet as string, filterName as string);
|
||||
}
|
||||
|
||||
function removeFilter(filterSet: string | number) {
|
||||
emit("removeFilter", filterSet as string);
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div class="taglist" v-if="haveElement">
|
||||
<button class="btn-small btn-outline" @click="showPopover = !showPopover">
|
||||
<strong>Tags</strong>
|
||||
<span
|
||||
class="badge pills"
|
||||
:class="{ 'bg-grey': tagNumber <= 0, 'bg-secondary': tagNumber > 0 }"
|
||||
>{{ tagNumber }} tag(s)</span
|
||||
>
|
||||
</button>
|
||||
<div class="card menu fg-dark" v-if="showPopover">
|
||||
<div
|
||||
class="small-text"
|
||||
v-for="(filter, key) in computedFieldMap"
|
||||
:key="key"
|
||||
>
|
||||
<p class="m-0 p-0">
|
||||
<strong>{{ filter.title }} : </strong>
|
||||
</p>
|
||||
<div>
|
||||
<button
|
||||
v-for="(isTrue, filterName) in filter.filters"
|
||||
:key="filterName"
|
||||
class="btn-small mb-0"
|
||||
:class="{ 'btn-grey': !isTrue, 'btn-primary': isTrue }"
|
||||
@click="switchFilter(key, filterName)"
|
||||
>
|
||||
{{ filterName }}
|
||||
</button>
|
||||
<button class="btn-small btn-danger mb-0" @click="removeFilter(key)">
|
||||
Vider filtres
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.taglist {
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.card {
|
||||
position: absolute;
|
||||
width: 480px;
|
||||
box-shadow: 0px 1px 1px 1px rgba(0, 0, 0, 0.3);
|
||||
background-color: white;
|
||||
right: 0;
|
||||
}
|
||||
|
||||
.btn-outline {
|
||||
border: 1px solid rgba(0, 0, 0, 0.2);
|
||||
&:hover {
|
||||
background-color: rgba(0, 0, 0, 0.05);
|
||||
}
|
||||
margin-bottom: 0.5rem;
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
}
|
||||
|
||||
.badge {
|
||||
font-size: 0.8em;
|
||||
border-radius: 999px;
|
||||
}
|
||||
</style>
|
|
@ -1,22 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { computed } from "vue";
|
||||
|
||||
const props = defineProps<{
|
||||
page: number;
|
||||
currentPage: number;
|
||||
}>();
|
||||
|
||||
const isPage = computed(() => {
|
||||
return props.page === props.currentPage;
|
||||
});
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<button
|
||||
class="btn-small btn-pagination"
|
||||
:class="{ 'btn-secondary': !isPage, 'bg-primary': isPage }"
|
||||
:disabled="isPage"
|
||||
>
|
||||
{{ page }}
|
||||
</button>
|
||||
</template>
|
|
@ -1,161 +0,0 @@
|
|||
<script setup lang="ts">
|
||||
import { computed } from "vue";
|
||||
import PageButton from "./PageButton.vue";
|
||||
|
||||
const PAGE_NUMBER = 7;
|
||||
|
||||
const props = defineProps<{
|
||||
pageNbr: number;
|
||||
currentPage: number;
|
||||
}>();
|
||||
|
||||
const emit = defineEmits(["setPage"]);
|
||||
|
||||
const pageToDraw = computed(() => {
|
||||
return Math.min(props.pageNbr, PAGE_NUMBER);
|
||||
});
|
||||
|
||||
const isAtStart = computed(() => {
|
||||
return props.currentPage < 4;
|
||||
});
|
||||
|
||||
const isAtEnd = computed(() => {
|
||||
return props.currentPage > props.pageNbr - 2;
|
||||
});
|
||||
|
||||
function setPage(page: number) {
|
||||
emit("setPage", page);
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<div>
|
||||
<button
|
||||
class="btn-small btn-navig"
|
||||
:disabled="currentPage <= 1"
|
||||
:class="{ 'btn-secondary': currentPage > 1, 'bg-grey': currentPage <= 1 }"
|
||||
@click="setPage(currentPage - 1)"
|
||||
>
|
||||
←
|
||||
</button>
|
||||
<span v-if="pageNbr <= PAGE_NUMBER">
|
||||
<span v-for="index in pageToDraw" :key="index">
|
||||
<PageButton
|
||||
@click="setPage(index)"
|
||||
:current-page="currentPage"
|
||||
:page="index"
|
||||
></PageButton>
|
||||
</span>
|
||||
</span>
|
||||
<span v-else-if="isAtStart">
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="1"
|
||||
@click="setPage(1)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="2"
|
||||
@click="setPage(2)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="3"
|
||||
@click="setPage(3)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="4"
|
||||
@click="setPage(4)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="5"
|
||||
@click="setPage(5)"
|
||||
></PageButton>
|
||||
<button disabled class="btn-small btn-pagination bg-grey disabled">
|
||||
…
|
||||
</button>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr"
|
||||
@click="setPage(pageNbr)"
|
||||
></PageButton>
|
||||
</span>
|
||||
<span v-else-if="isAtEnd">
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="1"
|
||||
@click="setPage(1)"
|
||||
></PageButton>
|
||||
<button disabled class="btn-small bg-grey btn-pagination disabled">
|
||||
…
|
||||
</button>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr - 4"
|
||||
@click="setPage(pageNbr - 4)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr - 3"
|
||||
@click="setPage(pageNbr - 3)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr - 2"
|
||||
@click="setPage(pageNbr - 2)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr - 1"
|
||||
@click="setPage(pageNbr - 1)"
|
||||
></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr"
|
||||
@click="setPage(pageNbr)"
|
||||
></PageButton>
|
||||
</span>
|
||||
<span v-else>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="1"
|
||||
@click="setPage(1)"
|
||||
></PageButton>
|
||||
<button disabled class="btn-small bg-grey btn-pagination disabled">
|
||||
…
|
||||
</button>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="currentPage - 1"
|
||||
@click="setPage(currentPage - 1)"
|
||||
></PageButton>
|
||||
<PageButton :current-page="currentPage" :page="currentPage"></PageButton>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="currentPage + 1"
|
||||
@click="setPage(currentPage + 1)"
|
||||
></PageButton>
|
||||
<button disabled class="btn-small bg-grey btn-pagination disabled">
|
||||
…
|
||||
</button>
|
||||
<PageButton
|
||||
:current-page="currentPage"
|
||||
:page="pageNbr"
|
||||
@click="setPage(pageNbr)"
|
||||
></PageButton>
|
||||
</span>
|
||||
<button
|
||||
class="btn-small btn-navig"
|
||||
:disabled="currentPage >= pageNbr"
|
||||
:class="{
|
||||
'btn-secondary': currentPage < pageNbr,
|
||||
'bg-grey': currentPage >= pageNbr,
|
||||
}"
|
||||
@click="setPage(currentPage + 1)"
|
||||
>
|
||||
→
|
||||
</button>
|
||||
</div>
|
||||
</template>
|
|
@ -1,60 +0,0 @@
|
|||
const objectFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "type", label: "Type", canBeFiltered: true },
|
||||
{ key: "rarete", label: "Rareté", canBeFiltered: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "cout", label: "Cout" },
|
||||
];
|
||||
|
||||
const equipMainsFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "type", label: "Type", canBeFiltered: true },
|
||||
{ key: "mains", label: "Mains", canBeFiltered: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "force", label: "Force" },
|
||||
{ key: "cout", label: "Cout" },
|
||||
];
|
||||
|
||||
const tenuesFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "armure", label: "Armure" },
|
||||
{ key: "cout", label: "cout" },
|
||||
];
|
||||
|
||||
const effetsFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "surcout", label: "Surcout" },
|
||||
];
|
||||
|
||||
const accessoiresFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "cout", label: "Cout" },
|
||||
];
|
||||
|
||||
const elementsFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "type", label: "Type", canBeFiltered: true },
|
||||
{ key: "effet", label: "Effet", canBeSearched: true },
|
||||
{ key: "oppose", label: "Opposé" },
|
||||
];
|
||||
|
||||
const terrainsFields = [
|
||||
{ key: "nom", label: "Nom", canBeSearched: true },
|
||||
{ key: "type", label: "Type", canBeFiltered: true },
|
||||
{ key: "nomTerrain", label: "Nom du Terrain", canBeSearched: true },
|
||||
{ key: "effetTerrain", label: "Effet", canBeSearched: true },
|
||||
{ key: "oppose", label: "Affaibli" },
|
||||
];
|
||||
|
||||
export {
|
||||
objectFields,
|
||||
equipMainsFields,
|
||||
tenuesFields,
|
||||
effetsFields,
|
||||
accessoiresFields,
|
||||
elementsFields,
|
||||
terrainsFields,
|
||||
};
|
14
src/main.ts
14
src/main.ts
|
@ -1,14 +0,0 @@
|
|||
import { createApp } from "vue";
|
||||
import { createPinia } from "pinia";
|
||||
|
||||
import App from "./App.vue";
|
||||
import router from "./router";
|
||||
|
||||
import "./styles/style.scss";
|
||||
|
||||
const app = createApp(App);
|
||||
|
||||
app.use(createPinia());
|
||||
app.use(router);
|
||||
|
||||
app.mount("#app");
|
|
@ -1,62 +0,0 @@
|
|||
import { createRouter, createWebHashHistory } from "vue-router";
|
||||
import HomeView from "../views/HomeView.vue";
|
||||
import RuleView from "../views/RuleView.vue";
|
||||
import JdrView from "../views/JdrView.vue";
|
||||
import FichesView from "../views/FichesView.vue";
|
||||
import ObjetsView from "../views/ObjetsView.vue";
|
||||
import EquipView from "../views/EquipView.vue";
|
||||
import ElementsView from "../views/ElementsView.vue";
|
||||
|
||||
const router = createRouter({
|
||||
history: createWebHashHistory(import.meta.env.BASE_URL),
|
||||
routes: [
|
||||
{
|
||||
path: "/",
|
||||
name: "home",
|
||||
component: HomeView,
|
||||
},
|
||||
{
|
||||
path: "/jdr/:jdr/rules/:category/:filepath",
|
||||
component: RuleView,
|
||||
},
|
||||
{
|
||||
path: "/jdr/:jdr/",
|
||||
component: JdrView,
|
||||
},
|
||||
{
|
||||
path: "/fiches",
|
||||
component: FichesView,
|
||||
},
|
||||
{
|
||||
path: "/about",
|
||||
name: "about",
|
||||
// route level code-splitting
|
||||
// this generates a separate chunk (About.[hash].js) for this route
|
||||
// which is lazy-loaded when the route is visited.
|
||||
component: () => import("../views/AboutView.vue"),
|
||||
},
|
||||
{
|
||||
path: "/jdr/:jdr/inventaire/objets/",
|
||||
component: ObjetsView,
|
||||
},
|
||||
{
|
||||
path: "/jdr/:jdr/inventaire/equipements/",
|
||||
component: EquipView,
|
||||
},
|
||||
{
|
||||
path: "/jdr/:jdr/elements/",
|
||||
component: ElementsView,
|
||||
},
|
||||
],
|
||||
scrollBehavior(to, from, savedPosition) {
|
||||
if (to.hash) {
|
||||
return {
|
||||
el: to.hash,
|
||||
behavior: "smooth",
|
||||
top: 64,
|
||||
};
|
||||
}
|
||||
},
|
||||
});
|
||||
|
||||
export default router;
|
|
@ -1,95 +0,0 @@
|
|||
import { ref } from "vue";
|
||||
import { defineStore } from "pinia";
|
||||
import type PelicanConfig from "@/types/PelicanConfig";
|
||||
import type LinkList from "@/types/LinkList";
|
||||
import type JdrConfig from "@/types/JdrConfig";
|
||||
import axios from "axios";
|
||||
import { cloneDeep } from "lodash";
|
||||
|
||||
export const useConfigStore = defineStore("config", () => {
|
||||
const config = ref(null as PelicanConfig | null);
|
||||
const currentJdr = ref("");
|
||||
const jdrConfig = ref(null as JdrConfig | null);
|
||||
const sidebar = ref([{ id: 0, links: [] }] as LinkList[]);
|
||||
|
||||
function computeSidebar() {
|
||||
const baseSideBar = cloneDeep(config.value?.sidebar ?? []);
|
||||
for (const cat of jdrConfig.value?.sidebar ?? []) {
|
||||
const sidebarItem = baseSideBar.find((a) => a.id === cat.id);
|
||||
if (sidebarItem) {
|
||||
sidebarItem.links = sidebarItem.links.concat(cat.links);
|
||||
} else {
|
||||
baseSideBar.push(cat);
|
||||
}
|
||||
}
|
||||
for (const hideLink of jdrConfig.value?.hideLinks ?? []) {
|
||||
const sidebarItem = baseSideBar.find((a) => a.id === hideLink.menu);
|
||||
if (sidebarItem) {
|
||||
const link = sidebarItem.links.find((a) => a.path === hideLink.link);
|
||||
if (link) {
|
||||
link.isHidden = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return baseSideBar;
|
||||
}
|
||||
|
||||
function setConfig(newConfig: PelicanConfig) {
|
||||
config.value = newConfig;
|
||||
sidebar.value = computeSidebar();
|
||||
}
|
||||
|
||||
function loadJdr(newJdr: string) {
|
||||
if (newJdr !== currentJdr.value) {
|
||||
axios.get(`/jdr/${newJdr}.json`).then((response) => {
|
||||
jdrConfig.value = response.data;
|
||||
currentJdr.value = newJdr;
|
||||
sidebar.value = computeSidebar();
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
function resetJdr() {
|
||||
jdrConfig.value = null;
|
||||
currentJdr.value = "";
|
||||
sidebar.value = [{ id: 0, links: [] }];
|
||||
}
|
||||
|
||||
function isJdrLoaded(): boolean {
|
||||
return currentJdr.value !== "";
|
||||
}
|
||||
|
||||
function getSidebar(): LinkList[] {
|
||||
if (isJdrLoaded()) {
|
||||
return sidebar.value;
|
||||
} else {
|
||||
return (
|
||||
config.value?.jdr?.sort((a, b) => a.id - b.id) ?? [{ id: 0, links: [] }]
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
function getVar(name?: string): string {
|
||||
if (name) {
|
||||
for (const varData of jdrConfig?.value?.vars ?? []) {
|
||||
if (varData.name === name) {
|
||||
return varData.value;
|
||||
}
|
||||
}
|
||||
}
|
||||
return "";
|
||||
}
|
||||
|
||||
return {
|
||||
config,
|
||||
currentJdr,
|
||||
jdrConfig,
|
||||
setConfig,
|
||||
getSidebar,
|
||||
loadJdr,
|
||||
resetJdr,
|
||||
isJdrLoaded,
|
||||
getVar,
|
||||
};
|
||||
});
|
|
@ -1,27 +0,0 @@
|
|||
import { ref } from "vue";
|
||||
import { defineStore } from "pinia";
|
||||
import type TocLine from "@/types/TocLine";
|
||||
|
||||
export const useTocStore = defineStore("toc", () => {
|
||||
const currentPage = ref("");
|
||||
const tocLines = ref([] as TocLine[]);
|
||||
|
||||
function addTocLine(page: string, line: TocLine) {
|
||||
if (page !== currentPage.value) {
|
||||
tocLines.value = [];
|
||||
currentPage.value = page;
|
||||
}
|
||||
tocLines.value.push(line);
|
||||
}
|
||||
|
||||
function getToc(): TocLine[] {
|
||||
return tocLines.value.sort((a, b) => a.order - b.order);
|
||||
}
|
||||
|
||||
function resetToc() {
|
||||
tocLines.value = [];
|
||||
currentPage.value = "";
|
||||
}
|
||||
|
||||
return { currentPage, tocLines, addTocLine, getToc, resetToc };
|
||||
});
|
|
@ -1,9 +0,0 @@
|
|||
/* 0. CORE
|
||||
** All the basic functions from the stylesheet
|
||||
*/
|
||||
|
||||
@import 'core/normalize';
|
||||
@import 'core/box-sizing';
|
||||
@import 'core/typography';
|
||||
@import 'core/containers';
|
||||
@import 'core/columns';
|
|
@ -1,12 +0,0 @@
|
|||
// DEFINITIONS
|
||||
|
||||
// Global definitions and variables of the stylesheet
|
||||
// With them, you can customize easily how the style look
|
||||
// Look at each component inside the definitions subfolder to customize the
|
||||
// styles
|
||||
|
||||
@import 'definitions/palette';
|
||||
@import 'definitions/shadows';
|
||||
@import 'definitions/fonts';
|
||||
@import 'definitions/borders';
|
||||
@import 'definitions/sizing';
|
|
@ -1,2 +0,0 @@
|
|||
// DEPENDECIES
|
||||
// Other style used as dependencies
|
|
@ -1,18 +0,0 @@
|
|||
/* --- 04. COMPOSANTS --- */
|
||||
|
||||
/*
|
||||
* Les différents composants réutilisables de la page.
|
||||
*
|
||||
*/
|
||||
|
||||
@import 'components/buttons';
|
||||
@import 'components/btn-groups';
|
||||
@import 'components/breadcrumb';
|
||||
@import 'components/pagination';
|
||||
@import 'components/cards';
|
||||
@import 'components/menus';
|
||||
@import 'components/toasts';
|
||||
@import 'components/tables';
|
||||
//@import 'components/previews';
|
||||
@import 'components/sidebar';
|
||||
@import 'components/input';
|
|
@ -1,8 +0,0 @@
|
|||
/* 4 - Custom styling
|
||||
* Styles that are custom to this particular theme
|
||||
**/
|
||||
|
||||
@import 'custom/global';
|
||||
//@import 'custom/previews';
|
||||
//@import 'custom/featured';
|
||||
@import 'custom/article';
|
|
@ -1,10 +0,0 @@
|
|||
// MIXINS
|
||||
// Include every mixins files
|
||||
|
||||
@import 'mixins/colors';
|
||||
@import 'mixins/responsive';
|
||||
@import 'mixins/borders';
|
||||
@import 'mixins/shape';
|
||||
@import 'mixins/btns';
|
||||
@import 'mixins/panels';
|
||||
@import 'mixins/li';
|
|
@ -1,12 +0,0 @@
|
|||
/* 1. Utils
|
||||
** All the utilities class of the stylesheet
|
||||
*/
|
||||
|
||||
@import 'utils/a11y';
|
||||
@import 'utils/align';
|
||||
@import 'utils/borders';
|
||||
@import 'utils/colorize';
|
||||
@import 'utils/lists';
|
||||
@import 'utils/sizing';
|
||||
@import 'utils/flex';
|
||||
@import 'utils/display';
|
|
@ -1,6 +0,0 @@
|
|||
.badge {
|
||||
@include button(0rem);
|
||||
padding-left: $button_small;
|
||||
padding-right: $button_small;
|
||||
text-decoration:none!important;
|
||||
}
|
|
@ -1,39 +0,0 @@
|
|||
/* ------------------ BREADCRUMB ------------------- */
|
||||
|
||||
ul.breadcrumb, ol.breadcrumb, .breadcrumb {
|
||||
padding-top: 0em;
|
||||
background-color:transparent;
|
||||
margin: 0;
|
||||
padding-bottom:$lineheight;
|
||||
@include li-flex();
|
||||
}
|
||||
|
||||
.breadcrumb li.breadcrumb-item {
|
||||
padding:0;
|
||||
margin:0!important;
|
||||
&:before {
|
||||
display:none;
|
||||
}
|
||||
|
||||
a, & > span {
|
||||
display:inline-block;
|
||||
@include button($button-large);
|
||||
@include button-fullcontrol($color-background-alt, accentuate($color-background-alt), get-color("dark2"));
|
||||
margin:0 $button-group-margin 0 $button-group-margin;
|
||||
|
||||
&.active {
|
||||
@include button-fullcontrol($color-secondary, $color-secondary, $color-font-light);
|
||||
}
|
||||
}
|
||||
|
||||
&:not(:first-child) a, &:not(:first-child) > span {
|
||||
border-top-left-radius: 0;
|
||||
border-bottom-left-radius:0;
|
||||
}
|
||||
|
||||
&:not(:last-child) a, &:not(:last-child) > span {
|
||||
border-top-right-radius: 0;
|
||||
border-bottom-right-radius:0;
|
||||
}
|
||||
|
||||
}
|
|
@ -1,26 +0,0 @@
|
|||
// BUTTONS GROUPS
|
||||
|
||||
.btn-toolbar {
|
||||
padding: 0 $button-large;
|
||||
}
|
||||
|
||||
.btn-group {
|
||||
& > .btn {
|
||||
@include border-radius($btn-radius);
|
||||
margin:0 $button-group-margin 0 $button-group-margin!important;
|
||||
}
|
||||
|
||||
&:not(:first-child) > .btn {
|
||||
border-top-left-radius: 0;
|
||||
border-bottom-left-radius:0;
|
||||
&:before {
|
||||
content: " "!important;
|
||||
border-left:1px solid rgba(0,0,0,0.2);
|
||||
}
|
||||
}
|
||||
|
||||
&:not(:last-child) > .btn {
|
||||
border-top-right-radius: 0;
|
||||
border-bottom-right-radius:0;
|
||||
}
|
||||
}
|
|
@ -1,35 +0,0 @@
|
|||
/*
|
||||
* 3. Buttons and labels
|
||||
* All clickable elements
|
||||
*
|
||||
*/
|
||||
|
||||
.btn {
|
||||
@include button($button_large);
|
||||
&:hover, &:active {
|
||||
@include borders();
|
||||
}
|
||||
|
||||
p &:last-child {
|
||||
margin-bottom:0;
|
||||
}
|
||||
}
|
||||
|
||||
.btn-small, .badge {
|
||||
@include button($button_small);
|
||||
padding-left: $button_small;
|
||||
padding-right: $button_small;
|
||||
text-decoration:none;
|
||||
}
|
||||
|
||||
// COLORIZE BUTTONS
|
||||
|
||||
strong.btn-fake {
|
||||
@include button($button_large);
|
||||
@include button-fullcontrol(transparent, transparent, rgba(0,0,0,1));
|
||||
}
|
||||
|
||||
.btn-readmore, .btn-link {
|
||||
@include button-fullcontrol(transparent, accentuate($color-background-alt), $color-primary);
|
||||
@include prefer-no-borders();
|
||||
}
|
|
@ -1,76 +0,0 @@
|
|||
/*
|
||||
* 2. Cards and containers
|
||||
* All elements that are supposed to contain other stuff
|
||||
*
|
||||
*
|
||||
*/
|
||||
|
||||
$card-bigpad: $lineheight;
|
||||
$card-smallpad: $lineheight_half;
|
||||
|
||||
.card {
|
||||
@include panel($card-bigpad);
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
color:$color-font;
|
||||
|
||||
&-body {
|
||||
padding:0!important;
|
||||
}
|
||||
|
||||
&-header {
|
||||
@include panel-header($card-bigpad);
|
||||
.fa {
|
||||
margin-right: 0.5em;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* CARD LIST - Make a list part of a card */
|
||||
|
||||
|
||||
@mixin list-symbol($symbol) {
|
||||
li.list-element {
|
||||
list-style: none;
|
||||
&::before {
|
||||
font-family: "ForkAwesome";
|
||||
content:$symbol;
|
||||
padding-right:$lineheight_half;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@mixin list-color($color) {
|
||||
li.list-element {
|
||||
&::before {
|
||||
color: $color;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
ul.card-list, .card > ul {
|
||||
padding:0;
|
||||
margin:0;
|
||||
li.list-element {
|
||||
line-height:$lineheight;
|
||||
padding-right:$lineheight_half;
|
||||
padding-left:$lineheight_quarter;
|
||||
padding-top:$lineheight_quarter;
|
||||
padding-bottom:$lineheight_quarter;
|
||||
margin:0;
|
||||
}
|
||||
}
|
||||
|
||||
.list {
|
||||
&-check {@include list-symbol("\f00c");}
|
||||
&-cross {@include list-symbol("\f00d");}
|
||||
|
||||
&-danger{@include list-color($color-danger);}
|
||||
&-success{@include list-color($color-success);}
|
||||
}
|
||||
|
||||
.smallcard {
|
||||
&-header {
|
||||
@include panel-header($card-bigpad);
|
||||
}
|
||||
}
|
|
@ -1,9 +0,0 @@
|
|||
input,
|
||||
textarea {
|
||||
width: 100%;
|
||||
background-color: $color-background;
|
||||
border-radius: $btn-radius;
|
||||
border: 0px solid rgba(0, 0, 0, 0);
|
||||
padding: $lineheight/4;
|
||||
line-height: $lineheight;
|
||||
}
|
|
@ -1,105 +0,0 @@
|
|||
/* Menu handling */
|
||||
|
||||
.menu {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
padding: $lineheight/4;
|
||||
|
||||
ul,
|
||||
li {
|
||||
list-style: none;
|
||||
padding: 0;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
a,
|
||||
a:visited {
|
||||
@include shape-style($lineheight_half);
|
||||
display: flex;
|
||||
line-height: $lineheight;
|
||||
padding: $lineheight_quarter;
|
||||
margin: 0;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
|
||||
word-wrap: none;
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
|
||||
@include shape-style($lineheight_half);
|
||||
//@include button-hover();
|
||||
@include prefer-no-borders();
|
||||
.badge {
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
|
||||
&.fg-light,
|
||||
.fg-light & {
|
||||
a {
|
||||
color: $color-font-light;
|
||||
|
||||
&.router-link-exact-active {
|
||||
background-color: transparentize($color-font-light, 0.85);
|
||||
}
|
||||
|
||||
&:hover,
|
||||
&:active {
|
||||
background-color: transparentize($color-font-light, 0.7);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.fg-dark,
|
||||
.fg-dark & {
|
||||
a {
|
||||
color: $color-font;
|
||||
|
||||
&:hover,
|
||||
&:active {
|
||||
background-color: transparentize($color-font, 0.85);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.toolbar {
|
||||
flex-direction: row;
|
||||
|
||||
ul {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
|
||||
flex-grow: 1;
|
||||
}
|
||||
|
||||
li {
|
||||
text-align: center;
|
||||
|
||||
a,
|
||||
span,
|
||||
em,
|
||||
strong,
|
||||
&.toolbar-element {
|
||||
display: block;
|
||||
padding: $lineheight/3;
|
||||
padding-left: $lineheight/2;
|
||||
padding-right: $lineheight/2;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.menu-divider {
|
||||
position: relative;
|
||||
left: -$lineheight_quarter;
|
||||
font-weight: $fontweight_hyper;
|
||||
padding-top: $lineheight_quarter;
|
||||
padding-bottom: $lineheight_quarter;
|
||||
}
|
||||
|
||||
.menu-label {
|
||||
@include shape-style($button_small);
|
||||
@include button-hover();
|
||||
padding-left: $button_small;
|
||||
padding-right: $button_small;
|
||||
}
|
|
@ -1,25 +0,0 @@
|
|||
nav.pagination {
|
||||
padding-bottom:$lineheight;
|
||||
.nav-links {
|
||||
text-align: center;
|
||||
width:100%;
|
||||
}
|
||||
.page-numbers, .next, .prev {
|
||||
@include button($button_small);
|
||||
padding-left: $button_small;
|
||||
padding-right: $button_small;
|
||||
margin-right : $button_small / 8;
|
||||
margin-left: $button_small / 8;
|
||||
|
||||
&:not(.current) {
|
||||
@include button-color($color-background-alt);
|
||||
}
|
||||
|
||||
&.current {
|
||||
@include background-color($color-primary);
|
||||
&:hover {
|
||||
@include background-color($color-primary);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,268 +0,0 @@
|
|||
/*
|
||||
* 4. Previews
|
||||
* Special style for previews cards
|
||||
*
|
||||
*/
|
||||
$preview-height: 8*$lineheight;
|
||||
$preview-content-height:165px;
|
||||
$comment-peek-height:0px;
|
||||
$comment-height:30px;
|
||||
|
||||
.preview-grid {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr;
|
||||
grid-template-rows: auto;
|
||||
grid-gap: $lineheight;
|
||||
padding-bottom: $lineheight;
|
||||
|
||||
@include md() {
|
||||
grid-template-columns: 1fr 1fr;
|
||||
}
|
||||
|
||||
@include xl() {
|
||||
grid-template-columns: 1fr 1fr 1fr;
|
||||
}
|
||||
|
||||
@include xxl() {
|
||||
grid-template-columns: 1fr 1fr 1fr 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
.preview-container {
|
||||
width:100%;
|
||||
}
|
||||
|
||||
@media(max-width:767px){}
|
||||
@media(min-width:768px){}
|
||||
@media(min-width:992px){
|
||||
|
||||
.prev-col-2 .preview-container {
|
||||
width:50%;
|
||||
}
|
||||
|
||||
.prev-col-3 .preview-container {
|
||||
width:33%;
|
||||
}
|
||||
|
||||
.prev-col-4 .preview-container {
|
||||
width:25%;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
.card-preview {
|
||||
padding:0;
|
||||
width:100%;
|
||||
margin:auto;
|
||||
box-shadow: $large-shadow, $inset-shadow;
|
||||
}
|
||||
|
||||
.preview-link {
|
||||
padding:0;
|
||||
background-color: transparent;
|
||||
margin:0!important;
|
||||
}
|
||||
|
||||
.preview-item {
|
||||
height: $preview-height;
|
||||
font-size:0.9rem;
|
||||
line-height: $lineheight !important;
|
||||
text-align:justify;
|
||||
background-color:rgba(0,0,0,0.00);
|
||||
color:dim(getFontColor());
|
||||
position: relative;
|
||||
|
||||
display: flex;
|
||||
-ms-flex-align: center !important;
|
||||
align-items: center !important;
|
||||
justify-content: center;
|
||||
|
||||
.preview-overlay {
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
top: 0;
|
||||
left: 0;
|
||||
position: absolute;
|
||||
padding-top: $card-header-vmargin/2;
|
||||
backdrop-filter: none;
|
||||
transition: background-color 0.3s;
|
||||
@include border-radius($card-radius);
|
||||
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
color: $color-font-light;
|
||||
font-size: 1rem;
|
||||
line-height: $lineheight;
|
||||
font-weight:$fontweight_big;
|
||||
}
|
||||
|
||||
.card-header {
|
||||
font-family: $basefont;
|
||||
font-size: 1rem;
|
||||
@include panel-header($lineheight_half);
|
||||
@include colorize-shape($color-primary);
|
||||
color:getTextColorFromBackground($color-primary);
|
||||
font-weight: $fontweight_big;
|
||||
margin-top:0px;
|
||||
}
|
||||
}
|
||||
|
||||
&:hover {
|
||||
.preview-overlay {
|
||||
backdrop-filter: blur(2px);
|
||||
background-color:rgba(0,0,0,0.4);
|
||||
|
||||
.metadata-pills {
|
||||
opacity: .9;
|
||||
transition: opacity .5s, height .5s;
|
||||
height:$preview-content-height - $comment-height;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.preview-content {
|
||||
max-height: $preview-height;
|
||||
overflow:hidden;
|
||||
background-size: cover;
|
||||
min-height:100%;
|
||||
min-width:100%;
|
||||
@include border-radius($card-radius);
|
||||
font-size:0.85rem;
|
||||
line-height:1.25rem;
|
||||
|
||||
h1, h2, h3, h4, h5, h6 {
|
||||
margin-bottom:0px;
|
||||
max-width:100%;
|
||||
display:none;
|
||||
}
|
||||
|
||||
& > p {
|
||||
width:100%;
|
||||
margin:auto;
|
||||
|
||||
& > img {
|
||||
max-width:100%;
|
||||
height:auto;
|
||||
vertical-align:middle;
|
||||
margin:auto;
|
||||
text-align:center;
|
||||
}
|
||||
|
||||
&.p-img {
|
||||
text-align:center;
|
||||
margin:auto;
|
||||
padding:auto;
|
||||
display: block;
|
||||
width:100%;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.preview-metadata {
|
||||
color: $color-font-light;
|
||||
height:$preview-content-height;
|
||||
overflow: hidden;
|
||||
@include border-radius($card-radius);
|
||||
|
||||
.metadata-pills {
|
||||
height:$preview-content-height - $comment-peek-height;
|
||||
opacity: 0;
|
||||
transition: opacity .3s, height .3s;
|
||||
display:flex;
|
||||
justify-content:space-between;
|
||||
padding-left: $lineheight/2;
|
||||
padding-right: $lineheight/2;
|
||||
font-size:0.9em;
|
||||
}
|
||||
}
|
||||
|
||||
.card-preview.head-info {
|
||||
.comment-text {
|
||||
background-color:$color-secondary;
|
||||
}
|
||||
}
|
||||
|
||||
.card-preview.card-grey {
|
||||
.comment-text {
|
||||
background-color:$color-muted;
|
||||
}
|
||||
}
|
||||
|
||||
.comment-text {
|
||||
color: $color-font-light;
|
||||
background-color:$color-primary;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.card-preview time {
|
||||
margin-bottom:0.4em;
|
||||
display:block;
|
||||
}
|
||||
|
||||
// Author area
|
||||
|
||||
.author-area {
|
||||
display:flex;
|
||||
|
||||
img.author-avatar, img.avatar {
|
||||
display:block;
|
||||
height: $lineheight*3;
|
||||
width:auto;
|
||||
border-radius:100%;
|
||||
padding:0;
|
||||
margin:0;
|
||||
margin-right:$lineheight;
|
||||
}
|
||||
|
||||
.author-metadata {
|
||||
align-items:center;
|
||||
display:flex;
|
||||
flex-direction:column;
|
||||
justify-content: center;
|
||||
align-items: flex-start;
|
||||
}
|
||||
|
||||
.author-date {
|
||||
font-style:italic;
|
||||
}
|
||||
|
||||
&:not(:last-child) {
|
||||
margin-bottom:$lineheight;
|
||||
}
|
||||
}
|
||||
|
||||
.pigimg {
|
||||
display:block;
|
||||
max-width: 100%;
|
||||
height:auto;
|
||||
margin:auto;
|
||||
}
|
||||
|
||||
.avatar {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.mwarea {
|
||||
padding-bottom: $lineheight;
|
||||
.avatar {
|
||||
width:80%;
|
||||
height:auto;
|
||||
display:block;
|
||||
margin:auto;
|
||||
}
|
||||
}
|
||||
|
||||
.cover {
|
||||
width:100%;
|
||||
height:auto;
|
||||
@include border-radius($card-radius);
|
||||
}
|
||||
|
||||
.roman {
|
||||
@include md() {
|
||||
width:80%;
|
||||
position:relative;
|
||||
top:-240px;
|
||||
margin:auto;
|
||||
}
|
||||
}
|
|
@ -1,21 +0,0 @@
|
|||
.sidebar-container {
|
||||
width:100%;
|
||||
|
||||
display: grid;
|
||||
grid-template-columns: 1fr;
|
||||
grid-template-rows: auto;
|
||||
row-gap: $lineheight;
|
||||
column-gap: $lineheight*2;
|
||||
grid-template-areas:
|
||||
"side"
|
||||
"main";
|
||||
|
||||
@include lg() {
|
||||
grid-template-columns: 360px auto;
|
||||
grid-template-areas: "side main";
|
||||
}
|
||||
|
||||
.sidebar {
|
||||
padding:1rem;
|
||||
}
|
||||
}
|
|
@ -1,63 +0,0 @@
|
|||
/* TABLE
|
||||
* Style tables
|
||||
*/
|
||||
|
||||
table {
|
||||
border-collapse: collapse;
|
||||
border-spacing: 0;
|
||||
&:not(:last-child) {
|
||||
margin-bottom: 1.5rem;
|
||||
}
|
||||
}
|
||||
|
||||
th, td {
|
||||
padding: 0.325rem;
|
||||
border:0;
|
||||
margin:0;
|
||||
}
|
||||
|
||||
th {
|
||||
vertical-align: center;
|
||||
font-weight: $fontweight_hyper;
|
||||
background-color:$color-primary;
|
||||
color:white;
|
||||
}
|
||||
|
||||
td {
|
||||
background-color:$color-background-alt;
|
||||
tr:nth-child(even) & {
|
||||
background-color: darken($color-background-alt, 7.5%);
|
||||
}
|
||||
}
|
||||
|
||||
thead {
|
||||
th:first-child {
|
||||
border-top-left-radius: 10px;
|
||||
}
|
||||
|
||||
th:last-child {
|
||||
border-top-right-radius: 10px;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
th {
|
||||
text-align: center;
|
||||
&:first-child {
|
||||
border-bottom-left-radius: 10px;
|
||||
}
|
||||
|
||||
&:last-child {
|
||||
border-bottom-right-radius: 10px;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
tr:last-child td:first-child {
|
||||
border-bottom-left-radius: 10px;
|
||||
}
|
||||
|
||||
tr:last-child td:last-child {
|
||||
border-bottom-right-radius: 10px;
|
||||
}
|
|
@ -1,11 +0,0 @@
|
|||
.toast {
|
||||
@include panel($card-smallpad);
|
||||
padding:$card-smallpad;
|
||||
font-size: 0.8rem;
|
||||
a:not(:hover) {
|
||||
background-color: rgba(0,0,0,0.2)!important;
|
||||
}
|
||||
a {
|
||||
margin: 0;
|
||||
}
|
||||
}
|
|
@ -1,18 +0,0 @@
|
|||
/* 0.2 - Box-sizing
|
||||
* Make sure that everything have its box-sizing to border-box
|
||||
**/
|
||||
|
||||
*,
|
||||
*::before,
|
||||
*::after {
|
||||
box-sizing: inherit;
|
||||
}
|
||||
|
||||
html {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
overflow-x: hidden;
|
||||
text-rendering: optimizeLegibility;
|
||||
}
|
|
@ -1,68 +0,0 @@
|
|||
@mixin column($size) {
|
||||
grid-column: span $size;
|
||||
width:100%;
|
||||
margin:0;
|
||||
|
||||
& > *:last-child {
|
||||
margin-bottom:0!important;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin column-list() {
|
||||
&-1 {@include column(1);}
|
||||
&-2 {@include column(2);}
|
||||
&-3 {@include column(3);}
|
||||
&-4 {@include column(4);}
|
||||
&-5 {@include column(5);}
|
||||
&-6 {@include column(6);}
|
||||
&-7 {@include column(7);}
|
||||
&-8 {@include column(8);}
|
||||
&-9 {@include column(9);}
|
||||
&-10 {@include column(10);}
|
||||
&-11 {@include column(11);}
|
||||
&-12 {@include column(12);}
|
||||
}
|
||||
|
||||
.columns {
|
||||
display:grid;
|
||||
grid-gap:$lineheight;
|
||||
grid-template-columns: repeat(12, 1fr);
|
||||
grid-template-rows: auto;
|
||||
padding:$lineheight;
|
||||
&-nogap {
|
||||
grid-gap:0px;
|
||||
}
|
||||
}
|
||||
|
||||
.column {
|
||||
@include column(12);
|
||||
}
|
||||
|
||||
.col {
|
||||
@include column-list();
|
||||
&-sm {
|
||||
@include sm() {
|
||||
@include column-list();
|
||||
}
|
||||
}
|
||||
&-md {
|
||||
@include md() {
|
||||
@include column-list();
|
||||
}
|
||||
}
|
||||
&-lg {
|
||||
@include lg() {
|
||||
@include column-list();
|
||||
}
|
||||
}
|
||||
&-xl {
|
||||
@include xl() {
|
||||
@include column-list();
|
||||
}
|
||||
}
|
||||
&-xxl {
|
||||
@include xxl() {
|
||||
@include column-list();
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,11 +0,0 @@
|
|||
#wrapper {
|
||||
background-color: $color-background;
|
||||
}
|
||||
|
||||
.container-big {
|
||||
@include container($container-size-large, $lineheight);
|
||||
}
|
||||
|
||||
.container, .container-onecolumn {
|
||||
@include container($container-size, $lineheight);
|
||||
}
|
|
@ -1,349 +0,0 @@
|
|||
/*! normalize.css v8.0.1 | MIT License | github.com/necolas/normalize.css */
|
||||
|
||||
/* Document
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* 1. Correct the line height in all browsers.
|
||||
* 2. Prevent adjustments of font size after orientation changes in iOS.
|
||||
*/
|
||||
|
||||
html {
|
||||
line-height: 1.15; /* 1 */
|
||||
-webkit-text-size-adjust: 100%; /* 2 */
|
||||
}
|
||||
|
||||
/* Sections
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* Remove the margin in all browsers.
|
||||
*/
|
||||
|
||||
body {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Render the `main` element consistently in IE.
|
||||
*/
|
||||
|
||||
main {
|
||||
display: block;
|
||||
}
|
||||
|
||||
/**
|
||||
* Correct the font size and margin on `h1` elements within `section` and
|
||||
* `article` contexts in Chrome, Firefox, and Safari.
|
||||
*/
|
||||
|
||||
h1 {
|
||||
font-size: 2em;
|
||||
margin: 0.67em 0;
|
||||
}
|
||||
|
||||
/* Grouping content
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* 1. Add the correct box sizing in Firefox.
|
||||
* 2. Show the overflow in Edge and IE.
|
||||
*/
|
||||
|
||||
hr {
|
||||
box-sizing: content-box; /* 1 */
|
||||
height: 0; /* 1 */
|
||||
overflow: visible; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Correct the inheritance and scaling of font size in all browsers.
|
||||
* 2. Correct the odd `em` font sizing in all browsers.
|
||||
*/
|
||||
|
||||
pre {
|
||||
font-family: monospace, monospace; /* 1 */
|
||||
font-size: 1em; /* 2 */
|
||||
}
|
||||
|
||||
/* Text-level semantics
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* Remove the gray background on active links in IE 10.
|
||||
*/
|
||||
|
||||
a {
|
||||
background-color: transparent;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Remove the bottom border in Chrome 57-
|
||||
* 2. Add the correct text decoration in Chrome, Edge, IE, Opera, and Safari.
|
||||
*/
|
||||
|
||||
abbr[title] {
|
||||
border-bottom: none; /* 1 */
|
||||
text-decoration: underline; /* 2 */
|
||||
text-decoration: underline dotted; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the correct font weight in Chrome, Edge, and Safari.
|
||||
*/
|
||||
|
||||
b,
|
||||
strong {
|
||||
font-weight: bolder;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Correct the inheritance and scaling of font size in all browsers.
|
||||
* 2. Correct the odd `em` font sizing in all browsers.
|
||||
*/
|
||||
|
||||
code,
|
||||
kbd,
|
||||
samp {
|
||||
font-family: monospace, monospace; /* 1 */
|
||||
font-size: 1em; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the correct font size in all browsers.
|
||||
*/
|
||||
|
||||
small {
|
||||
font-size: 80%;
|
||||
}
|
||||
|
||||
/**
|
||||
* Prevent `sub` and `sup` elements from affecting the line height in
|
||||
* all browsers.
|
||||
*/
|
||||
|
||||
sub,
|
||||
sup {
|
||||
font-size: 75%;
|
||||
line-height: 0;
|
||||
position: relative;
|
||||
vertical-align: baseline;
|
||||
}
|
||||
|
||||
sub {
|
||||
bottom: -0.25em;
|
||||
}
|
||||
|
||||
sup {
|
||||
top: -0.5em;
|
||||
}
|
||||
|
||||
/* Embedded content
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* Remove the border on images inside links in IE 10.
|
||||
*/
|
||||
|
||||
img {
|
||||
border-style: none;
|
||||
}
|
||||
|
||||
/* Forms
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* 1. Change the font styles in all browsers.
|
||||
* 2. Remove the margin in Firefox and Safari.
|
||||
*/
|
||||
|
||||
button,
|
||||
input,
|
||||
optgroup,
|
||||
select,
|
||||
textarea {
|
||||
font-family: inherit; /* 1 */
|
||||
font-size: 100%; /* 1 */
|
||||
line-height: 1.15; /* 1 */
|
||||
margin: 0; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Show the overflow in IE.
|
||||
* 1. Show the overflow in Edge.
|
||||
*/
|
||||
|
||||
button,
|
||||
input { /* 1 */
|
||||
overflow: visible;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the inheritance of text transform in Edge, Firefox, and IE.
|
||||
* 1. Remove the inheritance of text transform in Firefox.
|
||||
*/
|
||||
|
||||
button,
|
||||
select { /* 1 */
|
||||
text-transform: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Correct the inability to style clickable types in iOS and Safari.
|
||||
*/
|
||||
|
||||
button,
|
||||
[type="button"],
|
||||
[type="reset"],
|
||||
[type="submit"] {
|
||||
-webkit-appearance: button;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the inner border and padding in Firefox.
|
||||
*/
|
||||
|
||||
button::-moz-focus-inner,
|
||||
[type="button"]::-moz-focus-inner,
|
||||
[type="reset"]::-moz-focus-inner,
|
||||
[type="submit"]::-moz-focus-inner {
|
||||
border-style: none;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
/**
|
||||
* Restore the focus styles unset by the previous rule.
|
||||
*/
|
||||
|
||||
button:-moz-focusring,
|
||||
[type="button"]:-moz-focusring,
|
||||
[type="reset"]:-moz-focusring,
|
||||
[type="submit"]:-moz-focusring {
|
||||
outline: 1px dotted ButtonText;
|
||||
}
|
||||
|
||||
/**
|
||||
* Correct the padding in Firefox.
|
||||
*/
|
||||
|
||||
fieldset {
|
||||
padding: 0.35em 0.75em 0.625em;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Correct the text wrapping in Edge and IE.
|
||||
* 2. Correct the color inheritance from `fieldset` elements in IE.
|
||||
* 3. Remove the padding so developers are not caught out when they zero out
|
||||
* `fieldset` elements in all browsers.
|
||||
*/
|
||||
|
||||
legend {
|
||||
box-sizing: border-box; /* 1 */
|
||||
color: inherit; /* 2 */
|
||||
display: table; /* 1 */
|
||||
max-width: 100%; /* 1 */
|
||||
padding: 0; /* 3 */
|
||||
white-space: normal; /* 1 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the correct vertical alignment in Chrome, Firefox, and Opera.
|
||||
*/
|
||||
|
||||
progress {
|
||||
vertical-align: baseline;
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the default vertical scrollbar in IE 10+.
|
||||
*/
|
||||
|
||||
textarea {
|
||||
overflow: auto;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Add the correct box sizing in IE 10.
|
||||
* 2. Remove the padding in IE 10.
|
||||
*/
|
||||
|
||||
[type="checkbox"],
|
||||
[type="radio"] {
|
||||
box-sizing: border-box; /* 1 */
|
||||
padding: 0; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Correct the cursor style of increment and decrement buttons in Chrome.
|
||||
*/
|
||||
|
||||
[type="number"]::-webkit-inner-spin-button,
|
||||
[type="number"]::-webkit-outer-spin-button {
|
||||
height: auto;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Correct the odd appearance in Chrome and Safari.
|
||||
* 2. Correct the outline style in Safari.
|
||||
*/
|
||||
|
||||
[type="search"] {
|
||||
-webkit-appearance: textfield; /* 1 */
|
||||
outline-offset: -2px; /* 2 */
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove the inner padding in Chrome and Safari on macOS.
|
||||
*/
|
||||
|
||||
[type="search"]::-webkit-search-decoration {
|
||||
-webkit-appearance: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* 1. Correct the inability to style clickable types in iOS and Safari.
|
||||
* 2. Change font properties to `inherit` in Safari.
|
||||
*/
|
||||
|
||||
::-webkit-file-upload-button {
|
||||
-webkit-appearance: button; /* 1 */
|
||||
font: inherit; /* 2 */
|
||||
}
|
||||
|
||||
/* Interactive
|
||||
========================================================================== */
|
||||
|
||||
/*
|
||||
* Add the correct display in Edge, IE 10+, and Firefox.
|
||||
*/
|
||||
|
||||
details {
|
||||
display: block;
|
||||
}
|
||||
|
||||
/*
|
||||
* Add the correct display in all browsers.
|
||||
*/
|
||||
|
||||
summary {
|
||||
display: list-item;
|
||||
}
|
||||
|
||||
/* Misc
|
||||
========================================================================== */
|
||||
|
||||
/**
|
||||
* Add the correct display in IE 10+.
|
||||
*/
|
||||
|
||||
template {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/**
|
||||
* Add the correct display in IE 10.
|
||||
*/
|
||||
|
||||
[hidden] {
|
||||
display: none;
|
||||
}
|
|
@ -1,190 +0,0 @@
|
|||
/* 0.3 - Typography
|
||||
* This part of the (s)css handle everything related to the typography
|
||||
* like paragraphs, blockquote, etc.
|
||||
**/
|
||||
|
||||
/* 2.2 - Global Typography */
|
||||
|
||||
@mixin paragraph() {
|
||||
padding:0;
|
||||
padding-bottom: $lineheight;
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
html, body {
|
||||
font-family: $basefont;
|
||||
text-align: left;
|
||||
font-size: $fontsize;
|
||||
line-height: $lineheight;
|
||||
color: getFontColor();
|
||||
font-weight: $fontweight_base;
|
||||
}
|
||||
|
||||
strong {
|
||||
font-weight: $fontweight_bold;
|
||||
}
|
||||
|
||||
em {
|
||||
font-style: italic;
|
||||
font-weight: $fontweight_base;
|
||||
}
|
||||
|
||||
a, a:visited, mark {
|
||||
text-decoration: none;
|
||||
padding: 0.05rem 0.25rem;
|
||||
border-radius: 0.1rem;
|
||||
}
|
||||
|
||||
a, a:visited {
|
||||
@include background-color($color-link);
|
||||
&:hover, &:active, &:focus {
|
||||
color: $color-link;
|
||||
background-color: transparent;
|
||||
}
|
||||
|
||||
&:focus {
|
||||
outline-color: currentColor;
|
||||
outline-style: dashed;
|
||||
outline-width: 2px;
|
||||
}
|
||||
}
|
||||
|
||||
mark {
|
||||
background-color: lighten($color-mark, 30%);
|
||||
color: inherit;
|
||||
}
|
||||
|
||||
p, ul, ol {
|
||||
@include paragraph();
|
||||
&:last-child {
|
||||
padding-bottom:0;
|
||||
}
|
||||
}
|
||||
|
||||
ul, ol {
|
||||
list-style: disc;
|
||||
ul, ol {
|
||||
padding-bottom:0;
|
||||
margin:0;
|
||||
}
|
||||
li {
|
||||
margin:0;
|
||||
margin-left: $lineheight;
|
||||
line-height: $lineheight;
|
||||
}
|
||||
}
|
||||
|
||||
::selection, ::-moz-selection {
|
||||
@include background-color($color-selection);
|
||||
}
|
||||
|
||||
/* 2.3 - Titles */
|
||||
|
||||
@mixin newTitle($size, $weight) {
|
||||
$lineNumber: ceil($size / 1.5);
|
||||
font-size: $size * 1rem;
|
||||
line-height: $lineNumber * $lineheight;
|
||||
font-weight: $weight;
|
||||
}
|
||||
|
||||
h1, h2, h3, h4, h5, h6, h7 {
|
||||
font-family: $basefont;
|
||||
text-align: left;
|
||||
font-size: 1em;
|
||||
padding:0;
|
||||
margin:0;
|
||||
font-weight: $fontweight_base;
|
||||
padding-bottom: $lineheight;
|
||||
}
|
||||
|
||||
sup, sub {
|
||||
& > a {
|
||||
color: $color-link;
|
||||
background-color:transparent;
|
||||
&:hover, &:focus, &:active {
|
||||
color: darken($color-link, 10%);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.main-title {
|
||||
font-family: $titlefont;
|
||||
@include newTitle(3.815, $fontweight_hyper);
|
||||
}
|
||||
|
||||
h1, .title-1 {
|
||||
font-family: $titlefont;
|
||||
@include newTitle(2.441, $fontweight_hyper);
|
||||
color: $color-primary;
|
||||
}
|
||||
|
||||
h2, .title-2 {
|
||||
@include newTitle(2.441, $fontweight_big);
|
||||
}
|
||||
|
||||
h3, .title-3 {
|
||||
@include newTitle(1.953, $fontweight_bold);
|
||||
}
|
||||
|
||||
h4, .title-4 {
|
||||
@include newTitle(1.563, $fontweight_hyper);
|
||||
}
|
||||
|
||||
h5, .title-5 {
|
||||
@include newTitle(1.25, $fontweight_bold);
|
||||
}
|
||||
|
||||
h6, .title-6 {
|
||||
@include newTitle(1, $fontweight_hyper);
|
||||
}
|
||||
|
||||
/* 2.4 - hr */
|
||||
|
||||
hr {
|
||||
border: 0px solid rgba(1, 1, 1, 0.15);
|
||||
border-bottom: 1px;
|
||||
margin: 1.5em;
|
||||
}
|
||||
|
||||
/* 2.5 - Wells and quotes */
|
||||
|
||||
@mixin well() {
|
||||
border: 0;
|
||||
border-radius: $well-radius;
|
||||
|
||||
margin: 0 0 $lineheight 0;
|
||||
padding: $lineheight 1rem $lineheight 1rem;
|
||||
|
||||
max-width: 100%;
|
||||
font-style: italic;
|
||||
@include background-color($color-background-alt);
|
||||
box-shadow: $narrow-shadow;
|
||||
}
|
||||
|
||||
blockquote, .quote {
|
||||
&:before {
|
||||
content:"";
|
||||
}
|
||||
}
|
||||
|
||||
blockquote, .quote, .well, pre, .pre, .well-pre {
|
||||
@include well();
|
||||
}
|
||||
|
||||
code {
|
||||
background:transparent;
|
||||
color: $color-danger;
|
||||
}
|
||||
|
||||
.small-text {
|
||||
font-size: 0.9em;
|
||||
}
|
||||
|
||||
/* 2.6 - Special styling */
|
||||
|
||||
.time {
|
||||
font-style: italic;
|
||||
text-align: right;
|
||||
width: 100%;
|
||||
display: block;
|
||||
}
|
|
@ -1,39 +0,0 @@
|
|||
article:last-child {
|
||||
padding-bottom:1.5rem;
|
||||
}
|
||||
|
||||
article .table-auto table, table.table-auto {
|
||||
display: table;
|
||||
width: 100%;
|
||||
table-layout: auto;
|
||||
}
|
||||
|
||||
table {
|
||||
display: table;
|
||||
width: 100%;
|
||||
table-layout: fixed;
|
||||
}
|
||||
|
||||
.btn-pagination, .btn-navig {
|
||||
margin:0;
|
||||
border-radius: 0;
|
||||
width: 2rem;
|
||||
}
|
||||
|
||||
.btn-navig:first-child {
|
||||
border-top-left-radius: $btn-radius;
|
||||
border-bottom-left-radius: $btn-radius;
|
||||
}
|
||||
|
||||
.btn-navig:last-child {
|
||||
border-top-right-radius: $btn-radius;
|
||||
border-bottom-right-radius: $btn-radius;
|
||||
}
|
||||
|
||||
article th {
|
||||
height: 34px;
|
||||
}
|
||||
|
||||
article tr:nth-child(2n) {
|
||||
background-color: #fff;
|
||||
}
|
|
@ -1,48 +0,0 @@
|
|||
#featured-articles {
|
||||
display:grid;
|
||||
grid-template-columns: 1fr;
|
||||
grid-template-rows: auto;
|
||||
grid-gap: $lineheight;
|
||||
padding-bottom: $lineheight;
|
||||
@include lg() {
|
||||
grid-template-columns: 1fr 1fr 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
.preview-featured {
|
||||
font-size: 0.8rem;
|
||||
|
||||
.preview-link {
|
||||
display: block;
|
||||
padding:0;
|
||||
border-radius: $card-radius;
|
||||
overflow: hidden;
|
||||
.preview-item {
|
||||
width: 100%;
|
||||
height: auto;
|
||||
aspect-ratio: 16 / 9;
|
||||
background-size:100% auto;
|
||||
background-position: center center;
|
||||
transition: background-size .5s;
|
||||
|
||||
&:hover {
|
||||
background-size: 120% auto;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.preview-overlay {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: space-between;
|
||||
align-items: flex-start;
|
||||
height:100%;
|
||||
color: white !important;
|
||||
background: linear-gradient(to top, rgba(0, 0, 0, 0.75) 0%, rgba(0, 0, 0, 0) 60%);
|
||||
padding:$lineheight / 8;
|
||||
|
||||
h2 {
|
||||
text-shadow: 1px 1px 3px rgba(0, 0, 0, 0.7);
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,51 +0,0 @@
|
|||
#topbar {
|
||||
position:fixed;
|
||||
width:100%;
|
||||
z-index:2;
|
||||
font-size: 0.85rem;
|
||||
}
|
||||
|
||||
#wrapper {
|
||||
padding-top:3rem;
|
||||
display:flex;
|
||||
min-height:100vh;
|
||||
}
|
||||
|
||||
#sidebar {
|
||||
padding-top:1rem;
|
||||
padding-left:0.75rem;
|
||||
width:17rem;
|
||||
position: fixed;
|
||||
height: calc(100vh - 3rem);
|
||||
overflow: scroll;
|
||||
h1 {
|
||||
text-align:center;
|
||||
padding-bottom:.5rem;
|
||||
}
|
||||
.menu-item {
|
||||
margin:3px;
|
||||
}
|
||||
font-size:0.85rem;
|
||||
}
|
||||
|
||||
#page {
|
||||
flex-grow:1;
|
||||
padding-left:18rem;
|
||||
padding-right: 18rem;
|
||||
}
|
||||
|
||||
#toc {
|
||||
position: fixed;
|
||||
top: 4rem;
|
||||
right: 1rem;
|
||||
width: 16rem;
|
||||
.menu {
|
||||
padding-left:0.5rem;
|
||||
padding-right:0.5rem;
|
||||
}
|
||||
}
|
||||
|
||||
#content {
|
||||
max-width:1000px;
|
||||
margin:auto;
|
||||
}
|
|
@ -1,79 +0,0 @@
|
|||
.preview-grid {
|
||||
display: grid;
|
||||
grid-template-columns: 1fr;
|
||||
grid-template-rows: auto;
|
||||
grid-gap: $lineheight;
|
||||
padding-bottom: $lineheight;
|
||||
|
||||
@include md() {
|
||||
grid-template-columns: 1fr 1fr;
|
||||
}
|
||||
|
||||
@include xl() {
|
||||
grid-template-columns: 1fr 1fr 1fr;
|
||||
}
|
||||
|
||||
@include xxl() {
|
||||
grid-template-columns: 1fr 1fr 1fr 1fr;
|
||||
}
|
||||
}
|
||||
|
||||
.preview-list {
|
||||
@include sm() {
|
||||
.preview-thumbnail a {
|
||||
width: 240px;
|
||||
margin-right: $lineheight /2;
|
||||
}
|
||||
|
||||
.preview {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
margin-bottom: $lineheight;
|
||||
}
|
||||
}
|
||||
@include xl() {
|
||||
.preview-thumbnail a {
|
||||
width: 320px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.preview {
|
||||
font-size: 0.8rem;
|
||||
}
|
||||
|
||||
.preview-thumbnail a {
|
||||
display:block;
|
||||
width: 100%;
|
||||
background-color:transparent;
|
||||
margin:auto;
|
||||
object-fit: cover;
|
||||
padding:0;
|
||||
line-height:0;
|
||||
img {
|
||||
width:100%;
|
||||
object-fit: cover;
|
||||
height: auto;
|
||||
aspect-ratio: 16/9;
|
||||
border-radius: $card-radius;
|
||||
}
|
||||
}
|
||||
|
||||
.preview h2, .preview-featured h2 {
|
||||
font-size:1.25rem;
|
||||
line-height: 1.5rem;
|
||||
font-family: $titlefont;
|
||||
font-weight: 800;
|
||||
height:3rem;
|
||||
a {
|
||||
background-color:transparent!important;
|
||||
color:$color-font;
|
||||
}
|
||||
}
|
||||
|
||||
.preview-excerpt {
|
||||
margin-top: $lineheight / 2;
|
||||
font-size:0.8rem;
|
||||
line-height:1.25rem;
|
||||
color:transparentize($color-font, 0.2);
|
||||
}
|
|
@ -1,6 +0,0 @@
|
|||
// BORDERS AND BORDER-RADIUSES
|
||||
|
||||
$card-radius: 8px;
|
||||
$btn-radius: 4px;
|
||||
$well-radius: $btn-radius;
|
||||
$border-size: 0px;
|
|
@ -1,12 +0,0 @@
|
|||
// FONTS
|
||||
// Define how looks the text
|
||||
|
||||
$fontsize: 4.75mm;
|
||||
|
||||
$fontweight_big: 300;
|
||||
$fontweight_base: 400;
|
||||
$fontweight_bold: 600;
|
||||
$fontweight_hyper: 800;
|
||||
|
||||
$basefont: Open Sans, sans-serif;
|
||||
$titlefont: Open Sans, sans-serif;
|
|
@ -1,83 +0,0 @@
|
|||
/* --- 00. PALETTE --- */
|
||||
|
||||
/*
|
||||
* Les définitions globales des couleurs du theme.
|
||||
*
|
||||
* Elle permettent de définir rapidement à la fois les couleurs
|
||||
* de base qui seront utilisée pour tout le theme, mais
|
||||
* également celles spécifiques pour certains sujets (liens, texte)
|
||||
*
|
||||
*/
|
||||
|
||||
$whiteness_value: 0.8;
|
||||
|
||||
// Couleurs de base du theme :
|
||||
|
||||
$palette: (
|
||||
"brown":#876445,
|
||||
"blue":#1c7ed6,
|
||||
"violet":#6741d9,
|
||||
"red":#e03131,
|
||||
"orange":#e67700,
|
||||
"green":#37b24d,
|
||||
"skyblue":#1098ad,
|
||||
"dark": #343a40,
|
||||
"light":#fefefe,
|
||||
"yellow":#fcc419,
|
||||
"grey":#adb5bd,
|
||||
"dark2":#212529,
|
||||
"light2":#f1f3f5);
|
||||
|
||||
$semantics: (
|
||||
"primary":"brown",
|
||||
"secondary":"dark",
|
||||
"warning":"orange",
|
||||
"danger":"red",
|
||||
"info":"skyblue",
|
||||
"success":"green",
|
||||
"muted":"grey");
|
||||
|
||||
$helpers: (
|
||||
"font":"dark2",
|
||||
"font-light":"light",
|
||||
"background":"light",
|
||||
"background-alt":"light2",
|
||||
"link":"brown",
|
||||
"selection":"brown",
|
||||
"mark":"yellow",
|
||||
);
|
||||
|
||||
@function get-color($name) {
|
||||
@if map-has-key($helpers, $name) {
|
||||
@return map-get($palette, map-get($helpers, $name));
|
||||
} @else {
|
||||
@if map-has-key($semantics, $name) {
|
||||
@return map-get($palette, map-get($semantics, $name));
|
||||
} @else {
|
||||
@return map-get($palette, $name);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// **Couleurs du theme**
|
||||
// Ne pas retirer ces couleurs, qui
|
||||
// sont essentielle pour que le framework functionne.
|
||||
// Pour les modifier, modifier le contenu du tableau $semantics.
|
||||
|
||||
$color-link: get-color("link");
|
||||
$color-selection: get-color("selection");
|
||||
$color-mark: get-color("mark");
|
||||
$color-font: get-color("font");
|
||||
$color-font-light: get-color("font-light");
|
||||
|
||||
$color-primary: get-color("primary");
|
||||
$color-secondary: get-color("secondary");
|
||||
$color-warning: get-color("warning");
|
||||
$color-danger: get-color("danger");
|
||||
$color-info: get-color("info");
|
||||
$color-success: get-color("success");
|
||||
|
||||
$color-muted: get-color("muted");
|
||||
|
||||
$color-background: get-color("background");
|
||||
$color-background-alt: get-color("background-alt");
|
|
@ -1,8 +0,0 @@
|
|||
// SHADOWS
|
||||
// Define how looks the shadows and the relief effects
|
||||
|
||||
$large-shadow: 0px 2px 4px rgba(0, 0, 0, 0);
|
||||
$narrow-shadow: 0px 1px 2px rgba(0, 0, 0, 0);
|
||||
$inset-shadow: inset 0px -2px 0px rgba(0, 0, 0, 0);
|
||||
$inset-shadow-inverted: inset 0px 2px 0px rgba(0, 0, 0, 0);
|
||||
$inset-relief: inset 0px 2px 0px rgba(255, 255, 255, 0);
|
|
@ -1,34 +0,0 @@
|
|||
// SIZING
|
||||
// All the spacing and sizing variables
|
||||
|
||||
$baseline: 1.5;
|
||||
|
||||
$lineheight: $baseline * 1rem;
|
||||
$lineheight_half: $lineheight/2;
|
||||
$lineheight_quarter: $lineheight/4;
|
||||
|
||||
$card-header-vmargin: 0px;
|
||||
$card-header-hmargin: 0px;
|
||||
$card-header-padding: $lineheight;
|
||||
$card-header-width: 100%;
|
||||
$card-header-position:0px;
|
||||
// Buttons
|
||||
$button_large: $lineheight;
|
||||
$button_small: $lineheight_quarter;
|
||||
$button-group-margin: 0;
|
||||
|
||||
// Responsives sizes
|
||||
// - sm : Small tablets and large smartphones (landscape view)
|
||||
// - md : Small tablets (portrait view)
|
||||
// - lg : Tablets and small desktops
|
||||
// - xl : Large tablets and desktops
|
||||
// - xxl : Very large desktops
|
||||
$screen-sm-min: 576px;
|
||||
$screen-md-min: 768px;
|
||||
$screen-lg-min: 992px;
|
||||
$screen-xl-min: 1200px;
|
||||
$screen-xxl-min: 1600px;
|
||||
|
||||
// Containers size
|
||||
$container-size: $screen-xl-min;
|
||||
$container-size-large: $screen-xxl-min;
|
|
@ -1,15 +0,0 @@
|
|||
// Border, border radius and margin
|
||||
|
||||
@mixin borders() {
|
||||
border: $border-size solid rgba(0, 0, 0, 0.3)
|
||||
}
|
||||
|
||||
@mixin prefer-no-borders() {
|
||||
&:not(:hover) {
|
||||
border-color:transparent;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin border-radius($border-radius) {
|
||||
border-radius: $border-radius $border-radius $border-radius $border-radius;
|
||||
}
|
|
@ -1,51 +0,0 @@
|
|||
@mixin button($size) {
|
||||
@include button-layout($size);
|
||||
@include shape-style($size);
|
||||
@include button-hover();
|
||||
font-weight: $fontweight_base;
|
||||
}
|
||||
|
||||
@mixin button-layout($size) {
|
||||
padding: $size;
|
||||
padding-top: $size/3;
|
||||
padding-bottom: $size/3;
|
||||
margin:$size/2;
|
||||
margin-top: $size/3;
|
||||
margin-bottom: $lineheight;
|
||||
//font-size: 4.75mm;
|
||||
line-height:$lineheight;
|
||||
height:auto;
|
||||
}
|
||||
|
||||
@mixin button-hover() {
|
||||
transition: background-color .2s, border .2s, box-shadow .2s, color .2s;
|
||||
|
||||
&:focus {
|
||||
outline: none;
|
||||
box-shadow: $narrow-shadow, $inset-shadow, 0px 0px 0px 2px rgba(0, 0, 0, 0);
|
||||
&:before {
|
||||
box-shadow: $narrow-shadow, $inset-shadow, 0px 0px 0px 2px rgba(0, 0, 0, 0.3);
|
||||
outline: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@mixin button-fullcontrol($background-color, $hover-color, $text-color) {
|
||||
@include colorize-shape($background-color);
|
||||
color:$text-color;
|
||||
&:visited {
|
||||
@include colorize-shape($background-color);
|
||||
color:$text-color;
|
||||
}
|
||||
&, &:visited, &:not(.disabled):not(:disabled) {
|
||||
&:hover, &:active, &:focus {
|
||||
@include colorize-shape($hover-color);
|
||||
color:lighten($text-color, 5%);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@mixin button-color($background-color) {
|
||||
@include button-fullcontrol($background-color, mix($background-color, getTextColorFromBackground($background-color), 85%), getTextColorFromBackground($background-color));
|
||||
box-shadow: $narrow-shadow;
|
||||
}
|
|
@ -1,61 +0,0 @@
|
|||
/* --- 00. COLORS --- */
|
||||
|
||||
/*
|
||||
* La gestion des couleurs dans le theme. Cette partie de la stylesheet est
|
||||
* automatique et n'a pas besoin d'être modifiée
|
||||
*/
|
||||
|
||||
// FUNCTIONS TO GET MORE EASILY COLORS
|
||||
@function list-colors() {
|
||||
$newmap: map-merge($palette, $semantics);
|
||||
@return $newmap;
|
||||
}
|
||||
|
||||
@function luminance($color) {
|
||||
$c_red: red($color);
|
||||
$c_grn: green($color);
|
||||
$c_blu: blue($color);
|
||||
|
||||
$luminance: $c_red*0.299 + $c_grn*0.587 + $c_blu*0.114;
|
||||
|
||||
@return $luminance
|
||||
}
|
||||
|
||||
@function getFontColor() {
|
||||
@return getTextColorFromBackground(get-color("background-alt"));
|
||||
}
|
||||
|
||||
@function getTextColorFromBackground($background-color) {
|
||||
@if (luminance($background-color) < 255 * $whiteness_value) {
|
||||
@return $color-font-light;
|
||||
} @else {
|
||||
@return $color-font;
|
||||
}
|
||||
}
|
||||
|
||||
@function accentuate($color) {
|
||||
@if (luminance($color) > 64) {
|
||||
@return darken($color, 7.5%);
|
||||
} @else {
|
||||
@return lighten($color, 4%);
|
||||
}
|
||||
}
|
||||
|
||||
@function dim($color) {
|
||||
@if (luminance($color) > 255 * $whiteness_value) {
|
||||
@return transparentize($color, 0.8);
|
||||
} @else {
|
||||
@return transparentize($color, 0.6);
|
||||
}
|
||||
}
|
||||
|
||||
// fonction texte et background
|
||||
|
||||
@mixin text-color($text-color) {
|
||||
color: $text-color;
|
||||
}
|
||||
|
||||
@mixin background-color($background-color) {
|
||||
background-color: $background-color;
|
||||
color: getTextColorFromBackground($background-color);
|
||||
}
|
|
@ -1,13 +0,0 @@
|
|||
@mixin li-no-margin() {
|
||||
li {
|
||||
margin: 0;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin li-flex() {
|
||||
display:flex;
|
||||
flex-direction: row;
|
||||
align-items: flex-start;
|
||||
@include li-no-margin();
|
||||
list-style: none;
|
||||
}
|
|
@ -1,64 +0,0 @@
|
|||
@mixin panel($size) {
|
||||
@include border-radius($card-radius);
|
||||
background-color: $color-background-alt;
|
||||
box-shadow: $large-shadow;
|
||||
border: none;
|
||||
margin:0;
|
||||
margin-bottom:$lineheight;
|
||||
|
||||
& > * {
|
||||
margin-left: $size / 2;
|
||||
margin-right: $size / 2;
|
||||
&:first-child {
|
||||
margin-top: $size;
|
||||
&.card-header {
|
||||
margin-top:$card-header-vmargin;
|
||||
}
|
||||
}
|
||||
&:last-child {
|
||||
margin-bottom: $size;
|
||||
&.card-header {
|
||||
margin-bottom:$card-header-vmargin;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@mixin panel-header($size) {
|
||||
font-size:1.1em;
|
||||
font-weight: $fontweight_big;
|
||||
padding: $size/2;
|
||||
padding-left:$card-header-padding;
|
||||
padding-right:$card-header-padding;
|
||||
padding-bottom: $size/2!important;
|
||||
margin:$card-header-hmargin;
|
||||
margin-bottom:$lineheight_half;
|
||||
margin-top:$lineheight_half;
|
||||
line-height:$lineheight;
|
||||
white-space: nowrap;
|
||||
|
||||
position:relative;
|
||||
left: $card-header-position;
|
||||
width:$card-header-width;
|
||||
|
||||
@include shape-style($size);
|
||||
border-radius:0;
|
||||
&:first-child {
|
||||
border-top-left-radius: $card-radius;
|
||||
border-top-right-radius: $card-radius;
|
||||
}
|
||||
&:last-child {
|
||||
border-bottom-left-radius: $card-radius;
|
||||
border-bottom-right-radius: $card-radius;
|
||||
}
|
||||
|
||||
h1, h2, h3, h4, h5, h6, h7, h8, h9, h10 {
|
||||
font-family:$basefont;
|
||||
font-size:1rem;
|
||||
padding:0px;
|
||||
margin:0px;
|
||||
color:$color-font-light;
|
||||
font-weight: $fontweight_big;
|
||||
line-height:$lineheight;
|
||||
}
|
||||
}
|
|
@ -1,84 +0,0 @@
|
|||
// MIXINS RESPONSIVES
|
||||
|
||||
// Small devices
|
||||
@mixin sm {
|
||||
@media (min-width: #{$screen-sm-min}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
// Medium devices
|
||||
@mixin md {
|
||||
@media (min-width: #{$screen-md-min}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
// Large devices
|
||||
@mixin lg {
|
||||
@media (min-width: #{$screen-lg-min}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
// Extra large devices
|
||||
@mixin xl {
|
||||
@media (min-width: #{$screen-xl-min}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
// Extra large desktops
|
||||
@mixin xxl {
|
||||
@media (min-width: #{$screen-xxl-min}) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
// Custom devices
|
||||
@mixin rwd($screen) {
|
||||
@media (min-width: $screen+'px' ) {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin container($size, $padding) {
|
||||
padding-left: $padding;
|
||||
padding-right: $padding;
|
||||
max-width: $size;
|
||||
margin:auto;
|
||||
}
|
||||
|
||||
@mixin responsive() {
|
||||
@content;
|
||||
|
||||
&-sm {
|
||||
@include sm() {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
&-md {
|
||||
@include md() {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
&-lg {
|
||||
@include lg() {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
&-xl {
|
||||
@include xl() {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
|
||||
&-xxl {
|
||||
@include xxl() {
|
||||
@content;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,10 +0,0 @@
|
|||
@mixin shape-style($size) {
|
||||
@include borders();
|
||||
@include border-radius($btn-radius);
|
||||
|
||||
background-color:transparent;
|
||||
}
|
||||
|
||||
@mixin colorize-shape($background-color) {
|
||||
background-color: $background-color;
|
||||
}
|
|
@ -1,23 +0,0 @@
|
|||
/*
|
||||
Theme Name: Quarante-Douze
|
||||
Theme URI: https://git.kobold.cafe/quarante-douze/qdouze2-wordpress-theme
|
||||
Author: Kazhnuz
|
||||
Author URI: https://kazhnuz.space
|
||||
Description: The default theme for Quarante-Douze, my tech blog.
|
||||
Version: 0.1
|
||||
License: GNU General Public License v3 or later
|
||||
License URI: http://www.gnu.org/licenses/gpl-2.0.html
|
||||
Tags: blog, two-columns, right-sidebar
|
||||
Text Domain: qdouze2-wordpress-theme
|
||||
|
||||
This theme is licensed under the GPLv3.
|
||||
*/
|
||||
|
||||
@import 'dep';
|
||||
@import 'definitions';
|
||||
@import 'mixins';
|
||||
|
||||
@import 'core';
|
||||
@import 'drawing';
|
||||
@import 'utils';
|
||||
@import 'global';
|
|
@ -1,8 +0,0 @@
|
|||
/* 1.0 - Accessibility classes
|
||||
* Some classes to help accessibility
|
||||
**/
|
||||
|
||||
.screen-reader-text {
|
||||
visibility: collapse;
|
||||
font-size:0;
|
||||
}
|
|
@ -1,14 +0,0 @@
|
|||
/* 1.1 - Alignement classes
|
||||
* Handle easily alignement and flexboxes
|
||||
**/
|
||||
|
||||
.flex-that {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
.align {
|
||||
&-center {text-align: center;text-indent: 0!important;}
|
||||
&-left {text-align: left;}
|
||||
&-right {text-align: right;}
|
||||
}
|
|
@ -1,8 +0,0 @@
|
|||
.round, .pill {
|
||||
border-radius: 9999px;
|
||||
}
|
||||
|
||||
.no-borders {
|
||||
border-width:0px;
|
||||
border-style:none;
|
||||
}
|
|
@ -1,85 +0,0 @@
|
|||
/* 1.2 - Colorization classes
|
||||
* Colorize some aspect of a class
|
||||
**/
|
||||
|
||||
@mixin heading-color($background-color) {
|
||||
|
||||
& .card-header,
|
||||
& .menu-header,
|
||||
&.header-bg th {
|
||||
@include colorize-shape($background-color);
|
||||
color: getTextColorFromBackground($background-color);
|
||||
}
|
||||
|
||||
th {
|
||||
color: $background-color;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin bg-color($background-color) {
|
||||
@include background-color($background-color);
|
||||
|
||||
&>a,
|
||||
&>a:visited {
|
||||
color: $background-color;
|
||||
background-color: getTextColorFromBackground($background-color);
|
||||
|
||||
&:hover,
|
||||
&:active,
|
||||
&:visited {
|
||||
color: getTextColorFromBackground($background-color);
|
||||
background: none;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.bg {
|
||||
|
||||
@each $name,
|
||||
$color in list-colors() {
|
||||
&-#{$name} {
|
||||
@include bg-color(get-color($name));
|
||||
&:hover {
|
||||
@include bg-color(get-color($name));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.text {
|
||||
|
||||
@each $name,
|
||||
$color in list-colors() {
|
||||
&-#{$name} {
|
||||
@include text-color(get-color($name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.btn {
|
||||
|
||||
@each $name,
|
||||
$color in list-colors() {
|
||||
&-#{$name} {
|
||||
@include button-color(get-color($name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.head {
|
||||
|
||||
@each $name,
|
||||
$color in list-colors() {
|
||||
&-#{$name} {
|
||||
@include heading-color(get-color($name));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.fg-light {
|
||||
color: $color-font-light;
|
||||
}
|
||||
|
||||
.fg-dark {
|
||||
color: $color-font;
|
||||
}
|
|
@ -1,17 +0,0 @@
|
|||
.d-block {
|
||||
@include responsive() {
|
||||
display: block!important;
|
||||
}
|
||||
}
|
||||
|
||||
.d-none {
|
||||
@include responsive() {
|
||||
display: none!important;
|
||||
}
|
||||
}
|
||||
|
||||
.d-flex {
|
||||
@include responsive() {
|
||||
display: flex!important;
|
||||
}
|
||||
}
|
|
@ -1,35 +0,0 @@
|
|||
.f-column {
|
||||
display:flex;
|
||||
flex-direction: column;
|
||||
&.reverse {
|
||||
flex-direction:column-reverse;
|
||||
}
|
||||
}
|
||||
|
||||
.f-row {
|
||||
display:flex;
|
||||
flex-direction: row;
|
||||
&.reverse {
|
||||
flex-direction:row-reverse;
|
||||
}
|
||||
}
|
||||
|
||||
.f-start {
|
||||
justify-content: flex-start;
|
||||
}
|
||||
|
||||
.f-end {
|
||||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.f-center {
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.f-around {
|
||||
justify-content: space-around;
|
||||
}
|
||||
|
||||
.f-between {
|
||||
justify-content: space-between;
|
||||
}
|
|
@ -1,7 +0,0 @@
|
|||
/* 1.3 - List classes
|
||||
* Handle more easily list
|
||||
**/
|
||||
|
||||
.no-pills {
|
||||
list-style:none;
|
||||
}
|
|
@ -1,61 +0,0 @@
|
|||
/* 1.3 - Sizing classes
|
||||
* Handle sizing and margin
|
||||
**/
|
||||
|
||||
@mixin addmargins($name, $size) {
|
||||
&-#{$name} {
|
||||
margin:$size;
|
||||
}
|
||||
|
||||
&b-#{$name} {
|
||||
margin-bottom:$size;
|
||||
}
|
||||
|
||||
&r-#{$name} {
|
||||
margin-right:$size;
|
||||
}
|
||||
|
||||
&l-#{$name} {
|
||||
margin-left:$size;
|
||||
}
|
||||
|
||||
&t-#{$name} {
|
||||
margin-top:$size;
|
||||
}
|
||||
}
|
||||
|
||||
@mixin addpaddings($name, $size) {
|
||||
&-#{$name} {
|
||||
padding:$size;
|
||||
}
|
||||
|
||||
&b-#{$name} {
|
||||
padding-bottom:$size;
|
||||
}
|
||||
|
||||
&r-#{$name} {
|
||||
padding-right:$size;
|
||||
}
|
||||
|
||||
&l-#{$name} {
|
||||
padding-left:$size;
|
||||
}
|
||||
|
||||
&t-#{$name} {
|
||||
padding-top:$size;
|
||||
}
|
||||
}
|
||||
|
||||
.m {
|
||||
@include addmargins("half", $lineheight * .5);
|
||||
@for $i from 0 through 4 {
|
||||
@include addmargins($i, $lineheight*$i)
|
||||
}
|
||||
}
|
||||
|
||||
.p {
|
||||
@include addpaddings("half", $lineheight * .5);
|
||||
@for $i from 0 through 4 {
|
||||
@include addpaddings($i, $lineheight*$i)
|
||||
}
|
||||
}
|
|
@ -1,4 +0,0 @@
|
|||
export default interface HideLink {
|
||||
menu: number;
|
||||
link: string;
|
||||
}
|
|
@ -1,16 +0,0 @@
|
|||
import type HideLink from "./HideLink";
|
||||
import type LinkList from "./LinkList";
|
||||
|
||||
export default interface JdrConfig {
|
||||
name: string;
|
||||
sidebar: LinkList[];
|
||||
hideLinks: HideLink[];
|
||||
vars: { name: string; value: string }[];
|
||||
objects: string[];
|
||||
equipMains: string[];
|
||||
effetsMains: string[];
|
||||
tenues: string[];
|
||||
effetsTenues: string[];
|
||||
accessoires: string[];
|
||||
elements: string[];
|
||||
}
|
|
@ -1,5 +0,0 @@
|
|||
export default interface Link {
|
||||
title: string;
|
||||
path: string;
|
||||
isHidden?: boolean;
|
||||
}
|
|
@ -1,7 +0,0 @@
|
|||
import type Link from "./Link";
|
||||
|
||||
export default interface LinkList {
|
||||
title?: string;
|
||||
id: number;
|
||||
links: Link[];
|
||||
}
|
|
@ -1,9 +0,0 @@
|
|||
import type Link from "./Link";
|
||||
import type LinkList from "./LinkList";
|
||||
|
||||
export default interface PelicanConfig {
|
||||
version: string;
|
||||
sidebar: LinkList[];
|
||||
jdr: LinkList[];
|
||||
fiches: Link[];
|
||||
}
|
|
@ -1,5 +0,0 @@
|
|||
export default interface TocLine {
|
||||
order: number;
|
||||
text: string;
|
||||
anchor: string;
|
||||
}
|
|
@ -1,116 +0,0 @@
|
|||
import SimpleHtmlTable from "./SimpleHtmlTable";
|
||||
import { forEachCols, getColumn } from "./tableUtils";
|
||||
import type { FilterFieldsMap, Filters, TableField, TableItem } from "./types";
|
||||
|
||||
export default class FilteredHtmlTable {
|
||||
table: SimpleHtmlTable;
|
||||
filtersFieldMap: FilterFieldsMap = {};
|
||||
textSearch = "";
|
||||
|
||||
constructor() {
|
||||
this.table = new SimpleHtmlTable();
|
||||
}
|
||||
|
||||
private initFilters() {
|
||||
this.filtersFieldMap = {};
|
||||
for (const field of this.table.fields) {
|
||||
if (field.canBeFiltered) {
|
||||
// Create a filter for the field, that'll contain every
|
||||
// filters possible for the field
|
||||
this.filtersFieldMap[field.key] = {
|
||||
title: field.label,
|
||||
filters: {} as Filters,
|
||||
};
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
set fields(fields: TableField[]) {
|
||||
this.table.fields = fields;
|
||||
this.initFilters();
|
||||
}
|
||||
|
||||
addItems(rows: TableItem[]) {
|
||||
this.table.addItems(rows);
|
||||
forEachCols(rows, (colName: string, col: string) => {
|
||||
this.setFilterableValue(colName, col);
|
||||
});
|
||||
}
|
||||
|
||||
get items() {
|
||||
let filteredItem = this.table.items as TableItem[];
|
||||
|
||||
for (const fieldKey in this.filtersFieldMap) {
|
||||
if (this.haveFilter(fieldKey)) {
|
||||
filteredItem = filteredItem.filter((row) => {
|
||||
const filters = this.getFiltersForField(fieldKey);
|
||||
return !filters || filters[getColumn(row, fieldKey) as string];
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
if (this.textSearch !== "") {
|
||||
filteredItem = filteredItem.filter((row) => {
|
||||
for (const field of this.table.fields) {
|
||||
if (field.canBeSearched) {
|
||||
if ((row[field.key] as string).includes(this.textSearch)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
return filteredItem;
|
||||
}
|
||||
|
||||
search(query: string) {
|
||||
return this.items.filter((row) => {
|
||||
for (const field of this.table.fields) {
|
||||
if (field.canBeSearched) {
|
||||
if ((row[field.key] as string).includes(query)) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
private setFilterableValue(fieldKey: string, filterableValue: string) {
|
||||
const filters = this.getFiltersForField(fieldKey);
|
||||
if (filters) {
|
||||
filters[filterableValue] = false;
|
||||
}
|
||||
}
|
||||
|
||||
private getFiltersForField(fieldKey: string) {
|
||||
if (this.filtersFieldMap[fieldKey]) {
|
||||
return this.filtersFieldMap[fieldKey].filters;
|
||||
}
|
||||
}
|
||||
|
||||
private haveFilter(fieldKey: string) {
|
||||
for (const val in this.getFiltersForField(fieldKey)) {
|
||||
if (this.filtersFieldMap[fieldKey].filters[val]) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
public switchFilter(fieldKey: string, filterValue: string) {
|
||||
const filters = this.getFiltersForField(fieldKey);
|
||||
if (filters && filters[filterValue] !== undefined) {
|
||||
filters[filterValue] = !filters[filterValue];
|
||||
}
|
||||
}
|
||||
|
||||
public removeAllFilters(fieldKey: string) {
|
||||
const filters = this.getFiltersForField(fieldKey);
|
||||
for (const filterValue in filters) {
|
||||
filters[filterValue] = false;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -1,80 +0,0 @@
|
|||
import FilteredHtmlTable from "./FilteredHtmlTable";
|
||||
import type { TableField, TableItem } from "./types";
|
||||
|
||||
export interface PaginatedTable {
|
||||
filteredTable: FilteredHtmlTable;
|
||||
pageLenght: number;
|
||||
currentPage: number;
|
||||
pageNumber: number;
|
||||
items: TableItem[];
|
||||
textSearch: string;
|
||||
}
|
||||
|
||||
export default class PaginatedFilteredTable implements PaginatedTable {
|
||||
filteredTable: FilteredHtmlTable;
|
||||
pageLenght: number;
|
||||
currentPage = 0;
|
||||
|
||||
constructor(pageLenght: number) {
|
||||
this.filteredTable = new FilteredHtmlTable();
|
||||
this.pageLenght = pageLenght;
|
||||
}
|
||||
|
||||
get pageNumber() {
|
||||
return Math.floor((this.filteredTable.items.length - 1) / this.pageLenght);
|
||||
}
|
||||
|
||||
get items() {
|
||||
let items = this.filteredTable.items as TableItem[];
|
||||
|
||||
items = items.filter((value, index) => {
|
||||
const pageBegin = this.currentPage * this.pageLenght;
|
||||
return index >= pageBegin && index < pageBegin + this.pageLenght;
|
||||
});
|
||||
|
||||
return items;
|
||||
}
|
||||
|
||||
set fields(fields: TableField[]) {
|
||||
this.filteredTable.fields = fields;
|
||||
}
|
||||
|
||||
set textSearch(textSearch: string) {
|
||||
this.currentPage = 0;
|
||||
this.filteredTable.textSearch = textSearch;
|
||||
}
|
||||
|
||||
get textSearch() {
|
||||
return this.filteredTable.textSearch;
|
||||
}
|
||||
|
||||
public addItems(items: TableItem[]) {
|
||||
this.filteredTable.addItems(items);
|
||||
}
|
||||
|
||||
public search(query: string) {
|
||||
return this.filteredTable.search(query);
|
||||
}
|
||||
|
||||
public canGo(rel: number) {
|
||||
return (
|
||||
this.currentPage + rel >= 0 && this.currentPage + rel <= this.pageNumber
|
||||
);
|
||||
}
|
||||
|
||||
public go(rel: number) {
|
||||
if (this.canGo(rel)) {
|
||||
this.currentPage = this.currentPage + rel;
|
||||
}
|
||||
}
|
||||
|
||||
public switchFilter(fieldKey: string, filterValue: string) {
|
||||
this.filteredTable.switchFilter(fieldKey, filterValue);
|
||||
this.currentPage = 0;
|
||||
}
|
||||
|
||||
public removeAllFilters(fieldKey: string) {
|
||||
this.filteredTable.removeAllFilters(fieldKey);
|
||||
this.currentPage = 0;
|
||||
}
|
||||
}
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue