Code Coverage |
||||||||||
Lines |
Functions and Methods |
Classes and Traits |
||||||||
| Total | |
9.09% |
3 / 33 |
|
16.67% |
1 / 6 |
CRAP | |
0.00% |
0 / 1 |
| OOUIModule | |
9.09% |
3 / 33 |
|
16.67% |
1 / 6 |
161.26 | |
0.00% |
0 / 1 |
| getSkinThemeMap | |
100.00% |
3 / 3 |
|
100.00% |
1 / 1 |
1 | |||
| getThemePaths | |
0.00% |
0 / 11 |
|
0.00% |
0 / 1 |
30 | |||
| getThemePath | |
0.00% |
0 / 10 |
|
0.00% |
0 / 1 |
6 | |||
| getThemeScriptsPath | |
0.00% |
0 / 3 |
|
0.00% |
0 / 1 |
6 | |||
| getThemeStylesPath | |
0.00% |
0 / 3 |
|
0.00% |
0 / 1 |
6 | |||
| getThemeImagesPath | |
0.00% |
0 / 3 |
|
0.00% |
0 / 1 |
6 | |||
| 1 | <?php |
| 2 | /** |
| 3 | * @license GPL-2.0-or-later |
| 4 | * @file |
| 5 | */ |
| 6 | |
| 7 | namespace MediaWiki\ResourceLoader; |
| 8 | |
| 9 | use InvalidArgumentException; |
| 10 | use MediaWiki\Registration\ExtensionRegistry; |
| 11 | |
| 12 | /** |
| 13 | * Convenience methods for dealing with OOUI themes and their relations to MW skins. |
| 14 | * |
| 15 | * @ingroup ResourceLoader |
| 16 | * @internal |
| 17 | */ |
| 18 | trait OOUIModule { |
| 19 | /** @var string[] */ |
| 20 | protected static $knownScriptsModules = [ 'core' ]; |
| 21 | /** @var string[] */ |
| 22 | protected static $knownStylesModules = [ 'core', 'widgets', 'toolbars', 'windows' ]; |
| 23 | /** @var string[] */ |
| 24 | protected static $knownImagesModules = [ |
| 25 | 'indicators', |
| 26 | // Extra icons |
| 27 | 'icons-accessibility', |
| 28 | 'icons-alerts', |
| 29 | 'icons-content', |
| 30 | 'icons-editing-advanced', |
| 31 | 'icons-editing-citation', |
| 32 | 'icons-editing-functions', |
| 33 | 'icons-editing-core', |
| 34 | 'icons-editing-list', |
| 35 | 'icons-editing-styling', |
| 36 | 'icons-interactions', |
| 37 | 'icons-layout', |
| 38 | 'icons-location', |
| 39 | 'icons-media', |
| 40 | 'icons-moderation', |
| 41 | 'icons-movement', |
| 42 | 'icons-user', |
| 43 | 'icons-wikimedia', |
| 44 | ]; |
| 45 | |
| 46 | /** @var string[] Note that keys must be lowercase, values TitleCase. */ |
| 47 | protected static $builtinSkinThemeMap = [ |
| 48 | 'default' => 'WikimediaUI', |
| 49 | ]; |
| 50 | |
| 51 | /** @var string[][] Note that keys must be TitleCase. */ |
| 52 | protected static $builtinThemePaths = [ |
| 53 | 'WikimediaUI' => [ |
| 54 | 'scripts' => 'resources/lib/ooui/oojs-ui-wikimediaui.js', |
| 55 | 'styles' => 'resources/lib/ooui/oojs-ui-{module}-wikimediaui.css', |
| 56 | 'images' => 'resources/lib/ooui/themes/wikimediaui/{module}.json', |
| 57 | ], |
| 58 | 'Apex' => [ |
| 59 | 'scripts' => 'resources/lib/ooui/oojs-ui-apex.js', |
| 60 | 'styles' => 'resources/lib/ooui/oojs-ui-{module}-apex.css', |
| 61 | 'images' => 'resources/lib/ooui/themes/apex/{module}.json', |
| 62 | ], |
| 63 | ]; |
| 64 | |
| 65 | /** |
| 66 | * Return a map of skin names (in lowercase) to OOUI theme names, defining which theme a given |
| 67 | * skin should use. |
| 68 | * |
| 69 | * @return array |
| 70 | */ |
| 71 | public static function getSkinThemeMap() { |
| 72 | $themeMap = self::$builtinSkinThemeMap; |
| 73 | $themeMap += ExtensionRegistry::getInstance()->getAttribute( 'SkinOOUIThemes' ); |
| 74 | return $themeMap; |
| 75 | } |
| 76 | |
| 77 | /** |
| 78 | * Return a map of theme names to lists of paths from which a given theme should be loaded. |
| 79 | * |
| 80 | * Keys are theme names, values are associative arrays. Keys of the inner array are 'scripts', |
| 81 | * 'styles', or 'images', and values are paths. Paths may be strings or FilePaths. |
| 82 | * |
| 83 | * Additionally, the string '{module}' in paths represents the name of the module to load. |
| 84 | * |
| 85 | * @return array |
| 86 | */ |
| 87 | protected static function getThemePaths() { |
| 88 | $themePaths = self::$builtinThemePaths; |
| 89 | $themePaths += ExtensionRegistry::getInstance()->getAttribute( 'OOUIThemePaths' ); |
| 90 | |
| 91 | [ $defaultLocalBasePath, $defaultRemoteBasePath ] = |
| 92 | FileModule::extractBasePaths(); |
| 93 | |
| 94 | // Allow custom themes' paths to be relative to the skin/extension that defines them, |
| 95 | // like with ResourceModuleSkinStyles |
| 96 | foreach ( $themePaths as &$paths ) { |
| 97 | [ $localBasePath, $remoteBasePath ] = |
| 98 | FileModule::extractBasePaths( $paths ); |
| 99 | if ( $localBasePath !== $defaultLocalBasePath || $remoteBasePath !== $defaultRemoteBasePath ) { |
| 100 | foreach ( $paths as &$path ) { |
| 101 | $path = new FilePath( $path, $localBasePath, $remoteBasePath ); |
| 102 | } |
| 103 | } |
| 104 | } |
| 105 | |
| 106 | return $themePaths; |
| 107 | } |
| 108 | |
| 109 | /** |
| 110 | * Return a path to load given module of given theme from. |
| 111 | * |
| 112 | * The file at this path may not exist. This should be handled by the caller (throwing an error or |
| 113 | * falling back to default theme). |
| 114 | * |
| 115 | * @param string $theme OOUI theme name, for example 'WikimediaUI' or 'Apex' |
| 116 | * @param string $kind Kind of the module: 'scripts', 'styles', or 'images' |
| 117 | * @param string $module Module name, for valid values see $knownScriptsModules, |
| 118 | * $knownStylesModules, $knownImagesModules |
| 119 | * @return string|FilePath |
| 120 | */ |
| 121 | protected function getThemePath( $theme, $kind, $module ) { |
| 122 | $paths = self::getThemePaths(); |
| 123 | $path = $paths[$theme][$kind]; |
| 124 | if ( $path instanceof FilePath ) { |
| 125 | $path = new FilePath( |
| 126 | str_replace( '{module}', $module, $path->getPath() ), |
| 127 | $path->getLocalBasePath(), |
| 128 | $path->getRemoteBasePath() |
| 129 | ); |
| 130 | } else { |
| 131 | $path = str_replace( '{module}', $module, $path ); |
| 132 | } |
| 133 | return $path; |
| 134 | } |
| 135 | |
| 136 | /** |
| 137 | * @param string $theme See getThemePath() |
| 138 | * @param string $module See getThemePath() |
| 139 | * @return string|FilePath |
| 140 | */ |
| 141 | protected function getThemeScriptsPath( $theme, $module ) { |
| 142 | if ( !in_array( $module, self::$knownScriptsModules ) ) { |
| 143 | throw new InvalidArgumentException( "Invalid OOUI scripts module '$module'" ); |
| 144 | } |
| 145 | return $this->getThemePath( $theme, 'scripts', $module ); |
| 146 | } |
| 147 | |
| 148 | /** |
| 149 | * @param string $theme See getThemePath() |
| 150 | * @param string $module See getThemePath() |
| 151 | * @return string|FilePath |
| 152 | */ |
| 153 | protected function getThemeStylesPath( $theme, $module ) { |
| 154 | if ( !in_array( $module, self::$knownStylesModules ) ) { |
| 155 | throw new InvalidArgumentException( "Invalid OOUI styles module '$module'" ); |
| 156 | } |
| 157 | return $this->getThemePath( $theme, 'styles', $module ); |
| 158 | } |
| 159 | |
| 160 | /** |
| 161 | * @param string $theme See getThemePath() |
| 162 | * @param string $module See getThemePath() |
| 163 | * @return string|FilePath |
| 164 | */ |
| 165 | protected function getThemeImagesPath( $theme, $module ) { |
| 166 | if ( !in_array( $module, self::$knownImagesModules ) ) { |
| 167 | throw new InvalidArgumentException( "Invalid OOUI images module '$module'" ); |
| 168 | } |
| 169 | return $this->getThemePath( $theme, 'images', $module ); |
| 170 | } |
| 171 | } |