Projet

Général

Profil

Paste
Télécharger (33 ko) Statistiques
| Branche: | Révision:

root / drupal7 / sites / all / modules / panels / plugins / task_handlers / panel_context.inc @ a2bb1a14

1 85ad3d82 Assos Assos
<?php
2
3
/**
4
 * @file
5
 *
6
 * This is the task handler plugin to handle attaching a panel to any
7
 * task that advertises itself as a 'context' type, which all of the
8
 * basic page tasks provided by page_manager.module do by default.
9
 */
10
11
// Plugin definition
12
$plugin = array(
13
  // is a 'context' handler type, meaning it supports the API of the
14
  // context handlers provided by ctools context plugins.
15
  'handler type' => 'context',
16
  'visible' => TRUE, // may be added up front.
17
18
  // Administrative fields.
19
  'title' => t('Panel'),
20
  'admin summary' =>'panels_panel_context_admin_summary',
21
  'admin title' => 'panels_panel_context_title',
22
  'operations' => array(
23
    'settings' => array(
24
      'title' => t('General'),
25
      'description' => t('Change general settings about this variant.'),
26
      'form' => 'panels_panel_context_edit_settings',
27
    ),
28
    'criteria' => array(
29
      'title' => t('Selection rules'),
30
      'description' => t('Control the criteria used to decide whether or not this variant is used.'),
31
      'ajax' => FALSE,
32
      'form' => array(
33
        'order' => array(
34
          'form' => t('Selection rules'),
35
        ),
36
        'forms' => array(
37
          'form' => array(
38
            'include' => drupal_get_path('module', 'ctools') . '/includes/context-task-handler.inc',
39
            'form id' => 'ctools_context_handler_edit_criteria',
40
          ),
41
        ),
42
      ),
43
    ),
44
    'context' => array(
45
      'title' => t('Contexts'),
46
      'ajax' => FALSE,
47
      'description' => t('Add additional context objects to this variant that can be used by the content.'),
48
      'form' => array(
49
        'order' => array(
50
          'form' => t('Context'),
51
        ),
52
        'forms' => array(
53
          'form' => array(
54
            'include' => drupal_get_path('module', 'ctools') . '/includes/context-task-handler.inc',
55
            'form id' => 'ctools_context_handler_edit_context',
56
          ),
57
        ),
58
      ),
59
    ),
60
    'layout' => array(
61
      'title' => t('Layout'),
62
      'description' => t('Change the layout of this panel.'),
63
      // No AJAX so we get our CSS loaded.
64
      'ajax' => FALSE,
65
      'form' => array(
66
        'order' => array(
67
          'choose' => t('Change layout'),
68
          'move' => t('Move content from old layout'),
69
        ),
70
        'forms' => array(
71
          'choose' => array(
72
            'form id' => 'panels_panel_context_edit_layout',
73
          ),
74
          'move' => array(
75
            'include' => array(
76
              drupal_get_path('module', 'panels') . '/includes/display-layout.inc',
77
            ),
78
            'form id' => 'panels_panel_context_edit_move',
79
            'submit' => 'panels_change_layout_submit',
80
          ),
81
        ),
82
      ),
83
    ),
84
    'content' => array(
85
      'title' => t('Content'),
86
      'description' => t('Add content items and change their location with a drag and drop interface.'),
87
      'ajax' => FALSE,
88
      'form' => array(
89
        'order' => array(
90
          'form' => t('Content'),
91
        ),
92
        'forms' => array(
93
          'form' => array(
94
            'include' => array(
95
              drupal_get_path('module', 'panels') . '/includes/display-edit.inc',
96
            ),
97
            'form id' => 'panels_panel_context_edit_content',
98
            'no blocks' => TRUE,
99
          ),
100
        ),
101
      ),
102
    ),
103
    'preview' => array(
104
      'title' => t('Preview'),
105
      'description' => t('Get a preview of what this variant will look like.'),
106
      'form' => 'panels_panel_context_edit_preview',
107
      'ajax' => FALSE,
108
      'silent' => TRUE,
109
      'form info' => array('finish text' => t('Preview')),
110
      'no update and save' => TRUE,
111
    ),
112
  ),
113
114
  'tab operation' => 'panels_panel_context_tab_operation',
115
116
  // Callback to render the data.
117
  'render' => 'panels_panel_context_render',
118
  // Callback to return addressable data
119
  'addressable callback' => 'panels_panel_context_get_addressable',
120
121
  // Various callbacks for operations performed on the handler to ensure
122
  // related data is updated properly.
123
  'save' => 'panels_panel_context_save',
124
  'delete' => 'panels_panel_context_delete',
125
  'export' => 'panels_panel_context_export',
126
  'clone' => 'panels_panel_context_clone',
127
128
  'add features' => array(
129
    'criteria' => t('Selection rules'),
130
    'context' => t('Contexts'),
131
  ),
132
  // Where to go when finished.
133
  'add finish' => 'content',
134
135
  'required forms' => array(
136
    'choose' => t('Choose layout'),
137
    'settings' => t('Panel settings'),
138
    'content' => t('Panel content'),
139
  ),
140
141
  'edit forms' => array(
142
    'content' => t('Panel content'),
143
    'criteria' => t('Selection rules'),
144
    'settings' => t('General'),
145
    'context' => t('Contexts'),
146
    'layout' => t('Change layout'),
147
    'move' => '', // no title makes it a 'hidden' edit form.
148
  ),
149
  'forms' => array(
150
    'settings' => array(
151
      'form id' => 'panels_panel_context_edit_settings',
152
    ),
153
    'choose' => array(
154
      'form id' => 'panels_panel_context_edit_choose',
155
      'no back validate' => TRUE,
156
    ),
157
    'layout' => array(
158
      'no return' => TRUE,
159
      'form id' => 'panels_panel_context_edit_layout',
160
    ),
161
    'move' => array(
162
      'include' => array(
163
        drupal_get_path('module', 'panels') . '/includes/display-layout.inc',
164
      ),
165
      'form id' => 'panels_panel_context_edit_move',
166
      'submit' => 'panels_change_layout_submit',
167
    ),
168
    'content' => array(
169
      'include' => array(
170
        drupal_get_path('module', 'panels') . '/includes/display-edit.inc',
171
      ),
172
      'form id' => 'panels_panel_context_edit_content',
173
      'no blocks' => TRUE,
174
    ),
175
    'context' => array(
176
      'include' => drupal_get_path('module', 'ctools') . '/includes/context-task-handler.inc',
177
      'form id' => 'ctools_context_handler_edit_context',
178
    ),
179
    'criteria' => array(
180
      'include' => drupal_get_path('module', 'ctools') . '/includes/context-task-handler.inc',
181
      'form id' => 'ctools_context_handler_edit_criteria',
182
    ),
183
  ),
184
  'default conf' => array(
185
    'title' => t('Panel'),
186
    'no_blocks' => FALSE,
187 5a7e6170 Florent Torregrosa
    'pipeline' => variable_get('panels_renderer_default', 'standard'),
188 85ad3d82 Assos Assos
    'body_classes_to_remove' => '',
189
    'body_classes_to_add' => '',
190
    'css_id' => '',
191
    'css' => '',
192
    'contexts' => array(),
193
    'relationships' => array(),
194
  ),
195
);
196
197
/**
198
 * Provide the operation trail for the 'Edit panel' link.
199
 *
200
 * When editing the panel, go directly to the content tab.
201
 */
