Projet

Général

Profil

Paste
Télécharger (63,4 ko) Statistiques
| Branche: | Révision:

root / drupal7 / sites / all / modules / panels / plugins / display_renderers / panels_renderer_editor.class.php @ e4c061ad

1 85ad3d82 Assos Assos
<?php
2
3
/**
4
 * @file
5
 * Class file to control the main Panels editor.
6
 */
7
8
class panels_renderer_editor extends panels_renderer_standard {
9
10
  /**
11
   * An array of AJAX commands to return. If populated it will automatically
12
   * be used by the AJAX router.
13
   */
14
  var $commands = array();
15
  var $admin = TRUE;
16
17
  /**
18
   * Set to true if edit links (for panes and regions) should not be displayed.
19
   * This can be used for special edit modes such as layout change and layout
20
   * builder that do not actually have real content.
21
   */
22
  var $no_edit_links = FALSE;
23
  // -------------------------------------------------------------------------
24
  // Display edit rendering.
25
26
  function edit() {
27
    $form_state = array(
28
      'display' => &$this->display,
29
      'renderer' => &$this,
30
      'content_types' => $this->cache->content_types,
31
      'no_redirect' => TRUE,
32
      'display_title' => !empty($this->cache->display_title),
33
      'cache key' => $this->display->cache_key,
34
    );
35
36
    $output = drupal_build_form('panels_edit_display_form', $form_state);
37
    if (empty($form_state['executed']) || !empty($form_state['clicked_button']['preview'])) {
38
      return $output;
39
    }
40
41
    if (!empty($form_state['clicked_button']['#save-display'])) {
42
      drupal_set_message(t('Panel content has been updated.'));
43
      panels_save_display($this->display);
44
    }
45
    else {
46
      drupal_set_message(t('Your changes have been discarded.'));
47
    }
48
49
    panels_cache_clear('display', $this->display->did);
50
    return $this->display;
51
  }
52
53
  function add_meta() {
54
    parent::add_meta();
55
    if ($this->admin) {
56
      ctools_include('ajax');
57
      ctools_include('modal');
58
      ctools_modal_add_js();
59
60
      ctools_add_js('panels-base', 'panels');
61
      ctools_add_js('display_editor', 'panels');
62
      ctools_add_css('panels_dnd', 'panels');
63
      ctools_add_css('panels_admin', 'panels');
64
    }
65
  }
66
67
  function render() {
68
    // Pass through to normal rendering if not in admin mode.
69
    if (!$this->admin) {
70
      return parent::render();
71
    }
72
73
    $this->add_meta();
74
75
    $output = '<div class="panels-dnd" id="panels-dnd-main">';
76
    $output .= $this->render_layout();
77
    $output .= '</div>';
78
79
    return $output;
80
  }
81
82
  function render_region($region_id, $panes) {
83
    // Pass through to normal rendering if not in admin mode.
84
    if (!$this->admin) {
85
      return parent::render_region($region_id, $panes);
86
    }
87
88
    $content = implode('', $panes);
89
90
    $panel_buttons = $this->get_region_links($region_id);
91
92
    $output = "<div class='panel-region' id='panel-region-$region_id'>";
93
    $output .= $panel_buttons;
94
    $output .= "<h2 class='label'>" . check_plain($this->plugins['layout']['regions'][$region_id]) . "</h2>";
95
    $output .= $content;
96
    $output .= "</div>";
97
98
    return $output;
99
  }
100
101
  function render_pane(&$pane) {
102
    // Pass through to normal rendering if not in admin mode.
103
    if (!$this->admin) {
104
      return parent::render_pane($pane);
105
    }
106
107
    ctools_include('content');
108
    $content_type = ctools_get_content_type($pane->type);
109
110
    // This is just used for the title bar of the pane, not the content itself.
111
    // If we know the content type, use the appropriate title for that type,
112
    // otherwise, set the title using the content itself.
113
    $title = ctools_content_admin_title($content_type, $pane->subtype, $pane->configuration, $this->display->context);
114
    if (!$title) {
115
      $title = t('Deleted/missing content type @type', array('@type' => $pane->type));
116
    }
117
118
    $buttons = $this->get_pane_links($pane, $content_type);
119
120
    // Render administrative buttons for the pane.
121
122
    $block = new stdClass();
123
    if (empty($content_type)) {
124
      $block->title = '<em>' . t('Missing content type') . '</em>';
125
      $block->content = t('This pane\'s content type is either missing or has been deleted. This pane will not render.');
126
    }
127
    else {
128
      $block = ctools_content_admin_info($content_type, $pane->subtype, $pane->configuration, $this->display->context);
129
    }
130
131
    $grabber_class = 'grab-title grabber';
132
    // If there are region locks, add them.
133
    if (!empty($pane->locks['type'])) {
134
      if ($pane->locks['type'] == 'regions') {
135
        $settings['Panels']['RegionLock'][$pane->pid] = $pane->locks['regions'];
136
        drupal_add_js($settings, 'setting');
137
      }
138
      else if ($pane->locks['type'] == 'immovable') {
139
        $grabber_class = 'grab-title not-grabber';
140
      }
141
    }
142
143
    $output = '';
144
    $class = 'panel-pane';
145
146
    if (empty($pane->shown)) {
147
      $class .= ' hidden-pane';
148
    }
149
150
    if (isset($this->display->title_pane) && $this->display->title_pane == $pane->pid) {
151
      $class .= ' panel-pane-is-title';
152
    }
153
154
    $output = '<div class="' . $class . '" id="panel-pane-' . $pane->pid . '">';
155
156 5a7e6170 Florent Torregrosa
    if (empty($block->title)) {
157 85ad3d82 Assos Assos
      $block->title = t('No title');
158
    }
159
160
    $output .= '<div class="' . $grabber_class . '">';
161
    if ($buttons) {
162
      $output .= '<span class="buttons">' . $buttons . '</span>';
163
    }
164 e4c061ad Assos Assos
    $output .= '<span class="text" title="' . check_plain($title) . '">' . $title . '</span>';
165 85ad3d82 Assos Assos
    $output .= '</div>'; // grabber
166
167
    $output .= '<div class="panel-pane-collapsible">';
168
    $output .= '<div class="pane-title">' . $block->title . '</div>';
169
    $output .= '<div class="pane-content">' . filter_xss_admin(render($block->content)) . '</div>';
170
    $output .= '</div>'; // panel-pane-collapsible
171
172
    $output .= '</div>'; // panel-pane
173
174
    return $output;
175
  }
176
177
  /**
178
   * Get the style links.
179
   *
180
   * This is abstracted out since we have styles on both panes and regions.
181
   */
182
  function get_style_links($type, $id = NULL) {
183
    $info = $this->get_style($type, $id);
184
    $style = $info[0];
185
    $conf = $info[1];
186
187
    $style_title = isset($style['title']) ? $style['title'] : t('Default');
188
189 5a7e6170 Florent Torregrosa
    $style_links['title'] = array(
190 85ad3d82 Assos Assos
      'title' => $style_title,
191
      'attributes' => array('class' => array('panels-text')),
192
    );
193
194 5a7e6170 Florent Torregrosa
    $style_links['change'] = array(
195 85ad3d82 Assos Assos
      'title' => t('Change'),
196
      'href' => $this->get_url('style-type', $type, $id),
197
      'attributes' => array('class' => array('ctools-use-modal')),
198
    );
199
200
    $function = $type != 'pane' ? 'settings form' : 'pane settings form';
201
    if (panels_plugin_get_function('styles', $style, $function)) {
202 5a7e6170 Florent Torregrosa
      $style_links['settings'] = array(
203 85ad3d82 Assos Assos
        'title' => t('Settings'),
204
        'href' => $this->get_url('style-settings', $type, $id),
205
        'attributes' => array('class' => array('ctools-use-modal')),
206
      );
207
    }
208
209
    return $style_links;
210
  }
211
212
  /**
213
   * Get the links for a panel display.
214
   *
215
   * This is abstracted out for easy ajax replacement.
216
   */
217
  function get_display_links() {
218
    $links = array();
219
220
    if (user_access('administer panels styles')) {
221
      $style_links = $this->get_style_links('display');
222
      $links[] = array(
223
        'title' => '<span class="dropdown-header">' . t('Style') . '</span>' . theme_links(array('links' => $style_links, 'attributes' => array(), 'heading' => array())),
224
        'html' => TRUE,
225
        'attributes' => array('class' => array('panels-sub-menu')),
226
      );
227
    }
228
229
    if (user_access('use panels caching features')) {
230
      $links[] = array(
231
        'title' => '<hr />',
232
        'html' => TRUE,
233
      );
234
235
      $method = isset($this->display->cache['method']) ? $this->display->cache['method'] : 0;
236
      $info = panels_get_cache($method);
237
      $cache_method = isset($info['title']) ? $info['title'] : t('No caching');
238
239
      $cache_links[] = array(
240
        'title' => $cache_method,
241
        'attributes' => array('class' => array('panels-text')),
242
      );
243
      $cache_links[] = array(
244
        'title' => t('Change'),
245
        'href' => $this->get_url('cache-method', 'display'),
246
        'attributes' => array('class' => array('ctools-use-modal')),
247
      );
248
      if (panels_plugin_get_function('cache', $info, 'settings form')) {
249
        $cache_links[] = array(
250
          'title' => t('Settings'),
251
          'href' => $this->get_url('cache-settings', 'display'),
252
          'attributes' => array('class' => array('ctools-use-modal')),
253
        );
254
      }
255
256
      $links[] = array(
257
        'title' => '<span class="dropdown-header">' . t('Caching') . '</span>' . theme_links(array('links' => $cache_links, 'attributes' => array(), 'heading' => array())),
258
        'html' => TRUE,
259
        'attributes' => array('class' => array('panels-sub-menu')),
260
      );
261
    }
262
263
    return theme('ctools_dropdown', array('title' => t('Display settings'), 'links' => $links, 'class' => 'panels-display-links'));
264
  }
265
266
  /**
267
   * Render the links to display when editing a region.
268
   */
269
  function get_region_links($region_id) {
270
    if (!empty($this->no_edit_links)) {
271
      return '';
272
    }
273
    $links = array();
274
    $links[] = array(
275
      'title' => t('Add content'),
276
      'href' => $this->get_url('select-content', $region_id),
277
      'attributes' => array(
278
        'class' => array('ctools-use-modal'),
279
      ),
280
    );
281
282
    if (user_access('administer panels styles')) {
283
      $links[] = array(
284
        'title' => '<hr />',
285
        'html' => TRUE,
286
      );
287
288
      $style_links = $this->get_style_links('region', $region_id);
289
290
      $links[] = array(
291
        'title' => '<span class="dropdown-header">' . t('Style') . '</span>' . theme_links(array('links' => $style_links, 'attributes' => array(), 'heading' => array())),
292
        'html' => TRUE,
293
        'attributes' => array('class' => array('panels-sub-menu')),
294
      );
295
    }
296
297
    return theme('ctools_dropdown', array('title' => theme('image', array('path' => ctools_image_path('icon-addcontent.png', 'panels'))), 'links' => $links, 'image' => TRUE, 'class' => 'pane-add-link panels-region-links-' . $region_id));
298
  }
299
300
  /**
301
   * Render the links to display when editing a pane.
302
   */
303
  function get_pane_links($pane, $content_type) {
304
    if (!empty($this->no_edit_links)) {
305
      return '';
306
    }
307
    $links = array();
308
309
    if (!empty($pane->shown)) {
310 5a7e6170 Florent Torregrosa
      $links['top']['disabled'] = array(
311 85ad3d82 Assos Assos
        'title' => t('Disable this pane'),
312
        'href' => $this->get_url('hide', $pane->pid),
313
        'attributes' => array('class' => array('use-ajax')),
314
      );
315
    }
316
    else {
317 5a7e6170 Florent Torregrosa
      $links['top']['enable'] = array(
318 85ad3d82 Assos Assos
        'title' => t('Enable this pane'),
319
        'href' => $this->get_url('show', $pane->pid),
320
        'attributes' => array('class' => array('use-ajax')),
321
      );
322
    }
323
324
    if (isset($this->display->title_pane) && $this->display->title_pane == $pane->pid) {
325 5a7e6170 Florent Torregrosa
      $links['top']['panels-set-title'] = array(
326 85ad3d82 Assos Assos
        'title' => t('&#x2713;Panel title'),
327
        'html' => TRUE,
328
      );
329
    }
330
    else {
331 5a7e6170 Florent Torregrosa
      $links['top']['panels-set-title'] = array(
332 85ad3d82 Assos Assos
        'title' => t('Panel title'),
333
        'href' => $this->get_url('panel-title', $pane->pid),
334
        'attributes' => array('class' => array('use-ajax')),
335
      );
336
    }
337
338
    $subtype = ctools_content_get_subtype($content_type, $pane->subtype);
339
340
    if (ctools_content_editable($content_type, $subtype, $pane->configuration)) {
341 5a7e6170 Florent Torregrosa
      $links['top']['settings'] = array(
342 85ad3d82 Assos Assos
        'title' => isset($content_type['edit text']) ? $content_type['edit text'] : t('Settings'),
343
        'href' => $this->get_url('edit-pane', $pane->pid),
344
        'attributes' => array('class' => array('ctools-use-modal')),
345
      );
346
    }
347
348
    if (user_access('administer advanced pane settings')) {
349 5a7e6170 Florent Torregrosa
      $links['top']['css'] = array(
350 85ad3d82 Assos Assos
        'title' => t('CSS properties'),
351
        'href' => $this->get_url('pane-css', $pane->pid),
352
        'attributes' => array('class' => array('ctools-use-modal')),
353
      );
354
    }
355
356
    if (user_access('administer panels styles')) {
357 5a7e6170 Florent Torregrosa
      $links['style'] = $this->get_style_links('pane', $pane->pid);
358 85ad3d82 Assos Assos
    }
359
360
    if (user_access('administer pane access')) {
361
      $contexts = $this->display->context;
362
      // Make sure we have the logged in user context
363
      if (!isset($contexts['logged-in-user'])) {
364
        $contexts['logged-in-user'] = ctools_access_get_loggedin_context();
365
      }
366
367
      $visibility_links = array();
368
369
      if (!empty($pane->access['plugins'])) {
370
        foreach ($pane->access['plugins'] as $id => $test) {
371
          $plugin = ctools_get_access_plugin($test['name']);
372 5a7e6170 Florent Torregrosa
          $access_title = isset($plugin['title']) ? $plugin['title'] : t('Broken/missing access plugin %plugin', array('%plugin' => $test['name']));
373 85ad3d82 Assos Assos
          $access_description = ctools_access_summary($plugin, $contexts, $test);
374
375
          $visibility_links[] = array(
376
            'title' => $access_description,
377
            'href' => $this->get_url('access-configure-test', $pane->pid, $id),
378
            'attributes' => array('class' => array('ctools-use-modal', 'panels-italic')),
379
          );
380
        }
381
      }
382
      if (empty($visibility_links)) {
383 5a7e6170 Florent Torregrosa
        $visibility_links['no_rules'] = array(
384 85ad3d82 Assos Assos
          'title' => t('No rules'),
385
          'attributes' => array('class' => array('panels-text')),
386
        );
387
      }
388
389 5a7e6170 Florent Torregrosa
      $visibility_links['add_rule'] = array(
390 85ad3d82 Assos Assos
        'title' => t('Add new rule'),
391
        'href' => $this->get_url('access-add-test', $pane->pid),
392
        'attributes' => array('class' => array('ctools-use-modal')),
393
      );
394
395 5a7e6170 Florent Torregrosa
      $visibility_links['settings'] = array(
396 85ad3d82 Assos Assos
        'title' => t('Settings'),
397
        'href' => $this->get_url('access-settings', $pane->pid),
398
        'attributes' => array('class' => array('ctools-use-modal')),
399
      );
400
401 5a7e6170 Florent Torregrosa
      $links['visibility'] = $visibility_links;
402 85ad3d82 Assos Assos
    }
403
404
    if (user_access('use panels locks')) {
405
      $lock_type = !empty($pane->locks['type']) ? $pane->locks['type'] : 'none';
406
      switch ($lock_type) {
407
        case 'immovable':
408
          $lock_method = t('Immovable');
409
          break;
410
        case 'regions':
411
          $lock_method = t('Regions');
412
          break;
413
        case 'none':
414
        default:
415
          $lock_method = t('No lock');
416
          break;
417
      }
418
419 5a7e6170 Florent Torregrosa
      $lock_links['lock'] = array(
420 85ad3d82 Assos Assos
        'title' => $lock_method,
421
        'attributes' => array('class' => array('panels-text')),
422
      );
423 5a7e6170 Florent Torregrosa
      $lock_links['change'] = array(
424 85ad3d82 Assos Assos
        'title' => t('Change'),
425
        'href' => $this->get_url('lock', $pane->pid),
426
        'attributes' => array('class' => array('ctools-use-modal')),
427
      );
428
429 5a7e6170 Florent Torregrosa
      $links['lock'] = $lock_links;
430 85ad3d82 Assos Assos
    }
431
432
    if (panels_get_caches() && user_access('use panels caching features')) {
433
      $method = isset($pane->cache['method']) ? $pane->cache['method'] : 0;
434
      $info = panels_get_cache($method);
435
      $cache_method = isset($info['title']) ? $info['title'] : t('No caching');
436 5a7e6170 Florent Torregrosa
      $cache_links['title'] = array(
437 85ad3d82 Assos Assos
        'title' => $cache_method,
438
        'attributes' => array('class' => array('panels-text')),
439
      );
440 5a7e6170 Florent Torregrosa
      $cache_links['change'] = array(
441 85ad3d82 Assos Assos
        'title' => t('Change'),
442
        'href' => $this->get_url('cache-method', $pane->pid),
443
        'attributes' => array('class' => array('ctools-use-modal')),
444
      );
445
      if (panels_plugin_get_function('cache', $info, 'settings form')) {
446 5a7e6170 Florent Torregrosa
        $cache_links['settings'] = array(
447 85ad3d82 Assos Assos
          'title' => t('Settings'),
448
          'href' => $this->get_url('cache-settings', $pane->pid),
449
          'attributes' => array('class' => array('ctools-use-modal')),
450
        );
451
      }
452
453 5a7e6170 Florent Torregrosa
      $links['cache'] = $cache_links;
454 85ad3d82 Assos Assos
    }
455
456 5a7e6170 Florent Torregrosa
    $links['bottom']['remove'] = array(
457 85ad3d82 Assos Assos
      'title' => t('Remove'),
458
      'href' => '#',
459
      'attributes' => array(
460
        'class' => array('pane-delete'),
461
        'id' => "pane-delete-panel-pane-$pane->pid",
462
      ),
463
    );
464
465 5a7e6170 Florent Torregrosa
    // Allow others to add/remove links from pane context menu.
466
    // Grouped by 'top', 'style', 'visibility', 'lock', 'cache' and 'bottom'
467
    drupal_alter('get_pane_links', $links, $pane, $content_type);
468
469
    $dropdown_links = $links['top'];
470 e4c061ad Assos Assos
    $category_labels = array(
471
      'style' => 'Style',
472
      'visibility' => 'Visibility rules',
473
      'lock' => 'Locking',
474
      'cache' => 'Caching',
475
    );
476
    foreach ($category_labels as $category => $label) {
477
      if (array_key_exists($category, $links)) {
478
        $dropdown_links[] = array(
479
          'title' => '<hr />',
480
          'html' => TRUE,
481
        );
482
        $dropdown_links[] = array(
483
          'title' => '<span class="dropdown-header">' . t($label) . '</span>' . theme_links(array('links' => $links[$category], 'attributes' => array(), 'heading' => array())),
484
          'html' => TRUE,
485
          'attributes' => array('class' => array('panels-sub-menu')),
486
        );
487
      }
488 5a7e6170 Florent Torregrosa
    }
489
490
    $dropdown_links[] = array(
491
      'title' => '<hr />',
492
      'html' => TRUE,
493
    );
494
    $dropdown_links = array_merge($dropdown_links, $links['bottom']);
495
496
    return theme('ctools_dropdown', array('title' => theme('image', array('path' => ctools_image_path('icon-configure.png', 'panels'))), 'links' => $dropdown_links, 'image' => TRUE));
497 85ad3d82 Assos Assos
  }
498
499
  // -----------------------------------------------------------------------
500
  // Display edit AJAX callbacks and helpers.
501
502
  /**
503
   * Generate a URL path for the AJAX editor.
504
   */
505
  function get_url() {
506
    $args = func_get_args();
507
    $command = array_shift($args);
508
    $url = 'panels/ajax/' . $this->plugin['name'] . '/' . $command . '/' . $this->display->cache_key;
509
    if ($args) {
510
      $url .= '/' . implode('/', $args);
511
    }
512
513
    return $url;
514
  }
515
516
  /**
517
   * AJAX command to show a pane.
518
   */
519
  function ajax_show($pid = NULL) {
520
    if (empty($this->display->content[$pid])) {
521
      ctools_ajax_render_error(t('Invalid pane id.'));
522
    }
523
524
    $this->display->content[$pid]->shown = TRUE;
525
    panels_edit_cache_set($this->cache);
526
527
    $this->command_update_pane($pid);
528
  }
529
530
  /**
531
   * AJAX command to show a pane.
532
   */
533
  function ajax_hide($pid = NULL) {
534
    if (empty($this->display->content[$pid])) {
535
      ctools_ajax_render_error(t('Invalid pane id.'));
536
    }
537
538
    $this->display->content[$pid]->shown = FALSE;
539
    panels_edit_cache_set($this->cache);
540
541
    $this->command_update_pane($pid);
542
  }
543
544
  /**
545
   * AJAX command to present a dialog with a list of available content.
546
   */
547
  function ajax_select_content($region = NULL, $category = NULL) {
548
    if (!array_key_exists($region, $this->plugins['layout']['regions'])) {
549
      ctools_modal_render(t('Error'), t('Invalid input'));
550
    }
551
552
    $title = t('Add content to !s', array('!s' => $this->plugins['layout']['regions'][$region]));
553
554
    $categories = $this->get_categories($this->cache->content_types);
555
556
    if (empty($categories)) {
557
      $output = t('There are no content types you may add to this display.');
558
    }
559
    else {
560
      $output = theme('panels_add_content_modal', array('renderer' => $this, 'categories' => $categories, 'category' => $category, 'region' => $region));
561
    }
562
    $this->commands[] = ctools_modal_command_display($title, $output);
563
  }
564
565
  /**
566
   * Return the category name and the category key of a given content
567
   * type.
568
   *
569
   * @todo -- this should be in CTools.
570
   */
571
  function get_category($content_type) {
572 5a7e6170 Florent Torregrosa
    if (!empty($content_type['top level'])) {
573 85ad3d82 Assos Assos
      $category = 'root';
574
    }
575
    else if (isset($content_type['category'])) {
576
      if (is_array($content_type['category'])) {
577
        list($category, $weight) = $content_type['category'];
578
      }
579
      else {
580
        $category = $content_type['category'];
581
      }
582
    }
583
    else {
584
      $category = t('Uncategorized');
585
    }
586
587
    return array(preg_replace('/[^a-z0-9]/', '-', strtolower($category)), $category);
588
  }
589
590
591
  /**
592
   * Create a list of categories from all of the content type.
593
   *
594
   * @return array
595
   *   An array of categories. Each entry in the array will also be an array
596
   *   with 'title' as the printable title of the category, and 'content'
597
   *   being an array of all content in the category. Each item in the 'content'
598
   *   array contain the array plugin definition so that it can be later
599
   *   found in the content array. They will be keyed by the title so that they
600
   *   can be sorted.
601
   */
602
  function get_categories($content_types) {
603
    $categories = array();
604
    $category_names = array();
605
606
    foreach ($content_types as $type_name => $subtypes) {
607
      foreach ($subtypes as $subtype_name => $content_type) {
608
        list($category_key, $category) = $this->get_category($content_type);
609
610
        if (empty($categories[$category_key])) {
611
          $categories[$category_key] = array(
612
            'title' => $category,
613
            'content' => array(),
614
          );
615
          $category_names[$category_key] = $category;
616
        }
617
618
        $content_title = filter_xss_admin($content_type['title']);
619
620
        // Ensure content with the same title doesn't overwrite each other.
621
        while (isset($categories[$category_key]['content'][$content_title])) {
622
          $content_title .= '-';
623
        }
624
625
        $categories[$category_key]['content'][$content_title] = $content_type;
626
        $categories[$category_key]['content'][$content_title]['type_name'] = $type_name;
627
        $categories[$category_key]['content'][$content_title]['subtype_name'] = $subtype_name;
628
      }
629
    }
630
631
    // Now sort
632
    natcasesort($category_names);
633
    foreach ($category_names as $category => $name) {
634
      $output[$category] = $categories[$category];
635
    }
636
637
    return $output;
638
  }
639
640
  /**
641
   * AJAX entry point to add a new pane.
642
   */
643
  function ajax_add_pane($region = NULL, $type_name = NULL, $subtype_name = NULL, $step = NULL) {
644
    $content_type = ctools_get_content_type($type_name);
645
    $subtype = ctools_content_get_subtype($content_type, $subtype_name);
646
647 5a7e6170 Florent Torregrosa
    // Determine if we are adding a different pane than previously cached. This
648
    // is used to load the different pane into cache so that multistep forms
649
    // have the correct context instead of a previously cached version that
650
    // does not match the pane currently being added.
651
    $is_different_pane = FALSE;
652
    if (isset($this->cache) && isset($this->cache->new_pane)) {
653
      $diff_type = $type_name != $this->cache->new_pane->type;
654
      $diff_subtype = $subtype_name != $this->cache->new_pane->subtype;
655
656
      $is_different_pane = $diff_type || $diff_subtype;
657
    }
658
659
    if (!isset($step) || !isset($this->cache->new_pane) || $is_different_pane) {
660 85ad3d82 Assos Assos
      $pane = panels_new_pane($type_name, $subtype_name, TRUE);
661
      $this->cache->new_pane = &$pane;
662
    }
663
    else {
664
      $pane = &$this->cache->new_pane;
665
    }
666
667
    $form_state = array(
668
      'display' => &$this->cache->display,
669
      'contexts' => $this->cache->display->context,
670
      'pane' => &$pane,
671
      'cache_key' => $this->display->cache_key,
672
      'display cache' => &$this->cache,
673
      'ajax' => TRUE,
674
      'modal' => TRUE,
675
      // This will force the system to not automatically render.
676
      'modal return' => TRUE,
677
      'commands' => array(),
678
    );
679
680
    $form_info = array(
681
      'path' => $this->get_url('add-pane', $region, $type_name, $subtype_name, '%step'),
682
      'show cancel' => TRUE,
683
      'next callback' => 'panels_ajax_edit_pane_next',
684
      'finish callback' => 'panels_ajax_edit_pane_finish',
685
      'cancel callback' => 'panels_ajax_edit_pane_cancel',
686
    );
687
688
    $output = ctools_content_form('add', $form_info, $form_state, $content_type, $pane->subtype, $subtype, $pane->configuration, $step);
689
690
    // If $rc is FALSE, there was no actual form.
691
    if ($output === FALSE || !empty($form_state['complete'])) {
692
      // References get blown away with AJAX caching. This will fix that.
693
      $pane = $form_state['pane'];
694
      unset($this->cache->new_pane);
695
696
      // Add the pane to the display
697
      $this->display->add_pane($pane, $region);
698
      panels_edit_cache_set($this->cache);
699
700
      // Tell the client to draw the pane
701
      $this->command_add_pane($pane);
702
703
      // Dismiss the modal.
704
      $this->commands[] = ctools_modal_command_dismiss();
705
    }
706
    else if (!empty($form_state['cancel'])) {
707
      // If cancelling, return to the activity.
708
      list($category_key, $category) = $this->get_category($subtype);
709
      $this->ajax_select_content($region, $category_key);
710
    }
711
    else {
712
      // This overwrites any previous commands.
713
      $this->commands = ctools_modal_form_render($form_state, $output);
714
    }
715
  }
716
717
  /**
718
   * AJAX entry point to edit a pane.
719
   */
720
  function ajax_edit_pane($pid = NULL, $step = NULL) {
721
    if (empty($this->cache->display->content[$pid])) {
722
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
723
    }
724
725
    $pane = &$this->cache->display->content[$pid];
726
727
    $content_type = ctools_get_content_type($pane->type);
728
    $subtype = ctools_content_get_subtype($content_type, $pane->subtype);
729
730
    $form_state = array(
731
      'display' => &$this->cache->display,
732
      'contexts' => $this->cache->display->context,
733
      'pane' => &$pane,
734
      'display cache' => &$this->cache,
735
      'ajax' => TRUE,
736
      'modal' => TRUE,
737
      'modal return' => TRUE,
738
      'commands' => array(),
739
    );
740
741
    $form_info = array(
742
      'path' => $this->get_url('edit-pane', $pid, '%step'),
743
      'show cancel' => TRUE,
744
      'next callback' => 'panels_ajax_edit_pane_next',
745
      'finish callback' => 'panels_ajax_edit_pane_finish',
746
      'cancel callback' => 'panels_ajax_edit_pane_cancel',
747
    );
748
749
    $output = ctools_content_form('edit', $form_info, $form_state, $content_type, $pane->subtype,  $subtype, $pane->configuration, $step);
750
751
    // If $rc is FALSE, there was no actual form.
752
    if ($output === FALSE || !empty($form_state['cancel'])) {
753
      // Dismiss the modal.
754
      $this->commands[] = ctools_modal_command_dismiss();
755
    }
756
    else if (!empty($form_state['complete'])) {
757
      // References get blown away with AJAX caching. This will fix that.
758
      $this->cache->display->content[$pid] = $form_state['pane'];
759
760 5a7e6170 Florent Torregrosa
      // Conditionally overwrite the context for this panel if present in the form state.
761
      if (!empty($form_state['display_cache']->display->context)) {
762
        $this->cache->display->context = $form_state['display_cache']->display->context;
763
      }
764
765 85ad3d82 Assos Assos
      panels_edit_cache_set($this->cache);
766
      $this->command_update_pane($pid);
767
      $this->commands[] = ctools_modal_command_dismiss();
768
    }
769
    else {
770
      // This overwrites any previous commands.
771
      $this->commands = ctools_modal_form_render($form_state, $output);
772
    }
773
  }
774
775
  /**
776
   * AJAX entry point to select which pane is currently the title.
777
   *
778
   * @param string $pid
779
   *   The pane id for the pane object whose title state we're setting.
780
   */
781
  function ajax_panel_title($pid = NULL) {
782
    if (empty($this->display->content[$pid])) {
783
      ctools_ajax_render_error(t('Invalid pane id.'));
784
    }
785
786
    $pane = &$this->display->content[$pid];
787
788
    $old_title = !empty($this->display->title_pane) ? $this->display->title_pane : NULL;
789
    $this->display->title_pane = $pid;
790
791
    panels_edit_cache_set($this->cache);
792
793
    $this->command_update_pane($pane);
794
795
    if ($old_title && !empty($this->cache->display->content[$old_title])) {
796
      $this->command_update_pane($this->cache->display->content[$old_title]);
797
    }
798
  }
799
800
  /**
801
   * AJAX entry point to configure the cache method for a pane or the display.
802
   *
803
   * @param string $pid
804
   *   Either a pane id for a pane in the display, or 'display' to edit the
805
   *   display cache settings.
806
   */
807
  function ajax_cache_method($pid = NULL) {
808
    ctools_include('content');
809
    // This lets us choose whether we're doing the display's cache or
810
    // a pane's.
811
    if ($pid == 'display') {
812
      $conf = &$this->display->cache;
813
      $title = t('Cache method for this display');
814
    }
815
    else if (!empty($this->display->content[$pid])) {
816
      $pane = &$this->display->content[$pid];
817
      $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
818
      $conf = &$pane->cache;
819
      $title = t('Cache method for !subtype_title', array('!subtype_title' => $subtype['title']));
820
    }
821
    else {
822
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
823
    }
824
825
    $form_state = array(
826
      'display' => &$this->display,
827
      'conf' => &$conf,
828
      'title' => $title,
829
      'ajax' => TRUE,
830
    );
831
832
    $output = ctools_modal_form_wrapper('panels_edit_cache_method_form', $form_state);
833
    if (empty($form_state['executed'])) {
834
      $this->commands = $output;
835
      return;
836
    }
837
838
    // Preserve this; this way we don't actually change the method until they
839
    // have saved the form.
840
    $info = panels_get_cache($form_state['method']);
841
    $function = panels_plugin_get_function('cache', $info, 'settings form');
842
    if (!$function) {
843
      $conf['method'] = $form_state['method'];
844
      $conf['settings'] = array();
845
      panels_edit_cache_set($this->cache);
846
847
      $this->commands[] = ctools_modal_command_dismiss();
848
849
      if ($pid != 'display') {
850
        $this->command_update_pane($pane);
851
      }
852
      else {
853
        $this->command_update_display_links();
854
      }
855
    }
856
    else {
857
      $this->cache->method = $form_state['method'];
858
      panels_edit_cache_set($this->cache);
859
      // send them to next form.
860
      return $this->ajax_cache_settings($pid);
861
    }
862
  }
863
864
  /**
865
   * AJAX entry point to configure the cache settings for a pane or the display.
866
   *
867
   * @param string $pid
868
   *   Either a pane id for a pane in the display, or 'display' to edit the
869
   *   display cache settings.
870
   */
871
  function ajax_cache_settings($pid = 0) {
872
    ctools_include('content');
873
874
    // This lets us choose whether we're doing the display's cache or
875
    // a pane's.
876
    if ($pid == 'display') {
877
      $conf = &$this->display->cache;
878
      $title = t('Cache settings for this display');
879
    }
880
    else if (!empty($this->display->content[$pid])) {
881
      $pane = &$this->display->content[$pid];
882
      $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
883
884
      $conf = &$pane->cache;
885
      $title = t('Cache settings for !subtype_title', array('!subtype_title' => $subtype['title']));
886
    }
887
    else {
888
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
889
    }
890
891
    if (isset($this->cache->method) && (empty($conf['method']) || $conf['method'] != $this->cache->method)) {
892
      $conf['method'] = $this->cache->method;
893
      $info = panels_get_cache($conf['method']);
894
      $conf['settings'] = isset($info['defaults']) ? $info['defaults'] : array();
895
    }
896
897
    $form_state = array(
898
      'display' => &$this->display,
899
      'pid' => $pid,
900
      'conf' => &$conf,
901
      'ajax' => TRUE,
902
      'title' => $title,
903
      'url' => url($this->get_url('cache-settings', $pid), array('absolute' => TRUE)),
904
    );
905
906
    $output = ctools_modal_form_wrapper('panels_edit_cache_settings_form', $form_state);
907
    if (empty($form_state['executed'])) {
908
      $this->commands = $output;
909
      return;
910
    }
911
912
    panels_edit_cache_set($this->cache);
913
914
    $this->commands[] = ctools_modal_command_dismiss();
915
916
    if ($pid != 'display') {
917
      $this->command_update_pane($pane);
918
    }
919
    else {
920
      $this->command_update_display_links();
921
    }
922
  }
923
924
  /**
925
   * AJAX entry point to select the style for a display, region or pane.
926
   *
927
   * @param string $type
928
   *   Either display, region or pane
929
   * @param $pid
930
   *   The pane id, if a pane. The region id, if a region.
931
   */
932
  function ajax_style_type($type, $pid = NULL) {
933
    // This lets us choose whether we're doing the display's cache or
934
    // a pane's.
935
    switch ($type) {
936
      case 'display':
937
        $style = isset($this->display->panel_settings['style']) ? $this->display->panel_settings['style'] : 'default';
938
        $title = t('Default style for this display');
939
        break;
940
941
      case 'region':
942
        $style = isset($this->display->panel_settings[$pid]['style']) ? $this->display->panel_settings[$pid]['style'] : '-1'; // -1 signifies to use the default setting.
943
        $title = t('Panel style for region "!region"', array('!region' => $this->plugins['layout']['regions'][$pid]));
944
        break;
945
946
      case 'pane':
947
        ctools_include('content');
948
        $pane = &$this->display->content[$pid];
949
        $style = isset($pane->style['style']) ? $pane->style['style'] : 'default';
950 e4c061ad Assos Assos
        $title = ctools_content_admin_title($pane->type, $pane->subtype, $pane->configuration, $this->display->context);
951
        if (!$title) {
952
          $title = $pane->type;
953
        }
954
        $title = t('Pane style for "!title"', array('!title' => $title));
955 85ad3d82 Assos Assos
        break;
956
957
      default:
958
        ctools_modal_render(t('Error'), t('Invalid pane id.'));
959
    }
960
    $info = $this->get_style($type, $pid);
961
    $style_plugin = $info[0];
962
    $style_settings = $info[1];
963
964
    // Backward compatibility: Translate old-style stylizer to new style
965
    // stylizer.
966
    if ($style == 'stylizer' && !empty($style_settings['style']) && $style_settings['style'] != '$') {
967
      $style = 'stylizer:' . $style_settings['style'];
968
    }
969
970
    $form_state = array(
971
      'display' => &$this->display,
972
      'style' => $style,
973
      'pane' => ($type == 'pane') ? $this->display->content[$pid] : NULL,
974
      'title' => $title,
975
      'ajax' => TRUE,
976
      'type' => $type,
977
    );
978
979
    $output = ctools_modal_form_wrapper('panels_edit_style_type_form', $form_state);
980
    if (empty($form_state['executed'])) {
981
      $this->commands = $output;
982
      return;
983
    }
984
985
    // Preserve this; this way we don't actually change the method until they
986
    // have saved the form.
987
    $style = panels_get_style($form_state['style']);
988
    $function = panels_plugin_get_function('styles', $style, ($type == 'pane') ? 'pane settings form' : 'settings form');
989
    if (!$function) {
990
      if (isset($this->cache->style)) {
991
        unset($this->cache->style);
992
      }
993
994
      // If there's no settings form, just change the style and exit.
995
      switch($type) {
996
        case 'display':
997
          $this->display->panel_settings['style'] = $form_state['style'];
998
          if (isset($this->display->panel_settings['style_settings']['default'])) {
999
            unset($this->display->panel_settings['style_settings']['default']);
1000
          }
1001
          break;
1002
1003
        case 'region':
1004
          $this->display->panel_settings[$pid]['style'] = $form_state['style'];
1005
          if (isset($this->display->panel_settings['style_settings'][$pid])) {
1006
            unset($this->display->panel_settings['style_settings'][$pid]);
1007
          }
1008
          break;
1009
1010
        case 'pane':
1011
          $pane->style['style'] = $form_state['style'];
1012
          if (isset($pane->style['settings'])) {
1013
            unset($pane->style['settings']);
1014
          }
1015
1016
          break;
1017
      }
1018
      panels_edit_cache_set($this->cache);
1019
1020
      $this->commands[] = ctools_modal_command_dismiss();
1021
1022
      if ($type == 'pane') {
1023
        $this->command_update_pane($pane);
1024
      }
1025
      else if ($type == 'region') {
1026
        $this->command_update_region_links($pid);
1027
      }
1028
      else {
1029
        $this->command_update_display_links();
1030
      }
1031
    }
1032
    else {
1033
      if ($form_state['style'] != $form_state['old_style']) {
1034
        $this->cache->style = $form_state['style'];
1035
        panels_edit_cache_set($this->cache);
1036
      }
1037
1038
      // send them to next form.
1039
      return $this->ajax_style_settings($type, $pid);
1040
    }
1041
  }
1042
1043
  /**
1044
   * Get the appropriate style from the panel in the cache.
1045
   *
1046
   * Since we have styles for regions, panes and the display itself, and
1047
   * they are stored differently, we use this method to simplify getting
1048
   * style information into a way that's easy to cope with.
1049
   */
1050
  function get_style($type, $pid = '') {
1051
    if (isset($this->cache->style)) {
1052
      $style = panels_get_style($this->cache->style);
1053
      $defaults = isset($style['defaults']) ? $style['defaults'] : array();
1054
      // Get the &$conf variable based upon whose style we're editing.
1055
      switch ($type) {
1056
        case 'display':
1057
          $this->display->panel_settings['style'] = $this->cache->style;
1058
          $this->display->panel_settings['style_settings']['default'] = $defaults;
1059
          break;
1060
1061
        case 'region':
1062
          $this->display->panel_settings[$pid]['style'] = $this->cache->style;
1063
          $this->display->panel_settings['style_settings'][$pid] = $defaults;
1064
          break;
1065
1066
        case 'pane':
1067
          $pane = &$this->display->content[$pid];
1068
          $pane->style['style'] = $this->cache->style;
1069
          $pane->style['settings'] = $defaults;
1070
          $conf = &$pane->style['settings'];
1071
          break;
1072
      }
1073
    }
1074
    else {
1075
      switch ($type) {
1076
        case 'display':
1077
          $style = panels_get_style((!empty($this->display->panel_settings['style'])) ? $this->display->panel_settings['style'] : 'default');
1078
          break;
1079
1080
        case 'region':
1081
          $style = panels_get_style((!empty($this->display->panel_settings[$pid]['style'])) ? $this->display->panel_settings[$pid]['style'] : '-1');
1082
          break;
1083
1084
        case 'pane':
1085
          $pane = &$this->display->content[$pid];
1086
          $style = panels_get_style(!empty($pane->style['style']) ? $pane->style['style'] : 'default');
1087
          break;
1088
      }
1089
    }
1090
1091
    // Set up our $conf reference.
1092
    switch ($type) {
1093
      case 'display':
1094
        $conf = &$this->display->panel_settings['style_settings']['default'];
1095
        break;
1096
1097
      case 'region':
1098
        $conf = &$this->display->panel_settings['style_settings'][$pid];
1099
        break;
1100
1101
      case 'pane':
1102
        ctools_include('content');
1103
        $pane = &$this->display->content[$pid];
1104
        $conf = &$pane->style['settings'];
1105
        break;
1106
    }
1107
1108
    // Backward compatibility: Translate old-style stylizer to new style
1109
    // stylizer.
1110
    if ($style['name'] == 'stylizer' && !empty($conf['style']) && $conf['style'] != '$') {
1111
      $style = panels_get_style('stylizer:' . $conf['style']);
1112
    }
1113
1114
    return array($style, &$conf);
1115
  }
1116
1117
  /**
1118
   * AJAX entry point to configure the style for a display, region or pane.
1119
   *
1120
   * @param string $type
1121
   *   Either display, region or pane
1122
   * @param $pid
1123
   *   The pane id, if a pane. The region id, if a region.
1124
   */
1125
  function ajax_style_settings($type, $pid = '') {
1126
    $info = $this->get_style($type, $pid);
1127
    $style = $info[0];
1128
    $conf = &$info[1];
1129
1130
    switch ($type) {
1131
      case 'display':
1132
        $title = t('Style settings for @style (display)', array('@style' => $style['title']));
1133
        break;
1134
1135
      case 'region':
1136
        $title = t('Style settings for style @style (Region "!region")', array('@style' => $style['title'], '!region' => $this->plugins['layout']['regions'][$pid]));
1137
        break;
1138
1139
      case 'pane':
1140
        ctools_include('content');
1141
        $pane = &$this->display->content[$pid];
1142
        $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1143
        $title = t('Style settings for style @style (Pane "!pane")', array('@style' => $style['title'], '!pane' => $subtype['title']));
1144
        break;
1145
    }
1146
1147
    $form_state = array(
1148
      'display' => &$this->display,
1149
      'type' => $type,
1150
      'pid' => $pid,
1151
      'conf' => &$conf,
1152
      'style' => $style,
1153
      'ajax' => TRUE,
1154
      'title' => $title,
1155
      'url' => url($this->get_url('style-settings', $type, $pid), array('absolute' => TRUE)),
1156
      'renderer' => &$this,
1157
    );
1158
1159
    $output = ctools_modal_form_wrapper('panels_edit_style_settings_form', $form_state);
1160
    if (empty($form_state['executed'])) {
1161
      $this->commands = $output;
1162
      return;
1163
    }
1164
1165
    if (isset($this->cache->style)) {
1166
      unset($this->cache->style);
1167
    }
1168
1169 e4c061ad Assos Assos
    if (!empty($form_state['cancel'])) {
1170
      // The cache must be saved prior to dismissing the modal.
1171
      panels_edit_cache_set($this->cache);
1172
      $this->commands[] = ctools_modal_command_dismiss();
1173
      return;
1174
    }
1175
1176 5a7e6170 Florent Torregrosa
    // Copy settings from form state back into the cache.
1177
    if(!empty($form_state['values']['settings'])) {
1178 e4c061ad Assos Assos
      if ($type == 'pane') {
1179
        $this->cache->display->content[$pid]->style['settings'] = $form_state['values']['settings'];
1180
      }
1181
      else if($type == 'region') {
1182
        $this->cache->display->panel_settings['style_settings'][$pid] = $form_state['values']['settings'];
1183
      }
1184 5a7e6170 Florent Torregrosa
    }
1185
1186 85ad3d82 Assos Assos
    panels_edit_cache_set($this->cache);
1187
1188
    $this->commands[] = ctools_modal_command_dismiss();
1189
1190
    if ($type == 'pane') {
1191
      $this->command_update_pane($pane);
1192
    }
1193
    else if ($type == 'region') {
1194
      $this->command_update_region_links($pid);
1195
    }
1196
    else {
1197
      $this->command_update_display_links();
1198
    }
1199
  }
1200
1201
  /**
1202
   * AJAX entry point to configure CSS for a pane.
1203
   *
1204
   * @param $pid
1205
   *   The pane id to edit.
1206
   */
1207
  function ajax_pane_css($pid = NULL) {
1208
    if (empty($this->display->content[$pid])) {
1209
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
1210
    }
1211
1212
    $pane = &$this->display->content[$pid];
1213
    $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1214
1215
    $form_state = array(
1216
      'display' => &$this->display,
1217
      'pane' => &$pane,
1218
      'ajax' => TRUE,
1219
      'title' => t('Configure CSS on !subtype_title', array('!subtype_title' => $subtype['title'])),
1220
    );
1221
1222
    $output = ctools_modal_form_wrapper('panels_edit_configure_pane_css_form', $form_state);
1223
    if (empty($form_state['executed'])) {
1224
      $this->commands = $output;
1225
      return;
1226
    }
1227
1228
    panels_edit_cache_set($this->cache);
1229
    $this->command_update_pane($pid);
1230
    $this->commands[] = ctools_modal_command_dismiss();
1231
  }
1232
1233
  /**
1234
   * AJAX entry point to configure CSS for a pane.
1235
   *
1236
   * @param $pid
1237
   *   The pane id to edit.
1238
   */
1239
  function ajax_lock($pid = NULL) {
1240
    if (empty($this->display->content[$pid])) {
1241
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
1242
    }
1243
1244
    $pane = &$this->display->content[$pid];
1245
    $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1246
1247
    $form_state = array(
1248
      'display' => &$this->display,
1249
      'pane' => &$pane,
1250
      'ajax' => TRUE,
1251
      'title' => t('Configure lock on !subtype_title', array('!subtype_title' => $subtype['title'])),
1252
    );
1253
1254
    $output = ctools_modal_form_wrapper('panels_edit_configure_pane_lock_form', $form_state);
1255
    if (empty($form_state['executed'])) {
1256
      $this->commands = $output;
1257
      return;
1258
    }
1259
1260
    panels_edit_cache_set($this->cache);
1261
    $this->command_update_pane($pid);
1262
    $this->commands[] = ctools_modal_command_dismiss();
1263
  }
1264
1265
  /**
1266
   * AJAX entry point to configure access settings for a pane.
1267
   *
1268
   * @param $pid
1269
   *   The pane id to edit.
1270
   */
1271
  function ajax_access_settings($pid = NULL) {
1272
    if (empty($this->display->content[$pid])) {
1273
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
1274
    }
1275
1276
    $pane = &$this->display->content[$pid];
1277
    $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1278
1279
    $form_state = array(
1280
      'display' => &$this->display,
1281
      'pane' => &$pane,
1282
      'ajax' => TRUE,
1283
      'title' => t('Access settings on !subtype_title', array('!subtype_title' => $subtype['title'])),
1284
    );
1285
1286
    $output = ctools_modal_form_wrapper('panels_edit_configure_access_settings_form', $form_state);
1287
    if (empty($form_state['executed'])) {
1288
      $this->commands = $output;
1289
      return;
1290
    }
1291
1292
    panels_edit_cache_set($this->cache);
1293
    $this->command_update_pane($pid);
1294
    $this->commands[] = ctools_modal_command_dismiss();
1295
  }
1296
1297
  /**
1298
   * AJAX entry point for to add a visibility rule.
1299
   */
1300
  function ajax_access_add_test($pid = NULL) {
1301
    if (empty($this->display->content[$pid])) {
1302
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
1303
    }
1304
1305
    $pane = &$this->display->content[$pid];
1306
    $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1307
1308
    $form_state = array(
1309
      'display' => &$this->display,
1310
      'pane' => &$pane,
1311
      'ajax' => TRUE,
1312
      'title' => t('Add visibility rule for !subtype_title', array('!subtype_title' => $subtype['title'])),
1313
    );
1314
1315
    $output = ctools_modal_form_wrapper('panels_edit_add_access_test_form', $form_state);
1316
    if (!empty($form_state['executed'])) {
1317
      // Set up the plugin in cache
1318
      $plugin = ctools_get_access_plugin($form_state['values']['type']);
1319
      $this->cache->new_plugin = ctools_access_new_test($plugin);
1320
      panels_edit_cache_set($this->cache);
1321
1322
      // go to the next step.
1323
      return $this->ajax_access_configure_test($pid, 'add');
1324
    }
1325
1326
    $this->commands = $output;
1327
  }
1328
1329
  /**
1330
   * AJAX entry point for to configure vsibility rule.
1331
   */
1332
  function ajax_access_configure_test($pid = NULL, $id = NULL) {
1333
    if (empty($this->display->content[$pid])) {
1334
      ctools_modal_render(t('Error'), t('Invalid pane id.'));
1335
    }
1336
1337
    $pane = &$this->display->content[$pid];
1338
    $subtype = ctools_content_get_subtype($pane->type, $pane->subtype);
1339
1340
    // Set this up here because $id gets changed later.
1341
    $url = $this->get_url('access-configure-test', $pid, $id);
1342
1343
    // If we're adding a new one, get the stored data from cache and
1344
    // add it. It's stored as a cache so that if this is closed
1345
    // we don't accidentally add an unconfigured plugin.
1346
    if ($id == 'add') {
1347
      $pane->access['plugins'][] = $this->cache->new_plugin;
1348
      $id = max(array_keys($pane->access['plugins']));
1349
    }
1350
    else if (empty($pane->access['plugins'][$id])) {
1351
      ctools_modal_render(t('Error'), t('Invalid test id.'));
1352
    }
1353
1354
    $form_state = array(
1355
      'display' => &$this->display,
1356
      'pane' => &$pane,
1357
      'ajax' => TRUE,
1358
      'title' => t('Configure visibility rule for !subtype_title', array('!subtype_title' => $subtype['title'])),
1359
      'test' => &$pane->access['plugins'][$id],
1360
      'plugin' => ctools_get_access_plugin($pane->access['plugins'][$id]['name']),
1361
      'url' => url($url, array('absolute' => TRUE)),
1362
    );
1363
1364
    $output = ctools_modal_form_wrapper('panels_edit_configure_access_test_form', $form_state);
1365
    if (empty($form_state['executed'])) {
1366
      $this->commands = $output;
1367
      return;
1368
    }
1369
1370
    // Unset the new plugin
1371
    if (isset($this->cache->new_plugin)) {
1372
      unset($this->cache->new_plugin);
1373
    }
1374
1375
    if (!empty($form_state['remove'])) {
1376
      unset($pane->access['plugins'][$id]);
1377
    }
1378
1379
    panels_edit_cache_set($this->cache);
1380
    $this->command_update_pane($pid);
1381
    $this->commands[] = ctools_modal_command_dismiss();
1382
  }
1383
1384
  /**
1385
   * AJAX Router function for layout owned AJAX calls.
1386
   *
1387
   * Layouts like the flexible layout builder need callbacks of their own.
1388
   * This allows those layouts to simply declare their callbacks and use
1389
   * them with $this->get_url('layout', $command).
1390
   */
1391
  function ajax_layout() {
1392
    $args = func_get_args();
1393
    if (empty($args)) {
1394
      return MENU_NOT_FOUND;
1395
    }
1396
1397
    $command = array_shift($args);
1398
    if (empty($this->plugins['layout']['ajax'][$command]) || !function_exists($this->plugins['layout']['ajax'][$command])) {
1399
      return MENU_NOT_FOUND;
1400
    }
1401
1402
    // Make sure the this is always available to the called functions.
1403
    array_unshift($args, $this);
1404
    return call_user_func_array($this->plugins['layout']['ajax'][$command], $args);
1405
  }
1406
1407
  /**
1408
   * AJAX Router function for style owned AJAX calls.
1409
   *
1410
   * Styles like the stylizer need AJAX callbacks of their own. This
1411
   * allows the system to figure out which style is being referenced,
1412
   * load it, and execute the callback.
1413
   *
1414
   * This allows those layouts to simply declare their callbacks and use
1415
   * them using $this->get_url('style', $command, $type, $pid).
1416
   */
1417
  function ajax_style() {
1418
    $args = func_get_args();
1419
    if (count($args) < 3) {
1420
      return MENU_NOT_FOUND;
1421
    }
1422
1423
    $command = array_shift($args);
1424
    $type = array_shift($args);
1425
    $pid = array_shift($args);
1426
1427
    $info = $this->get_style($type, $pid);
1428
1429
    $style = $info[0];
1430
    $conf = &$info[1];
1431
1432
    if (empty($style['ajax'][$command]) || !function_exists($style['ajax'][$command])) {
1433
      return MENU_NOT_FOUND;
1434
    }
1435
1436
    // Make sure the this is always available to the called functions.
1437
    $args = array_merge(array(&$this, $style, &$conf, $type, $pid), $args);
1438
    return call_user_func_array($style['ajax'][$command], $args);
1439
  }
1440
1441
  // ------------------------------------------------------------------------
1442
  // AJAX command generators
1443
  //
1444
  // These are used to make sure that child implementations can control their
1445
  // own AJAX commands as needed.
1446
1447
  /**
1448
   * Create a command array to redraw a pane.
1449
   */
1450
  function command_update_pane($pid) {
1451
    if (is_object($pid)) {
1452
      $pane = $pid;
1453
    }
1454
    else {
1455
      $pane = $this->display->content[$pid];
1456
    }
1457
1458
    $this->commands[] = ajax_command_replace("#panel-pane-$pane->pid", $this->render_pane($pane));
1459
    $this->commands[] = ajax_command_changed("#panel-pane-$pane->pid", "div.grab-title span.text");
1460
  }
1461
1462
  /**
1463
   * Create a command array to add a new pane.
1464
   */
1465
  function command_add_pane($pid) {
1466
    if (is_object($pid)) {
1467
      $pane = $pid;
1468
    }
1469
    else {
1470
      $pane = $this->display->content[$pid];
1471
    }
1472
1473
    $this->commands[] = ajax_command_append("#panel-region-$pane->panel", $this->render_pane($pane));
1474
    $this->commands[] = ajax_command_changed("#panel-pane-$pane->pid", "div.grab-title span.text");
1475
  }
1476
1477
  /**
1478
   * Create a command to update the links on a display after a change was made.
1479
   */
1480
  function command_update_display_links() {
1481
    $this->commands[] = ajax_command_replace('.panels-display-links', $this->get_display_links());
1482
  }
1483
1484
  /**
1485
   * Create a command to update the links on a region after a change was made.
1486
   */
1487
  function command_update_region_links($id) {
1488
    $this->commands[] = ajax_command_replace('.panels-region-links-' . $id, $this->get_region_links($id));
1489
  }
1490
}
1491
1492
/**
1493
 * Handle the 'next' click on the add/edit pane form wizard.
1494
 *
1495
 * All we need to do is store the updated pane in the cache.
1496
 */
