Proyectos de Subversion Moodle

Rev

Ir a la última revisión | | Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
<?php
2
// This file is part of Moodle - http://moodle.org/
3
//
4
// Moodle is free software: you can redistribute it and/or modify
5
// it under the terms of the GNU General Public License as published by
6
// the Free Software Foundation, either version 3 of the License, or
7
// (at your option) any later version.
8
//
9
// Moodle is distributed in the hope that it will be useful,
10
// but WITHOUT ANY WARRANTY; without even the implied warranty of
11
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
// GNU General Public License for more details.
13
//
14
// You should have received a copy of the GNU General Public License
15
// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
16
 
17
/**
18
 * Contains the default section controls output class.
19
 *
20
 * @package   core_courseformat
21
 * @copyright 2020 Ferran Recio <ferran@moodle.com>
22
 * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
23
 */
24
 
25
namespace core_courseformat\output\local\content\section;
26
 
27
use action_menu;
28
use action_menu_link_secondary;
29
use context_course;
30
use core\output\named_templatable;
31
use core_courseformat\base as course_format;
32
use core_courseformat\output\local\courseformat_named_templatable;
33
use moodle_url;
34
use pix_icon;
35
use renderable;
36
use section_info;
37
use stdClass;
38
 
39
/**
40
 * Base class to render section controls.
41
 *
42
 * @package   core_courseformat
43
 * @copyright 2020 Ferran Recio <ferran@moodle.com>
44
 * @license   http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
45
 */
