Ganchos de tema vs ganchos de módulo


10

A veces, cuando trato de aplicar un gancho, solo para darme cuenta de que se supone que está en un archivo de módulo.

¿Hay alguna manera de saber qué ganchos se pueden implementar en el archivo template.php de un tema o en un módulo?


44
Generalmente, cuando un gancho no está disponible para ser anulado en un tema, es por una buena razón. Los temas solo deben ser para el código relacionado con la visualización del contenido y la funcionalidad que proporcionan los módulos. El código que agrega / elimina / cambia la funcionalidad o el contenido generalmente debe estar en un módulo. También piense en el hecho de que si cambia de tema pierde cualquier personalización hecha en template.php, por lo que si está haciendo cambios que probablemente querría conservar si alguna vez cambiara de tema, definitivamente querría ir a un módulo.
rooby

Respuestas:


11

En términos generales, los temas solo pueden implementar alter hooks, lo que significa ganchos como hook_form_alter()y hook_menu_alter(), en resumen, todos los ganchos que se invocan drupal_alter()en Drupal 7 y versiones inferiores ( ModuleHandler()::alter()o ThemeManager::alter()en Drupal 8).

Otros ganchos, que son invocados por module_invoke_all()( ModuleHandler::invokeAll()en Drupal 8), no se invocan para temas simplemente porque, de hecho, el código no verifica si el tema habilitado actualmente define algún gancho.

  foreach (module_implements($hook) as $module) {
    $function = $module . '_' . $hook;
    if (function_exists($function)) {
      $result = call_user_func_array($function, $args);
      if (isset($result) && is_array($result)) {
        $return = array_merge_recursive($return, $result);
      }
      elseif (isset($result)) {
        $return[] = $result;
      }
    }
  }

En Drupal 8, donde la ModuleHandlerclase invoca ganchos implementados desde módulos y la ThemeManagerclase invoca ganchos implementados por temas, solo la primera clase implementa invoke()y invokeAll(). Esto significa que en Drupal 8 los ganchos del tema no son invocados por el núcleo de Drupal.

Esto es válido para los ganchos centrales de Drupal, y principalmente para todos los ganchos utilizados por módulos de terceros. Luego, depende de un módulo verificar que un tema también sea implementado por un tema e invocarlo. Esto es lo que hace el módulo Vistas.

  // Let modules modify the view just prior to rendering it.
  foreach (module_implements('views_pre_render') as $module) {
    $function = $module . '_views_pre_render';
    $function($this);
  }

  // Let the themes play too, because pre render is a very themey thing.
  foreach ($GLOBALS['base_theme_info'] as $base) {
    $function = $base->name . '_views_pre_render';
    if (function_exists($function)) {
      $function($this);
    }
  }
  $function = $GLOBALS['theme'] . '_views_pre_render';
  if (function_exists($function)) {
    $function($this);
  }

Para los ganchos utilizados por módulos de terceros, debe verificar el código utilizado para invocarlos. Lo más probable es que solo se invoquen los ganchos alternos para los temas, pero en algunos casos también se podrían implementar otros ganchos por temas.
Tenga en cuenta que en el caso de los temas, no todos los temas habilitados se verifican para implementaciones de gancho, al contrario de lo que sucede con los módulos. Solo se verifican el tema utilizado actualmente y los temas base, como se hace desde el módulo Vistas.


hook_entity_view_alter () no funciona en los temas.
dxvargas

Al menos en D7, los ganchos alternos en los temas solo se invocan si el tema ya se ha inicializado en la misma solicitud (es decir, llamando theme()). Si no se ha inicializado, no se ejecutará ningún enlace alternativo en ningún tema.
zwirbeltier

@zwirbeltier Los ganchos de tema se invocan para el tema utilizado para representar la página. theme()no cambia el tema utilizado para la página, pero invoca una función para representar datos. No cambia el tema, por ejemplo, de Garland a Minelli.
kiamlaluno

@kiamlaluno: Si miras el código drupal_alter(), ves que solo invoca alter-hooks en el tema si drupal_theme_initialize()se llamó antes. Si no fuera así, no hay un tema activo (todavía) y, por lo tanto, no se llaman ganchos. Al menos en D7 no hay garantía cuando drupal_theme_initialize()se llama por primera vez en una solicitud.
zwirbeltier

@zwirbeltier El tema establecido en Drupal ya se inicializa cuando se representa una página. Si un módulo establece un tema para una página sin llamar a la función apropiada, es su responsabilidad inicializarlo.
kiamlaluno
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.