1497
function panels_ajax_edit_pane_next(&$form_state) {
1498
  $form_state['display cache']->new_pane = $form_state['pane'];
1499
  panels_edit_cache_set($form_state['display cache']);
1500
}
1501
1502
/**
1503
 * Handle the 'finish' click on teh add/edit pane form wizard.
1504
 *
1505
 * All we need to do is set a flag so the return can handle adding
1506
 * the pane.
1507
 */
1508
function panels_ajax_edit_pane_finish(&$form_state) {
1509
  $form_state['complete'] = TRUE;
1510
  return;
1511
}
1512
1513
/**
1514
 * Handle the 'cancel' click on the add/edit pane form wizard.
1515
 */
1516
function panels_ajax_edit_pane_cancel(&$form_state) {
1517
  $form_state['cancel'] = TRUE;
1518
  return;
1519
}
1520
1521
// --------------------------------------------------------------------------
1522
// Forms for the editor object
1523
1524
/**
1525
 * Choose cache method form
1526
 */
1527
function panels_edit_cache_method_form($form, &$form_state) {
1528 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1529
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1530 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1531
  $conf = &$form_state['conf'];
1532
1533
  // Set to 0 to ensure we get a selected radio.
1534
  if (!isset($conf['method'])) {
1535
    $conf['method'] = 0;
1536
  }
1537
1538
  $caches = panels_get_caches();
1539
  if (empty($caches)) {
1540
    $form['markup'] = array('#value' => t('No caching options are available at this time. Please enable a panels caching module in order to use caching options.'));
1541
    return $form;
1542
  }
1543
1544
  $options[0] = t('No caching');
1545
  foreach ($caches as $cache => $info) {
1546
    $options[$cache] = check_plain($info['title']);
1547
  }
1548
1549
  $form['method'] = array(
1550
    '#prefix' => '<div class="no-float">',
1551
    '#suffix' => '</div>',
1552
    '#type' => 'radios',
1553
    '#title' => t('Method'),
1554
    '#options' => $options,
1555
    '#default_value' => $conf['method'],
1556
  );
1557
1558
  $form['submit'] = array(
1559
    '#type' => 'submit',
1560
    '#value' => t('Next'),
1561
  );
1562
  return $form;
1563
}
1564
1565
/**
1566
 * Submit callback for panels_edit_cache_method_form.
1567
 *
1568
 * All this needs to do is return the method.
1569
 */