202
function panels_panel_context_tab_operation($handler, $contexts, $args) {
203
  return array('handlers', $handler->name, 'content');
204
}
205
206
/**
207
 * Get the display for a task handler.
208
 *
209
 * There are three methods that the display can be found.
210
 * - In the database. $handler->conf['did'] will be set in this case,
211
 *   and $handler->conf['display'] won't be.
212
 * - In $handler->conf['display'], with $handler->conf['did'] empty. This
213
 *   will be true for a default/imported task handler as well as a handler
214
 *   that has just been created but has not yet been saved.
215
 * - in $handler->conf['display'] with $handler->conf['did' populated. This
216
 *   simply means that the display has been modified and is awaiting
217
 *   save. The modified one should always be used for editing purposes.
218
 * - If none of the above is true, then a new display needs to be created
219
 *   for the handler and pla
220
 */
221
function &panels_panel_context_get_display(&$handler) {
222 08475715 Assos Assos
  if (!isset($handler->conf['display'])) {
223
    if (isset($handler->conf['did'])) {
224
      $handler->conf['display'] = panels_load_display($handler->conf['did']);
225
    }
226 85ad3d82 Assos Assos
227 08475715 Assos Assos
    // Check for again for a valid display. If no valid display could be loaded,
228
    // something is wrong and we'll create a new one.
229
    if (empty($handler->conf['display'])) {
230
      $handler->conf['display'] = panels_new_display();
231 85ad3d82 Assos Assos
    }
232
  }
233
234 08475715 Assos Assos
  $display =& $handler->conf['display'];
235
  $display->storage_type = 'page_manager';
236
  $display->storage_id = !empty($handler->name) ? $handler->name : 'new';
237 85ad3d82 Assos Assos
238 08475715 Assos Assos
  return $display;
239 85ad3d82 Assos Assos
}
240
241 5a7e6170 Florent Torregrosa
/**
242
 * Build the cache key so that the editor and IPE can properly find
243
 * everything needed for this display.
244
 */
245
function panels_panel_context_cache_key($task_name, $handler_id, $args) {
246
  $arguments = array();
247
  foreach ($args as $arg) {
248
    // Sadly things like panels everywhere actually use non-string arguments
249
    // and they basically can't be represented here. Luckily, PE also does
250
    // not use a system where this matters, so replace its args with a 0
251
    // for a placeholder.
252
    if (is_string($arg)) {
253
      $arguments[] = $arg;
254
    }
255
    else {
256
      $arguments[] = '0';
257
    }
258
  }
259
  $cache_key = 'panel_context:' . $task_name . '::' . $handler_id . '::' . implode('\\', $arguments) . '::';
260
  return $cache_key;
261
}
262
263 85ad3d82 Assos Assos
/**
264
 * Check selection rules and, if passed, render the contexts.
265
 */
