MediaWiki master
TraditionalImageGallery.php
Go to the documentation of this file.
1<?php
2
12use Wikimedia\Assert\Assert;
13
47 public function toHTML() {
48 $resolveFilesViaParser = $this->mParser instanceof Parser;
49 if ( $resolveFilesViaParser ) {
50 $parserOutput = $this->mParser->getOutput();
51 $repoGroup = null;
52 $linkRenderer = $this->mParser->getLinkRenderer();
53 $badFileLookup = $this->mParser->getBadFileLookup();
54 } else {
55 $parserOutput = $this->getOutput();
56 $services = MediaWikiServices::getInstance();
57 $repoGroup = $services->getRepoGroup();
58 $linkRenderer = $services->getLinkRenderer();
59 $badFileLookup = $services->getBadFileLookup();
60 }
61
62 Html::addClass( $this->mAttribs['class'], 'gallery' );
63 Html::addClass( $this->mAttribs['class'], 'mw-gallery-' . $this->mMode );
64
65 if ( $this->mPerRow > 0 ) {
66 $maxwidth = $this->mPerRow * ( $this->mWidths + $this->getAllPadding() );
67 $oldStyle = $this->mAttribs['style'] ?? '';
68 $this->mAttribs['style'] = "max-width: {$maxwidth}px;" . $oldStyle;
69 }
70
71 $parserOutput->addModules( $this->getModules() );
72 $parserOutput->addModuleStyles( [ 'mediawiki.page.gallery.styles' ] );
73 $output = Html::openElement( 'ul', $this->mAttribs );
74 if ( $this->mCaption ) {
75 $output .= "\n\t" . Html::rawElement( 'li', [ 'class' => 'gallerycaption' ], $this->mCaption );
76 }
77
78 if ( $this->mShowFilename ) {
79 // Preload LinkCache info for when generating links
80 // of the filename below
81 $linkBatchFactory = MediaWikiServices::getInstance()->getLinkBatchFactory();
82 $lb = $linkBatchFactory->newLinkBatch()->setCaller( __METHOD__ );
83 foreach ( $this->mImages as [ $title, /* see below */ ] ) {
84 $lb->addObj( $title );
85 }
86 $lb->execute();
87 }
88
89 $lang = $this->getRenderLang();
90 $hookRunner = new HookRunner( MediaWikiServices::getInstance()->getHookContainer() );
91
92 # Output each image...
93 foreach ( $this->mImages as [ $nt, $text, $alt, $link, $handlerOpts, $loading, $imageOptions ] ) {
94 // "text" means "caption" here
97 $descQuery = false;
98 if ( $nt->inNamespace( NS_FILE ) && !$nt->isExternal() ) {
99 # Get the file...
100 if ( $resolveFilesViaParser ) {
101 # Give extensions a chance to select the file revision for us
102 $options = [];
103 $hookRunner->onBeforeParserFetchFileAndTitle(
104 // @phan-suppress-next-line PhanTypeMismatchArgument Type mismatch on pass-by-ref args
105 $this->mParser, $nt, $options, $descQuery );
106 # Fetch and register the file (file title may be different via hooks)
107 [ $img, $nt ] = $this->mParser->fetchFileAndTitle( $nt, $options );
108 } else {
109 $img = $repoGroup->findFile( $nt );
110 }
111 } else {
112 $img = false;
113 }
114
115 $transformOptions = $this->getThumbParams( $img ) + $handlerOpts;
116 $thumb = $img ? $img->transform( $transformOptions ) : false;
117
118 $rdfaType = 'mw:File';
119
120 $isBadFile = $img && $thumb && $this->mHideBadImages &&
121 $badFileLookup->isBadFile( $nt->getDBkey(), $this->getContextTitle() );
122
123 if ( !$img || !$thumb || $thumb->isError() || $isBadFile ) {
124 $rdfaType = 'mw:Error ' . $rdfaType;
125
126 $currentExists = $img && $img->exists();
127 if ( $currentExists && !$thumb ) {
128 $label = wfMessage( 'thumbnail_error', '' )->text();
129 } elseif ( $thumb && $thumb->isError() ) {
130 Assert::invariant(
131 $thumb instanceof MediaTransformError,
132 'Unknown MediaTransformOutput: ' . get_class( $thumb )
133 );
134 $label = $thumb->toText();
135 } else {
136 $label = $alt ?? '';
137 }
138 $thumbhtml = Linker::makeBrokenImageLinkObj(
139 $nt, $label, '', '', '', false, $transformOptions, $currentExists
140 );
141 $thumbhtml = Html::rawElement( 'span', [ 'typeof' => $rdfaType ], $thumbhtml );
142
143 $thumbhtml = "\n\t\t\t" . Html::rawElement(
144 'div',
145 [
146 'class' => 'thumb',
147 'style' => 'height: ' . ( $this->getThumbPadding() + $this->mHeights ) . 'px;'
148 ],
149 $thumbhtml
150 );
151
152 if ( !$img && $resolveFilesViaParser ) {
153 $this->mParser->addTrackingCategory( 'broken-file-category' );
154 }
155 } else {
157 $vpad = $this->getVPad( $this->mHeights, $thumb->getHeight() );
158
159 // Backwards compat before the $imageOptions existed
160 if ( $imageOptions === null ) {
161 $imageParameters = [
162 'desc-link' => true,
163 'desc-query' => $descQuery,
164 'alt' => $alt ?? '',
165 'custom-url-link' => $link
166 ];
167 } else {
168 $params = [];
169 // An empty alt indicates an image is not a key part of the
170 // content and that non-visual browsers may omit it from
171 // rendering. Only set the parameter if it's explicitly
172 // requested.
173 if ( $alt !== null ) {
174 $params['alt'] = $alt;
175 }
176 $params['title'] = $imageOptions['title'];
177 $params['img-class'] = 'mw-file-element';
178 $imageParameters = Linker::getImageLinkMTOParams(
179 $imageOptions, $descQuery, $this->mParser
180 ) + $params;
181 }
182
183 if ( $loading === ImageGalleryBase::LOADING_LAZY ) {
184 $imageParameters['loading'] = 'lazy';
185 }
186
187 $this->adjustImageParameters( $thumb, $imageParameters );
188
189 Linker::processResponsiveImages( $img, $thumb, $transformOptions );
190
191 $thumbhtml = $thumb->toHtml( $imageParameters );
192 $thumbhtml = Html::rawElement(
193 'span', [ 'typeof' => $rdfaType ], $thumbhtml
194 );
195
196 # Set both fixed width and min-height.
197 $width = $this->getThumbDivWidth( $thumb->getWidth() );
198 $height = $this->getThumbPadding() + $this->mHeights;
199 $thumbhtml = "\n\t\t\t" . Html::rawElement( 'div', [
200 'class' => 'thumb',
201 'style' => "width: {$width}px;" .
202 ( $this->mMode === 'traditional' ? " height: {$height}px;" : '' ),
203 ], $thumbhtml );
204
205 // Call parser transform hook
206 if ( $resolveFilesViaParser ) {
208 $handler = $img->getHandler();
209 if ( $handler ) {
210 $handler->parserTransformHook( $this->mParser, $img );
211 }
212 $this->mParser->modifyImageHtml(
213 $img, [ 'handler' => $imageParameters ], $thumbhtml );
214 }
215 }
216
217 $meta = [];
218 if ( $img ) {
219 if ( $this->mShowDimensions ) {
220 $meta[] = htmlspecialchars( $img->getDimensionsString() );
221 }
222 if ( $this->mShowBytes ) {
223 $meta[] = htmlspecialchars( $lang->formatSize( $img->getSize() ) );
224 }
225 } elseif ( $this->mShowDimensions || $this->mShowBytes ) {
226 $meta[] = $this->msg( 'filemissing' )->escaped();
227 }
228 $meta = $lang->semicolonList( $meta );
229 if ( $meta ) {
230 $meta .= Html::rawElement( 'br', [] ) . "\n";
231 }
232
233 $textlink = $this->mShowFilename ?
234 $this->getCaptionHtml( $nt, $lang, $linkRenderer ) :
235 '';
236
237 $galleryText = $this->wrapGalleryText( $textlink . $text . $meta, $thumb );
238
239 $gbWidth = $this->getGBWidthOverwrite( $thumb ) ?: $this->getGBWidth( $thumb ) . 'px';
240 # Weird double wrapping (the extra div inside the li) needed due to FF2 bug
241 # Can be safely removed if FF2 falls completely out of existence
242 $output .= "\n\t\t" .
243 Html::rawElement(
244 'li',
245 [ 'class' => 'gallerybox', 'style' => 'width: ' . $gbWidth ],
246 $thumbhtml
247 . $galleryText
248 . "\n\t\t"
249 );
250 }
251 $output .= "\n" . Html::closeElement( 'ul' );
252
253 return $output;
254 }
255
262 protected function getCaptionHtml( Title $nt, Language $lang, LinkRenderer $linkRenderer ) {
263 // Preloaded into LinkCache in toHTML
264 return $linkRenderer->makeKnownLink(
265 $nt,
266 is_int( $this->getCaptionLength() ) ?
267 $lang->truncateForVisual( $nt->getText(), $this->getCaptionLength() ) :
268 $nt->getText(),
269 [
270 'class' => 'galleryfilename' .
271 ( $this->getCaptionLength() === true ? ' galleryfilename-truncate' : '' )
272 ]
273 ) . "\n";
274 }
275
284 protected function wrapGalleryText( $galleryText, $thumb ) {
285 return "\n\t\t\t" . Html::rawElement( 'div', [ 'class' => "gallerytext" ], $galleryText );
286 }
287
294 protected function getThumbPadding() {
295 return 30;
296 }
297
303 protected function getGBPadding() {
304 return 5;
305 }
306
314 protected function getGBBorders() {
315 return 8;
316 }
317
325 protected function getCaptionLength() {
327 }
328
334 protected function getAllPadding() {
335 return $this->getThumbPadding() + $this->getGBPadding() + $this->getGBBorders();
336 }
337
347 protected function getVPad( $boxHeight, $thumbHeight ) {
348 return ( $this->getThumbPadding() + $boxHeight - $thumbHeight ) / 2;
349 }
350
357 protected function getThumbParams( $img ) {
358 return [
359 'width' => $this->mWidths,
360 'height' => $this->mHeights
361 ];
362 }
363
371 protected function getThumbDivWidth( $thumbWidth ) {
372 return $this->mWidths + $this->getThumbPadding();
373 }
374
385 protected function getGBWidth( $thumb ) {
386 return $this->mWidths + $this->getThumbPadding() + $this->getGBPadding();
387 }
388
400 protected function getGBWidthOverwrite( $thumb ) {
401 return false;
402 }
403
411 protected function getModules() {
412 return [];
413 }
414
422 protected function adjustImageParameters( $thumb, &$imageParameters ) {
423 }
424}
const NS_FILE
Definition Defines.php:71
wfMessage( $key,... $params)
This is the function for getting translated interface messages.
bool int $mCaptionLength
Length to truncate filename to in caption when using "showfilename".
getRenderLang()
Determines the correct language to be used for this image gallery.
Basic media transform error class.
Base class for the output of MediaHandler::doTransform() and File::transform().
msg( $key,... $params)
Get a Message object with context set Parameters are the same as wfMessage()
Implements some public methods and some protected utility functions which are required by multiple ch...
Definition File.php:93
This class provides an implementation of the core hook interfaces, forwarding hook calls to HookConta...
This class is a collection of static functions that serve two purposes:
Definition Html.php:57
Base class for language-specific code.
Definition Language.php:81
truncateForVisual( $string, $length, $ellipsis='...', $adjustLength=true)
Truncate a string to a specified number of characters, appending an optional string (e....
Class that generates HTML for internal links.
makeKnownLink( $target, $text=null, array $extraAttribs=[], array $query=[])
Make a link that's styled as if the target page exists (usually a "blue link", although the styling m...
Some internal bits split of from Skin.php.
Definition Linker.php:61
Service locator for MediaWiki core services.
PHP Parser - Processes wiki markup (which uses a more user-friendly syntax, such as "[[link]]" for ma...
Definition Parser.php:147
Represents a title within MediaWiki.
Definition Title.php:78
exists( $flags=0)
Check if page exists.
Definition Title.php:3152
getText()
Get the text form (spaces not underscores) of the main part.
Definition Title.php:1019
getThumbPadding()
How much padding the thumb has between the image and the inner div that contains the border.
getCaptionLength()
Length (in characters) to truncate filename to in caption when using "showfilename" (if int).
getVPad( $boxHeight, $thumbHeight)
Get vertical padding for a thumbnail.
getCaptionHtml(Title $nt, Language $lang, LinkRenderer $linkRenderer)
getThumbParams( $img)
Get the transform parameters for a thumbnail.
toHTML()
Return a HTML representation of the image gallery.
getGBWidth( $thumb)
Computed width of gallerybox .
getModules()
Get a list of modules to include in the page.
getGBBorders()
Get how much extra space the borders around the image takes up.
wrapGalleryText( $galleryText, $thumb)
Add the wrapper html around the thumb's caption.
adjustImageParameters( $thumb, &$imageParameters)
Adjust the image parameters for a thumbnail.
getGBWidthOverwrite( $thumb)
Allows overwriting the computed width of the gallerybox with a string, like '100'.
getThumbDivWidth( $thumbWidth)
Get the width of the inner div that contains the thumbnail in question.