Skip to content

Commit

Permalink
refactor: post content
Browse files Browse the repository at this point in the history
  • Loading branch information
yilanboy committed Feb 21, 2024
1 parent 842717f commit 0c53d89
Show file tree
Hide file tree
Showing 2 changed files with 64 additions and 43 deletions.
105 changes: 63 additions & 42 deletions resources/ts/post-content.ts
Original file line number Diff line number Diff line change
Expand Up @@ -36,42 +36,76 @@ function createPostContentLink(
}
}

function activePostContentLink(
headingPositions: number[],
contentLinks: NodeListOf<HTMLAnchorElement>,
): void {
let currentScrollPosition: number = window.scrollY;
function createHeadingSectionsInPostBdy(postBody: Element) {
let childNodes: NodeListOf<ChildNode> = postBody.childNodes;

let currentH2: Element | null = null;
let currentSection: Element | null = null;
let newPostBody: any[] = [];

// change the style of heading link when scrolling
headingPositions.forEach((position: number, index: number) => {
childNodes.forEach((childNode: ChildNode) => {
if (
currentScrollPosition <
headingPositions[0] - (viewportHeight * 3) / 4
currentH2 === null &&
currentSection === null &&
childNode.nodeName !== 'H2'
) {
contentLinks.forEach((link: HTMLAnchorElement) => {
link.classList.remove('bg-gray-300', 'dark:bg-gray-700');
});
}
newPostBody.push(childNode.cloneNode(true));
} else if (childNode.nodeName === 'H2') {
currentH2 = childNode as Element;

if (currentScrollPosition >= position - (viewportHeight * 3) / 4) {
contentLinks.forEach((link: HTMLAnchorElement) => {
link.classList.remove('bg-gray-300', 'dark:bg-gray-700');
});
let section = document.createElement('div');
currentSection = section;
section.id = `${currentH2.id}-section`;

contentLinks[index].classList.add(
'bg-gray-300',
'dark:bg-gray-700',
);
section.appendChild(childNode.cloneNode(true));

newPostBody.push(section);
} else if (currentH2 && currentSection && childNode.nodeName !== 'H2') {
// call by reference
currentSection.appendChild(childNode.cloneNode(true));
}
});

// Remove all child nodes from postBody
postBody.innerHTML = '';

// Append all sectionGroups to postBody
newPostBody.forEach((sectionGroup: ChildNode) => {
postBody.appendChild(sectionGroup);
});
}

function showWhereAmI(
headingPositions: number[],
contentLinks: NodeListOf<HTMLAnchorElement>,
): void {
window.addEventListener('scroll', () => {
activePostContentLink(headingPositions, contentLinks);
function showWhereAmI(contentLinks: NodeListOf<HTMLAnchorElement>) {
contentLinks.forEach((contentLink: HTMLAnchorElement, index: number) => {
let section: Element | null = document.getElementById(
`heading-${index}-section`,
);

console.log(`heading-${index}-section`);

if (section === null) {
return;
}

let sectionObserver = new IntersectionObserver(
function (entries) {
console.log('show');
if (entries[0].isIntersecting) {
contentLink.classList.add(
'bg-gray-300',
'dark:bg-gray-600',
);
} else {
contentLink.classList.remove(
'bg-gray-300',
'dark:bg-gray-600',
);
}
},
{ threshold: [0] },
);

sectionObserver.observe(section);
});
}

Expand All @@ -87,24 +121,11 @@ window.setupPostContent = function (
}

createPostContentLink(postContent, headings);
createHeadingSectionsInPostBdy(postBody);

// Get all content links, must be after createPostContentLink
let contentLinks: NodeListOf<HTMLAnchorElement> =
postContent.querySelectorAll('a');

// Resize observer will execute at least once, and
// When the post body is resized
const resizeObserver = new ResizeObserver((entries) => {
let headingPositions: number[] = [];

headings.forEach((heading: HTMLHeadingElement) => {
let position = window.scrollY + heading.getBoundingClientRect().top;
headingPositions.push(position);
});

activePostContentLink(headingPositions, contentLinks);
showWhereAmI(headingPositions, contentLinks);
});

resizeObserver.observe(postBody);
showWhereAmI(contentLinks);
};
2 changes: 1 addition & 1 deletion resources/views/livewire/pages/posts/show.blade.php
Original file line number Diff line number Diff line change
Expand Up @@ -30,14 +30,14 @@
<script>
Alpine.data('showPostPage', () => ({
init() {
setupPostContent(this.$refs.postContent, this.$refs.postBody);
hljs.highlightAll();
codeBlockCopyButton(this.$refs.postBody);
processYoutubeOEmbeds();
processTwitterOEmbeds(this.$refs.postBody);
setupProgressBar(this.$refs.section, this.$refs.progressBar);
setupScrollToTopButton(this.$refs.scrollToTopBtn);
setupSharer();
setupPostContent(this.$refs.postContent, this.$refs.postBody);
scrollToAnchor();
}
}));
Expand Down

0 comments on commit 0c53d89

Please sign in to comment.