Skip to content

Commit

Permalink
Extract CSS providers
Browse files Browse the repository at this point in the history
  • Loading branch information
jdreesen committed Mar 1, 2024
1 parent 12d7000 commit 2b772ce
Show file tree
Hide file tree
Showing 11 changed files with 238 additions and 57 deletions.
8 changes: 8 additions & 0 deletions config/services.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@

use Neusta\Pimcore\BackendBrandingBundle\Controller\CssController;
use Neusta\Pimcore\BackendBrandingBundle\Controller\JsController;
use Neusta\Pimcore\BackendBrandingBundle\CssProvider;
use Neusta\Pimcore\BackendBrandingBundle\EventListener\BackendAssetsListener;
use Neusta\Pimcore\BackendBrandingBundle\EventListener\BackendResponseListener;

Expand All @@ -21,9 +22,16 @@
->autoconfigure()
->arg('$env', '%kernel.runtime_environment%')
->arg('$config', param('neusta_pimcore_backend_branding.environments'))
->arg('$cssProvider', service(CssProvider::class))
->set(JsController::class)
->autoconfigure()
->arg('$env', '%kernel.runtime_environment%')
->arg('$config', param('neusta_pimcore_backend_branding.environments'))
->set(CssProvider::class)
->autoconfigure()
->arg('$providers', tagged_iterator('neusta_pimcore_backend_branding.css_provider'))
->load('Neusta\Pimcore\BackendBrandingBundle\CssProvider\\', '../src/CssProvider')
->autoconfigure()
->exclude('../src/CssProvider/*Config.php')
;
};
9 changes: 9 additions & 0 deletions src/Attributes/AsCssProvider.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\Attributes;

#[\Attribute(\Attribute::TARGET_CLASS)]
final class AsCssProvider
{
}
62 changes: 5 additions & 57 deletions src/Controller/CssController.php
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,8 @@

namespace Neusta\Pimcore\BackendBrandingBundle\Controller;

