diff --git a/application/src/I18n/Translator.php b/application/src/I18n/Translator.php index 14c3ac961f..088565d123 100644 --- a/application/src/I18n/Translator.php +++ b/application/src/I18n/Translator.php @@ -1,8 +1,9 @@ translator->translate($message, $textDomain, $locale); + if ($message instanceof TranslatorAwareInterface) { + $message->setTranslator($this->translator, $textDomain); + return $message->translate($textDomain, $locale); } - $translation = $this->translator->translate($message->getMessage(), $textDomain, $locale); - if ($message->hasArgs()) { - $translation = sprintf($translation, ...$message->getArgs()); + + if ($message instanceof MessageInterface) { + $translation = $this->translator->translate($message->getMessage(), $textDomain, $locale); + return $message->interpolate($translation, $message->getContext()); } - return $translation; + + return $this->translator->translate($message, $textDomain, $locale); } public function translatePlural($singular, $plural, $number, $textDomain = 'default', $locale = null) diff --git a/application/src/Stdlib/Message.php b/application/src/Stdlib/Message.php index 0db9ac4f25..914072956a 100644 --- a/application/src/Stdlib/Message.php +++ b/application/src/Stdlib/Message.php @@ -1,7 +1,10 @@ args = $args; } - /** - * Get the message string. - * - * @return string - */ public function getMessage() { return $this->message; } + public function getContext() + { + return $this->args; + } + + public function hasContext() + { + return (bool) $this->args; + } + /** * Get the message arguments. + * + * @deprecated 1.4.0 Use getContext() instead. + * @return array */ public function getArgs() { @@ -51,6 +62,7 @@ public function getArgs() /** * Does this message have arguments? * + * @deprecated 1.4.0 Use hasContext() instead. * @return bool */ public function hasArgs() @@ -68,9 +80,14 @@ public function escapeHtml() return $this->escapeHtml; } + public function interpolate($message, array $context = []) + { + return (string) sprintf($message, ...$context); + } + public function __toString() { - return (string) sprintf($this->getMessage(), ...$this->getArgs()); + return $this->interpolate($this->getMessage(), $this->getContext()); } public function jsonSerialize() diff --git a/application/src/Stdlib/MessageInterface.php b/application/src/Stdlib/MessageInterface.php new file mode 100644 index 0000000000..4b8a9e41f5 --- /dev/null +++ b/application/src/Stdlib/MessageInterface.php @@ -0,0 +1,45 @@ + $val) { + if (is_null($val) + || is_scalar($val) + || (is_object($val) && method_exists($val, '__toString')) + ) { + $replacements['{' . $key . '}'] = $val; + } elseif (is_array($val)) { + $replacements['{' . $key . '}'] = 'array' . @json_encode($val); + } elseif (is_object($val)) { + $replacements['{' . $key . '}'] = '[object ' . get_class($val) . ']'; + } elseif (is_resource($val)) { + $replacements['{' . $key . '}'] = '[resource ' . get_resource_type($val) . ']'; + } else { + $replacements['{' . $key . '}'] = '[' . gettype($val) . ']'; + } + } + + return strtr($message, $replacements); + } +} diff --git a/application/src/Stdlib/PsrMessage.php b/application/src/Stdlib/PsrMessage.php new file mode 100644 index 0000000000..5ca18d9646 --- /dev/null +++ b/application/src/Stdlib/PsrMessage.php @@ -0,0 +1,141 @@ +getEvent()->getApplication()->getServiceManager()->get('MvcTranslator'); + * // or: + * $translator = $this->viewHelpers()->get('translate')->getTranslator(); + * + * // To get translator in a view: + * $translator = $this->plugin('translate')->getTranslator(); + * + * // To set the translator: + * $psrMessage->setTranslator($translator); + * // To disable the translation when the translator is set: + * $psrMessage->setTranslatorEnabled(false); + * ``` + * + * @see \Omeka\Stdlib\Message + */ +class PsrMessage implements MessageInterface, TranslatorAwareInterface, \JsonSerializable, PsrInterpolateInterface +{ + use PsrInterpolateTrait; + use TranslatorAwareTrait; + + /** + * @var string + */ + protected $message; + + /** + * @var array + */ + protected $context = []; + + /** + * @var bool + */ + protected $escapeHtml = true; + + /** + * Set the message string and its context. The plural is not managed. + */ + public function __construct($message, array $context = []) + { + $this->message = $message; + $this->context = $context; + } + + /** + * Get the message string. + */ + public function getMessage(): string + { + return (string) $this->message; + } + + /** + * Get the message context. + */ + public function getContext(): array + { + return $this->context; + } + + /** + * Does this message have context? + */ + public function hasContext(): bool + { + return (bool) $this->context; + } + + /** + * Get the message arguments for compatibility purpose only. + * + * @deprecated Use hasContext() instead. + * @return array Non-associative array in order to comply with sprintf. + */ + public function getArgs() + { + return array_values($this->getContext()); + } + + /** + * Does this message have arguments? For compatibility purpose only. + * + * @deprecated Use hasContext() instead. + * @return bool + */ + public function hasArgs() + { + return $this->hasContext(); + } + + public function setEscapeHtml($escapeHtml): self + { + $this->escapeHtml = (bool) $escapeHtml; + return $this; + } + + public function escapeHtml(): bool + { + return $this->escapeHtml; + } + + public function __toString() + { + return $this->isTranslatorEnabled() + ? $this->translate() + : $this->interpolate($this->getMessage(), $this->getContext()); + } + + /** + * Translate the message with the context. + * + * Same as TranslatorInterface::translate(), but the message is the current one. + */ + public function translate($textDomain = 'default', $locale = null): string + { + return $this->hasTranslator() + ? $this->interpolate($this->translator->translate($this->getMessage(), $textDomain, $locale), $this->getContext()) + : $this->interpolate($this->getMessage(), $this->getContext()); + } + + public function jsonSerialize() + { + return (string) $this; + } +} diff --git a/application/src/View/Helper/Messages.php b/application/src/View/Helper/Messages.php index 95310cab82..4338369a41 100644 --- a/application/src/View/Helper/Messages.php +++ b/application/src/View/Helper/Messages.php @@ -1,9 +1,10 @@ getView(); + $escape = $view->plugin('escapeHtml'); + $translate = $view->plugin('translate'); + $translator = $translate->getTranslator(); $output = '
';