No flicker when rendering thumbnails
Some checks failed
DokuWiki Default Tasks / all (push) Has been cancelled
Some checks failed
DokuWiki Default Tasks / all (push) Has been cancelled
This commit is contained in:
56
Output.php
56
Output.php
@@ -56,6 +56,7 @@ class Output
|
||||
|
||||
$thumbW = 150;
|
||||
$thumbH = 150;
|
||||
$thumbQ = 80;
|
||||
|
||||
$placeholderUrl = DOKU_BASE . 'lib/images/blank.gif';
|
||||
$syntax = plugin_load('syntax', 'luxtools');
|
||||
@@ -81,12 +82,21 @@ class Output
|
||||
$safePlaceholderUrl = hsc($placeholderUrl);
|
||||
$label = hsc($item['name']);
|
||||
|
||||
$renderer->doc .= '<a href="' . $safeUrl . '" class="media" title="' . $label . '">';
|
||||
$initialSrc = $safePlaceholderUrl;
|
||||
$dataThumb = ' data-thumb-src="' . $safeThumbUrl . '"';
|
||||
$thumbCachePath = $this->thumbCachePathForItem($item, $thumbW, $thumbH, $thumbQ);
|
||||
if (is_string($thumbCachePath) && $thumbCachePath !== '' && @is_file($thumbCachePath)) {
|
||||
// Thumb already exists: start with it immediately (no JS swap needed)
|
||||
$initialSrc = $safeThumbUrl;
|
||||
$dataThumb = '';
|
||||
}
|
||||
|
||||
$renderer->doc .= '<a href="' . $safeUrl . '" class="media" title="' . $label . '" aria-label="' . $label . '">';
|
||||
$renderer->doc .= '<img'
|
||||
. ' class="luxtools-thumb"'
|
||||
. ' src="' . $safePlaceholderUrl . '"'
|
||||
. ' data-thumb-src="' . $safeThumbUrl . '"'
|
||||
. ' alt="' . $label . '"'
|
||||
. ' src="' . $initialSrc . '"'
|
||||
. $dataThumb
|
||||
. ' alt=""'
|
||||
. ' width="' . $thumbW . '"'
|
||||
. ' height="' . $thumbH . '"'
|
||||
. ' loading="lazy"'
|
||||
@@ -122,6 +132,44 @@ class Output
|
||||
return $url . $glue . http_build_query($params, '', '&', PHP_QUERY_RFC3986) . $fragment;
|
||||
}
|
||||
|
||||
/**
|
||||
* Compute the expected thumbnail cache path for an item.
|
||||
*
|
||||
* Mirrors the hashing scheme in file.php so we can detect whether a thumb
|
||||
* already exists and can be used immediately.
|
||||
*
|
||||
* @param array $item
|
||||
* @param int $w
|
||||
* @param int $h
|
||||
* @param int $q
|
||||
* @return string|null
|
||||
*/
|
||||
protected function thumbCachePathForItem(array $item, int $w, int $h, int $q): ?string
|
||||
{
|
||||
if (!isset($item['path']) || !is_string($item['path']) || $item['path'] === '') return null;
|
||||
if (!isset($item['mtime'])) return null;
|
||||
|
||||
$path = $item['path'];
|
||||
$mtime = (int)$item['mtime'];
|
||||
|
||||
// Decide output format the same way file.php does.
|
||||
try {
|
||||
[, $mime,] = mimetype($path, false);
|
||||
} catch (\Throwable $e) {
|
||||
return null;
|
||||
}
|
||||
if (!is_string($mime) || !str_starts_with($mime, 'image/')) return null;
|
||||
$dstFormat = ($mime === 'image/png' || $mime === 'image/gif') ? 'png' : 'jpg';
|
||||
|
||||
global $conf;
|
||||
if (!isset($conf['cachedir']) || !is_string($conf['cachedir']) || trim($conf['cachedir']) === '') return null;
|
||||
|
||||
$hash = sha1($path . '|' . $mtime . '|w=' . $w . '|h=' . $h . '|q=' . $q . '|f=' . $dstFormat);
|
||||
$sub = substr($hash, 0, 2);
|
||||
$cacheDir = rtrim($conf['cachedir'], '/');
|
||||
return $cacheDir . '/luxtools/thumbs/' . $sub . '/' . $hash . '.' . $dstFormat;
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders the files as a table, including details if configured that way.
|
||||
*
|
||||
|
||||
@@ -239,7 +239,7 @@ class plugin_luxtools_test extends DokuWikiTest
|
||||
$this->structureCheck($doc, $structure);
|
||||
|
||||
$this->assertStringContainsString('exampleimage.png', $xhtml);
|
||||
$this->assertStringContainsString('data-thumb-src=', $xhtml);
|
||||
$this->assertStringContainsString('thumb=1', $xhtml);
|
||||
$this->assertStringContainsString('width="150"', $xhtml);
|
||||
$this->assertStringContainsString('height="150"', $xhtml);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user