The Quick Tabs module allows you to create blocks of tabbed content. You can create a block on your site containing up to six tabs with corresponding content. Clicking on the tabs makes the corresponding content display instantly (it uses jQuery). The content for each tabbed section can be either a view or an existing block. It is an ideal way to do something like the Most Popular / Most Emailed stories tabs you see on many news websites.

Once created, the Quick Tabs blocks show up in your block listing, ready to be configured and enabled like other blocks.

Multiple Quick Tabs blocks can be placed on a single page.

Visit the Quick Tabs configuration page to choose a style for your Quick Tabs blocks.

Click on the "New QT block" tab below to get started.

', array('@configuration' => url('admin/settings/quicktabs'))); case 'admin/build/quicktabs/add': return '

'. t('Here you can create a new Quick Tabs block. Once you have created this block you will be taken to the blocks page to configure and enable it.', array('@overview' => url('admin/build/block'))) .'

'; } } function quicktabs_theme() { return array( 'quicktabs_settings' => array( 'arguments' => array('form' => NULL), ), 'quicktabs_preview_page' => array( 'arguments' => array(), ), 'qt_tabs' => array( 'arguments' => array('form' => NULL), ), 'qtaj_tabs' => array( 'arguments' => array('form' => NULL), ), 'quicktabs_block' => array( 'arguments' => array('block', 'title' => TRUE), ), 'quicktabs_tabs' => array( 'arguments' => array('tabs'), ), ); } /** * Implementation of hook_menu(). */ function quicktabs_menu() { $items = array(); $items['admin/build/quicktabs'] = array( 'title' => 'Quick Tabs', 'description' => 'Create blocks of tabbed content - content for each tab can be a view or a block', 'page callback' => 'quicktabs_list', 'access arguments' => array('administer quicktabs blocks'), ); $items['admin/build/quicktabs/list'] = array( 'title' => 'List', 'type' => MENU_DEFAULT_LOCAL_TASK, 'weight' => -10); $items['admin/build/quicktabs/add'] = array( 'title' => 'New QT block', 'access arguments' => array('create quicktabs block'), 'page callback' => 'quicktabs_new', 'weight' => 0, 'type' => MENU_LOCAL_TASK); $items['admin/build/quicktabs/ajax/add'] = array( 'title' => 'New QT AJAX block', 'access arguments' => array('create quicktabs block'), 'page callback' => 'quicktabs_new', 'page arguments' => array(TRUE), 'weight' => 1, 'type' => MENU_LOCAL_TASK); $items['admin/build/quicktabs/delete'] = array( 'title' => 'Delete QT block', 'access arguments' => array('administer blocks'), 'page callback' => 'drupal_get_form', 'page arguments' => array('quicktabs_block_delete'), 'type' => MENU_CALLBACK); $items['admin/build/quicktabs/edit'] = array( 'title' => 'Edit QT block', 'access arguments' => array('administer blocks'), 'page callback' => 'quicktabs_block_edit', 'type' => MENU_CALLBACK); $items['admin/settings/quicktabs'] = array( 'title' => 'Quick Tabs', 'description' => 'Select a style for your Quick Tabs blocks', 'page callback' => 'drupal_get_form', 'page arguments' => array('quicktabs_settings'), 'type' => MENU_NORMAL_ITEM, 'access arguments' => array('administer site configuration'), ); $items['quicktabs/preview'] = array( 'page callback' => 'quicktabs_preview_page', 'type' => MENU_CALLBACK, 'access arguments' => array('administer site configuration'), ); $items['quicktabs/ahah'] = array( 'page callback' => 'quicktabs_ahah', 'type' => MENU_CALLBACK, 'access arguments' => array('administer site configuration'), ); $items['quicktabs/views/displays'] = array( 'page callback' => 'quicktabs_ajax', 'type' => MENU_CALLBACK, 'access arguments' => array('administer site configuration'), ); $items['quicktabs/ajax/views'] = array( 'page callback' => 'quicktabs_ajax_views', 'type' => MENU_CALLBACK, 'access arguments' => array('access content'), ); $items['quicktabs/ajax/node'] = array( 'page callback' => 'quicktabs_ajax_node', 'type' => MENU_CALLBACK, 'access arguments' => array('access content'), ); return $items; } /** * Implementation of hook_perm(). */ function quicktabs_perm() { return array('create quicktabs block', 'administer quicktabs blocks'); } function quicktabs_list() { $result = db_query('SELECT qtid, title FROM {quicktabs}'); $header = array(t('Quick Tabs Block Name'), t('Delete')); $rows = array(); while ($row = db_fetch_object($result)) { $tablerow = array( array('data' => $row->title .' ('. l('edit', 'admin/build/quicktabs/edit/'. $row->qtid) .')'), array('data' => l(t('Delete'), 'admin/build/quicktabs/delete/'. $row->qtid)), ); $rows[] = $tablerow; } $output = theme('table', $header, $rows, array('id' => 'quicktabs')); return $output; } function quicktabs_new($ajax = FALSE) { global $base_url; $quicktabsForm = array( 'ajax_path' => $base_url .'/quicktabs/views/displays' ); drupal_add_js('/misc/jquery.form.js'); drupal_add_js(array('quicktabsForm' => $quicktabsForm), 'setting'); drupal_add_js(drupal_get_path('module', 'quicktabs') .'/js/quicktabs_form.js'); drupal_add_css(drupal_get_path('module', 'quicktabs') .'/quicktabs.css'); if (!$ajax) { return drupal_get_form('quicktabs_form'); } else { return drupal_get_form('quicktabs_aj_form'); } } function _quicktabs_get_default_views() { views_include('view'); views_include_default_views(); $defaults = module_invoke_all('views_default_views'); $views = array(); foreach ($defaults as $name => $view) { // Only views with a sufficiently high api version are eligible. if (isset($view->api_version) && $view->api_version >= 2) { $views[$name] = $view; } } return $views; } function _quicktabs_get_default_views_names() { $views = array(); foreach (_quicktabs_get_default_views() as $name => $view) { $views[] = array( 'name' => $name, ); } return $views; } function _quicktabs_get_default_view_displays($selected_view) { $displays = array(); foreach (_quicktabs_get_default_views() as $name => $view) { if ($name == $selected_view) { $display_array = $view->display; foreach ($display_array as $key => $display) { $displays[$key] = $key; } break; } } return $displays; } function quicktabs_get_views() { $result = db_query("SELECT v.name, v.description FROM {views_view} v"); $views = array(); while ($view = db_fetch_object($result)) { $views[$view->name] = $view->name; } $status = variable_get('views_defaults', array()); foreach (_quicktabs_get_default_views_names() as $view) { // Determine if default view is enabled or disabled. if (isset($status[$view['name']])) { $view['disabled'] = $status[$view['name']]; } if (empty($views[$view['name']]) && $view['disabled'] != 1) { $views[$view['name']] = $view['name']; } } return $views; } function quicktabs_get_blocks() { $blocks = _block_rehash(); $blocksarray = array(); foreach ($blocks as $i => $block) { if ($block['module'] != 'quicktabs') { $key = $block['module'] .'_delta_'. $block['delta']; $blocksarray[$key] = $block['info']; } } return $blocksarray; } function quicktabs_get_nodes() { $nodes = array(); // TODO: make the allowed node types an admin setting $result = db_query('SELECT nid, title FROM {node} WHERE type in ("page", "story")'); while ($row = db_fetch_object($result)) { $key = $row->nid; $nodes[$key] = $row->title; } return $nodes; } function quicktabs_form(&$form, $form_state = NULL) { $form = array( '#cache' => TRUE, ); $form['title'] = array( '#title' => t('Block Title'), '#type' => 'textfield', '#description' => t('The title of the whole block'), '#default_value' => ($form_state['values']['title'] ? $form_state['values']['title'] : ''), '#weight' => -5 ); $formtype = $form_state['values']['formtype']; if ($formtype == 'edit') { $tabcontent = $form_state['values']['tabs']; $form['qtid'] = array( '#type' => 'hidden', '#value' => $form_state['values']['qtid'] ); } if (isset($form_state['qt_count'])) { $qt_count = $form_state['qt_count']; } else { $qt_count = max(2, empty($tabcontent) ? 2 : count($tabcontent)); } // Add a wrapper for the tabs and Add Another Tab button. $form['qt_wrapper'] = array( '#tree' => FALSE, '#weight' => -4, '#prefix' => '
', '#suffix' => '
', ); $form['qt_wrapper']['tabs'] = array( '#prefix' => '
', '#suffix' => '
', '#theme' => 'qt_tabs', ); // Add the current tabs to the form. for ($delta = 0; $delta < $qt_count; $delta++) { $weight = isset($tabcontent[$delta]['weight']) ? $tabcontent[$delta]['weight'] : $delta-10; $title = isset($tabcontent[$delta]['title']) ? $tabcontent[$delta]['title'] : ''; $type = isset($tabcontent[$delta]['type']) ? $tabcontent[$delta]['type'] : 'block'; $bid = isset($tabcontent[$delta]['bvid']) ? $tabcontent[$delta]['bvid'] : NULL; $hide_title = isset($tabcontent[$delta]['hide_title']) ? $tabcontent[$delta]['hide_title'] : 1; $vid = isset($tabcontent[$delta]['bvid']) ? $tabcontent[$delta]['bvid'] : 'default'; $args = isset($tabcontent[$delta]['args']) ? $tabcontent[$delta]['args'] : NULL; $display = isset($tabcontent[$delta]['display']) ? $tabcontent[$delta]['display'] : 'default'; //$limit = isset($tabcontent[$delta]['limit']) ? $tabcontent[$delta]['limit'] : NULL; $form['qt_wrapper']['tabs'][$delta] = _quicktabs_form($delta, $weight, $title, $type, $bid, $hide_title, $vid, $args, $display); } $form['qt_wrapper']['tabs_more'] = array( '#type' => 'submit', '#prefix' => '
', '#suffix' => '
', '#value' => t('More tabs'), '#description' => t("Click here to add more tabs."), '#attributes' => array('class' => 'add-tab'), '#weight' => 1, '#submit' => array('qt_more_tabs_submit'), // If no javascript action. '#ahah' => array( 'path' => 'quicktabs/ahah', 'wrapper' => 'quicktabs-tabs', 'method' => 'replace', 'effect' => 'fade', ), ); $form['submit'] = array( '#type' => 'submit', '#value' => t('Save'), ); return $form; } function _quicktabs_form($delta, $weight = -10, $title = '', $type='block', $bid = 0, $hide_title = 1, $vid = 'default', $args = NULL, $display = 'default') { //$admin = user_access('administer quicktabs blocks'); $form = array( '#tree' => TRUE, ); $blocks = quicktabs_get_blocks(); // We'll manually set the #parents property of these fields so that // their values appear in the $form_state['values']['tabs'] array. $form['tabweight'] = array( '#type' => 'weight', '#default_value' => $weight, '#parents' => array('tabs', $delta, 'tabweight'), ); $form['tabtext'] = array( '#type' => 'textfield', '#size' => '10', '#title' => t('Tab @n', array('@n' => ($delta + 1))), '#default_value' => $title, '#parents' => array('tabs', $delta, 'tabtext'), ); if (module_exists('views')) { $views = quicktabs_get_views(); $form['type_options'] = array( '#type' => 'value', '#value' => array( 'block' => 'block', 'view' => 'view', ) ); $form['tabtype'] = array( '#type' => 'radios', '#options' => $form['type_options']['#value'], '#title' => t('Tab Content'), '#default_value' => $type, '#parents' => array('tabs', $delta, 'tabtype'), ); $views_keys = array_keys($views); $selected_view = ($vid ? ($vid == 'default' ? $views_keys[0] : ($type == 'block' ? $views_keys[0] : $vid)) : $views_keys[0]); $form['vid'] = array( '#type' => 'select', '#options' => $views, '#default_value' => $selected_view, '#title' => t('Select a view'), '#parents' => array('tabs', $delta, 'vid'), ); $form['args'] = array( '#type' => 'textfield', '#title' => 'arguments', '#size' => '10', '#required' => false, '#default_value' => $args, '#description' => t('Provide a comma separated list of arguments to pass to the view.'), '#parents' => array('tabs', $delta, 'args') ); $form['display'] = array( '#type' => 'select', '#title' => 'display', '#options' => _quicktabs_get_views_displays($selected_view), '#default_value' => $display, '#description' => t('Choose a display for your view.'), '#parents' => array('tabs', $delta, 'display') ); } else { $form['tabtype'] = array( '#type' => 'hidden', '#title' => t('Type for tab @n', array('@n' => ($delta + 1))), '#value' => $type, '#parents' => array('tabs', $delta, 'tabtype'), ); } $form['bid'] = array( '#type' => 'select', '#options' => $blocks, '#default_value' => $bid, '#title' => t('Select a block'), '#parents' => array('tabs', $delta, 'bid'), ); $form['hide_title'] = array( '#type' => 'checkbox', '#title' => t('Hide the title of this block'), '#default_value' => $hide_title, '#parents' => array('tabs', $delta, 'hide_title'), ); $form['remove'] = array( '#type' => 'submit', '#value' => 'remove_'. $delta, '#attributes' => array('class' => 'delete-tab'), '#parents' => array('tabs', $delta, 'remove'), '#ahah' => array( 'path' => 'quicktabs/ahah/'. $delta, 'wrapper' => 'quicktabs-tabs', 'method' => 'replace', 'effect' => 'fade', ), ); return $form; } function theme_qt_tabs($form) { // Change the button title to reflect the behavior when using JavaScript. drupal_add_tabledrag('qt-tablist-table', 'order', 'sibling', 'qt-tabs-weight'); drupal_add_js('if (Drupal.jsEnabled) { $(document).ready(function() { $("#edit-tabs-more").val("'. t('Add another tab') .'"); }); }', 'inline'); $rows = array(); $headers = array( t('Tab Title'), t('Weight'), module_exists('views') ? t('Tab type') : '', t('Content'), t('Remove') ); foreach (element_children($form) as $key) { // No need to print the field title every time. unset($form[$key]['tabtext']['#title'], $form[$key]['tabtype']['#title'], $form[$key]['bvid']['#title']); $form[$key]['tabweight']['#attributes']['class'] = 'qt-tabs-weight'; // Build the table row. $row = array( 'data' => array( array('data' => drupal_render($form[$key]['tabtext']), 'class' => 'qt-tab-title'), array('data' => drupal_render($form[$key]['tabweight']), 'class' => 'qt-tab-weight'), module_exists('views') ? array('data' => drupal_render($form[$key]['tabtype']), 'class' => 'qt-tab-type') : array('data' => '', 'class' => 'qt-tabtype-hidden'), array('data' => drupal_render($form[$key]['bid']) . drupal_render($form[$key]['hide_title']) . (module_exists('views') ? drupal_render($form[$key]['vid']) . drupal_render($form[$key]['args']) . drupal_render($form[$key]['limit']) . drupal_render($form[$key]['display']) : ''), 'class' => 'qt-tab-bvid'), array('data' => drupal_render($form[$key]['remove']), 'class' => 'qt-tab-remove') ), 'class' => 'draggable', ); // Add additional attributes to the row, such as a class for this row. if (isset($form[$key]['#attributes'])) { $row = array_merge($row, $form[$key]['#attributes']); } $rows[] = $row; } $output = theme('table', $headers, $rows, array('id' => 'qt-tablist-table')); $output .= drupal_render($form); return $output; } function quicktabs_form_validate($form, &$form_state) { if (empty($form_state['values']['title'])) { form_set_error('title', t('You must give your Quick Tabs block a title.')); } else { foreach ($form_state['values']['tabs'] as $j => $tab) { if (empty($tab['tabtext'])) { form_set_error('tabs]['. $j .'][tabtext', t('You must give each tab a title.')); } } } } function quicktabs_form_submit($form, $form_state) { $formvalues_tabs = array(); foreach ($form_state['values']['tabs'] as $j => $tab) { $formvalues_tabs[] = array( 'title' => $form_state['values']['tabs'][$j]['tabtext'], 'type' => $form_state['values']['tabs'][$j]['tabtype'], 'bvid' => ($form_state['values']['tabs'][$j]['tabtype'] == 'block' ? $form_state['values']['tabs'][$j]['bid'] : $form_state['values']['tabs'][$j]['vid']), 'hide_title' => ($form_state['values']['tabs'][$j]['tabtype'] == 'block' ? $form_state['values']['tabs'][$j]['hide_title'] : 0), 'weight' => $form_state['values']['tabs'][$j]['tabweight'], 'args' => ($form_state['values']['tabs'][$j]['type'] == 'block' ? '' : $form_state['values']['tabs'][$j]['args']), 'display' => ($form_state['values']['tabs'][$j]['type'] == 'block' ? '' : $form_state['values']['tabs'][$j]['display']), ); } $fullcontent = array( 'blocktitle' => $form_state['values']['title'], 'blockcontent' => $formvalues_tabs, ); if ($form_state['values']['qtid']) { $qtid = $form_state['values']['qtid']; quicktabs_updateblock($qtid, $fullcontent); $msg = t('Your Quick Tabs block has been updated.'); } else { quicktabs_createblock($fullcontent); $msg = t('Your Quick Tabs block has been created and can now be enabled.'); } drupal_set_message($msg); drupal_goto('admin/build/quicktabs'); } /** * ajax version */ function quicktabs_aj_form(&$form, $form_state = NULL) { $form = array( '#cache' => TRUE, ); $form['title'] = array( '#title' => t('Block Title'), '#type' => 'textfield', '#description' => t('The title of the whole block'), '#default_value' => ($form_state['values']['title'] ? $form_state['values']['title'] : ''), '#weight' => -5 ); $formtype = $form_state['values']['formtype']; if ($formtype == 'edit') { $tabcontent = $form_state['values']['tabs']; $form['qtid'] = array( '#type' => 'hidden', '#value' => $form_state['values']['qtid'] ); } if (isset($form_state['qt_count'])) { $qt_count = $form_state['qt_count']; } else { $qt_count = max(2, empty($tabcontent) ? 2 : count($tabcontent)); } // Add a wrapper for the tabs and Add Another Tab button. $form['qt_wrapper'] = array( '#tree' => FALSE, '#weight' => -4, '#prefix' => '
', '#suffix' => '
', ); $form['qt_wrapper']['tabs'] = array( '#prefix' => '
', '#suffix' => '
', '#theme' => 'qtaj_tabs', ); // Add the current tabs to the form. for ($delta = 0; $delta < $qt_count; $delta++) { $weight = isset($tabcontent[$delta]['weight']) ? $tabcontent[$delta]['weight'] : $delta-10; $title = isset($tabcontent[$delta]['title']) ? $tabcontent[$delta]['title'] : ''; $type = isset($tabcontent[$delta]['type']) ? $tabcontent[$delta]['type'] : 'node'; $nid = isset($tabcontent[$delta]['bnid']) ? $tabcontent[$delta]['bnid'] : NULL; $vid = isset($tabcontent[$delta]['bnid']) ? $tabcontent[$delta]['bnid'] : 'default'; $args = isset($tabcontent[$delta]['args']) ? $tabcontent[$delta]['args'] : NULL; $display = isset($tabcontent[$delta]['display']) ? $tabcontent[$delta]['display'] : 'default'; $form['qt_wrapper']['tabs'][$delta] = _quicktabs_aj_form($delta, $weight, $title, $type, $nid, $vid, $args, $display); } $form['qt_wrapper']['tabs_more'] = array( '#type' => 'submit', '#prefix' => '
', '#suffix' => '
', '#value' => t('More tabs'), '#description' => t("Click here to add more tabs."), '#attributes' => array('class' => 'add-tab'), '#weight' => 1, '#submit' => array('qt_more_tabs_submit'), // If no javascript action. '#ahah' => array( 'path' => 'quicktabs/ahah/true', 'wrapper' => 'quicktabs-tabs', 'method' => 'replace', 'effect' => 'fade', ), ); $form['submit'] = array( '#type' => 'submit', '#value' => t('Save'), ); return $form; } function _quicktabs_aj_form($delta, $weight = -10, $title = '', $type='node', $nid = 0, $vid = 'default', $args = NULL, $display = 'default') { //$admin = user_access('administer quicktabs blocks'); $form = array( '#tree' => TRUE, ); $nodes = quicktabs_get_nodes(); // We'll manually set the #parents property of these fields so that // their values appear in the $form_state['values']['tabs'] array. $form['tabweight'] = array( '#type' => 'weight', '#default_value' => $weight, '#parents' => array('tabs', $delta, 'tabweight'), ); $form['tabtext'] = array( '#type' => 'textfield', '#size' => '10', '#title' => t('Tab @n', array('@n' => ($delta + 1))), '#default_value' => $title, '#parents' => array('tabs', $delta, 'tabtext'), ); if (module_exists('views')) { $views = quicktabs_get_views(); $form['type_options'] = array( '#type' => 'value', '#value' => array( 'node' => 'node', 'view' => 'view', ) ); $form['tabtype'] = array( '#type' => 'radios', '#options' => $form['type_options']['#value'], '#title' => t('Tab Content'), '#default_value' => $type, '#parents' => array('tabs', $delta, 'tabtype'), ); $views_keys = array_keys($views); $selected_view = ($vid ? ($vid == 'default' ? $views_keys[0] : ($type == 'node' ? $views_keys[0] : $vid)) : $views_keys[0]); $form['vid'] = array( '#type' => 'select', '#options' => $views, '#default_value' => $selected_view, '#title' => t('Select a view'), '#parents' => array('tabs', $delta, 'vid'), ); $form['args'] = array( '#type' => 'textfield', '#title' => 'arguments', '#size' => '10', '#required' => false, '#default_value' => $args, '#description' => t('Provide a comma separated list of arguments to pass to the view.'), '#parents' => array('tabs', $delta, 'args') ); $form['display'] = array( '#type' => 'select', '#title' => 'display', '#options' => _quicktabs_get_views_displays($selected_view), '#default_value' => $display, '#description' => t('Choose a display for your view.'), '#parents' => array('tabs', $delta, 'display') ); } else { $form['tabtype'] = array( '#type' => 'hidden', '#title' => t('Type for tab @n', array('@n' => ($delta + 1))), '#value' => $type, '#parents' => array('tabs', $delta, 'tabtype'), ); } $form['nid'] = array( '#type' => 'select', '#options' => $nodes, '#default_value' => $nid, '#title' => t('Select a node'), '#parents' => array('tabs', $delta, 'nid'), ); $form['remove'] = array( '#type' => 'submit', '#value' => 'remove_'. $delta, '#attributes' => array('class' => 'delete-tab'), '#parents' => array('tabs', $delta, 'remove'), '#ahah' => array( 'path' => 'quicktabs/ahah/true/'. $delta, 'wrapper' => 'quicktabs-tabs', 'method' => 'replace', 'effect' => 'fade', ), ); return $form; } function theme_qtaj_tabs($form) { // Change the button title to reflect the behavior when using JavaScript. drupal_add_tabledrag('qt-tablist-table', 'order', 'sibling', 'qt-tabs-weight'); drupal_add_js('if (Drupal.jsEnabled) { $(document).ready(function() { $("#edit-tabs-more").val("'. t('Add another tab') .'"); }); }', 'inline'); $rows = array(); $headers = array( t('Tab Title'), t('Weight'), module_exists('views') ? t('Tab type') : '', t('Content'), t('Remove') ); foreach (element_children($form) as $key) { // No need to print the field title every time. unset($form[$key]['tabtext']['#title'], $form[$key]['tabtype']['#title'], $form[$key]['bnid']['#title']); $form[$key]['tabweight']['#attributes']['class'] = 'qt-tabs-weight'; // Build the table row. $row = array( 'data' => array( array('data' => drupal_render($form[$key]['tabtext']), 'class' => 'qt-tab-title'), array('data' => drupal_render($form[$key]['tabweight']), 'class' => 'qt-tab-weight'), module_exists('views') ? array('data' => drupal_render($form[$key]['tabtype']), 'class' => 'qt-tab-type') : array('data' => '', 'class' => 'qt-tabtype-hidden'), array('data' => drupal_render($form[$key]['nid']) . (module_exists('views') ? drupal_render($form[$key]['vid']) . drupal_render($form[$key]['args']) . drupal_render($form[$key]['limit']) . drupal_render($form[$key]['display']) : ''), 'class' => 'qt-tab-bvid'), array('data' => drupal_render($form[$key]['remove']), 'class' => 'qt-tab-remove') ), 'class' => 'draggable', ); // Add additional attributes to the row, such as a class for this row. if (isset($form[$key]['#attributes'])) { $row = array_merge($row, $form[$key]['#attributes']); } $rows[] = $row; } $output = theme('table', $headers, $rows, array('id' => 'qt-tablist-table')); $output .= drupal_render($form); return $output; } function quicktabs_aj_form_validate($form, &$form_state) { if (empty($form_state['values']['title'])) { form_set_error('title', t('You must give your Quick Tabs block a title.')); } else { foreach ($form_state['values']['tabs'] as $j => $tab) { if (empty($tab['tabtext'])) { form_set_error('tabs]['. $j .'][tabtext', t('You must give each tab a title.')); } } } } function quicktabs_aj_form_submit($form, $form_state) { $formvalues_tabs = array(); foreach ($form_state['values']['tabs'] as $j => $tab) { $formvalues_tabs[] = array( 'title' => $form_state['values']['tabs'][$j]['tabtext'], 'type' => $form_state['values']['tabs'][$j]['tabtype'], 'bnid' => ($form_state['values']['tabs'][$j]['tabtype'] == 'node' ? $form_state['values']['tabs'][$j]['nid'] : $form_state['values']['tabs'][$j]['vid']), 'weight' => $form_state['values']['tabs'][$j]['tabweight'], 'args' => ($form_state['values']['tabs'][$j]['type'] == 'node' ? '' : $form_state['values']['tabs'][$j]['args']), 'display' => ($form_state['values']['tabs'][$j]['type'] == 'node' ? '' : $form_state['values']['tabs'][$j]['display']), ); } $fullcontent = array( 'blocktitle' => $form_state['values']['title'], 'blockcontent' => $formvalues_tabs, ); if ($form_state['values']['qtid']) { $qtid = $form_state['values']['qtid']; quicktabs_updateblock($qtid, $fullcontent); $msg = t('Your Quick Tabs block has been updated.'); } else { quicktabs_createblock($fullcontent, TRUE); $msg = t('Your Quick Tabs block has been created and can now be enabled.'); } drupal_set_message($msg); drupal_goto('admin/build/quicktabs'); } /** * Menu callback for AHAH additions. */ function quicktabs_ahah($ajax = FALSE, $delta = -1) { // Build the new form. $form_state = array('submitted' => FALSE); $form_build_id = $_POST['form_build_id']; // Add the new element to the stored form. Without adding the element to the // form, Drupal is not aware of this new elements existence and will not // process it. We retreive the cached form, add the element, and resave. $form = form_get_cache($form_build_id, $form_state); if ($delta == -1) { $delta = count($_POST['tabs']); $maxweight = -10; foreach ($_POST['tabs'] as $tab) { if ($tab['tabweight'] > $maxweight) { $maxweight = $tab['tabweight']; } } $newweight = $maxweight+1; if ($delta < 10) { // Build our new form element. $form_element = $ajax ? _quicktabs_aj_form($delta, $newweight) : _quicktabs_form($delta, $newweight); } $form['qt_wrapper']['tabs'][$delta] = $form_element; } else { $op = 'remove'; if (count($form['qt_wrapper']['tabs']) > 2) { unset($form['qt_wrapper']['tabs'][$delta]); } else { drupal_set_message('The number of tabs cannot be less than two. Simply change the content of the second tab.'); } } form_set_cache($form_build_id, $form, $form_state); $form += array( '#post' => $_POST, '#programmed' => FALSE, ); // Rebuild the form. $form = form_builder('quicktabs_form', $form, $form_state); // Render the new output. $qt_form = $form['qt_wrapper']['tabs']; unset($qt_form['#prefix'], $qt_form['#suffix']); // Prevent duplicate wrappers. if ($op != 'remove') { $stripe = $delta % 2 ? 'even' : 'odd'; $qt_form[$delta]['#attributes']['class'] = empty($qt_form[$delta]['#attributes']['class']) ? 'draggable ahah-new-content'. $stripe : $qt_form[$delta]['#attributes']['class'] .'draggable ahah-new-content'; } $output = theme('status_messages') . drupal_render($qt_form); drupal_json(array('status' => TRUE, 'data' => $output)); } function _quicktabs_get_views_displays($view) { $displays = array(); $result = db_query('SELECT d.id FROM {views_view} v INNER JOIN {views_display} d ON v.vid = d.vid WHERE v.name = "%s" ORDER BY position ASC', $view); while ($row = db_fetch_object($result)) { $displays[$row->id] = $row->id; } if (empty($displays)) { $displays = _quicktabs_get_default_view_displays($view); } return $displays; } function quicktabs_ajax($view, $delta) { $form_element = array( '#name' => 'tabs['. $delta .'][display]', '#type' => 'select', '#title' => 'display', '#options' => _quicktabs_get_views_displays($view), '#description' => t('Choose a display for your view.'), '#parents' => array('tabs', $delta, 'display') ); $form_state = array('submitted' => FALSE); $form_build_id = $_POST['form_build_id']; $form = form_get_cache($form_build_id, $form_state); $form['qt_wrapper']['tabs'][$delta]['display'] = $form_element; form_set_cache($form_build_id, $form, $form_state); $form += array( '#post' => $_POST, '#programmed' => FALSE, ); // Rebuild the form. $form = form_builder('quicktabs_form', $form, $form_state); $output = drupal_render($form_element); print drupal_to_js(array('status' => TRUE, 'data' => $output)); } function quicktabs_createblock($fullcontent, $ajax = FALSE) { $qtid = db_last_insert_id('quicktabs', 'qtid'); $title = $fullcontent['blocktitle']; $tabs = serialize($fullcontent['blockcontent']); if (!$ajax) { db_query('INSERT INTO {quicktabs} (qtid, title, tabs) VALUES(%d, "%s", "%s")', $qtid, $title, $tabs); } else { db_query('INSERT INTO {quicktabs} (qtid, ajax, title, tabs) VALUES(%d, 1, "%s", "%s")', $qtid, $title, $tabs); } return; } function quicktabs_updateblock($qtid, $fullcontent) { $title = $fullcontent['blocktitle']; $tabs = serialize($fullcontent['blockcontent']); db_query('UPDATE {quicktabs} SET title="%s", tabs="%s" WHERE qtid=%d', $title, $tabs, $qtid); return; } /** * Implementation of hook_block */ function quicktabs_block($op = 'list', $delta = 0, $edit = array()) { switch ($op) { case 'list': $jqueryblocks = array(); $result = db_query('SELECT * FROM {quicktabs}'); while ($row = db_fetch_object($result)) { $jqueryblocks[$row->qtid] = $row->title; } foreach ($jqueryblocks as $key => $val) { $blocks[$key]['info'] = t($val); } return $blocks; break; case 'view': if ($qtblock = db_fetch_object(db_query('SELECT qtid, ajax, title, tabs FROM {quicktabs} WHERE qtid = %d', $delta))) { quicktabs_add_css(); drupal_add_js(drupal_get_path('module', 'quicktabs') .'/js/quicktabs.js'); if ($qtblock->ajax == 0) { $mainblock['subject'] = $qtblock->title; $tabs = unserialize($qtblock->tabs); foreach ($tabs as $key => $tab) { $weight[$key] = $tab['weight']; } array_multisort($weight, SORT_ASC, $tabs); $tabtitles = array(); foreach ($tabs as $tab) { $tabtitles[] = $tab['title']; } $output = '
'; $output .= theme('quicktabs_tabs', $tabtitles); $output .= '
'; foreach ($tabs as $j => $tab) { $output .= '
'; if ($tab['type'] == 'view') { if (module_exists('views')) { $args = array(); if ($tab['args'] != '') { $args_array = explode(',', $tab['args']); foreach($args_array as $arg) { $args[] = trim($arg); } } $func_args = array_merge(array($tab['bvid'], $tab['display']), $args); $output .= call_user_func_array('views_embed_view', $func_args); } else { $output .= 'Views module not enabled, cannot display tab content'; } } else { $pos = strpos($tab['bvid'], '_delta_'); $blockmodule = substr($tab['bvid'], 0, $pos); $blockdelta = substr($tab['bvid'], $pos+7); $block = (object) module_invoke($blockmodule, 'block', 'view', $blockdelta); $block->module = $blockmodule; $block->delta = $blockdelta; if ($tab['hide_title'] != 1) { $output .= $block->content ? theme('quicktabs_block', $block, TRUE) : ''; } else { $output .= $block->content ? theme('quicktabs_block', $block, FALSE) : ''; } } $output .= '
'; } $output .= '
'; $mainblock['content'] = $output; } else { $mainblock['subject'] = $qtblock->title; $tabs = unserialize($qtblock->tabs); foreach ($tabs as $key => $tab) { $weight[$key] = $tab['weight']; } array_multisort($weight, SORT_ASC, $tabs); $fullpath = explode('?', $_SERVER['REQUEST_URI']); $queries = $_GET; unset($queries['quicktabs_'. $delta]); unset($queries['q']); $querystring = ''; if (!empty($queries)) { $i = 0; foreach ($queries as $key => $value) { $querystring .= $i > 0 ? '&'. $key .'='. $value : $key .'='. $value; $i++; } $querystring .= '&'; } $path = $fullpath[0]; $path .= '?'. $querystring; $output = '
'; $output .= ''; $output .= '
'; $output .= '
'; $active_tab = $_GET['quicktabs_'. $delta] ? $_GET['quicktabs_'. $delta] : 0; if ($tabs[$active_tab]['type'] == 'view') { $args = array(); if ($tabs[$active_tab]['args'] != '') { $args_array = explode(',', $tabs[$active_tab]['args']); foreach($args_array as $arg) { $args[] = trim($arg); } } $func_args = array_merge(array($tabs[$active_tab]['bnid'], $tabs[$active_tab]['display']), $args); $output .= call_user_func_array('views_embed_view', $func_args); } else { $node = node_load($tabs[$active_tab]['bnid']); $output .= theme('node', $node); } $output .= '
'; $output .= '
'; $mainblock['content'] = $output; } } return $mainblock; break; } } function quicktabs_ajax_views($vid, $did, $args = NULL) { $args_ar = array(); if ($args) { $args_array = explode('|', $args); foreach($args_array as $arg) { $args_ar[] = trim($arg); } } $func_args = array_merge(array($vid, $did), $args_ar); $output = call_user_func_array('views_embed_view', $func_args); print drupal_to_js(array('status' => TRUE, 'data' => $output)); } function quicktabs_ajax_node($nid) { $node = node_load($nid); $output = theme('node', $node); print drupal_to_js(array('status' => TRUE, 'data' => $output)); } function theme_quicktabs_block($block, $title = TRUE) { $output = "
module\" id=\"block-$block->module-$block->delta\">\n"; if ($title) { $output .= "

$block->subject

\n"; } $output .= "
$block->content
\n"; $output .= "
\n"; return $output; } /** * Theme function for output of the tabs. Use this to ADD extra classes. * The general structure 'ul.quicktabs_tabs li a' needs to be maintained * for the jQuery to work. */ function theme_quicktabs_tabs($tabs) { $output .= ''; return $output; } function quicktabs_block_get_name($qtid) { $result = db_result(db_query('SELECT title FROM {quicktabs} WHERE qtid=%d', $qtid)); return $result; } function quicktabs_block_delete(&$form_state, $qtid =0) { $qt_name = quicktabs_block_get_name($qtid); $form['qtid'] = array('#type' => 'hidden', '#value' => $qtid); $form['qt_name'] = array('#type' => 'hidden', '#value' => $qt_name); return confirm_form($form, t('Are you sure you want to delete the Quick Tabs block %name?', array('%name' => $qt_name)), 'admin/build/quicktabs', '', t('Delete'), t('Cancel')); } function quicktabs_block_edit($qtid) { if ($qtblock = db_fetch_object(db_query('SELECT title, tabs, ajax FROM {quicktabs} WHERE qtid = %d', $qtid))) { $tabs = unserialize($qtblock->tabs); foreach ($tabs as $key => $tab) { $weight[$key] = $tab['weight']; } array_multisort($weight, SORT_ASC, $tabs); $form_state = array(); $form_state['values'] = array( 'qtid' => $qtid, 'title' => $qtblock->title, 'tabs' => $tabs, 'formtype' => 'edit', ); global $base_url; $quicktabsForm = array( 'ajax_path' => $base_url .'/quicktabs/views/displays' ); drupal_add_js(array('quicktabsForm' => $quicktabsForm), 'setting'); drupal_add_js(drupal_get_path('module', 'quicktabs') .'/js/quicktabs_form.js'); drupal_add_css(drupal_get_path('module', 'quicktabs') .'/quicktabs.css'); if ($qtblock->ajax == 0) { $output = drupal_get_form('quicktabs_form', $form_state); } else { $output = drupal_get_form('quicktabs_aj_form', $form_state); } return $output; } else { drupal_goto('admin/build/quicktabs'); } } /** * Deletion of Quick Tabs blocks. */ function quicktabs_block_delete_submit($form, $form_state) { db_query('DELETE FROM {quicktabs} WHERE qtid = %d', $form_state['values']['qtid']); drupal_set_message(t('The Quick Tabs block %name has been removed.', array('%name' => $form_state['values']['qt_name']))); cache_clear_all(); drupal_goto('admin/build/quicktabs'); }; /** * Callback function for admin/settings/quicktabs. Display the settings form. */ function quicktabs_settings() { $form = array(); $form['quicktabs_tabstyle'] = array( '#type' => 'radios', '#title' => t('Tab Style'), '#options' => array('default' => t('Default (no style)')) + module_invoke_all('quicktabs_tabstyles'), '#default_value' => variable_get('quicktabs_tabstyle', 'default'), '#description' => t('Choose a tab style for your Quick Tabs blocks.'), '#attributes' => array('class' => 'quicktabs-tabstyles clear-block'), ); $form['submit'] = array( '#type' => 'submit', '#value' => t('Submit'), ); return $form; } function quicktabs_settings_submit($form, $form_state) { variable_set('quicktabs_tabstyle', $form_state['values']['quicktabs_tabstyle']); variable_set('quicktabs_blocktitles', $form_state['values']['quicktabs_blocktitles']); //variable_set('quicktabs_viewbuild', $form_state['values']['quicktabs_viewbuild']); } function theme_quicktabs_settings($form) { quicktabs_add_css(); drupal_set_title(t('Quick Tabs Settings')); // Default preview. $form['quicktabs_tabstyle']['default']['#description'] = 'Default '. t('Preview') .':
'; // Preview for each style. $tabstyle_number = 0; foreach (element_children($form['quicktabs_tabstyle']) as $tabstyle_key) { if ($tabstyle_key != 'default') { $form['quicktabs_tabstyle'][$tabstyle_key]['#description'] = $form['quicktabs_tabstyle'][$tabstyle_key]['#title'] .' '. t('Preview') .':
'; $tabstyle_number++; } } return drupal_render($form); } /** * Callback function for quicktabs/preview. */ function quicktabs_preview_page($tabstyle_number = NULL) { $tabstyles = module_invoke_all('quicktabs_tabstyles'); $css_files = array_keys($tabstyles); if (isset($css_files[$tabstyle_number])) { quicktabs_add_css($css_files[$tabstyle_number]); } else { quicktabs_add_css('default'); } drupal_add_js(drupal_get_path('module', 'quicktabs') .'/js/quicktabs.js'); print theme('quicktabs_preview_page'); exit; } function theme_quicktabs_preview_page() { $output = "\n"; $output .= ''; $output .= ''; $output .= ' '. t('Quick Tabs Preview') .''; $output .= drupal_get_html_head(); $output .= drupal_get_css(); $output .= drupal_get_js(); $output .= ' '; $output .= ' '; $output .= '
'; $output .= ''; $output .= '
'; $output .= ''; return $output; } /** * Fetch the necessary CSS files for the tab styles. */ function quicktabs_add_css($tabstyle_css = NULL) { // Add quicktabs CSS. drupal_add_css(drupal_get_path('module', 'quicktabs') .'/quicktabs.css'); // Add specific CSS. if (!isset($tabstyle_css)) { $tabstyle_css = variable_get('quicktabs_tabstyle', 'default'); } if ($tabstyle_css != 'default') { drupal_add_css($tabstyle_css, 'module'); } } /** * Implementation of hook_quicktabs_widgets. * * This hook allows other modules to create additional tab styles for * the quicktabs module. * * @return array * An array of key => value pairs suitable for inclusion as the #options in a * select or radios form element. Each key must be the location of a css * file for a quick tabs style. Each value should be the name of the style. */ function quicktabs_quicktabs_tabstyles() { $tabstyles_directory = drupal_get_path('module', 'quicktabs') .'/tabstyles'; $files = file_scan_directory($tabstyles_directory, '\.css$'); $tabstyles = array(); foreach ($files as $file) { $tabstyles[$file->filename] = drupal_ucfirst($file->name); } return $tabstyles; }