More efficient querying of courses (from Martin Langhoff)
[moodle.git] / blocks / moodleblock.class.php
blob0fcce08b3c21343c99745bb4bd84cf96f0c5281d
1 <?php // $Id$
3 define('BLOCK_TYPE_LIST', 1);
4 define('BLOCK_TYPE_TEXT', 2);
5 define('BLOCK_TYPE_NUKE', 3);
7 class MoodleBlock {
8 var $str;
9 var $title = NULL;
10 var $course = NULL;
11 var $content_type = NULL;
12 var $content = NULL;
13 var $edit_controls = NULL;
14 var $version = NULL;
16 function name() {
17 // Returns the block name, as present in the class name,
18 // the database, the block directory, etc etc.
19 static $myname;
20 if($myname === NULL) {
21 $myname = strtolower(get_class($this));
22 $myname = substr($myname, strpos($myname, '_') + 1);
24 return $myname;
27 function get_content() {
28 // This should be implemented by the derived class.
29 return NULL;
31 function get_title() {
32 // Intentionally doesn't check if a title is set, for _test_self()
33 return $this->title;
35 function get_content_type() {
36 // Intentionally doesn't check if a content_type is set, for _test_self()
37 return $this->content_type;
39 function get_version() {
40 // Intentionally doesn't check if a version is set, for _test_self()
41 return $this->version;
43 function get_header() {
44 // Intentionally doesn't check if a header is set, for _test_self()
45 return $this->header;
47 function refresh_content() {
48 // Nothing special here, depends on content()
49 $this->content = NULL;
50 return $this->get_content();
52 function print_block() {
53 // Wrap the title in a floating DIV, in case we have edit controls to display
54 // These controls will always be wrapped on a right-floating DIV
55 $title = '<div style="float: left;">'.$this->title.'</div>';
56 if($this->edit_controls !== NULL) {
57 $title .= $this->edit_controls;
60 $this->get_content();
61 if(!isset($this->content->footer)) {
62 $this->content->footer = '';
65 switch($this->content_type) {
66 case BLOCK_TYPE_NUKE:
67 case BLOCK_TYPE_TEXT:
68 if(empty($this->content->text) && empty($this->content->footer)) {
69 if(empty($this->edit_controls)) {
70 // No content, no edit controls, so just shut up
71 break;
73 else {
74 // No content but editing, so show something at least
75 $this->print_shadow();
78 else {
79 if($this->hide_header() && empty($this->edit_controls)) {
80 // Header wants to hide, no edit controls to show, so no header it is
81 print_side_block(NULL, $this->content->text, NULL, NULL, $this->content->footer, $this->html_attributes());
83 else {
84 // The full treatment, please
85 print_side_block($title, $this->content->text, NULL, NULL, $this->content->footer, $this->html_attributes());
88 break;
89 case BLOCK_TYPE_LIST:
90 if(empty($this->content->items) && empty($this->content->footer)) {
91 if(empty($this->edit_controls)) {
92 // No content, no edit controls, so just shut up
93 break;
95 else {
96 // No content but editing, so show something at least
97 $this->print_shadow();
100 else {
101 if($this->hide_header() && empty($this->edit_controls)) {
102 // Header wants to hide, no edit controls to show, so no header it is
103 print_side_block(NULL, '', $this->content->items, $this->content->icons, $this->content->footer, $this->html_attributes());
105 else {
106 // The full treatment, please
107 print_side_block($title, '', $this->content->items, $this->content->icons, $this->content->footer, $this->html_attributes());
110 break;
113 function print_shadow() {
114 $title = '<div style="float: left;">'.$this->title.'</div>';
115 if($this->edit_controls !== NULL) {
116 $title .= $this->edit_controls;
118 print_side_block($title, '&nbsp;', NULL, NULL, '');
121 function add_edit_controls($options, $blockid) {
122 global $CFG, $THEME, $USER;
124 // The block may be disabled
125 $blockid = intval($blockid);
126 $enabled = $blockid > 0;
127 $blockid = abs($blockid);
129 if (!isset($this->str)) {
130 $this->str->delete = get_string('delete');
131 $this->str->moveup = get_string('moveup');
132 $this->str->movedown = get_string('movedown');
133 $this->str->moveright = get_string('moveright');
134 $this->str->moveleft = get_string('moveleft');
135 $this->str->hide = get_string('hide');
136 $this->str->show = get_string('show');
139 $path = $CFG->wwwroot.'/course';
141 if (empty($THEME->custompix)) {
142 $pixpath = $path.'/../pix';
143 } else {
144 $pixpath = $path.'/../theme/'.$CFG->theme.'/pix';
147 $sesskeystr = '&amp;sesskey='.$USER->sesskey;
149 $movebuttons = '<div style="float: right;">';
151 if($enabled) {
152 $icon = '/t/hide.gif';
153 $title = $this->str->hide;
155 else {
156 $icon = '/t/show.gif';
157 $title = $this->str->show;
160 $movebuttons .= '<a style="margin-right: 6px; margin-left: 3px;" title="'.$title.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=toggle&amp;blockid='.$blockid.$sesskeystr.'">' .
161 '<img src="'.$pixpath.$icon.'" /></a>';
163 $movebuttons .= '<a title="'.$this->str->delete.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=delete&amp;blockid='.$blockid.$sesskeystr.'">' .
164 '<img src="'.$pixpath.'/t/delete.gif" /></a> ';
166 if ($options & BLOCK_MOVE_LEFT) {
167 $movebuttons .= '<a style="margin-right: 2px; margin-left: 2px;" title="'.$this->str->moveleft.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=moveside&amp;blockid='.$blockid.$sesskeystr.'">' .
168 '<img src="'.$pixpath.'/t/left.gif" /></a>';
170 if ($options & BLOCK_MOVE_UP) {
171 $movebuttons .= '<a style="margin-right: 2px; margin-left: 2px;" title="'.$this->str->moveup.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=moveup&amp;blockid='.$blockid.$sesskeystr.'">' .
172 '<img src="'.$pixpath.'/t/up.gif" /></a>';
174 if ($options & BLOCK_MOVE_DOWN) {
175 $movebuttons .= '<a style="margin-right: 2px; margin-left: 2px;" title="'.$this->str->movedown.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=movedown&amp;blockid='.$blockid.$sesskeystr.'">' .
176 '<img src="'.$pixpath.'/t/down.gif" /></a>';
178 if ($options & BLOCK_MOVE_RIGHT) {
179 $movebuttons .= '<a style="margin-right: 2px; margin-left: 2px;" title="'.$this->str->moveright.'" href="'.$path.'/view.php?id='.$this->course->id.'&amp;blockaction=moveside&amp;blockid='.$blockid.$sesskeystr.'">' .
180 '<img src="'.$pixpath.'/t/right.gif" /></a>';
183 $movebuttons .= '</div>';
184 $this->edit_controls = $movebuttons;
187 function _self_test() {
188 // Tests if this block has been implemented correctly.
189 // Also, $errors isn't used right now
190 $errors = array();
192 $correct = true;
193 if($this->get_title() === NULL) {
194 $errors[] = 'title_not_set';
195 $correct = false;
197 if(!in_array($this->get_content_type(), array(BLOCK_TYPE_LIST, BLOCK_TYPE_TEXT, BLOCK_TYPE_NUKE))) {
198 $errors[] = 'invalid_content_type';
199 $correct = false;
201 if($this->get_content() === NULL) {
202 $errors[] = 'content_not_set';
203 $correct = false;
205 if($this->get_version() === NULL) {
206 $errors[] = 'version_not_set';
207 $correct = false;
210 $formats = $this->applicable_formats();
211 if(empty($formats) || array_sum($formats) === 0) {
212 $errors[] = 'no_course_formats';
213 $correct = false;
216 $width = $this->preferred_width();
217 if(!is_int($width) || $width <= 0) {
218 $errors[] = 'invalid_width';
219 $correct = false;
221 return $correct;
224 function has_config() {
225 return false;
227 function print_config() {
228 // This does nothing, it's here to prevent errors from
229 // derived classes if they implement has_config() but not print_config()
231 function handle_config() {
232 // This does nothing, it's here to prevent errors from
233 // derived classes if they implement has_config() but not handle_config()
235 function applicable_formats() {
236 // Default case: the block can be used in all course types
237 return array('all' => true);
239 function preferred_width() {
240 // Default case: the block wants to be 180 pixels wide
241 return 180;
243 function hide_header() {
244 //Default, false--> the header is shown
245 return false;
247 function html_attributes() {
248 // Default case: just an id for the block, with our name in it
249 return array('id' => 'block_'.$this->name());
253 class MoodleBlock_Nuke extends MoodleBlock {
254 function get_content() {
256 if($this->content !== NULL) {
257 return $this->content;
260 global $CFG;
261 $this->content = &New stdClass;
263 // This whole thing begs to be written for PHP >= 4.3.0 using glob();
264 $dir = $CFG->dirroot.'/blocks/'.$this->name().'/nuke/';
265 if($dh = @opendir($dir)) {
266 while (($file = readdir($dh)) !== false) {
267 $regs = array();
268 if(ereg('^block\-(.*)\.php$', $file, $regs)) {
269 // Found it! Let's prepare the environment...
271 $oldvals = array();
272 if(isset($GLOBALS['admin'])) {
273 $oldvals['admin'] = $GLOBALS['admin'];
276 $GLOBALS['admin'] = isteacher($this->course->id);
277 @include($dir.$file);
279 foreach($oldvals as $key => $val) {
280 $GLOBALS[$key] = $val;
283 // We should have $content set now
284 if(!isset($content)) {
285 return NULL;
287 return $this->content->text = $content;
292 // If we reached here, we couldn't find the nuke block for some reason
293 return $this->content->text = get_string('blockmissingnuke');