From 3fc23fdbf4b4968cac3bb8ca68ad7dda79c2dd73 Mon Sep 17 00:00:00 2001
From: Seb
Date: Fri, 24 Jul 2020 17:27:42 -0400
Subject: [PATCH] Supporting Multilang glossary in branch 3.8.x

---
rootdir/mod/glossary/sql-postprocessing.php            | 33 ++++++++++++++++++++++
rootdir/theme/mytheme/style/glossary.css      | 25 ++++++++++++++++
 2 files changed, 58 insertions(+)
 create mode 100644 rootdir/mod/glossary/sql-postprocessing.php
 create mode 100644 rootdir/theme/mytheme/style/glossary.css

diff --git a/rootdir/mod/glossary/sql-postprocessing.php b/rootdir/mod/glossary/sql-postprocessing.php
new file mode 100644
index 0000000..8bebde6
--- /dev/null
+++ b/rootdir/mod/glossary/sql-postprocessing.php
@@ -0,0 +1,33 @@
+<?php
+/**
+ *
+ * Post processing of multilang glossary entries
+ *
+ */
+$filter_multilang = new filter_multilang($context, array());
+$filteredentries = array();
+
+foreach ($allentries as $entry) {
+	$entry->concept = $filter_multilang->filter($entry->concept);
+	$entry->definition = $filter_multilang->filter($entry->definition);
+
+	// Filter entries by alphabetic selector
+	if ($mode == 'letter' && isset($hook) && $hook != 'ALL') {
+		$filteredbyletter = true;
+		$letter = core_text::strtoupper($hook);
+		$len = core_text::strlen($letter);
+		if (substr($entry->concept, 0, $len) === $letter) {
+			$filteredentries[] = $entry;
+		}
+	} else {
+		$filteredentries[] = $entry;
+	}
+}
+if (count($filteredentries) > 0) {
+	usort($filteredentries, function ($a, $b) {
+		return strcmp($a->concept, $b->concept);
+	});
+}
+
+$count = count($filteredentries);
+$allentries = array_slice($filteredentries, $offset, $pagelimit);
\ No newline at end of file
diff --git a/rootdir/theme/mytheme/style/glossary.css b/rootdir/theme/mytheme/style/glossary.css
new file mode 100644
index 0000000..cb23a33
--- /dev/null
+++ b/rootdir/theme/mytheme/style/glossary.css
@@ -0,0 +1,25 @@
+
+.path-mod-glossary .acronym, .acronym {font-weight:bold;display:inline; float:left; padding-right:10px;}
+.path-mod-glossary .alternateentry, .alternateentry {font-style:italic; display:inline; color:#3673b6;}
+.path-mod-glossary .glossaryreference {padding-bottom:10px;}
+.path-mod-glossary .glossarycategoryheader th {background-color:#F0F0F0; padding:0; margin:0;}
+.path-mod-glossary .glossarycategoryheader th h2 {padding:0; margin:0;}
+.path-mod-glossary .glossarycategoryheader {width:100%}
+.path-mod-glossary .entry p {margin-top:10px; margin-bottom:0px;}
+.path-mod-glossary .entry p, .path-mod-glossary .entry li {text-align:justify;}
+
+.glossaryAlternatives, .alternateentry {
+	padding-bottom:20px;
+	color:#999999;
+	font-style:italic;
+	font-size: .8em;
+}
+
+.glossaryReference, .glosssaryreference {
+	width:75%;
+	margin-left:auto;
+	padding:0 0 20px 0;
+	text-align:right;
+	color:#999999;
+	font-size: .8em;;
+}
-- 
2.8.1

From f3788c5fbba51d886dbe7abfcbe3e1e8678c6d7a Mon Sep 17 00:00:00 2001
From: Seb
Date: Fri, 24 Jul 2020 18:19:17 -0400
Subject: [PATCH] Supporting Multilang glossary in branch 3.8.x

---
 rootdir/filter/glossary/filter.php                | 8 +++++++-
 rootdir/mod/glossary/classes/local/concept_cache.php      | 2 +-
 rootdir/mod/glossary/lib.php                      | 7 +------
 rootdir/mod/glossary/showentry_ajax.php           | 1 +
 rootdir/mod/glossary/sql.php                      | 6 +++---
 rootdir/mod/glossary/view.php                     | 6 ++++--
 rootdir/theme/mytheme/config.php                     | 2 +-
 7 files changed, 18 insertions(+), 14 deletions(-)

diff --git a/rootdir/filter/glossary/filter.php b/rootdir/filter/glossary/filter.php
index 1f25918..bf5771d 100644
--- a/rootdir/filter/glossary/filter.php
+++ b/rootdir/filter/glossary/filter.php
@@ -50,7 +50,7 @@ class filter_glossary extends moodle_text_filter {
      * Get all the concepts for this context.
      * @return filterobject[] the concepts, and filterobjects.
      */
-    protected function get_all_concepts() {
+    protected function  get_all_concepts() {
         global $USER;
 
         if ($this->cache === null) {
@@ -88,9 +88,11 @@ class filter_glossary extends moodle_text_filter {
         }
 
         $conceptlist = array();
+	    $filter_multilang = new filter_multilang($coursectx, array());
 
         foreach ($allconcepts as $concepts) {
             foreach ($concepts as $concept) {
+	            $concept->concept = $filter_multilang->filter($concept->concept);  // Meridium Edit
                 $conceptlist[] = new filterobject($concept->concept, null, null,
                         $concept->casesensitive, $concept->fullmatch, null,
                         [$this, 'filterobject_prepare_replacement_callback'], [$concept, $glossaries]);
@@ -160,6 +162,10 @@ class filter_glossary extends moodle_text_filter {
     public function filter($text, array $options = array()) {
         global $GLOSSARY_EXCLUDEENTRY;
 
+	    if (strpos($_SERVER['REQUEST_URI'],"glossary")) {
+		    return $text;   // Meridium : Prevent glossary filtering on Glossary entries
+	    }
+
         $conceptlist = $this->get_all_concepts();
 
         if (empty($conceptlist)) {
diff --git a/rootdir/mod/glossary/classes/local/concept_cache.php b/rootdir/mod/glossary/classes/local/concept_cache.php
index cd5adc8..b42b9f7 100644
--- a/rootdir/mod/glossary/classes/local/concept_cache.php
+++ b/rootdir/mod/glossary/classes/local/concept_cache.php
@@ -122,7 +122,7 @@ class concept_cache {
         $concepts = array();
         $rs = $DB->get_recordset_sql($sql);
         foreach ($rs as $concept) {
-            $currentconcept = trim(strip_tags($concept->concept));
+            $currentconcept = trim($concept->concept); // Meridium : Keep all lang tags for further processing/filtering
 
             // Concept must be HTML-escaped, so do the same as format_string to turn ampersands into &amp;.
             $currentconcept = replace_ampersands_not_followed_by_entity($currentconcept);
diff --git a/rootdir/mod/glossary/lib.php b/rootdir/mod/glossary/lib.php
index 2615e43..a7d0d1d 100644
--- a/rootdir/mod/glossary/lib.php
+++ b/rootdir/mod/glossary/lib.php
@@ -3433,12 +3433,7 @@ function glossary_entry_view($entry, $context) {
 function glossary_get_entries_by_letter($glossary, $context, $letter, $from, $limit, $options = array()) {
 
     $qb = new mod_glossary_entry_query_builder($glossary);
-    if ($letter != 'ALL' && $letter != 'SPECIAL' && core_text::strlen($letter)) {
-        $qb->filter_by_concept_letter($letter);
-    }
-    if ($letter == 'SPECIAL') {
-        $qb->filter_by_concept_non_letter();
-    }
+    //  Meridium: Do not filter entries at database level
 
     if (!empty($options['includenotapproved']) && has_capability('mod/glossary:approve', $context)) {
         $qb->filter_by_non_approved(mod_glossary_entry_query_builder::NON_APPROVED_ALL);
diff --git a/rootdir/mod/glossary/showentry_ajax.php b/rootdir/mod/glossary/showentry_ajax.php
index 204d766..c324192 100644
--- a/rootdir/mod/glossary/showentry_ajax.php
+++ b/rootdir/mod/glossary/showentry_ajax.php
@@ -43,6 +43,7 @@ if ($eid) {
 
 if ($entries) {
     foreach ($entries as $key => $entry) {
+	    $entry->concept = format_string($entry->concept);
         // Need to get the course where the entry is,
         // in order to check for visibility/approve permissions there
         $entrycourse = $DB->get_record('course', array('id' => $entry->courseid), '*', MUST_EXIST);
diff --git a/rootdir/mod/glossary/sql.php b/rootdir/mod/glossary/sql.php
index 914cc0c..4c92e9b 100644
--- a/rootdir/mod/glossary/sql.php
+++ b/rootdir/mod/glossary/sql.php
@@ -77,7 +77,7 @@ switch ($tab) {
         switch ($mode) {
             case 'search':
                 list($allentries, $count) = glossary_get_entries_by_search($glossary, $context, $hook, $fullsearch,
-                    $sortkey, $sortorder, $offset, $pagelimit);
+                    $sortkey, $sortorder, 0,1000);  // Meridium: Always get all glossary entries
                 break;
 
             case 'term':
@@ -102,8 +102,8 @@ switch ($tab) {
 
             case 'letter':
             default:
-                list($allentries, $count) = glossary_get_entries_by_letter($glossary, $context, $hook, $offset, $pagelimit);
-                break;
+                list($allentries, $count) = glossary_get_entries_by_letter($glossary, $context, $hook, 0, 1000); // Meridium: Always get all glossary entries
+		        break;
         }
         break;
 }
diff --git a/rootdir/mod/glossary/view.php b/rootdir/mod/glossary/view.php
index 4c5c8fc..828fdaf 100644
--- a/rootdir/mod/glossary/view.php
+++ b/rootdir/mod/glossary/view.php
@@ -427,7 +427,9 @@ $paging = NULL;
 
 if ($allentries) {
 
-    //Decide if we must show the ALL link in the pagebar
+	require("sql-postprocessing.php"); // Meridium Edit
+
+	//Decide if we must show the ALL link in the pagebar
     $specialtext = '';
     if ($glossary->showall) {
         $specialtext = get_string("allentries","glossary");
@@ -464,7 +466,7 @@ if ($allentries) {
 
     foreach ($allentries as $entry) {
 
-        // Setting the pivot for the current entry
+	    // Setting the pivot for the current entry
         if ($printpivot) {
             $pivot = $entry->{$pivotkey};
             $upperpivot = core_text::strtoupper($pivot);
diff --git a/rootdir/theme/mytheme/config.php b/rootdir/theme/mytheme/config.php
index a5ac170..41093de 100644
--- a/rootdir/theme/mytheme/config.php
+++ b/rootdir/theme/mytheme/config.php
@@ -34,7 +34,7 @@ $THEME->name = 'msss';
 // This setting list the style sheets we want to include in our theme. Because we want to use SCSS instead of CSS - we won't
 // list any style sheets. If we did we would list the name of a file in the /styles/ folder for our theme without any css file
 // extensions.
-$THEME->sheets = ['custom','lesson'];
+$THEME->sheets = ['custom','lesson','glossary'];
 
 // This is a setting that can be used to provide some styling to the content in the TinyMCE text editor. This is no longer the
 // default text editor and "Atto" does not need this setting so we won't provide anything. If we did it would work the same
-- 
2.8.1