1570
function panels_edit_cache_method_form_submit($form, &$form_state) {
1571
  $form_state['method'] = $form_state['values']['method'];
1572
}
1573
1574
/**
1575
 * Cache settings form
1576
 */
1577
function panels_edit_cache_settings_form($form, &$form_state) {
1578 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1579
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1580 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1581
  $conf = &$form_state['conf'];
1582
  $pid = $form_state['pid'];
1583
  $info = panels_get_cache($conf['method']);
1584
1585
  $form['#action'] = $form_state['url'];
1586
1587
  $form['description'] = array(
1588
    '#prefix' => '<div class="description">',
1589
    '#suffix' => '</div>',
1590
    '#value' => check_plain($info['description']),
1591
  );
1592
1593
  $function = panels_plugin_get_function('cache', $conf['method'], 'settings form');
1594
1595
  $form['settings'] = $function($conf['settings'], $display, $pid);
1596
  $form['settings']['#tree'] = TRUE;
1597
1598
  $form['display'] = array(
1599
    '#type' => 'value',
1600
    '#value' => $display,
1601
  );
1602
1603
  $form['pid'] = array(
1604
    '#type' => 'value',
1605
    '#value' => $pid,
1606
  );
1607
1608
  $form['submit'] = array(
1609
    '#type' => 'submit',
1610
    '#value' => t('Save'),
1611
  );
1612
1613
  return $form;
1614
}
1615
1616
/**
1617
 * Validate cache settings.
1618
 */