266
function panels_panel_context_render($handler, $base_contexts, $args, $test = TRUE) {
267
  // Go through arguments and see if they match.
268
  ctools_include('context');
269
  ctools_include('context-task-handler');
270
  ctools_include('plugins', 'panels');
271
272
  // Add my contexts
273
  $contexts = ctools_context_handler_get_handler_contexts($base_contexts, $handler);
274
275
  // Test.
276
  if ($test && !ctools_context_handler_select($handler, $contexts)) {
277
    return;
278
  }
279
280
  if (isset($handler->handler)) {
281
    ctools_context_handler_pre_render($handler, $contexts, $args);
282
  }
283
284
  // Load the display
285
  $display = panels_panel_context_get_display($handler);
286
287
  $display->context = $contexts;
288
  $display->args = $args;
289 136a805a Assos Assos
  $page_css_id = ctools_context_keyword_substitute($handler->conf['css_id'], array(), $contexts);
290 2545992a Assos Assos
  $display->css_id = check_plain($page_css_id);
291 85ad3d82 Assos Assos
  $task_name = page_manager_make_task_name($handler->task, $handler->subtask);
292
293 5a7e6170 Florent Torregrosa
  $display->cache_key = panels_panel_context_cache_key($task_name, $handler->name, $args);
294 85ad3d82 Assos Assos
295
  // Check to see if there is any CSS.
296
  if (!empty($handler->conf['css'])) {
297
    ctools_include('css');
298
    $css_id = 'panel_context:' . $handler->name;
299
    $filename = ctools_css_retrieve($css_id);
300
    if (!$filename) {
301 136a805a Assos Assos
      // Add keywords from context
302
      $css = ctools_context_keyword_substitute($handler->conf['css'], array(), $contexts, array('css safe' => TRUE));
303
      $filename = ctools_css_store($css_id, $css);
304 85ad3d82 Assos Assos
    }
305
    drupal_add_css($filename);
306
  }
307
308
  // With an argument, this actually sets the display.
309
  panels_get_current_page_display($display);
310
311
  $renderer = panels_get_renderer($handler->conf['pipeline'], $display);
312 5a7e6170 Florent Torregrosa
  // If the IPE is enabled, but the user does not have access to edit
313
  // load the standard renderer instead.
314
315
  $parents = class_parents($renderer);
316
  if (!empty($parents['panels_renderer_editor']) && !user_access('user page manager') && !user_access('use ipe with page manager')) {
317
    $renderer = panels_get_renderer_handler('standard', $display);
318
  }
319 85ad3d82 Assos Assos
320
  // Remove and add body element classes
321
  $panel_body_css = &drupal_static('panel_body_css');
322
323 e4c061ad Assos Assos
  if (isset($handler->conf['body_classes_to_remove'])) {
324 136a805a Assos Assos
    $classes = ctools_context_keyword_substitute($handler->conf['body_classes_to_remove'], array(), $contexts, array('css safe' => TRUE));
325 e4c061ad Assos Assos
    if (!isset($panel_body_css['body_classes_to_remove'])) {
326 2545992a Assos Assos
      $panel_body_css['body_classes_to_remove'] = check_plain($classes);
327 e4c061ad Assos Assos
    }
328
    else{
329 2545992a Assos Assos
      $panel_body_css['body_classes_to_remove'] .= ' ' . check_plain($classes);
330 e4c061ad Assos Assos
    }
331 85ad3d82 Assos Assos
  }
332 e4c061ad Assos Assos
  if (isset($handler->conf['body_classes_to_add'])) {
333 136a805a Assos Assos
    $classes = ctools_context_keyword_substitute($handler->conf['body_classes_to_add'], array(), $contexts, array('css safe' => TRUE));
334 e4c061ad Assos Assos
    if (!isset($panel_body_css['body_classes_to_add'])) {
335 2545992a Assos Assos
    $panel_body_css['body_classes_to_add'] = check_plain($classes);
336 e4c061ad Assos Assos
    }
337
    else {
338 2545992a Assos Assos
      $panel_body_css['body_classes_to_add'] .= ' '. check_plain($classes);
339 e4c061ad Assos Assos
    }
340 85ad3d82 Assos Assos
  }
341
342
  $info = array(
343
    'content' => panels_render_display($display, $renderer),
344
    'no_blocks' => !empty($handler->conf['no_blocks']),
345
  );
346
347
  $info['title'] = $display->get_title();
348
349
  return $info;
350
}
351
352
/**
353
 * Callback to allow the handler to react to being saved.
354
 *
355
 * When a handler with a display is saved, two things have to happen.
356
 * First, we have to save the display so that it becomes a real display,
357
 * not the fake one we started with. Second, we have to cache
358
 * any CSS that the display is using. This CSS can get re-cached
359
 * later if the file disappears, but it's imperative that we do it here
360
 * to make sure that old, dirty CSS cache gets removed.
361
 */
