NotificationRenderer.php 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208
  1. <?php
  2. /**
  3. * Copyright © Magento, Inc. All rights reserved.
  4. * See COPYING.txt for license details.
  5. */
  6. namespace Magento\ReleaseNotification\Ui\Renderer;
  7. use Magento\Framework\Escaper;
  8. /**
  9. * Builds the HTML for the release notification modals
  10. */
  11. class NotificationRenderer
  12. {
  13. /**
  14. * @var Escaper
  15. */
  16. private $escaper;
  17. /**
  18. * @param Escaper $escaper
  19. */
  20. public function __construct(
  21. Escaper $escaper
  22. ) {
  23. $this->escaper = $escaper;
  24. }
  25. /**
  26. * Returns the HTML for notification's title to the ui component
  27. *
  28. * @param array $page
  29. * @return string
  30. */
  31. public function getNotificationTitle(array $page)
  32. {
  33. $title = $this->escaper->escapeHtml($page['mainContent']['title']);
  34. $imageUrl = $this->escaper->escapeUrl($page['mainContent']['imageUrl']);
  35. $content = "";
  36. if (!empty($imageUrl)) {
  37. $content .= "<div class='release-notification-title-with-image' style='background-image: url(\"" . $imageUrl
  38. . "\")'>";
  39. $content .= $title;
  40. $content .= "</div>";
  41. } else {
  42. $content = $title;
  43. }
  44. return $content;
  45. }
  46. /**
  47. * Returns the HTML for the content in the notification ui component
  48. *
  49. * @param array $page
  50. * @return string
  51. */
  52. public function getNotificationContent(array $page)
  53. {
  54. $content = $this->buildMainContent($page['mainContent']);
  55. $content .= $this->buildSubHeadings($page['subHeading']);
  56. $content .= $this->buildFooter($page['footer']);
  57. return $content;
  58. }
  59. /**
  60. * Builds the HTML for the main content in the notification ui component
  61. *
  62. * @param array $mainContent
  63. * @return string
  64. */
  65. private function buildMainContent(array $mainContent)
  66. {
  67. $content = $this->buildContentTextAreas($mainContent['content']);
  68. $content .= $this->buildLists($mainContent['lists']);
  69. return $this->formatContentWithLinks($content);
  70. }
  71. /**
  72. * Builds the HTML for the main text areas in the notification ui component
  73. *
  74. * @param array $contentAreas
  75. * @return string
  76. */
  77. private function buildContentTextAreas(array $contentAreas)
  78. {
  79. $content = "";
  80. $lastContentArea = end($contentAreas);
  81. foreach ($contentAreas as $contentArea) {
  82. $content .= "<p>";
  83. $content .= $this->escaper->escapeHtml($contentArea['text']);
  84. $content .= "</p>";
  85. if ($contentArea != $lastContentArea) {
  86. $content .= "<br />";
  87. }
  88. }
  89. return $content;
  90. }
  91. /**
  92. * Builds the HTML for the bullet list content in the notification ui component
  93. *
  94. * @param array $lists
  95. * @return string
  96. */
  97. private function buildLists(array $lists)
  98. {
  99. $content = "<ul>";
  100. foreach ($lists as $listItem) {
  101. $content .= "<li><span>";
  102. $content .= $this->escaper->escapeHtml($listItem['text']);
  103. $content .= "</span></li>";
  104. }
  105. $content .= "</ul>";
  106. return $content;
  107. }
  108. /**
  109. * Builds the HTML for the highlighted sub heads for the overview page in the notification ui component
  110. *
  111. * @param array $subHeadings
  112. * @return string
  113. */
  114. private function buildSubHeadings(array $subHeadings)
  115. {
  116. $content = "";
  117. foreach ($subHeadings as $subHeading) {
  118. if (!empty($subHeading['imageUrl'])) {
  119. $content .= "<div class='highlight-item' style='background-image: url(\""
  120. . $this->escaper->escapeUrl($subHeading['imageUrl']) . "\")'>";
  121. } else {
  122. $content .= "<div class='highlight-item-no-image'>";
  123. }
  124. $content .= "<h3>";
  125. $content .= $this->escaper->escapeHtml($subHeading['title']);
  126. $content .= "</h3>";
  127. $content .= "<p>";
  128. $content .= $this->formatContentWithLinks($subHeading['content']);
  129. $content .= "</p>";
  130. $content .= "</div>";
  131. }
  132. return $content;
  133. }
  134. /**
  135. * Builds the HTML for the footer content in the notification ui component
  136. *
  137. * @param array $footer
  138. * @return string
  139. */
  140. private function buildFooter(array $footer)
  141. {
  142. $content = "<p>";
  143. $content .= $this->escaper->escapeHtml($footer['content']);
  144. $content .= "</p>";
  145. return $this->formatContentWithLinks($content);
  146. }
  147. /**
  148. * Searches a given string for a URL, formats it to an HTML anchor tag, and returns the original string in the
  149. * correct HTML format.
  150. *
  151. * @param string $content
  152. * @return string
  153. */
  154. private function formatContentWithLinks($content)
  155. {
  156. $urlRegex = '#\bhttps?://[^,\s()<>]+(?:\([\w\d]+\)|([^,[:punct:]\s]|/))#';
  157. $urlTextRegex = '/\[(.*?)\]/';
  158. preg_match_all($urlRegex, $content, $urlMatches);
  159. preg_match_all($urlTextRegex, $content, $urlTextMatches);
  160. foreach ($urlMatches[0] as $key => $urlMatch) {
  161. if (!empty($urlTextMatches[0])) {
  162. $linkMatch = $urlMatch . " " . $urlTextMatches[0][$key];
  163. $content = str_replace(
  164. $linkMatch,
  165. "<a target='_blank' href='{$this->escaper->escapeUrl($urlMatch)}'>
  166. {$this->escaper->escapeHtml($urlTextMatches[1][$key])}</a>",
  167. $content
  168. );
  169. } else {
  170. $content = str_replace(
  171. $urlMatch,
  172. "<a target='_blank' href='{$this->escaper->escapeUrl($urlMatch)}'>
  173. {$this->escaper->escapeUrl($urlMatch)}</a>",
  174. $content
  175. );
  176. }
  177. }
  178. return $content;
  179. }
  180. }