Anyone know a way to get a Controller to load $data for a Virtual Page?

Continuing the discussion from Virtual page with Rewirte Api without Custom Post Type:

I hope someone can help shed some light on this for me. I’ve been trying to understand how the Controller works in sage, and I must admit I’m struggling. I would like to hookup virtual pages which makes use of the Controller’s to handle the data as was raised by helgi in the above thread but no real solution was arrived at.
As discussed in that thread and in other documentation I’ve found the Controller is linked to the wordpress templates somehow by the code in app/filters.php and in particular I believe this:
$data = collect(get_body_class())->reduce(function ($data, $class) use ($template) {
return apply_filters(“sage/template/{$class}/data”, $data, $template);
}, []);
Somehow this filter knows which Controller to use to populate the $data variable which is then passed to the template() function which load the blade template. Am I understanding that correctly?
If so, then I think this is the key to understanding how to wire up a Controller to a virtual page along with the desired blade template file.

Does anyone know how to associate a Controller class to provide $data to a given virtual page’s blade template?

Thanks for your help.

get_body_class() is how it knows. It parses that for matching names to determine what data to load. In theory you could manipulate that to load whatever data you want, whenever you want.

Thanks alwaysblank. So with that in mind this seems to work:

add_action( 'init', function() {
  add_rewrite_endpoint( 'feedback', EP_ALL );
} );

function get_classes( $endpoint ){
  return array_unique( [
    'virtual-' . $endpoint . '-data']);

add_action( 'template_redirect', function() {
  global $wp_query;

  if( !isset( $wp_query -> query_vars[ 'feedback' ] ) ) {

  add_filter( 'body_class', function( $classes ) {
    return get_classes('feedback' );
  } );

  $template = locate_template( [ "virtual-feedback.blade.php" ] );

  if( $template ) {
    $data = collect( get_body_class() ) -> reduce( function( $data, $class ) use ( $template ) {
      return apply_filters( "sage/template/{$class}/data", $data, $template );
    }, [] );

    echo template( $template, $data );
} );

This topic was automatically closed after 42 days. New replies are no longer allowed.