diff --git a/modules/access_misc/access_misc.install b/modules/access_misc/access_misc.install
index 9980a1a2..0b3e5622 100644
--- a/modules/access_misc/access_misc.install
+++ b/modules/access_misc/access_misc.install
@@ -2254,3 +2254,77 @@ function access_misc_update_10035() {
}
return t('field_rp_description already correct type or does not exist.');
}
+
+/**
+ * Create inline blocks for tools_case_study layout: Allocation Information - title, Software - Title.
+ */
+function access_misc_update_10036() {
+ $storage = \Drupal::entityTypeManager()->getStorage('block_content');
+ $blocks = [
+ [
+ 'label' => 'Allocation Information - title',
+ 'body' => '
Allocation Information ',
+ ],
+ [
+ 'label' => 'Software - Title',
+ 'body' => 'Software ',
+ ],
+ ];
+ $created = [];
+ foreach ($blocks as $data) {
+ $existing = $storage->loadByProperties(['info' => $data['label']]);
+ if (empty($existing)) {
+ $block = $storage->create([
+ 'type' => 'basic',
+ 'info' => $data['label'],
+ 'body' => [
+ 'value' => $data['body'],
+ 'format' => 'full_html',
+ ],
+ ]);
+ $block->save();
+ $created[] = $data['label'];
+ }
+ }
+ if ($created) {
+ return t('Created blocks: @labels.', ['@labels' => implode(', ', $created)]);
+ }
+ return t('Blocks already exist, skipped.');
+}
+
+/**
+ * Create inline blocks for tools_case_study layout: Research Topic - title, Project Summary - title.
+ */
+function access_misc_update_10037() {
+ $storage = \Drupal::entityTypeManager()->getStorage('block_content');
+ $blocks = [
+ [
+ 'label' => 'Research Topic - title',
+ 'body' => 'Research Topic ',
+ ],
+ [
+ 'label' => 'Project Summary - title',
+ 'body' => 'Project Summary ',
+ ],
+ ];
+ $created = [];
+ foreach ($blocks as $data) {
+ $existing = $storage->loadByProperties(['info' => $data['label']]);
+ if (empty($existing)) {
+ $block = $storage->create([
+ 'type' => 'basic',
+ 'info' => $data['label'],
+ 'body' => [
+ 'value' => $data['body'],
+ 'format' => 'full_html',
+ ],
+ ]);
+ $block->save();
+ $created[] = $data['label'];
+ }
+ }
+ if ($created) {
+ return t('Created blocks: @labels.', ['@labels' => implode(', ', $created)]);
+ }
+ return t('Blocks already exist, skipped.');
+}
diff --git a/modules/access_misc/access_misc.module b/modules/access_misc/access_misc.module
index 4a5617a2..6601888b 100644
--- a/modules/access_misc/access_misc.module
+++ b/modules/access_misc/access_misc.module
@@ -19,6 +19,26 @@ use Drupal\symfony_mailer\Entity\MailerTransport;
use Drupal\views\ViewExecutable;
+/**
+ * Implements hook_theme().
+ */
+function access_misc_theme() {
+ return [
+ 'tcs_case_study_researchers_block' => [
+ 'variables' => [
+ 'researchers' => [],
+ ],
+ 'template' => 'tcs-case-study-researchers-block',
+ ],
+ 'tcs_case_study_tools_used_block' => [
+ 'variables' => [
+ 'tools' => [],
+ ],
+ 'template' => 'tcs-case-study-tools-used-block',
+ ],
+ ];
+}
+
/**
* Implements hook_mailer_build().
*
@@ -199,6 +219,12 @@ function access_misc_views_data() {
* Implements hook_views_pre_render().
*/
function access_misc_views_pre_render(ViewExecutable $view) {
+ if ($view->id() == 'tool_case_study') {
+ $view->element['#attached']['library'][] = 'access_misc/copyclip';
+ }
+ if ($view->id() == 'tool_case_study_slideshow') {
+ $view->element['#attached']['library'][] = 'aspTheme/carousel';
+ }
if ($view->id() == 'infrastructure_news') {
$view->element['#attached']['library'][] = 'access_misc/add_select';
}
@@ -496,6 +522,83 @@ function access_misc_preprocess_views_view_field(&$variables) {
$variables['output'] = Markup::create($affinity_groups);
}
+ // Overwrite Access Tools on /tools/researcher-stories page on the
+ // /admin/structure/views/view/tool_case_study/edit/page_1.
+ if ($view->id() == 'tool_case_study' && $view->current_display == 'page_1' && $field->options['id'] == 'nothing') {
+ $current_output = (string) $variables['output'];
+
+ if (preg_match('/ACCESS_TOOLS:[\d,\s]+/', $current_output)) {
+ $node = $variables['row']->_entity ?? NULL;
+ $replacement = '';
+
+ if ($node && $node->hasField('field_tcs_access_tools_used') && !$node->get('field_tcs_access_tools_used')->isEmpty()) {
+ $items = '';
+ foreach ($node->get('field_tcs_access_tools_used') as $item) {
+ $term = $item->entity;
+ if (!$term) {
+ continue;
+ }
+
+ $link_url = '';
+ $image_url = '';
+
+ if ($term->hasField('field_tsc_link_to_tool') && !$term->get('field_tsc_link_to_tool')->isEmpty()) {
+ $link_url = $term->get('field_tsc_link_to_tool')->uri;
+ }
+
+ if ($term->hasField('field_tool_logo') && !$term->get('field_tool_logo')->isEmpty()) {
+ $file = $term->get('field_tool_logo')->entity;
+ if ($file) {
+ $image_url = \Drupal::service('file_url_generator')->generateAbsoluteString($file->getFileUri());
+ }
+ }
+
+ if ($link_url && $image_url) {
+ $alt = htmlspecialchars($term->getName(), ENT_QUOTES, 'UTF-8');
+ $href = htmlspecialchars($link_url, ENT_QUOTES, 'UTF-8');
+ $src = htmlspecialchars($image_url, ENT_QUOTES, 'UTF-8');
+ $items .= '';
+ $items .= '';
+ $items .= ' ';
+ $items .= ' ';
+ $items .= ' ';
+ }
+ }
+
+ if ($items) {
+ $replacement = '';
+ }
+ }
+
+ $new_output = preg_replace('/ACCESS_TOOLS:[\d,\s]+/', $replacement, $current_output);
+ $variables['output'] = Markup::create($new_output);
+ }
+ }
+
+ // Replace COPYCLIP_GOES_HERE placeholder with a copy-link button on the
+ // researcher stories page.
+ if ($view->id() == 'tool_case_study' && $view->current_display == 'page_1' && $field->options['id'] == 'nothing') {
+ $current_output = (string) $variables['output'];
+
+ if (strpos($current_output, 'COPYCLIP_GOES_HERE') === FALSE) {
+ return;
+ }
+
+ $node = $variables['row']->_entity ?? NULL;
+ $title = $node ? $node->label() : '';
+ $clean_id = \Drupal\Component\Utility\Html::getId($title);
+
+ $copyclip_html = ''
+ . ''
+ . ' Copy link '
+ . ''
+ . ' Copied! '
+ . ' ';
+
+ $new_output = str_replace('COPYCLIP_GOES_HERE', $copyclip_html, $current_output);
+ $variables['output'] = Markup::create($new_output);
+ }
+
}
/**
diff --git a/modules/access_misc/src/Plugin/Block/TcsCaseStudyResearchersBlock.php b/modules/access_misc/src/Plugin/Block/TcsCaseStudyResearchersBlock.php
new file mode 100644
index 00000000..1129207d
--- /dev/null
+++ b/modules/access_misc/src/Plugin/Block/TcsCaseStudyResearchersBlock.php
@@ -0,0 +1,161 @@
+entityTypeManager = $entity_type_manager;
+ $this->routeMatch = $route_match;
+ $this->fileUrlGenerator = $file_url_generator;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
+ return new static(
+ $configuration,
+ $plugin_id,
+ $plugin_definition,
+ $container->get('entity_type.manager'),
+ $container->get('current_route_match'),
+ $container->get('file_url_generator'),
+ );
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function build() {
+ $node = $this->routeMatch->getParameter('node');
+ if (!$node || $node->bundle() !== 'tools_case_study') {
+ return [];
+ }
+
+ if ($node->get('field_tcs_researcher_name')->isEmpty()) {
+ return [];
+ }
+
+ $researchers = [];
+ $delta = 0;
+ foreach ($node->get('field_tcs_researcher_name') as $item) {
+ /** @var \Drupal\user\UserInterface $user */
+ $user = $item->entity;
+ if (!$user) {
+ $delta++;
+ continue;
+ }
+
+ $photo_url = NULL;
+ if ($user->hasField('user_picture') && !$user->get('user_picture')->isEmpty()) {
+ $file = $user->get('user_picture')->entity;
+ if ($file) {
+ $photo_url = $this->fileUrlGenerator->generateAbsoluteString($file->getFileUri());
+ }
+ }
+
+ $role = NULL;
+ if ($node->hasField('field_tcs_role') && !$node->get('field_tcs_role')->isEmpty()) {
+ $role_item = $node->get('field_tcs_role')->get($delta)
+ ?? $node->get('field_tcs_role')->get(0);
+ if ($role_item) {
+ $role = $role_item->value;
+ }
+ }
+
+ $institution = NULL;
+ if ($node->hasField('field_tcs_institution') && !$node->get('field_tcs_institution')->isEmpty()) {
+ $institution_item = $node->get('field_tcs_institution')->get($delta)
+ ?? $node->get('field_tcs_institution')->get(0);
+ if ($institution_item) {
+ $institution = $institution_item->value;
+ }
+ }
+
+ $researchers[] = [
+ 'uid' => $user->id(),
+ 'name' => $user->getDisplayName(),
+ 'photo_url' => $photo_url,
+ 'role' => $role,
+ 'institution' => $institution,
+ ];
+ $delta++;
+ }
+
+ if (empty($researchers)) {
+ return [];
+ }
+
+ return [
+ '#theme' => 'tcs_case_study_researchers_block',
+ '#researchers' => $researchers,
+ '#cache' => [
+ 'tags' => $node->getCacheTags(),
+ 'contexts' => ['route'],
+ ],
+ ];
+ }
+
+}
diff --git a/modules/access_misc/src/Plugin/Block/TcsCaseStudyToolsUsedBlock.php b/modules/access_misc/src/Plugin/Block/TcsCaseStudyToolsUsedBlock.php
new file mode 100644
index 00000000..6d71df41
--- /dev/null
+++ b/modules/access_misc/src/Plugin/Block/TcsCaseStudyToolsUsedBlock.php
@@ -0,0 +1,143 @@
+entityTypeManager = $entity_type_manager;
+ $this->routeMatch = $route_match;
+ $this->fileUrlGenerator = $file_url_generator;
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public static function create(ContainerInterface $container, array $configuration, $plugin_id, $plugin_definition) {
+ return new static(
+ $configuration,
+ $plugin_id,
+ $plugin_definition,
+ $container->get('entity_type.manager'),
+ $container->get('current_route_match'),
+ $container->get('file_url_generator'),
+ );
+ }
+
+ /**
+ * {@inheritdoc}
+ */
+ public function build() {
+ $node = $this->routeMatch->getParameter('node');
+ if (!$node || $node->bundle() !== 'tools_case_study') {
+ return [];
+ }
+
+ if ($node->get('field_tcs_access_tools_used')->isEmpty()) {
+ return [];
+ }
+
+ $tools = [];
+ foreach ($node->get('field_tcs_access_tools_used') as $item) {
+ /** @var \Drupal\taxonomy\TermInterface $term */
+ $term = $item->entity;
+ if (!$term) {
+ continue;
+ }
+
+ $logo_url = NULL;
+ if ($term->hasField('field_tool_logo') && !$term->get('field_tool_logo')->isEmpty()) {
+ $file = $term->get('field_tool_logo')->entity;
+ if ($file) {
+ $logo_url = $this->fileUrlGenerator->generateAbsoluteString($file->getFileUri());
+ }
+ }
+
+ $link_url = NULL;
+ if ($term->hasField('field_tsc_link_to_tool') && !$term->get('field_tsc_link_to_tool')->isEmpty()) {
+ $link_url = $term->get('field_tsc_link_to_tool')->uri;
+ }
+
+ $tools[] = [
+ 'name' => $term->getName(),
+ 'logo_url' => $logo_url,
+ 'link_url' => $link_url,
+ ];
+ }
+
+ if (empty($tools)) {
+ return [];
+ }
+
+ return [
+ '#theme' => 'tcs_case_study_tools_used_block',
+ '#tools' => $tools,
+ '#cache' => [
+ 'tags' => $node->getCacheTags(),
+ 'contexts' => ['route'],
+ ],
+ ];
+ }
+
+}
diff --git a/modules/access_misc/templates/tcs-case-study-researchers-block.html.twig b/modules/access_misc/templates/tcs-case-study-researchers-block.html.twig
new file mode 100644
index 00000000..eca3000c
--- /dev/null
+++ b/modules/access_misc/templates/tcs-case-study-researchers-block.html.twig
@@ -0,0 +1,45 @@
+{#
+/**
+ * @file
+ * Template for the TCS Case Study Researchers block.
+ *
+ * Available variables:
+ * - researchers: Array of researcher data with uid, name, photo_url, and institution.
+ */
+#}
+
+
+ {% for researcher in researchers %}
+
+
+
+ {% if researcher.institution %}
+
{{ researcher.role }}, {{ researcher.institution }}
+ {% endif %}
+
+ {% endfor %}
+
diff --git a/modules/access_misc/templates/tcs-case-study-tools-used-block.html.twig b/modules/access_misc/templates/tcs-case-study-tools-used-block.html.twig
new file mode 100644
index 00000000..1c1158af
--- /dev/null
+++ b/modules/access_misc/templates/tcs-case-study-tools-used-block.html.twig
@@ -0,0 +1,32 @@
+{#
+/**
+ * @file
+ * Template for the TCS Case Study Tools Used block.
+ *
+ * Available variables:
+ * - tools: Array of tool data with name, logo_url, and link_url.
+ */
+#}
+
+