362
function panels_panel_context_save(&$handler, $update) {
363
  // Only save the display if we believe it has been modified.
364
  if (isset($handler->conf['display'])) {
365
    panels_save_display($handler->conf['display']);
366
    $handler->conf['did'] = $handler->conf['display']->did;
367
    unset($handler->conf['display']);
368
  }
369
370
  // Delete any previous CSS cache file.
371
  ctools_include('css');
372
  ctools_css_clear('panel_context:' . $handler->name);
373
374 08475715 Assos Assos
  if (isset($handler->conf['temp_layout'])) {
375
    unset($handler->conf['temp_layout']);
376 85ad3d82 Assos Assos
  }
377
}
378
379
/**
380
 * Special handling for exporting a panel task handler.
381
 *
382
 * When a panel is exported, we need to export the display separately
383
 * rather than just letting its object be unpacked, which does not work
384
 * very well.
385
 */
386
function panels_panel_context_export(&$handler, $indent) {
387
  $display = panels_panel_context_get_display($handler);
388
  foreach (array('display', 'did', 'css_cache', 'temp_layout') as $item) {
389
    if (isset($handler->conf[$item])) {
390
      unset($handler->conf[$item]);
391
    }
392
  }
393
394
  $output = panels_export_display($display, $indent);
395
  $output .= $indent . '$handler->conf[\'display\'] = $display' . ";\n";
396
  return $output;
397
}
398
399
/**
400
 * When a handler is cloned, we have to clone the display.
401
 */
402
  function panels_panel_context_clone(&$handler) {
403
  $old_display = panels_panel_context_get_display($handler);
404
  $code = panels_export_display($old_display);
405
  eval($code);
406
  foreach (array('display', 'did', 'css_cache', 'temp_layout') as $item) {
407
    if (isset($handler->conf[$item])) {
408
      unset($handler->conf[$item]);
409
    }
410
  }
411 5a7e6170 Florent Torregrosa
  $display = (object) array(
412
    'did' => 'new',
413
    'uuid' => ctools_uuid_generate(),
414
  );
415 85ad3d82 Assos Assos
  $handler->conf['display'] = $display;
416
}
417
418
/**
419
 * Callback to delete the display when a handler is deleted.
420
 */
421
function panels_panel_context_delete(&$handler) {
422
  if (!empty($handler->conf['did'])) {
423
    panels_delete_display($handler->conf['did']);
424
  }
425
}
426
427
/**
428
 * Set up a title for the panel based upon the selection rules.
429
 */
430
function panels_panel_context_title($handler, $task, $subtask) {
431
  if (isset($handler->conf['title'])) {
432
    return check_plain($handler->conf['title']);
433
  }
434
  else {
435
    return t('Panel');
436
  }
437
}
438
439
/**
440
 * Provide a nice little summary of what's in a panel.
441
 *
442
 * The task handler manager provides a summary of a given handler in a
443
 * collapsible div. This callback provides that. For a Panel, we
444
 * provide a summary of the layout type and content on one side, and
445
 * a summary of the contexts in use on the other.
446
 */
447
function panels_panel_context_admin_summary($handler, $task, $subtask, $page, $show_title = TRUE) {
448
  $task_name = page_manager_make_task_name($task['name'], $subtask['name']);
449
  $output = '';
450
451
  $display = panels_panel_context_get_display($handler);
452
453
  ctools_include('plugins', 'panels');
454
  ctools_include('context');
455
  ctools_include('context-task-handler');
456
457
  // Get the operations
458
  $operations = page_manager_get_operations($page);
459
460
  // Get operations for just this handler.
461
  $operations = $operations['handlers']['children'][$handler->name]['children']['actions']['children'];
462
  $args = array('handlers', $handler->name, 'actions');
463
  $rendered_operations = page_manager_render_operations($page, $operations, array(), array('class' => array('actions')), 'actions', $args);
464
465
  $layout = panels_get_layout($display->layout);
466
467
  $plugin = page_manager_get_task_handler($handler->handler);
468
469
  $object = ctools_context_handler_get_task_object($task, $subtask, $handler);
470
  $display->context = ctools_context_load_contexts($object, TRUE);
471
472
  $access = ctools_access_group_summary(!empty($handler->conf['access']) ? $handler->conf['access'] : array(), $display->context);
473
  if ($access) {
474
    $access = t('This panel will be selected if @conditions.', array('@conditions' => $access));
475
  }
476
  else {
477
    $access = t('This panel will always be selected.');
478
  }
479
480
  $rows = array();
481
482
  $type = $handler->type == t('Default') ? t('In code') : $handler->type;
483
  $rows[] = array(
484
    array('class' => t('page-summary-label'), 'data' => t('Storage')),
485
    array('class' => t('page-summary-data'), 'data' => $type),
486
    array('class' => t('page-summary-operation'), 'data' => ''),
487
  );
488
489
  if (!empty($handler->disabled)) {
490
    $link = l(t('Enable'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'actions', 'enable')));
491
    $text = t('Disabled');
492
  }
