content_type_extras.module 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419
  1. <?php
  2. define('CONTENT_TYPE_EXTRAS_ADMIN_DEFAULTS', 'administer content type defaults');
  3. define('CONTENT_TYPE_EXTRAS_NODE_DISPLAY_PERM', 'override content type title display');
  4. /**
  5. * Implements hook_init().
  6. */
  7. function content_type_extras_init() {
  8. drupal_add_css(drupal_get_path('module', 'content_type_extras') . '/css/content_type_extras.css');
  9. }
  10. /**
  11. * Implements hook_permission().
  12. */
  13. function content_type_extras_permission() {
  14. return array(
  15. CONTENT_TYPE_EXTRAS_ADMIN_DEFAULTS => array(
  16. 'title' => t('Administer content type defaults'),
  17. 'description' => t('Set the default settings to use on content types that are not overridden.'),
  18. ),
  19. CONTENT_TYPE_EXTRAS_NODE_DISPLAY_PERM => array(
  20. 'title' => t('Override content type title display'),
  21. 'description' => t('Allow the default node title display setting to be overridden on a per-node basis.'),
  22. ),
  23. );
  24. }
  25. /**
  26. * Implements hook_preprocess_page().
  27. */
  28. function content_type_extras_preprocess_page(&$vars) {
  29. // We have to check for the front page first since it's setting take precedence
  30. // over the node type setting.
  31. if (drupal_is_front_page()) {
  32. $hide_title_front = content_type_extras_get_default('content_type_extras_title_hide_front');
  33. if ($hide_title_front) {
  34. $hide_title_css = content_type_extras_get_default('content_type_extras_title_hide_css');
  35. if ($hide_title_css) {
  36. $vars['title_prefix']['content_type_extras'] = array(
  37. '#prefix' => '<div class="element-invisible">',
  38. );
  39. $vars['title_suffix']['content_type_extras'] = array(
  40. '#suffix' => '</div>',
  41. );
  42. }
  43. else {
  44. $vars['title'] = '';
  45. }
  46. }
  47. }
  48. elseif (!empty($vars['node'])) {
  49. $hide_title = content_type_extras_get_setting('content_type_extras_title_hide', $vars['node']->type);
  50. if ($hide_title) {
  51. $hide_title_css = content_type_extras_get_default('content_type_extras_title_hide_css');
  52. if ($hide_title_css) {
  53. $vars['title_prefix']['content_type_extras'] = array(
  54. '#prefix' => '<div class="element-invisible">',
  55. );
  56. $vars['title_suffix']['content_type_extras'] = array(
  57. '#suffix' => '</div>',
  58. );
  59. }
  60. else {
  61. $vars['title'] = '';
  62. }
  63. }
  64. }
  65. }
  66. /**
  67. * Implements hook_menu().
  68. */
  69. function content_type_extras_menu() {
  70. $items['admin/structure/types/defaults'] = array(
  71. 'title' => 'Default Settings',
  72. 'page callback' => 'drupal_get_form',
  73. 'page arguments' => array('content_type_extras_settings'),
  74. 'access arguments' => array(CONTENT_TYPE_EXTRAS_ADMIN_DEFAULTS),
  75. 'type' => MENU_LOCAL_TASK,
  76. 'file' => 'content_type_extras.admin.inc',
  77. 'file path' => drupal_get_path('module', 'content_type_extras') . '/includes',
  78. 'weight' => 10,
  79. );
  80. return $items;
  81. }
  82. /**
  83. * Implements hook_form_alter()
  84. */
  85. function content_type_extras_form_alter(&$form, &$form_state, $form_id) {
  86. // This is a list of node form ids to omit from being processed, since they don't
  87. // play nice with content_type_extras.
  88. $exclude_node_form = array(
  89. 'subscriptions_ui_node_form',
  90. );
  91. // node_type_form = Content type edit forms.
  92. if ($form_id == 'node_type_form') {
  93. module_load_include('inc', 'content_type_extras', 'includes/content_type_extras.node_type_form');
  94. content_type_extras_node_type_form($form);
  95. }
  96. // Viewing a specific node edit form
  97. elseif (strpos($form_id, '_node_form') && !in_array($form_id, $exclude_node_form)) {
  98. $type = $form['type']['#value'];
  99. // We need to check to see if auto_nodetitle module is hiding the title field
  100. // Thus, we check for $form['title']['#value'] != 'ant'
  101. if (user_access(CONTENT_TYPE_EXTRAS_NODE_DISPLAY_PERM) && (isset($form['title']['#value']) && $form['title']['#value'] != 'ant')) {
  102. $hide = content_type_extras_get_setting('content_type_extras_title_hide', $type);
  103. if (!empty($form['nid']['#value'])) {
  104. $hide = _content_type_extras_get_node_display($form['nid']['#value']);
  105. }
  106. $form['title_hide'] = array(
  107. '#type' => 'checkbox',
  108. '#title' => t("Exclude this node's title from display"),
  109. '#default_value' => $hide,
  110. '#weight' => 0,
  111. );
  112. if (variable_get('site_frontpage', '') . '/edit' == current_path()) {
  113. // We need to get the default settings since that is the only place that
  114. // the hide_title_front setting is stored.
  115. $defaults = content_type_extras_get_default();
  116. if (!empty($defaults['extras']['title_hide_front'])) {
  117. $form['title_hide']['#disabled'] = TRUE;
  118. $form['title_hide']['#description'] = t('<em>You cannot edit this option as it is set as the front page and the front page title is set to be hidden by the administrator.</em>');
  119. }
  120. }
  121. }
  122. $title_label = content_type_extras_get_setting('title_label', $type);
  123. if (isset($title_label) && $title_label != t('Title')) {
  124. $form['title']['#title'] = $title_label;
  125. }
  126. $save_and_new = content_type_extras_get_setting('content_type_extras_save_and_new', $type);
  127. if (!empty($save_and_new)) {
  128. $form['actions']['save_and_new'] = array(
  129. '#type' => 'submit',
  130. '#value' => content_type_extras_get_setting('content_type_extras_save_and_new_button', $type),
  131. '#weight' => $form['actions']['submit']['#weight'] + 1,
  132. '#submit' => array(
  133. 'node_form_submit',
  134. 'content_type_extras_node_form_new_submit',
  135. ),
  136. );
  137. }
  138. $save_and_edit = content_type_extras_get_setting('content_type_extras_save_and_edit', $type);
  139. if (!empty($save_and_edit)) {
  140. $form['actions']['save_and_edit'] = array(
  141. '#type' => 'submit',
  142. '#value' => content_type_extras_get_setting('content_type_extras_save_and_edit_button', $type),
  143. '#weight' => $form['actions']['submit']['#weight'] + 2,
  144. '#submit' => array(
  145. 'node_form_submit',
  146. 'content_type_extras_node_form_edit_submit',
  147. ),
  148. );
  149. }
  150. $preview = content_type_extras_get_setting('node_preview', $type);
  151. if (!empty($preview)) {
  152. $form['actions']['preview']['#value'] = content_type_extras_get_setting('content_type_extras_preview_button', $type);
  153. }
  154. $cancel = content_type_extras_get_setting('content_type_extras_cancel', $type);
  155. if (!empty($cancel)) {
  156. drupal_add_js(drupal_get_path('module', 'content_type_extras') . '/js/content_type_extras.cancel_button.js');
  157. $form['actions']['cancel'] = array(
  158. '#type' => 'button',
  159. '#value' => t('Cancel'),
  160. '#weight' => 100, // We want this at the end of whatever buttons are showing
  161. '#post_render' => array('content_type_extras_change_button_type'),
  162. );
  163. }
  164. // Add the form buttons to the top of the page
  165. // Based on: http://blog.urbaninsight.com/2011/09/20/editors-perspective-creating-content-drupal
  166. $top_buttons = content_type_extras_get_default('content_type_extras_top_buttons');
  167. if (!empty($top_buttons['node_edit'])) {
  168. $form['pre_actions'] = $form['actions'];
  169. $form['pre_actions']['#weight'] = -100;
  170. }
  171. $form['#submit'][] = 'content_type_extras_node_form_submit';
  172. }
  173. // Content type field machine names can only be a maximum of 32 characters (including 'field_')
  174. // but the user can enter a name any length, getting an error message if the name is too long
  175. // That drives me crazy!! This fixes that!
  176. elseif ($form_id == 'field_ui_field_overview_form') {
  177. drupal_add_js(drupal_get_path('module', 'content_type_extras') . '/js/content_type_extras.manage_fields.js');
  178. $top_buttons = content_type_extras_get_default('content_type_extras_top_buttons');
  179. if (!empty($top_buttons['manage_fields'])) {
  180. $form['pre_actions'] = $form['actions'];
  181. $form['pre_actions']['#weight'] = -100;
  182. }
  183. $form['fields']['_add_new_field']['field_name']['#maxlength'] = 26;
  184. $form['fields']['_add_new_field']['field_name']['#description'] .= t(' - <span class="characters">26</span> characters max.');
  185. // The field_group module does the same thing, so if that is enabled, handle it the same way
  186. if (module_exists('field_group')) {
  187. $form['fields']['_add_new_group']['group_name']['#maxlength'] = 26;
  188. $form['fields']['_add_new_group']['group_name']['#description'] .= t(' - <span class="characters">26</span> characters max.');
  189. }
  190. }
  191. }
  192. /**
  193. * Form submission handler for $form_id *_node_form
  194. */
  195. function content_type_extras_node_form_submit(&$form, &$form_state) {
  196. if (!empty($form_state['values']['title_hide'])) {
  197. _content_type_extras_set_node_display($form_state['values']['nid'], $form_state['values']['title_hide']);
  198. }
  199. }
  200. /**
  201. * Form submission for $form_id *_node_form
  202. */
  203. function content_type_extras_node_form_new_submit(&$form, &$form_state) {
  204. $form_state['redirect'] = 'node/add/' . str_replace('_', '-', $form_state['node']->type);
  205. }
  206. /**
  207. * Form submission for $form_id *_node_form
  208. */
  209. function content_type_extras_node_form_edit_submit(&$form, &$form_state) {
  210. $form_state['redirect'] = 'node/' . $form_state['values']['nid'] . '/edit';
  211. }
  212. /**
  213. * Implements hook_node_type_delete().
  214. */
  215. function content_type_extras_node_type_delete($info) {
  216. db_delete('variable')
  217. ->condition('name', 'content_type_extras_%_' . $info->type, 'LIKE')
  218. ->execute();
  219. }
  220. /**
  221. * Function to change the type of button from 'submit' to 'button.
  222. * -- From http://drupal.org/node/133861#comment-4002698
  223. */
  224. function content_type_extras_change_button_type($markup, $element) {
  225. $markup = str_replace('type="submit', 'type="button', $markup);
  226. return $markup;
  227. }
  228. /**
  229. * Function to set values for node title display
  230. */
  231. function _content_type_extras_set_node_display($nid, $hide) {
  232. $settings = variable_get('content_type_extras_node_display', array());
  233. $settings[$nid] = $hide;
  234. variable_set('content_type_extras_node_display', $settings);
  235. }
  236. /**
  237. * Function to get values for node title display
  238. */
  239. function _content_type_extras_get_node_display($nid) {
  240. $settings = variable_get('content_type_extras_node_display', array());
  241. if (isset($settings[$nid])) {
  242. return $settings[$nid];
  243. }
  244. return FALSE;
  245. }
  246. /**
  247. * Function to get values based on node type.
  248. *
  249. * @param $setting
  250. * Retrieve a specific setting from $type.
  251. * @param $type
  252. * The type of content to get $setting from.
  253. *
  254. * @return
  255. * Returns the requested setting for the given content type.
  256. */
  257. function content_type_extras_get_setting($setting, $type) {
  258. // We have to handle title_label differently because it is stored in the node_type
  259. // table, not in variables
  260. if ($setting == 'title_label') {
  261. $result = db_query("SELECT title_label
  262. FROM {node_type}
  263. WHERE module = 'node'
  264. AND type = :type", array(':type' => $type))->fetchField();
  265. if ($result) {
  266. return $result;
  267. }
  268. }
  269. return variable_get($setting . '_' . $type, content_type_extras_get_default($setting));
  270. }
  271. /**
  272. * Function to get default setting(s), when settings for content type do not exist.
  273. *
  274. * @param $setting
  275. * Retrieve a specific default setting.
  276. *
  277. * @return
  278. * Returns the requested setting or, if NULL, returns all default settings.
  279. */
  280. function content_type_extras_get_default($setting = NULL) {
  281. // This has to be unserialized as it will crash the default settings page.
  282. $defaults = variable_get('content_type_extras_default_settings');
  283. if ($setting == NULL) {
  284. if (!empty($defaults)) {
  285. return $defaults;
  286. }
  287. else {
  288. return content_type_extras_get_initial();
  289. }
  290. }
  291. else {
  292. if (isset($defaults[$setting])) {
  293. return $defaults[$setting];
  294. }
  295. else {
  296. return content_type_extras_get_initial($setting);
  297. }
  298. }
  299. }
  300. /**
  301. * Function to retrive intial (module default) settings when no other settings exist.
  302. * This will primarily be used when the module is first installed.
  303. *
  304. * @param $setting
  305. * Retrieve a specific initial setting.
  306. *
  307. * @return
  308. * Returns the requested setting or, if NULL, returns all initial settings.
  309. */
  310. function content_type_extras_get_initial($setting = NULL) {
  311. $initial_values = array(
  312. // Values set by Drupal Core (node.module)
  313. 'title_label' => t('Title'),
  314. 'node_preview' => 1,
  315. 'node_options' => array(
  316. 'status' => 'status',
  317. 'promote' => 'promote',
  318. 'sticky' => 0,
  319. 'revision' => 0,
  320. ),
  321. 'node_submitted' => 1,
  322. // Values set by content_type_extras.module
  323. 'content_type_extras_preview_button' => t('Preview'),
  324. 'content_type_extras_save_and_new' => 0,
  325. 'content_type_extras_save_and_new_button' => t('Save and New'),
  326. 'content_type_extras_save_and_edit' => 0,
  327. 'content_type_extras_save_and_edit_button' => t('Save and Edit'),
  328. 'content_type_extras_cancel' => 0,
  329. 'content_type_extras_title_hide' => 0,
  330. 'content_type_extras_title_hide_css' => 0,
  331. 'content_type_extras_title_hide_front' => 0,
  332. 'content_type_extras_top_buttons' => array(),
  333. 'content_type_extras_remove_body' => 0,
  334. 'content_type_extras_descriptions_required' => 0,
  335. 'content_type_extras_user_permissions_select' => 'cte',
  336. // Values set by comment.module
  337. 'comment' => array(
  338. 'comment' => 2,
  339. 'default_mode' => 1,
  340. 'default_per_page' => 50,
  341. 'anonymous' => 0,
  342. 'subject_field' => 1,
  343. 'form_location' => 1,
  344. 'preview' => 1,
  345. ),
  346. // Values set by pathauto module
  347. 'pathauto_node' => '',
  348. // Values set by xmlsitemap.module
  349. 'xmlsitemap_settings' => array(
  350. 'status' => 1,
  351. 'priority' => '0.5',
  352. ),
  353. );
  354. $admin_role = variable_get('user_admin_role', '');
  355. $initial_values['user_permissions'] = array(
  356. 'create_roles' => array($admin_role => $admin_role),
  357. 'edit_roles' => array($admin_role => $admin_role),
  358. 'delete_roles' => array($admin_role => $admin_role),
  359. );
  360. if ($setting == NULL) {
  361. return $initial_values;
  362. }
  363. return $initial_values[$setting];
  364. }
  365. /**
  366. * Redirect function to content_type_extras_node_type_form_submit().
  367. *
  368. * We use this method because when other modules are enabled, like Location,
  369. * that modify node_type_form an error is thrown saying that
  370. * content_type_extras_node_type_form_submit() is not declared. This is a
  371. * workaround to keep the actual function in
  372. * content_type_extras.node_type_form.inc for organization, but keep the
  373. * submission form from throwing an error.
  374. * @TODO: I'd like to find a better way to handle this, if one exists!
  375. */
  376. function content_type_extras_node_type_form_submit_redirect(&$form, &$form_state) {
  377. include_once(drupal_get_path('module', 'content_type_extras') . '/includes/content_type_extras.node_type_form.inc');
  378. content_type_extras_node_type_form_submit($form, $form_state);
  379. }