1619
function panels_edit_cache_settings_form_validate($form, &$form_state) {
1620
  if ($function = panels_plugin_get_function('cache', $form_state['conf']['method'], 'settings form validate')) {
1621
    $function($form, $form_state['values']['settings']);
1622
  }
1623
}
1624
1625
/**
1626
 * Allows panel styles to validate their style settings.
1627
 */
1628
function panels_edit_cache_settings_form_submit($form, &$form_state) {
1629
  if ($function = panels_plugin_get_function('cache', $form_state['conf']['method'], 'settings form submit')) {
1630
    $function($form_state['values']['settings']);
1631
  }
1632
1633
  $form_state['conf']['settings'] = $form_state['values']['settings'];
1634
}
1635
1636
/**
1637
 * Choose style form
1638
 */
1639
function panels_edit_style_type_form($form, &$form_state) {
1640 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1641
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1642 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1643
  $style = $form_state['style'];
1644
  $type = $form_state['type'];
1645
1646
  $styles = panels_get_styles();
1647
1648
  $function = ($type == 'pane' ? 'render pane' : 'render region');
1649
  $options = array();
1650
  if ($type == 'region') {
1651
    $options[-1] = t('Use display default style');
1652
  }
1653
1654
  uasort($styles, 'ctools_plugin_sort');
1655
1656
  foreach ($styles as $id => $info) {
1657
    if (empty($info['hidden']) && (!empty($info[$function]) || $id == 'default')) {
1658
      $options[$id] = check_plain($info['title']);
1659
    }
1660
  }
1661
1662
  $form['style'] = array(
1663
    '#prefix' => '<div class="no-float">',
1664
    '#suffix' => '</div>',
1665
    '#type' => 'radios',
1666
    '#title' => t('Style'),
1667
    '#options' => $options,
1668
    '#default_value' => $style,
1669
  );
1670
1671
  $form['submit'] = array(
1672
    '#type' => 'submit',
1673
    '#value' => t('Next'),
1674
  );
1675
  return $form;
1676
}
1677
1678
/**
1679
 * Submit callback for panels_edit_style_type_form.
1680
 *
1681
 * All this needs to do is return the method.
1682
 */
