Skip to content

Commit

Permalink
Merge pull request #1764 from tomudding/feature/marked-decision-searc…
Browse files Browse the repository at this point in the history
…h-results

Add search highlighting to decision search
  • Loading branch information
tomudding authored Nov 19, 2023
2 parents e13f0bc + 2be9115 commit 4c2447f
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 1 deletion.
1 change: 1 addition & 0 deletions composer.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@
"ext-exif": "*",
"ext-fileinfo": "*",
"ext-gd": "*",
"ext-iconv": "*",
"ext-intl": "*",
"ext-imagick": "^3.5.0",
"ext-mbstring": "*",
Expand Down
1 change: 1 addition & 0 deletions module/Decision/src/Controller/DecisionController.php
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,7 @@ public function searchAction(): ViewModel
return new ViewModel(
[
'result' => $result,
'prompt' => $form->getData()['query'],
'form' => $form,
],
);
Expand Down
54 changes: 53 additions & 1 deletion module/Decision/view/decision/decision/search.phtml
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,61 @@ declare(strict_types=1);

use Application\View\HelperTrait;
use Decision\Form\SearchDecision as SearchDecisionForm;
use Decision\Model\Decision as DecisionModel;
use Laminas\View\Renderer\PhpRenderer;

/**
* @var PhpRenderer|HelperTrait $this
* @var SearchDecisionForm $form
* @var DecisionModel[]|null $result
* @var string|null $prompt
*/

$this->headTitle($this->translate('Search for decision'));

/**
* Insert `<mark>` around a search prompt in the content of a decision.
*/
function highlightSearch(
string $decision,
string $search,
): string {
// Convert the decision to something that is easily searchable (i.e. it MUST NOT contain any non-ASCII characters).
$transliteratedDecision = iconv(
'UTF-8',
'ASCII//TRANSLIT//IGNORE',
transliterator_transliterate('Any-Latin; Latin-ASCII', $decision),
);
// Do the same for the search prompt, as otherwise searches WITH non-ASCII characters will not work.
$search = iconv(
'UTF-8',
'ASCII//TRANSLIT//IGNORE',
transliterator_transliterate('Any-Latin; Latin-ASCII', $search),
);

$offset = 0;
$output = '';
$length = mb_strlen($search);

// There is a very important assumption here; the transliterated version of the decision MUST be exactly as long as
// the original version. Otherwise, the insertion is done with an incorrect offset.
while (false !== ($position = mb_stripos($transliteratedDecision, $search, $offset, 'UTF-8'))) {
// Progressively insert markers into the original decision.
$output .= sprintf('%s%s%s%s',
mb_substr($decision, $offset, $position - $offset, 'UTF-8'),
'<mark>',
mb_substr($decision, $position, $length, 'UTF-8'),
'</mark>',
);

$offset = $position + $length;
}

// Add the final part of the decision back.
$output .= mb_substr($decision, $offset, null, 'UTF-8');

return $output;
}
?>
<section class="section">
<div class="container">
Expand Down Expand Up @@ -78,7 +125,12 @@ $this->headTitle($this->translate('Search for decision'));
) ?>
</a>
</strong>
<span class="decision-content"><?= $this->escapeHtml($decision->getContent()) ?></span>
<span class="decision-content">
<?= highlightSearch(
$this->escapeHtml($decision->getContent()),
$this->escapeHtml($prompt),
) ?>
</span>
</li>
<?php endforeach ?>
</ul>
Expand Down

0 comments on commit 4c2447f

Please sign in to comment.