use Neusta\Pimcore\BackendBrandingBundle\Css\CssProperty;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRuleList;
use Neusta\Pimcore\BackendBrandingBundle\CssProvider;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\HttpKernel\Attribute\AsController;
use Symfony\Component\Routing\Annotation\Route;
Expand All @@ -14,16 +13,12 @@
final class CssController
{
/**
* @param array<string, array{
* bezelColor: string,
* sidebarColor: string,
* signet: array{url: string, size: string, position: string, color: string|null},
* tabBarIcon: array{url: string, size: string|null, position: string|null},
* }> $config
* @param array<string, array<mixed>> $config Configuration by environment
*/
public function __construct(
private readonly string $env,
private readonly array $config,
private readonly CssProvider $cssProvider,
) {
}

Expand All @@ -32,55 +27,8 @@ public function __invoke(): Response
$config = $this->config[$this->env] ?? [];
$css = new CssRuleList();

if (isset($config['bezelColor'])) {
$bezelColor = new CssProperty('background-color', $config['bezelColor']);
$css->addRule(new CssRule('body.x-body #pimcore_body', $bezelColor));
$css->addRule(new CssRule('body.x-body #pimcore_loading.loaded', $bezelColor));
$css->addRule(new CssRule('body.x-body .sf-minitoolbar', $bezelColor));
$css->addRule(new CssRule('body.x-body #pimcore_panel_tabs > .x-panel-bodyWrap > .x-tab-bar', $bezelColor));
$css->addRule(new CssRule('#pimcore_loading.loaded', $bezelColor));
$css->addRule(new CssRule('.x-body .sf-minitoolbar', $bezelColor));
}

if (isset($config['sidebarColor'])) {
$sidebarColor = new CssProperty('background-color', $config['sidebarColor']);
$css->addRule(new CssRule('#pimcore_sidebar', $sidebarColor));
$css->addRule(new CssRule('#pimcore_loading.loaded', $sidebarColor));
$css->addRule(new CssRule('.x-body .sf-minitoolbar', $sidebarColor));
}

if (isset($config['signet'])) {
$signet = new CssRule('#pimcore_signet',
new CssProperty('background-image', $config['signet']['url'], isUrl: true),
new CssProperty('background-size', $config['signet']['size']),
new CssProperty('background-position', $config['signet']['position']),
);

if (isset($config['signet']['color'])) {
$signet->setProperty(new CssProperty('background-color', $config['signet']['color'], isImportant: true));

$css->addRule(new CssRule('#pimcore_avatar',
new CssProperty('background-color', $config['signet']['color'], isImportant: true),
));
}

$css->addRule($signet);
}

if (isset($config['tabBarIcon'])) {
$tabBarIcon = new CssRule('#pimcore_panel_tabs > .x-panel-bodyWrap > .x-tab-bar',
new CssProperty('background-image', $config['tabBarIcon']['url'], isUrl: true),
);

if (isset($config['tabBarIcon']['size'])) {
$tabBarIcon->setProperty(new CssProperty('background-size', $config['tabBarIcon']['size']));
}

if (isset($config['tabBarIcon']['position'])) {
$tabBarIcon->setProperty(new CssProperty('background-position', $config['tabBarIcon']['position']));
}

$css->addRule($tabBarIcon);
foreach (($this->cssProvider)($config) as $rule) {
$css->addRule($rule);
}

return new Response($css->toString(), Response::HTTP_OK, ['Content-type' => 'text/css']);
Expand Down
63 changes: 63 additions & 0 deletions src/CssProvider.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle;

use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;

final class CssProvider
{
/**
* @param iterable<callable():iterable<CssRule>> $providers
*/
public function __construct(
private readonly iterable $providers,
) {
}

/**
* @param array<mixed> $config
*
* @return iterable<CssRule>
*/
public function __invoke(array $config): iterable
{
foreach ($this->providers as $provider) {
\assert(\is_callable($provider), sprintf('Provider "%s" is not callable.', get_debug_type($provider)));

$reflector = new \ReflectionFunction($provider(...));

$arguments = [];
foreach ($reflector->getParameters() as $parameter) {
$name = $parameter->getName();
$type = $parameter->getType();

\assert(
$type instanceof \ReflectionNamedType,
sprintf('Parameter "%s" of provider "%s" has no or more than one type.', $name, get_debug_type($provider)),
);

$typeName = $type->getName();

\assert(
\in_array($typeName, ['array', 'bool', 'float', 'int', 'string']) || class_exists($typeName),
sprintf('Parameter "%s" of provider "%s" has an unsupported type "%s".', $name, get_debug_type($provider), $typeName),
);

if (isset($config[$name])) {
$argument = $config[$name];

if (class_exists($typeName)) {
$argument = new $typeName(...$argument);
}

$arguments[$name] = $argument;
}
}

if ($arguments || !$reflector->getNumberOfParameters()) {
yield from $provider(...$arguments);
}
}
}
}
27 changes: 27 additions & 0 deletions src/CssProvider/BezelColor.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

use Neusta\Pimcore\BackendBrandingBundle\Attributes\AsCssProvider;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssProperty;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;

#[AsCssProvider]
final class BezelColor
{
/**
* @return iterable<CssRule>
*/
public function __invoke(string $bezelColor): iterable
{
$backgroundColor = new CssProperty('background-color', $bezelColor);

yield new CssRule('body.x-body #pimcore_body', $backgroundColor);
yield new CssRule('body.x-body #pimcore_loading.loaded', $backgroundColor);
yield new CssRule('body.x-body .sf-minitoolbar', $backgroundColor);
yield new CssRule('body.x-body #pimcore_panel_tabs > .x-panel-bodyWrap > .x-tab-bar', $backgroundColor);
yield new CssRule('#pimcore_loading.loaded', $backgroundColor);
yield new CssRule('.x-body .sf-minitoolbar', $backgroundColor);
}
}
24 changes: 24 additions & 0 deletions src/CssProvider/SidebarColor.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

use Neusta\Pimcore\BackendBrandingBundle\Attributes\AsCssProvider;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssProperty;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;

#[AsCssProvider]
final class SidebarColor
{
/**
* @return iterable<CssRule>
*/
public function __invoke(string $sidebarColor): iterable
{
$backgroundColor = new CssProperty('background-color', $sidebarColor);

yield new CssRule('#pimcore_sidebar', $backgroundColor);
yield new CssRule('#pimcore_loading.loaded', $backgroundColor);
yield new CssRule('.x-body .sf-minitoolbar', $backgroundColor);
}
}
32 changes: 32 additions & 0 deletions src/CssProvider/Signet.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

use Neusta\Pimcore\BackendBrandingBundle\Attributes\AsCssProvider;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssProperty;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;

#[AsCssProvider]
final class Signet
{
/**
* @return iterable<CssRule>
*/
public function __invoke(SignetConfig $signet): iterable
{
yield $signetRule = new CssRule('#pimcore_signet',
new CssProperty('background-image', $signet->url, isUrl: true),
new CssProperty('background-size', $signet->size),
new CssProperty('background-position', $signet->position),
);

if (isset($signet->color)) {
$signetRule->setProperty(new CssProperty('background-color', $signet->color, isImportant: true));

yield new CssRule('#pimcore_avatar',
new CssProperty('background-color', $signet->color, isImportant: true),
);
}
}
}
15 changes: 15 additions & 0 deletions src/CssProvider/SignetConfig.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

final class SignetConfig
{
public function __construct(
public readonly string $url,
public readonly string $size,
public readonly string $position,
public readonly ?string $color = null,
) {
}
}
32 changes: 32 additions & 0 deletions src/CssProvider/TabBarIcon.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

use Neusta\Pimcore\BackendBrandingBundle\Attributes\AsCssProvider;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssProperty;
use Neusta\Pimcore\BackendBrandingBundle\Css\CssRule;

#[AsCssProvider]
final class TabBarIcon
{
/**
* @return iterable<CssRule>
*/
public function __invoke(TabBarIconConfig $tabBarIcon): iterable
{
$tabBarIconRule = new CssRule('#pimcore_panel_tabs > .x-panel-bodyWrap > .x-tab-bar',
new CssProperty('background-image', $tabBarIcon->url, isUrl: true),
);

if (isset($tabBarIcon->size)) {
$tabBarIconRule->setProperty(new CssProperty('background-size', $tabBarIcon->size));
}

if (isset($tabBarIcon->position)) {
$tabBarIconRule->setProperty(new CssProperty('background-position', $tabBarIcon->position));
}

yield $tabBarIconRule;
}
}
14 changes: 14 additions & 0 deletions src/CssProvider/TabBarIconConfig.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
<?php
declare(strict_types=1);

namespace Neusta\Pimcore\BackendBrandingBundle\CssProvider;

final class TabBarIconConfig
{
public function __construct(
public readonly string $url,
public readonly ?string $size = null,
public readonly ?string $position = null,
) {
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,9 @@

namespace Neusta\Pimcore\BackendBrandingBundle\DependencyInjection;

use Neusta\Pimcore\BackendBrandingBundle\Attributes\AsCssProvider;
use Symfony\Component\Config\FileLocator;
use Symfony\Component\DependencyInjection\ChildDefinition;
use Symfony\Component\DependencyInjection\ContainerBuilder;
use Symfony\Component\DependencyInjection\Loader\PhpFileLoader;
use Symfony\Component\HttpKernel\DependencyInjection\ConfigurableExtension;
Expand All @@ -19,5 +21,12 @@ protected function loadInternal(array $mergedConfig, ContainerBuilder $container
$loader->load('services.php');

$container->setParameter('neusta_pimcore_backend_branding.environments', $mergedConfig['environments']);

$container->registerAttributeForAutoconfiguration(
AsCssProvider::class,
static function (ChildDefinition $definition, AsCssProvider $attribute): void {
$definition->addTag('neusta_pimcore_backend_branding.css_provider');
},
);
}
}

0 comments on commit 2b772ce

Please sign in to comment.