Files
futurewalker/app/Http/Controllers/Front/FrontPostController.php

133 lines
4.9 KiB
PHP

<?php
namespace App\Http\Controllers\Front;
use App\Http\Controllers\Controller;
use App\Models\Post;
use GrahamCampbell\Markdown\Facades\Markdown;
use Illuminate\Http\Request;
use Symfony\Component\DomCrawler\Crawler;
class FrontPostController extends Controller
{
public function index(Request $request, $slug)
{
$post = Post::where('slug', $slug)->where('status', 'publish')->first();
if (is_null($post)) {
return abort(404);
}
$content = Markdown::convert($post->body)->getContent();
//dd($content);
$content = $this->injectBootstrapClasses($content);
$content = $this->injectTableOfContents($content);
$content = $this->injectFeaturedImage($post, $content);
return view('front.single_post', compact('post', 'content'));
}
private function injectBootstrapClasses($content)
{
$crawler = new Crawler($content);
$crawler->filter('h1')->each(function (Crawler $node) {
$node->getNode(0)->setAttribute('class', trim($node->attr('class').' display-6 fw-bolder mt-3 mb-4'));
});
$crawler->filter('h2')->each(function (Crawler $node) {
$node->getNode(0)->setAttribute('class', trim($node->attr('class').'h4 mb-3'));
});
$crawler->filter('h3')->each(function (Crawler $node) {
$node->getNode(0)->setAttribute('class', trim($node->attr('class').'h6 mb-2'));
});
$crawler->filter('p')->each(function (Crawler $pNode) {
$precedingHeaders = $pNode->previousAll()->filter('h2');
// If there are no preceding <h2> tags, just process the <p>
if (! $precedingHeaders->count()) {
$existingClasses = $pNode->attr('class');
$newClasses = trim($existingClasses.' mt-2 mb-4');
$pNode->getNode(0)->setAttribute('class', $newClasses);
return;
}
$precedingHeader = $precedingHeaders->first();
if (trim($precedingHeader->text()) !== 'FAQs') {
$existingClasses = $pNode->attr('class');
$newClasses = trim($existingClasses.' mt-2 mb-4');
$pNode->getNode(0)->setAttribute('class', $newClasses);
}
if (strpos($pNode->text(), 'Q:') === 0) {
$currentClasses = $pNode->attr('class');
$newClasses = trim($currentClasses.' fw-bold');
$pNode->getNode(0)->setAttribute('class', $newClasses);
}
});
$crawler->filter('ul')->each(function (Crawler $node) {
$node->getNode(0)->setAttribute('class', trim($node->attr('class').'py-2'));
});
$crawler->filter('ol')->each(function (Crawler $node) {
$node->getNode(0)->setAttribute('class', trim($node->attr('class').'py-2'));
});
// Convert the modified DOM back to string
$modifiedContent = '';
foreach ($crawler as $domElement) {
$modifiedContent .= $domElement->ownerDocument->saveHTML($domElement);
}
return $modifiedContent;
}
private function injectTableOfContents($html)
{
$crawler = new Crawler($html);
// Create the Table of Contents
$toc = '<div class="p-3 rounded-3 bg-light mb-3"><ol>';
$crawler->filter('h2')->each(function (Crawler $node, $i) use (&$toc) {
$content = $node->text();
$id = 'link-'.$i; // Creating a simple id based on the index
$node->getNode(0)->setAttribute('id', $id); // Set the id to the h2 tag
$toc .= "<li class=\"py-1\"><a class=\"text-decoration-none hover-text-decoration-underline\" href='#{$id}'>{$content}</a></li>";
});
$toc .= '</ol></div>';
// Insert TOC after h1
$domDocument = $crawler->getNode(0)->ownerDocument;
$fragment = $domDocument->createDocumentFragment();
$fragment->appendXML($toc);
$h1Node = $crawler->filter('h1')->getNode(0);
$h1Node->parentNode->insertBefore($fragment, $h1Node->nextSibling);
// Get the updated HTML
$updatedHtml = $crawler->filter('body')->html();
return $updatedHtml;
}
private function injectFeaturedImage($post, $content)
{
if (! is_empty($post->featured_image)) {
$featured_image_alt = strtolower($post->short_title);
$featured_image_alt_caps = strtoupper($post->short_title);
$featured_image = "<div class=\"w-100 d-flex justify-content-center\"><figure class=\"text-center\"><img decoding=\"async\" class=\"img-fluid rounded mb-2 shadow\" src=\"{$post->featured_image_cdn}\" alt=\"{$featured_image_alt}\"><figcaption class=\"text-secondary small\">{$featured_image_alt_caps}</figcaption></figure></div>";
$content = preg_replace('/(<\/h1>)/', '$1'.$featured_image, $content, 1);
}
return $content;
}
}