493
  else {
494
    $link = l(t('Disable'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'actions', 'disable')));
495
    $text = t('Enabled');
496
  }
497
498
  $rows[] = array(
499
    array('class' => t('page-summary-label'), 'data' => t('Status')),
500
    array('class' => t('page-summary-data'), 'data' => $text),
501
    array('class' => t('page-summary-operation'), 'data' => $link),
502
  );
503
504
  $link = l(t('Edit'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'criteria')));
505
  $rows[] = array(
506
    array('class' => t('page-summary-label'), 'data' => t('Selection rule')),
507
    array('class' => t('page-summary-data'), 'data' => $access),
508
    array('class' => t('page-summary-operation'), 'data' => $link),
509
  );
510
511
  $link = l(t('Change layout'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'layout')));
512
  $link .= '<br />' . l(t('Edit content'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'content')));
513
  $link .= '<br />' . l(t('Preview'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'preview')));
514
  $rows[] = array(
515
    array('class' => t('page-summary-label'), 'data' => t('Layout')),
516
    array('class' => t('page-summary-data'), 'data' => check_plain($layout['title'])),
517
    array('class' => t('page-summary-operation'), 'data' => $link),
518
  );
519
520
  $content_link = ' [' . l(t('Edit'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'content'))) . ']';
521
  $context_link = ' [' . l(t('Edit'), page_manager_edit_url($task_name, array('handlers', $handler->name, 'context'))) . ']';
522
523
  $info = theme('table', array('rows' => $rows, 'attributes' => array('class' => 'page-manager-handler-summary')));
524
525
  $title = $handler->conf['title'];
526
  if ($title != t('Panel')) {
527
    $title = t('Panel: @title', array('@title' => $title));
528
  }
529
530
  $output .= '<div class="clearfix">';
531
  if ($show_title) {
532
  $output .= '<div class="handler-title clearfix">';
533
    $output .= '<div class="actions handler-actions">' . $rendered_operations['actions'] . '</div>';
534
    $output .= '<span class="title-label">' . $title . '</span>';
535
  }
536
537
  $output .= '</div>';
538
  $output .= $info;
539
  $output .= '</div>';
540
/*
541
  $output .= '<div class="right-container">';
542
  $output .= '<h3 class="context-title">' . t('Contexts') . $context_link . '</h3>';
543
  $output .= $contexts;
544
  $output .= '</div>';
545
546
  $output .= '<div class="left-container">';
547
//  $output .= $icon;
548
  $output .= '<h3 class="handler-title">' . t('Content') . $content_link . '</h3>';
549
  $output .= $content;
550
  $output .= '</div>';
551
*/
552
  return $output;
553
}
554
555
// --------------------------------------------------------------------------
556
// Forms
557
558
/**
559
 * General notes about forms: The handler is automatically cached by the form
560
 * wizard, so anything we store on $form_state['handler'] anywhere will get
561
 * saved and appear on the next form. The cache is a 'working' cache and
562
 * if the user hits cancel on any page of the multi-page wizard, all
563
 * changes since the last 'update/finish' click will be flushed away.
564
 *
565
 * Many of the Panels forms call through to the real Panels cousins. These
566
 * forms are smart enough to know that they're being wrapped in another
567
 * form and act appropriately. Some of them are so smart that we just let
568
 * their submit and validate handlers do the work rather than writing
569
 * additional ones here.
570
 */
571
572
/**
573
 * Choose a layout for this panel.
574
 *
575
 * This is only called during 'add', when we know that there isn't a
576
 * previous layout to choose from. a different, only slightly different
577
 * variant is called to change a pre-existing layout.
578
 */
579
function panels_panel_context_edit_choose($form, &$form_state) {
580
  ctools_include('common', 'panels');
581
  ctools_include('display-layout', 'panels');
582
  ctools_include('plugins', 'panels');
583
584
  // @todo -- figure out where/how to deal with this.
585
  $form_state['allowed_layouts'] = 'panels_page';
586
587
  $form_state['display'] = &panels_panel_context_get_display($form_state['handler']);
588
589
  // Tell the Panels form not to display buttons.
590
  $form_state['no buttons'] = TRUE;
591
592
  // Change the #id of the form so the CSS applies properly.
593
  $form['#id'] = 'panels-choose-layout';
594
  $form = panels_choose_layout($form, $form_state);
595
596
  return $form;
597
}
598
599
/**
600
 * Validate that a layout was chosen.
601
 */
602
function panels_panel_context_edit_choose_validate(&$form, &$form_state) {
603
  if (empty($form_state['values']['layout'])) {
604
    form_error($form['layout'], t('You must select a layout.'));
605
  }
606
}
607
608
/**
609
 * A layout has been selected, set it up.
610
 */
