From 22b8abc43566b75c60c3a3ac956c006e8c7c5ce7 Mon Sep 17 00:00:00 2001 From: James C <5689414+james-cnz@users.noreply.github.com> Date: Sat, 11 Mar 2023 18:41:38 +1300 Subject: [PATCH 01/50] Code checker updates for PHP 8.1 and Moodle 4.2 --- .github/workflows/moodle-ci.yml | 12 ++++++++---- .../output/courseformat/content/section/summary.php | 4 ++-- duplicate.php | 2 +- templates/local/content.mustache | 2 ++ templates/local/content/section.mustache | 2 ++ templates/local/content/section/content.mustache | 2 ++ version.php | 2 +- 7 files changed, 18 insertions(+), 8 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 50b5f57..3e9921f 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -10,7 +10,7 @@ jobs: services: postgres: - image: postgres:12 # Moodle 4.0: >= 10 + image: postgres:13 # Moodle 4.2: >= 13 env: POSTGRES_USER: 'postgres' POSTGRES_HOST_AUTH_METHOD: 'trust' @@ -18,7 +18,7 @@ jobs: - 5432:5432 options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 3 mariadb: - image: mariadb:10.5 # Moodle 4.0 >=10.2.29 + image: mariadb:10.6 # Moodle 4.2 >=10.6.7 env: MYSQL_USER: 'root' MYSQL_ALLOW_EMPTY_PASSWORD: "true" @@ -37,11 +37,15 @@ jobs: moodle-branch: 'MOODLE_400_STABLE' database: pgsql # Moodle 4.1, PHP 7.4, MariaDB - - php: '7.4' # 7.4-8.0 + - php: '7.4' # 7.4-8.1 moodle-branch: 'MOODLE_401_STABLE' database: mariadb # Moodle 4.1, PHP 8.0, PostgreSQL - - php: '8.0' # 7.4-8.0 + - php: '8.0' # 7.4-8.1 + moodle-branch: 'MOODLE_401_STABLE' + database: pgsql + # Moodle 4.1, PHP 8.1, PostgreSQL + - php: '8.1' # 7.4-8.1 moodle-branch: 'MOODLE_401_STABLE' database: pgsql diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index 5f0b873..480ce4a 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -139,7 +139,7 @@ private function replace_resources(section_info $section) { $completioninfo = new \completion_info($course); if (!isset($initialised)) { - $groupbuttons = ($course->groupmode || (!$course->groupmodeforce)); + $groupbuttons = ($course->groupmode || (!$course->groupmodeforce)); $groupbuttonslink = (!$course->groupmodeforce); include_once($CFG->dirroot . '/mod/forum/lib.php'); if ($usetracking = forum_tp_can_track_forums()) { @@ -157,7 +157,7 @@ private function replace_resources(section_info $section) { $summary = $section->summary; $htmlresource = ''; - $htmlmore = ''; + $htmlmore = ''; if (!empty($section->sequence)) { $sectionmods = explode(",", $section->sequence); diff --git a/duplicate.php b/duplicate.php index f8ae275..e938464 100644 --- a/duplicate.php +++ b/duplicate.php @@ -166,7 +166,7 @@ foreach ($sectionmods as $modnumber) { $k++; $mod = $modinfo->cms[$modnumber]; - $cm = get_coursemodule_from_id('', $mod->id, 0, true, MUST_EXIST); + $cm = get_coursemodule_from_id('', $mod->id, 0, true, MUST_EXIST); $modcontext = context_module::instance($cm->id); if (has_capability('moodle/course:manageactivities', $modcontext) && !$cm->deletioninprogress) { diff --git a/templates/local/content.mustache b/templates/local/content.mustache index f64841e..b036b38 100644 --- a/templates/local/content.mustache +++ b/templates/local/content.mustache @@ -32,6 +32,7 @@ "cmname": "Forum example", "hasname": "true" }, + "cmid": 3, "id": 3, "anchor": "module-3", "module": "forum", @@ -86,6 +87,7 @@ "cmname": "Assign example", "hasname": "true" }, + "cmid": 4, "id": 4, "anchor": "module-4", "module": "assign", diff --git a/templates/local/content/section.mustache b/templates/local/content/section.mustache index 9615a39..6269b46 100644 --- a/templates/local/content/section.mustache +++ b/templates/local/content/section.mustache @@ -41,6 +41,7 @@ "cmname": "Forum example", "hasname": "true" }, + "cmid": 3, "id": 3, "module": "forum", "anchor": "activity-3", @@ -53,6 +54,7 @@ "cmname": "Assign example", "hasname": "true" }, + "cmid": 4, "id": 4, "anchor": "activity-4", "module": "assign", diff --git a/templates/local/content/section/content.mustache b/templates/local/content/section/content.mustache index a12e4c1..beabf44 100644 --- a/templates/local/content/section/content.mustache +++ b/templates/local/content/section/content.mustache @@ -38,6 +38,7 @@ "cmname": "Forum example", "hasname": "true" }, + "cmid": 3, "id": 3, "module": "forum", "anchor": "activity-3", @@ -50,6 +51,7 @@ "cmname": "Assign example", "hasname": "true" }, + "cmid": 4, "id": 4, "anchor": "activity-4", "module": "assign", diff --git a/version.php b/version.php index 725723d..0c6d56a 100644 --- a/version.php +++ b/version.php @@ -25,7 +25,7 @@ defined('MOODLE_INTERNAL') || die(); $plugin->version = 2022081607; // The current plugin version (Date: YYYYMMDDXX). -$plugin->requires = 2022041902; // Requires this Moodle version. +$plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; $plugin->release = '4.1.03(PiedrasTeherán)'; From bb814197ef4b4dbc6099f684d4d78e57af5c6434 Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 6 Apr 2023 22:54:50 -0500 Subject: [PATCH 02/50] Added Navigation options and some site settings --- README.txt | 5 +- changenumsections.php | 7 +- classes/output/courseformat/content.php | 32 ++++- .../content/sectionnavigation.php | 109 ++++++++++++++++++ .../courseformat/content/sectionselector.php | 86 ++++++++++++++ classes/tabs.php | 4 +- lang/en/format_onetopic.php | 13 +++ lib.php | 38 ++++++ settings.php | 19 +++ styles.css | 56 ++++++++- templates/local/content.mustache | 4 +- version.php | 4 +- 12 files changed, 363 insertions(+), 14 deletions(-) create mode 100644 classes/output/courseformat/content/sectionnavigation.php create mode 100644 classes/output/courseformat/content/sectionselector.php diff --git a/README.txt b/README.txt index 78fd03e..364d1fc 100644 --- a/README.txt +++ b/README.txt @@ -17,10 +17,13 @@ COMING SOON ============= - Fix: the topics bar is not refresh when change a section (move a section in boost sections bar). - Show "Availability information" in summary template mode. -- Navegation options: Next/previous section. IN VERSION ============= +2022081608: +- Navigation options: Next/previous section, with different display options. +- A site setting option to define if use an anchor to navigate to the top of tabs when click in a tab. + 2022081607: - Duplicate section feature. diff --git a/changenumsections.php b/changenumsections.php index b5063cc..e918075 100644 --- a/changenumsections.php +++ b/changenumsections.php @@ -109,6 +109,11 @@ } } +$anchortotabstree = get_config('format_onetopic', 'anchortotabstree'); + +if ($anchortotabstree) { + $returnurl->set_anchor('tabs-tree-start'); +} + // Redirect to where we were.. -$returnurl->set_anchor('tabs-tree-start'); redirect($returnurl); diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index e17b5e3..b8b8c57 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -110,18 +110,38 @@ public function export_for_template(\renderer_base $output) { 'tabsviewclass' => $tabsview, 'hasformatmsgs' => count(\format_onetopic::$formatmsgs) > 0, 'formatmsgs' => \format_onetopic::$formatmsgs, - 'hidetabsbar' => ($course->hidetabsbar == 1 && $format->show_editor()) + 'hidetabsbar' => ($course->hidetabsbar == 1 && $format->show_editor()), + 'sectionclasses' => '' ]; // The current section format has extra navigation. if ($currentsection || $currentsection === 0) { - if (!$PAGE->theme->usescourseindex) { - $sectionnavigation = new $this->sectionnavigationclass($format, $currentsection); - $data->sectionnavigation = $sectionnavigation->export_for_template($output); - $sectionselector = new $this->sectionselectorclass($format, $sectionnavigation); - $data->sectionselector = $sectionselector->export_for_template($output); + $usessectionsnavigation = isset($course->usessectionsnavigation) ? $course->usessectionsnavigation : null; + if (empty($usessectionsnavigation)) { + $usessectionsnavigation = get_config('format_onetopic', 'defaultsectionsnavigation'); } + + if ($usessectionsnavigation != \format_onetopic::SECTIONSNAVIGATION_NOT) { + if ($usessectionsnavigation != \format_onetopic::SECTIONSNAVIGATION_SUPPORT || + !$PAGE->theme->usescourseindex) { + + $sectionnavigation = new $this->sectionnavigationclass($format, $currentsection); + + // Not show navigation in top section if is not both. + if ($usessectionsnavigation == \format_onetopic::SECTIONSNAVIGATION_BOTH) { + $data->sectionnavigation = $sectionnavigation->export_for_template($output); + } + + $sectionselector = new $this->sectionselectorclass($format, $sectionnavigation); + $data->sectionselector = $sectionselector->export_for_template($output); + + if ($usessectionsnavigation == \format_onetopic::SECTIONSNAVIGATION_SLIDES) { + $data->sectionclasses .= ' sectionsnavigation-slides'; + } + } + } + $data->sectionreturn = $currentsection; } diff --git a/classes/output/courseformat/content/sectionnavigation.php b/classes/output/courseformat/content/sectionnavigation.php new file mode 100644 index 0000000..b3ad937 --- /dev/null +++ b/classes/output/courseformat/content/sectionnavigation.php @@ -0,0 +1,109 @@ +. + +/** + * Contains the default section navigation output class. + * + * @package format_onetopic + * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +namespace format_onetopic\output\courseformat\content; + +use context_course; +use core\output\named_templatable; +use core_courseformat\base as course_format; +use core_courseformat\output\local\courseformat_named_templatable; +use core_courseformat\output\local\content\sectionnavigation as sectionnavigation_base; +use renderable; +use stdClass; + +/** + * Base class to render a course add section navigation. + * + * @package format_onetopic + * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class sectionnavigation extends sectionnavigation_base { + + /** @var stdClass the calculated data to prevent calculations when rendered several times */ + private $data = null; + + /** + * Export this data so it can be used as the context for a mustache template. + * + * @param renderer_base $output typically, the renderer that's calling this function + * @return stdClass data context for a mustache template + */ + public function export_for_template(\renderer_base $output): stdClass { + global $USER; + + if ($this->data !== null) { + return $this->data; + } + + $format = $this->format; + $course = $format->get_course(); + $context = context_course::instance($course->id); + + $modinfo = $this->format->get_modinfo(); + $sections = $modinfo->get_section_info_all(); + + // FIXME: This is really evil and should by using the navigation API. + $canviewhidden = has_capability('moodle/course:viewhiddensections', $context, $USER); + + $data = (object)[ + 'previousurl' => '', + 'nexturl' => '', + 'larrow' => $output->larrow(), + 'rarrow' => $output->rarrow(), + 'currentsection' => $this->sectionno, + ]; + + $firstsection = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; + $back = $this->sectionno - 1; + while ($back > ($firstsection - 1) && empty($data->previousurl)) { + if ($canviewhidden || $sections[$back]->uservisible) { + if (!$sections[$back]->visible) { + $data->previoushidden = true; + } + $data->previousname = get_section_name($course, $sections[$back]); + $data->previousurl = course_get_url($course, $back); + $data->hasprevious = true; + } + $back--; + } + + $forward = $this->sectionno + 1; + $numsections = course_get_format($course)->get_last_section_number(); + while ($forward <= $numsections && empty($data->nexturl)) { + if ($canviewhidden || $sections[$forward]->uservisible) { + if (!$sections[$forward]->visible) { + $data->nexthidden = true; + } + $data->nextname = get_section_name($course, $sections[$forward]); + $data->nexturl = course_get_url($course, $forward); + $data->hasnext = true; + } + $forward++; + } + + $this->data = $data; + return $data; + } +} diff --git a/classes/output/courseformat/content/sectionselector.php b/classes/output/courseformat/content/sectionselector.php new file mode 100644 index 0000000..126ca24 --- /dev/null +++ b/classes/output/courseformat/content/sectionselector.php @@ -0,0 +1,86 @@ +. + +/** + * Contains the default section selector. + * + * @package format_onetopic + * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + + namespace format_onetopic\output\courseformat\content; + +use core\output\named_templatable; +use core_courseformat\base as course_format; +use core_courseformat\output\local\courseformat_named_templatable; +use core_courseformat\output\local\content\sectionselector as sectionselector_base; +use renderable; +use stdClass; +use url_select; + +/** + * Represents the section selector. + * + * @package format_onetopic + * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class sectionselector extends sectionselector_base { + + /** + * Export this data so it can be used as the context for a mustache template. + * + * @param renderer_base $output typically, the renderer that's calling this function + * @return stdClass data context for a mustache template + */ + public function export_for_template(\renderer_base $output): stdClass { + + $format = $this->format; + $course = $format->get_course(); + + $modinfo = $this->format->get_modinfo(); + + $data = $this->navigation->export_for_template($output); + + $anchortotabstree = get_config('format_onetopic', 'anchortotabstree'); + + $anchor = $anchortotabstree ? '#tabs-tree-start' : ''; + + // Add the section selector. + $sectionmenu = []; + $section = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; + $numsections = $format->get_last_section_number(); + while ($section <= $numsections) { + $thissection = $modinfo->get_section_info($section); + $formatoptions = course_get_format($course)->get_format_options($thissection); + $prefix = is_array($formatoptions) && $formatoptions['level'] > 0 ? '    ' : ''; + + $url = course_get_url($course, $section); + if ($thissection->uservisible && $url) { + $sectionmenu[$url->out(false) . $anchor] = $prefix . get_section_name($course, $section); + } + $section++; + } + + $select = new url_select($sectionmenu, '', ['' => get_string('jumpto')]); + $select->class = 'jumpmenu'; + $select->formid = 'sectionmenu'; + + $data->selector = $output->render($select); + return $data; + } +} diff --git a/classes/tabs.php b/classes/tabs.php index 2945f95..355c7de 100644 --- a/classes/tabs.php +++ b/classes/tabs.php @@ -73,6 +73,8 @@ public function get_list(bool $assubtabs = false) : array { $tabstree = []; + $anchortotabstree = get_config('format_onetopic', 'anchortotabstree'); + foreach ($this->tabslist as $tab) { if ($assubtabs) { @@ -80,7 +82,7 @@ public function get_list(bool $assubtabs = false) : array { } $newtab = new \stdClass(); - $newtab->link = $tab->link . '#tabs-tree-start'; + $newtab->link = $tab->link . ($anchortotabstree ? '#tabs-tree-start' : ''); $newtab->title = $tab->title; $newtab->text = $tab->content; $newtab->active = $tab->selected; diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 0f63928..987dee2 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -100,3 +100,16 @@ $string['hiddentabsbar'] = 'The tabs are set to be hidden. They will not be seen when not in edit mode.'; $string['enablecustomstyles'] = 'Enable custom styles'; $string['enablecustomstyles_help'] = 'Enable font color, background color and other custom tab styles in the sections configuration.'; + +$string['usessectionsnavigation'] = 'Uses sections navigation'; +$string['usessectionsnavigation_help'] = 'Show buttons for navigate to next or previous section.'; +$string['sectionsnavigation_support'] = 'Only if theme not support the "uses course index" feature'; +$string['sectionsnavigation_not'] = 'Not use'; +$string['sectionsnavigation_bottom'] = 'Only at the bottom'; +$string['sectionsnavigation_both'] = 'At top and bottom section'; +$string['sectionsnavigation_slides'] = 'Like slides'; +$string['enableanchorposition'] = 'Enable anchor position'; +$string['enableanchorposition_help'] = 'Use an anchor to navigate to the top of tabs when click in a tab.'; +$string['defaultsectionsnavigation'] = 'Default value to sections navigation'; +$string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; +$string['sectionsnavigation_sitelevel'] = 'Use the default site value'; diff --git a/lib.php b/lib.php index 6dca906..c4b971e 100644 --- a/lib.php +++ b/lib.php @@ -56,6 +56,21 @@ class format_onetopic extends core_courseformat\base { /** @var int One line view */ const TABSVIEW_ONELINE = 2; + /** @var int Only if theme not support "usescourseindex" */ + const SECTIONSNAVIGATION_SUPPORT = 1; + + /** @var int Not use */ + const SECTIONSNAVIGATION_NOT = 2; + + /** @var int Only at the bottom */ + const SECTIONSNAVIGATION_BOTTOM = 3; + + /** @var int Only at the bottom */ + const SECTIONSNAVIGATION_BOTH = 4; + + /** @var int Like slides */ + const SECTIONSNAVIGATION_SLIDES = 5; + /** @var bool If the class was previously instanced, in one execution cycle */ private static $loaded = false; @@ -428,6 +443,10 @@ public function course_format_options($foreditform = false) { 'tabsview' => [ 'default' => 0, 'type' => PARAM_INT + ], + 'usessectionsnavigation' => [ + 'default' => 0, + 'type' => PARAM_INT ] ]; } @@ -508,6 +527,22 @@ public function course_format_options($foreditform = false) { ], 'help' => 'tabsview', 'help_component' => 'format_onetopic', + ], + 'usessectionsnavigation' => [ + 'label' => new lang_string('usessectionsnavigation', 'format_onetopic'), + 'element_type' => 'select', + 'element_attributes' => [ + [ + '' => new lang_string('sectionsnavigation_sitelevel', 'format_onetopic'), + self::SECTIONSNAVIGATION_SUPPORT => new lang_string('sectionsnavigation_support', 'format_onetopic'), + self::SECTIONSNAVIGATION_NOT => new lang_string('sectionsnavigation_not', 'format_onetopic'), + self::SECTIONSNAVIGATION_BOTTOM => new lang_string('sectionsnavigation_bottom', 'format_onetopic'), + self::SECTIONSNAVIGATION_BOTH => new lang_string('sectionsnavigation_both', 'format_onetopic'), + self::SECTIONSNAVIGATION_SLIDES => new lang_string('sectionsnavigation_slides', 'format_onetopic'), + ] + ], + 'help' => 'usessectionsnavigation', + 'help_component' => 'format_onetopic', ] ]; $courseformatoptions = array_merge_recursive($courseformatoptions, $courseformatoptionsedit); @@ -563,6 +598,7 @@ public function update_course_format_options($data, $oldcourse = null) { if ($oldcourse !== null) { $oldcourse = (array)$oldcourse; $options = $this->course_format_options(); + foreach ($options as $key => $unused) { if (!array_key_exists($key, $data)) { if (array_key_exists($key, $oldcourse)) { @@ -577,6 +613,8 @@ public function update_course_format_options($data, $oldcourse = null) { $data['templatetopic_icons'] = 0; } else if ($key === 'tabsview') { $data['tabsview'] = self::TABSVIEW_DEFAULT; + } else if ($key === 'usessectionsnavigation') { + $data['usessectionsnavigation'] = 0; } } } diff --git a/settings.php b/settings.php index 096c128..b9eeb12 100644 --- a/settings.php +++ b/settings.php @@ -24,8 +24,27 @@ defined('MOODLE_INTERNAL') || die; +require_once($CFG->dirroot. '/course/format/onetopic/lib.php'); + if ($ADMIN->fulltree) { $settings->add(new admin_setting_configcheckbox('format_onetopic/enablecustomstyles', get_string('enablecustomstyles', 'format_onetopic'), get_string('enablecustomstyles_help', 'format_onetopic'), 1)); + + $settings->add(new admin_setting_configcheckbox('format_onetopic/anchortotabstree', + get_string('enableanchorposition', 'format_onetopic'), + get_string('enableanchorposition_help', 'format_onetopic'), 1)); + + $fields = [ + \format_onetopic::SECTIONSNAVIGATION_SUPPORT => new lang_string('sectionsnavigation_support', 'format_onetopic'), + \format_onetopic::SECTIONSNAVIGATION_NOT => new lang_string('sectionsnavigation_not', 'format_onetopic'), + \format_onetopic::SECTIONSNAVIGATION_BOTTOM => new lang_string('sectionsnavigation_bottom', 'format_onetopic'), + \format_onetopic::SECTIONSNAVIGATION_BOTH => new lang_string('sectionsnavigation_both', 'format_onetopic'), + \format_onetopic::SECTIONSNAVIGATION_SLIDES => new lang_string('sectionsnavigation_slides', 'format_onetopic'), + ]; + $settings->add(new admin_setting_configselect('format_onetopic/defaultsectionsnavigation', + get_string('defaultsectionsnavigation', 'format_onetopic'), + get_string('defaultsectionsnavigation_help', 'format_onetopic'), + \format_onetopic::SECTIONSNAVIGATION_SUPPORT, + $fields)); } diff --git a/styles.css b/styles.css index ae3a569..03bcd66 100644 --- a/styles.css +++ b/styles.css @@ -287,6 +287,60 @@ content: ""; } +.format-onetopic .single-section .nextsection span { + float: right; +} + +/* The slide navigation is only available to wide screens */ +@media (min-width: 600px) { + + .format-onetopic .sectionsnavigation-slides { + position: relative; + } + + .format-onetopic .single-section.sectionsnavigation-slides .nextsection a, + .format-onetopic .single-section.sectionsnavigation-slides .prevsection a { + display: none; + font-size: 0; + position: absolute; + top: calc(50% - 40px); + background-color: #fff; + border-radius: 50%; + border: 1px solid #dee2e6; + width: 50px; + height: 50px; + align-items: center; + justify-content: center; + opacity: 0.3; + box-shadow: 2px 2px 4px 1px #ccc; + text-decoration: none; + } + + .format-onetopic .single-section.sectionsnavigation-slides:hover .nextsection a, + .format-onetopic .single-section.sectionsnavigation-slides:hover .prevsection a { + display: flex; + } + + .format-onetopic .single-section.sectionsnavigation-slides:hover .nextsection a { + right: -30px; + } + + .format-onetopic .single-section.sectionsnavigation-slides:hover .prevsection a { + left: -20px; + } + + .format-onetopic .single-section.sectionsnavigation-slides .nextsection span, + .format-onetopic .single-section.sectionsnavigation-slides .prevsection span { + font-size: 40px; + } + + .format-onetopic .single-section.sectionsnavigation-slides .nextsection a:hover, + .format-onetopic .single-section.sectionsnavigation-slides .prevsection a:hover { + opacity: 1; + cursor: pointer; + } +} + @media (max-width: 600px) { .format-onetopic .verticaltabs.hastopictabs { display: block; @@ -295,4 +349,4 @@ .format-onetopic .verticaltabs .onetopic-tab-body { width: auto; } -} +} \ No newline at end of file diff --git a/templates/local/content.mustache b/templates/local/content.mustache index b036b38..8cca869 100644 --- a/templates/local/content.mustache +++ b/templates/local/content.mustache @@ -140,8 +140,8 @@ {{/hastopictabs}} -
- {{availability}} +
+ {{availability}} {{#sectionnavigation}} {{$ core_courseformat/local/content/sectionnavigation }} {{> core_courseformat/local/content/sectionnavigation }} diff --git a/version.php b/version.php index 0c6d56a..a0aa272 100644 --- a/version.php +++ b/version.php @@ -24,9 +24,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081607; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2022081608; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.1.03(PiedrasTeherán)'; +$plugin->release = '4.1.04(PiedrasTeherán)'; $plugin->dependencies = array('format_topics' => 2022041900); From 1f3d7c6e44baf6351751db1bda75d6ffc2b5f759 Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 7 Apr 2023 00:28:55 -0500 Subject: [PATCH 03/50] New course setting to hide the course index bar. --- README.txt | 1 + lang/en/format_onetopic.php | 4 +++- lang/es/format_onetopic.php | 15 +++++++++++++++ lib.php | 27 ++++++++++++++++++++++++++- styles.css | 17 ++++++++++++++++- 5 files changed, 61 insertions(+), 3 deletions(-) diff --git a/README.txt b/README.txt index 364d1fc..2d53614 100644 --- a/README.txt +++ b/README.txt @@ -23,6 +23,7 @@ IN VERSION 2022081608: - Navigation options: Next/previous section, with different display options. - A site setting option to define if use an anchor to navigate to the top of tabs when click in a tab. +- New course setting to hide the course index bar. 2022081607: - Duplicate section feature. diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 987dee2..8dfe5d4 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -103,6 +103,7 @@ $string['usessectionsnavigation'] = 'Uses sections navigation'; $string['usessectionsnavigation_help'] = 'Show buttons for navigate to next or previous section.'; +$string['sectionsnavigation_sitelevel'] = 'Use the default site value'; $string['sectionsnavigation_support'] = 'Only if theme not support the "uses course index" feature'; $string['sectionsnavigation_not'] = 'Not use'; $string['sectionsnavigation_bottom'] = 'Only at the bottom'; @@ -112,4 +113,5 @@ $string['enableanchorposition_help'] = 'Use an anchor to navigate to the top of tabs when click in a tab.'; $string['defaultsectionsnavigation'] = 'Default value to sections navigation'; $string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; -$string['sectionsnavigation_sitelevel'] = 'Use the default site value'; +$string['usescourseindex'] = 'Uses course index'; +$string['usescourseindex_help'] = 'Use the course index bar to navigate through the sections and resources'; diff --git a/lang/es/format_onetopic.php b/lang/es/format_onetopic.php index 0e30270..a625885 100644 --- a/lang/es/format_onetopic.php +++ b/lang/es/format_onetopic.php @@ -99,3 +99,18 @@ $string['hiddentabsbar'] = 'Las pestañas están configuradas para estar ocultas. No se verán cuando no esté en modo de edición.'; $string['enablecustomstyles'] = 'Habilitar estilos personalizados'; $string['enablecustomstyles_help'] = 'Habilitar color de fuente, color de fondo y otros estilos personalizados de pestañas en la configuración de la sección.'; + +$string['usessectionsnavigation'] = 'Usar navegación en secciones'; +$string['usessectionsnavigation_help'] = 'Mostrar un botón para navegar a la sección anterior y a la siguiente.'; +$string['sectionsnavigation_sitelevel'] = 'Usar el valor por defecto del sitio'; +$string['sectionsnavigation_support'] = 'Solamente si el tema no soporta la funcionalidad "Índice de curso"'; +$string['sectionsnavigation_not'] = 'No usar'; +$string['sectionsnavigation_bottom'] = 'Usar en la parte inferior'; +$string['sectionsnavigation_both'] = 'En la parte superior e inferior de la sección'; +$string['sectionsnavigation_slides'] = 'Similar a un pase de diapositivas'; +$string['enableanchorposition'] = 'Habilitar ancla de posición'; +$string['enableanchorposition_help'] = 'Usar una ancla para posicionarse en la parte superior de las pestañas cuando se haga clic en una pestaña.'; +$string['defaultsectionsnavigation'] = 'Valor por defecto para la navegación de secciones'; +$string['defaultsectionsnavigation_help'] = 'Valor por defecto a ser utilizado para definir el comportamiento de la funcionalidad "Usar navegación en secciones". Este valor puede ser sobreescrito por cada curso.'; +$string['usescourseindex'] = 'Usar índice de curso'; +$string['usescourseindex_help'] = 'Usar la barra lateral conocida como Índice de curso que permite la navegación a través de secciones y recursos.'; diff --git a/lib.php b/lib.php index c4b971e..e652967 100644 --- a/lib.php +++ b/lib.php @@ -187,7 +187,14 @@ public function uses_sections() { * @return bool */ public function uses_course_index() { - return true; + + if ($this->show_editor()) { + return true; + } + + $course = $this->get_course(); + + return isset($course->usescourseindex) ? $course->usescourseindex : true; } /** @@ -447,6 +454,10 @@ public function course_format_options($foreditform = false) { 'usessectionsnavigation' => [ 'default' => 0, 'type' => PARAM_INT + ], + 'usescourseindex' => [ + 'default' => 1, + 'type' => PARAM_INT ] ]; } @@ -543,6 +554,18 @@ public function course_format_options($foreditform = false) { ], 'help' => 'usessectionsnavigation', 'help_component' => 'format_onetopic', + ], + 'usescourseindex' => [ + 'label' => get_string('usescourseindex', 'format_onetopic'), + 'help' => 'usescourseindex', + 'help_component' => 'format_onetopic', + 'element_type' => 'select', + 'element_attributes' => [ + [ + 0 => new lang_string('no'), + 1 => new lang_string('yes') + ] + ], ] ]; $courseformatoptions = array_merge_recursive($courseformatoptions, $courseformatoptionsedit); @@ -615,6 +638,8 @@ public function update_course_format_options($data, $oldcourse = null) { $data['tabsview'] = self::TABSVIEW_DEFAULT; } else if ($key === 'usessectionsnavigation') { $data['usessectionsnavigation'] = 0; + } else if ($key === 'usescourseindex') { + $data['usescourseindex'] = 1; } } } diff --git a/styles.css b/styles.css index 03bcd66..b0b884e 100644 --- a/styles.css +++ b/styles.css @@ -305,7 +305,7 @@ position: absolute; top: calc(50% - 40px); background-color: #fff; - border-radius: 50%; + border-radius: 25px; border: 1px solid #dee2e6; width: 50px; height: 50px; @@ -338,6 +338,21 @@ .format-onetopic .single-section.sectionsnavigation-slides .prevsection a:hover { opacity: 1; cursor: pointer; + width: auto; + font-size: inherit; + } + + .format-onetopic .single-section.sectionsnavigation-slides .prevsection a:hover { + text-align: left; + justify-content: left; + padding-right: 10px; + } + + .format-onetopic .single-section.sectionsnavigation-slides .nextsection a:hover { + text-align: right; + justify-content: right; + padding-left: 10px; + flex-direction: row-reverse; } } From f772629f9be456512cbb5418e30cbdb38dd56261 Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 23 May 2023 00:57:00 -0500 Subject: [PATCH 04/50] New feature: tabs styles editor in site settings --- amd/build/main.min.js | 4 +- amd/build/main.min.js.map | 2 +- amd/build/tabstyles.min.js | 8 + amd/build/tabstyles.min.js.map | 1 + amd/src/main.js | 48 ++++ amd/src/tabstyles.js | 266 +++++++++++++++++ classes/output/courseformat/content.php | 87 +++++- .../courseformat/content/section/summary.php | 58 ++-- classes/tabs.php | 2 +- classes/tabstyles.php | 151 ++++++++++ lang/en/format_onetopic.php | 64 +++++ lib.php | 84 +----- settings.php | 18 ++ styles.css | 267 +++++++++--------- .../content/cm/activity_infoinline.mustache | 66 +++++ .../content/cm/activityinline.mustache | 60 +++- .../content/cm/availabilityinline.mustache | 50 ++++ .../courseformat/content/cminline.mustache | 4 +- .../content/cminlinecompletion.mustache | 31 ++ templates/local/content.mustache | 11 +- .../local/content/section/content.mustache | 6 +- templates/setting_tabstyles.mustache | 202 +++++++++++++ version.php | 6 +- 23 files changed, 1227 insertions(+), 269 deletions(-) create mode 100644 amd/build/tabstyles.min.js create mode 100644 amd/build/tabstyles.min.js.map create mode 100644 amd/src/tabstyles.js create mode 100644 classes/tabstyles.php create mode 100644 templates/courseformat/content/cm/activity_infoinline.mustache create mode 100644 templates/courseformat/content/cm/availabilityinline.mustache create mode 100644 templates/courseformat/content/cminlinecompletion.mustache create mode 100644 templates/setting_tabstyles.mustache diff --git a/amd/build/main.min.js b/amd/build/main.min.js index ac62b5f..b52cbe5 100644 --- a/amd/build/main.min.js +++ b/amd/build/main.min.js @@ -1,8 +1,8 @@ -define("format_onetopic/main",["exports","format_onetopic/oneline"],(function(_exports,OneLine){function _getRequireWildcardCache(nodeInterop){if("function"!=typeof WeakMap)return null;var cacheBabelInterop=new WeakMap,cacheNodeInterop=new WeakMap;return(_getRequireWildcardCache=function(nodeInterop){return nodeInterop?cacheNodeInterop:cacheBabelInterop})(nodeInterop)}Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.init=void 0,OneLine=function(obj,nodeInterop){if(!nodeInterop&&obj&&obj.__esModule)return obj;if(null===obj||"object"!=typeof obj&&"function"!=typeof obj)return{default:obj};var cache=_getRequireWildcardCache(nodeInterop);if(cache&&cache.has(obj))return cache.get(obj);var newObj={},hasPropertyDescriptor=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var key in obj)if("default"!==key&&Object.prototype.hasOwnProperty.call(obj,key)){var desc=hasPropertyDescriptor?Object.getOwnPropertyDescriptor(obj,key):null;desc&&(desc.get||desc.set)?Object.defineProperty(newObj,key,desc):newObj[key]=obj[key]}newObj.default=obj,cache&&cache.set(obj,newObj);return newObj} +define("format_onetopic/main",["exports","format_onetopic/oneline","jquery","core/modal_factory","core/str"],(function(_exports,OneLine,_jquery,_modal_factory,_str){function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}}function _getRequireWildcardCache(nodeInterop){if("function"!=typeof WeakMap)return null;var cacheBabelInterop=new WeakMap,cacheNodeInterop=new WeakMap;return(_getRequireWildcardCache=function(nodeInterop){return nodeInterop?cacheNodeInterop:cacheBabelInterop})(nodeInterop)}Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.init=void 0,OneLine=function(obj,nodeInterop){if(!nodeInterop&&obj&&obj.__esModule)return obj;if(null===obj||"object"!=typeof obj&&"function"!=typeof obj)return{default:obj};var cache=_getRequireWildcardCache(nodeInterop);if(cache&&cache.has(obj))return cache.get(obj);var newObj={},hasPropertyDescriptor=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var key in obj)if("default"!==key&&Object.prototype.hasOwnProperty.call(obj,key)){var desc=hasPropertyDescriptor?Object.getOwnPropertyDescriptor(obj,key):null;desc&&(desc.get||desc.set)?Object.defineProperty(newObj,key,desc):newObj[key]=obj[key]}newObj.default=obj,cache&&cache.set(obj,newObj);return newObj} /* * @package format_onetopic * @copyright 2021 David Herney Bernal - cirano * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */(OneLine);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons)}})); + */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle="";(0,_str.get_string)("aboutresource","format_onetopic").then((str=>{infotitle=str})),(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); //# sourceMappingURL=main.min.js.map \ No newline at end of file diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index c064514..8eef34c 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n};"],"names":["formattype","icons","OneLine","load"],"mappings":";;;;;6BA6BoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = '';\n getString('aboutresource', 'format_onetopic').then(str => {\n infotitle = str;\n });\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find( '.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function (match, p1) {\n return p1;\n }\n );\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","then","str","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,UAAY,uBACN,gBAAiB,mBAAmBC,MAAKC,MAC/CF,UAAYE,2BAGd,4CAA4CC,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAM,4BAEvBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQb,kCAICc,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAAUC,MAAOC,WAC9DA,MAIML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file diff --git a/amd/build/tabstyles.min.js b/amd/build/tabstyles.min.js new file mode 100644 index 0000000..b74c165 --- /dev/null +++ b/amd/build/tabstyles.min.js @@ -0,0 +1,8 @@ +define("format_onetopic/tabstyles",["exports","jquery","core/modal_factory"],(function(_exports,_jquery,_modal_factory){function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}} +/* + * @package format_onetopic + * @copyright 2023 David Herney Bernal - cirano + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.init=void 0,_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);var $tabstyles=null,$styleswindow=null,currenttype="default",globalstyles={},$inputtosave=null;_exports.init=()=>{if($tabstyles=(0,_jquery.default)("#onetopic-tabstyles"),$inputtosave=$tabstyles.find("textarea.savecontrol"),$styleswindow=(0,_jquery.default)("#onetopic-styleswindow"),""!==$inputtosave.val().trim()){try{null===(globalstyles=JSON.parse($inputtosave.val()))&&(globalstyles={})}catch(e){console.error(e),globalstyles={}}applyStyles()}var $colorpicker=$styleswindow.find(".colorpicker"),$setcolor=$colorpicker.find('[data-action="setcolor"]'),$colorpickerinput=$colorpicker.find("input");$styleswindow.find('[data-control="colorpicker"]').on("click",(function(){var $node=(0,_jquery.default)(this);$colorpicker.show(),$colorpickerinput.val($node.val()),$setcolor.data("target",$node)})).on("change",(function(){var $node=(0,_jquery.default)(this),color=$node.val().trim();$node.css("background-color",color)})),$setcolor.on("click",(function(e){e.preventDefault(),$colorpicker.hide(),$setcolor.data("target").val($colorpickerinput.val()).trigger("change")})),$colorpicker.find('[data-action="cancel"]').on("click",(function(){$colorpicker.hide()}));var title=$styleswindow.data("title");_modal_factory.default.create({title:title,body:""}).done((function(modal){var $modalBody=modal.getBody();$styleswindow.show(),$modalBody.append($styleswindow),$styleswindow.data("modal",modal)})),$styleswindow.find('[data-action="cancelstyles"]').on("click",(function(){$styleswindow.data("modal").hide()})),$styleswindow.find('[data-action="setstyles"]').on("click",(function(){var modal=$styleswindow.data("modal"),newstyles={};$styleswindow.find("[data-style]").each((function(){var $node=(0,_jquery.default)(this),key=$node.data("style"),value=$node.val();""!==value&&(newstyles[key]=value)})),globalstyles[currenttype]=newstyles,$inputtosave.val(JSON.stringify(globalstyles)),applyStyles(),modal.hide()}));["default","active","parent","highlighted","disabled","hover","childs","childindex"].forEach((type=>{(0,_jquery.default)("#onetopic-tabstyles #tabstyleset"+type).on("click",(function(e){e.preventDefault(),showStylesWindow(type)}))})),(0,_jquery.default)("#onetopic-tabstyles #tabstyleclear").on("click",(function(e){e.preventDefault(),globalstyles={},$inputtosave.val(""),applyStyles()}))};var showStylesWindow=function(type){if(currenttype=type,$styleswindow.find("[data-style]").each((function(){var $node=(0,_jquery.default)(this);$node.is('input[type="text"]')?($node.val(""),$node.trigger("change")):$node.is("select")&&$node.find("option").first().prop("selected",!0)})),void 0!==globalstyles[type]){var currentstyles=globalstyles[type];Object.entries(currentstyles).forEach((_ref=>{let[key,value]=_ref;$styleswindow.find('[data-style="'+key+'"]').val(value),$styleswindow.find('[data-control="colorpicker"]').trigger("change")}))}$styleswindow.data("modal").show()},applyStyles=function(){var withunits=["font-size","line-height","margin","padding","border-width","border-radius"],csscontent="";Object.entries(globalstyles).forEach((_ref2=>{let[type,styles]=_ref2;switch(type){case"active":csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, ",csscontent+=".format-onetopic .nav-tabs a.nav-link.active";break;case"parent":csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, ",csscontent+=".format-onetopic .nav-tabs .nav-item.haschilds a.nav-link";break;case"highlighted":csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, ",csscontent+=".format-onetopic .nav-tabs .nav-item.marker a.nav-link";break;case"disabled":csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, ",csscontent+=".format-onetopic .nav-tabs .nav-item.disabled a.nav-link";break;case"hover":csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, ",csscontent+=".format-onetopic .nav-tabs .nav-item a.nav-link:hover";break;case"childs":csscontent+=".format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link";break;case"childindex":csscontent+=".format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic.tab_initial a.nav-link";break;default:csscontent+=".format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, ",csscontent+=".format-onetopic .nav-tabs a.nav-link"}csscontent+="{";var units=[],stylesarray=Object.entries(styles);stylesarray.forEach((_ref3=>{let[key,value]=_ref3;0===key.indexOf("unit-")&&(key=key.replace("unit-",""),units[key]=value)})),stylesarray.forEach((_ref4=>{let[key,value]=_ref4;0!==key.indexOf("unit-")&&(void 0!==units[key]?value+=units[key]:-1!==withunits.indexOf(key)&&(value+="px"),csscontent+="others"==key?value+";":key+":"+value+";")})),csscontent+="}"}));var $stylecontainer=$tabstyles.find("style");$stylecontainer.length>0&&$stylecontainer.remove(),$stylecontainer=(0,_jquery.default)('"),$tabstyles.append($stylecontainer)}})); + +//# sourceMappingURL=tabstyles.min.js.map \ No newline at end of file diff --git a/amd/build/tabstyles.min.js.map b/amd/build/tabstyles.min.js.map new file mode 100644 index 0000000..08cd92a --- /dev/null +++ b/amd/build/tabstyles.min.js.map @@ -0,0 +1 @@ +{"version":3,"file":"tabstyles.min.js","sources":["../src/tabstyles.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2023 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\n\nvar $tabstyles = null;\nvar $styleswindow = null;\nvar currenttype = 'default';\nvar globalstyles = {};\nvar $inputtosave = null;\n\n/**\n * Component initialization.\n *\n * @method init\n */\nexport const init = () => {\n\n $tabstyles = $('#onetopic-tabstyles');\n $inputtosave = $tabstyles.find('textarea.savecontrol');\n $styleswindow = $('#onetopic-styleswindow');\n\n if ($inputtosave.val().trim() !== '') {\n\n try {\n globalstyles = JSON.parse($inputtosave.val());\n\n if (globalstyles === null) {\n globalstyles = {};\n }\n } catch (e) {\n console.error(e);\n globalstyles = {};\n }\n\n applyStyles();\n }\n\n var $colorpicker = $styleswindow.find('.colorpicker');\n var $setcolor = $colorpicker.find('[data-action=\"setcolor\"]');\n var $colorpickerinput = $colorpicker.find('input');\n\n // Color picker control.\n $styleswindow.find('[data-control=\"colorpicker\"]').on('click', function() {\n var $node = $(this);\n\n $colorpicker.show();\n $colorpickerinput.val($node.val());\n $setcolor.data('target', $node);\n }).on('change', function() {\n var $node = $(this);\n var color = $node.val().trim();\n\n $node.css('background-color', color);\n });\n\n $setcolor.on('click', function(e) {\n e.preventDefault();\n\n $colorpicker.hide();\n $setcolor.data('target').val($colorpickerinput.val()).trigger('change');\n });\n\n $colorpicker.find('[data-action=\"cancel\"]').on('click', function() {\n $colorpicker.hide();\n });\n\n var title = $styleswindow.data('title');\n\n // Initialize the modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n var $modalBody = modal.getBody();\n $styleswindow.show();\n $modalBody.append($styleswindow);\n $styleswindow.data('modal', modal);\n });\n\n // Save the styles.\n $styleswindow.find('[data-action=\"cancelstyles\"]').on('click', function() {\n $styleswindow.data('modal').hide();\n });\n\n $styleswindow.find('[data-action=\"setstyles\"]').on('click', function() {\n var modal = $styleswindow.data('modal');\n var newstyles = {};\n\n $styleswindow.find('[data-style]').each(function() {\n var $node = $(this);\n var key = $node.data('style');\n var value = $node.val();\n\n if (value !== '') {\n newstyles[key] = value;\n }\n });\n\n globalstyles[currenttype] = newstyles;\n $inputtosave.val(JSON.stringify(globalstyles));\n applyStyles();\n\n modal.hide();\n });\n\n var types = ['default', 'active', 'parent', 'highlighted', 'disabled', 'hover', 'childs', 'childindex'];\n types.forEach(type => {\n $('#onetopic-tabstyles #tabstyleset' + type).on('click', function(e) {\n e.preventDefault();\n showStylesWindow(type);\n });\n });\n\n $('#onetopic-tabstyles #tabstyleclear').on('click', function(e) {\n e.preventDefault();\n globalstyles = {};\n $inputtosave.val('');\n applyStyles();\n });\n\n};\n\n/**\n * Show the styles window.\n *\n * @param {string} type\n */\nvar showStylesWindow = function(type) {\n\n currenttype = type;\n $styleswindow.find('[data-style]').each(function() {\n var $node = $(this);\n\n if ($node.is('input[type=\"text\"]')) {\n $node.val('');\n $node.trigger('change');\n } else if ($node.is('select')) {\n $node.find('option').first().prop('selected', true);\n }\n });\n\n if (globalstyles[type] !== undefined) {\n var currentstyles = globalstyles[type];\n\n Object.entries(currentstyles).forEach(([key, value]) => {\n $styleswindow.find('[data-style=\"' + key + '\"]').val(value);\n\n // Apply the color.\n $styleswindow.find('[data-control=\"colorpicker\"]').trigger('change');\n });\n }\n\n $styleswindow.data('modal').show();\n\n};\n\n/**\n * Apply the styles to the tabs for check current visualization.\n */\nvar applyStyles = function() {\n\n var withunits = ['font-size', 'line-height', 'margin', 'padding', 'border-width', 'border-radius'];\n var csscontent = '';\n\n Object.entries(globalstyles).forEach(([type, styles]) => {\n\n switch (type) {\n case 'active':\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, ';\n csscontent += '.format-onetopic .nav-tabs a.nav-link.active';\n break;\n case 'parent':\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, ';\n csscontent += '.format-onetopic .nav-tabs .nav-item.haschilds a.nav-link';\n break;\n case 'highlighted':\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, ';\n csscontent += '.format-onetopic .nav-tabs .nav-item.marker a.nav-link';\n break;\n case 'disabled':\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, ';\n csscontent += '.format-onetopic .nav-tabs .nav-item.disabled a.nav-link';\n break;\n case 'hover':\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, ';\n csscontent += '.format-onetopic .nav-tabs .nav-item a.nav-link:hover';\n break;\n case 'childs':\n csscontent += '.format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link';\n break;\n case 'childindex':\n csscontent += '.format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic.tab_initial a.nav-link';\n break;\n default:\n csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, ';\n csscontent += '.format-onetopic .nav-tabs a.nav-link';\n }\n\n csscontent += '{';\n var units = [];\n var stylesarray = Object.entries(styles);\n\n // Check if exist units for some rules.\n stylesarray.forEach(([key, value]) => {\n // Check if the key start with the units prefix.\n if (key.indexOf('unit-') === 0) {\n\n // Remove the prefix.\n key = key.replace('unit-', '');\n units[key] = value;\n }\n });\n\n stylesarray.forEach(([key, value]) => {\n\n // Exclude the units rules.\n if (key.indexOf('unit-') === 0) {\n return;\n }\n\n // If exist a unit for the rule, apply it.\n if (units[key] !== undefined) {\n value = value + units[key];\n } else if (withunits.indexOf(key) !== -1) {\n // If the rule need units, apply px by default.\n value = value + 'px';\n }\n\n if (key == 'others') {\n csscontent += value + ';';\n } else {\n csscontent += key + ':' + value + ';';\n }\n });\n csscontent += '}';\n });\n\n var $stylecontainer = $tabstyles.find('style');\n\n if ($stylecontainer.length > 0) {\n $stylecontainer.remove();\n }\n\n $stylecontainer = $('');\n $tabstyles.append($stylecontainer);\n\n};\n"],"names":["$tabstyles","$styleswindow","currenttype","globalstyles","$inputtosave","find","val","trim","JSON","parse","e","console","error","applyStyles","$colorpicker","$setcolor","$colorpickerinput","on","$node","this","show","data","color","css","preventDefault","hide","trigger","title","create","done","modal","$modalBody","getBody","append","newstyles","each","key","value","stringify","forEach","type","showStylesWindow","is","first","prop","undefined","currentstyles","Object","entries","_ref","withunits","csscontent","_ref2","styles","units","stylesarray","_ref3","indexOf","replace","_ref4","$stylecontainer","length","remove"],"mappings":";;;;;oLAuBIA,WAAa,KACbC,cAAgB,KAChBC,YAAc,UACdC,aAAe,GACfC,aAAe,mBAOC,QAEhBJ,YAAa,mBAAE,uBACfI,aAAeJ,WAAWK,KAAK,wBAC/BJ,eAAgB,mBAAE,0BAEgB,KAA9BG,aAAaE,MAAMC,OAAe,KAKT,QAFrBJ,aAAeK,KAAKC,MAAML,aAAaE,UAGnCH,aAAe,IAErB,MAAOO,GACLC,QAAQC,MAAMF,GACdP,aAAe,GAGnBU,kBAGAC,aAAeb,cAAcI,KAAK,gBAClCU,UAAYD,aAAaT,KAAK,4BAC9BW,kBAAoBF,aAAaT,KAAK,SAG1CJ,cAAcI,KAAK,gCAAgCY,GAAG,SAAS,eACvDC,OAAQ,mBAAEC,MAEdL,aAAaM,OACbJ,kBAAkBV,IAAIY,MAAMZ,OAC5BS,UAAUM,KAAK,SAAUH,UAC1BD,GAAG,UAAU,eACRC,OAAQ,mBAAEC,MACVG,MAAQJ,MAAMZ,MAAMC,OAExBW,MAAMK,IAAI,mBAAoBD,UAGlCP,UAAUE,GAAG,SAAS,SAASP,GAC3BA,EAAEc,iBAEFV,aAAaW,OACbV,UAAUM,KAAK,UAAUf,IAAIU,kBAAkBV,OAAOoB,QAAQ,aAGlEZ,aAAaT,KAAK,0BAA0BY,GAAG,SAAS,WACpDH,aAAaW,cAGbE,MAAQ1B,cAAcoB,KAAK,gCAGlBO,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WACTC,WAAaD,MAAME,UACvB/B,cAAcmB,OACdW,WAAWE,OAAOhC,eAClBA,cAAcoB,KAAK,QAASS,UAIhC7B,cAAcI,KAAK,gCAAgCY,GAAG,SAAS,WAC3DhB,cAAcoB,KAAK,SAASI,UAGhCxB,cAAcI,KAAK,6BAA6BY,GAAG,SAAS,eACpDa,MAAQ7B,cAAcoB,KAAK,SAC3Ba,UAAY,GAEhBjC,cAAcI,KAAK,gBAAgB8B,MAAK,eAChCjB,OAAQ,mBAAEC,MACViB,IAAMlB,MAAMG,KAAK,SACjBgB,MAAQnB,MAAMZ,MAEJ,KAAV+B,QACAH,UAAUE,KAAOC,UAIzBlC,aAAaD,aAAegC,UAC5B9B,aAAaE,IAAIE,KAAK8B,UAAUnC,eAChCU,cAEAiB,MAAML,UAGE,CAAC,UAAW,SAAU,SAAU,cAAe,WAAY,QAAS,SAAU,cACpFc,SAAQC,2BACR,mCAAqCA,MAAMvB,GAAG,SAAS,SAASP,GAC9DA,EAAEc,iBACFiB,iBAAiBD,gCAIvB,sCAAsCvB,GAAG,SAAS,SAASP,GACzDA,EAAEc,iBACFrB,aAAe,GACfC,aAAaE,IAAI,IACjBO,sBAUJ4B,iBAAmB,SAASD,SAE5BtC,YAAcsC,KACdvC,cAAcI,KAAK,gBAAgB8B,MAAK,eAChCjB,OAAQ,mBAAEC,MAEVD,MAAMwB,GAAG,uBACTxB,MAAMZ,IAAI,IACVY,MAAMQ,QAAQ,WACPR,MAAMwB,GAAG,WAChBxB,MAAMb,KAAK,UAAUsC,QAAQC,KAAK,YAAY,WAI3BC,IAAvB1C,aAAaqC,MAAqB,KAC9BM,cAAgB3C,aAAaqC,MAEjCO,OAAOC,QAAQF,eAAeP,SAAQU,WAAEb,IAAKC,YACzCpC,cAAcI,KAAK,gBAAkB+B,IAAM,MAAM9B,IAAI+B,OAGrDpC,cAAcI,KAAK,gCAAgCqB,QAAQ,aAInEzB,cAAcoB,KAAK,SAASD,QAO5BP,YAAc,eAEVqC,UAAY,CAAC,YAAa,cAAe,SAAU,UAAW,eAAgB,iBAC9EC,WAAa,GAEjBJ,OAAOC,QAAQ7C,cAAcoC,SAAQa,YAAEZ,KAAMa,qBAEjCb,UACC,SACDW,YAAc,qFACdA,YAAc,yDAEb,SACDA,YAAc,wFACdA,YAAc,sEAEb,cACDA,YAAc,qFACdA,YAAc,mEAEb,WACDA,YAAc,uFACdA,YAAc,qEAEb,QACDA,YAAc,oFACdA,YAAc,kEAEb,SACDA,YAAc,wFAEb,aACDA,YAAc,wGAGdA,YAAc,8EACdA,YAAc,wCAGtBA,YAAc,QACVG,MAAQ,GACRC,YAAcR,OAAOC,QAAQK,QAGjCE,YAAYhB,SAAQiB,YAAEpB,IAAKC,aAEM,IAAzBD,IAAIqB,QAAQ,WAGZrB,IAAMA,IAAIsB,QAAQ,QAAS,IAC3BJ,MAAMlB,KAAOC,UAIrBkB,YAAYhB,SAAQoB,YAAEvB,IAAKC,aAGM,IAAzBD,IAAIqB,QAAQ,gBAKGZ,IAAfS,MAAMlB,KACNC,OAAgBiB,MAAMlB,MACa,IAA5Bc,UAAUO,QAAQrB,OAEzBC,OAAgB,MAIhBc,YADO,UAAPf,IACcC,MAAQ,IAERD,IAAM,IAAMC,MAAQ,QAG1Cc,YAAc,WAGdS,gBAAkB5D,WAAWK,KAAK,SAElCuD,gBAAgBC,OAAS,GACzBD,gBAAgBE,SAGpBF,iBAAkB,mBAAE,0BAA4BT,WAAa,YAC7DnD,WAAWiC,OAAO2B"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index b38d3ce..347ac3f 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -19,6 +19,9 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ import * as OneLine from 'format_onetopic/oneline'; +import $ from 'jquery'; +import ModalFactory from 'core/modal_factory'; +import {get_string as getString} from 'core/str'; /** * Component initialization. @@ -32,4 +35,49 @@ export const init = (formattype, icons) => { if (formattype == 2) { OneLine.load(icons); } + + var infotitle = ''; + getString('aboutresource', 'format_onetopic').then(str => { + infotitle = str; + }); + + $('.format-onetopic .onetopic .iconwithhelp').each(function() { + var $node = $(this); + $node.on('click', function(e) { + e.preventDefault(); + var $content = $node.find( '.iconwithhelp-content'); + + if ($content.data('modal')) { + $content.data('modal').show(); + return; + } + + var title = $content.data('title'); + + if (!title) { + title = infotitle; + } + + // Show the content in a modal window. + ModalFactory.create({ + 'title': title, + 'body': '' + }).done(function(modal) { + + var contenthtml = $content.html(); + + // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline. + contenthtml = contenthtml.replace(//g, function (match, p1) { + return p1; + } + ); + + var $modalBody = modal.getBody(); + $modalBody.append(contenthtml); + modal.show(); + $content.data('modal', modal); + }); + }); + }); + }; \ No newline at end of file diff --git a/amd/src/tabstyles.js b/amd/src/tabstyles.js new file mode 100644 index 0000000..2ef1413 --- /dev/null +++ b/amd/src/tabstyles.js @@ -0,0 +1,266 @@ +// This file is part of Moodle - http://moodle.org/ +// +// Moodle is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// Moodle is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// You should have received a copy of the GNU General Public License +// along with Moodle. If not, see . + +/* + * @package format_onetopic + * @copyright 2023 David Herney Bernal - cirano + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +import $ from 'jquery'; +import ModalFactory from 'core/modal_factory'; + +var $tabstyles = null; +var $styleswindow = null; +var currenttype = 'default'; +var globalstyles = {}; +var $inputtosave = null; + +/** + * Component initialization. + * + * @method init + */ +export const init = () => { + + $tabstyles = $('#onetopic-tabstyles'); + $inputtosave = $tabstyles.find('textarea.savecontrol'); + $styleswindow = $('#onetopic-styleswindow'); + + if ($inputtosave.val().trim() !== '') { + + try { + globalstyles = JSON.parse($inputtosave.val()); + + if (globalstyles === null) { + globalstyles = {}; + } + } catch (e) { + console.error(e); + globalstyles = {}; + } + + applyStyles(); + } + + var $colorpicker = $styleswindow.find('.colorpicker'); + var $setcolor = $colorpicker.find('[data-action="setcolor"]'); + var $colorpickerinput = $colorpicker.find('input'); + + // Color picker control. + $styleswindow.find('[data-control="colorpicker"]').on('click', function() { + var $node = $(this); + + $colorpicker.show(); + $colorpickerinput.val($node.val()); + $setcolor.data('target', $node); + }).on('change', function() { + var $node = $(this); + var color = $node.val().trim(); + + $node.css('background-color', color); + }); + + $setcolor.on('click', function(e) { + e.preventDefault(); + + $colorpicker.hide(); + $setcolor.data('target').val($colorpickerinput.val()).trigger('change'); + }); + + $colorpicker.find('[data-action="cancel"]').on('click', function() { + $colorpicker.hide(); + }); + + var title = $styleswindow.data('title'); + + // Initialize the modal window. + ModalFactory.create({ + 'title': title, + 'body': '' + }).done(function(modal) { + var $modalBody = modal.getBody(); + $styleswindow.show(); + $modalBody.append($styleswindow); + $styleswindow.data('modal', modal); + }); + + // Save the styles. + $styleswindow.find('[data-action="cancelstyles"]').on('click', function() { + $styleswindow.data('modal').hide(); + }); + + $styleswindow.find('[data-action="setstyles"]').on('click', function() { + var modal = $styleswindow.data('modal'); + var newstyles = {}; + + $styleswindow.find('[data-style]').each(function() { + var $node = $(this); + var key = $node.data('style'); + var value = $node.val(); + + if (value !== '') { + newstyles[key] = value; + } + }); + + globalstyles[currenttype] = newstyles; + $inputtosave.val(JSON.stringify(globalstyles)); + applyStyles(); + + modal.hide(); + }); + + var types = ['default', 'active', 'parent', 'highlighted', 'disabled', 'hover', 'childs', 'childindex']; + types.forEach(type => { + $('#onetopic-tabstyles #tabstyleset' + type).on('click', function(e) { + e.preventDefault(); + showStylesWindow(type); + }); + }); + + $('#onetopic-tabstyles #tabstyleclear').on('click', function(e) { + e.preventDefault(); + globalstyles = {}; + $inputtosave.val(''); + applyStyles(); + }); + +}; + +/** + * Show the styles window. + * + * @param {string} type + */ +var showStylesWindow = function(type) { + + currenttype = type; + $styleswindow.find('[data-style]').each(function() { + var $node = $(this); + + if ($node.is('input[type="text"]')) { + $node.val(''); + $node.trigger('change'); + } else if ($node.is('select')) { + $node.find('option').first().prop('selected', true); + } + }); + + if (globalstyles[type] !== undefined) { + var currentstyles = globalstyles[type]; + + Object.entries(currentstyles).forEach(([key, value]) => { + $styleswindow.find('[data-style="' + key + '"]').val(value); + + // Apply the color. + $styleswindow.find('[data-control="colorpicker"]').trigger('change'); + }); + } + + $styleswindow.data('modal').show(); + +}; + +/** + * Apply the styles to the tabs for check current visualization. + */ +var applyStyles = function() { + + var withunits = ['font-size', 'line-height', 'margin', 'padding', 'border-width', 'border-radius']; + var csscontent = ''; + + Object.entries(globalstyles).forEach(([type, styles]) => { + + switch (type) { + case 'active': + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, '; + csscontent += '.format-onetopic .nav-tabs a.nav-link.active'; + break; + case 'parent': + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, '; + csscontent += '.format-onetopic .nav-tabs .nav-item.haschilds a.nav-link'; + break; + case 'highlighted': + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, '; + csscontent += '.format-onetopic .nav-tabs .nav-item.marker a.nav-link'; + break; + case 'disabled': + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, '; + csscontent += '.format-onetopic .nav-tabs .nav-item.disabled a.nav-link'; + break; + case 'hover': + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, '; + csscontent += '.format-onetopic .nav-tabs .nav-item a.nav-link:hover'; + break; + case 'childs': + csscontent += '.format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link'; + break; + case 'childindex': + csscontent += '.format-onetopic .onetopic-tab-body .nav-tabs .nav-item.subtopic.tab_initial a.nav-link'; + break; + default: + csscontent += '.format-onetopic .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, '; + csscontent += '.format-onetopic .nav-tabs a.nav-link'; + } + + csscontent += '{'; + var units = []; + var stylesarray = Object.entries(styles); + + // Check if exist units for some rules. + stylesarray.forEach(([key, value]) => { + // Check if the key start with the units prefix. + if (key.indexOf('unit-') === 0) { + + // Remove the prefix. + key = key.replace('unit-', ''); + units[key] = value; + } + }); + + stylesarray.forEach(([key, value]) => { + + // Exclude the units rules. + if (key.indexOf('unit-') === 0) { + return; + } + + // If exist a unit for the rule, apply it. + if (units[key] !== undefined) { + value = value + units[key]; + } else if (withunits.indexOf(key) !== -1) { + // If the rule need units, apply px by default. + value = value + 'px'; + } + + if (key == 'others') { + csscontent += value + ';'; + } else { + csscontent += key + ':' + value + ';'; + } + }); + csscontent += '}'; + }); + + var $stylecontainer = $tabstyles.find('style'); + + if ($stylecontainer.length > 0) { + $stylecontainer.remove(); + } + + $stylecontainer = $(''); + $tabstyles.append($stylecontainer); + +}; diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index b8b8c57..891a28f 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -97,6 +97,90 @@ public function export_for_template(\renderer_base $output) { $hassecondrow = is_object($secondtabslist) && count($secondtabslist->tabs) > 0; + $withunits = ['font-size', 'line-height', 'margin', 'padding', 'border-width', 'border-radius']; + $csscontent = ''; + $csstabstyles = ''; + $tabstyles = get_config('format_onetopic', 'tabstyles'); + if (!empty($tabstyles)) { + $tabstyles = @json_decode($tabstyles); + + if (is_object($tabstyles)) { + + foreach ($tabstyles as $type => $styles) { + + switch ($type) { + case 'active': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, '; + $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link.active'; + break; + case 'parent': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.haschilds a.nav-link'; + break; + case 'highlighted': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.marker a.nav-link'; + break; + case 'disabled': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.disabled a.nav-link'; + break; + case 'hover': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, '; + $csscontent .= '#tabs-tree-start .format_onetopic-tabs.nav-tabs .nav-item a.nav-link:hover'; + break; + case 'childs': + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link'; + break; + case 'childindex': + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.tab_initial a.nav-link'; + break; + default: + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link'; + } + + $csscontent .= '{'; + $units = []; + + // Check if exist units for some rules. + foreach ($styles as $key => $value) { + + // Check if the key start with the units prefix. + if (strpos($key, 'unit-') === 0) { + + // Remove the prefix. + $ownerkey = str_replace('unit-', '', $key); + $units[$ownerkey] = $value; + unset($styles->$key); + } + } + + foreach ($styles as $key => $value) { + + // If exist a unit for the rule, apply it. + if (isset($units[$key])) { + $value = $value . $units[$key]; + } else if (in_array($key, $withunits)) { + // If the rule need units, apply px by default. + $value = $value . 'px'; + } + + if ($key == 'others') { + $csscontent .= $value . ';'; + } else { + $csscontent .= $key . ':' . $value . ';'; + } + } + + $csscontent .= '}'; + } + + // Clean the CSS for html tags. + $csstabstyles = preg_replace('/<[^>]*>/', '', $csscontent); + } + } + $data = (object)[ 'title' => $format->page_title(), // This method should be in the course_format class. 'initialsection' => $initialsection, @@ -111,7 +195,8 @@ public function export_for_template(\renderer_base $output) { 'hasformatmsgs' => count(\format_onetopic::$formatmsgs) > 0, 'formatmsgs' => \format_onetopic::$formatmsgs, 'hidetabsbar' => ($course->hidetabsbar == 1 && $format->show_editor()), - 'sectionclasses' => '' + 'sectionclasses' => '', + 'csstabstyles' => $csstabstyles, ]; // The current section format has extra navigation. diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index 480ce4a..fecaceb 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -156,9 +156,6 @@ private function replace_resources(section_info $section) { $summary = $section->summary; - $htmlresource = ''; - $htmlmore = ''; - if (!empty($section->sequence)) { $sectionmods = explode(",", $section->sequence); @@ -184,23 +181,26 @@ private function replace_resources(section_info $section) { // Display the link to the module (or do nothing if module has no url). $cmdata = $cm->export_for_template($this->output); $cmdata->modinline = true; - $cmdata->hideicons = $course->templatetopic_icons == 0; + $cmdata->hideicons = !$course->templatetopic_icons; + $cmdata->uniqueid = 'cm_' . $mod->id . '_' . time() . '_' . rand(0, 1000); + $cmdata->singlename = $instancename; + $cmdata->showinlinehelp = $cmdata->activityinfo->hascompletion + || $cmdata->activityinfo->hasdates + || !empty($cmdata->altcontent); $url = $mod->url; - if (!empty($url)) { - // If there is content but NO link (eg label), then display the - // content here (BEFORE any icons). In this case cons must be - // displayed after the content so that it makes more sense visually - // and for accessibility reasons, e.g. if you have a one-line label - // it should work similarly (at least in terms of ordering) to an - // activity. - $renderer = $this->format->get_renderer($PAGE); - $htmlresource = $renderer->render_from_template('format_onetopic/courseformat/content/cminline', $cmdata); + if (empty($url)) { + // If there is content but NO link (like label), then don't display it. + continue; } + $template = 'format_onetopic/courseformat/content/cminline'; + if ($completioninfo->is_enabled($mod) !== COMPLETION_TRACKING_NONE) { $completion = $DB->get_record('course_modules_completion', - array('coursemoduleid' => $mod->id, 'userid' => $USER->id, 'completionstate' => 1)); + ['coursemoduleid' => $mod->id, 'userid' => $USER->id, 'completionstate' => 1]); + + $template = 'format_onetopic/courseformat/content/cminlinecompletion'; $showcompletionconditions = $course->showcompletionconditions == COMPLETION_SHOW_CONDITIONS; @@ -214,32 +214,14 @@ private function replace_resources(section_info $section) { $completedclass .= ' hascompletionconditions'; } - $htmlresource = '' . $htmlresource; - - if ($showcompletionconditions) { - - // Fetch activity dates. - $activitydates = []; - if ($course->showactivitydates) { - $activitydates = \core\activity_dates::get_dates_for_module($mod, $USER->id); - } - - // Fetch completion details. - $completiondetails = \core_completion\cm_completion_details::get_instance($mod, - $USER->id, - $showcompletionconditions); - - $completionhtml = $this->output->activity_information($mod, $completiondetails, $activitydates); + $cmdata->completedclass = $completedclass; + $cmdata->showcompletionconditions = $showcompletionconditions; - $htmlresource .= ''; - $htmlresource .= $this->output->image_icon('i/info', ''); - $htmlresource .= $completionhtml; - $htmlresource .= ''; - } - - $htmlresource .= ''; } + $renderer = $this->format->get_renderer($PAGE); + $htmlresource = $renderer->render_from_template($template, $cmdata); + // Replace the link in pattern: [[resource name]]. $this->tplstringreplace = $htmlresource; $this->tplstringsearch = $instancename; @@ -256,7 +238,7 @@ private function replace_resources(section_info $section) { } } - return $summary . $htmlmore; + return $summary; } diff --git a/classes/tabs.php b/classes/tabs.php index 355c7de..3833960 100644 --- a/classes/tabs.php +++ b/classes/tabs.php @@ -77,7 +77,7 @@ public function get_list(bool $assubtabs = false) : array { foreach ($this->tabslist as $tab) { - if ($assubtabs) { + if ($assubtabs && strpos($tab->specialclass, ' subtopic ') === false) { $tab->specialclass .= ' subtopic '; } diff --git a/classes/tabstyles.php b/classes/tabstyles.php new file mode 100644 index 0000000..a3f7945 --- /dev/null +++ b/classes/tabstyles.php @@ -0,0 +1,151 @@ +. + +/** + * Class containing a tab styles implementation. + * + * @package format_onetopic + * @copyright 2023 David Herney - https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +namespace format_onetopic; + +/** + * Implement the tab styles control. + * + * @copyright 2023 David Herney - https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class tabstyles extends \admin_setting_configtextarea { + + /** + * Return an XHTML string for the setting + * @return string Returns an XHTML string + */ + public function output_html($data, $query='') { + global $OUTPUT, $PAGE; + + $tabs = new \format_onetopic\tabs(); + + // Default tab. + $title = get_string('tablabeldefault', 'format_onetopic', 1); + $tab = new \format_onetopic\singletab(0, $title, '#', $title); + $tabs->add($tab); + + // Active tab. + $title = get_string('tablabelactive', 'format_onetopic'); + $tab = new \format_onetopic\singletab(1, $title, '#', $title); + $tab->selected = true; + $tabs->add($tab); + + // Parent tab. + $title = get_string('tablabelparent', 'format_onetopic'); + $tab = new \format_onetopic\singletab(2, $title, '#', $title); + $tab->selected = true; + + // Default child index tab. + $title = get_string('index', 'format_onetopic'); + $childtab = new \format_onetopic\singletab(2, $title, '#', $title); + $childtab->specialclass = 'tab_initial'; + $tab->add_child($childtab); + + // Default child tab. + $title = get_string('tablabeldefault', 'format_onetopic', '3.1'); + $childtab = new \format_onetopic\singletab(3, $title, '#', $title); + $tab->add_child($childtab); + + // Default child tab 2. + $title = get_string('tablabeldefault', 'format_onetopic', '3.2'); + $childtab = new \format_onetopic\singletab(3, $title, '#', $title); + $tab->add_child($childtab); + $tabs->add($tab); + + // Higlighted tab. + $title = get_string('tablabelhighlighted', 'format_onetopic'); + $tab = new \format_onetopic\singletab(3, $title, '#', $title); + $tab->specialclass = 'marker'; + $tabs->add($tab); + + // Disabled tab. + $title = get_string('tablabeldisabled', 'format_onetopic'); + $tab = new \format_onetopic\singletab(4, $title, '#', $title); + $tab->specialclass = 'dimmed disabled'; + $tabs->add($tab); + + // Other default child tab. + $title = get_string('tablabeldefault', 'format_onetopic', '5'); + $tab = new \format_onetopic\singletab(5, $title, '#', $title); + $tabs->add($tab); + + $tabslist = $tabs->get_list(); + + $cp = new \admin_setting_configcolourpicker('colorpicker', + get_string('colorpicker', 'format_onetopic'), + get_string('colorpicker_help', 'format_onetopic'), ''); + + $csssizeoptions = range(0, 100); + $csssizeoptions[0] = ''; + + $cssunits = [ + ['value' => '', 'label' => ''], + ['value' => 'px', 'label' => get_string('cssunit_px', 'format_onetopic')], + ['value' => 'em', 'label' => get_string('cssunit_em', 'format_onetopic')], + ['value' => '%', 'label' => get_string('cssunit_percent', 'format_onetopic')], + ['value' => 'in', 'label' => get_string('cssunit_in', 'format_onetopic')], + ]; + + $secondtabslist = $tabs->get_secondlist(); + + $default = $this->get_defaultsetting(); + $context = (object) [ + 'id' => $this->get_id(), + 'name' => $this->get_full_name(), + 'value' => $data, + 'tabs' => $tabslist, + 'secondrow' => $secondtabslist, + 'tabsviewclass' => 'verticaltabs', + 'colorpicker' => $cp->output_html(''), + 'csssizeoptions' => $csssizeoptions, + 'cssunits' => $cssunits, + ]; + $element = $OUTPUT->render_from_template('format_onetopic/setting_tabstyles', $context); + + $styles = new \stdClass(); + $PAGE->requires->js_call_amd('format_onetopic/tabstyles', 'init'); + + return format_admin_setting($this, $this->visiblename, $element, $this->description, true, '', $default, $query); + } + + /** + * Validate the contents of the SCSS to ensure its parsable. Does not + * attempt to detect undefined scss variables. + * + * @param string $data The scss code from text field. + * @return mixed bool true for success or string:error on failure. + */ + public function validate($data) { + if (empty($data)) { + return true; + } + + $object = @json_decode($data); + if (json_last_error() !== JSON_ERROR_NONE) { + return get_string('invalidjsonstyles', 'format_onetopic', json_last_error_msg()); + } + + return true; + } +} diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 8dfe5d4..c316a99 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -115,3 +115,67 @@ $string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; $string['usescourseindex'] = 'Uses course index'; $string['usescourseindex_help'] = 'Use the course index bar to navigate through the sections and resources'; + +$string['aboutresource'] = 'About the resource'; +$string['courseindex'] = 'Course index'; +$string['courseindex_help'] = 'Enable or disable the course index bar to navigate through the sections and resources. +This option is only usable if the Course index feature is available in the current Theme. +This option can be overwrite for each course.'; +$string['usecourseindexsite'] = 'Use the default site value'; +$string['settingsheaderstyles'] = 'Styles'; +$string['tabstyles'] = 'Tab styles'; +$string['tabstyles_help'] = 'Set the styles for the differents tab states.'; +$string['tablabeldefault'] = 'Default tab {$a}'; +$string['tablabelactive'] = 'Active tab'; +$string['tablabelparent'] = 'Parent tab'; +$string['tablabelhighlighted'] = 'Highlighted'; +$string['tablabeldisabled'] = 'Disabled'; +$string['tabstylesetdefault'] = 'Set Default'; +$string['tabstylesetactive'] = 'Set Active'; +$string['tabstylesetparent'] = 'Set Parent'; +$string['tabstylesethighlighted'] = 'Set Highlighted'; +$string['tabstylesetdisabled'] = 'Set Disabled'; +$string['tabstylesethover'] = 'Set Hover'; +$string['tabstylestitle'] = 'Tab styles'; +$string['tabstylesset'] = 'Set styles'; +$string['tabstyleclear'] = 'Clear styles'; +$string['cssbackground'] = 'Background'; +$string['cssfont'] = 'Font'; +$string['csscolor'] = 'Color'; +$string['cssweight'] = 'Weight'; +$string['cssweightbold'] = 'Bold'; +$string['cssweightlighter'] = 'Lighter'; +$string['colorpicker'] = 'Color picker'; +$string['colorpicker_help'] = ''; +$string['csssize'] = 'Size'; +$string['cssstyle'] = 'Font style'; +$string['cssnormal'] = 'Normal'; +$string['cssitalic'] = 'Italic'; +$string['cssoblique'] = 'Oblique'; +$string['cssother'] = 'Other styles'; +$string['cssborder'] = 'Border'; +$string['cssnone'] = 'None'; +$string['csssolid'] = 'Solid'; +$string['cssdashed'] = 'Dashed'; +$string['cssdotted'] = 'Dotted'; +$string['cssdouble'] = 'Double'; +$string['cssgroove'] = 'Groove'; +$string['csshidden'] = 'Hidden'; +$string['cssinset'] = 'Inset'; +$string['cssoutset'] = 'Outset'; +$string['cssridge'] = 'Ridge'; +$string['cssradius'] = 'Radius'; +$string['cssunit'] = 'Unit'; +$string['cssunit_px'] = 'px'; +$string['cssunit_em'] = 'em'; +$string['cssunit_percent'] = '%'; +$string['cssunit_in'] = 'in'; +$string['invalidjsonstyles'] = 'Styles configuration is not valid, fails with: {$a}'; +$string['tabstylebuttons_help'] = 'Click on each button to configure the appearance of the tab in each of its possible states.'; +$string['tabstylesetchilds'] = 'Set Childs'; +$string['tabstylesetchildindex'] = 'Set Child index'; +$string[''] = ''; +$string[''] = ''; +$string[''] = ''; +$string[''] = ''; +$string[''] = ''; diff --git a/lib.php b/lib.php index e652967..c872625 100644 --- a/lib.php +++ b/lib.php @@ -194,7 +194,12 @@ public function uses_course_index() { $course = $this->get_course(); - return isset($course->usescourseindex) ? $course->usescourseindex : true; + // The 2 value is Use the site configuration. + if (isset($course->usescourseindex) && $course->usescourseindex < 2) { + return $course->usescourseindex; + } + + return get_config('format_onetopic', 'courseindex') == 1; } /** @@ -456,7 +461,7 @@ public function course_format_options($foreditform = false) { 'type' => PARAM_INT ], 'usescourseindex' => [ - 'default' => 1, + 'default' => 2, 'type' => PARAM_INT ] ]; @@ -544,7 +549,7 @@ public function course_format_options($foreditform = false) { 'element_type' => 'select', 'element_attributes' => [ [ - '' => new lang_string('sectionsnavigation_sitelevel', 'format_onetopic'), + '0' => new lang_string('sectionsnavigation_sitelevel', 'format_onetopic'), self::SECTIONSNAVIGATION_SUPPORT => new lang_string('sectionsnavigation_support', 'format_onetopic'), self::SECTIONSNAVIGATION_NOT => new lang_string('sectionsnavigation_not', 'format_onetopic'), self::SECTIONSNAVIGATION_BOTTOM => new lang_string('sectionsnavigation_bottom', 'format_onetopic'), @@ -562,8 +567,9 @@ public function course_format_options($foreditform = false) { 'element_type' => 'select', 'element_attributes' => [ [ + 2 => new lang_string('usecourseindexsite', 'format_onetopic'), 0 => new lang_string('no'), - 1 => new lang_string('yes') + 1 => new lang_string('yes'), ] ], ] @@ -639,7 +645,7 @@ public function update_course_format_options($data, $oldcourse = null) { } else if ($key === 'usessectionsnavigation') { $data['usessectionsnavigation'] = 0; } else if ($key === 'usescourseindex') { - $data['usescourseindex'] = 1; + $data['usescourseindex'] = 2; } } } @@ -946,71 +952,3 @@ function format_onetopics_inplace_editable($itemtype, $itemid, $newvalue) { return course_get_format($section->course)->inplace_editable_update_section_name($section, $itemtype, $newvalue); } } - -/** - * Class used in order to replace tags into text. It is a part of templates functionality. - * - * Called by preg_replace_callback in renderer.php. - * - * @since 2.0 - * @package format_onetopic - * @copyright 2012 David Herney Bernal - cirano - * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */ -class format_onetopic_replace_regularexpression { - /** @var string Text to search */ - public $_string_search; - - /** @var string Text to replace */ - public $_string_replace; - - /** @var string Temporal key */ - public $_tag_string = '{label_tag_replace}'; - - /** - * Replace a tag into a text. - * - * @param array $match - * @return array - */ - public function replace_tag_in_expresion ($match) { - - $term = $match[0]; - $term = str_replace("[[", '', $term); - $term = str_replace("]]", '', $term); - - $text = strip_tags($term); - - if (strpos($text, ':') > -1) { - - $pattern = '/([^:])+:/i'; - $text = preg_replace($pattern, '', $text); - - // Change text for alternative text. - $newreplace = str_replace($this->_string_search, $text, $this->_string_replace); - - // Posible html tags position. - $pattern = '/([>][^<]*:[^<]*[<])+/i'; - $term = preg_replace($pattern, '><:><', $term); - - $pattern = '/([>][^<]*:[^<]*$)+/i'; - $term = preg_replace($pattern, '><:>', $term); - - $pattern = '/(^[^<]*:[^<]*[<])+/i'; - $term = preg_replace($pattern, '<:><', $term); - - $pattern = '/(^[^<]*:[^<]*$)/i'; - $term = preg_replace($pattern, '<:>', $term); - - $pattern = '/([>][^<^:]*[<])+/i'; - $term = preg_replace($pattern, '><', $term); - - $term = str_replace('<:>', $newreplace, $term); - } else { - // Change tag for resource or mod name. - $newreplace = str_replace($this->_tag_string, $this->_string_search, $this->_string_replace); - $term = str_replace($this->_string_search, $newreplace, $term); - } - return $term; - } -} diff --git a/settings.php b/settings.php index b9eeb12..7a55b69 100644 --- a/settings.php +++ b/settings.php @@ -35,6 +35,11 @@ get_string('enableanchorposition', 'format_onetopic'), get_string('enableanchorposition_help', 'format_onetopic'), 1)); + $options = ['0' => get_string('disable'), '1' => get_string('enable')]; + $settings->add(new admin_setting_configselect('format_onetopic/courseindex', + get_string('courseindex', 'format_onetopic'), + get_string('courseindex_help', 'format_onetopic'), 1, $options)); + $fields = [ \format_onetopic::SECTIONSNAVIGATION_SUPPORT => new lang_string('sectionsnavigation_support', 'format_onetopic'), \format_onetopic::SECTIONSNAVIGATION_NOT => new lang_string('sectionsnavigation_not', 'format_onetopic'), @@ -47,4 +52,17 @@ get_string('defaultsectionsnavigation_help', 'format_onetopic'), \format_onetopic::SECTIONSNAVIGATION_SUPPORT, $fields)); + + // Styles settings. + $name = 'format_onetopic/settingsheaderstyles'; + $heading = get_string('settingsheaderstyles', 'format_onetopic'); + $setting = new admin_setting_heading($name, $heading, ''); + $settings->add($setting); + + $name = 'format_onetopic/tabstyles'; + $title = get_string('tabstyles', 'format_onetopic'); + $description = get_string('tabstyles_help', 'format_onetopic'); + $setting = new \format_onetopic\tabstyles($name, $title, $description, ''); + $settings->add($setting); + } diff --git a/styles.css b/styles.css index b0b884e..82f3d89 100644 --- a/styles.css +++ b/styles.css @@ -1,43 +1,18 @@ /** Styles included in topics course format */ -.format-onetopic .jumpmenu { - text-align: center; -} - -.format-onetopic .course-content div.single-section .tabtree .tabrow0 li { - line-height: 28px; - display: inline-block; -} - -.format-onetopic .course-content div.single-section .tabtree .tabrow0 li.here .empty { - bottom: 3px; - display: block; - height: 1px; - left: 0; - right: 0; -} - -.format-onetopic .course-content div.single-section .tabtree { - margin-bottom: 0; -} - -.format-onetopic .tab_content { +.format-onetopic .format_onetopic-tabs .nav-link { white-space: nowrap; width: 100%; + max-width: 300px; overflow: hidden; text-overflow: ellipsis; } -.format-onetopic .course-content ul.nav-tabs li.marker a { +.format-onetopic ul.nav-tabs.format_onetopic-tabs li.marker a { font-weight: bold; } -.format-onetopic .utilities-separator { - clear: both; - margin-top: 15px; -} - -.format-onetopic .course-content ul.nav-tabs li.dimmed a { +.format-onetopic ul.nav-tabs.format_onetopic-tabs li.dimmed a { color: #999; opacity: 0.5; } @@ -52,114 +27,18 @@ margin: 0; } -.format-onetopic .subtopic-increase-sections { - margin-right: 10px; -} - -.format-onetopic li.sublevel { - padding-left: 20px; -} - -.format-onetopic .onetopic .nav-tabs > li > a { - padding: 0; -} - -.format-onetopic .onetopic .tab_content { - padding: 8px 12px; - display: inline-block; -} - -.format-onetopic .onetopic .cmnameinline .activityiconcontainer { - width: auto; - height: auto; - padding: 0.2rem; -} - -.format-onetopic .availability_info_box { - display: inline; -} - -.format-onetopic .summary img.activityicon { - margin-right: 3px; - vertical-align: text-bottom; -} - -.format-onetopic #course_format_onetopic_config_movesection .form-item { - border-bottom: 1px solid #999; - padding: 10px; -} - -.format-onetopic #course_format_onetopic_config_movesection .form-label { - font-weight: bold; -} - -.format-onetopic #course_format_onetopic_config_movesection .form-setting { +/* Its a subtabs bar */ +.format-onetopic .onetopic-tab-body .format_onetopic-tabs { padding-left: 20px; } +/* End Its a subtabs bar */ -.format-onetopic #course_format_onetopic_config_movesection .form-description { - padding-left: 50px; - font-style: italic; -} - -.format-onetopic #course_format_onetopic_config_movesection #changenumsections { - text-align: left; -} - -.format-onetopic .onetopic .content > .summary .quickeditlink { - display: none; -} - -.format-onetopic .onetopic .content > .summary .iconhelp { +.format-onetopic .content .summarytext .iconwithhelp { cursor: pointer; - margin-left: 2px; -} - -.format-onetopic .onetopic .content > .summary .iconhelp i { - margin: 0; -} - -.format-onetopic .onetopic .completiontag > form, -.format-onetopic .onetopic .completiontag > form > div { - display: inline; } -.format-onetopic .onetopic .completiontag > form > div button { - padding: 0; +.format-onetopic .content .summarytext .iconwithhelp .icon { margin: 0; - line-height: 0; -} - -.format-onetopic .onetopic .completiontag img.icon { - margin: 0 3px 0 5px; -} - -.format-onetopic .onetopic .completiontag .showcompletionconditions { - position: absolute; -} - -.format-onetopic .onetopic .completiontag.hascompletionconditions { - padding-right: 24px; -} - -.format-onetopic .onetopic .completiontag .showcompletionconditions:hover { - z-index: 2; - background-color: #fff; - padding: 5px; - border: 1px solid; - border-radius: 5px; -} - -.format-onetopic .onetopic .completiontag .showcompletionconditions .activity-information { - display: none; -} - -.format-onetopic .onetopic .completiontag .showcompletionconditions:hover .activity-information { - display: block; -} - -.format-onetopic .onetopic .completiontag .showcompletionconditions:hover > img { - display: none; } .format-onetopic .verticaltabs.hastopictabs { @@ -287,8 +166,124 @@ content: ""; } -.format-onetopic .single-section .nextsection span { - float: right; +/* Template styles */ +.format-onetopic .onetopic .cmnameinline .activityiconcontainer { + width: auto; + height: auto; + padding: 0.2rem; +} + +.format-onetopic .availability_info_box { + display: inline; +} + +.format-onetopic .activityinsummarytpl .description .course-description-item { + background-color: transparent; +} + +.format-onetopic .activityinsummarytpl .description .availabilityinfo { + display: inline-block; + min-width: 300px; + margin: 0; + padding: 0; +} + +/* End of template styles */ + +/* Completion */ +.format-onetopic .onetopic .completiontag img.icon { + margin: 0 3px 0 5px; +} +/* End of completion*/ + +/* Sections/activities navigation */ +.format-onetopic .section-navigation .prevsection, +.format-onetopic .section-navigation .nextsection { + display: flex; + min-width: 100px; +} + +.format-onetopic .section-navigation .nextsection { + justify-content: right; + margin-left: 5px; +} + +.format-onetopic .section-navigation .prevsection { + justify-content: left; + margin-right: 5px; +} + +.format-onetopic .section-navigation .prevsection a, +.format-onetopic .section-navigation .nextsection a { + display: flex; + align-items: center; + line-height: 100%; +} + +.format-onetopic .section-navigation .prevsection a { + padding-right: 10px; +} + +.format-onetopic .section-navigation .nextsection a { + flex-direction: row-reverse; + padding-left: 10px; + text-align: right; +} + +/* The jump list if exist */ +.format-onetopic .single-section .section-navigation.mdl-bottom div:nth-child(2) { + max-width: calc(100% - 210px); +} + +/* Tab styles configuration */ +#onetopic-tabstyles .tabstyleset-buttons button { + margin-bottom: 10px; +} + +#onetopic-styleswindow fieldset { + display: flex; + flex-wrap: wrap; +} + +#onetopic-styleswindow fieldset > div { + display: flex; + padding: 5px; +} + +#onetopic-styleswindow fieldset > div > div { + display: flex; +} + +#onetopic-styleswindow fieldset > div.whithlabel { + flex-direction: column; +} + +#onetopic-styleswindow fieldset > div.whithlabel label { + color: #888; + text-align: center; +} + +#onetopic-styleswindow [data-control="colorpicker"] { + width: 100px; +} + +#onetopic-styleswindow .colorpicker { + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; + background-color: #fffe; + padding: 10px; +} + +#onetopic-styleswindow .colorpicker #admin-colorpicker { + flex-direction: column; + align-items: center; +} + +#onetopic-styleswindow .buttons-box { + text-align: center; } /* The slide navigation is only available to wide screens */ @@ -364,4 +359,12 @@ .format-onetopic .verticaltabs .onetopic-tab-body { width: auto; } + + .format-onetopic .verticaltabs > .tabs-wrapper { + width: auto; + } + + .format-onetopic .course-content .section-navigation { + flex-direction: column; + } } \ No newline at end of file diff --git a/templates/courseformat/content/cm/activity_infoinline.mustache b/templates/courseformat/content/cm/activity_infoinline.mustache new file mode 100644 index 0000000..0f27ba9 --- /dev/null +++ b/templates/courseformat/content/cm/activity_infoinline.mustache @@ -0,0 +1,66 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/courseformat/content/cm/activity_infoinline + + Container to display activity information on the course page such as: + - Activity completion requirements (automatic completion) + - Manual completion button + + Example context (json): + { + "activityname": "Course announcements", + "hascompletion": true, + "uservisible": true, + "isautomatic": true, + "showmanualcompletion": true, + "completiondetails": [ + { + "statuscomplete": 1, + "description": "Viewed" + }, + { + "statusincomplete": 1, + "description": "Receive a grade" + } + ] + } +}} + + {{#hascompletion}} + {{#uservisible}} + + {{#isautomatic}} + + {{#completiondetails}} + {{$ core_course/completion_automatic }} + {{> core_course/completion_automatic }} + {{/ core_course/completion_automatic }} + {{/completiondetails}} + + {{/isautomatic}} + {{^isautomatic}} + {{#showmanualcompletion}} + {{$ core_course/completion_manual }} + {{> core_course/completion_manual }} + {{/ core_course/completion_manual }} + {{/showmanualcompletion}} + {{/isautomatic}} + + {{/uservisible}} + {{/hascompletion}} + diff --git a/templates/courseformat/content/cm/activityinline.mustache b/templates/courseformat/content/cm/activityinline.mustache index e0029f0..de52bc5 100644 --- a/templates/courseformat/content/cm/activityinline.mustache +++ b/templates/courseformat/content/cm/activityinline.mustache @@ -56,7 +56,7 @@ "modstealth": true } }} -
+ {{^hasname}} {{$ core_courseformat/local/content/cm/badges }} {{> core_courseformat/local/content/cm/badges }} @@ -68,19 +68,57 @@ {{/ format_onetopic/courseformat/content/cm/cmnameinline }} {{/cmname}} {{#afterlink}} - + {{/afterlink}} - {{#activityinfo}} - {{#hascompletion}} -
- {{> core_courseformat/local/content/cm/activity_info}} -
- {{/hascompletion}} - {{/activityinfo}} -
+ {{#showinlinehelp}} + {{#activityinfo}} + + {{#pix}} e/help, core, {{#str}} info {{/str}} {{/pix}} + + + {{/activityinfo}} + {{/showinlinehelp}} + {{#hasname}} {{$ core_courseformat/local/content/cm/badges }} {{> core_courseformat/local/content/cm/badges }} diff --git a/templates/courseformat/content/cm/availabilityinline.mustache b/templates/courseformat/content/cm/availabilityinline.mustache new file mode 100644 index 0000000..6c4f0d2 --- /dev/null +++ b/templates/courseformat/content/cm/availabilityinline.mustache @@ -0,0 +1,50 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/courseformat/content/cm/availabilityinline + + Displays a activity availability with inline tags. + + Example context (json): + { + "info": [ + { + "classes": "", + "text": "Not available unless:
  • It is on or after 8 June 2012
", + "ishidden": 0, + "isstealth": 0, + "isrestricted": 1, + "isfullinfo": 1 + } + ], + "hasmodavailability": true + } +}} +{{#hasmodavailability}} + {{#info}} + + {{^isrestricted}} + {{{text}}} + {{/isrestricted}} + {{#isrestricted}} + + {{#pix}}t/unlock, core{{/pix}} + + {{/isrestricted}} + + {{/info}} +{{/hasmodavailability}} diff --git a/templates/courseformat/content/cminline.mustache b/templates/courseformat/content/cminline.mustache index 6a2631e..c4e6e3a 100644 --- a/templates/courseformat/content/cminline.mustache +++ b/templates/courseformat/content/cminline.mustache @@ -56,7 +56,7 @@ "modstealth": true } }} -
{{! @@ -66,4 +66,4 @@ {{$ format_onetopic/courseformat/content/cm/activityinline }} {{> format_onetopic/courseformat/content/cm/activityinline }} {{/ format_onetopic/courseformat/content/cm/activityinline }} -
+ diff --git a/templates/courseformat/content/cminlinecompletion.mustache b/templates/courseformat/content/cminlinecompletion.mustache new file mode 100644 index 0000000..7be7c85 --- /dev/null +++ b/templates/courseformat/content/cminlinecompletion.mustache @@ -0,0 +1,31 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/courseformat/content/cminlinecompletion + + Displays a course module instance inside a course section. + + Example context (json): + { + "completedclass": "complete" + } +}} + + {{$ format_onetopic/courseformat/content/cminline }} + {{> format_onetopic/courseformat/content/cminline }} + {{/ format_onetopic/courseformat/content/cminline }} + diff --git a/templates/local/content.mustache b/templates/local/content.mustache index 8cca869..695c89d 100644 --- a/templates/local/content.mustache +++ b/templates/local/content.mustache @@ -15,7 +15,7 @@ along with Moodle. If not, see . }} {{! - @template format_onetopic/local/tabtree + @template format_onetopic/local/content Displays the complete course format. @@ -101,7 +101,8 @@ "summary": { "summarytext": "Summary text!" } - } + }, + "csstabstyles": "" } }}
@@ -172,6 +173,12 @@ {{/ core_courseformat/local/content/addsection}} {{/numsections}}
+{{#csstabstyles}} + +{{/csstabstyles}} + {{#js}} require(['core_courseformat/local/content'], function(component) { component.init('{{uniqid}}-course-format', {}, {{sectionreturn}}); diff --git a/templates/local/content/section/content.mustache b/templates/local/content/section/content.mustache index beabf44..0f01f3c 100644 --- a/templates/local/content/section/content.mustache +++ b/templates/local/content/section/content.mustache @@ -96,9 +96,9 @@ {{/ core_courseformat/local/content/section/summary }} {{/summary}} {{#availability}} - {{$ core_courseformat/local/content/section/availability }} - {{> core_courseformat/local/content/section/availability }} - {{/ core_courseformat/local/content/section/availability }} + {{$ format_onetopic/courseformat/content/cm/availabilityinline }} + {{> format_onetopic/courseformat/content/cm/availabilityinline }} + {{/ format_onetopic/courseformat/content/cm/availabilityinline }} {{/availability}}
{{#cmsummary}} diff --git a/templates/setting_tabstyles.mustache b/templates/setting_tabstyles.mustache new file mode 100644 index 0000000..712f5ab --- /dev/null +++ b/templates/setting_tabstyles.mustache @@ -0,0 +1,202 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/setting_tabstyles + + Admin text setting template. + + Context variables required for this template: + * name - form element name + * id - element id + * value - element value + * size - element size + * forceltr - always display as ltr + * attributes - list of additional attributes containing name, value + * readonly - bool + + Example context (json): + { + "name": "test", + "id": "test0", + "value": "A tall, dark stranger will have more fun than you.", + "size": "21", + "forceltr": false, + "readonly": false, + "attributes": [ { "name": "readonly", "value": "readonly" } ] + } +}} +
+{{! + Input to save the configured styles. +}} + + + {{^readonly}} +
+ + + + + + + + + +
+

{{#str}} tabstylebuttons_help, format_onetopic {{/str}}

+ {{/readonly}} + +

{{#str}} tabsview_default, format_onetopic {{/str}}

+
+
+ {{>format_onetopic/courseformat/tabtree}} +
+ +
+ {{#secondrow}} + {{>format_onetopic/courseformat/tabtree}} + {{/secondrow}} +
+ +
+ +

{{#str}} tabsview_vertical, format_onetopic {{/str}}

+
+
+ {{>format_onetopic/courseformat/tabtree}} +
+ +
+ {{#secondrow}} + {{>format_onetopic/courseformat/tabtree}} + {{/secondrow}} +
+ +
+ + +
diff --git a/version.php b/version.php index a0aa272..07687ae 100644 --- a/version.php +++ b/version.php @@ -24,9 +24,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081608; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2022081608.02; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). -$plugin->maturity = MATURITY_STABLE; +$plugin->maturity = MATURITY_BETA; $plugin->release = '4.1.04(PiedrasTeherán)'; -$plugin->dependencies = array('format_topics' => 2022041900); +$plugin->dependencies = ['format_topics' => 2022041900]; From 4535e02e7007ed99f79e3f571fb39b91387ea239 Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 23 May 2023 01:28:50 -0500 Subject: [PATCH 05/50] Code styles --- amd/build/main.min.js | 2 +- amd/build/main.min.js.map | 2 +- amd/src/main.js | 10 ++++++---- amd/src/tabstyles.js | 1 + classes/output/courseformat/content.php | 3 ++- classes/tabstyles.php | 5 ++++- lib.php | 2 +- templates/courseformat/content/cminline.mustache | 11 +++++++---- .../courseformat/content/cminlinecompletion.mustache | 5 ++++- templates/setting_tabstyles.mustache | 11 ++++++++--- 10 files changed, 35 insertions(+), 17 deletions(-) diff --git a/amd/build/main.min.js b/amd/build/main.min.js index b52cbe5..9d3c97a 100644 --- a/amd/build/main.min.js +++ b/amd/build/main.min.js @@ -3,6 +3,6 @@ define("format_onetopic/main",["exports","format_onetopic/oneline","jquery","cor * @package format_onetopic * @copyright 2021 David Herney Bernal - cirano * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle="";(0,_str.get_string)("aboutresource","format_onetopic").then((str=>{infotitle=str})),(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); + */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle="";(0,_str.get_string)("aboutresource","format_onetopic").then((str=>{infotitle=str})).catch((function(){infotitle=""})),(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); //# sourceMappingURL=main.min.js.map \ No newline at end of file diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index 8eef34c..8a8e738 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = '';\n getString('aboutresource', 'format_onetopic').then(str => {\n infotitle = str;\n });\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find( '.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function (match, p1) {\n return p1;\n }\n );\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","then","str","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,UAAY,uBACN,gBAAiB,mBAAmBC,MAAKC,MAC/CF,UAAYE,2BAGd,4CAA4CC,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAM,4BAEvBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQb,kCAICc,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAAUC,MAAOC,WAC9DA,MAIML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = '';\n getString('aboutresource', 'format_onetopic').then(str => {\n infotitle = str;\n })\n .catch(function() {\n infotitle = '';\n });\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find('.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","then","str","catch","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,UAAY,uBACN,gBAAiB,mBAAmBC,MAAKC,MAC/CF,UAAYE,OAEfC,OAAM,WACHH,UAAY,0BAGd,4CAA4CI,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAK,4BAEtBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQd,kCAICe,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,WAC7DA,MAGML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index 347ac3f..2a12451 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -39,13 +39,16 @@ export const init = (formattype, icons) => { var infotitle = ''; getString('aboutresource', 'format_onetopic').then(str => { infotitle = str; + }) + .catch(function() { + infotitle = ''; }); $('.format-onetopic .onetopic .iconwithhelp').each(function() { var $node = $(this); $node.on('click', function(e) { e.preventDefault(); - var $content = $node.find( '.iconwithhelp-content'); + var $content = $node.find('.iconwithhelp-content'); if ($content.data('modal')) { $content.data('modal').show(); @@ -67,10 +70,9 @@ export const init = (formattype, icons) => { var contenthtml = $content.html(); // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline. - contenthtml = contenthtml.replace(//g, function (match, p1) { + contenthtml = contenthtml.replace(//g, function(match, p1) { return p1; - } - ); + }); var $modalBody = modal.getBody(); $modalBody.append(contenthtml); diff --git a/amd/src/tabstyles.js b/amd/src/tabstyles.js index 2ef1413..c3c8fe4 100644 --- a/amd/src/tabstyles.js +++ b/amd/src/tabstyles.js @@ -47,6 +47,7 @@ export const init = () => { globalstyles = {}; } } catch (e) { + // eslint-disable-next-line no-console console.error(e); globalstyles = {}; } diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index 891a28f..dd7fa58 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -133,7 +133,8 @@ public function export_for_template(\renderer_base $output) { $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link'; break; case 'childindex': - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.tab_initial a.nav-link'; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs' . + ' .nav-item.subtopic.tab_initial a.nav-link'; break; default: $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, '; diff --git a/classes/tabstyles.php b/classes/tabstyles.php index a3f7945..0c7b875 100644 --- a/classes/tabstyles.php +++ b/classes/tabstyles.php @@ -33,9 +33,12 @@ class tabstyles extends \admin_setting_configtextarea { /** * Return an XHTML string for the setting + * + * @param array $data The data to be output + * @param string $query The query string * @return string Returns an XHTML string */ - public function output_html($data, $query='') { + public function output_html($data, $query = '') { global $OUTPUT, $PAGE; $tabs = new \format_onetopic\tabs(); diff --git a/lib.php b/lib.php index c872625..79e6ea1 100644 --- a/lib.php +++ b/lib.php @@ -208,7 +208,7 @@ public function uses_course_index() { * @return bool if the course format uses indentation. */ public function uses_indentation(): bool { - return false; + return true; } /** diff --git a/templates/courseformat/content/cminline.mustache b/templates/courseformat/content/cminline.mustache index c4e6e3a..cf91dc7 100644 --- a/templates/courseformat/content/cminline.mustache +++ b/templates/courseformat/content/cminline.mustache @@ -53,12 +53,14 @@ } ] }, - "modstealth": true + "modstealth": true, + "testingcminline": true } }} - + }}{{#modinline}}activityinline{{/modinline}}" data-activityname="{{activityname}}">{{/testingcminline}} {{! Place the actual content of the activity-item in a separate template to make it easier for other formats to add additional content to the activity wrapper. @@ -66,4 +68,5 @@ {{$ format_onetopic/courseformat/content/cm/activityinline }} {{> format_onetopic/courseformat/content/cm/activityinline }} {{/ format_onetopic/courseformat/content/cm/activityinline }} - +{{^testingcminline}}{{/testingcminline}} +{{#testingcminline}}
{{/testingcminline}} diff --git a/templates/courseformat/content/cminlinecompletion.mustache b/templates/courseformat/content/cminlinecompletion.mustache index 7be7c85..828a8f3 100644 --- a/templates/courseformat/content/cminlinecompletion.mustache +++ b/templates/courseformat/content/cminlinecompletion.mustache @@ -21,11 +21,14 @@ Example context (json): { - "completedclass": "complete" + "completedclass": "complete", + "testingcompletion": true } }} +{{#testingcompletion}}
{{/testingcompletion}} {{$ format_onetopic/courseformat/content/cminline }} {{> format_onetopic/courseformat/content/cminline }} {{/ format_onetopic/courseformat/content/cminline }} +{{#testingcompletion}}
{{/testingcompletion}} diff --git a/templates/setting_tabstyles.mustache b/templates/setting_tabstyles.mustache index 712f5ab..a9fadab 100644 --- a/templates/setting_tabstyles.mustache +++ b/templates/setting_tabstyles.mustache @@ -23,8 +23,6 @@ * name - form element name * id - element id * value - element value - * size - element size - * forceltr - always display as ltr * attributes - list of additional attributes containing name, value * readonly - bool @@ -36,7 +34,14 @@ "size": "21", "forceltr": false, "readonly": false, - "attributes": [ { "name": "readonly", "value": "readonly" } ] + "attributes": [ { "name": "readonly", "value": "readonly" } ], + "cssunits": [ + { "value": "px", "label": "px" }, + { "value": "em", "label": "em" }, + { "value": "%", "label": "%" } + ], + "csssizeoptions": [ "8", "9", "10", "11", "12", "14", "16", "18", "20", "22", "24", "26", "28", "36", "48", "72" ], + "colorpicker": "" } }}
From 8592419ece09756cb145ea0385ef5c3d86e476a4 Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 23 May 2023 01:58:17 -0500 Subject: [PATCH 06/50] Code styles --- amd/build/main.min.js | 2 +- amd/build/main.min.js.map | 2 +- amd/src/main.js | 8 +------- lang/en/format_onetopic.php | 7 +------ templates/courseformat/content/cminline.mustache | 2 +- .../content/cminlinecompletion.mustache | 6 +++--- templates/setting_tabstyles.mustache | 15 ++++++++------- 7 files changed, 16 insertions(+), 26 deletions(-) diff --git a/amd/build/main.min.js b/amd/build/main.min.js index 9d3c97a..a26cdf8 100644 --- a/amd/build/main.min.js +++ b/amd/build/main.min.js @@ -3,6 +3,6 @@ define("format_onetopic/main",["exports","format_onetopic/oneline","jquery","cor * @package format_onetopic * @copyright 2021 David Herney Bernal - cirano * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle="";(0,_str.get_string)("aboutresource","format_onetopic").then((str=>{infotitle=str})).catch((function(){infotitle=""})),(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); + */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle=(0,_str.get_string)("aboutresource","format_onetopic");(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); //# sourceMappingURL=main.min.js.map \ No newline at end of file diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index 8a8e738..c4b7d8f 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = '';\n getString('aboutresource', 'format_onetopic').then(str => {\n infotitle = str;\n })\n .catch(function() {\n infotitle = '';\n });\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find('.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","then","str","catch","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,UAAY,uBACN,gBAAiB,mBAAmBC,MAAKC,MAC/CF,UAAYE,OAEfC,OAAM,WACHH,UAAY,0BAGd,4CAA4CI,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAK,4BAEtBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQd,kCAICe,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,WAC7DA,MAGML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = getString('aboutresource', 'format_onetopic');\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find('.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,WAAY,mBAAU,gBAAiB,uCAEzC,4CAA4CC,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAK,4BAEtBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQX,kCAICY,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,WAC7DA,MAGML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index 2a12451..cbfa15e 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -36,13 +36,7 @@ export const init = (formattype, icons) => { OneLine.load(icons); } - var infotitle = ''; - getString('aboutresource', 'format_onetopic').then(str => { - infotitle = str; - }) - .catch(function() { - infotitle = ''; - }); + var infotitle = getString('aboutresource', 'format_onetopic'); $('.format-onetopic .onetopic .iconwithhelp').each(function() { var $node = $(this); diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index c316a99..f06457e 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -148,7 +148,7 @@ $string['colorpicker'] = 'Color picker'; $string['colorpicker_help'] = ''; $string['csssize'] = 'Size'; -$string['cssstyle'] = 'Font style'; +$string['cssstyle'] = 'Style'; $string['cssnormal'] = 'Normal'; $string['cssitalic'] = 'Italic'; $string['cssoblique'] = 'Oblique'; @@ -174,8 +174,3 @@ $string['tabstylebuttons_help'] = 'Click on each button to configure the appearance of the tab in each of its possible states.'; $string['tabstylesetchilds'] = 'Set Childs'; $string['tabstylesetchildindex'] = 'Set Child index'; -$string[''] = ''; -$string[''] = ''; -$string[''] = ''; -$string[''] = ''; -$string[''] = ''; diff --git a/templates/courseformat/content/cminline.mustache b/templates/courseformat/content/cminline.mustache index cf91dc7..284b478 100644 --- a/templates/courseformat/content/cminline.mustache +++ b/templates/courseformat/content/cminline.mustache @@ -69,4 +69,4 @@ {{> format_onetopic/courseformat/content/cm/activityinline }} {{/ format_onetopic/courseformat/content/cm/activityinline }} {{^testingcminline}}{{/testingcminline}} -{{#testingcminline}}
{{/testingcminline}} +{{#testingcminline}}
{{/testingcminline}} diff --git a/templates/courseformat/content/cminlinecompletion.mustache b/templates/courseformat/content/cminlinecompletion.mustache index 828a8f3..15dcaf6 100644 --- a/templates/courseformat/content/cminlinecompletion.mustache +++ b/templates/courseformat/content/cminlinecompletion.mustache @@ -25,10 +25,10 @@ "testingcompletion": true } }} -{{#testingcompletion}}
{{/testingcompletion}} - +{{#testingcompletion}}
{{/testingcompletion}} +{{^testingcompletion}}{{/testingcompletion}} {{$ format_onetopic/courseformat/content/cminline }} {{> format_onetopic/courseformat/content/cminline }} {{/ format_onetopic/courseformat/content/cminline }} - +{{^testingcompletion}}{{/testingcompletion}} {{#testingcompletion}}
{{/testingcompletion}} diff --git a/templates/setting_tabstyles.mustache b/templates/setting_tabstyles.mustache index a9fadab..583a9e2 100644 --- a/templates/setting_tabstyles.mustache +++ b/templates/setting_tabstyles.mustache @@ -41,7 +41,8 @@ { "value": "%", "label": "%" } ], "csssizeoptions": [ "8", "9", "10", "11", "12", "14", "16", "18", "20", "22", "24", "26", "28", "36", "48", "72" ], - "colorpicker": "" + "colorpicker": "", + "testingmode": true } }}
@@ -107,7 +108,7 @@ - + {{^testingmode}}{{/testingmode}} @@ -128,7 +129,7 @@
{{#csssizeoptions}} - {{/csssizeoptions}}} + {{/csssizeoptions}} - + {{^testingmode}}{{/testingmode}} @@ -174,7 +175,7 @@ " }, - "sectionreturn": 1, "singlesection": { "num": 1, "id": 35, @@ -102,85 +62,26 @@ "summarytext": "Summary text!" } }, - "csstabstyles": "" } }} -
-

{{{title}}}

- {{{completionhelp}}} - {{#hasformatmsgs}} - {{#formatmsgs}} - {{>core/notification_info}} - {{/formatmsgs}} - {{/hasformatmsgs}} - - {{#initialsection}} -
-
    - {{$ format_onetopic/local/content/section }} - {{> format_onetopic/local/content/section }} - {{/ format_onetopic/local/content/section }} -
-
- {{/initialsection}} - -
- {{#hastopictabs}} -
- {{>format_onetopic/courseformat/tabtree}} -
- -
- - {{#hassecondrow}} - {{#secondrow}} - {{>format_onetopic/courseformat/tabtree}} - {{/secondrow}} - {{/hassecondrow}} - - {{/hastopictabs}} - -
- {{availability}} - {{#sectionnavigation}} - {{$ core_courseformat/local/content/sectionnavigation }} - {{> core_courseformat/local/content/sectionnavigation }} - {{/ core_courseformat/local/content/sectionnavigation }} - {{/sectionnavigation}} -
    - {{#singlesection}} - {{$ format_onetopic/local/content/section }} - {{> format_onetopic/local/content/section }} - {{/ format_onetopic/local/content/section }} - {{/singlesection}} -
- {{#sectionselector}} - {{$ core_courseformat/local/content/sectionselector }} - {{> core_courseformat/local/content/sectionselector }} - {{/ core_courseformat/local/content/sectionselector }} - {{/sectionselector}} -
- {{#hastopictabs}} - {{! End of onetopic-tab-body box. }} -
- {{/hastopictabs}} -
- - {{#numsections}} - {{$ core_courseformat/local/content/addsection}} - {{> core_courseformat/local/content/addsection}} - {{/ core_courseformat/local/content/addsection}} - {{/numsections}} +
+ {{availability}} + {{#sectionnavigation}} + {{$ core_courseformat/local/content/sectionnavigation }} + {{> core_courseformat/local/content/sectionnavigation }} + {{/ core_courseformat/local/content/sectionnavigation }} + {{/sectionnavigation}} +
    + {{#singlesection}} + {{$ format_onetopic/local/content/section }} + {{> format_onetopic/local/content/section }} + {{/ format_onetopic/local/content/section }} + {{/singlesection}} +
+ {{#sectionselector}} + {{$ core_courseformat/local/content/sectionselector }} + {{> core_courseformat/local/content/sectionselector }} + {{/ core_courseformat/local/content/sectionselector }} + {{/sectionselector}}
-{{#csstabstyles}} - -{{/csstabstyles}} - -{{#js}} -require(['core_courseformat/local/content'], function(component) { - component.init('{{uniqid}}-course-format', {}, {{sectionreturn}}); -}); -{{/js}} diff --git a/version.php b/version.php index 8cec768..109e5a7 100644 --- a/version.php +++ b/version.php @@ -24,7 +24,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081609; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2022081609.04; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From 3d706a007cdb0c2f543cb8843be4b7b60b95034f Mon Sep 17 00:00:00 2001 From: Tim Schroeder Date: Fri, 4 Aug 2023 18:41:22 +0200 Subject: [PATCH 16/50] fixed endless redirects in case the section is unavailable (i.e. has availability restrictions that are not met) but the user can view hidden sections (i.e. has 'moodle/course:viewhiddensections' --- lib.php | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/lib.php b/lib.php index 79e6ea1..e7c9b8b 100644 --- a/lib.php +++ b/lib.php @@ -133,14 +133,11 @@ protected function __construct($format, $courseid) { $realsection = 1; } - // Can view the hidden sections in current course? - $canviewhidden = has_capability('moodle/course:viewhiddensections', $context); - $modinfo = get_fast_modinfo($course); $sections = $modinfo->get_section_info_all(); // Check if the display section is available. - if ((!$canviewhidden && (!$sections[$realsection]->uservisible || !$sections[$realsection]->available))) { + if (!$sections[$realsection]->uservisible) { self::$formatmsgs[] = get_string('hidden_message', 'format_onetopic', $this->get_section_name($realsection)); @@ -150,8 +147,7 @@ protected function __construct($format, $courseid) { do { $formatoptions = $this->get_format_options($k); if ($formatoptions['level'] == 0 - && ($sections[$k]->available && $sections[$k]->uservisible) - || $canviewhidden) { + && $sections[$k]->uservisible) { $valid = true; break; } From 055b9280f9145a9f237385c600c7434e1d41fb7d Mon Sep 17 00:00:00 2001 From: Tim Schroeder Date: Fri, 4 Aug 2023 19:19:17 +0200 Subject: [PATCH 17/50] disable unavailable sections also to users that have the capability 'moodle/course:viewhiddensections' but don't have 'moodle/course:ignoreavailabilityrestrictions' --- classes/output/courseformat/content.php | 14 +++----------- 1 file changed, 3 insertions(+), 11 deletions(-) diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index 3f73f89..baf3769 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -344,10 +344,6 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $displaysection = $this->format->get_section_number(); $enablecustomstyles = get_config('format_onetopic', 'enablecustomstyles'); - // Can we view the section in question? - $context = \context_course::instance($course->id); - $canviewhidden = has_capability('moodle/course:viewhiddensections', $context); - // Init custom tabs. $section = 0; @@ -366,12 +362,8 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $thissection = $sections[$section]; - $showsection = true; - if (!$thissection->visible || !$thissection->available) { - $showsection = $canviewhidden || !($course->hiddensections == 1); - } - - if ($showsection) { + // Can we view the section in question? + if ($thissection->uservisible || $course->hiddensections != 1) { $formatoptions = course_get_format($course)->get_format_options($thissection); @@ -419,7 +411,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for if (!$thissection->visible || !$thissection->available) { $specialclass .= ' dimmed disabled '; - if (!$canviewhidden) { + if (!$thissection->uservisible) { $inactivetab = true; } } From 72eacc50412779bfe49088d357b129131842a5dc Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 8 Aug 2023 02:21:12 -0500 Subject: [PATCH 18/50] Stabilization --- classes/header.php | 8 ++++++-- format.php | 14 -------------- templates/footer.mustache | 5 +++-- templates/local/content.mustache | 2 +- 4 files changed, 10 insertions(+), 19 deletions(-) diff --git a/classes/header.php b/classes/header.php index 311d915..f6c13c8 100644 --- a/classes/header.php +++ b/classes/header.php @@ -74,7 +74,6 @@ public function export_for_template(\renderer_base $output) { $coursecontext = \context_course::instance($course->id); $canviewhidden = has_capability('moodle/course:viewhiddensections', $coursecontext); - $tabslist = []; $secondtabslist = null; if ($course->tabsview != \format_onetopic::TABSVIEW_COURSEINDEX && @@ -103,7 +102,7 @@ public function export_for_template(\renderer_base $output) { $hassecondrow = false; $hastopictabs = true; } else { - $hastopictabs = $format->hastopicstabs; + $hastopictabs = $format->hastopictabs; $hassecondrow = is_object($secondtabslist) && count($secondtabslist->tabs) > 0; } @@ -153,6 +152,11 @@ public function export_for_template(\renderer_base $output) { 'right' => $OUTPUT->pix_icon('t/collapsed', ''), ] ]; + + // Include course format js module. + $PAGE->requires->js('/course/format/topics/format.js'); + $PAGE->requires->js('/course/format/onetopic/format.js'); + $PAGE->requires->yui_module('moodle-core-notification-dialogue', 'M.course.format.dialogueinit'); $PAGE->requires->js_call_amd('format_onetopic/main', 'init', $params); return $data; diff --git a/format.php b/format.php index 9477263..4f701dc 100644 --- a/format.php +++ b/format.php @@ -78,17 +78,3 @@ $outputclass = $format->get_output_classname('content'); $widget = new $outputclass($format); echo $renderer->render($widget); - -// Include course format js module. -$PAGE->requires->js('/course/format/topics/format.js'); -$PAGE->requires->js('/course/format/onetopic/format.js'); -$PAGE->requires->yui_module('moodle-core-notification-dialogue', 'M.course.format.dialogueinit'); - -$params = array( - 'formattype' => $course->tabsview, - 'icons' => [ - 'left' => $OUTPUT->pix_icon('t/collapsed_rtl', ''), - 'right' => $OUTPUT->pix_icon('t/collapsed', ''), - ] -); -$PAGE->requires->js_call_amd('format_onetopic/main', 'init', $params); diff --git a/templates/footer.mustache b/templates/footer.mustache index c4d22df..036c856 100644 --- a/templates/footer.mustache +++ b/templates/footer.mustache @@ -33,9 +33,10 @@ {{#hastopictabs}}
{{/hastopictabs}} +
{{/testing}} -
{{! Used in order to break the div wraped in output.course_content_header }} +
{{! Used in order to break the div wraped in output.course_content_footer }} {{#hastopictabs}} {{! End of onetopic-tab-body box. }} @@ -46,7 +47,7 @@
{{#csstabstyles}} - {{/csstabstyles}} diff --git a/templates/local/content.mustache b/templates/local/content.mustache index dec7f1e..b2d4038 100644 --- a/templates/local/content.mustache +++ b/templates/local/content.mustache @@ -61,7 +61,7 @@ "summary": { "summarytext": "Summary text!" } - }, + } } }} From 96c89bc6d0cefb308925463dcc5d34b2a9c270bf Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 8 Aug 2023 03:10:22 -0500 Subject: [PATCH 19/50] Separate dynamic tab styles into a CSS-PHP file --- classes/footer.php | 105 +----------------------------- lib.php | 8 +++ styles.php | 132 ++++++++++++++++++++++++++++++++++++++ templates/footer.mustache | 7 -- version.php | 2 +- 5 files changed, 142 insertions(+), 112 deletions(-) create mode 100644 styles.php diff --git a/classes/footer.php b/classes/footer.php index 3957595..6ad87fd 100644 --- a/classes/footer.php +++ b/classes/footer.php @@ -65,113 +65,10 @@ public function export_for_template(\renderer_base $output) { $format = $this->format; $currentsection = $this->format->get_section_number(); - $withunits = ['font-size', 'line-height', 'margin', 'padding', 'border-width', 'border-radius']; - $csscontent = ''; - $csstabstyles = ''; - $tabstyles = get_config('format_onetopic', 'tabstyles'); - if (!empty($tabstyles)) { - $tabstyles = @json_decode($tabstyles); - - if (is_object($tabstyles)) { - - $precedence = ['default', 'childs', 'childindex', 'active', 'parent', 'highlighted', 'disabled', 'hover']; - - $orderedtabs = new \stdClass(); - foreach ($precedence as $type) { - if (property_exists($tabstyles, $type)) { - $orderedtabs->$type = $tabstyles->$type; - } - } - - foreach ($orderedtabs as $type => $styles) { - - switch ($type) { - case 'active': - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, '; - $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link.active, '; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs a.nav-link.active, '; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link.active'; - break; - case 'parent': - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, '; - $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.haschilds a.nav-link'; - break; - case 'highlighted': - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, '; - $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.marker a.nav-link, '; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.marker a.nav-link'; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.marker a.nav-link'; - break; - case 'disabled': - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, '; - $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.disabled a.nav-link, '; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.disabled a.nav-link'; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.disabled a.nav-link'; - break; - case 'hover': - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, '; - $csscontent .= '#tabs-tree-start .format_onetopic-tabs.nav-tabs .nav-item a.nav-link:hover, '; - $csscontent .= '#tabs-tree-start .onetopic-tab-body .format_onetopic-tabs.nav-tabs' . - ' .nav-item a.nav-link:hover'; - break; - case 'childs': - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link'; - break; - case 'childindex': - $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs' . - ' .nav-item.subtopic.tab_initial a.nav-link'; - break; - default: - $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, '; - $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link'; - } - - $csscontent .= '{'; - $units = []; - - // Check if exist units for some rules. - foreach ($styles as $key => $value) { - - // Check if the key start with the units prefix. - if (strpos($key, 'unit-') === 0) { - - // Remove the prefix. - $ownerkey = str_replace('unit-', '', $key); - $units[$ownerkey] = $value; - unset($styles->$key); - } - } - - foreach ($styles as $key => $value) { - - // If exist a unit for the rule, apply it. - if (isset($units[$key])) { - $value = $value . $units[$key]; - } else if (in_array($key, $withunits)) { - // If the rule need units, apply px by default. - $value = $value . 'px'; - } - - if ($key == 'others') { - $csscontent .= $value . ';'; - } else { - $csscontent .= $key . ':' . $value . ';'; - } - } - - $csscontent .= '}'; - } - - // Clean the CSS for html tags. - $csstabstyles = preg_replace('/<[^>]*>/', '', $csscontent); - } - } - $data = (object)[ 'uniqid' => $format->uniqid, 'sectionreturn' => $currentsection ?? 0, - 'hastopictabs' => $format->hastopictabs, - 'csstabstyles' => $csstabstyles, + 'hastopictabs' => $format->hastopictabs ]; return $data; diff --git a/lib.php b/lib.php index 318542a..b3a5e32 100644 --- a/lib.php +++ b/lib.php @@ -1054,6 +1054,14 @@ public function show_editor(?array $capabilities = ['moodle/course:manageactivit } +/** + * Moodle native lib/navigationlib.php calls this hook allowing us to override UI. + */ +function format_onetopic_before_http_headers() { + global $PAGE; + $PAGE->requires->css('/course/format/onetopic/styles.php'); +} + /** * Implements callback inplace_editable() allowing to edit values in-place. * diff --git a/styles.php b/styles.php new file mode 100644 index 0000000..108f4cf --- /dev/null +++ b/styles.php @@ -0,0 +1,132 @@ +. + +/** + * Display the general CSS style to tabs. + * + * @package format_onetopic + * @copyright 2023 David Herney Bernal - cirano + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +require_once('../../../config.php'); + +@header('Content-Disposition: inline; filename="styles.php"'); +@header('Content-Type: text/css; charset=utf-8'); + +$withunits = ['font-size', 'line-height', 'margin', 'padding', 'border-width', 'border-radius']; +$csscontent = ''; +$csstabstyles = ''; +$tabstyles = get_config('format_onetopic', 'tabstyles'); +if (!empty($tabstyles)) { + $tabstyles = @json_decode($tabstyles); + + if (is_object($tabstyles)) { + + $precedence = ['default', 'childs', 'childindex', 'active', 'parent', 'highlighted', 'disabled', 'hover']; + + $orderedtabs = new \stdClass(); + foreach ($precedence as $type) { + if (property_exists($tabstyles, $type)) { + $orderedtabs->$type = $tabstyles->$type; + } + } + + foreach ($orderedtabs as $type => $styles) { + + switch ($type) { + case 'active': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, '; + $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link.active, '; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs a.nav-link.active, '; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link.active'; + break; + case 'parent': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.haschilds a.nav-link'; + break; + case 'highlighted': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.marker a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.marker a.nav-link, '; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.marker a.nav-link'; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.marker a.nav-link'; + break; + case 'disabled': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.disabled a.nav-link, '; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.disabled a.nav-link'; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.disabled a.nav-link'; + break; + case 'hover': + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, '; + $csscontent .= '#tabs-tree-start .format_onetopic-tabs.nav-tabs .nav-item a.nav-link:hover, '; + $csscontent .= '#tabs-tree-start .onetopic-tab-body .format_onetopic-tabs.nav-tabs' . + ' .nav-item a.nav-link:hover'; + break; + case 'childs': + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link'; + break; + case 'childindex': + $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs' . + ' .nav-item.subtopic.tab_initial a.nav-link'; + break; + default: + $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link, '; + $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link'; + } + + $csscontent .= '{'; + $units = []; + + // Check if exist units for some rules. + foreach ($styles as $key => $value) { + + // Check if the key start with the units prefix. + if (strpos($key, 'unit-') === 0) { + + // Remove the prefix. + $ownerkey = str_replace('unit-', '', $key); + $units[$ownerkey] = $value; + unset($styles->$key); + } + } + + foreach ($styles as $key => $value) { + + // If exist a unit for the rule, apply it. + if (isset($units[$key])) { + $value = $value . $units[$key]; + } else if (in_array($key, $withunits)) { + // If the rule need units, apply px by default. + $value = $value . 'px'; + } + + if ($key == 'others') { + $csscontent .= $value . ';'; + } else { + $csscontent .= $key . ':' . $value . ';'; + } + } + + $csscontent .= '} '; + } + + // Clean the CSS for html tags. + $csstabstyles = preg_replace('/<[^>]*>/', '', $csscontent); + } +} + +echo $csstabstyles; diff --git a/templates/footer.mustache b/templates/footer.mustache index 036c856..71abe13 100644 --- a/templates/footer.mustache +++ b/templates/footer.mustache @@ -21,7 +21,6 @@ { "uniqid": "course-1", "sectionreturn": 1, - "csstabstyles": "/* CSS styles for the tabs */", "hastopictabs": true, "testing": true } @@ -46,12 +45,6 @@
-{{#csstabstyles}} - -{{/csstabstyles}} - {{#js}} require(['core_courseformat/local/content'], function(component) { component.init('{{uniqid}}-course-format', {}, {{sectionreturn}}); diff --git a/version.php b/version.php index 109e5a7..1e49588 100644 --- a/version.php +++ b/version.php @@ -24,7 +24,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081609.04; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2022081609.05; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From c9fc85ab7a26a057376d0bdfd4cb98e19992509a Mon Sep 17 00:00:00 2001 From: David Herney Date: Tue, 8 Aug 2023 03:26:20 -0500 Subject: [PATCH 20/50] Separate dynamic tab styles into a CSS-PHP file --- styles.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/styles.php b/styles.php index 108f4cf..bd763cd 100644 --- a/styles.php +++ b/styles.php @@ -22,6 +22,8 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ +// Require_login is not needed here. +// phpcs:disable moodle.Files.RequireLogin.Missing require_once('../../../config.php'); @header('Content-Disposition: inline; filename="styles.php"'); From a0d12eabd5ec2a91d5e5197147d490fb93bad83c Mon Sep 17 00:00:00 2001 From: james-cnz <5689414+james-cnz@users.noreply.github.com> Date: Mon, 30 Oct 2023 12:50:07 +1300 Subject: [PATCH 21/50] Code checker updates: Short array syntax and more --- changenumsections.php | 10 +-- classes/output/courseformat/content.php | 10 +-- .../output/courseformat/content/section.php | 4 +- .../courseformat/content/section/cmlist.php | 4 +- .../content/section/controlmenu.php | 8 +-- .../courseformat/content/section/summary.php | 4 +- classes/tabs.php | 2 +- duplicate.php | 18 ++--- format.php | 10 ++- lib.php | 66 +++++++++---------- 10 files changed, 67 insertions(+), 69 deletions(-) diff --git a/changenumsections.php b/changenumsections.php index e918075..6021845 100644 --- a/changenumsections.php +++ b/changenumsections.php @@ -35,10 +35,10 @@ $sectionreturn = optional_param('sectionreturn', null, PARAM_INT); // Section to return to, ignored if $returnurl is specified. $aschild = optional_param('aschild', 0, PARAM_BOOL); // It is created as child. -$course = $DB->get_record('course', array('id' => $courseid), '*', MUST_EXIST); +$course = $DB->get_record('course', ['id' => $courseid], '*', MUST_EXIST); $courseformatoptions = course_get_format($course)->get_format_options(); -$PAGE->set_url('/course/format/onetopic/changenumsections.php', array('courseid' => $courseid)); +$PAGE->set_url('/course/format/onetopic/changenumsections.php', ['courseid' => $courseid]); // Authorisation checks. require_login($course); require_capability('moodle/course:update', context_course::instance($course->id)); @@ -81,8 +81,8 @@ // Don't go less than 0, intentionally redirect silently (for the case of // double clicks). if ($courseformatoptions['numsections'] >= 0) { - update_course((object)array('id' => $course->id, - 'numsections' => $courseformatoptions['numsections'])); + update_course((object)['id' => $course->id, + 'numsections' => $courseformatoptions['numsections'], ]); } if (!$returnurl) { $returnurl = course_get_url($course); @@ -100,7 +100,7 @@ if ($aschild) { // Set level to one because it is a child tab. - $courseformat->update_section_format_options(array('level' => 1, 'id' => $section->id)); + $courseformat->update_section_format_options(['level' => 1, 'id' => $section->id]); } } if (!$returnurl) { diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index 3f73f89..2546d4e 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -406,7 +406,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } if ($section == 0) { - $url = new \moodle_url('/course/view.php', array('id' => $course->id, 'section' => 0)); + $url = new \moodle_url('/course/view.php', ['id' => $course->id, 'section' => 0]); } else { $url = course_get_url($course, $section); } @@ -515,10 +515,10 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $icon = $output->pix_icon('t/switch_plus', s($straddsection)); $insertposition = $displaysection + 1; - $paramstotabs = array('courseid' => $course->id, - 'increase' => true, - 'sesskey' => sesskey(), - 'insertsection' => $insertposition); + $paramstotabs = ['courseid' => $course->id, + 'increase' => true, + 'sesskey' => sesskey(), + 'insertsection' => $insertposition, ]; // Define if subtabs are displayed (a subtab is selected or the selected tab has subtabs). $selectedsubtabs = $selectedparent ? $tabs->get_tab($selectedparent->index) : null; diff --git a/classes/output/courseformat/content/section.php b/classes/output/courseformat/content/section.php index 12ff6c7..7fb0b74 100644 --- a/classes/output/courseformat/content/section.php +++ b/classes/output/courseformat/content/section.php @@ -44,7 +44,7 @@ class section extends section_base { * Export this data so it can be used as the context for a mustache template. * * @param renderer_base $output typically, the renderer that's calling this function - * @return array data context for a mustache template + * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output): stdClass { global $USER, $PAGE; @@ -63,7 +63,7 @@ public function export_for_template(\renderer_base $output): stdClass { 'summary' => $summary->export_for_template($output), 'highlightedlabel' => $format->get_section_highlighted_name(), 'sitehome' => $course->id == SITEID, - 'editing' => $PAGE->user_is_editing() + 'editing' => $PAGE->user_is_editing(), ]; $haspartials = []; diff --git a/classes/output/courseformat/content/section/cmlist.php b/classes/output/courseformat/content/section/cmlist.php index b6d6b0e..24e3104 100644 --- a/classes/output/courseformat/content/section/cmlist.php +++ b/classes/output/courseformat/content/section/cmlist.php @@ -46,7 +46,7 @@ class cmlist extends cmlist_base { * Export this data so it can be used as the context for a mustache template. * * @param renderer_base $output typically, the renderer that's calling this function - * @return array data context for a mustache template + * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output): stdClass { global $USER; @@ -99,7 +99,7 @@ public function export_for_template(\renderer_base $output): stdClass { $item = new $this->itemclass($format, $section, $mod, $this->displayoptions); $data->cms[] = (object)[ 'cmitem' => $item->export_for_template($output), - 'moveurl' => new moodle_url('/course/mod.php', array('moveto' => $modnumber, 'sesskey' => sesskey())), + 'moveurl' => new moodle_url('/course/mod.php', ['moveto' => $modnumber, 'sesskey' => sesskey()]), ]; } } diff --git a/classes/output/courseformat/content/section/controlmenu.php b/classes/output/courseformat/content/section/controlmenu.php index 86775b7..377f587 100644 --- a/classes/output/courseformat/content/section/controlmenu.php +++ b/classes/output/courseformat/content/section/controlmenu.php @@ -80,7 +80,7 @@ public function section_control_items() { 'pixattr' => ['class' => ''], 'attr' => [ 'class' => 'editing_highlight', - 'data-action' => 'removemarker' + 'data-action' => 'removemarker', ], ]; } else { @@ -93,7 +93,7 @@ public function section_control_items() { 'pixattr' => ['class' => ''], 'attr' => [ 'class' => 'editing_highlight', - 'data-action' => 'setmarker' + 'data-action' => 'setmarker', ], ]; } @@ -147,7 +147,7 @@ public function section_control_items() { 'name' => get_string('duplicate', 'format_onetopic'), 'pixattr' => ['class' => ''], 'attr' => [ - 'class' => 'editing_duplicate' + 'class' => 'editing_duplicate', ], ]; } @@ -160,7 +160,7 @@ public function section_control_items() { 'id' => $section->id, 'sr' => $section->section - 1, 'delete' => 1, - 'sesskey' => sesskey()]); + 'sesskey' => sesskey(), ]); $parentcontrols['delete']['url'] = $url; unset($parentcontrols['delete']['attr']['data-action']); } diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index fecaceb..0ad8c67 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -78,7 +78,7 @@ public function __construct(course_format $format, section_info $section) { * Export this data so it can be used as the context for a mustache template. * * @param renderer_base $output typically, the renderer that's calling this function - * @return array data context for a mustache template + * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output): stdClass { @@ -227,7 +227,7 @@ private function replace_resources(section_info $section) { $this->tplstringsearch = $instancename; $newsummary = preg_replace_callback("/(\[\[)(([<][^>]*>)*)((" . preg_quote($this->tplstringsearch, '/') . - ")(:?))([^\]]*)\]\]/i", array($this, "replace_tag_in_expresion"), $summary); + ")(:?))([^\]]*)\]\]/i", [$this, "replace_tag_in_expresion"], $summary); if ($newsummary != $summary) { $this->format->tplcmsused[] = $modnumber; diff --git a/classes/tabs.php b/classes/tabs.php index 3833960..c629741 100644 --- a/classes/tabs.php +++ b/classes/tabs.php @@ -41,7 +41,7 @@ class tabs { * */ public function __construct() { - $this->tabslist = array(); + $this->tabslist = []; } /** diff --git a/duplicate.php b/duplicate.php index e938464..710a430 100644 --- a/duplicate.php +++ b/duplicate.php @@ -30,7 +30,7 @@ $courseid = required_param('courseid', PARAM_INT); $section = required_param('section', PARAM_INT); -$course = $DB->get_record('course', array('id' => $courseid), '*', MUST_EXIST); +$course = $DB->get_record('course', ['id' => $courseid], '*', MUST_EXIST); $urlstring = '/course/format/onetopic/duplicate.php'; $PAGE->set_url($urlstring, ['courseid' => $courseid, 'section' => $section]); @@ -73,7 +73,7 @@ $PAGE->set_pagelayout('course'); $PAGE->set_heading($course->fullname); -$PAGE->set_title(get_string('coursetitle', 'moodle', array('course' => $course->fullname))); +$PAGE->set_title(get_string('coursetitle', 'moodle', ['course' => $course->fullname])); echo $OUTPUT->header(); @@ -84,7 +84,7 @@ $courseformat = course_get_format($course); - $lastsectionnum = $DB->get_field('course_sections', 'MAX(section)', array('course' => $courseid), MUST_EXIST); + $lastsectionnum = $DB->get_field('course_sections', 'MAX(section)', ['course' => $courseid], MUST_EXIST); $numnewsection = $lastsectionnum + 1; @@ -109,11 +109,11 @@ if ($files && is_array($files)) { foreach ($files as $f) { - $fileinfo = array( + $fileinfo = [ 'contextid' => $context->id, 'component' => 'course', 'filearea' => 'section', - 'itemid' => $newsectionid); + 'itemid' => $newsectionid, ]; $fs->create_file_from_storedfile($fileinfo, $f); } @@ -135,12 +135,12 @@ // Trigger an event for course section update. $event = \core\event\course_section_updated::create( - array( + [ 'objectid' => $newsectionid, 'courseid' => $course->id, 'context' => $context, - 'other' => array('sectionnum' => $numnewsection) - ) + 'other' => ['sectionnum' => $numnewsection], + ] ); $event->trigger(); @@ -150,7 +150,7 @@ $pbar->update_full(10, get_string('rebuild_course_cache', 'format_onetopic')); $newsectioninfo = $modinfo->get_section_info($numnewsection); - $modules = array(); + $modules = []; if (is_object($modinfo) && isset($modinfo->sections[$section])) { $sectionmods = $modinfo->sections[$section]; diff --git a/format.php b/format.php index fe3b425..821dadd 100644 --- a/format.php +++ b/format.php @@ -56,12 +56,10 @@ $section = $displaysection; -$renderer->numsections = course_get_format($course)->get_last_section_number(); - $disableajax = optional_param('onetopic_da', -1, PARAM_INT); if (!isset($USER->onetopic_da)) { - $USER->onetopic_da = array(); + $USER->onetopic_da = []; } if ($disableajax !== -1) { @@ -85,11 +83,11 @@ $PAGE->requires->js('/course/format/onetopic/format.js'); $PAGE->requires->yui_module('moodle-core-notification-dialogue', 'M.course.format.dialogueinit'); -$params = array( +$params = [ 'formattype' => $course->tabsview, 'icons' => [ 'left' => $OUTPUT->pix_icon('t/collapsed_rtl', ''), 'right' => $OUTPUT->pix_icon('t/collapsed', ''), - ] -); + ], +]; $PAGE->requires->js_call_amd('format_onetopic/main', 'init', $params); diff --git a/lib.php b/lib.php index 79e6ea1..78b7b43 100644 --- a/lib.php +++ b/lib.php @@ -434,36 +434,36 @@ public function course_format_options($foreditform = false) { $courseformatoptions = [ 'hiddensections' => [ 'default' => $courseconfig->hiddensections, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'hidetabsbar' => [ 'default' => 0, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'coursedisplay' => [ 'default' => $courseconfig->coursedisplay, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'templatetopic' => [ 'default' => self::TEMPLATETOPIC_NOT, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'templatetopic_icons' => [ 'default' => 0, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'tabsview' => [ 'default' => 0, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'usessectionsnavigation' => [ 'default' => 0, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'usescourseindex' => [ 'default' => 2, - 'type' => PARAM_INT - ] + 'type' => PARAM_INT, + ], ]; } @@ -478,8 +478,8 @@ public function course_format_options($foreditform = false) { [ 0 => new lang_string('hiddensectionscollapsed'), 1 => new lang_string('hiddensectionsinvisible'), - 2 => new lang_string('hiddensectionshelp', 'format_onetopic') - ] + 2 => new lang_string('hiddensectionshelp', 'format_onetopic'), + ], ], ], 'hidetabsbar' => [ @@ -490,8 +490,8 @@ public function course_format_options($foreditform = false) { 'element_attributes' => [ [ 0 => new lang_string('no'), - 1 => new lang_string('yes') - ] + 1 => new lang_string('yes'), + ], ], ], 'coursedisplay' => [ @@ -500,8 +500,8 @@ public function course_format_options($foreditform = false) { 'element_attributes' => [ [ COURSE_DISPLAY_SINGLEPAGE => new lang_string('coursedisplay_single', 'format_onetopic'), - COURSE_DISPLAY_MULTIPAGE => new lang_string('coursedisplay_multi', 'format_onetopic') - ] + COURSE_DISPLAY_MULTIPAGE => new lang_string('coursedisplay_multi', 'format_onetopic'), + ], ], 'help' => 'coursedisplay', 'help_component' => 'format_onetopic', @@ -513,8 +513,8 @@ public function course_format_options($foreditform = false) { [ self::TEMPLATETOPIC_NOT => new lang_string('templetetopic_not', 'format_onetopic'), self::TEMPLATETOPIC_SINGLE => new lang_string('templetetopic_single', 'format_onetopic'), - self::TEMPLATETOPIC_LIST => new lang_string('templetetopic_list', 'format_onetopic') - ] + self::TEMPLATETOPIC_LIST => new lang_string('templetetopic_list', 'format_onetopic'), + ], ], 'help' => 'templatetopic', 'help_component' => 'format_onetopic', @@ -527,8 +527,8 @@ public function course_format_options($foreditform = false) { 'element_attributes' => [ [ 0 => new lang_string('no'), - 1 => new lang_string('yes') - ] + 1 => new lang_string('yes'), + ], ], ], 'tabsview' => [ @@ -538,8 +538,8 @@ public function course_format_options($foreditform = false) { [ self::TABSVIEW_DEFAULT => new lang_string('tabsview_default', 'format_onetopic'), self::TABSVIEW_VERTICAL => new lang_string('tabsview_vertical', 'format_onetopic'), - self::TABSVIEW_ONELINE => new lang_string('tabsview_oneline', 'format_onetopic') - ] + self::TABSVIEW_ONELINE => new lang_string('tabsview_oneline', 'format_onetopic'), + ], ], 'help' => 'tabsview', 'help_component' => 'format_onetopic', @@ -555,7 +555,7 @@ public function course_format_options($foreditform = false) { self::SECTIONSNAVIGATION_BOTTOM => new lang_string('sectionsnavigation_bottom', 'format_onetopic'), self::SECTIONSNAVIGATION_BOTH => new lang_string('sectionsnavigation_both', 'format_onetopic'), self::SECTIONSNAVIGATION_SLIDES => new lang_string('sectionsnavigation_slides', 'format_onetopic'), - ] + ], ], 'help' => 'usessectionsnavigation', 'help_component' => 'format_onetopic', @@ -570,9 +570,9 @@ public function course_format_options($foreditform = false) { 2 => new lang_string('usecourseindexsite', 'format_onetopic'), 0 => new lang_string('no'), 1 => new lang_string('yes'), - ] + ], ], - ] + ], ]; $courseformatoptions = array_merge_recursive($courseformatoptions, $courseformatoptionsedit); } @@ -687,28 +687,28 @@ public function section_format_options($foreditform = false) { $sectionformatoptions = [ 'level' => [ 'default' => 0, - 'type' => PARAM_INT + 'type' => PARAM_INT, ], 'firsttabtext' => [ 'default' => get_string('index', 'format_onetopic'), - 'type' => PARAM_TEXT - ] + 'type' => PARAM_TEXT, + ], ]; if ($enablecustomstyles) { $sectionformatoptions['fontcolor'] = [ 'default' => '', - 'type' => PARAM_RAW + 'type' => PARAM_RAW, ]; $sectionformatoptions['bgcolor'] = [ 'default' => '', - 'type' => PARAM_RAW + 'type' => PARAM_RAW, ]; $sectionformatoptions['cssstyles'] = [ 'default' => '', - 'type' => PARAM_RAW + 'type' => PARAM_RAW, ]; } } @@ -723,8 +723,8 @@ public function section_format_options($foreditform = false) { 'element_attributes' => [ [ 0 => get_string('asprincipal', 'format_onetopic'), - 1 => get_string('aschild', 'format_onetopic') - ] + 1 => get_string('aschild', 'format_onetopic'), + ], ], 'help' => 'level', 'help_component' => 'format_onetopic', @@ -735,7 +735,7 @@ public function section_format_options($foreditform = false) { 'label' => get_string('firsttabtext', 'format_onetopic'), 'help' => 'firsttabtext', 'help_component' => 'format_onetopic', - ] + ], ]; if ($enablecustomstyles) { From 5af3c0381deb5ebb8b57010cfd80ba973f3e576c Mon Sep 17 00:00:00 2001 From: David Herney Date: Sun, 19 Nov 2023 22:37:35 -0500 Subject: [PATCH 22/50] Changed selectors to courseindex feature --- lang/en/format_onetopic.php | 2 +- lib.php | 2 +- styles.css | 4 ++++ templates/footer.mustache | 8 +++++++- 4 files changed, 13 insertions(+), 3 deletions(-) diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 86e8d03..a8a94bb 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -94,7 +94,7 @@ $string['tabsview_default'] = 'By default'; $string['tabsview_vertical'] = 'Vertically'; $string['tabsview_oneline'] = 'Only one line'; -$string['tabsview_courseindex'] = 'Embed course index'; +$string['tabsview_courseindex'] = 'Embedded course index'; $string['increasesections'] = 'Add a section after the currently selected section'; diff --git a/lib.php b/lib.php index b3a5e32..b811bdd 100644 --- a/lib.php +++ b/lib.php @@ -56,7 +56,7 @@ class format_onetopic extends core_courseformat\base { /** @var int One line view */ const TABSVIEW_ONELINE = 2; - /** @var int Embed course index */ + /** @var int Embedded course index */ const TABSVIEW_COURSEINDEX = 3; /** @var int Only if theme not support "usescourseindex" */ diff --git a/styles.css b/styles.css index 4eded36..1396375 100644 --- a/styles.css +++ b/styles.css @@ -6,6 +6,8 @@ max-width: 300px; overflow: hidden; text-overflow: ellipsis; + position: relative; + padding-right: 1.3rem; } .format-onetopic ul.nav-tabs.format_onetopic-tabs li.marker a { @@ -21,6 +23,8 @@ cursor: pointer; margin-left: 5px; pointer-events: auto; + position: absolute; + right: 3px; } .format-onetopic ul.nav-tabs li a span.iconhelp i { diff --git a/templates/footer.mustache b/templates/footer.mustache index 71abe13..8f572ec 100644 --- a/templates/footer.mustache +++ b/templates/footer.mustache @@ -47,6 +47,12 @@ {{#js}} require(['core_courseformat/local/content'], function(component) { - component.init('{{uniqid}}-course-format', {}, {{sectionreturn}}); + component.init('{{uniqid}}-course-format', + { + SECTION: `.onetopic-tab-body [data-for='section']`, + SECTION_CMLIST: `.onetopic-tab-body [data-for='cmlist']`, + CM: `.onetopic-tab-body [data-for='cmitem']`, + }, + {{sectionreturn}}); }); {{/js}} From d4340780e236d8d2e95d6f0231f9da2855fadd04 Mon Sep 17 00:00:00 2001 From: David Herney Date: Sun, 19 Nov 2023 23:08:35 -0500 Subject: [PATCH 23/50] New release to Moodle 4.1 --- .github/workflows/moodle-ci.yml | 4 ++-- README.md | 6 ++++++ version.php | 2 +- 3 files changed, 9 insertions(+), 3 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 3e9921f..6a77047 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -10,7 +10,7 @@ jobs: services: postgres: - image: postgres:13 # Moodle 4.2: >= 13 + image: postgres:12 # Moodle 4.0: >= 10 env: POSTGRES_USER: 'postgres' POSTGRES_HOST_AUTH_METHOD: 'trust' @@ -18,7 +18,7 @@ jobs: - 5432:5432 options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 3 mariadb: - image: mariadb:10.6 # Moodle 4.2 >=10.6.7 + image: mariadb:10.4 # Moodle 4.1 >=10.4 env: MYSQL_USER: 'root' MYSQL_ALLOW_EMPTY_PASSWORD: "true" diff --git a/README.md b/README.md index d644a7e..0324536 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,12 @@ Download zip package, extract the onetopic folder and upload this folder into co ## IN VERSION +### 2022081610: +* New tabs view option: course index + * ![Tabs view Course index](https://boa.nuestroscursos.net/api/c/web/resources/NDU1MEVCNjAtODQ4Qy00RTk3LUI2NzUtOUJBN0E5ODk0QTkyQGJvYS51ZGVhLmVkdS5jbw==/!/onetopic/tabsview_courseindex.png) +* New scope to show tabs: modules. Included admin setting to enable it. Funded by [Ecole hôtelière de Lausanne](https://www.ehl.edu/) + * ![Scope modules](https://boa.nuestroscursos.net/api/c/web/resources/NDU1MEVCNjAtODQ4Qy00RTk3LUI2NzUtOUJBN0E5ODk0QTkyQGJvYS51ZGVhLmVkdS5jbw==/!/onetopic/tabs_scopemodules.png) + ### 2022081609: * New tabs style editor in site settings. Funded by [Ecole hôtelière de Lausanne](https://www.ehl.edu/) * ![Editor preview](https://boa.nuestroscursos.net/api/c/web/resources/NDU1MEVCNjAtODQ4Qy00RTk3LUI2NzUtOUJBN0E5ODk0QTkyQGJvYS51ZGVhLmVkdS5jbw==/!/onetopic/tabs_styles_editor.png) diff --git a/version.php b/version.php index 1e49588..745af12 100644 --- a/version.php +++ b/version.php @@ -24,7 +24,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081609.05; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2022081610; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From ef91f15cc6ccf2a82f89ff2ec2d8d9f13a2658c4 Mon Sep 17 00:00:00 2001 From: David Herney Date: Sun, 19 Nov 2023 23:10:27 -0500 Subject: [PATCH 24/50] New release to Moodle 4.1 --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index 745af12..4b103b3 100644 --- a/version.php +++ b/version.php @@ -28,5 +28,5 @@ $plugin->requires = 2022041902; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.1.05(PiedrasTeherán)'; +$plugin->release = '4.1.10(PiedrasTeherán)'; $plugin->dependencies = ['format_topics' => 2022041900]; From b049705d6717ecc1ea37aa8cb1fa3e4c5495d73b Mon Sep 17 00:00:00 2001 From: David Herney Date: Sun, 19 Nov 2023 23:47:53 -0500 Subject: [PATCH 25/50] Moodle CI compatibility to 4.2 --- .github/workflows/moodle-ci.yml | 37 +++++++++++++++++---------------- version.php | 17 +++++++++++---- 2 files changed, 32 insertions(+), 22 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 6a77047..e9452a6 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -10,7 +10,7 @@ jobs: services: postgres: - image: postgres:12 # Moodle 4.0: >= 10 + image: postgres:13 # Moodle 4.2: >=13 env: POSTGRES_USER: 'postgres' POSTGRES_HOST_AUTH_METHOD: 'trust' @@ -18,7 +18,7 @@ jobs: - 5432:5432 options: --health-cmd pg_isready --health-interval 10s --health-timeout 5s --health-retries 3 mariadb: - image: mariadb:10.4 # Moodle 4.1 >=10.4 + image: mariadb:10.6 # Moodle 4.2: >=10.6.7 env: MYSQL_USER: 'root' MYSQL_ALLOW_EMPTY_PASSWORD: "true" @@ -32,26 +32,25 @@ jobs: fail-fast: false matrix: include: - # Moodle 4.0, PHP 7.3, PostgreSQL - - php: '7.3' # 7.3-8.0 - moodle-branch: 'MOODLE_400_STABLE' + # Moodle 4.2, PHP 8.0, PostgreSQL + - php: '8.0' # 8.0-8.2 + moodle-branch: 'MOODLE_402_STABLE' database: pgsql - # Moodle 4.1, PHP 7.4, MariaDB - - php: '7.4' # 7.4-8.1 - moodle-branch: 'MOODLE_401_STABLE' + plugin-ci: ^4 + # Moodle 4.2, PHP 8.1, PostgreSQL + - php: '8.1' # 8.0-8.2 + moodle-branch: 'MOODLE_402_STABLE' database: mariadb - # Moodle 4.1, PHP 8.0, PostgreSQL - - php: '8.0' # 7.4-8.1 - moodle-branch: 'MOODLE_401_STABLE' - database: pgsql - # Moodle 4.1, PHP 8.1, PostgreSQL - - php: '8.1' # 7.4-8.1 - moodle-branch: 'MOODLE_401_STABLE' + plugin-ci: ^4 + # Moodle 4.2, PHP 8.1, PostgreSQL + - php: '8.2' # 8.0-8.2 + moodle-branch: 'MOODLE_402_STABLE' database: pgsql + plugin-ci: ^4 steps: - name: Check out repository code - uses: actions/checkout@v2 + uses: actions/checkout@v3 with: path: plugin @@ -61,11 +60,13 @@ jobs: php-version: ${{ matrix.php }} extensions: ${{ matrix.extensions }} ini-values: max_input_vars=5000 + # If you are not using code coverage, keep "none". Otherwise, use "pcov" (Moodle 3.10 and up) or "xdebug". + # If you try to use code coverage with "none", it will fallback to phpdbg (which has known problems). coverage: none - name: Initialise moodle-plugin-ci run: | - composer create-project -n --no-dev --prefer-dist moodlehq/moodle-plugin-ci ci ^3 + composer create-project -n --no-dev --prefer-dist moodlehq/moodle-plugin-ci ci ${{ matrix.plugin-ci }} echo $(cd ci/bin; pwd) >> $GITHUB_PATH echo $(cd ci/vendor/bin; pwd) >> $GITHUB_PATH sudo locale-gen en_AU.UTF-8 @@ -94,7 +95,7 @@ jobs: - name: Moodle Code Checker if: ${{ always() }} - run: moodle-plugin-ci codechecker --max-warnings 0 + run: moodle-plugin-ci phpcs --max-warnings 0 - name: Moodle PHPDoc Checker if: ${{ always() }} diff --git a/version.php b/version.php index 4b103b3..989594e 100644 --- a/version.php +++ b/version.php @@ -17,6 +17,15 @@ /** * Version details. * + * Component releases: + * Un recorderis de las Veredas de mi pueblo, en homenaje a los campesinos de mi tierra. + * + * Old releases: Guarango, Pantalio, Chalarca, Mazorcal, Chuscalito, Las Teresas, La Madera, Las Brisas, Buenavista, + * San Juan, La Almería, Piedras Teherán + * + * Next releases: El Cardal, Santa Cruz, Vallejuelito, Fátima, La Cabaña, La Palmera, Las Acacias, Las Colmenas, Minitas, + * Quebrada Negra, San Francisco, San Miguel Abajo, San Miguel, La Concha, La Divisa + * * @package format_onetopic * @copyright 2015 David Herney Bernal - cirano. https://bambuco.co * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later @@ -24,9 +33,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081610; // The current plugin version (Date: YYYYMMDDXX). -$plugin->requires = 2022041902; // Requires this Moodle version. +$plugin->version = 2022081610.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->requires = 2023042403; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.1.10(PiedrasTeherán)'; -$plugin->dependencies = ['format_topics' => 2022041900]; +$plugin->release = '4.2.01(ElCardal)'; +$plugin->dependencies = ['format_topics' => 2023042400]; From 6c6950b531df56fc8fafc43176f05ffc996c5d86 Mon Sep 17 00:00:00 2001 From: David Herney Date: Mon, 20 Nov 2023 00:35:46 -0500 Subject: [PATCH 26/50] Code checker compliance --- classes/footer.php | 2 +- classes/header.php | 10 ++++++---- classes/output/courseformat/content.php | 2 +- settings.php | 2 +- 4 files changed, 9 insertions(+), 7 deletions(-) diff --git a/classes/footer.php b/classes/footer.php index 6ad87fd..ebd918b 100644 --- a/classes/footer.php +++ b/classes/footer.php @@ -68,7 +68,7 @@ public function export_for_template(\renderer_base $output) { $data = (object)[ 'uniqid' => $format->uniqid, 'sectionreturn' => $currentsection ?? 0, - 'hastopictabs' => $format->hastopictabs + 'hastopictabs' => $format->hastopictabs, ]; return $data; diff --git a/classes/header.php b/classes/header.php index f6c13c8..913346d 100644 --- a/classes/header.php +++ b/classes/header.php @@ -150,7 +150,7 @@ public function export_for_template(\renderer_base $output) { 'icons' => [ 'left' => $OUTPUT->pix_icon('t/collapsed_rtl', ''), 'right' => $OUTPUT->pix_icon('t/collapsed', ''), - ] + ], ]; // Include course format js module. @@ -240,7 +240,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } if ($section == 0) { - $url = new \moodle_url('/course/view.php', array('id' => $course->id, 'section' => 0)); + $url = new \moodle_url('/course/view.php', ['id' => $course->id, 'section' => 0]); } else { $url = course_get_url($course, $section); } @@ -349,10 +349,12 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $icon = $output->pix_icon('t/switch_plus', s($straddsection)); $insertposition = $displaysection + 1; - $paramstotabs = array('courseid' => $course->id, + $paramstotabs = [ + 'courseid' => $course->id, 'increase' => true, 'sesskey' => sesskey(), - 'insertsection' => $insertposition); + 'insertsection' => $insertposition, + ]; // Define if subtabs are displayed (a subtab is selected or the selected tab has subtabs). $selectedsubtabs = $selectedparent ? $tabs->get_tab($selectedparent->index) : null; diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index 8ed744c..e2a05f1 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -77,7 +77,7 @@ public function export_for_template(\renderer_base $output) { 'title' => $format->page_title(), // This method should be in the course_format class. 'sections' => $sections, 'format' => $format->get_format(), - 'sectionclasses' => '' + 'sectionclasses' => '', ]; // The current section format has extra navigation. diff --git a/settings.php b/settings.php index cf3a218..6554bd8 100644 --- a/settings.php +++ b/settings.php @@ -54,7 +54,7 @@ $options)); $options = [ - \format_onetopic::SCOPE_MOD => new lang_string('scope_mod', 'format_onetopic') + \format_onetopic::SCOPE_MOD => new lang_string('scope_mod', 'format_onetopic'), ]; $settings->add(new admin_setting_configmulticheckbox('format_onetopic/defaultscope', get_string('defaultscope', 'format_onetopic'), From 222a82486399bd31356a4d8cbb360b37e7bf627e Mon Sep 17 00:00:00 2001 From: Stefan Hanauska Date: Tue, 20 Feb 2024 18:56:06 +0100 Subject: [PATCH 27/50] MBS-8819: Show action menu when loading course modules via ajax --- lib.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib.php b/lib.php index 7526eb7..d5f29b7 100644 --- a/lib.php +++ b/lib.php @@ -135,7 +135,7 @@ protected function __construct($format, $courseid) { $scope = []; } - $pagesavailable = ['course-view-onetopic', 'course-view']; + $pagesavailable = ['course-view-onetopic', 'course-view', 'lib-ajax-service']; if (!in_array($PAGE->pagetype, $pagesavailable)) { From 607573623c06437b8258fb83313587f67b558cad Mon Sep 17 00:00:00 2001 From: Alistair Spark Date: Thu, 14 Mar 2024 02:25:07 +0000 Subject: [PATCH 28/50] Add 4.3 and main to testing matrix Sync latest template changes --- .github/workflows/moodle-ci.yml | 45 ++++++++++++++++++++++----------- 1 file changed, 30 insertions(+), 15 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index e9452a6..5aa9bca 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -47,10 +47,19 @@ jobs: moodle-branch: 'MOODLE_402_STABLE' database: pgsql plugin-ci: ^4 - + # Moodle 4.3, PHP 8.1, MySQL + - php: '8.1' + moodle-branch: 'MOODLE_403_STABLE' + database: mariadb + plugin-ci: ^4 + # Moodle 4.3, PHP 8.1, MySQL + - php: '8.1' + moodle-branch: 'main' + database: mariadb + plugin-ci: ^4 steps: - name: Check out repository code - uses: actions/checkout@v3 + uses: actions/checkout@v4 with: path: plugin @@ -78,49 +87,55 @@ jobs: env: DB: ${{ matrix.database }} MOODLE_BRANCH: ${{ matrix.moodle-branch }} + # Uncomment this to run Behat tests using the Moodle App. + # MOODLE_APP: 'true' - name: PHP Lint - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci phplint - name: PHP Copy/Paste Detector continue-on-error: true # This step will show errors but will not fail - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci phpcpd - name: PHP Mess Detector continue-on-error: true # This step will show errors but will not fail - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci phpmd - name: Moodle Code Checker - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci phpcs --max-warnings 0 - name: Moodle PHPDoc Checker - if: ${{ always() }} - run: moodle-plugin-ci phpdoc + if: ${{ !cancelled() }} + run: moodle-plugin-ci phpdoc --max-warnings 0 - name: Validating - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci validate - name: Check upgrade savepoints - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci savepoints - name: Mustache Lint - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci mustache - name: Grunt - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci grunt --max-lint-warnings 0 - name: PHPUnit tests - if: ${{ always() }} + if: ${{ !cancelled() }} run: moodle-plugin-ci phpunit --fail-on-warning - name: Behat features - if: ${{ always() }} - run: moodle-plugin-ci behat --profile chrome \ No newline at end of file + if: ${{ !cancelled() }} + run: moodle-plugin-ci behat --profile chrome + + - name: Mark cancelled jobs as failed. + if: ${{ cancelled() }} + run: exit 1 From 0181d590015d4ca406bfeace579ef5e32727efeb Mon Sep 17 00:00:00 2001 From: Alistair Spark Date: Thu, 14 Mar 2024 02:28:31 +0000 Subject: [PATCH 29/50] Update description for main --- .github/workflows/moodle-ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 5aa9bca..8e4e856 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -52,7 +52,7 @@ jobs: moodle-branch: 'MOODLE_403_STABLE' database: mariadb plugin-ci: ^4 - # Moodle 4.3, PHP 8.1, MySQL + # Moodle main (not yet released 4.4), PHP 8.1, MySQL - php: '8.1' moodle-branch: 'main' database: mariadb From e80effb96b18773f3630a568579e18fcbe579947 Mon Sep 17 00:00:00 2001 From: Mark Johnson Date: Mon, 22 Apr 2024 14:16:53 +0100 Subject: [PATCH 30/50] Add NO_MOODLE_COOKIES to styles.php styles.php never uses the Moodle session, so doesn't need to initialise the session or get a session lock. --- styles.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/styles.php b/styles.php index bd763cd..27804a0 100644 --- a/styles.php +++ b/styles.php @@ -22,6 +22,8 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ +define('NO_MOODLE_COOKIES', true); + // Require_login is not needed here. // phpcs:disable moodle.Files.RequireLogin.Missing require_once('../../../config.php'); From 2fc8e148f76b7fef6cebb25a92129ba866dff77c Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?I=C3=B1igo=20Zendegi?= Date: Fri, 3 May 2024 11:59:39 +0200 Subject: [PATCH 31/50] Fix filter issue --- classes/header.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/classes/header.php b/classes/header.php index 913346d..fbfe5cf 100644 --- a/classes/header.php +++ b/classes/header.php @@ -304,7 +304,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } while ($parentformatoptions['level'] == 1 && $prevsectionindex >= $firstsection); if ($parentformatoptions['firsttabtext']) { - $indextab->content = $parentformatoptions['firsttabtext']; + $indextab->content = format_string($parentformatoptions['firsttabtext'], true, $course->id); } else { $indextab->content = get_string('index', 'format_onetopic'); } From 00d3a636544739c608ace4d6d28a9dc4270dbd1a Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 3 May 2024 12:54:19 -0500 Subject: [PATCH 32/50] Support bulk edit tools --- README.md | 5 ++++- classes/output/courseformat/content.php | 5 +++++ templates/local/content.mustache | 6 ++++++ version.php | 6 +++--- 4 files changed, 18 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 0324536..ca8059f 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # COURSE FORMAT Onetopic -Package tested in: moodle 4.0+, 4.1+. +Package tested in: moodle 4.2+. ## QUICK INSTALL Download zip package, extract the onetopic folder and upload this folder into course/format/. @@ -16,6 +16,9 @@ Download zip package, extract the onetopic folder and upload this folder into co ## IN VERSION +### 2024050301: +* Support bulk edit tools. + ### 2022081610: * New tabs view option: course index * ![Tabs view Course index](https://boa.nuestroscursos.net/api/c/web/resources/NDU1MEVCNjAtODQ4Qy00RTk3LUI2NzUtOUJBN0E5ODk0QTkyQGJvYS51ZGVhLmVkdS5jbw==/!/onetopic/tabsview_courseindex.png) diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index e2a05f1..e24da3c 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -117,6 +117,11 @@ public function export_for_template(\renderer_base $output) { $data->numsections = $addsection->export_for_template($output); } + if ($format->show_editor()) { + $bulkedittools = new $this->bulkedittoolsclass($format); + $data->bulkedittools = $bulkedittools->export_for_template($output); + } + return $data; } diff --git a/templates/local/content.mustache b/templates/local/content.mustache index b2d4038..3a24efe 100644 --- a/templates/local/content.mustache +++ b/templates/local/content.mustache @@ -84,4 +84,10 @@ {{> core_courseformat/local/content/sectionselector }} {{/ core_courseformat/local/content/sectionselector }} {{/sectionselector}} + {{#bulkedittools}} + {{$ core_courseformat/local/content/bulkedittools}} + {{> core_courseformat/local/content/bulkedittools}} + {{/ core_courseformat/local/content/bulkedittools}} + {{/bulkedittools}} +
diff --git a/version.php b/version.php index 66b4f9c..a11e9f9 100644 --- a/version.php +++ b/version.php @@ -33,9 +33,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2022081610.02; // The current plugin version (Date: YYYYMMDDXX). -$plugin->requires = 2023042403; // Requires this Moodle version. +$plugin->version = 2024050301; // The current plugin version (Date: YYYYMMDDXX). +$plugin->requires = 2023041800; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.2.01(ElCardal)'; +$plugin->release = '4.2.02(ElCardal)'; $plugin->dependencies = ['format_topics' => 2023042400]; From 46515acfa0c36e6d29d76fdf58b1c04cfbcda2eb Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 3 May 2024 14:38:52 -0500 Subject: [PATCH 33/50] =?UTF-8?q?Estilo=20de=20c=C3=B3digo?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- classes/output/courseformat/content/section/summary.php | 2 +- classes/privacy/provider.php | 2 +- classes/singletab.php | 4 ++-- classes/tabs.php | 4 ++-- 4 files changed, 6 insertions(+), 6 deletions(-) diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index 0ad8c67..bdc0546 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -248,7 +248,7 @@ private function replace_resources(section_info $section) { * @param array $match * @return array */ - public function replace_tag_in_expresion ($match) { + public function replace_tag_in_expresion($match) { $term = $match[0]; $term = str_replace("[[", '', $term); diff --git a/classes/privacy/provider.php b/classes/privacy/provider.php index de72f97..fa1814d 100644 --- a/classes/privacy/provider.php +++ b/classes/privacy/provider.php @@ -35,7 +35,7 @@ class provider implements \core_privacy\local\metadata\null_provider { * * @return string */ - public static function get_reason() : string { + public static function get_reason(): string { return 'privacy:metadata'; } } diff --git a/classes/singletab.php b/classes/singletab.php index ef15d9b..949df1c 100644 --- a/classes/singletab.php +++ b/classes/singletab.php @@ -72,12 +72,12 @@ class singletab { public $specialclass; /** - * @var boolean If tab is selected. + * @var bool If tab is selected. */ public $selected = false; /** - * @var boolean If tab is active. + * @var bool If tab is active. */ public $active = true; diff --git a/classes/tabs.php b/classes/tabs.php index c629741..3aa04f7 100644 --- a/classes/tabs.php +++ b/classes/tabs.php @@ -69,7 +69,7 @@ public function add(singletab $tab) { * @param bool $assubtabs It's a subtabs list. * @return array of object. */ - public function get_list(bool $assubtabs = false) : array { + public function get_list(bool $assubtabs = false): array { $tabstree = []; @@ -126,7 +126,7 @@ public function count_tabs() { * * @return object With list of tabs in a tabs attribute. */ - public function get_secondlist() : object { + public function get_secondlist(): object { $tabstree = new \stdClass(); $tabstree->tabs = []; From 1a0bfc225ea3c9583b6a231695f17a16dfcc1410 Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 3 May 2024 19:36:05 -0500 Subject: [PATCH 34/50] Fixed canviewhidden sections --- classes/header.php | 8 +------- .../output/courseformat/content/sectionnavigation.php | 11 ++++------- version.php | 2 +- 3 files changed, 6 insertions(+), 15 deletions(-) diff --git a/classes/header.php b/classes/header.php index 5f3334a..ee24193 100644 --- a/classes/header.php +++ b/classes/header.php @@ -48,8 +48,6 @@ class header implements \renderable, \templatable { * @param \format_onetopic $format Course format instance. */ public function __construct(\format_onetopic $format) { - global $COURSE; - $this->format = $format; } @@ -60,7 +58,7 @@ public function __construct(\format_onetopic $format) { * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output) { - global $COURSE, $PAGE, $CFG, $OUTPUT; + global $PAGE, $CFG, $OUTPUT; $format = $this->format; $course = $this->format->get_course(); @@ -71,9 +69,6 @@ public function export_for_template(\renderer_base $output) { $firstsection = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; $currentsection = $this->format->get_section_number(); - $coursecontext = \context_course::instance($course->id); - $canviewhidden = has_capability('moodle/course:viewhiddensections', $coursecontext); - $tabslist = []; $secondtabslist = null; if ($course->tabsview != \format_onetopic::TABSVIEW_COURSEINDEX && @@ -113,7 +108,6 @@ public function export_for_template(\renderer_base $output) { 'format' => $this->format->get_format(), 'templatetopic' => $course->templatetopic, 'withicons' => $course->templatetopic_icons, - 'canviewhidden' => $canviewhidden, 'hastopictabs' => $hastopictabs, 'tabs' => $tabslist, 'hassecondrow' => $hassecondrow, diff --git a/classes/output/courseformat/content/sectionnavigation.php b/classes/output/courseformat/content/sectionnavigation.php index b3ad937..a0ea837 100644 --- a/classes/output/courseformat/content/sectionnavigation.php +++ b/classes/output/courseformat/content/sectionnavigation.php @@ -18,7 +18,7 @@ * Contains the default section navigation output class. * * @package format_onetopic - * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @copyright 2022 David Herney - cirano. https://bambuco.co * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ @@ -36,7 +36,7 @@ * Base class to render a course add section navigation. * * @package format_onetopic - * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co + * @copyright 2022 David Herney - cirano. https://bambuco.co * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ class sectionnavigation extends sectionnavigation_base { @@ -64,9 +64,6 @@ public function export_for_template(\renderer_base $output): stdClass { $modinfo = $this->format->get_modinfo(); $sections = $modinfo->get_section_info_all(); - // FIXME: This is really evil and should by using the navigation API. - $canviewhidden = has_capability('moodle/course:viewhiddensections', $context, $USER); - $data = (object)[ 'previousurl' => '', 'nexturl' => '', @@ -78,7 +75,7 @@ public function export_for_template(\renderer_base $output): stdClass { $firstsection = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; $back = $this->sectionno - 1; while ($back > ($firstsection - 1) && empty($data->previousurl)) { - if ($canviewhidden || $sections[$back]->uservisible) { + if ($sections[$back]->uservisible) { if (!$sections[$back]->visible) { $data->previoushidden = true; } @@ -92,7 +89,7 @@ public function export_for_template(\renderer_base $output): stdClass { $forward = $this->sectionno + 1; $numsections = course_get_format($course)->get_last_section_number(); while ($forward <= $numsections && empty($data->nexturl)) { - if ($canviewhidden || $sections[$forward]->uservisible) { + if ($sections[$forward]->uservisible) { if (!$sections[$forward]->visible) { $data->nexthidden = true; } diff --git a/version.php b/version.php index a11e9f9..e050293 100644 --- a/version.php +++ b/version.php @@ -33,7 +33,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050301; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050301.01; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2023041800; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From 31dee0b88ae797ad9b1ea16c1897d6c879050d71 Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 3 May 2024 19:48:57 -0500 Subject: [PATCH 35/50] New release --- version.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/version.php b/version.php index e050293..0269d13 100644 --- a/version.php +++ b/version.php @@ -33,7 +33,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050301.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050302; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2023041800; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From 565786c9b10b93fb621bad34ffec8cadeea2e6c8 Mon Sep 17 00:00:00 2001 From: David Herney Date: Wed, 8 May 2024 20:56:43 -0500 Subject: [PATCH 36/50] Update section control menu for Moodle 4.2 --- README.md | 3 + .../content/section/controlmenu.php | 59 ++---- duplicate.php | 200 ------------------ version.php | 2 +- 4 files changed, 16 insertions(+), 248 deletions(-) delete mode 100644 duplicate.php diff --git a/README.md b/README.md index ca8059f..2cec533 100644 --- a/README.md +++ b/README.md @@ -16,6 +16,9 @@ Download zip package, extract the onetopic folder and upload this folder into co ## IN VERSION +### 2024050303: +* Update section control menu for Moodle 4.2 + ### 2024050301: * Support bulk edit tools. diff --git a/classes/output/courseformat/content/section/controlmenu.php b/classes/output/courseformat/content/section/controlmenu.php index 377f587..b6189b3 100644 --- a/classes/output/courseformat/content/section/controlmenu.php +++ b/classes/output/courseformat/content/section/controlmenu.php @@ -25,7 +25,7 @@ namespace format_onetopic\output\courseformat\content\section; use context_course; -use core_courseformat\output\local\content\section\controlmenu as controlmenu_base; +use format_topics\output\courseformat\content\section\controlmenu as controlmenu_format_topics; /** * Base class to render a course section menu. @@ -34,7 +34,7 @@ * @copyright 2022 David Herney Bernal - cirano. https://bambuco.co * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -class controlmenu extends controlmenu_base { +class controlmenu extends controlmenu_format_topics { /** @var course_format the course format class */ protected $format; @@ -69,35 +69,6 @@ public function section_control_items() { $url->param('sesskey', sesskey()); $othercontrols = []; - if ($section->section && has_capability('moodle/course:setcurrentsection', $coursecontext)) { - if ($course->marker == $section->section) { // Show the "light globe" on/off. - $url->param('marker', 0); - $highlightoff = get_string('highlightoff'); - $othercontrols['highlight'] = [ - 'url' => $url, - 'icon' => 'i/marked', - 'name' => $highlightoff, - 'pixattr' => ['class' => ''], - 'attr' => [ - 'class' => 'editing_highlight', - 'data-action' => 'removemarker', - ], - ]; - } else { - $url->param('marker', $section->section); - $highlight = get_string('highlight'); - $othercontrols['highlight'] = [ - 'url' => $url, - 'icon' => 'i/marker', - 'name' => $highlight, - 'pixattr' => ['class' => ''], - 'attr' => [ - 'class' => 'editing_highlight', - 'data-action' => 'setmarker', - ], - ]; - } - } $movecontrols = []; if ($section->section && !$isstealth && has_capability('moodle/course:movesections', $coursecontext, $USER)) { @@ -136,22 +107,6 @@ public function section_control_items() { } } - // Duplicate current section option. - if ($section->section && has_capability('moodle/course:manageactivities', $coursecontext)) { - $urlduplicate = new \moodle_url('/course/format/onetopic/duplicate.php', - ['courseid' => $course->id, 'section' => $section->section, 'sesskey' => sesskey()]); - - $othercontrols['duplicate'] = [ - 'url' => $urlduplicate, - 'icon' => 'i/reload', - 'name' => get_string('duplicate', 'format_onetopic'), - 'pixattr' => ['class' => ''], - 'attr' => [ - 'class' => 'editing_duplicate', - ], - ]; - } - $parentcontrols = parent::section_control_items(); // ToDo: reload the page is a temporal solution. We need control the delete tab action with JS. @@ -165,6 +120,16 @@ public function section_control_items() { unset($parentcontrols['delete']['attr']['data-action']); } + // Create the permalink according to the Onetopic format. + if (array_key_exists("permalink", $parentcontrols)) { + $sectionlink = new \moodle_url( + '/course/view.php', + ['id' => $course->id, 'sectionid' => $section->id], + 'tabs-tree-start'); + + $parentcontrols['permalink']['url'] = $sectionlink; + } + // If the edit key exists, we are going to insert our controls after it. $merged = []; $editcontrolexists = array_key_exists("edit", $parentcontrols); diff --git a/duplicate.php b/duplicate.php deleted file mode 100644 index 710a430..0000000 --- a/duplicate.php +++ /dev/null @@ -1,200 +0,0 @@ -. - -/** - * Duplicate resources on a section as a new section - * - * @package format_onetopic - * @copyright 2015 David Herney Bernal - cirano - * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */ - -define('NO_OUTPUT_BUFFERING', true); - -require_once('../../../config.php'); -require_once($CFG->dirroot.'/course/lib.php'); - -$courseid = required_param('courseid', PARAM_INT); -$section = required_param('section', PARAM_INT); - -$course = $DB->get_record('course', ['id' => $courseid], '*', MUST_EXIST); - -$urlstring = '/course/format/onetopic/duplicate.php'; -$PAGE->set_url($urlstring, ['courseid' => $courseid, 'section' => $section]); - -// Authorization checks. -require_login($course); -$context = context_course::instance($course->id); -require_capability('moodle/course:update', $context); -require_capability('moodle/course:manageactivities', $context); -require_sesskey(); - -$course = course_get_format($course)->get_course(); -$modinfo = get_fast_modinfo($course); -$sectioninfo = $modinfo->get_section_info($section); -$context = context_course::instance($course->id); -$numnewsection = null; - -$cancelurl = course_get_url($course, $sectioninfo); -$confirm = optional_param('confirm', false, PARAM_BOOL) && confirm_sesskey(); - -if (!$confirm) { - $strconfirm = get_string('duplicate', 'format_onetopic'); - - $PAGE->navbar->add($strconfirm); - $PAGE->set_title($strconfirm); - $PAGE->set_heading($course->fullname); - echo $OUTPUT->header(); - echo $OUTPUT->box_start('noticebox'); - $optionsyes = ['courseid' => $courseid, 'confirm' => 1, 'section' => $section, 'sesskey' => sesskey()]; - $duplicateurl = new moodle_url($urlstring, $optionsyes); - $formcontinue = new single_button($duplicateurl, get_string('duplicate')); - $formcancel = new single_button($cancelurl, get_string('cancel'), 'get'); - echo $OUTPUT->confirm(get_string('duplicate_confirm', 'format_onetopic', - get_section_name($course, $sectioninfo)), $formcontinue, $formcancel); - echo $OUTPUT->box_end(); - echo $OUTPUT->footer(); - exit; -} - -$PAGE->set_pagelayout('course'); -$PAGE->set_heading($course->fullname); - -$PAGE->set_title(get_string('coursetitle', 'moodle', ['course' => $course->fullname])); - -echo $OUTPUT->header(); - -if (!empty($sectioninfo)) { - - $pbar = new progress_bar('onetopic_duplicate_bar', 500, true); - $pbar->update_full(1, get_string('duplicating', 'format_onetopic')); - - $courseformat = course_get_format($course); - - $lastsectionnum = $DB->get_field('course_sections', 'MAX(section)', ['course' => $courseid], MUST_EXIST); - - $numnewsection = $lastsectionnum + 1; - - $pbar->update_full(5, get_string('creating_section', 'format_onetopic')); - - // Assign same section info. - $data = new stdClass(); - $data->course = $sectioninfo->course; - $data->section = $numnewsection; - // The name is not duplicated. - $data->summary = $sectioninfo->summary; - $data->summaryformat = $sectioninfo->summaryformat; - $data->visible = $sectioninfo->visible; - $data->availability = $sectioninfo->availability; - - $newsectionid = $DB->insert_record('course_sections', $data, true); - - try { - $fs = get_file_storage(); - $files = $fs->get_area_files($context->id, 'course', 'section', $sectioninfo->id); - - if ($files && is_array($files)) { - foreach ($files as $f) { - - $fileinfo = [ - 'contextid' => $context->id, - 'component' => 'course', - 'filearea' => 'section', - 'itemid' => $newsectionid, ]; - - $fs->create_file_from_storedfile($fileinfo, $f); - } - } - } catch (Exception $e) { - debugging('Error copying section files.' . $e->getMessage(), DEBUG_DEVELOPER); - } - - $moved = move_section_to($course, $numnewsection, $section + 1); - if ($moved) { - $numnewsection = $section + 1; - } - - $formatoptions = $courseformat->get_format_options($section); - if (is_array($formatoptions) && count($formatoptions) > 0) { - $formatoptions['id'] = $newsectionid; - $courseformat->update_section_format_options($formatoptions); - } - - // Trigger an event for course section update. - $event = \core\event\course_section_updated::create( - [ - 'objectid' => $newsectionid, - 'courseid' => $course->id, - 'context' => $context, - 'other' => ['sectionnum' => $numnewsection], - ] - ); - $event->trigger(); - - $course = course_get_format($course)->get_course(); - $modinfo = get_fast_modinfo($course); - - $pbar->update_full(10, get_string('rebuild_course_cache', 'format_onetopic')); - $newsectioninfo = $modinfo->get_section_info($numnewsection); - - $modules = []; - - if (is_object($modinfo) && isset($modinfo->sections[$section])) { - $sectionmods = $modinfo->sections[$section]; - - if (is_array($sectionmods)) { - - $progressbarelements = count($sectionmods); - $dataprogress = new stdClass(); - $dataprogress->current = 0; - $dataprogress->size = $progressbarelements; - $k = 0; - $pbar->update_full(40, get_string('progress_counter', 'format_onetopic', $dataprogress)); - foreach ($sectionmods as $modnumber) { - $k++; - $mod = $modinfo->cms[$modnumber]; - $cm = get_coursemodule_from_id('', $mod->id, 0, true, MUST_EXIST); - - $modcontext = context_module::instance($cm->id); - if (has_capability('moodle/course:manageactivities', $modcontext) && !$cm->deletioninprogress) { - // Duplicate the module. - $newcm = duplicate_module($course, $cm); - - // Move new module to new section. - if ($newcm && is_object($newcm)) { - $DB->set_field($newcm->modname, 'name', $cm->name, ['id' => $newcm->instance]); - moveto_module($newcm, $newsectioninfo); - } - } - $dataprogress->current = $k; - $percent = 40 + ($k / $progressbarelements) * 60; - $pbar->update_full($percent, get_string('progress_counter', 'format_onetopic', $dataprogress)); - } - } - } else { - $pbar->update_full(100, get_string('progress_full', 'format_onetopic')); - } - - $sectiontogo = $numnewsection; -} else { - $sectiontogo = $section; - echo get_string('error_nosectioninfo', 'format_onetopic'); - echo $OUTPUT->continue_button(course_get_url($course, $section)); - echo $OUTPUT->footer(); -} - -echo $OUTPUT->continue_button(course_get_url($course, $numnewsection)); -echo $OUTPUT->footer(); diff --git a/version.php b/version.php index 0269d13..346135e 100644 --- a/version.php +++ b/version.php @@ -33,7 +33,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050302; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050302.01; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2023041800; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; From 60d658a57700258449291eda5c4797410c4d17f0 Mon Sep 17 00:00:00 2001 From: David Herney Date: Wed, 8 May 2024 21:47:38 -0500 Subject: [PATCH 37/50] Fixed: #161 --- classes/header.php | 44 ++++++++++++++++++++++++-------------------- format.php | 2 -- styles.php | 6 +++++- 3 files changed, 29 insertions(+), 23 deletions(-) diff --git a/classes/header.php b/classes/header.php index ee24193..6e79960 100644 --- a/classes/header.php +++ b/classes/header.php @@ -54,7 +54,7 @@ public function __construct(\format_onetopic $format) { /** * Export this data so it can be used as the context for a mustache template (core/inplace_editable). * - * @param renderer_base $output typically, the renderer that's calling this function + * @param \renderer_base $output typically, the renderer that's calling this function * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output) { @@ -164,31 +164,36 @@ public function export_for_template(\renderer_base $output) { * @return \format_onetopic\tabs an object with tabs information */ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \format_onetopic\tabs { - global $PAGE; + global $section; + + if ($section && $section > 0) { + $displaysection = $section; + } else { + $displaysection = $this->format->get_section_number(); + } $course = $this->format->get_course(); $sections = $modinfo->get_section_info_all(); $numsections = count($sections); - $displaysection = $this->format->get_section_number(); $enablecustomstyles = get_config('format_onetopic', 'enablecustomstyles'); // Init custom tabs. - $section = 0; + $localsection = 0; $tabs = new \format_onetopic\tabs(); $selectedparent = null; $parenttab = null; $firstsection = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; - while ($section < $numsections) { + while ($localsection < $numsections) { $inactivetab = false; - if ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE && $section == 0) { - $section++; + if ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE && $localsection == 0) { + $localsection++; continue; } - $thissection = $sections[$section]; + $thissection = $sections[$localsection]; // Can we view the section in question? if ($thissection->uservisible || $course->hiddensections != 1) { @@ -220,19 +225,19 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } } - if (isset($formatoptions['level']) && $section > $firstsection) { + if (isset($formatoptions['level']) && $localsection > $firstsection) { $level = $formatoptions['level']; } } - if ($section == 0) { + if ($localsection == 0) { $url = new \moodle_url('/course/view.php', ['id' => $course->id, 'section' => 0]); } else { - $url = course_get_url($course, $section); + $url = course_get_url($course, $localsection); } - $specialclass = 'tab_position_' . $section . ' tab_level_' . $level; - if ($course->marker == $section) { + $specialclass = 'tab_position_' . $localsection . ' tab_level_' . $level; + if ($course->marker == $localsection) { $specialclass .= ' marker '; } @@ -247,7 +252,6 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for // Check if display available message is required. $availablemessage = null; if ($course->hiddensections == 2) { - $sectiontpl = new content_base\section($this->format, $thissection); $availabilityclass = $this->format->get_output_classname('content\\section\\availability'); $availability = new $availabilityclass($this->format, $thissection); $availabledata = $availability->export_for_template($output); @@ -257,11 +261,11 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } } - $newtab = new \format_onetopic\singletab($section, $sectionname, $url, $title, + $newtab = new \format_onetopic\singletab($localsection, $sectionname, $url, $title, $availablemessage, $customstyles, $specialclass); $newtab->active = !$inactivetab; - if ($displaysection == $section) { + if ($displaysection == $localsection) { $newtab->selected = true; } @@ -282,7 +286,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $parenttab->customstyles, $specialclasstmp); - $prevsectionindex = $section - 1; + $prevsectionindex = $localsection - 1; do { $parentsection = $sections[$prevsectionindex]; $parentformatoptions = course_get_format($course)->get_format_options($parentsection); @@ -309,7 +313,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for // Load subtabs. $parenttab->add_child($newtab); - if ($displaysection == $section) { + if ($displaysection == $localsection) { $selectedparent = $parenttab; $parenttab->selected = true; } @@ -321,7 +325,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } - $section++; + $localsection++; } if ($this->format->show_editor()) { @@ -346,7 +350,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for $selectedsubtabs = $selectedparent ? $tabs->get_tab($selectedparent->index) : null; $showsubtabs = $selectedsubtabs && $selectedsubtabs->has_childs(); - if ($showsubtabs) { + if ($showsubtabs && $selectedparent) { // Increase number of sections in child tabs. $paramstotabs['aschild'] = 1; $url = new \moodle_url('/course/format/onetopic/changenumsections.php', $paramstotabs); diff --git a/format.php b/format.php index bb90563..2cfa24c 100644 --- a/format.php +++ b/format.php @@ -53,8 +53,6 @@ $renderer = $PAGE->get_renderer('format_onetopic'); -$section = $displaysection; - $disableajax = optional_param('onetopic_da', -1, PARAM_INT); if (!isset($USER->onetopic_da)) { diff --git a/styles.php b/styles.php index bd763cd..361318a 100644 --- a/styles.php +++ b/styles.php @@ -49,12 +49,14 @@ foreach ($orderedtabs as $type => $styles) { + $important = false; switch ($type) { case 'active': $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link.active, '; $csscontent .= '#tabs-tree-start .nav-tabs a.nav-link.active, '; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs a.nav-link.active, '; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic a.nav-link.active'; + $important = true; break; case 'parent': $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.haschilds a.nav-link, '; @@ -65,12 +67,14 @@ $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.marker a.nav-link, '; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.marker a.nav-link'; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.marker a.nav-link'; + $important = true; break; case 'disabled': $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item.disabled a.nav-link, '; $csscontent .= '#tabs-tree-start .nav-tabs .nav-item.disabled a.nav-link, '; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.disabled a.nav-link'; $csscontent .= '#tabs-tree-start .onetopic-tab-body .nav-tabs .nav-item.subtopic.disabled a.nav-link'; + $important = true; break; case 'hover': $csscontent .= '#tabs-tree-start .verticaltabs .format_onetopic-tabs .nav-item a.nav-link:hover, '; @@ -119,7 +123,7 @@ if ($key == 'others') { $csscontent .= $value . ';'; } else { - $csscontent .= $key . ':' . $value . ';'; + $csscontent .= $key . ':' . $value . ($important ? '!important' : '') . ';'; } } From 61cef852b241a6fdd1c6db5c6c5fab7bdaede74d Mon Sep 17 00:00:00 2001 From: David Herney Date: Wed, 8 May 2024 23:05:31 -0500 Subject: [PATCH 38/50] New release --- README.md | 2 +- classes/header.php | 2 +- version.php | 4 ++-- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/README.md b/README.md index 2cec533..c3b200d 100644 --- a/README.md +++ b/README.md @@ -17,7 +17,7 @@ Download zip package, extract the onetopic folder and upload this folder into co ## IN VERSION ### 2024050303: -* Update section control menu for Moodle 4.2 +* Update section control menu for Moodle 4.2 and stabilization improvements. ### 2024050301: * Support bulk edit tools. diff --git a/classes/header.php b/classes/header.php index ad62791..96ac0a8 100644 --- a/classes/header.php +++ b/classes/header.php @@ -294,7 +294,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } while ($parentformatoptions['level'] == 1 && $prevsectionindex >= $firstsection); if ($parentformatoptions['firsttabtext']) { - $indextab->content = format_string($parentformatoptions['firsttabtext'], true, $course->id); + $indextab->content = format_text($parentformatoptions['firsttabtext'], true, $course->id); } else { $indextab->content = get_string('index', 'format_onetopic'); } diff --git a/version.php b/version.php index 346135e..b8372e6 100644 --- a/version.php +++ b/version.php @@ -33,9 +33,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050302.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050303; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2023041800; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.2.02(ElCardal)'; +$plugin->release = '4.2.03(ElCardal)'; $plugin->dependencies = ['format_topics' => 2023042400]; From 45f21f6fea84fe1dd9754ca4ca8adeaa62c84012 Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 9 May 2024 00:15:53 -0500 Subject: [PATCH 39/50] Code compliance --- .github/workflows/moodle-ci.yml | 7 +- lang/en/format_onetopic.php | 244 +++++++++--------- lang/es/format_onetopic.php | 135 +++++----- .../content/cm/activity_infoinline.mustache | 2 +- 4 files changed, 180 insertions(+), 208 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 8e4e856..494e39b 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -48,15 +48,10 @@ jobs: database: pgsql plugin-ci: ^4 # Moodle 4.3, PHP 8.1, MySQL - - php: '8.1' + - php: '8.1' moodle-branch: 'MOODLE_403_STABLE' database: mariadb plugin-ci: ^4 - # Moodle main (not yet released 4.4), PHP 8.1, MySQL - - php: '8.1' - moodle-branch: 'main' - database: mariadb - plugin-ci: ^4 steps: - name: Check out repository code uses: actions/checkout@v4 diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index a8a94bb..043a50c 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -23,158 +23,146 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -$string['currentsection'] = 'This topic'; -$string['sectionname'] = 'Topic'; -$string['pluginname'] = 'Onetopic format'; -$string['page-course-view-topics'] = 'Any course main page in onetopic format'; -$string['page-course-view-topics-x'] = 'Any course page in onetopic format'; -$string['hidefromothers'] = 'Hide topic'; -$string['showfromothers'] = 'Show topic'; -$string['hidetabsbar'] = 'Hide tabs bar'; -$string['hidetabsbar_help'] = 'Hide tabs bar in the course page. The navigation is with the sections navbar.'; - -$string['movesectionto'] = 'Move current topic'; -$string['movesectionto_help'] = 'Move current topic to left/right of selected topic'; - -$string['utilities'] = 'Tabs edition utilities'; -$string['disableajax'] = 'Asynchronous edit actions'; -$string['disable'] = 'Disable'; -$string['enable'] = 'Enable'; -$string['disableajax_help'] = 'Use this action in order to move resources between topic tabs. It only disables the asynchronous actions in current session, it is not permanently.'; - -$string['subtopictoright'] = 'Move to right as subtopic'; - -$string['duplicatesection'] = 'Duplicate current topic'; -$string['duplicatesection_help'] = 'Used to duplicate the resources of current topic in a new topic'; -$string['duplicate'] = 'Duplicate'; -$string['duplicating'] = 'Duplicating'; -$string['creating_section'] = 'Creating new topic'; -$string['rebuild_course_cache'] = 'Rebuild course cache'; -$string['duplicate_confirm'] = 'Are you sure you want to duplicate the current topic? The task can take a while depending on the amount of resources.'; -$string['cantcreatesection'] = 'Error creating a new topic'; -$string['progress_counter'] = 'Duplicating activities ({$a->current}/{$a->size})'; -$string['progress_full'] = 'Duplicating topic'; -$string['error_nosectioninfo'] = 'The indicated topic have not information'; - -$string['level'] = 'Level'; -$string['index'] = 'Index'; -$string['asprincipal'] = 'Normal, as a first level tab'; +$string['aboutresource'] = 'About the resource'; $string['asbrother'] = 'Same level that the previous tab'; $string['aschild'] = 'Child of previous tab'; -$string['level_help'] = 'Change the tab level.'; -$string['fontcolor'] = 'Font color'; -$string['fontcolor_help'] = 'Used to change the tab font color. The value can be a color in a CSS valid representation, for example:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Name: green
'; +$string['asprincipal'] = 'Normal, as a first level tab'; $string['bgcolor'] = 'Background color'; $string['bgcolor_help'] = 'Used to change the tab background color. The value can be a color in a CSS valid representation, for example:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Name: green
'; -$string['cssstyles'] = 'CSS properties'; -$string['cssstyles_help'] = 'Used to change CSS properties of the tab. Use a standard value to the attribute style in a html tag. Example:
font-weight: bold; font-size: 16px;'; -$string['firsttabtext'] = 'Text of the first tab in sublevel'; -$string['firsttabtext_help'] = 'If this tab has sublevels, this will be the text of the first tab'; - +$string['cantcreatesection'] = 'Error creating a new topic'; +$string['colorpicker'] = 'Color picker'; +$string['colorpicker_help'] = ''; $string['coursedisplay'] = 'Visualization mode of section 0'; $string['coursedisplay_help'] = 'This define as display the section 0: as a first tab or as section before the tabs bar.'; -$string['coursedisplay_single'] = 'As tab'; $string['coursedisplay_multi'] = 'Before the tabs'; - -$string['templatetopic'] = 'Use topic summary as template'; -$string['templatetopic_help'] = 'This option is used in order to use the summary topic as a template. If it is used as template, you can include the resources in the content, not only as tradicional moodle\'s lists.
In order to include a resource, write the resource name between double brackets, for example: [[News forum]]. This functionality is similar to activity name filter, however, it is different because the user can chose if included the resource icon and decide than activities are be included.'; -$string['templetetopic_not'] = 'No, display as default'; -$string['templetetopic_single'] = 'Yes, use the summary as template'; -$string['templetetopic_list'] = 'Yes, use the summary as template, list the resources that are not referenced'; -$string['templatetopic_icons'] = 'Show icon in resource links in summary'; -$string['templatetopic_icons_help'] = 'This option defines if the icons are displayed in the summary when it is a template.'; -$string['hidden_message'] = 'The section {$a} is not currently available.'; -$string['privacy:metadata'] = 'The Onetopic format plugin does not store any personal data.'; -$string['hiddensectionshelp'] = 'Hidden sections are shown in collapsed form with available message'; - -$string['tabsview'] = 'Tabs view'; -$string['tabsview_help'] = 'By default: is the traditional view.
-Vertically: show tabs in vertical direction. Tabs on the left and content on the right.
-One single line: all tabs are displayed in a single line with horizontal scroll. Useful if too many tabs are used.'; -$string['tabsview_default'] = 'By default'; -$string['tabsview_vertical'] = 'Vertically'; -$string['tabsview_oneline'] = 'Only one line'; -$string['tabsview_courseindex'] = 'Embedded course index'; - -$string['increasesections'] = 'Add a section after the currently selected section'; - -$string['hiddentabsbar'] = 'The tabs are set to be hidden. They will not be seen when not in edit mode.'; -$string['enablecustomstyles'] = 'Enable custom styles'; -$string['enablecustomstyles_help'] = 'Enable font color, background color and other custom tab styles in the sections configuration.'; - -$string['usessectionsnavigation'] = 'Uses sections navigation'; -$string['usessectionsnavigation_help'] = 'Show buttons for navigate to next or previous section.'; -$string['sectionsnavigation_sitelevel'] = 'Use the default site value'; -$string['sectionsnavigation_support'] = 'Only if theme not support the "uses course index" feature'; -$string['sectionsnavigation_not'] = 'Not use'; -$string['sectionsnavigation_bottom'] = 'Only at the bottom'; -$string['sectionsnavigation_both'] = 'At top and bottom section'; -$string['sectionsnavigation_slides'] = 'Like slides'; -$string['enableanchorposition'] = 'Enable anchor position'; -$string['enableanchorposition_help'] = 'Use an anchor to navigate to the top of tabs when click in a tab.'; -$string['defaultsectionsnavigation'] = 'Default value to sections navigation'; -$string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; -$string['usescourseindex'] = 'Uses course index'; -$string['usescourseindex_help'] = 'Use the course index bar to navigate through the sections and resources'; - -$string['aboutresource'] = 'About the resource'; +$string['coursedisplay_single'] = 'As tab'; $string['courseindex'] = 'Course index'; $string['courseindex_help'] = 'Enable or disable the course index bar to navigate through the sections and resources. This option is only usable if the Course index feature is available in the current Theme. This option can be overwrite for each course.'; -$string['usecourseindexsite'] = 'Use the default site value'; -$string['settingsheaderstyles'] = 'Styles'; -$string['tabstyles'] = 'Tab styles'; -$string['tabstyles_help'] = 'Set the styles for the differents tab states.'; -$string['tablabeldefault'] = 'Default tab {$a}'; -$string['tablabelactive'] = 'Active tab'; -$string['tablabelparent'] = 'Parent tab'; -$string['tablabelhighlighted'] = 'Highlighted'; -$string['tablabeldisabled'] = 'Disabled'; -$string['tabstylesetdefault'] = 'Set Default'; -$string['tabstylesetactive'] = 'Set Active'; -$string['tabstylesetparent'] = 'Set Parent'; -$string['tabstylesethighlighted'] = 'Set Highlighted'; -$string['tabstylesetdisabled'] = 'Set Disabled'; -$string['tabstylesethover'] = 'Set Hover'; -$string['tabstylestitle'] = 'Tab styles'; -$string['tabstylesset'] = 'Set styles'; -$string['tabstyleclear'] = 'Clear styles'; +$string['creating_section'] = 'Creating new topic'; $string['cssbackground'] = 'Background'; -$string['cssfont'] = 'Font'; -$string['csscolor'] = 'Color'; -$string['cssweight'] = 'Weight'; -$string['cssweightbold'] = 'Bold'; -$string['cssweightlighter'] = 'Lighter'; -$string['colorpicker'] = 'Color picker'; -$string['colorpicker_help'] = ''; -$string['csssize'] = 'Size'; -$string['cssstyle'] = 'Style'; -$string['cssnormal'] = 'Normal'; -$string['cssitalic'] = 'Italic'; -$string['cssoblique'] = 'Oblique'; -$string['cssother'] = 'Other styles'; $string['cssborder'] = 'Border'; -$string['cssnone'] = 'None'; -$string['csssolid'] = 'Solid'; +$string['csscolor'] = 'Color'; $string['cssdashed'] = 'Dashed'; $string['cssdotted'] = 'Dotted'; $string['cssdouble'] = 'Double'; +$string['cssfont'] = 'Font'; $string['cssgroove'] = 'Groove'; $string['csshidden'] = 'Hidden'; $string['cssinset'] = 'Inset'; +$string['cssitalic'] = 'Italic'; +$string['cssnone'] = 'None'; +$string['cssnormal'] = 'Normal'; +$string['cssoblique'] = 'Oblique'; +$string['cssother'] = 'Other styles'; $string['cssoutset'] = 'Outset'; -$string['cssridge'] = 'Ridge'; $string['cssradius'] = 'Radius'; +$string['cssridge'] = 'Ridge'; +$string['csssize'] = 'Size'; +$string['csssolid'] = 'Solid'; +$string['cssstyle'] = 'Style'; +$string['cssstyles'] = 'CSS properties'; +$string['cssstyles_help'] = 'Used to change CSS properties of the tab. Use a standard value to the attribute style in a html tag. Example:
font-weight: bold; font-size: 16px;'; $string['cssunit'] = 'Unit'; -$string['cssunit_px'] = 'px'; $string['cssunit_em'] = 'em'; -$string['cssunit_percent'] = '%'; $string['cssunit_in'] = 'in'; -$string['invalidjsonstyles'] = 'Styles configuration is not valid, fails with: {$a}'; -$string['tabstylebuttons_help'] = 'Click on each button to configure the appearance of the tab in each of its possible states.'; -$string['tabstylesetchilds'] = 'Set Childs'; -$string['tabstylesetchildindex'] = 'Set Child index'; +$string['cssunit_percent'] = '%'; +$string['cssunit_px'] = 'px'; +$string['cssweight'] = 'Weight'; +$string['cssweightbold'] = 'Bold'; +$string['cssweightlighter'] = 'Lighter'; +$string['currentsection'] = 'This topic'; $string['defaultscope'] = 'Default scope'; $string['defaultscope_help'] = 'Default scope used to define the pages on which the tab menu is printed.'; +$string['defaultsectionsnavigation'] = 'Default value to sections navigation'; +$string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; +$string['disable'] = 'Disable'; +$string['disableajax'] = 'Asynchronous edit actions'; +$string['disableajax_help'] = 'Use this action in order to move resources between topic tabs. It only disables the asynchronous actions in current session, it is not permanently.'; +$string['duplicate'] = 'Duplicate'; +$string['duplicate_confirm'] = 'Are you sure you want to duplicate the current topic? The task can take a while depending on the amount of resources.'; +$string['duplicatesection'] = 'Duplicate current topic'; +$string['duplicatesection_help'] = 'Used to duplicate the resources of current topic in a new topic'; +$string['duplicating'] = 'Duplicating'; +$string['enable'] = 'Enable'; +$string['enableanchorposition'] = 'Enable anchor position'; +$string['enableanchorposition_help'] = 'Use an anchor to navigate to the top of tabs when click in a tab.'; +$string['enablecustomstyles'] = 'Enable custom styles'; +$string['enablecustomstyles_help'] = 'Enable font color, background color and other custom tab styles in the sections configuration.'; +$string['error_nosectioninfo'] = 'The indicated topic have not information'; +$string['firsttabtext'] = 'Text of the first tab in sublevel'; +$string['firsttabtext_help'] = 'If this tab has sublevels, this will be the text of the first tab'; +$string['fontcolor'] = 'Font color'; +$string['fontcolor_help'] = 'Used to change the tab font color. The value can be a color in a CSS valid representation, for example:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Name: green
'; +$string['hidden_message'] = 'The section {$a} is not currently available.'; +$string['hiddensectionshelp'] = 'Hidden sections are shown in collapsed form with available message'; +$string['hiddentabsbar'] = 'The tabs are set to be hidden. They will not be seen when not in edit mode.'; +$string['hidefromothers'] = 'Hide topic'; +$string['hidetabsbar'] = 'Hide tabs bar'; +$string['hidetabsbar_help'] = 'Hide tabs bar in the course page. The navigation is with the sections navbar.'; +$string['increasesections'] = 'Add a section after the currently selected section'; +$string['index'] = 'Index'; +$string['invalidjsonstyles'] = 'Styles configuration is not valid, fails with: {$a}'; +$string['level'] = 'Level'; +$string['level_help'] = 'Change the tab level.'; +$string['movesectionto'] = 'Move current topic'; +$string['movesectionto_help'] = 'Move current topic to left/right of selected topic'; +$string['page-course-view-topics'] = 'Any course main page in onetopic format'; +$string['page-course-view-topics-x'] = 'Any course page in onetopic format'; +$string['pluginname'] = 'Onetopic format'; +$string['privacy:metadata'] = 'The Onetopic format plugin does not store any personal data.'; +$string['progress_counter'] = 'Duplicating activities ({$a->current}/{$a->size})'; +$string['progress_full'] = 'Duplicating topic'; +$string['rebuild_course_cache'] = 'Rebuild course cache'; $string['scope_mod'] = 'Modules'; +$string['sectionname'] = 'Topic'; +$string['sectionsnavigation_both'] = 'At top and bottom section'; +$string['sectionsnavigation_bottom'] = 'Only at the bottom'; +$string['sectionsnavigation_not'] = 'Not use'; +$string['sectionsnavigation_sitelevel'] = 'Use the default site value'; +$string['sectionsnavigation_slides'] = 'Like slides'; +$string['sectionsnavigation_support'] = 'Only if theme not support the "uses course index" feature'; +$string['settingsheaderstyles'] = 'Styles'; +$string['showfromothers'] = 'Show topic'; +$string['subtopictoright'] = 'Move to right as subtopic'; +$string['tablabelactive'] = 'Active tab'; +$string['tablabeldefault'] = 'Default tab {$a}'; +$string['tablabeldisabled'] = 'Disabled'; +$string['tablabelhighlighted'] = 'Highlighted'; +$string['tablabelparent'] = 'Parent tab'; +$string['tabstylebuttons_help'] = 'Click on each button to configure the appearance of the tab in each of its possible states.'; +$string['tabstyleclear'] = 'Clear styles'; +$string['tabstyles'] = 'Tab styles'; +$string['tabstyles_help'] = 'Set the styles for the differents tab states.'; +$string['tabstylesetactive'] = 'Set Active'; +$string['tabstylesetchildindex'] = 'Set Child index'; +$string['tabstylesetchilds'] = 'Set Childs'; +$string['tabstylesetdefault'] = 'Set Default'; +$string['tabstylesetdisabled'] = 'Set Disabled'; +$string['tabstylesethighlighted'] = 'Set Highlighted'; +$string['tabstylesethover'] = 'Set Hover'; +$string['tabstylesetparent'] = 'Set Parent'; +$string['tabstylesset'] = 'Set styles'; +$string['tabstylestitle'] = 'Tab styles'; +$string['tabsview'] = 'Tabs view'; +$string['tabsview_courseindex'] = 'Embedded course index'; +$string['tabsview_default'] = 'By default'; +$string['tabsview_help'] = 'By default: is the traditional view.
+Vertically: show tabs in vertical direction. Tabs on the left and content on the right.
+One single line: all tabs are displayed in a single line with horizontal scroll. Useful if too many tabs are used.'; +$string['tabsview_oneline'] = 'Only one line'; +$string['tabsview_vertical'] = 'Vertically'; +$string['templatetopic'] = 'Use topic summary as template'; +$string['templatetopic_help'] = 'This option is used in order to use the summary topic as a template. If it is used as template, you can include the resources in the content, not only as tradicional moodle\'s lists.
In order to include a resource, write the resource name between double brackets, for example: [[News forum]]. This functionality is similar to activity name filter, however, it is different because the user can chose if included the resource icon and decide than activities are be included.'; +$string['templatetopic_icons'] = 'Show icon in resource links in summary'; +$string['templatetopic_icons_help'] = 'This option defines if the icons are displayed in the summary when it is a template.'; +$string['templetetopic_list'] = 'Yes, use the summary as template, list the resources that are not referenced'; +$string['templetetopic_not'] = 'No, display as default'; +$string['templetetopic_single'] = 'Yes, use the summary as template'; +$string['usecourseindexsite'] = 'Use the default site value'; +$string['usescourseindex'] = 'Uses course index'; +$string['usescourseindex_help'] = 'Use the course index bar to navigate through the sections and resources'; +$string['usessectionsnavigation'] = 'Uses sections navigation'; +$string['usessectionsnavigation_help'] = 'Show buttons for navigate to next or previous section.'; +$string['utilities'] = 'Tabs edition utilities'; diff --git a/lang/es/format_onetopic.php b/lang/es/format_onetopic.php index a625885..d45f3a7 100644 --- a/lang/es/format_onetopic.php +++ b/lang/es/format_onetopic.php @@ -23,94 +23,83 @@ * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ +$string['aschild'] = 'Hijo de la pestaña anterior'; +$string['asprincipal'] = 'Normal, como una pestaña de primer nivel'; +$string['bgcolor'] = 'Color de fondo'; +$string['bgcolor_help'] = 'Utilizado para cambiar el color de fondo del texto en el nombre de la pestaña. El valor puede ser un color en cualquier representación válida para CSS como por ejemplo:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Nombre: green
'; +$string['cantcreatesection'] = 'Error creando un nuevo tema'; +$string['coursedisplay'] = 'Modo de visualización de la sección 0'; +$string['coursedisplay_help'] = 'Define como se muestra la sección 0: como la primera pestaña o como una sección encima de las demás pestañas.'; +$string['coursedisplay_multi'] = 'Arriba de las pestañas'; +$string['coursedisplay_single'] = 'Como pestaña'; +$string['creating_section'] = 'Creando el nuevo tema'; +$string['cssstyles'] = 'Propiedades CSS'; +$string['cssstyles_help'] = 'Sirve para cambiar las propiedades CSS de la pestaña. Utilice el formato tradicional del atributo style de una etiqueta html. Ejemplo:
font-weight: bold; font-size: 16px;'; $string['currentsection'] = 'Este tema'; -$string['pluginname'] = 'Temas en pestañas'; -$string['sectionname'] = 'Tema'; -$string['page-course-view-topics'] = 'Alguna página principal de curso en formato onetopic'; -$string['page-course-view-topics-x'] = 'Alguna página de curso en formato onetopic'; -$string['hidefromothers'] = 'Ocultar tema'; -$string['showfromothers'] = 'Mostrar tema'; -$string['hidetabsbar'] = 'Ocultar barra de pestañas'; -$string['hidetabsbar_help'] = 'Oculta la barra de pestañas en la página principal del curso, la navegación se llevará a cabo con la barra de navegación entre temas.'; - -$string['movesectionto'] = 'Mover el tema actual'; -$string['movesectionto_help'] = 'Mover el tema actual antes de (para temas a la izquierda del actual) o después de (para temas a la derecha del actual) el tema que seleccione'; - -$string['utilities'] = 'Utilidades de edición de pestañas'; -$string['disableajax'] = 'Acciones de edición asíncronas'; +$string['defaultsectionsnavigation'] = 'Valor por defecto para la navegación de secciones'; +$string['defaultsectionsnavigation_help'] = 'Valor por defecto a ser utilizado para definir el comportamiento de la funcionalidad "Usar navegación en secciones". Este valor puede ser sobreescrito por cada curso.'; $string['disable'] = 'Deshabilitar'; -$string['enable'] = 'Habilitar'; +$string['disableajax'] = 'Acciones de edición asíncronas'; $string['disableajax_help'] = 'Deshabilitarlas le permite mover recursos entre pestañas de temas. Sólo se deshabilitan las acciones asíncronas en la sesión actual, no es permanente.'; - -$string['subtopictoright'] = 'Mover a la derecha como pestaña hija'; - +$string['duplicate'] = 'Duplicar'; +$string['duplicate_confirm'] = '¿Está seguro de que desea duplicar el tema actual? La tarea puede tardar un buen rato dependiendo de la cantidad de recursos.'; $string['duplicatesection'] = 'Duplicar tema actual'; $string['duplicatesection_help'] = 'Usado para duplicar los recursos del tema actual en un nuevo tema.'; -$string['duplicate'] = 'Duplicar'; $string['duplicating'] = 'Duplicando'; -$string['creating_section'] = 'Creando el nuevo tema'; -$string['rebuild_course_cache'] = 'Recreando el caché del curso'; -$string['duplicate_confirm'] = '¿Está seguro de que desea duplicar el tema actual? La tarea puede tardar un buen rato dependiendo de la cantidad de recursos.'; -$string['cantcreatesection'] = 'Error creando un nuevo tema'; -$string['progress_counter'] = 'Duplicando actividades ({$a->current}/{$a->size})'; -$string['progress_full'] = 'Duplicando el tema'; +$string['enable'] = 'Habilitar'; +$string['enableanchorposition'] = 'Habilitar ancla de posición'; +$string['enableanchorposition_help'] = 'Usar una ancla para posicionarse en la parte superior de las pestañas cuando se haga clic en una pestaña.'; +$string['enablecustomstyles'] = 'Habilitar estilos personalizados'; +$string['enablecustomstyles_help'] = 'Habilitar color de fuente, color de fondo y otros estilos personalizados de pestañas en la configuración de la sección.'; $string['error_nosectioninfo'] = 'El tema indicado no contiene información.'; - -$string['level'] = 'Nivel'; -$string['index'] = 'Inicio'; -$string['asprincipal'] = 'Normal, como una pestaña de primer nivel'; -$string['aschild'] = 'Hijo de la pestaña anterior'; -$string['level_help'] = 'Cambiar el nivel de la pestaña, para aparecer como un subnivel de pestañas.'; -$string['fontcolor'] = 'Color de fuente'; -$string['fontcolor_help'] = 'Utilizado para cambiar el color de la fuente en el nombre de la pestaña. El valor puede ser un color en cualquier representación válida para CSS como por ejemplo:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Nombre: green
'; -$string['bgcolor'] = 'Color de fondo'; -$string['bgcolor_help'] = 'Utilizado para cambiar el color de fondo del texto en el nombre de la pestaña. El valor puede ser un color en cualquier representación válida para CSS como por ejemplo:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Nombre: green
'; -$string['cssstyles'] = 'Propiedades CSS'; -$string['cssstyles_help'] = 'Sirve para cambiar las propiedades CSS de la pestaña. Utilice el formato tradicional del atributo style de una etiqueta html. Ejemplo:
font-weight: bold; font-size: 16px;'; $string['firsttabtext'] = 'Nombre de la primera pestaña (inicio) en el subnivel'; $string['firsttabtext_help'] = 'Si la pestaña tiene un subnivel de pestañas, éste será el texto para la primera pestaña del subnivel.'; - -$string['coursedisplay'] = 'Modo de visualización de la sección 0'; -$string['coursedisplay_help'] = 'Define como se muestra la sección 0: como la primera pestaña o como una sección encima de las demás pestañas.'; -$string['coursedisplay_single'] = 'Como pestaña'; -$string['coursedisplay_multi'] = 'Arriba de las pestañas'; - -$string['templatetopic'] = 'Usar resumen de tema como plantilla'; -$string['templatetopic_help'] = 'Permite usar el resumen del tema como una plantilla, de esa manera se pueden ubicar los recursos en cualquier parte del contenido, no necesariamente como listas secuenciales como se muestran tradicionalmente en Moodle.
Para ubicar un recurso, simplemente agrege en el resumen de la sección el nombre del recurso encerrado entre dobles corchetes, ejemplo: [[Foro de Novedades]]. Su comportamiento es similar al filtro por nombre de actividad con la diferencia de que se puede agregar el icono del recurso y además se puede elegir cuales recursos se muestran y cuales no.'; -$string['templetetopic_not'] = 'No, mostrar normal'; -$string['templetetopic_single'] = 'Si, usar el resumen como una plantilla'; -$string['templetetopic_list'] = 'Si, usar el resumen como plantilla y listar los recursos no referenciados'; -$string['templatetopic_icons'] = 'Mostrar icono en enlaces de recursos en el resumen'; -$string['templatetopic_icons_help'] = 'Esta opción define si se muestran o no los iconos de los recursos como parte del nombre, cuando el resumen del tema se utiliza como plantilla.'; +$string['fontcolor'] = 'Color de fuente'; +$string['fontcolor_help'] = 'Utilizado para cambiar el color de la fuente en el nombre de la pestaña. El valor puede ser un color en cualquier representación válida para CSS como por ejemplo:
  • Hexadecimal: #ffffff
  • RGB: rgb(0,255,0)
  • Nombre: green
'; $string['hidden_message'] = 'El tema {$a} no está disponible en este momento.'; -$string['privacy:metadata'] = 'El formato Temas en pestañas no almacena datos personales.'; $string['hiddensectionshelp'] = 'Las secciones ocultas se muestran en forma colapsada con mensaje de disponibilidad'; - +$string['hiddentabsbar'] = 'Las pestañas están configuradas para estar ocultas. No se verán cuando no esté en modo de edición.'; +$string['hidefromothers'] = 'Ocultar tema'; +$string['hidetabsbar'] = 'Ocultar barra de pestañas'; +$string['hidetabsbar_help'] = 'Oculta la barra de pestañas en la página principal del curso, la navegación se llevará a cabo con la barra de navegación entre temas.'; +$string['increasesections'] = 'Adicionar una nueva sección después de la sección actual'; +$string['index'] = 'Inicio'; +$string['level'] = 'Nivel'; +$string['level_help'] = 'Cambiar el nivel de la pestaña, para aparecer como un subnivel de pestañas.'; +$string['movesectionto'] = 'Mover el tema actual'; +$string['movesectionto_help'] = 'Mover el tema actual antes de (para temas a la izquierda del actual) o después de (para temas a la derecha del actual) el tema que seleccione'; +$string['page-course-view-topics'] = 'Alguna página principal de curso en formato onetopic'; +$string['page-course-view-topics-x'] = 'Alguna página de curso en formato onetopic'; +$string['pluginname'] = 'Temas en pestañas'; +$string['privacy:metadata'] = 'El formato Temas en pestañas no almacena datos personales.'; +$string['progress_counter'] = 'Duplicando actividades ({$a->current}/{$a->size})'; +$string['progress_full'] = 'Duplicando el tema'; +$string['rebuild_course_cache'] = 'Recreando el caché del curso'; +$string['sectionname'] = 'Tema'; +$string['sectionsnavigation_both'] = 'En la parte superior e inferior de la sección'; +$string['sectionsnavigation_bottom'] = 'Usar en la parte inferior'; +$string['sectionsnavigation_not'] = 'No usar'; +$string['sectionsnavigation_sitelevel'] = 'Usar el valor por defecto del sitio'; +$string['sectionsnavigation_slides'] = 'Similar a un pase de diapositivas'; +$string['sectionsnavigation_support'] = 'Solamente si el tema no soporta la funcionalidad "Índice de curso"'; +$string['showfromothers'] = 'Mostrar tema'; +$string['subtopictoright'] = 'Mover a la derecha como pestaña hija'; $string['tabsview'] = 'Vista de pestañas'; +$string['tabsview_default'] = 'Por defecto'; $string['tabsview_help'] = 'Por defecto: es la vista tradicional de pestañas.
Verticalmente: se muestran las pestañas al lado izquierdo de manera vertical. El contenido queda a la derecha del menú.
Una sola línea: todas las pestañas son mostradas en una sola línea, con desplazamiento horizontal si es necesario. Es útil sobre todo cuando hay demasiadas pestañas.'; -$string['tabsview_default'] = 'Por defecto'; -$string['tabsview_vertical'] = 'Verticalmente'; $string['tabsview_oneline'] = 'Una sola línea'; - -$string['increasesections'] = 'Adicionar una nueva sección después de la sección actual'; - -$string['hiddentabsbar'] = 'Las pestañas están configuradas para estar ocultas. No se verán cuando no esté en modo de edición.'; -$string['enablecustomstyles'] = 'Habilitar estilos personalizados'; -$string['enablecustomstyles_help'] = 'Habilitar color de fuente, color de fondo y otros estilos personalizados de pestañas en la configuración de la sección.'; - -$string['usessectionsnavigation'] = 'Usar navegación en secciones'; -$string['usessectionsnavigation_help'] = 'Mostrar un botón para navegar a la sección anterior y a la siguiente.'; -$string['sectionsnavigation_sitelevel'] = 'Usar el valor por defecto del sitio'; -$string['sectionsnavigation_support'] = 'Solamente si el tema no soporta la funcionalidad "Índice de curso"'; -$string['sectionsnavigation_not'] = 'No usar'; -$string['sectionsnavigation_bottom'] = 'Usar en la parte inferior'; -$string['sectionsnavigation_both'] = 'En la parte superior e inferior de la sección'; -$string['sectionsnavigation_slides'] = 'Similar a un pase de diapositivas'; -$string['enableanchorposition'] = 'Habilitar ancla de posición'; -$string['enableanchorposition_help'] = 'Usar una ancla para posicionarse en la parte superior de las pestañas cuando se haga clic en una pestaña.'; -$string['defaultsectionsnavigation'] = 'Valor por defecto para la navegación de secciones'; -$string['defaultsectionsnavigation_help'] = 'Valor por defecto a ser utilizado para definir el comportamiento de la funcionalidad "Usar navegación en secciones". Este valor puede ser sobreescrito por cada curso.'; +$string['tabsview_vertical'] = 'Verticalmente'; +$string['templatetopic'] = 'Usar resumen de tema como plantilla'; +$string['templatetopic_help'] = 'Permite usar el resumen del tema como una plantilla, de esa manera se pueden ubicar los recursos en cualquier parte del contenido, no necesariamente como listas secuenciales como se muestran tradicionalmente en Moodle.
Para ubicar un recurso, simplemente agrege en el resumen de la sección el nombre del recurso encerrado entre dobles corchetes, ejemplo: [[Foro de Novedades]]. Su comportamiento es similar al filtro por nombre de actividad con la diferencia de que se puede agregar el icono del recurso y además se puede elegir cuales recursos se muestran y cuales no.'; +$string['templatetopic_icons'] = 'Mostrar icono en enlaces de recursos en el resumen'; +$string['templatetopic_icons_help'] = 'Esta opción define si se muestran o no los iconos de los recursos como parte del nombre, cuando el resumen del tema se utiliza como plantilla.'; +$string['templetetopic_list'] = 'Si, usar el resumen como plantilla y listar los recursos no referenciados'; +$string['templetetopic_not'] = 'No, mostrar normal'; +$string['templetetopic_single'] = 'Si, usar el resumen como una plantilla'; $string['usescourseindex'] = 'Usar índice de curso'; $string['usescourseindex_help'] = 'Usar la barra lateral conocida como Índice de curso que permite la navegación a través de secciones y recursos.'; +$string['usessectionsnavigation'] = 'Usar navegación en secciones'; +$string['usessectionsnavigation_help'] = 'Mostrar un botón para navegar a la sección anterior y a la siguiente.'; +$string['utilities'] = 'Utilidades de edición de pestañas'; diff --git a/templates/courseformat/content/cm/activity_infoinline.mustache b/templates/courseformat/content/cm/activity_infoinline.mustache index 0f27ba9..af2e45e 100644 --- a/templates/courseformat/content/cm/activity_infoinline.mustache +++ b/templates/courseformat/content/cm/activity_infoinline.mustache @@ -25,7 +25,7 @@ { "activityname": "Course announcements", "hascompletion": true, - "uservisible": true, + "uservisible": false, "isautomatic": true, "showmanualcompletion": true, "completiondetails": [ From 6a67433b957afe16b90e8f9dad8593a4cd27bde2 Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 9 May 2024 00:35:29 -0500 Subject: [PATCH 40/50] Moodle 4.4 checks --- .github/workflows/moodle-ci.yml | 48 ++++++++++++++++++++------------- 1 file changed, 29 insertions(+), 19 deletions(-) diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 494e39b..470d2d4 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -32,26 +32,31 @@ jobs: fail-fast: false matrix: include: - # Moodle 4.2, PHP 8.0, PostgreSQL - - php: '8.0' # 8.0-8.2 - moodle-branch: 'MOODLE_402_STABLE' - database: pgsql - plugin-ci: ^4 - # Moodle 4.2, PHP 8.1, PostgreSQL - - php: '8.1' # 8.0-8.2 - moodle-branch: 'MOODLE_402_STABLE' + # Moodle 4.3, PHP 8.1, MariaDB + - php: '8.1' + moodle-branch: 'MOODLE_403_STABLE' database: mariadb plugin-ci: ^4 - # Moodle 4.2, PHP 8.1, PostgreSQL - - php: '8.2' # 8.0-8.2 - moodle-branch: 'MOODLE_402_STABLE' + # Moodle 4.3, PHP 8.2, PostgreSQL + - php: '8.2' + moodle-branch: 'MOODLE_403_STABLE' database: pgsql plugin-ci: ^4 - # Moodle 4.3, PHP 8.1, MySQL + # Moodle 4.4, PHP 8.1, MariaDB - php: '8.1' - moodle-branch: 'MOODLE_403_STABLE' + moodle-branch: 'MOODLE_404_STABLE' + database: mariadb + plugin-ci: ^4 + # Moodle 4.4, PHP 8.2, MariaDB + - php: '8.2' + moodle-branch: 'MOODLE_404_STABLE' database: mariadb plugin-ci: ^4 + # Moodle 4.4, PHP 8.2, PostgreSQL + - php: '8.3' + moodle-branch: 'MOODLE_404_STABLE' + database: pgsql + plugin-ci: ^4 steps: - name: Check out repository code uses: actions/checkout@v4 @@ -89,11 +94,6 @@ jobs: if: ${{ !cancelled() }} run: moodle-plugin-ci phplint - - name: PHP Copy/Paste Detector - continue-on-error: true # This step will show errors but will not fail - if: ${{ !cancelled() }} - run: moodle-plugin-ci phpcpd - - name: PHP Mess Detector continue-on-error: true # This step will show errors but will not fail if: ${{ !cancelled() }} @@ -128,9 +128,19 @@ jobs: run: moodle-plugin-ci phpunit --fail-on-warning - name: Behat features + id: behat if: ${{ !cancelled() }} run: moodle-plugin-ci behat --profile chrome + - name: Upload Behat Faildump + if: ${{ failure() && steps.behat.outcome == 'failure' }} + uses: actions/upload-artifact@v4 + with: + name: Behat Faildump (${{ join(matrix.*, ', ') }}) + path: ${{ github.workspace }}/moodledata/behat_dump + retention-days: 7 + if-no-files-found: ignore + - name: Mark cancelled jobs as failed. if: ${{ cancelled() }} - run: exit 1 + run: exit 1 \ No newline at end of file From 058503092cb819ecb87469cfc4cf1300affe75e8 Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 9 May 2024 01:45:59 -0500 Subject: [PATCH 41/50] Moodle 4.4+ compatibility --- .github/workflows/moodle-ci.yml | 15 +++---- README.md | 5 ++- classes/footer.php | 3 +- classes/header.php | 12 ++++-- .../hooks/output/before_http_headers.php | 39 +++++++++++++++++++ classes/output/courseformat/content.php | 6 +-- .../output/courseformat/content/section.php | 4 +- .../content/section/controlmenu.php | 2 +- db/hooks.php | 34 ++++++++++++++++ format.php | 4 +- lang/en/format_onetopic.php | 1 + lang/es/format_onetopic.php | 1 + lib.php | 27 +++++++------ version.php | 10 ++--- 14 files changed, 122 insertions(+), 41 deletions(-) create mode 100644 classes/local/hooks/output/before_http_headers.php create mode 100644 db/hooks.php diff --git a/.github/workflows/moodle-ci.yml b/.github/workflows/moodle-ci.yml index 470d2d4..2ee6b5b 100644 --- a/.github/workflows/moodle-ci.yml +++ b/.github/workflows/moodle-ci.yml @@ -32,16 +32,6 @@ jobs: fail-fast: false matrix: include: - # Moodle 4.3, PHP 8.1, MariaDB - - php: '8.1' - moodle-branch: 'MOODLE_403_STABLE' - database: mariadb - plugin-ci: ^4 - # Moodle 4.3, PHP 8.2, PostgreSQL - - php: '8.2' - moodle-branch: 'MOODLE_403_STABLE' - database: pgsql - plugin-ci: ^4 # Moodle 4.4, PHP 8.1, MariaDB - php: '8.1' moodle-branch: 'MOODLE_404_STABLE' @@ -52,6 +42,11 @@ jobs: moodle-branch: 'MOODLE_404_STABLE' database: mariadb plugin-ci: ^4 + # Moodle 4.4, PHP 8.3, MariaDB + - php: '8.3' + moodle-branch: 'MOODLE_404_STABLE' + database: mariadb + plugin-ci: ^4 # Moodle 4.4, PHP 8.2, PostgreSQL - php: '8.3' moodle-branch: 'MOODLE_404_STABLE' diff --git a/README.md b/README.md index c3b200d..3202f5a 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,6 @@ # COURSE FORMAT Onetopic -Package tested in: moodle 4.2+. +Package tested in: moodle 4.4+. ## QUICK INSTALL Download zip package, extract the onetopic folder and upload this folder into course/format/. @@ -16,6 +16,9 @@ Download zip package, extract the onetopic folder and upload this folder into co ## IN VERSION +### 2024050901: +* Compatibility with moodle 4.4 + ### 2024050303: * Update section control menu for Moodle 4.2 and stabilization improvements. diff --git a/classes/footer.php b/classes/footer.php index ebd918b..902a0d1 100644 --- a/classes/footer.php +++ b/classes/footer.php @@ -60,10 +60,9 @@ public function __construct(\format_onetopic $format) { * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output) { - global $COURSE, $PAGE, $CFG, $OUTPUT; $format = $this->format; - $currentsection = $this->format->get_section_number(); + $currentsection = $this->format->get_sectionnum(); $data = (object)[ 'uniqid' => $format->uniqid, diff --git a/classes/header.php b/classes/header.php index 96ac0a8..73a0e8e 100644 --- a/classes/header.php +++ b/classes/header.php @@ -67,7 +67,7 @@ public function export_for_template(\renderer_base $output) { $course->realcoursedisplay = property_exists($course, 'coursedisplay') ? $course->coursedisplay : false; $firstsection = ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; - $currentsection = $this->format->get_section_number(); + $currentsection = $this->format->get_sectionnum(); $tabslist = []; $secondtabslist = null; @@ -148,7 +148,9 @@ public function export_for_template(\renderer_base $output) { ]; // Include course format js module. - $PAGE->requires->js('/course/format/topics/format.js'); +// $PAGE->requires->js('/course/format/topics/format.js'); + $PAGE->requires->js_call_amd('format_topics/mutations', 'init'); + $PAGE->requires->js_call_amd('format_topics/section', 'init'); $PAGE->requires->js('/course/format/onetopic/format.js'); $PAGE->requires->yui_module('moodle-core-notification-dialogue', 'M.course.format.dialogueinit'); $PAGE->requires->js_call_amd('format_onetopic/main', 'init', $params); @@ -169,7 +171,11 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for if ($section && $section > 0) { $displaysection = $section; } else { - $displaysection = $this->format->get_section_number(); + $displaysection = $this->format->get_sectionnum(); + } + + if ($displaysection === null) { + $displaysection = 0; } $course = $this->format->get_course(); diff --git a/classes/local/hooks/output/before_http_headers.php b/classes/local/hooks/output/before_http_headers.php new file mode 100644 index 0000000..24f33f0 --- /dev/null +++ b/classes/local/hooks/output/before_http_headers.php @@ -0,0 +1,39 @@ +. + +namespace format_onetopic\local\hooks\output; + +/** + * Hook callbacks for format_onetopic + * + * @package format_onetopic + * @copyright 2024 David Herney @ BambuCo + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class before_http_headers { + + /** + * Moodle native lib/navigationlib.php calls this hook allowing us to override UI. + * + * @param \core\hook\output\before_http_headers $hook + */ + public static function callback(\core\hook\output\before_http_headers $hook): void { + $renderer = $hook->renderer; + + global $PAGE; + $PAGE->requires->css('/course/format/onetopic/styles.php'); + } +} diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index e24da3c..246af67 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -61,14 +61,14 @@ public function get_template_name(\renderer_base $renderer): string { /** * Export this data so it can be used as the context for a mustache template (core/inplace_editable). * - * @param renderer_base $output typically, the renderer that's calling this function + * @param \renderer_base $output typically, the renderer that's calling this function * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output) { global $PAGE; $format = $this->format; $course = $format->get_course(); - $currentsection = $this->format->get_section_number(); + $currentsection = $this->format->get_sectionnum(); // If format use the section 0 as a separate section so remove from the list. $sections = $this->export_sections($output); @@ -181,7 +181,7 @@ protected function export_sections(\renderer_base $output): array { */ private function get_sections_to_display(course_modinfo $modinfo): array { $sections = []; - $singlesection = $this->format->get_section_number(); + $singlesection = $this->format->get_sectionnum(); $sections[] = $modinfo->get_section_info($singlesection); return $sections; diff --git a/classes/output/courseformat/content/section.php b/classes/output/courseformat/content/section.php index 7fb0b74..183de25 100644 --- a/classes/output/courseformat/content/section.php +++ b/classes/output/courseformat/content/section.php @@ -43,7 +43,7 @@ class section extends section_base { /** * Export this data so it can be used as the context for a mustache template. * - * @param renderer_base $output typically, the renderer that's calling this function + * @param \renderer_base $output typically, the renderer that's calling this function * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output): stdClass { @@ -58,7 +58,7 @@ public function export_for_template(\renderer_base $output): stdClass { $data = (object)[ 'num' => $section->section ?? '0', 'id' => $section->id, - 'sectionreturnid' => $format->get_section_number(), + 'sectionreturnid' => $format->get_sectionnum(), 'insertafter' => false, 'summary' => $summary->export_for_template($output), 'highlightedlabel' => $format->get_section_highlighted_name(), diff --git a/classes/output/courseformat/content/section/controlmenu.php b/classes/output/courseformat/content/section/controlmenu.php index b6189b3..c2ddce7 100644 --- a/classes/output/courseformat/content/section/controlmenu.php +++ b/classes/output/courseformat/content/section/controlmenu.php @@ -55,7 +55,7 @@ public function section_control_items() { $format = $this->format; $section = $this->section; $course = $format->get_course(); - $sectionreturn = $format->get_section_number(); + $sectionreturn = $format->get_sectionnum(); $coursecontext = context_course::instance($course->id); $numsections = $format->get_last_section_number(); diff --git a/db/hooks.php b/db/hooks.php new file mode 100644 index 0000000..de29fac --- /dev/null +++ b/db/hooks.php @@ -0,0 +1,34 @@ +. + +/** + * Hook callbacks for Onetopic format + * + * @package format_onetopic + * @copyright 2024 2024 David Herney @ BambuCo + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +defined('MOODLE_INTERNAL') || die(); + +$callbacks = [ + + [ + 'hook' => core\hook\output\before_http_headers::class, + 'callback' => 'format_onetopic\local\hooks\output\before_http_headers::callback', + 'priority' => 0, + ], +]; diff --git a/format.php b/format.php index 2cfa24c..5438eee 100644 --- a/format.php +++ b/format.php @@ -67,8 +67,8 @@ } } -if (!empty($displaysection)) { - $format->set_section_number($displaysection); +if (!is_null($displaysection)) { + $format->set_sectionnum($displaysection); } $outputclass = $format->get_output_classname('content'); diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 043a50c..e17528d 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -111,6 +111,7 @@ $string['page-course-view-topics'] = 'Any course main page in onetopic format'; $string['page-course-view-topics-x'] = 'Any course page in onetopic format'; $string['pluginname'] = 'Onetopic format'; +$string['plugin_description'] = 'Course sections are displayed separately in tabs.'; $string['privacy:metadata'] = 'The Onetopic format plugin does not store any personal data.'; $string['progress_counter'] = 'Duplicating activities ({$a->current}/{$a->size})'; $string['progress_full'] = 'Duplicating topic'; diff --git a/lang/es/format_onetopic.php b/lang/es/format_onetopic.php index d45f3a7..19a5293 100644 --- a/lang/es/format_onetopic.php +++ b/lang/es/format_onetopic.php @@ -71,6 +71,7 @@ $string['page-course-view-topics'] = 'Alguna página principal de curso en formato onetopic'; $string['page-course-view-topics-x'] = 'Alguna página de curso en formato onetopic'; $string['pluginname'] = 'Temas en pestañas'; +$string['plugin_description'] = 'Las secciones del curso se muestran separadas en pestañas.'; $string['privacy:metadata'] = 'El formato Temas en pestañas no almacena datos personales.'; $string['progress_counter'] = 'Duplicando actividades ({$a->current}/{$a->size})'; $string['progress_full'] = 'Duplicando el tema'; diff --git a/lib.php b/lib.php index b12a5fe..aa09eb2 100644 --- a/lib.php +++ b/lib.php @@ -284,6 +284,17 @@ public function get_section_name($section) { } } + /** + * Get the current section number to display. + * Some formats has the hability to swith from one section to multiple sections per page. + * + * @since Moodle 4.4 + * @return int|null the current section number or null when there is no single section. + */ + public function get_sectionnum(): ?int { + return $this->singlesection == null ? 0 : $this->singlesection; + } + /** * Returns the default section name for the topics course format. * @@ -311,7 +322,7 @@ public function get_default_section_name($section) { * @return string the page title */ public function page_title(): string { - return get_string('topicoutline'); + return get_string('sectionoutline'); } /** @@ -846,7 +857,7 @@ public function can_delete_section($section) { * @param moodle_page $page instance of page calling set_cm */ public function page_set_cm(moodle_page $page) { - $this->set_section_number($page->cm->sectionnum); + $this->set_sectionnum($page->cm->sectionnum); } /** @@ -892,11 +903,11 @@ public function course_content_footer() { public function inplace_editable_render_section_name($section, $linkifneeded = true, $editable = null, $edithint = null, $editlabel = null) { if (empty($edithint)) { - $edithint = new lang_string('editsectionname', 'format_topics'); + $edithint = new lang_string('editsectionname'); } if (empty($editlabel)) { $title = get_section_name($section->course, $section); - $editlabel = new lang_string('newsectionname', 'format_topics', $title); + $editlabel = new lang_string('newsectionname', 'core', $title); } return parent::inplace_editable_render_section_name($section, $linkifneeded, $editable, $edithint, $editlabel); } @@ -1049,14 +1060,6 @@ public function show_editor(?array $capabilities = ['moodle/course:manageactivit } -/** - * Moodle native lib/navigationlib.php calls this hook allowing us to override UI. - */ -function format_onetopic_before_http_headers() { - global $PAGE; - $PAGE->requires->css('/course/format/onetopic/styles.php'); -} - /** * Implements callback inplace_editable() allowing to edit values in-place. * diff --git a/version.php b/version.php index b8372e6..2f53bbd 100644 --- a/version.php +++ b/version.php @@ -33,9 +33,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050303; // The current plugin version (Date: YYYYMMDDXX). -$plugin->requires = 2023041800; // Requires this Moodle version. +$plugin->version = 2024050900.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->requires = 2024041600; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). -$plugin->maturity = MATURITY_STABLE; -$plugin->release = '4.2.03(ElCardal)'; -$plugin->dependencies = ['format_topics' => 2023042400]; +$plugin->maturity = MATURITY_BETA; +$plugin->release = '4.4.01(LasAcacias)'; +$plugin->dependencies = ['format_topics' => 2024042200]; From 895be0fb9e149904cfc0d95be42cff638eed7ac8 Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 9 May 2024 03:41:27 -0500 Subject: [PATCH 42/50] Moodle 4.4+ stabilization --- classes/courseformat/stateactions.php | 30 ++++++++++++++ classes/header.php | 1 - .../output/courseformat/content/section.php | 3 +- .../content/section/controlmenu.php | 8 ---- lang/en/format_onetopic.php | 2 +- lang/es/format_onetopic.php | 2 +- lib.php | 13 ++++++ styles.css | 4 ++ .../local/content/section/content.mustache | 34 ++++++++++----- tests/behat/edit_delete_sections.feature | 41 +++++++++++-------- version.php | 8 ++-- 11 files changed, 103 insertions(+), 43 deletions(-) create mode 100644 classes/courseformat/stateactions.php diff --git a/classes/courseformat/stateactions.php b/classes/courseformat/stateactions.php new file mode 100644 index 0000000..a30e444 --- /dev/null +++ b/classes/courseformat/stateactions.php @@ -0,0 +1,30 @@ +. + +namespace format_onetopic\courseformat; + +use format_topics\courseformat\stateactions as stateactions_format_topics; + +/** + * Contains the core course state actions specific to topics format. + * + * @package format_onetopic + * @copyright 2024 David Herney - cirano. https://bambuco.co + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class stateactions extends stateactions_format_topics { + +} diff --git a/classes/header.php b/classes/header.php index 73a0e8e..9436de0 100644 --- a/classes/header.php +++ b/classes/header.php @@ -148,7 +148,6 @@ public function export_for_template(\renderer_base $output) { ]; // Include course format js module. -// $PAGE->requires->js('/course/format/topics/format.js'); $PAGE->requires->js_call_amd('format_topics/mutations', 'init'); $PAGE->requires->js_call_amd('format_topics/section', 'init'); $PAGE->requires->js('/course/format/onetopic/format.js'); diff --git a/classes/output/courseformat/content/section.php b/classes/output/courseformat/content/section.php index 183de25..f03af17 100644 --- a/classes/output/courseformat/content/section.php +++ b/classes/output/courseformat/content/section.php @@ -47,7 +47,7 @@ class section extends section_base { * @return stdClass data context for a mustache template */ public function export_for_template(\renderer_base $output): stdClass { - global $USER, $PAGE; + global $PAGE; $format = $this->format; $course = $format->get_course(); @@ -64,6 +64,7 @@ public function export_for_template(\renderer_base $output): stdClass { 'highlightedlabel' => $format->get_section_highlighted_name(), 'sitehome' => $course->id == SITEID, 'editing' => $PAGE->user_is_editing(), + 'displayonesection' => ($course->id != SITEID && !is_null($format->get_sectionid())), ]; $haspartials = []; diff --git a/classes/output/courseformat/content/section/controlmenu.php b/classes/output/courseformat/content/section/controlmenu.php index c2ddce7..025d199 100644 --- a/classes/output/courseformat/content/section/controlmenu.php +++ b/classes/output/courseformat/content/section/controlmenu.php @@ -68,8 +68,6 @@ public function section_control_items() { } $url->param('sesskey', sesskey()); - $othercontrols = []; - $movecontrols = []; if ($section->section && !$isstealth && has_capability('moodle/course:movesections', $coursecontext, $USER)) { $baseurl = course_get_url($course); @@ -136,8 +134,6 @@ public function section_control_items() { $visibilitycontrolexists = array_key_exists("visibility", $parentcontrols); if (!$editcontrolexists) { - $merged = array_merge($merged, $othercontrols); - if (!$visibilitycontrolexists) { $merged = array_merge($merged, $movecontrols); } @@ -147,10 +143,6 @@ public function section_control_items() { // Step through the array and merge the arrays. foreach ($parentcontrols as $key => $action) { $merged[$key] = $action; - if ($key == "edit") { - // If we have come to the edit key, merge these controls here. - $merged = array_merge($merged, $othercontrols); - } if (($key == "edit" && !$visibilitycontrolexists) || $key == "visibility") { $merged = array_merge($merged, $movecontrols); diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index e17528d..655f5d5 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -110,8 +110,8 @@ $string['movesectionto_help'] = 'Move current topic to left/right of selected topic'; $string['page-course-view-topics'] = 'Any course main page in onetopic format'; $string['page-course-view-topics-x'] = 'Any course page in onetopic format'; -$string['pluginname'] = 'Onetopic format'; $string['plugin_description'] = 'Course sections are displayed separately in tabs.'; +$string['pluginname'] = 'Onetopic format'; $string['privacy:metadata'] = 'The Onetopic format plugin does not store any personal data.'; $string['progress_counter'] = 'Duplicating activities ({$a->current}/{$a->size})'; $string['progress_full'] = 'Duplicating topic'; diff --git a/lang/es/format_onetopic.php b/lang/es/format_onetopic.php index 19a5293..e6a55d4 100644 --- a/lang/es/format_onetopic.php +++ b/lang/es/format_onetopic.php @@ -70,8 +70,8 @@ $string['movesectionto_help'] = 'Mover el tema actual antes de (para temas a la izquierda del actual) o después de (para temas a la derecha del actual) el tema que seleccione'; $string['page-course-view-topics'] = 'Alguna página principal de curso en formato onetopic'; $string['page-course-view-topics-x'] = 'Alguna página de curso en formato onetopic'; -$string['pluginname'] = 'Temas en pestañas'; $string['plugin_description'] = 'Las secciones del curso se muestran separadas en pestañas.'; +$string['pluginname'] = 'Temas en pestañas'; $string['privacy:metadata'] = 'El formato Temas en pestañas no almacena datos personales.'; $string['progress_counter'] = 'Duplicando actividades ({$a->current}/{$a->size})'; $string['progress_full'] = 'Duplicando el tema'; diff --git a/lib.php b/lib.php index aa09eb2..3928963 100644 --- a/lib.php +++ b/lib.php @@ -316,6 +316,19 @@ public function get_default_section_name($section) { } } + /** + * Get if the current format instance will show multiple sections or an individual one. + * + * Some formats has the hability to swith from one section to multiple sections per page, + * output components will use this method to know if the current display is a single or + * multiple sections. + * + * @return int|null null for all sections or the sectionid. + */ + public function get_sectionid(): ?int { + return null; + } + /** * Generate the title for this section page. * diff --git a/styles.css b/styles.css index 1396375..11c29b4 100644 --- a/styles.css +++ b/styles.css @@ -1,5 +1,9 @@ /** Styles included in topics course format */ +.format-onetopic ul.onetopic { + padding: 0; +} + .format-onetopic .format_onetopic-tabs .nav-link { white-space: nowrap; width: 100%; diff --git a/templates/local/content/section/content.mustache b/templates/local/content/section/content.mustache index 0f01f3c..14297db 100644 --- a/templates/local/content/section/content.mustache +++ b/templates/local/content/section/content.mustache @@ -85,10 +85,31 @@ "highlightedlabel" : "Highlighted" } }} +{{#restrictionlock}} +
+ {{#pix}}t/unlock, core{{/pix}} +
+{{/restrictionlock}} +{{#collapsemenu}} + {{^displayonesection}} + + {{/displayonesection}} +{{/collapsemenu}} +
+ class="content {{^iscoursedisplaymultipage}}{{^sitehome}}{{^displayonesection}}course-content-item-content collapse {{^contentcollapsed}}show{{/contentcollapsed}}{{/displayonesection}}{{/sitehome}}{{/iscoursedisplaymultipage}}">
{{#summary}} {{$ core_courseformat/local/content/section/summary }} @@ -112,11 +133,4 @@ {{/ core_courseformat/local/content/section/cmlist }} {{/cmlist}} {{{cmcontrols}}} - {{#insertafter}} - {{#numsections}} - {{$ core_courseformat/local/content/addsection}} - {{> core_courseformat/local/content/addsection}} - {{/ core_courseformat/local/content/addsection}} - {{/numsections}} - {{/insertafter}}
\ No newline at end of file diff --git a/tests/behat/edit_delete_sections.feature b/tests/behat/edit_delete_sections.feature index 22f9527..1250b6e 100644 --- a/tests/behat/edit_delete_sections.feature +++ b/tests/behat/edit_delete_sections.feature @@ -25,32 +25,30 @@ Feature: Sections can be edited and deleted in Onetopic format Scenario: View the default name of the general section in Onetopic format When I edit the section "0" - Then the field "Custom" matches value "0" - And the field "New value for Section name" matches value "General" + Then the field "Section name" matches value "" + And I should see "General" Scenario: Edit the default name of the general section in Onetopic format When I edit the section "0" and I fill the form with: - | Custom | 1 | - | New value for Section name | This is the general section | + | Section name | This is the general section | Then I should see "This is the general section" in the ".format_onetopic-tabs .tab_position_0 .nav-link.active" "css_element" Scenario: View the default name of the second section in Onetopic format When I click on "Topic 2" "link" in the "#page-content ul.nav.nav-tabs" "css_element" And I edit the section "2" - Then the field "Custom" matches value "0" - And the field "New value for Section name" matches value "Topic 2" + Then the field "Section name" matches value "" + And I should see "Topic 2" - Scenario: Edit section summary in Onetopic format + Scenario: Edit section description in Onetopic format When I click on "Topic 2" "link" in the "#page-content ul.nav.nav-tabs" "css_element" And I edit the section "2" and I fill the form with: - | Summary | Welcome to section 2 | + | Description | Welcome to section 2 | Then I should see "Welcome to section 2" in the "#page-content li#section-2" "css_element" Scenario: Edit section default name in Onetopic format When I click on "Topic 2" "link" in the "#page-content ul.nav.nav-tabs" "css_element" And I edit the section "2" and I fill the form with: - | Custom | 1 | - | New value for Section name | This is the second topic | + | Section name | This is the second topic | Then I should see "This is the second topic" in the ".format_onetopic-tabs .tab_position_2 .nav-link.active" "css_element" And I should not see "Topic 2" in the ".format_onetopic-tabs .tab_position_2 .nav-link.active" "css_element" @@ -63,15 +61,16 @@ Feature: Sections can be edited and deleted in Onetopic format And I should see "Topic 4" Scenario: Deleting the middle section in Onetopic format - When I click on "Topic 4" "link" in the "#page-content ul.nav.nav-tabs" "css_element" - And I delete section "4" + When I click on "Topic 3" "link" in the "#page-content ul.nav.nav-tabs" "css_element" + And I delete section "3" + Then I should see "Are you absolutely sure you want to completely delete \"Topic 3\" and all the activities it contains?" And I press "Delete" - Then I should not see "Topic 5" + And I should not see "Topic 5" And I should see "Topic 3" in the ".format_onetopic-tabs .tab_position_3 .nav-link.active" "css_element" - And I click on "Topic 4" "link" in the "#page-content ul.nav.nav-tabs" "css_element" - And I should not see "Test chat name" - And I should see "Test choice name" in the "#page-content li#section-4" "css_element" - And I should see "Topic 4" + And I click on "Topic 3" "link" in the "#page-content ul.nav.nav-tabs" "css_element" + And I should not see "Test book name" + And I should see "Test chat name" in the "#page-content li#section-3" "css_element" + And I should see "Topic 3" Scenario: Adding a section in Onetopic format When I follow "Add a section after the currently selected section" @@ -86,3 +85,11 @@ Feature: Sections can be edited and deleted in Onetopic format Then I should see "Topic 6" And I should not see "Test choice name" in the "#page-content li#section-5" "css_element" And ".format_onetopic-tabs .tab_position_7 .nav-link" "css_element" should not exist + + @javascript + Scenario: Copy section permalink URL to clipboard + Given I am on "Course 1" course homepage with editing mode on + When I open section "1" edit menu + And I click on "Permalink" "link" in the "Section 1" "section" + And I click on "Copy to clipboard" "link" in the "Permalink" "dialogue" + Then I should see "Text copied to clipboard" diff --git a/version.php b/version.php index 2f53bbd..f28ff95 100644 --- a/version.php +++ b/version.php @@ -21,19 +21,19 @@ * Un recorderis de las Veredas de mi pueblo, en homenaje a los campesinos de mi tierra. * * Old releases: Guarango, Pantalio, Chalarca, Mazorcal, Chuscalito, Las Teresas, La Madera, Las Brisas, Buenavista, - * San Juan, La Almería, Piedras Teherán + * San Juan, La Almería, Piedras Teherán, El Cardal. * - * Next releases: El Cardal, Santa Cruz, Vallejuelito, Fátima, La Cabaña, La Palmera, Las Acacias, Las Colmenas, Minitas, + * Next releases: Santa Cruz, Vallejuelito, Fátima, La Cabaña, La Palmera, Las Acacias, Las Colmenas, Minitas, * Quebrada Negra, San Francisco, San Miguel Abajo, San Miguel, La Concha, La Divisa * * @package format_onetopic - * @copyright 2015 David Herney Bernal - cirano. https://bambuco.co + * @copyright 2015 David Herney - cirano. https://bambuco.co * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050900.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050900.04; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2024041600; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_BETA; From 04a954ebc13a01978a355577c39754b7bc27cd7f Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 9 May 2024 04:10:24 -0500 Subject: [PATCH 43/50] Behat test changes --- tests/behat/edit_delete_sections.feature | 22 +++++++++++----------- 1 file changed, 11 insertions(+), 11 deletions(-) diff --git a/tests/behat/edit_delete_sections.feature b/tests/behat/edit_delete_sections.feature index 1250b6e..aba447a 100644 --- a/tests/behat/edit_delete_sections.feature +++ b/tests/behat/edit_delete_sections.feature @@ -2,7 +2,7 @@ Feature: Sections can be edited and deleted in Onetopic format In order to rearrange my course contents As a teacher - I need to edit and Delete topics + I need to edit and delete topics Background: Given the following "users" exist: @@ -15,7 +15,7 @@ Feature: Sections can be edited and deleted in Onetopic format | activity | name | intro | course | idnumber | section | | assign | Test assignment name | Test assignment description | C1 | assign1 | 0 | | book | Test book name | Test book description | C1 | book1 | 1 | - | chat | Test chat name | Test chat description | C1 | chat1 | 4 | + | lesson | Test lesson name | Test lesson description | C1 | lesson1 | 4 | | choice | Test choice name | Test choice description | C1 | choice1 | 5 | And the following "course enrolments" exist: | user | course | role | @@ -61,16 +61,16 @@ Feature: Sections can be edited and deleted in Onetopic format And I should see "Topic 4" Scenario: Deleting the middle section in Onetopic format - When I click on "Topic 3" "link" in the "#page-content ul.nav.nav-tabs" "css_element" - And I delete section "3" - Then I should see "Are you absolutely sure you want to completely delete \"Topic 3\" and all the activities it contains?" + When I click on "Topic 4" "link" in the "#page-content ul.nav.nav-tabs" "css_element" + And I delete section "4" + Then I should see "Are you absolutely sure you want to completely delete \"Topic 4\" and all the activities it contains?" And I press "Delete" And I should not see "Topic 5" And I should see "Topic 3" in the ".format_onetopic-tabs .tab_position_3 .nav-link.active" "css_element" - And I click on "Topic 3" "link" in the "#page-content ul.nav.nav-tabs" "css_element" - And I should not see "Test book name" - And I should see "Test chat name" in the "#page-content li#section-3" "css_element" - And I should see "Topic 3" + And I click on "Topic 4" "link" in the "#page-content ul.nav.nav-tabs" "css_element" + And I should not see "Test lesson name" + And I should see "Test choice name" in the "#page-content li#section-4" "css_element" + And I should see "Topic 4" Scenario: Adding a section in Onetopic format When I follow "Add a section after the currently selected section" @@ -88,8 +88,8 @@ Feature: Sections can be edited and deleted in Onetopic format @javascript Scenario: Copy section permalink URL to clipboard - Given I am on "Course 1" course homepage with editing mode on - When I open section "1" edit menu + When I click on "Topic 1" "link" in the "#page-content ul.nav.nav-tabs" "css_element" + And I open section "1" edit menu And I click on "Permalink" "link" in the "Section 1" "section" And I click on "Copy to clipboard" "link" in the "Permalink" "dialogue" Then I should see "Text copied to clipboard" From cfd1a0afdc63cdfbc3f99ce88768cd133d356ef1 Mon Sep 17 00:00:00 2001 From: David Herney Date: Sat, 11 May 2024 17:54:16 -0500 Subject: [PATCH 44/50] Behat test tuning --- tests/behat/edit_delete_sections.feature | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/behat/edit_delete_sections.feature b/tests/behat/edit_delete_sections.feature index aba447a..8b3124c 100644 --- a/tests/behat/edit_delete_sections.feature +++ b/tests/behat/edit_delete_sections.feature @@ -90,6 +90,6 @@ Feature: Sections can be edited and deleted in Onetopic format Scenario: Copy section permalink URL to clipboard When I click on "Topic 1" "link" in the "#page-content ul.nav.nav-tabs" "css_element" And I open section "1" edit menu - And I click on "Permalink" "link" in the "Section 1" "section" + And I click on "Permalink" "link" And I click on "Copy to clipboard" "link" in the "Permalink" "dialogue" Then I should see "Text copied to clipboard" From d14c8f14440dd44c8ea961752caf9dba99506d1e Mon Sep 17 00:00:00 2001 From: David Herney Date: Thu, 16 May 2024 00:00:53 -0500 Subject: [PATCH 45/50] Fixed: Duplication of activitiy in section 0 #154 - M 4.4+ --- classes/output/courseformat/content.php | 12 ++++++++++-- classes/output/courseformat/content/section.php | 9 +++++++++ lib.php | 15 +++++++++++---- version.php | 2 +- 4 files changed, 31 insertions(+), 7 deletions(-) diff --git a/classes/output/courseformat/content.php b/classes/output/courseformat/content.php index 246af67..0f9f2b0 100644 --- a/classes/output/courseformat/content.php +++ b/classes/output/courseformat/content.php @@ -128,7 +128,7 @@ public function export_for_template(\renderer_base $output) { /** * Export sections array data. * - * @param renderer_base $output typically, the renderer that's calling this function + * @param \renderer_base $output typically, the renderer that's calling this function * @return array data context for a mustache template */ protected function export_sections(\renderer_base $output): array { @@ -137,11 +137,14 @@ protected function export_sections(\renderer_base $output): array { $course = $format->get_course(); $modinfo = $this->format->get_modinfo(); + $realcoursedisplay = property_exists($course, 'realcoursedisplay') ? $course->realcoursedisplay : false; + $firstsectionastab = ($realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; + // Generate section list. $sections = []; $stealthsections = []; $numsections = $format->get_last_section_number(); - foreach ($this->get_sections_to_display($modinfo) as $sectionnum => $thissection) { + foreach ($this->get_sections_to_display($modinfo) as $thissection) { // The course/view.php check the section existence but the output can be called // from other parts so we need to check it. if (!$thissection) { @@ -149,6 +152,11 @@ protected function export_sections(\renderer_base $output): array { } $section = new $this->sectionclass($format, $thissection); + $sectionnum = $section->get_sectionnum(); + + if ($sectionnum === 0 && $firstsectionastab) { + continue; + } if ($sectionnum > $numsections) { // Activities inside this section are 'orphaned', this section will be printed as 'stealth' below. diff --git a/classes/output/courseformat/content/section.php b/classes/output/courseformat/content/section.php index f03af17..65c8f5e 100644 --- a/classes/output/courseformat/content/section.php +++ b/classes/output/courseformat/content/section.php @@ -77,4 +77,13 @@ public function export_for_template(\renderer_base $output): stdClass { return $data; } + + /** + * Get the section number. + * + * @return int + */ + public function get_sectionnum() { + return $this->section->section; + } } diff --git a/lib.php b/lib.php index 3928963..a7633b2 100644 --- a/lib.php +++ b/lib.php @@ -186,16 +186,20 @@ protected function __construct($format, $courseid) { } if ($course->realcoursedisplay == COURSE_DISPLAY_MULTIPAGE && $realsection === 0 && $numsections >= 1) { - $realsection = 1; + $realsection = null; } $modinfo = get_fast_modinfo($course); $sections = $modinfo->get_section_info_all(); // Check if the display section is available. - if (!$sections[$realsection]->uservisible) { + if ($realsection === null || !$sections[$realsection]->uservisible) { - self::$formatmsgs[] = get_string('hidden_message', 'format_onetopic', $this->get_section_name($realsection)); + if ($realsection) { + self::$formatmsgs[] = get_string('hidden_message', + 'format_onetopic', + $this->get_section_name($realsection)); + } $valid = false; $k = $course->realcoursedisplay ? 1 : 0; @@ -214,7 +218,10 @@ protected function __construct($format, $courseid) { $realsection = $valid ? $k : 0; } + $realsection = $realsection ?? 0; + // The $section var is a global var, we need to set it to the real section. $section = $realsection; + $this->set_sectionnum($section); $USER->display[$course->id] = $realsection; $urlparams['section'] = $realsection; $PAGE->set_url('/course/view.php', $urlparams); @@ -1008,7 +1015,7 @@ public function fot_get_sections_extra() { } $course = $this->get_course(); - $realcoursedisplay = property_exists($course, 'coursedisplay') ? $course->coursedisplay : false; + $realcoursedisplay = property_exists($course, 'realcoursedisplay') ? $course->realcoursedisplay : false; $firstsection = ($realcoursedisplay == COURSE_DISPLAY_MULTIPAGE) ? 1 : 0; $sections = $this->get_sections(); $parentsections = []; diff --git a/version.php b/version.php index f28ff95..0716221 100644 --- a/version.php +++ b/version.php @@ -33,7 +33,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050900.04; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050901; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2024041600; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_BETA; From 3f2ba2dcb5f6d2a1a2dcbee9fa0c65225be8de54 Mon Sep 17 00:00:00 2001 From: David Herney Date: Fri, 19 Jul 2024 01:51:24 -0500 Subject: [PATCH 46/50] upgrade activityinformation --- .../courseformat/content/section/summary.php | 6 +-- .../content/cm/cmiconinline.mustache | 41 +++++++++++++++++++ .../content/cm/cmnameinline.mustache | 11 +++-- 3 files changed, 51 insertions(+), 7 deletions(-) create mode 100644 templates/courseformat/content/cm/cmiconinline.mustache diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index bdc0546..ad1fb79 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -185,9 +185,9 @@ private function replace_resources(section_info $section) { $cmdata->uniqueid = 'cm_' . $mod->id . '_' . time() . '_' . rand(0, 1000); $cmdata->singlename = $instancename; - $cmdata->showinlinehelp = $cmdata->activityinfo->hascompletion - || $cmdata->activityinfo->hasdates - || !empty($cmdata->altcontent); + // ToDo: Implement additional activity information. Now it's called "activity badge". + $cmdata->showinlinehelp = false; + $url = $mod->url; if (empty($url)) { // If there is content but NO link (like label), then don't display it. diff --git a/templates/courseformat/content/cm/cmiconinline.mustache b/templates/courseformat/content/cm/cmiconinline.mustache new file mode 100644 index 0000000..c4e598f --- /dev/null +++ b/templates/courseformat/content/cm/cmiconinline.mustache @@ -0,0 +1,41 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/courseformat/content/cm/cmiconinline + + Displays a course module icon. + + Example context (json): + { + "icon": "../../../pix/help.svg", + "iconclass": "", + "purpose": "content", + "modname": "resource", + "pluginname": "File", + "showtooltip": 1 + } +}} + + {{#showtooltip}}{{#cleanstr}} activityicon, moodle, {{{pluginname}}} {{/cleanstr}}{{/showtooltip}} + diff --git a/templates/courseformat/content/cm/cmnameinline.mustache b/templates/courseformat/content/cm/cmnameinline.mustache index 5deb1c3..3361ccd 100644 --- a/templates/courseformat/content/cm/cmnameinline.mustache +++ b/templates/courseformat/content/cm/cmnameinline.mustache @@ -15,7 +15,7 @@ along with Moodle. If not, see . }} {{! - @template format_onetopic/courseformat/content/cm/cmname + @template format_onetopic/courseformat/content/cm/cmnameinline Convenience mustache to displays a course module inplcae editable from the format renderer. @@ -46,9 +46,12 @@ {{#url}} {{^hideicons}} - - {{{modname}}} icon - + {{! Icon }} + {{#activityicon}} + {{$ format_onetopic/courseformat/content/cm/cmiconinline }} + {{> format_onetopic/courseformat/content/cm/cmiconinline }} + {{/ format_onetopic/courseformat/content/cm/cmiconinline }} + {{/activityicon}} {{/hideicons}} {{#activityname}} From 62a88a5118ff01b436c53def6dee7884aef7450e Mon Sep 17 00:00:00 2001 From: David Herney Date: Sat, 20 Jul 2024 14:56:14 -0500 Subject: [PATCH 47/50] Includes SCORM player scope as a site-level configuration option. --- classes/privacy/provider.php | 1 + lang/en/format_onetopic.php | 3 ++- lang/es/format_onetopic.php | 4 ++++ lib.php | 10 ++++++++++ settings.php | 1 + version.php | 2 +- 6 files changed, 19 insertions(+), 2 deletions(-) diff --git a/classes/privacy/provider.php b/classes/privacy/provider.php index fa1814d..7ced1dd 100644 --- a/classes/privacy/provider.php +++ b/classes/privacy/provider.php @@ -20,6 +20,7 @@ * @copyright 2019 David Herney Bernal - cirano * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ + namespace format_onetopic\privacy; /** diff --git a/lang/en/format_onetopic.php b/lang/en/format_onetopic.php index 655f5d5..92a10db 100644 --- a/lang/en/format_onetopic.php +++ b/lang/en/format_onetopic.php @@ -74,7 +74,7 @@ $string['cssweightlighter'] = 'Lighter'; $string['currentsection'] = 'This topic'; $string['defaultscope'] = 'Default scope'; -$string['defaultscope_help'] = 'Default scope used to define the pages on which the tab menu is printed.'; +$string['defaultscope_help'] = 'Default scope used to define the pages on which the tab menu is printed. The SCORM Player scope require the Modules scope.'; $string['defaultsectionsnavigation'] = 'Default value to sections navigation'; $string['defaultsectionsnavigation_help'] = 'Default value used in courses to define the "Uses sections navigation" feature. This can be overwrite for each course.'; $string['disable'] = 'Disable'; @@ -117,6 +117,7 @@ $string['progress_full'] = 'Duplicating topic'; $string['rebuild_course_cache'] = 'Rebuild course cache'; $string['scope_mod'] = 'Modules'; +$string['scope_scorm'] = 'SCORM Player'; $string['sectionname'] = 'Topic'; $string['sectionsnavigation_both'] = 'At top and bottom section'; $string['sectionsnavigation_bottom'] = 'Only at the bottom'; diff --git a/lang/es/format_onetopic.php b/lang/es/format_onetopic.php index e6a55d4..8436115 100644 --- a/lang/es/format_onetopic.php +++ b/lang/es/format_onetopic.php @@ -36,6 +36,8 @@ $string['cssstyles'] = 'Propiedades CSS'; $string['cssstyles_help'] = 'Sirve para cambiar las propiedades CSS de la pestaña. Utilice el formato tradicional del atributo style de una etiqueta html. Ejemplo:
font-weight: bold; font-size: 16px;'; $string['currentsection'] = 'Este tema'; +$string['defaultscope'] = 'Alcance predeterminado'; +$string['defaultscope_help'] = 'Alcance predeterminado utilizado para definir las páginas adicionales en las que se imprime el menú de pestañas. El alcance del Reproductor SCORM requiere el alcance de los Módulos.'; $string['defaultsectionsnavigation'] = 'Valor por defecto para la navegación de secciones'; $string['defaultsectionsnavigation_help'] = 'Valor por defecto a ser utilizado para definir el comportamiento de la funcionalidad "Usar navegación en secciones". Este valor puede ser sobreescrito por cada curso.'; $string['disable'] = 'Deshabilitar'; @@ -76,6 +78,8 @@ $string['progress_counter'] = 'Duplicando actividades ({$a->current}/{$a->size})'; $string['progress_full'] = 'Duplicando el tema'; $string['rebuild_course_cache'] = 'Recreando el caché del curso'; +$string['scope_mod'] = 'Módulos'; +$string['scope_scorm'] = 'Reproductor de SCORM'; $string['sectionname'] = 'Tema'; $string['sectionsnavigation_both'] = 'En la parte superior e inferior de la sección'; $string['sectionsnavigation_bottom'] = 'Usar en la parte inferior'; diff --git a/lib.php b/lib.php index a7633b2..4307b86 100644 --- a/lib.php +++ b/lib.php @@ -80,6 +80,9 @@ class format_onetopic extends core_courseformat\base { /** @var string Course modules scope */ const SCOPE_MOD = 'mod'; + /** @var string Scorm modules scope */ + const SCOPE_SCORM = 'scorm'; + /** @var bool If the class was previously instanced, in one execution cycle */ private static $loaded = false; @@ -143,6 +146,13 @@ protected function __construct($format, $courseid) { $this->currentscope = self::SCOPE_MOD; $patternavailable = '/^mod-.*-view$/'; $this->printable = preg_match($patternavailable, $PAGE->pagetype); + + if (!$this->printable) { + if (in_array(self::SCOPE_SCORM, $scope) && $PAGE->pagetype == 'mod-scorm-player') { + $this->printable = true; + } + } + } else { $this->printable = false; } diff --git a/settings.php b/settings.php index 6554bd8..12be252 100644 --- a/settings.php +++ b/settings.php @@ -55,6 +55,7 @@ $options = [ \format_onetopic::SCOPE_MOD => new lang_string('scope_mod', 'format_onetopic'), + \format_onetopic::SCOPE_SCORM => new lang_string('scope_scorm', 'format_onetopic'), ]; $settings->add(new admin_setting_configmulticheckbox('format_onetopic/defaultscope', get_string('defaultscope', 'format_onetopic'), diff --git a/version.php b/version.php index 0716221..8e2a808 100644 --- a/version.php +++ b/version.php @@ -33,7 +33,7 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050901; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050901.01; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2024041600; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_BETA; From 15af18fbfcf239a5f270d8c3dd2c45c93b2d47a1 Mon Sep 17 00:00:00 2001 From: David Herney Date: Sat, 20 Jul 2024 15:05:50 -0500 Subject: [PATCH 48/50] Code style --- classes/output/courseformat/content/section/summary.php | 2 +- classes/privacy/provider.php | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index ad1fb79..9a879fc 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -51,7 +51,7 @@ class summary extends summary_base { /** @var section_info the course section class */ private $section; - /** @var renderer_base the renderer output class */ + /** @var \renderer_base the renderer output class */ private $output; /** @var string Text to search */ diff --git a/classes/privacy/provider.php b/classes/privacy/provider.php index 7ced1dd..a2d7eb5 100644 --- a/classes/privacy/provider.php +++ b/classes/privacy/provider.php @@ -13,6 +13,7 @@ // // You should have received a copy of the GNU General Public License // along with Moodle. If not, see . + /** * Privacy Subsystem implementation for format_onetopic. * From 77e6d39d9eedd1451d50d2190378f5ed8aeef9db Mon Sep 17 00:00:00 2001 From: David Herney Date: Sat, 20 Jul 2024 17:44:57 -0500 Subject: [PATCH 49/50] Include activity badges in summary template --- amd/build/main.min.js | 2 +- amd/build/main.min.js.map | 2 +- amd/src/main.js | 9 +- classes/header.php | 2 +- .../courseformat/content/section/summary.php | 20 +++- styles.css | 22 ++++- .../content/cm/activity_infoinline.mustache | 66 ------------- .../content/cm/activityinline.mustache | 56 ++--------- .../content/cm/cmhelpinfo.mustache | 95 +++++++++++++++++++ version.php | 4 +- 10 files changed, 146 insertions(+), 132 deletions(-) delete mode 100644 templates/courseformat/content/cm/activity_infoinline.mustache create mode 100644 templates/courseformat/content/cm/cmhelpinfo.mustache diff --git a/amd/build/main.min.js b/amd/build/main.min.js index a26cdf8..d7ffca9 100644 --- a/amd/build/main.min.js +++ b/amd/build/main.min.js @@ -3,6 +3,6 @@ define("format_onetopic/main",["exports","format_onetopic/oneline","jquery","cor * @package format_onetopic * @copyright 2021 David Herney Bernal - cirano * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle=(0,_str.get_string)("aboutresource","format_onetopic");(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=$node.find(".iconwithhelp-content");if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1})),modal.getBody().append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); + */(OneLine),_jquery=_interopRequireDefault(_jquery),_modal_factory=_interopRequireDefault(_modal_factory);_exports.init=(formattype,icons)=>{2==formattype&&OneLine.load(icons);var infotitle=(0,_str.get_string)("aboutresource","format_onetopic");(0,_jquery.default)(".format-onetopic .onetopic .iconwithhelp[data-helpwindow]").each((function(){var $node=(0,_jquery.default)(this);$node.on("click",(function(e){e.preventDefault();var $content=(0,_jquery.default)("#hw-"+$node.data("helpwindow"));if($content.data("modal"))$content.data("modal").show();else{var title=$content.data("title");title||(title=infotitle),_modal_factory.default.create({title:title,body:""}).done((function(modal){var contenthtml=$content.html();contenthtml=contenthtml.replace(//g,(function(match,p1){return p1}));var $modalBody=modal.getBody();$modalBody.css("min-height","150px"),$modalBody.append(contenthtml),modal.show(),$content.data("modal",modal)}))}}))}))}})); //# sourceMappingURL=main.min.js.map \ No newline at end of file diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index c4b7d8f..32e27f9 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = getString('aboutresource', 'format_onetopic');\n\n $('.format-onetopic .onetopic .iconwithhelp').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $node.find('.iconwithhelp-content');\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': ''\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};"],"names":["formattype","icons","OneLine","load","infotitle","each","$node","this","on","e","preventDefault","$content","find","data","show","title","create","done","modal","contenthtml","html","replace","match","p1","getBody","append"],"mappings":";;;;;2HAgCoB,CAACA,WAAYC,SAEX,GAAdD,YACAE,QAAQC,KAAKF,WAGbG,WAAY,mBAAU,gBAAiB,uCAEzC,4CAA4CC,MAAK,eAC3CC,OAAQ,mBAAEC,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,qBACEC,SAAWL,MAAMM,KAAK,4BAEtBD,SAASE,KAAK,SACdF,SAASE,KAAK,SAASC,gBAIvBC,MAAQJ,SAASE,KAAK,SAErBE,QACDA,MAAQX,kCAICY,OAAO,OACPD,WACD,KACTE,MAAK,SAASC,WAETC,YAAcR,SAASS,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,WAC7DA,MAGML,MAAMM,UACZC,OAAON,aAClBD,MAAMJ,OACNH,SAASE,KAAK,QAASK"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = getString('aboutresource', 'format_onetopic');\n\n $('.format-onetopic .onetopic .iconwithhelp[data-helpwindow]').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $('#hw-' + $node.data('helpwindow'));\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': '',\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.css('min-height', '150px');\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};\n"],"names":["_interopRequireDefault","obj","__esModule","default","_getRequireWildcardCache","nodeInterop","WeakMap","cacheBabelInterop","cacheNodeInterop","OneLine","cache","has","get","newObj","hasPropertyDescriptor","Object","defineProperty","getOwnPropertyDescriptor","key","prototype","hasOwnProperty","call","desc","set","_interopRequireWildcard","_jquery","_modal_factory","_exports","init","formattype","icons","load","infotitle","getString","$","each","$node","this","on","e","preventDefault","$content","data","show","title","ModalFactory","create","body","done","modal","contenthtml","html","replace","match","p1","$modalBody","getBody","css","append"],"mappings":"qKAsB8C,SAAAA,uBAAAC,YAAAA,KAAAA,IAAAC,WAAAD,KAAAE,QAAAF,KAAA,SAAAG,yBAAAC,mCAAAC,wBAAAC,sBAAAD,QAAAE,qBAAAF,eAAAF,kCAAAC,oBAAAA,YAAAG,iBAAAD,oBAAAF,0FAF9CI,QAE8C,SAAAR,IAAAI,iBAAAA,aAAAJ,KAAAA,IAAAC,kBAAAD,cAAAA,sBAAAA,wBAAAA,WAAAE,QAAAF,SAAAS,MAAAN,yBAAAC,gBAAAK,OAAAA,MAAAC,IAAAV,YAAAS,MAAAE,IAAAX,SAAAY,UAAAC,sBAAAC,OAAAC,gBAAAD,OAAAE,iCAAAC,OAAAjB,mBAAAiB,KAAAH,OAAAI,UAAAC,eAAAC,KAAApB,IAAAiB,UAAAI,KAAAR,sBAAAC,OAAAE,yBAAAhB,IAAAiB,UAAAI,OAAAA,KAAAV,KAAAU,KAAAC,KAAAR,OAAAC,eAAAH,OAAAK,IAAAI,MAAAT,OAAAK,KAAAjB,IAAAiB,KAAAL,OAAAV,QAAAF,IAAAS,OAAAA,MAAAa,IAAAtB,IAAAY,eAAAA;;;;;KAF9CW,CAAAf,SACAgB,QAAAzB,uBAAAyB,SACAC,eAAA1B,uBAAA0B,gBAyDEC,SAAAC,KA/CkBA,CAACC,WAAYC,SAEX,GAAdD,YACApB,QAAQsB,KAAKD,OAGjB,IAAIE,WAAY,EAAAC,iBAAU,gBAAiB,oBAE3C,EAAAC,iBAAE,6DAA6DC,MAAK,WAChE,IAAIC,OAAQ,EAAAF,iBAAEG,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,iBACF,IAAIC,UAAW,EAAAP,iBAAE,OAASE,MAAMM,KAAK,eAErC,GAAID,SAASC,KAAK,SACdD,SAASC,KAAK,SAASC,WAD3B,CAKA,IAAIC,MAAQH,SAASC,KAAK,SAErBE,QACDA,MAAQZ,WAIZa,uBAAaC,OAAO,CAChBF,MAASA,MACTG,KAAQ,KACTC,MAAK,SAASC,OAEb,IAAIC,YAAcT,SAASU,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,IACpE,OAAOA,MAGX,IAAIC,WAAaN,MAAMO,UACvBD,WAAWE,IAAI,aAAc,SAC7BF,WAAWG,OAAOR,aAClBD,MAAMN,OACNF,SAASC,KAAK,QAASO,gBAGjC,CAEJ"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index cbfa15e..7c5ed3f 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -38,11 +38,11 @@ export const init = (formattype, icons) => { var infotitle = getString('aboutresource', 'format_onetopic'); - $('.format-onetopic .onetopic .iconwithhelp').each(function() { + $('.format-onetopic .onetopic .iconwithhelp[data-helpwindow]').each(function() { var $node = $(this); $node.on('click', function(e) { e.preventDefault(); - var $content = $node.find('.iconwithhelp-content'); + var $content = $('#hw-' + $node.data('helpwindow')); if ($content.data('modal')) { $content.data('modal').show(); @@ -58,7 +58,7 @@ export const init = (formattype, icons) => { // Show the content in a modal window. ModalFactory.create({ 'title': title, - 'body': '' + 'body': '', }).done(function(modal) { var contenthtml = $content.html(); @@ -69,6 +69,7 @@ export const init = (formattype, icons) => { }); var $modalBody = modal.getBody(); + $modalBody.css('min-height', '150px'); $modalBody.append(contenthtml); modal.show(); $content.data('modal', modal); @@ -76,4 +77,4 @@ export const init = (formattype, icons) => { }); }); -}; \ No newline at end of file +}; diff --git a/classes/header.php b/classes/header.php index 9436de0..903b6de 100644 --- a/classes/header.php +++ b/classes/header.php @@ -299,7 +299,7 @@ private function get_tabs(course_modinfo $modinfo, \renderer_base $output): \for } while ($parentformatoptions['level'] == 1 && $prevsectionindex >= $firstsection); if ($parentformatoptions['firsttabtext']) { - $indextab->content = format_text($parentformatoptions['firsttabtext'], true, $course->id); + $indextab->content = format_string($parentformatoptions['firsttabtext'], true, $course->id); } else { $indextab->content = get_string('index', 'format_onetopic'); } diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index 9a879fc..e77d21a 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -25,12 +25,10 @@ namespace format_onetopic\output\courseformat\content\section; use context_course; -use core\output\named_templatable; use core_courseformat\base as course_format; use core_courseformat\output\local\courseformat_named_templatable; use core_courseformat\output\local\content\cm as cm_base; use core_courseformat\output\local\content\section\summary as summary_base; -use renderable; use section_info; use stdClass; @@ -103,11 +101,12 @@ public function format_summary_text(): string { $course = $this->format->get_course(); $context = context_course::instance($section->course); + $summarytext = $section->summary; if ($course->templatetopic != \format_onetopic::TEMPLATETOPIC_NOT) { - $section->summary = $this->replace_resources($section); + $summarytext = $this->replace_resources($section); } - $summarytext = file_rewrite_pluginfile_urls($section->summary, 'pluginfile.php', + $summarytext = file_rewrite_pluginfile_urls($summarytext, 'pluginfile.php', $context->id, 'course', 'section', $section->id); $options = new stdClass(); @@ -186,7 +185,16 @@ private function replace_resources(section_info $section) { $cmdata->singlename = $instancename; // ToDo: Implement additional activity information. Now it's called "activity badge". + $cmdata->hascompletion = isset($cmdata->completion) && $cmdata->completion; + + $hasavailability = isset($cmdata->modavailability) ? $cmdata->modavailability->hasmodavailability : false; + $cmdata->showinlinehelp = false; + if ($cmdata->hascompletion + || (isset($cmdata->hasdates) && $cmdata->hasdates) + || $hasavailability){ + $cmdata->showinlinehelp = true; + } $url = $mod->url; if (empty($url)) { @@ -233,6 +241,10 @@ private function replace_resources(section_info $section) { $this->format->tplcmsused[] = $modnumber; } + if ($cmdata->showinlinehelp) { + $newsummary .= $renderer->render_from_template('format_onetopic/courseformat/content/cm/cmhelpinfo', $cmdata); + } + $summary = $newsummary; } diff --git a/styles.css b/styles.css index 11c29b4..a31b1ed 100644 --- a/styles.css +++ b/styles.css @@ -176,9 +176,9 @@ /* Template styles */ .format-onetopic .onetopic .cmnameinline .activityiconcontainer { - width: auto; - height: auto; - padding: 0.2rem; + padding-left: 0.2rem; + padding-right: 0; + display: inline; } .format-onetopic .activityinsummarytpl .description .course-description-item { @@ -200,6 +200,22 @@ display: block; } +.format-onetopic .modal-body .activity-info .completion-dropdown a[role="button"].btn, +.format-onetopic .modal-body .activity-info .completion-dropdown button.btn { + color: #1d2125; + background-color: #fff; + border-color: #ced4da; + min-height: 32px; + font-weight: bold; + border-radius: 0.5rem; +} + +.format-onetopic .modal-body .activity-info .completion-dropdown a[role="button"].btn:hover, +.format-onetopic .modal-body .activity-info .completion-dropdown button.btn:hover { + color: #fff; + background-color: #6a737b; + border-color: #b1bbc4; +} /* End of template styles */ /* Completion */ diff --git a/templates/courseformat/content/cm/activity_infoinline.mustache b/templates/courseformat/content/cm/activity_infoinline.mustache deleted file mode 100644 index af2e45e..0000000 --- a/templates/courseformat/content/cm/activity_infoinline.mustache +++ /dev/null @@ -1,66 +0,0 @@ -{{! - This file is part of Moodle - http://moodle.org/ - - Moodle is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - Moodle is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with Moodle. If not, see . -}} -{{! - @template format_onetopic/courseformat/content/cm/activity_infoinline - - Container to display activity information on the course page such as: - - Activity completion requirements (automatic completion) - - Manual completion button - - Example context (json): - { - "activityname": "Course announcements", - "hascompletion": true, - "uservisible": false, - "isautomatic": true, - "showmanualcompletion": true, - "completiondetails": [ - { - "statuscomplete": 1, - "description": "Viewed" - }, - { - "statusincomplete": 1, - "description": "Receive a grade" - } - ] - } -}} - - {{#hascompletion}} - {{#uservisible}} - - {{#isautomatic}} - - {{#completiondetails}} - {{$ core_course/completion_automatic }} - {{> core_course/completion_automatic }} - {{/ core_course/completion_automatic }} - {{/completiondetails}} - - {{/isautomatic}} - {{^isautomatic}} - {{#showmanualcompletion}} - {{$ core_course/completion_manual }} - {{> core_course/completion_manual }} - {{/ core_course/completion_manual }} - {{/showmanualcompletion}} - {{/isautomatic}} - - {{/uservisible}} - {{/hascompletion}} - diff --git a/templates/courseformat/content/cm/activityinline.mustache b/templates/courseformat/content/cm/activityinline.mustache index b7c7fa7..b107fd5 100644 --- a/templates/courseformat/content/cm/activityinline.mustache +++ b/templates/courseformat/content/cm/activityinline.mustache @@ -69,55 +69,11 @@ {{/afterlink}} {{#showinlinehelp}} - {{#activityinfo}} - {{! Only show the icon if there is a name to display. }} - {{#hasname}} - - {{#pix}} e/help, core, {{#str}} info {{/str}} {{/pix}} - - - {{/hasname}} - {{/activityinfo}} + {{! Only show the icon if there is a name to display. }} + {{#hasname}} + + {{#pix}} e/help, core, {{#str}} info {{/str}} {{/pix}} + + {{/hasname}} {{/showinlinehelp}}
diff --git a/templates/courseformat/content/cm/cmhelpinfo.mustache b/templates/courseformat/content/cm/cmhelpinfo.mustache new file mode 100644 index 0000000..9589a79 --- /dev/null +++ b/templates/courseformat/content/cm/cmhelpinfo.mustache @@ -0,0 +1,95 @@ +{{! + This file is part of Moodle - http://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template format_onetopic/courseformat/content/cm/cmhelpinfo + + Mustache to displays the help information for a course module instance. + + Example context (json): + { + "url": "#", + "icon": "../../../pix/help.svg", + "pluginname": "File", + "textclasses": "", + "purpose": "content", + "modname": "resource", + "activityname": { + "displayvalue" : "Moodle", + "value" : "Moodle", + "itemid" : "1", + "component" : "core_unknown", + "itemtype" : "unknown", + "edithint" : "Edit this", + "editlabel" : "New name for this", + "type" : "text", + "options" : "", + "linkeverything": 0 + } + } +}} + +{{! Only show the icon if there is a name to display. }} +{{#hasname}} + +{{/hasname}} diff --git a/version.php b/version.php index 8e2a808..038d904 100644 --- a/version.php +++ b/version.php @@ -33,9 +33,9 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2024050901.01; // The current plugin version (Date: YYYYMMDDXX). +$plugin->version = 2024050902; // The current plugin version (Date: YYYYMMDDXX). $plugin->requires = 2024041600; // Requires this Moodle version. $plugin->component = 'format_onetopic'; // Full name of the plugin (used for diagnostics). $plugin->maturity = MATURITY_BETA; -$plugin->release = '4.4.01(LasAcacias)'; +$plugin->release = '4.4.02(LasAcacias)'; $plugin->dependencies = ['format_topics' => 2024042200]; From 9ef67acb01841edc0f63a4712f14135b1b70d7fb Mon Sep 17 00:00:00 2001 From: David Herney Date: Sat, 20 Jul 2024 18:58:25 -0500 Subject: [PATCH 50/50] Include activity badges in summary template --- amd/build/main.min.js.map | 2 +- amd/src/main.js | 1 - classes/output/courseformat/content/section/summary.php | 3 +-- 3 files changed, 2 insertions(+), 4 deletions(-) diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index 32e27f9..f07379d 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = getString('aboutresource', 'format_onetopic');\n\n $('.format-onetopic .onetopic .iconwithhelp[data-helpwindow]').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $('#hw-' + $node.data('helpwindow'));\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': '',\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.css('min-height', '150px');\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n\n};\n"],"names":["_interopRequireDefault","obj","__esModule","default","_getRequireWildcardCache","nodeInterop","WeakMap","cacheBabelInterop","cacheNodeInterop","OneLine","cache","has","get","newObj","hasPropertyDescriptor","Object","defineProperty","getOwnPropertyDescriptor","key","prototype","hasOwnProperty","call","desc","set","_interopRequireWildcard","_jquery","_modal_factory","_exports","init","formattype","icons","load","infotitle","getString","$","each","$node","this","on","e","preventDefault","$content","data","show","title","ModalFactory","create","body","done","modal","contenthtml","html","replace","match","p1","$modalBody","getBody","css","append"],"mappings":"qKAsB8C,SAAAA,uBAAAC,YAAAA,KAAAA,IAAAC,WAAAD,KAAAE,QAAAF,KAAA,SAAAG,yBAAAC,mCAAAC,wBAAAC,sBAAAD,QAAAE,qBAAAF,eAAAF,kCAAAC,oBAAAA,YAAAG,iBAAAD,oBAAAF,0FAF9CI,QAE8C,SAAAR,IAAAI,iBAAAA,aAAAJ,KAAAA,IAAAC,kBAAAD,cAAAA,sBAAAA,wBAAAA,WAAAE,QAAAF,SAAAS,MAAAN,yBAAAC,gBAAAK,OAAAA,MAAAC,IAAAV,YAAAS,MAAAE,IAAAX,SAAAY,UAAAC,sBAAAC,OAAAC,gBAAAD,OAAAE,iCAAAC,OAAAjB,mBAAAiB,KAAAH,OAAAI,UAAAC,eAAAC,KAAApB,IAAAiB,UAAAI,KAAAR,sBAAAC,OAAAE,yBAAAhB,IAAAiB,UAAAI,OAAAA,KAAAV,KAAAU,KAAAC,KAAAR,OAAAC,eAAAH,OAAAK,IAAAI,MAAAT,OAAAK,KAAAjB,IAAAiB,KAAAL,OAAAV,QAAAF,IAAAS,OAAAA,MAAAa,IAAAtB,IAAAY,eAAAA;;;;;KAF9CW,CAAAf,SACAgB,QAAAzB,uBAAAyB,SACAC,eAAA1B,uBAAA0B,gBAyDEC,SAAAC,KA/CkBA,CAACC,WAAYC,SAEX,GAAdD,YACApB,QAAQsB,KAAKD,OAGjB,IAAIE,WAAY,EAAAC,iBAAU,gBAAiB,oBAE3C,EAAAC,iBAAE,6DAA6DC,MAAK,WAChE,IAAIC,OAAQ,EAAAF,iBAAEG,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,iBACF,IAAIC,UAAW,EAAAP,iBAAE,OAASE,MAAMM,KAAK,eAErC,GAAID,SAASC,KAAK,SACdD,SAASC,KAAK,SAASC,WAD3B,CAKA,IAAIC,MAAQH,SAASC,KAAK,SAErBE,QACDA,MAAQZ,WAIZa,uBAAaC,OAAO,CAChBF,MAASA,MACTG,KAAQ,KACTC,MAAK,SAASC,OAEb,IAAIC,YAAcT,SAASU,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,IACpE,OAAOA,MAGX,IAAIC,WAAaN,MAAMO,UACvBD,WAAWE,IAAI,aAAc,SAC7BF,WAAWG,OAAOR,aAClBD,MAAMN,OACNF,SAASC,KAAK,QAASO,gBAGjC,CAEJ"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/*\n * @package format_onetopic\n * @copyright 2021 David Herney Bernal - cirano\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as OneLine from 'format_onetopic/oneline';\nimport $ from 'jquery';\nimport ModalFactory from 'core/modal_factory';\nimport {get_string as getString} from 'core/str';\n\n/**\n * Component initialization.\n *\n * @method init\n * @param {string} formattype The course format type: 0: default, 1: vertical, 2: oneline.\n * @param {object} icons A list of usable icons: left arrow, right arrow.\n */\nexport const init = (formattype, icons) => {\n\n if (formattype == 2) {\n OneLine.load(icons);\n }\n\n var infotitle = getString('aboutresource', 'format_onetopic');\n\n $('.format-onetopic .onetopic .iconwithhelp[data-helpwindow]').each(function() {\n var $node = $(this);\n $node.on('click', function(e) {\n e.preventDefault();\n var $content = $('#hw-' + $node.data('helpwindow'));\n\n if ($content.data('modal')) {\n $content.data('modal').show();\n return;\n }\n\n var title = $content.data('title');\n\n if (!title) {\n title = infotitle;\n }\n\n // Show the content in a modal window.\n ModalFactory.create({\n 'title': title,\n 'body': '',\n }).done(function(modal) {\n\n var contenthtml = $content.html();\n\n // Uncomment html in contenthtml. The comment is used in order to load content with tags not inline.\n contenthtml = contenthtml.replace(//g, function(match, p1) {\n return p1;\n });\n\n var $modalBody = modal.getBody();\n $modalBody.css('min-height', '150px');\n $modalBody.append(contenthtml);\n modal.show();\n $content.data('modal', modal);\n });\n });\n });\n};\n"],"names":["_interopRequireDefault","obj","__esModule","default","_getRequireWildcardCache","nodeInterop","WeakMap","cacheBabelInterop","cacheNodeInterop","OneLine","cache","has","get","newObj","hasPropertyDescriptor","Object","defineProperty","getOwnPropertyDescriptor","key","prototype","hasOwnProperty","call","desc","set","_interopRequireWildcard","_jquery","_modal_factory","_exports","init","formattype","icons","load","infotitle","getString","$","each","$node","this","on","e","preventDefault","$content","data","show","title","ModalFactory","create","body","done","modal","contenthtml","html","replace","match","p1","$modalBody","getBody","css","append"],"mappings":"qKAsB8C,SAAAA,uBAAAC,YAAAA,KAAAA,IAAAC,WAAAD,KAAAE,QAAAF,KAAA,SAAAG,yBAAAC,mCAAAC,wBAAAC,sBAAAD,QAAAE,qBAAAF,eAAAF,kCAAAC,oBAAAA,YAAAG,iBAAAD,oBAAAF,0FAF9CI,QAE8C,SAAAR,IAAAI,iBAAAA,aAAAJ,KAAAA,IAAAC,kBAAAD,cAAAA,sBAAAA,wBAAAA,WAAAE,QAAAF,SAAAS,MAAAN,yBAAAC,gBAAAK,OAAAA,MAAAC,IAAAV,YAAAS,MAAAE,IAAAX,SAAAY,UAAAC,sBAAAC,OAAAC,gBAAAD,OAAAE,iCAAAC,OAAAjB,mBAAAiB,KAAAH,OAAAI,UAAAC,eAAAC,KAAApB,IAAAiB,UAAAI,KAAAR,sBAAAC,OAAAE,yBAAAhB,IAAAiB,UAAAI,OAAAA,KAAAV,KAAAU,KAAAC,KAAAR,OAAAC,eAAAH,OAAAK,IAAAI,MAAAT,OAAAK,KAAAjB,IAAAiB,KAAAL,OAAAV,QAAAF,IAAAS,OAAAA,MAAAa,IAAAtB,IAAAY,eAAAA;;;;;KAF9CW,CAAAf,SACAgB,QAAAzB,uBAAAyB,SACAC,eAAA1B,uBAAA0B,gBAwDEC,SAAAC,KA9CkBA,CAACC,WAAYC,SAEX,GAAdD,YACApB,QAAQsB,KAAKD,OAGjB,IAAIE,WAAY,EAAAC,iBAAU,gBAAiB,oBAE3C,EAAAC,iBAAE,6DAA6DC,MAAK,WAChE,IAAIC,OAAQ,EAAAF,iBAAEG,MACdD,MAAME,GAAG,SAAS,SAASC,GACvBA,EAAEC,iBACF,IAAIC,UAAW,EAAAP,iBAAE,OAASE,MAAMM,KAAK,eAErC,GAAID,SAASC,KAAK,SACdD,SAASC,KAAK,SAASC,WAD3B,CAKA,IAAIC,MAAQH,SAASC,KAAK,SAErBE,QACDA,MAAQZ,WAIZa,uBAAaC,OAAO,CAChBF,MAASA,MACTG,KAAQ,KACTC,MAAK,SAASC,OAEb,IAAIC,YAAcT,SAASU,OAG3BD,YAAcA,YAAYE,QAAQ,sBAAsB,SAASC,MAAOC,IACpE,OAAOA,MAGX,IAAIC,WAAaN,MAAMO,UACvBD,WAAWE,IAAI,aAAc,SAC7BF,WAAWG,OAAOR,aAClBD,MAAMN,OACNF,SAASC,KAAK,QAASO,gBAGjC,CACJ"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index 7c5ed3f..936a917 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -76,5 +76,4 @@ export const init = (formattype, icons) => { }); }); }); - }; diff --git a/classes/output/courseformat/content/section/summary.php b/classes/output/courseformat/content/section/summary.php index e77d21a..0facddb 100644 --- a/classes/output/courseformat/content/section/summary.php +++ b/classes/output/courseformat/content/section/summary.php @@ -184,7 +184,6 @@ private function replace_resources(section_info $section) { $cmdata->uniqueid = 'cm_' . $mod->id . '_' . time() . '_' . rand(0, 1000); $cmdata->singlename = $instancename; - // ToDo: Implement additional activity information. Now it's called "activity badge". $cmdata->hascompletion = isset($cmdata->completion) && $cmdata->completion; $hasavailability = isset($cmdata->modavailability) ? $cmdata->modavailability->hasmodavailability : false; @@ -192,7 +191,7 @@ private function replace_resources(section_info $section) { $cmdata->showinlinehelp = false; if ($cmdata->hascompletion || (isset($cmdata->hasdates) && $cmdata->hasdates) - || $hasavailability){ + || $hasavailability) { $cmdata->showinlinehelp = true; }