Skip to content

Commit

Permalink
Improve handling of callouts which contain asides / margin elements
Browse files Browse the repository at this point in the history
-> Automatically ‘escape’ the margin elements outside the callout body
-> Forward collapse classes so the element will follow the collapse behaviot of the callout
-> Position it next to the callout contents
  • Loading branch information
dragonstyle committed May 3, 2022
1 parent cb95c64 commit d92f227
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 2 deletions.
38 changes: 38 additions & 0 deletions src/format/html/format-html-bootstrap.ts
Original file line number Diff line number Diff line change
Expand Up @@ -450,6 +450,9 @@ function processColumnElements(
// Process captions that may appear in the margin
processMarginCaptions(doc);

// Process margin elements that may appear in callouts
processMarginElsInCallouts(doc);

// Group margin elements by their parents and wrap them in a container
// Be sure to ignore containers which are already processed
// and should be left alone
Expand Down Expand Up @@ -640,6 +643,41 @@ const processMarginCaptions = (doc: Document) => {
});
};

const processMarginElsInCallouts = (doc: Document) => {
const calloutNodes = doc.querySelectorAll("div.callout");
calloutNodes.forEach((calloutNode) => {
const calloutEl = calloutNode as Element;
const collapseEl = calloutEl.querySelector(".callout-collapse");
const isSimple = calloutEl.classList.contains("callout-style-simple");

//Get the collapse classes (if any) to forward long
const collapseClasses: string[] = [];
if (collapseEl) {
collapseEl.classList.forEach((clz) => collapseClasses.push(clz));
}

const marginNodes = calloutEl.querySelectorAll(
".callout-body > .column-margin, .callout-body > aside",
);

if (marginNodes.length > 0) {
const marginArr = Array.from(marginNodes);
marginArr.reverse().forEach((marginNode) => {
const marginEl = marginNode as Element;
collapseClasses.forEach((clz) => {
marginEl.classList.add(clz);
});
marginEl.classList.add("callout-margin-content");
if (isSimple) {
marginEl.classList.add("callout-margin-content-simple");
}

calloutEl.after(marginEl);
});
}
});
};

interface MarginNodeProcessor {
selector: string;
canProcess(el: Element): boolean;
Expand Down
4 changes: 3 additions & 1 deletion src/resources/filters/quarto-pre/callout.lua
Original file line number Diff line number Diff line change
Expand Up @@ -196,15 +196,17 @@ function calloutDiv(div)
headerDiv.content:insert(pandoc.Plain(toggleButton));

-- configure the header div for collapse
local bsTargetClz = calloutid .. "-contents"
headerDiv.attr.attributes["bs-toggle"] = "collapse"
headerDiv.attr.attributes["bs-target"] = "#" .. calloutid
headerDiv.attr.attributes["bs-target"] = "." .. bsTargetClz
headerDiv.attr.attributes["aria-controls"] = calloutid
headerDiv.attr.attributes["aria-expanded"] = expandedAttrVal
headerDiv.attr.attributes["aria-label"] = 'Toggle callout'

-- configure the body div for collapse
local collapseDiv = pandoc.Div({})
collapseDiv.attr.identifier = calloutid
collapseDiv.attr.classes:insert(bsTargetClz)
collapseDiv.attr.classes:insert("callout-collapse")
collapseDiv.attr.classes:insert("collapse")
if expandedAttrVal == "true" then
Expand Down
15 changes: 14 additions & 1 deletion src/resources/formats/html/bootstrap/_bootstrap-rules.scss
Original file line number Diff line number Diff line change
Expand Up @@ -655,12 +655,25 @@ aside,
font-size: 0.825rem;
}

.column-margin.column-container > * {
.column-margin.column-container > *:not(.collapse) {
padding-top: 0.5em;
padding-bottom: 0.5em;
display: block;
}

.column-margin.column-container > *.collapse:not(.show) {
display: none;
}

@include media-breakpoint-up(md) {
.column-margin.column-container .callout-margin-content:first-child {
margin-top: 4.5em;
}
.column-margin.column-container .callout-margin-content-simple:first-child {
margin-top: 3.5em;
}
}

.margin-caption > * {
padding-top: 0.5em;
padding-bottom: 0.5em;
Expand Down

0 comments on commit d92f227

Please sign in to comment.