611
function panels_panel_context_edit_choose_submit(&$form, &$form_state) {
612
  $form_state['display']->layout = $form_state['values']['layout'];
613
  $form_state['handler']->conf['display'] = $form_state['display'];
614
  if (isset($form_state['page']->display_cache[$form_state['handler_id']])) {
615
    $form_state['page']->display_cache[$form_state['handler_id']]->display = $form_state['display'];
616
  }
617
}
618
619
/**
620
 * Change the layout for this panel.
621
 *
622
 * This form is only used if a layout already exists and the user wants
623
 * to change to a different one. The submit handler changes the next form
624
 * to the move content form, which is 'hidden' so it won't be accessed
625
 * directly.
626
 */
627
function panels_panel_context_edit_layout($form, &$form_state) {
628
  ctools_include('common', 'panels');
629
  ctools_include('display-layout', 'panels');
630
  ctools_include('plugins', 'panels');
631
632
  // @todo -- figure out where/how to deal with this.
633
  $form_state['allowed_layouts'] = 'panels_page';
634
635
  $form_state['display'] = &panels_panel_context_get_display($form_state['handler']);
636
637
  // Tell the Panels form not to display buttons.
638
  $form_state['no buttons'] = TRUE;
639
640
  // Change the #id of the form so the CSS applies properly.
641
  $form['#id'] = 'panels-choose-layout';
642
  $form = panels_choose_layout($form, $form_state);
643
644
  return $form;
645
}
646
647
/**
648
 * Validate that a layout was chosen.
649
 */
650
function panels_panel_context_edit_layout_validate(&$form, &$form_state) {
651
  $display = &panels_panel_context_get_display($form_state['handler']);
652
653
  if (empty($form_state['values']['layout'])) {
654
    form_error($form['layout'], t('You must select a layout.'));
655
  }
656
  if ($form_state['values']['layout'] == $display->layout) {
657
    form_error($form['layout'], t('You must select a different layout if you wish to change layouts.'));
658
  }
659
}
660
661
/**
662
 * A layout has been selected, set it up.
663
 */
664
function panels_panel_context_edit_layout_submit(&$form, &$form_state) {
665
  $display = &panels_panel_context_get_display($form_state['handler']);
666
667
  if ($form_state['values']['layout'] != $display->layout) {
668
    $form_state['handler']->conf['temp_layout'] = $form_state['values']['layout'];
669
  }
670
}
671
672
/**
673
 * When a layout is changed, the user is given the opportunity to move content.
674
 */
675
function panels_panel_context_edit_move($form, &$form_state) {
676
  $form_state['display'] = &panels_panel_context_get_display($form_state['handler']);
677
  $form_state['layout'] = $form_state['handler']->conf['temp_layout'];
678
679 5a7e6170 Florent Torregrosa
  $form_state['cache_key'] = panels_panel_context_cache_key($form_state['task_name'], $form_state['handler_id'], array());
680 85ad3d82 Assos Assos
681
  ctools_include('common', 'panels');
682
  ctools_include('display-layout', 'panels');
683
  ctools_include('plugins', 'panels');
684
685
  // Tell the Panels form not to display buttons.
686
  $form_state['no buttons'] = TRUE;
687
688
  // Change the #id of the form so the CSS applies properly.
689
  $form = panels_change_layout($form, $form_state);
690
691
  // Change the 'back' button to just go directly to the previous form
692
//  $task_id = $form_state['task']['name'];
693
//  $handler_id = $form_state['handler']->handler;
694
//  $name = $form_state['handler']->name;
695
696
  // This form is outside the normal wizard list, so we need to specify the
697
  // previous/next forms.
698
  $form['buttons']['previous']['#next'] = 'layout';
699
  $form['buttons']['next']['#next'] = 'content';
700
701
  $form_state['form_info']['return path'] = page_manager_edit_url($form_state['page']->task_name, array('handlers', $form_state['handler_id'], 'content'));
702
  return $form;
703
}
704
705
/**
706
 * Present the panels drag & drop editor to edit the display attached
707
 * to the task handler.
708
 */
709
function panels_panel_context_edit_content($form, &$form_state) {
710
  ctools_include('ajax');
711
  ctools_include('plugins', 'panels');
712
  ctools_include('common', 'panels');
713
  ctools_include('context');
714
  ctools_include('context-task-handler');
715
716 5a7e6170 Florent Torregrosa
  $cache = panels_edit_cache_get(panels_panel_context_cache_key($form_state['task_name'], $form_state['handler_id'], array()));
717 85ad3d82 Assos Assos
718
  $form_state['renderer'] = panels_get_renderer_handler('editor', $cache->display);
719
  $form_state['renderer']->cache = &$cache;
720
721
  $form_state['display'] = &$cache->display;
722
  $form_state['content_types'] = $cache->content_types;
723
  // Tell the Panels form not to display buttons.
724
  $form_state['no buttons'] = TRUE;
725
  $form_state['display_title'] = !empty($cache->display_title);
726
  $form_state['no preview'] = TRUE;
727
  $form_state['page']->display_cache[$form_state['handler_id']] = $cache;
728
729
  $form = panels_edit_display_form($form, $form_state);
730
731
  if (!isset($form_state['type']) || $form_state['type'] != 'add' && !empty($form_state['handler_id']) && !empty($form['buttons'])) {
732
    $form['buttons']['preview'] = $form['buttons']['return'];
733
    $form['buttons']['preview']['#value'] = t('Update and preview');
734
  }
735
  return $form;
736
}
737
738
/**
739
 * Validate changes to the panel content form.
740
 */
