dynamic branding options (#1205)
This commit is contained in:
@@ -26,9 +26,6 @@ trait StringAccessibleConfigTrait
|
||||
*/
|
||||
protected $initialized = false;
|
||||
|
||||
/**
|
||||
* @param array $settings
|
||||
*/
|
||||
public function __construct(ConfigLoaderInterface $repository, array $settings)
|
||||
{
|
||||
$this->repository = $repository;
|
||||
@@ -120,4 +117,45 @@ trait StringAccessibleConfigTrait
|
||||
|
||||
return $config[$search];
|
||||
}
|
||||
|
||||
/**
|
||||
* @return bool
|
||||
*/
|
||||
public function offsetExists($offset)
|
||||
{
|
||||
try {
|
||||
$this->find($offset);
|
||||
} catch (\Exception $ex) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return mixed
|
||||
*/
|
||||
public function offsetGet($offset)
|
||||
{
|
||||
return $this->find($offset);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mixed $offset
|
||||
* @param mixed $value
|
||||
* @throws \BadMethodCallException
|
||||
*/
|
||||
public function offsetSet($offset, $value)
|
||||
{
|
||||
throw new \BadMethodCallException('SystemBundleConfiguration does not support offsetSet()');
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mixed $offset
|
||||
* @throws \BadMethodCallException
|
||||
*/
|
||||
public function offsetUnset($offset)
|
||||
{
|
||||
throw new \BadMethodCallException('SystemBundleConfiguration does not support offsetUnset()');
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,7 +9,7 @@
|
||||
|
||||
namespace App\Configuration;
|
||||
|
||||
class ThemeConfiguration implements SystemBundleConfiguration
|
||||
class ThemeConfiguration implements SystemBundleConfiguration, \ArrayAccess
|
||||
{
|
||||
use StringAccessibleConfigTrait;
|
||||
|
||||
|
||||
@@ -312,6 +312,30 @@ class SystemConfigurationController extends AbstractController
|
||||
->setType(TextType::class)
|
||||
->setConstraints([new DateTime(['format' => 'H:i']), new NotNull()]),
|
||||
]),
|
||||
(new SystemConfigurationModel())
|
||||
->setSection(SystemConfigurationModel::SECTION_BRANDING)
|
||||
->setConfiguration([
|
||||
(new Configuration())
|
||||
->setName('theme.branding.logo')
|
||||
->setTranslationDomain('system-configuration')
|
||||
->setRequired(false)
|
||||
->setType(TextType::class),
|
||||
(new Configuration())
|
||||
->setName('theme.branding.company')
|
||||
->setTranslationDomain('system-configuration')
|
||||
->setRequired(false)
|
||||
->setType(TextType::class),
|
||||
(new Configuration())
|
||||
->setName('theme.branding.mini')
|
||||
->setTranslationDomain('system-configuration')
|
||||
->setRequired(false)
|
||||
->setType(TextType::class),
|
||||
(new Configuration())
|
||||
->setName('theme.branding.title')
|
||||
->setTranslationDomain('system-configuration')
|
||||
->setRequired(false)
|
||||
->setType(TextType::class),
|
||||
]),
|
||||
];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -9,6 +9,7 @@
|
||||
|
||||
namespace App\DependencyInjection\Compiler;
|
||||
|
||||
use App\Configuration\ThemeConfiguration;
|
||||
use Symfony\Component\DependencyInjection\Compiler\CompilerPassInterface;
|
||||
use Symfony\Component\DependencyInjection\ContainerBuilder;
|
||||
|
||||
@@ -24,8 +25,8 @@ class TwigContextCompilerPass implements CompilerPassInterface
|
||||
public function process(ContainerBuilder $container)
|
||||
{
|
||||
$twig = $container->getDefinition('twig');
|
||||
$theme = $container->getParameter('kimai.theme');
|
||||
|
||||
$theme = $container->getDefinition(ThemeConfiguration::class);
|
||||
$twig->addMethodCall('addGlobal', ['kimai_context', $theme]);
|
||||
|
||||
if ($container->hasDefinition('twig.loader.native_filesystem')) {
|
||||
|
||||
@@ -33,6 +33,10 @@ final class Configuration
|
||||
* @var string
|
||||
*/
|
||||
private $type;
|
||||
/**
|
||||
* @var array
|
||||
*/
|
||||
private $options = [];
|
||||
/**
|
||||
* @var bool
|
||||
*/
|
||||
@@ -155,4 +159,16 @@ final class Configuration
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function getOptions(): array
|
||||
{
|
||||
return $this->options;
|
||||
}
|
||||
|
||||
public function setOptions(array $options): Configuration
|
||||
{
|
||||
$this->options = $options;
|
||||
|
||||
return $this;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -16,6 +16,7 @@ class SystemConfiguration
|
||||
public const SECTION_FORM_USER = 'form_user';
|
||||
public const SECTION_THEME = 'theme';
|
||||
public const SECTION_CALENDAR = 'calendar';
|
||||
public const SECTION_BRANDING = 'branding';
|
||||
|
||||
/**
|
||||
* @var string
|
||||
|
||||
@@ -54,13 +54,15 @@ class SystemConfigurationType extends AbstractType
|
||||
$type = HiddenType::class;
|
||||
}
|
||||
|
||||
$event->getForm()->add('value', $type, [
|
||||
$options = [
|
||||
'label' => 'label.' . ($preference->getLabel() ?? $preference->getName()),
|
||||
'constraints' => $preference->getConstraints(),
|
||||
'required' => $required,
|
||||
'disabled' => !$preference->isEnabled(),
|
||||
'translation_domain' => $preference->getTranslationDomain(),
|
||||
]);
|
||||
];
|
||||
|
||||
$event->getForm()->add('value', $type, array_merge($options, $preference->getOptions()));
|
||||
}
|
||||
);
|
||||
$builder->add('name', HiddenType::class);
|
||||
|
||||
@@ -47,6 +47,11 @@ class ConfigurationRepository extends EntityRepository implements ConfigLoaderIn
|
||||
$entity = $this->findOneBy(['name' => $configuration->getName()]);
|
||||
$value = $configuration->getValue();
|
||||
|
||||
if (null === $value && null !== $entity) {
|
||||
$em->remove($entity);
|
||||
continue;
|
||||
}
|
||||
|
||||
if (null === $entity) {
|
||||
$entity = new Configuration();
|
||||
$entity->setName($configuration->getName());
|
||||
|
||||
Reference in New Issue
Block a user