htmlburger / wpemerge-theme

An organized, ES6 and SASS powered theme taking advantage of the WP Emerge framework. 🚀
https://wpemerge.com/
GNU General Public License v2.0
286 stars 33 forks source link

Twig alternative template #23

Closed j0j00 closed 5 years ago

j0j00 commented 5 years ago

Twig is included as one of the project's USP but it is not available inside the https://github.com/htmlburger/wpemerge-theme/tree/master/theme/alternative folder.

Are there any working templates available for new people to work from?

Thanks

atanas-dev commented 5 years ago

Hi @j0j00 ,

Unfortunately, at this time there are no prepared twig templates for the theme as the focus is on PHP and Blade. You can use the NameProxyViewEngine to use the available php templates and add new ones using twig if that suits your needs.

j0j00 commented 5 years ago

Are you sure the https://github.com/htmlburger/wpemerge-twig/ plugin actually works?

I planned to create the twig alternate templates and create a pull-request for it, but the plugin seems incomplete compared to the blade version.

It doesn't use the .twig file format at all.

Am I just completely misunderstanding what the twig plugin does and how it works?

Would it be possible to provide a working implementation of how it would even be used in practice? Since you need to declare the variables and their names somewhere and then render them in context.

atanas-dev commented 5 years ago

The Twig implementation is rather rudimentary - it started as an experiment / proof of concept that I ended up packaging for a couple of reasons:

  1. It covers the required basics - render a twig template when passed through app_view() with support for globals and view composers.
  2. Serves as a simpler real-world example of how to write an extension for WP Emerge.
  3. Serves as a simpler real-world example of how to render templates using a third party template engine.

Due to how it works, Twig requires more work to get stuff like the The Loop to be renderable which is very much doable but I just don't have the time to dedicate right now (I'm already spread thin over the framework, theme, CLI, Blade and docs projects not to mention the soon-to-be-released routing rewrite along with other high priority items that are yet to be implemented yadda yadda). This means that in order to have fully functioning alternative Twig templates there needs to be added support for all WordPress functions related to The Loop (and most probably the $post object). Timber for example has a whole host of custom variables which substitute The Loop.

Now if you don't care about The Loop and only want to render a custom Twig template with some variables you can do so with a View Composer or by passing the context directly: In a route handler:

Router::get( '/', function () {
    return app_view( 'my-custom-template.twig.php' )
        ->with( [
            'my_variable' => 'foo',
        ] );
} );

In a partial inside a PHP view:

<?php
app_render( 'my-custom-template.twig.php', [
    'my_variable' => 'foo',
] );
?>

You will also need to use the NameProxyViewEngine to render the default PHP templates that do use The Loop as usual:

// getContainer() used for brevity's sake - use a Service Provider instead.
$container = WPEmerge::getContainer();
$container[ WPEMERGE_VIEW_ENGINE_KEY ] = function( $container ) {
    return new \WPEmerge\View\NameProxyViewEngine( [
        '.twig.php' => WPEMERGETWIG_VIEW_TWIG_VIEW_ENGINE_KEY,
    ], WPEMERGE_VIEW_PHP_VIEW_ENGINE_KEY );
};
j0j00 commented 5 years ago

I understand what you mean now. The default replace_default_engine needs to be set to false because the current state of the plugin doesn't support WordPress loops out of the box.

But the expected behaviour can be achieved by having a php "controller" which renders the twig template, e.g. for a single, it'd be done this way:

<?php
// single.php
$post = get_the_post();
// Other variables that can be passed in.
app_render( 'twig/single.twig', [
    'post' => $post,
] );
?>

Is my thinking correct? If so, would you be okay to take it in as a pull-request?

atanas-dev commented 5 years ago

That method can work but not using built-ins like the_content() etc. will cause crucial filters and actions to never fire. I'd also suggest you use View Composers instead of passing the variables directly for a couple of reasons:

  1. Composers will always pass their context to the template regardless of which parent template loads it.
  2. Composers are reusable and can compose multiple views (e.g. if you want to pass the post you may reuse the same composer for both single.twig and page.twig).
  3. Multiple composers can compose the same view combining their contexts.
  4. Composers are testable.

I will refrain from merging PRs that deal with Twig default templates until I have spent enough time to evaluate all potential solutions and their upsides/downsides (which will obviously be a while) so feel free to publish it as a separate extension if that works for you.

j0j00 commented 5 years ago

Appreciate all the feedback, you raise a very good point regarding missing filters. To be honest, the amount of code required to render all the theme templates/views in twig in an intuitive manner isn't actually worth the trouble just to gain some syntactic sugar.

I'll probably be sticking with PHP template views for now since there's no extra overhead involved. I'll still play around with the twig integration to better understand how the framework works in general.

Also just out of curiosity, is this framework/theme production ready (performance/stability wise)?

There's not a lot of stars/forks, so I am a bit skeptical even though I like the documentation and features!

atanas-dev commented 5 years ago

Appreciate all the feedback

Happy to help :)

Also just out of curiosity, is this framework/theme production ready (performance/stability wise)?

The only projects I can speak for are ones I have been directly involved in and in those cases both the framework and theme have been used in production (for multiple projects) for over a year now.

There's not a lot of stars/forks

A project that is not (yet) popular does not mean that it is not (yet) great. Also you have the full power to push it forward with a ⭐ of your own :)