741
function panels_panel_context_edit_content_validate(&$form, &$form_state) {
742
  panels_edit_display_form_validate($form, $form_state);
743
}
744
745
function panels_panel_context_edit_content_submit(&$form, &$form_state) {
746 136a805a Assos Assos
  // Update the storage_id if this is a new variant before saving.
747
  if ($form_state['display']->storage_id == 'new') {
748
    $form_state['display']->storage_id = $form_state['handler_id'];
749
  }
750 85ad3d82 Assos Assos
  panels_edit_display_form_submit($form, $form_state);
751
  $handler = &$form_state['handler'];
752
753
  // update the cached display:
754
  $display = $form_state['page']->display_cache[$form_state['handler_id']]->display;
755
  $handler->conf['display'] = $display;
756
  unset($form_state['page']->display_cache[$form_state['handler_id']]);
757
758
  if ($form_state['clicked_button']['#value'] == t('Update and preview')) {
759
    $form_state['new trail'] = array('handlers', $form_state['handler_id'], 'preview');
760
  }
761
}
762
763
/**
764
 * General settings for the panel
765
 */
766
function panels_panel_context_edit_settings($form, &$form_state) {
767
  $conf = $form_state['handler']->conf;
768
  $form['conf']['title'] = array(
769
    '#type' => 'textfield',
770
    '#default_value' => $conf['title'],
771
    '#title' => t('Administrative title'),
772
    '#description' => t('Administrative title of this variant.'),
773
  );
774
775
  $form['conf']['no_blocks'] = array(
776
    '#type' => 'checkbox',
777
    '#default_value' => $conf['no_blocks'],
778
    '#title' => t('Disable Drupal blocks/regions'),
779
    '#description' => t('Check this to have the page disable all regions displayed in the theme. Note that some themes support this setting better than others. If in doubt, try with stock themes to see.'),
780
  );
781
782
  $form['conf']['body_classes_to_remove'] = array(
783
    '#type' => 'textfield',
784
    '#size' => 128,
785 e4c061ad Assos Assos
    '#default_value' => empty($conf['body_classes_to_remove']) ? '' : $conf['body_classes_to_remove'],
786 85ad3d82 Assos Assos
    '#title' => t('Remove body CSS classes'),
787 136a805a Assos Assos
    '#description' => t('The CSS classes to remove from the body element of this page. Separated by a space. For example: no-sidebars one-sidebar sidebar-first sidebar-second two-sidebars. Keywords from context are allowed.'),
788 85ad3d82 Assos Assos
  );
789
790
  $form['conf']['body_classes_to_add'] = array(
791
    '#type' => 'textfield',
792
    '#size' => 128,
793 e4c061ad Assos Assos
    '#default_value' => empty($conf['body_classes_to_add']) ? '' : $conf['body_classes_to_add'],
794 85ad3d82 Assos Assos
    '#title' => t('Add body CSS classes'),
795 136a805a Assos Assos
    '#description' => t('The CSS classes to add to the body element of this page. Separated by a space. For example: no-sidebars one-sidebar sidebar-first sidebar-second two-sidebars. Keywords from context are allowed.'),
796 85ad3d82 Assos Assos
  );
797
798
  ctools_include('plugins', 'panels');
799
  $pipelines = panels_get_renderer_pipelines();
800
801
  // Handle backward compatibility with the IPE checkbox.
802
  if (empty($conf['pipeline'])) {
803
    $conf['pipeline'] = !empty($conf['use_ipe']) ? 'ipe' : 'standard';
804
  }
805
806
  // If there are no pipelines, that probably means we're operating in
807
  // legacy mode.
808
  if (empty($pipelines)) {
809
    // We retain the original pipeline so we don't wreck things by installing
810
    // old modules.
811
    $form['conf']['pipeline'] = array(
812
      '#type' => 'value',
813
      '#value' => $conf['pipeline'],
814
    );
815
  }
816
  else {
817
    $options = array();
818
    foreach ($pipelines as $name => $pipeline) {
819
      $options[$name] = check_plain($pipeline->admin_title) . '<div class="description">' . check_plain($pipeline->admin_description) . '</div>';
820
    }
821
822
    $form['conf']['pipeline'] = array(
823
      '#type' => 'radios',
824
      '#options' => $options,
825
      '#title' => t('Renderer'),
826
      '#default_value' => $conf['pipeline'],
827
    );
828
  }
829
830
  $form['conf']['css_id'] = array(
831
    '#type' => 'textfield',
832
    '#size' => 35,
833
    '#default_value' => $conf['css_id'],
834
    '#title' => t('CSS ID'),
835 136a805a Assos Assos
    '#description' => t('The CSS ID to apply to this page. Keywords from context are allowed.'),
836 85ad3d82 Assos Assos
  );
837
838
  $form['conf']['css'] = array(
839
    '#type' => 'textarea',
840
    '#title' => t('CSS code'),
841 136a805a Assos Assos
    '#description' => t('Enter well-formed CSS code here; this code will be embedded into the page, and should only be used for minor adjustments; it is usually better to try to put CSS for the page into the theme if possible. This CSS will be filtered for safety so some CSS may not work. Keywords from context are allowed.'),
842 85ad3d82 Assos Assos
    '#default_value' => $conf['css'],
843
  );
844
845
  return $form;
846
}
847
848
/**
849
 * Submit handler for general settings form.
850
 */
