How to hide page title based on node type using template_preprocess_page()
and my reading suggests the best practice is to handle template logic in template.php using preprocess and process functions.


Decoupling the logic from the rendering code simply means the code in template.php sets a variable that is checked in the template file. In this way, the logic is all contained in the template.php file, while the rendering code is all in the template files.

template.php

function mytheme_preprocess_page(&amp;$variables) {
  if (!empty($variables['node']) &amp;&amp; $variables['node']-&gt;type == 'concert') {
    $variables['show_title'] = FALSE;
  }
}


page.tpl.php

&lt;?php if ($show_title &amp;&amp; $title): ?&gt;&lt;h1 class="title" id="page-title"&gt;&lt;?php print $title; ?&gt;&lt;/h1&gt;&lt;?php endif; ?&gt;


hide() doesn't work because $variables['title'] is a string, not a rendering array. hide() is always used with a rendering array, and it doesn't have any effect with a string, not even when the string is passed to render().
Actually, passing a string (or any value that is not a reference to a variable containing an array) to hide() would cause a PHP error, since the function uses this code.

function hide(&amp;$element) {
  $element['#printed'] = TRUE;
  return $element;
}


Unsetting $variables['title'] with unset($variables['title']) doesn't work too, as template_process_page() would get the page title from drupal_get_title().

if (!isset($variables['title'])) {
  $variables['title'] = drupal_get_title();
}