1683
function panels_edit_style_type_form_submit($form, &$form_state) {
1684
  $form_state['old_style'] = $form_state['style'];
1685
  $form_state['style'] = $form_state['values']['style'];
1686
}
1687
1688
/**
1689
 * Style settings form
1690
 */
1691
function panels_edit_style_settings_form($form, &$form_state) {
1692 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1693
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1694 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1695
  $conf = &$form_state['conf'];
1696
  $pid = $form_state['pid'];
1697
  $style = $form_state['style'];
1698
  $type = $form_state['type'];
1699
1700
  $form['#action'] = $form_state['url'];
1701
1702
  $form['description'] = array(
1703
    '#prefix' => '<div class="description">',
1704
    '#suffix' => '</div>',
1705
    '#value' => check_plain($style['description']),
1706
  );
1707
1708
  $function = panels_plugin_get_function('styles', $style, ($type == 'pane') ? 'pane settings form' : 'settings form');
1709
1710
  $form['settings'] = $function($conf, $display, $pid, $type, $form_state);
1711
  $form['settings']['#tree'] = TRUE;
1712
1713
  $form['submit'] = array(
1714
    '#type' => 'submit',
1715
    '#value' => t('Save'),
1716
  );
1717
1718 e4c061ad Assos Assos
1719
  // Need a cancel button since the style cache can persist and impact the wrong
1720
  // pane (or region, or display).
1721
  $form['cancel_style'] = array(
1722
    '#type' => 'submit',
1723
    '#value' => t('Cancel'),
1724
    '#submit' => array('panels_edit_style_settings_form_cancel'),
1725
  );
1726
1727 85ad3d82 Assos Assos
  return $form;
1728
}
1729
1730 e4c061ad Assos Assos
/**
1731
 * Cancel style settings form.
1732
 *
1733
 * Clears the editing cache to prevent styles being applied to incorrect regions
1734
 * or panes.
1735
 */