851
function panels_panel_context_edit_settings_submit(&$form, &$form_state) {
852
  $form_state['handler']->conf['no_blocks'] = $form_state['values']['no_blocks'];
853
  $form_state['handler']->conf['body_classes_to_remove'] = $form_state['values']['body_classes_to_remove'];
854
  $form_state['handler']->conf['body_classes_to_add'] = $form_state['values']['body_classes_to_add'];
855
  $form_state['handler']->conf['pipeline'] = $form_state['values']['pipeline'];
856
  $form_state['handler']->conf['css_id'] = $form_state['values']['css_id'];
857
  $form_state['handler']->conf['css'] = $form_state['values']['css'];
858
  $form_state['handler']->conf['title'] = $form_state['values']['title'];
859
860
  // Unset the old checkbox so we don't store needless data.
861
  if (isset($form_state['handler']->conf['use_ipe'])) {
862
    unset($form_state['handler']->conf['use_ipe']);
863
  }
864
}
865
866
/**
867
 * Form to show a nice preview.
868
 */
869
function panels_panel_context_edit_preview($form, &$form_state) {
870
  ctools_include('context');
871
  ctools_include('context-task-handler');
872
873
  $contexts = ctools_context_handler_get_all_contexts($form_state['task'], $form_state['subtask'], $form_state['handler']);
874
  $form['preview'] = array();
875
  ctools_context_replace_form($form['preview'], $contexts);
876
877
  // automatically preview if there are no argument placeholders.
878
  if (empty($form['preview'])) {
879
    $display = panels_panel_context_get_display($form_state['handler']);
880
    $display->context = $contexts;
881
    $display->skip_cache = TRUE;
882
    $output = panels_render_display($display);
883
    if (isset($form['buttons'])) {
884
      unset($form['buttons']);
885
    }
886
  }
887
  else {
888
    $form['preview']['#tree'] = TRUE;
889
    $form_state['contexts'] = $contexts;
890
  }
891
892
  if (!empty($output)) {
893
    $form['output'] = array(
894
      '#markup' => $output,
895
    );
896
  }
897
898
  $form_state['do not cache'] = TRUE;
899
900
  return $form;
901
}
902
903
/**
904
 * Display a preview upon submit if arguments were needed.
905
 */
906
function panels_panel_context_edit_preview_submit(&$form, &$form_state) {
907
  $display = panels_panel_context_get_display($form_state['handler']);
908
  $display->context = ctools_context_replace_placeholders($form_state['contexts'], $form_state['values']['preview']);
909
910
  $form_state['content'] = panels_render_display($display);
911
  $form_state['redirect'] = FALSE;
912
  $form_state['rerender'] = TRUE;
913
}
914
915
function panels_panel_context_get_addressable($task, $subtask_name, $handler, $address, $contexts, $arguments, $type) {
916
  // Load the display
917
  $display = panels_panel_context_get_display($handler);
918
919
  $display->context = $contexts;
920
  $display->args = $arguments;
921
  $display->css_id = $handler->conf['css_id'];
922 5a7e6170 Florent Torregrosa
  $display->cache_key = panels_panel_context_cache_key($task->name, $handler->name, $arguments);
923 85ad3d82 Assos Assos
924
  $renderer = panels_get_renderer($handler->conf['pipeline'], $display);
925 5a7e6170 Florent Torregrosa
  $renderer->prepare();
926 85ad3d82 Assos Assos
927 5a7e6170 Florent Torregrosa
  if ($address) {
928 85ad3d82 Assos Assos
    $pid = array_shift($address);
929
    if (!empty($renderer->prepared['panes'][$pid])) {
930 5a7e6170 Florent Torregrosa
      if ($type == 'content') {
931
        return $renderer->render_pane($renderer->prepared['panes'][$pid]);
932
      }
933
      elseif ($type == 'pane') {
934
        return $renderer->prepared['panes'][$pid];
935
      }
936
    }
937
  }
938
  else {
939
    if ($type == 'content') {
940
      return $renderer->render();
941
    }
942
    elseif ($type == 'renderer') {
943
      return $renderer;
944 85ad3d82 Assos Assos
    }
945
  }
946
}