rewrite DocsCollapsible

now with disabled js support and less broken animations
This commit is contained in:
outfoxxed 2024-10-19 01:49:00 -07:00
parent 22b8e154f3
commit 45fc2eed5a
Signed by: outfoxxed
GPG key ID: 4C88A185FB89301E
9 changed files with 136 additions and 46 deletions

View file

@ -0,0 +1,55 @@
---
import "@styles/components/accordion.css"
---
<details class=`accordion ${Astro.props.class ?? ""}` {...Astro.props}>
<summary>
<slot name="header"/>
</summary>
<div class="accordion-container">
<div>
<slot/>
</div>
</div>
</details>
<script>
document.addEventListener("DOMContentLoaded", () => {
document.querySelectorAll(".accordion").forEach(element => {
const accordion = element as HTMLDetailsElement;
const summary = accordion.querySelector("summary")!;
const body = accordion.querySelector(".accordion-container") as HTMLDivElement;
summary.addEventListener("click", event => {
event.preventDefault();
body.classList.toggle("animate", true);
if (!accordion.open || accordion.classList.contains("closing")) {
accordion.classList.toggle("closing", false);
body.style.setProperty("--height", "0px");
requestAnimationFrame(() => {
accordion.open = true;
body.style.setProperty("--height", body.scrollHeight + "px");
});
} else {
body.style.setProperty("--height", body.scrollHeight + "px");
requestAnimationFrame(() => {
accordion.classList.toggle("closing", true);
body.style.setProperty("--height", "0px");
});
}
});
body.addEventListener("transitionend", event => {
if ((event as TransitionEvent).propertyName == "max-height") {
body.classList.toggle("animate", false);
if (accordion.classList.contains("closing")) {
accordion.classList.toggle("closing", false);
accordion.open = false;
}
}
});
});
});
</script>

View file

@ -0,0 +1,16 @@
---
import Accordion from "./Accordion.astro"
import collapsibleMarker from "@icons/collapsible-marker.svg?raw"
interface Props {
title: string
}
const { title } = Astro.props;
---
<Accordion class="docs-collapsible">
<div slot="header">
<Fragment set:html={collapsibleMarker}/>
{title}
</div>
<slot>
</Accordion>

View file

@ -1,18 +0,0 @@
import { Collapsible } from "@ark-ui/solid";
import type { Component, JSX } from "solid-js";
import { CaretCircleRight } from "@icons";
export const DocsCollapsible: Component<{
title: string;
children: JSX.Element;
}> = props => {
return (
<Collapsible.Root>
<Collapsible.Trigger>
<CaretCircleRight />
{props.title}
</Collapsible.Trigger>
<Collapsible.Content>{props.children}</Collapsible.Content>
</Collapsible.Root>
);
};

View file

@ -0,0 +1,2 @@
<svg xmlns="http://www.w3.org/2000/svg" width="1em" height="1em" viewBox="0 0 256 256"><path fill="currentColor" d="M128 24a104 104 0 1 0 104 104A104.11 104.11 0 0 0 128 24m0 192a88 88 0 1 1 88-88a88.1 88.1 0 0 1-88 88m29.66-93.66a8 8 0 0 1 0 11.32l-40 40a8 8 0 0 1-11.32-11.32L140.69 128l-34.35-34.34a8 8 0 0 1 11.32-11.32Z"/></svg>

After

Width:  |  Height:  |  Size: 335 B

View file

@ -3,7 +3,7 @@ layout: "@layouts/ConfigLayout.astro"
title: "Introduction" title: "Introduction"
--- ---
import { DocsCollapsible } from "@components/Collapsible.tsx"; import Collapsible from "@components/Collapsible.astro";
import MD_Title from "@components/MD_Title.tsx" import MD_Title from "@components/MD_Title.tsx"
# {frontmatter.title} # {frontmatter.title}
@ -35,7 +35,7 @@ The shell root is not a visual element but instead contains all of the visual
and non visual objects in your shell. You can have multiple different shells and non visual objects in your shell. You can have multiple different shells
with shared components and different shell roots. with shared components and different shell roots.
<DocsCollapsible title="Shell search paths and manifests" client:visible> <Collapsible title="Shell search paths and manifests">
Quickshell can be launched with configurations in locations other than the default one. Quickshell can be launched with configurations in locations other than the default one.
The `-p` or `--path` option will launch the shell root at the given path. The `-p` or `--path` option will launch the shell root at the given path.
@ -68,7 +68,7 @@ myconf4 = ~/.config/quickshell/myconf
You can use `quickshell --current` to print the current values of any of these You can use `quickshell --current` to print the current values of any of these
options and what set them. options and what set them.
</DocsCollapsible> </Collapsible>
## <MD_Title titleVar={2}> Creating Windows </MD_Title> ## <MD_Title titleVar={2}> Creating Windows </MD_Title>