1736
function panels_edit_style_settings_form_cancel($form, &$form_state) {
1737
  $form_state['cancel'] = TRUE;
1738
}
1739
1740 85ad3d82 Assos Assos
/**
1741
 * Validate style settings.
1742
 */
1743
function panels_edit_style_settings_form_validate($form, &$form_state) {
1744
  $name = $form_state['type'] == 'pane' ? 'pane settings form validate' : 'settings form validate';
1745
  if ($function = panels_plugin_get_function('styles', $form_state['style'], $name)) {
1746
    $function($form, $form_state['values']['settings'], $form_state);
1747
  }
1748
}
1749
1750
/**
1751
 * Allows panel styles to validate their style settings.
1752
 */
1753
function panels_edit_style_settings_form_submit($form, &$form_state) {
1754
  $name = $form_state['type'] == 'pane' ? 'pane settings form submit' : 'settings form submit';
1755
  if ($function = panels_plugin_get_function('styles', $form_state['style'], $name)) {
1756
    $function($form, $form_state['values']['settings'], $form_state);
1757
  }
1758
1759
  $form_state['conf'] = $form_state['values']['settings'];
1760
}
1761
1762
1763
/**
1764
 * Configure CSS on a pane form.
1765
 */
1766
function panels_edit_configure_pane_css_form($form, &$form_state) {
1767 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1768
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1769 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1770
  $pane = &$form_state['pane'];
1771
1772
  $form['css_id'] = array(
1773
    '#type' => 'textfield',
1774
    '#default_value' => isset($pane->css['css_id']) ? $pane->css['css_id'] : '',
1775
    '#title' => t('CSS ID'),
1776
    '#description' => t('CSS ID to apply to this pane. This may be blank.'),
1777
  );
1778
  $form['css_class'] = array(
1779
    '#type' => 'textfield',
1780
    '#default_value' => isset($pane->css['css_class']) ? $pane->css['css_class'] : '',
1781
    '#title' => t('CSS class'),
1782
    '#description' => t('CSS class to apply to this pane. This may be blank.'),
1783
  );
1784
1785
  $form['next'] = array(
1786
    '#type' => 'submit',
1787
    '#value' => t('Save'),
1788
  );
1789
1790
  return $form;
1791
}
1792
1793
/**
1794
 * FAPI submission function for the CSS configure form.
1795
 *
1796
 * All this does is set up $pane properly. The caller is responsible for
1797
 * actually storing this somewhere.
1798
 */
