auto_nodetitle.module

Tracking 5.x-1.x branch
  1. drupal
    1. 5 contributions/auto_nodetitle/auto_nodetitle.module
    2. 6 contributions/auto_nodetitle/auto_nodetitle.module
    3. 7 contributions/auto_nodetitle/auto_nodetitle.module

Allows hiding of the node title field and automatic title creation

Constants

NameDescription
AUTO_NODETITLE_DISABLED
AUTO_NODETITLE_ENABLED
AUTO_NODETITLE_OPTIONAL

Functions & methods

NameDescription
auto_nodetitle_evalEvaluates php code and passes $node to it
auto_nodetitle_form_alterImplementation of hook_form_alter().
auto_nodetitle_get_settingGets the auto node title setting associated with the given content type.
auto_nodetitle_is_neededReturns whether the auto nodetitle has to be set.
auto_nodetitle_nodeapiImplementation of hook_nodeapi().
auto_nodetitle_node_operationsImplementation of hook_node_operations().
auto_nodetitle_node_settings_formHelper function for hook_form_alter() renders the settings per node-type. @TODO: a re-evaluate PHP pattern on edit? option.
auto_nodetitle_node_typeImplementation of hook_node_type().
auto_nodetitle_operations_updateCallback function for updating node titles.
auto_nodetitle_permImplementation of hook_perm()
auto_nodetitle_set_title
_auto_nodetitle_patternprocessorHelper function to generate the title according to the PHP code. Right now its only a wrapper, but if this is to be expanded, here is the place to be.

File