View file

@ -3,7 +3,7 @@ layout: "@layouts/ConfigLayout.astro"
title: "QML Overview" title: "QML Overview"
--- ---
import MD_Title from "@components/MD_Title.tsx" import MD_Title from "@components/MD_Title.tsx"
import { DocsCollapsible } from "@components/Collapsible.tsx"; import Collapsible from "@components/Collapsible.astro";
# {frontmatter.title} # {frontmatter.title}
@ -140,7 +140,7 @@ import QtQuick.Layouts 6.0 as L
import "jsfile.js" as JsFile import "jsfile.js" as JsFile
``` ```
<DocsCollapsible title="When no module version" client:visible> <Collapsible title="When no module version">
By default, when no module version is requested, the QML engine will pick By default, when no module version is requested, the QML engine will pick
the latest available version of the module. Requesting a specific version the latest available version of the module. Requesting a specific version
@ -151,7 +151,7 @@ While Qt's types usually don't majorly change across versions, quickshell's
are much more likely to break. To put off dealing with the breakage we suggest are much more likely to break. To put off dealing with the breakage we suggest
specifying a version at least when importing quickshell modules. specifying a version at least when importing quickshell modules.
</DocsCollapsible> </Collapsible>
<span class="small"> <span class="small">
[Qt Documentation: Import [Qt Documentation: Import
@ -321,14 +321,14 @@ the object a name it can be referred to throughout the current file. The id must
} }
``` ```
<DocsCollapsible title="The `id` property compared to normal properties" client:visible> <Collapsible title="The `id` property compared to normal properties">
The `id` property isn't really a property, and doesn't do anything other than The `id` property isn't really a property, and doesn't do anything other than
expose the object to the current file. It is only called a property because it expose the object to the current file. It is only called a property because it
uses very similar syntax to one, and is the only exception to standard property uses very similar syntax to one, and is the only exception to standard property
definition rules. The name `id` is always reserved for the id property. definition rules. The name `id` is always reserved for the id property.
</DocsCollapsible> </Collapsible>
##### <MD_Title titleVar={5}> Property access scopes </MD_Title> ##### <MD_Title titleVar={5}> Property access scopes </MD_Title>

View file

@ -0,0 +1,17 @@
.accordion {
& summary {
list-style: none;
}
& .accordion-container {
/* fixes jumps due to margins on inline items */
display: flex;
}
& .accordion-container.animate {
/* this somehow breaks if both min AND max aren't animated */
transition: min-height 0.3s ease, max-height 0.3s ease;
min-height: var(--height);
max-height: var(--height);
}
}

View file

@ -57,26 +57,6 @@
} }
} }
@keyframes rotateIn90 {
from {
transform: rotate(0deg);
}
to {
transform: rotate(90deg);
}
}
@keyframes rotateOut90 {
from {
transform: rotate(90deg);
}
to {
transform: rotate(0deg);
}
}
@keyframes percentToFifty { @keyframes percentToFifty {
from { from {
--percent: 0%; --percent: 0%;

View file

@ -142,3 +142,41 @@ ul {
min-width: 33.8rem; min-width: 33.8rem;
} }
} }
.docs-collapsible {
background-color: hsl(var(--white) 40 50 / 0.1);
border-radius: 0.618rem;
overflow: hidden;
& summary {
padding: 1.2rem;
user-select: none;
& > div {
display: flex;
flex-direction: row;
align-items: center;
gap: 0.1em;
font-size: 1.117rem;
font-weight: 500;
& svg {
transition: transform 0.3s ease;
font-size: 1.1em;
}
}
}
& .accordion-container > div {
padding: 0 1.2rem;
& p:first-child {
padding-top: 0;
margin-top: 0;
}
}
}
.docs-collapsible[open]:not(.closing) > summary > div > svg {
transform: rotate(90deg);
}