1799
function panels_edit_configure_pane_css_form_submit($form, &$form_state) {
1800
  $pane = &$form_state['pane'];
1801
  $display = $form_state['display'];
1802
1803
  $pane->css['css_id'] = $form_state['values']['css_id'];
1804
  $pane->css['css_class'] = $form_state['values']['css_class'];
1805
}
1806
1807
/**
1808
 * Configure lock on a pane form.
1809
 */
1810
function panels_edit_configure_pane_lock_form($form, &$form_state) {
1811 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1812
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1813 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1814
  $pane = &$form_state['pane'];
1815
1816
  if (empty($pane->locks)) {
1817
    $pane->locks = array('type' => 'none', 'regions' => array());
1818
  }
1819
1820
  $form['type'] = array(
1821
    '#type' => 'radios',
1822
    '#title' => t('Lock type'),
1823
    '#options' => array(
1824
      'none' => t('No lock'),
1825
      'immovable' => t('Immovable'),
1826
      'regions' => t('Regions'),
1827
    ),
1828
    '#default_value' => $pane->locks['type'],
1829
  );
1830
1831
  $layout = panels_get_layout($display->layout);
1832
  $regions = panels_get_regions($layout, $display);
1833
1834
  $form['regions'] = array(
1835
    '#type' => 'checkboxes',
1836
    '#title' => t('Regions'),
1837
    '#options' => $regions,
1838
    '#description' => t('Select which regions this pane can be moved to.'),
1839
    '#dependency' => array(
1840
      'radio:type' => array('regions'),
1841
    ),
1842
    '#default_value' => $pane->locks['regions'],
1843
  );
1844
1845
  $form['#after_build'][] = 'panels_edit_configure_pane_lock_form_after_build';
1846
  $form['next'] = array(
1847
    '#type' => 'submit',
1848
    '#value' => t('Save'),
1849
  );
1850
1851
  return $form;
1852
}
1853
1854
function panels_edit_configure_pane_lock_form_after_build($element, $form_state) {
1855
  $region = $form_state['pane']->panel;
1856
  $element['regions'][$region]['#required'] = TRUE;
1857
  $element['regions'][$region]['#disabled'] = TRUE;
1858
  $element['regions'][$region]['#value'] = TRUE;
1859
  $element['regions'][$region]['#checked'] = TRUE;
1860
  $element['regions'][$region]['#attributes']['disabled'] = TRUE;
1861
  return $element;
1862
}
1863
1864
/**
1865
 * FAPI submission function for the lock configure form.
1866
 *
1867
 * All this does is set up $pane properly. The caller is responsible for
1868
 * actually storing this somewhere.
1869
 */