View source
  1. <?php
  2. /**
  3. * @file
  4. * Allows hiding of the node title field and automatic title creation
  5. */
  6. define('AUTO_NODETITLE_DISABLED', 0);
  7. define('AUTO_NODETITLE_ENABLED', 1);
  8. define('AUTO_NODETITLE_OPTIONAL', 2);
  9. /**
  10. * Implementation of hook_perm()
  11. */
  12. function auto_nodetitle_perm() {
  13. return array('use PHP for title patterns');
  14. }
  15. /**
  16. * Implementation of hook_form_alter().
  17. */
  18. function auto_nodetitle_form_alter($form_id, &$form) {
  19. if (isset($form['#node_type']) && 'node_type_form' == $form_id) {
  20. auto_nodetitle_node_settings_form($form);
  21. }
  22. else if (isset($form['#node']) && isset($form['#post']) && $form['#node']->type .'_node_form' == $form_id) {
  23. //this is a node form
  24. if (auto_nodetitle_get_setting($form['#node']->type) == AUTO_NODETITLE_ENABLED) {
  25. // we will autogenerate the title later, just hide the title field in the meanwhile
  26. $form['title']['#value'] = 'ant';
  27. $form['title']['#type'] = 'value';
  28. $form['title']['#required'] = FALSE;
  29. }
  30. else if (auto_nodetitle_get_setting($form['#node']->type) == AUTO_NODETITLE_OPTIONAL) {
  31. // we will make the title optional
  32. $form['title']['#required'] = FALSE;
  33. }
  34. }
  35. }
  36. /**
  37. * Implementation of hook_nodeapi().
  38. *
  39. * Sets the node title.
  40. * To let node previews work this is also done during node validation.
  41. */
  42. function auto_nodetitle_nodeapi(&$node, $op, $form = NULL, $a4 = NULL) {
  43. if ($op == 'validate' && $form['#post']['op'] == t('Preview') && auto_nodetitle_is_needed($node)) {
  44. // As changes to $node are not persistent during validation, we use form_set_value()!
  45. auto_nodetitle_set_title($node);
  46. form_set_value($form['title'], $node->title);
  47. }
  48. else if ($op == 'submit' && auto_nodetitle_is_needed($node)) {
  49. auto_nodetitle_set_title($node);
  50. }
  51. }
  52. /**
  53. * Returns whether the auto nodetitle has to be set.
  54. */
  55. function auto_nodetitle_is_needed($node) {
  56. return empty($node->auto_nodetitle_applied) && ($setting = auto_nodetitle_get_setting($node->type)) && !($setting == AUTO_NODETITLE_OPTIONAL && !empty($node->title));
  57. }
  58. /*
  59. * Sets the automatically generated nodetitle for the node
  60. */
  61. function auto_nodetitle_set_title(&$node) {
  62. $types = node_get_types();
  63. $pattern = variable_get('ant_pattern_'. $node->type, '');
  64. if (trim($pattern)) {
  65. $node->changed = time();
  66. $node->title = _auto_nodetitle_patternprocessor($pattern, $node);
  67. }
  68. else if ($node->nid) {
  69. $node->title = t('@type @node-id', array('@type' => $types[$node->type]->name, '@node-id' => $node->nid));
  70. }
  71. else {
  72. $node->title = t('@type', array('@type' => $types[$node->type]->name));
  73. }
  74. // Ensure the generated title isn't too long.
  75. $node->title = substr($node->title, 0, 255);
  76. // With that flag we ensure we don't apply the title two times to the same node.
  77. $node->auto_nodetitle_applied = TRUE;
  78. }
  79. /**
  80. * Implementation of hook_node_operations().
  81. */
  82. function auto_nodetitle_node_operations() {
  83. $operations = array(
  84. 'nodetitle_update' => array(
  85. 'label' => t('Update automatic nodetitles'),
  86. 'callback' => 'auto_nodetitle_operations_update',
  87. ),
  88. );
  89. return $operations;
  90. }
  91. /**
  92. * Callback function for updating node titles.
  93. */
  94. function auto_nodetitle_operations_update($nodes) {
  95. foreach ($nodes as $nid) {
  96. $node = node_load($nid);
  97. if ($node && auto_nodetitle_is_needed($node)) {
  98. $previous_title = $node->title;
  99. auto_nodetitle_set_title($node);
  100. // Only save if the title has actually changed.
  101. if ($node->title != $previous_title) {
  102. node_save($node);
  103. }
  104. }
  105. }
  106. }
  107. /**
  108. * Helper function to generate the title according to the PHP code.
  109. * Right now its only a wrapper, but if this is to be expanded, here is the place to be.
  110. * @return a title string
  111. */
  112. function _auto_nodetitle_patternprocessor($output, $node) {
  113. if (module_exists('token')) {
  114. $output = token_replace($output, 'node', $node);
  115. }
  116. if (variable_get('ant_php_'. $node->type, 0)) {
  117. $output = auto_nodetitle_eval($output, $node);
  118. }
  119. if (variable_get('ant_php_'. $node->type, 0) || module_exists('token')) {
  120. $output = preg_replace('/[\t\n\r\0\x0B]/', '', strip_tags($output));
  121. }
  122. return $output;
  123. }
  124. /**
  125. * Helper function for hook_form_alter() renders the settings per node-type.
  126. * @TODO: a re-evaluate PHP pattern on edit? option.
  127. */
  128. function auto_nodetitle_node_settings_form(&$form) {
  129. $form['auto_nodetitle'] = array(
  130. '#type' => 'fieldset',
  131. '#title' => t('Automatic title generation'),
  132. '#weight' => 0,
  133. '#collapsible' => TRUE,
  134. '#collapsed' => TRUE,
  135. );
  136. $form['auto_nodetitle']['ant'] = array(
  137. '#type' => 'radios',
  138. '#default_value' => auto_nodetitle_get_setting($form['#node_type']->type),
  139. '#options' => array(
  140. t('Disabled'),
  141. t('Automatically generate the title and hide the title field'),
  142. t('Automatically generate the title if the title field is left empty'),
  143. )
  144. );
  145. if (module_exists('token') || user_access('use PHP for title patterns')) {
  146. $description = t('Leave blank for using the per default generated title. Otherwise this string will be used as title.');
  147. if (module_exists('token')) {
  148. $description .= ' '. t('Use the syntax [token] if you want to insert a replacement pattern.');
  149. }
  150. $form['auto_nodetitle']['ant_pattern'] = array(
  151. '#type' => 'textarea',
  152. '#title' => t('Pattern for the title'),
  153. '#description' => $description,
  154. '#default_value' => variable_get('ant_pattern_'. $form['#node_type']->type, ''),
  155. );
  156. // Don't allow editing of the pattern if PHP is used, but the users lacks
  157. // permission for PHP.
  158. if (variable_get('ant_php_' . $form['#node_type']->type, '') && !user_access('use PHP for title patterns')) {
  159. $form['auto_nodetitle']['ant_pattern']['#value'] = $form['auto_nodetitle']['ant_pattern']['#default_value'];
  160. $form['auto_nodetitle']['ant_pattern']['#disabled'] = TRUE;
  161. $form['auto_nodetitle']['ant_pattern']['#description'] = t('You are not allow the configure the pattern for the title, as you lack the %permission permission.', array('%permission' => t('Use PHP for title patterns')));
  162. }
  163. }
  164. if (module_exists('token')) {
  165. $form['auto_nodetitle']['token_help'] = array(
  166. '#title' => t('Replacement patterns'),
  167. '#type' => 'fieldset',
  168. '#collapsible' => TRUE,
  169. '#collapsed' => TRUE,
  170. '#description' => t('Prefer raw-text replacements for text to avoid problems with HTML entities!'),
  171. );
  172. $form['auto_nodetitle']['token_help']['help'] = array(
  173. '#value' => theme('token_help', 'node'),
  174. );
  175. }
  176. if (user_access('use PHP for title patterns')) {
  177. $form['auto_nodetitle']['ant_php'] = array(
  178. '#type' => 'checkbox',
  179. '#title' => t('Evaluate PHP in pattern.'),
  180. '#description' => t('Put PHP code above that returns your string, but make sure you surround code in &lt;?php and ?&gt;. Note that $node is available and can be used by your code.'),
  181. '#default_value' => variable_get('ant_php_'. $form['#node_type']->type, ''),
  182. );
  183. }
  184. else {
  185. $form['auto_nodetitle']['auto_nodetitle_php'] = array(
  186. '#type' => 'value',
  187. '#value' => variable_get('ant_php_'. $form['#node_type']->type, ''),
  188. );
  189. }
  190. }
  191. /**
  192. * Gets the auto node title setting associated with the given content type.
  193. */
  194. function auto_nodetitle_get_setting($type) {
  195. return variable_get('ant_'. $type, AUTO_NODETITLE_DISABLED);
  196. }
  197. /**
  198. * Evaluates php code and passes $node to it
  199. */
  200. function auto_nodetitle_eval($code, $node) {
  201. ob_start();
  202. print eval('?>'. $code);
  203. $output = ob_get_contents();
  204. ob_end_clean();
  205. return $output;
  206. }
  207. /**
  208. * Implementation of hook_node_type().
  209. */
  210. function auto_nodetitle_node_type($op, $info) {
  211. switch ($op) {
  212. case 'delete':
  213. variable_del('ant_'. $info->type);
  214. variable_del('ant_pattern_'. $info->type);
  215. variable_del('ant_php_'. $info->type);
  216. break;
  217. case 'update':
  218. if (!empty($info->old_type) && $info->old_type != $info->type) {
  219. variable_set('ant_'. $info->type, auto_nodetitle_get_setting($info->old_type));
  220. variable_set('ant_pattern_'. $info->type, variable_get('ant_pattern_'. $info->old_type, ''));
  221. variable_set('ant_php_'. $info->type, variable_get('ant_php_'. $info->old_type, ''));
  222. variable_del('ant_'. $info->old_type);
  223. variable_del('ant_pattern_'. $info->old_type);
  224. variable_del('ant_php_'. $info->old_type);
  225. }
  226. break;
  227. }
  228. }