46
class controlmenu implements named_templatable, renderable {
47
 
48
    use courseformat_named_templatable;
49
 
50
    /** @var course_format the course format class */
51
    protected $format;
52
 
53
    /** @var section_info the course section class */
54
    protected $section;
55
 
56
    /**
57
     * Constructor.
58
     *
59
     * @param course_format $format the course format
60
     * @param section_info $section the section info
61
     */
62
    public function __construct(course_format $format, section_info $section) {
63
        $this->format = $format;
64
        $this->section = $section;
65
    }
66
 
67
    /**
68
     * Export this data so it can be used as the context for a mustache template.
69
     *
70
     * @param \renderer_base $output typically, the renderer that's calling this function
71
     * @return array data context for a mustache template
72
     */
73
    public function export_for_template(\renderer_base $output): stdClass {
74
        $menu = $this->get_action_menu($output);
75
        if (empty($menu)) {
76
            return new stdClass();
77
        }
78
 
79
        $data = (object)[
80
            'menu' => $output->render($menu),
81
            'hasmenu' => true,
82
            'id' => $this->section->id,
83
        ];
84
 
85
        return $data;
86
    }
87
 
88
    /**
89
     * Generate the action menu element depending on the section.
90
     *
91
     * Sections controlled by a plugin will delegate the control menu to the plugin.
92
     *
93
     * @param \renderer_base $output typically, the renderer that's calling this function
94
     * @return action_menu|null the activity action menu or null if no action menu is available
95
     */
96
    public function get_action_menu(\renderer_base $output): ?action_menu {
97
        $sectiondelegate = $this->section->get_component_instance();
98
        if ($sectiondelegate) {
99
            return $sectiondelegate->get_section_action_menu($this->format, $this, $output);
100
        }
101
        return $this->get_default_action_menu($output);
102
    }
103
 
104
    /**
105
     * Generate the default section action menu.
106
     *
107
     * This method is public in case some block needs to modify the menu before output it.
108
     *
109
     * @param \renderer_base $output typically, the renderer that's calling this function
110
     * @return action_menu|null the activity action menu
111
     */
112
    public function get_default_action_menu(\renderer_base $output): ?action_menu {
113
        $controls = $this->section_control_items();
114
        if (empty($controls)) {
115
            return null;
116
        }
117
 
118
        // Convert control array into an action_menu.
119
        $menu = new action_menu();
120
        $menu->set_kebab_trigger(get_string('edit'));
121
        $menu->attributes['class'] .= ' section-actions';
122
        foreach ($controls as $value) {
123
            $url = empty($value['url']) ? '' : $value['url'];
124
            $icon = empty($value['icon']) ? '' : $value['icon'];
125
            $name = empty($value['name']) ? '' : $value['name'];
126
            $attr = empty($value['attr']) ? [] : $value['attr'];
127
            $class = empty($value['pixattr']['class']) ? '' : $value['pixattr']['class'];
128
            $al = new action_menu_link_secondary(
129
                new moodle_url($url),
130
                new pix_icon($icon, '', null, ['class' => "smallicon " . $class]),
131
                $name,
132
                $attr
133
            );
134
            $menu->add($al);
135
        }
136
        return $menu;
137
    }
138
 
139
    /**
140
     * Generate the edit control items of a section.
141
     *
142
     * It is not clear this kind of controls are still available in 4.0 so, for now, this
143
     * method is almost a clone of the previous section_control_items from the course/renderer.php.
144
     *
145
     * This method must remain public until the final deprecation of section_edit_control_items.
146
     *
147
     * @return array of edit control items
148
     */
149
    public function section_control_items() {
150
        global $USER, $PAGE;
151
 
152
        $format = $this->format;
153
        $section = $this->section;
154
        $course = $format->get_course();
155
        $sectionreturn = !is_null($format->get_sectionid()) ? $format->get_sectionnum() : null;
156
        $user = $USER;
157
 
158
        $usecomponents = $format->supports_components();
159
        $coursecontext = context_course::instance($course->id);
160
        $numsections = $format->get_last_section_number();
161
        $isstealth = $section->section > $numsections;
162
 
163
        $baseurl = course_get_url($course, $sectionreturn);
164
        $baseurl->param('sesskey', sesskey());
165
 
166
        $controls = [];
167
 
168
        // Only show the view link if we are not already in the section view page.
169
        if ($PAGE->pagetype !== 'course-view-section-' . $course->format) {
170
            $controls['view'] = [
171
                'url'   => new moodle_url('/course/section.php', ['id' => $section->id]),
172
                'icon' => 'i/viewsection',
173
                'name' => get_string('view'),
174
                'pixattr' => ['class' => ''],
175
                'attr' => ['class' => 'icon view'],
176
            ];
177
        }
178
 
179
        if (!$isstealth && has_capability('moodle/course:update', $coursecontext, $user)) {
180
            $params = ['id' => $section->id];
181
            $params['sr'] = $section->section;
182
            if (get_string_manager()->string_exists('editsection', 'format_'.$format->get_format())) {
183
                $streditsection = get_string('editsection', 'format_'.$format->get_format());
184
            } else {
185
                $streditsection = get_string('editsection');
186
            }
187
 
188
            $controls['edit'] = [
189
                'url'   => new moodle_url('/course/editsection.php', $params),
190
                'icon' => 'i/settings',
191
                'name' => $streditsection,
192
                'pixattr' => ['class' => ''],
193
                'attr' => ['class' => 'icon edit'],
194
            ];
195
 
196
            $duplicatesectionurl = clone($baseurl);
197
            $duplicatesectionurl->param('section', $section->section);
198
            $duplicatesectionurl->param('duplicatesection', $section->section);
199
            if (!is_null($sectionreturn)) {
200
                $duplicatesectionurl->param('sr', $sectionreturn);
201
            }
202
            $controls['duplicate'] = [
203
                'url' => $duplicatesectionurl,
204
                'icon' => 't/copy',
205
                'name' => get_string('duplicate'),
206
                'pixattr' => ['class' => ''],
207
                'attr' => ['class' => 'icon duplicate'],
208
            ];
209
        }
210
 
211
        if ($section->section) {
212
            $url = clone($baseurl);
213
            if (!is_null($sectionreturn)) {
214
                $url->param('sectionid', $format->get_sectionid());
215
            }
216
            if (!$isstealth) {
217
                if (has_capability('moodle/course:sectionvisibility', $coursecontext, $user)) {
218
                    $strhidefromothers = get_string('hidefromothers', 'format_' . $course->format);
219
                    $strshowfromothers = get_string('showfromothers', 'format_' . $course->format);
220
                    if ($section->visible) { // Show the hide/show eye.
221
                        $url->param('hide', $section->section);
222
                        $controls['visiblity'] = [
223
                            'url' => $url,
224
                            'icon' => 'i/hide',
225
                            'name' => $strhidefromothers,
226
                            'pixattr' => ['class' => ''],
227
                            'attr' => [
228
                                'class' => 'icon editing_showhide',
229
                                'data-sectionreturn' => $sectionreturn,
230
                                'data-action' => ($usecomponents) ? 'sectionHide' : 'hide',
231
                                'data-id' => $section->id,
232
                                'data-swapname' => $strshowfromothers,
233
                                'data-swapicon' => 'i/show',
234
                            ],
235
                        ];
236
                    } else {
237
                        $url->param('show',  $section->section);
238
                        $controls['visiblity'] = [
239
                            'url' => $url,
240
                            'icon' => 'i/show',
241
                            'name' => $strshowfromothers,
242
                            'pixattr' => ['class' => ''],
243
                            'attr' => [
244
                                'class' => 'icon editing_showhide',
245
                                'data-sectionreturn' => $sectionreturn,
246
                                'data-action' => ($usecomponents) ? 'sectionShow' : 'show',
247
                                'data-id' => $section->id,
248
                                'data-swapname' => $strhidefromothers,
249
                                'data-swapicon' => 'i/hide',
250
                            ],
251
                        ];
252
                    }
253
                }
254
 
255
                if (!$sectionreturn && has_capability('moodle/course:movesections', $coursecontext, $user)) {
256
                    if ($usecomponents) {
257
                        // This tool will appear only when the state is ready.
258
                        $url = clone ($baseurl);
259
                        $url->param('movesection', $section->section);
260
                        $url->param('section', $section->section);
261
                        $controls['movesection'] = [
262
                            'url' => $url,
263
                            'icon' => 'i/dragdrop',
264
                            'name' => get_string('move', 'moodle'),
265
                            'pixattr' => ['class' => ''],
266
                            'attr' => [
267
                                'class' => 'icon move waitstate',
268
                                'data-action' => 'moveSection',
269
                                'data-id' => $section->id,
270
                            ],
271
                        ];
272
                    }
273
                    // Legacy move up and down links for non component-based formats.
274
                    $url = clone($baseurl);
275
                    if ($section->section > 1) { // Add a arrow to move section up.
276
                        $url->param('section', $section->section);
277
                        $url->param('move', -1);
278
                        $strmoveup = get_string('moveup');
279
                        $controls['moveup'] = [
280
                            'url' => $url,
281
                            'icon' => 'i/up',
282
                            'name' => $strmoveup,
283
                            'pixattr' => ['class' => ''],
284
                            'attr' => ['class' => 'icon moveup whilenostate'],
285
                        ];
286
                    }
287
 
288
                    $url = clone($baseurl);
289
                    if ($section->section < $numsections) { // Add a arrow to move section down.
290
                        $url->param('section', $section->section);
291
                        $url->param('move', 1);
292
                        $strmovedown = get_string('movedown');
293
                        $controls['movedown'] = [
294
                            'url' => $url,
295
                            'icon' => 'i/down',
296
                            'name' => $strmovedown,
297
                            'pixattr' => ['class' => ''],
298
                            'attr' => ['class' => 'icon movedown whilenostate'],
299
                        ];
300
                    }
301
                }
302
            }
303
 
304
            if (course_can_delete_section($course, $section)) {
305
                if (get_string_manager()->string_exists('deletesection', 'format_'.$course->format)) {
306
                    $strdelete = get_string('deletesection', 'format_'.$course->format);
307
                } else {
308
                    $strdelete = get_string('deletesection');
309
                }
310
                $params = [
311
                    'id' => $section->id,
312
                    'delete' => 1,
313
                    'sesskey' => sesskey(),
314
                ];
315
                if (!is_null($sectionreturn)) {
316
                    $params['sr'] = $sectionreturn;
317
                }
318
                $url = new moodle_url(
319
                    '/course/editsection.php',
320
                    $params,
321
                );
322
                $controls['delete'] = [
323
                    'url' => $url,
324
                    'icon' => 'i/delete',
325
                    'name' => $strdelete,
326
                    'pixattr' => ['class' => ''],
327
                    'attr' => [
328
                        'class' => 'icon editing_delete text-danger',
329
                        'data-action' => 'deleteSection',
330
                        'data-id' => $section->id,
331
                    ],
332
                ];
333
            }
334
        }
335
        if (
336
            has_any_capability([
337
                'moodle/course:movesections',
338
                'moodle/course:update',
339
                'moodle/course:sectionvisibility',
340
            ], $coursecontext)
341
        ) {
342
            $sectionlink = new moodle_url(
343
                '/course/section.php',
344
                ['id' => $section->id]
345
            );
346
            $controls['permalink'] = [
347
                'url' => $sectionlink,
348
                'icon' => 'i/link',
349
                'name' => get_string('sectionlink', 'course'),
350
                'pixattr' => ['class' => ''],
351
                'attr' => [
352
                    'class' => 'icon',
353
                    'data-action' => 'permalink',
354
                ],
355
            ];
356
        }
357
 
358
        return $controls;
359
    }
360
}