1870
function panels_edit_configure_pane_lock_form_submit($form, &$form_state) {
1871
  $pane = &$form_state['pane'];
1872
  $display = $form_state['display'];
1873
1874
  // We set this to true but forms do not submit disabled checkboxes
1875
  // and fapi is ignoring the #value directive probably because it
1876
  // is checkboxes:
1877
  $region = $form_state['pane']->panel;
1878
  $form_state['values']['regions'][$region] = $region;
1879
1880
  $pane->locks['type'] = $form_state['values']['type'];
1881
  $pane->locks['regions'] = array_filter($form_state['values']['regions']);
1882
}
1883
1884
/**
1885
 * Form to control basic visibility settings.
1886
 */
1887
function panels_edit_configure_access_settings_form($form, &$form_state) {
1888 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1889
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1890 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1891
  $pane = &$form_state['pane'];
1892
1893
  $form['logic'] = array(
1894
    '#type' => 'radios',
1895
    '#options' => array(
1896
      'and' => t('All criteria must pass.'),
1897
      'or' => t('Only one criterion must pass.'),
1898
    ),
1899
    '#default_value' => isset($pane->access['logic']) ? $pane->access['logic'] : 'and',
1900
  );
1901
1902
  $form['next'] = array(
1903
    '#type' => 'submit',
1904
    '#value' => t('Save'),
1905
  );
1906
1907
  return $form;
1908
}
1909
1910
/**
1911
 * FAPI submission function for the edit access settings form.
1912
 *
1913
 * All this does is set up $pane properly. The caller is responsible for
1914
 * actually storing this somewhere.
1915
 */
1916
function panels_edit_configure_access_settings_form_submit($form, &$form_state) {
1917
  $pane = &$form_state['pane'];
1918
  $display = $form_state['display'];
1919
1920
  $pane->access['logic'] = $form_state['values']['logic'];
1921
}
1922
1923
/**
1924
 * Form to add a visibility rule.
1925
 */
1926
function panels_edit_add_access_test_form($form, &$form_state) {
1927 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1928
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1929 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1930
  $pane = &$form_state['pane'];
1931
1932
  $plugins = ctools_get_relevant_access_plugins($display->context);
1933
  $options = array();
1934
  foreach ($plugins as $id => $plugin) {
1935
    $options[$id] = $plugin['title'];
1936
  }
1937
1938
  asort($options);
1939
1940
  $form['type'] = array(
1941
    // This ensures that the form item is added to the URL.
1942
    '#type' => 'radios',
1943
    '#options' => $options,
1944
  );
1945
1946
  $form['next'] = array(
1947
    '#type' => 'submit',
1948
    '#value' => t('Next'),
1949
  );
1950
1951
  return $form;
1952
}
1953
1954
/**
1955
 * Form to configure a visibility rule.
1956
 */
1957
function panels_edit_configure_access_test_form($form, &$form_state) {
1958 5a7e6170 Florent Torregrosa
  ctools_form_include($form_state, 'plugins', 'panels');
1959
  form_load_include($form_state, 'php', 'panels', '/plugins/display_renderers/panels_renderer_editor.class');
1960 85ad3d82 Assos Assos
  $display = &$form_state['display'];
1961
  $test = &$form_state['test'];
1962
  $plugin = &$form_state['plugin'];
1963
1964
  $form['#action'] = $form_state['url'];
1965
1966
  $contexts = $display->context;
1967
  if (!isset($contexts['logged-in-user'])) {
1968
    $contexts['logged-in-user'] = ctools_access_get_loggedin_context();
1969
  }
1970
1971
  if (isset($plugin['required context'])) {
1972
    $form['context'] = ctools_context_selector($contexts, $plugin['required context'], $test['context']);
1973
  }
1974
1975
  $form['settings'] = array('#tree' => TRUE);
1976
  if ($function = ctools_plugin_get_function($plugin, 'settings form')) {
1977
    $form = $function($form, $form_state, $test['settings']);
1978
  }
1979
1980
  $form['not'] = array(
1981
    '#type' => 'checkbox',
1982
    '#title' => t('Reverse (NOT)'),
1983
    '#default_value' => !empty($test['not']),
1984
  );
1985
1986
  $form['save'] = array(
1987
    '#type' => 'submit',
1988
    '#value' => t('Save'),
1989
  );
1990
1991
  $form['remove'] = array(
1992
    '#type' => 'submit',
1993
    '#value' => t('Remove'),
1994
    '#remove' => TRUE,
1995
  );
1996
1997
  return $form;
1998
}
1999
2000
/**
2001
 * Validate handler for visibility rule settings
2002
 */
2003
function panels_edit_configure_access_test_form_validate(&$form, &$form_state) {
2004
  if (!empty($form_state['clicked_button']['#remove'])) {
2005
    return;
2006
  }
2007
2008
  if ($function = ctools_plugin_get_function($form_state['plugin'], 'settings form validate')) {
2009
    $function($form, $form_state);
2010
  }
2011
}
2012
2013
/**
2014
 * Submit handler for visibility rule settings
2015
 */
2016
function panels_edit_configure_access_test_form_submit(&$form, &$form_state) {
2017
  if (!empty($form_state['clicked_button']['#remove'])) {
2018
    $form_state['remove'] = TRUE;
2019
    return;
2020
  }
2021
2022
  if ($function = ctools_plugin_get_function($form_state['plugin'], 'settings form submit')) {
2023
    $function($form, $form_state);
2024
  }
2025
2026
  $form_state['test']['settings'] = $form_state['values']['settings'];
2027
  if (isset($form_state['values']['context'])) {
2028
    $form_state['test']['context'] = $form_state['values']['context'];
2029
  }
2030
  $form_state['test']['not'] = !empty($form_state['values']['not']);
2031
}