[Resolved] Rendering BuddyPress pages with special layouts

Home Forums Support [Resolved] Rendering BuddyPress pages with special layouts

Home Forums Support Rendering BuddyPress pages with special layouts

Viewing 13 posts - 1 through 13 (of 13 total)
  • Author
    Posts
  • #257037
    Jay Martin

    Hi, Tom. I’m trying to solve a problem that I think a number of developers will encounter, and was hoping to get some advice from you.

    I am using BuddyPress (BP) for providing comprehensive membership and group capabilities. A critical part of the membership model is the Registration process. Here is my problem, in a nutshell:

    I need to effect a full-width layout for the Registration-related pages (registration page, activation page, etc.), instead of the site default 2-column “left sidebar / content” design. I also need to replace the default header with a simple full-width image, similar to that effected by a post’s “Page Header Image” control; in essence, I need to effect a post design such that:

    • A Page Header Image is specified, rendered as full-width
    • Under the “Disable Elements” control, disable these elements: Header, Primary Navigation, Secondary Navigation, and Content Title

    I am fully cognizant of BP’s “theme compatibility mode” and have created the appropriate “buddypress” tree in my child theme (which uses GP as the parent theme) and placed all relevant specialized files in that tree.

    For the Registration page, I cloned GP’s page.php to create the /wp-content/themes/generatepress-child/buddypress/members/index-register.php file that drives the overall template action.

    I have effected a full-width layout by hooking into the ‘generate_sidebar_layout’ filter and returning ‘no-sidebar’ for the layout, based upon the approaches in your excellent “Sidebar Layouts” article in the GP Knowledge Base.

    I am still wresting with how to replace the default site header with just a full-width image. This is likely due lack of experience with WordPress, and I was hoping you could point me in the right direction as to the “Best Practice” for this kind of thing. From a newbie perspective, I would think that I have to mimic the usual get_header() process, but I’ll bet there is a simpler, more elegant solution possible (that I have yet to find).

    I would hate to have to hard-code an explicit header section if a more elegant and reusable approach is available.

    Thanks in advance for any light you may shed on this problem.

    #257084
    Jay Martin

    All of this customization stuff is the result of BuddyPress “capturing” the “register” URI slug and generating the page from templates based on BP’s template hierarchy. If I could only get BP to simply use a well-defined page (that allows me to specify page attributes in the usual, simple manner), then this effort would be a cakewalk.

    From what I can tell by reverse-engineering the code using my IDE’s debugging facilities (PHPStorm), it’s as if I need to use the standard get_header() function, but somehow in advance alter the target post’s meta data in order to inject the characteristics I described in the original post, such as layout, Disabled Elements, Page Header image, etc.

    Is this approach a viable solution, and if so, do you have any tips as to how I would effect the alteration of the post metadata so that the usual header mechanics work as usual?

    Or is another approach better?

    #257105
    Tom
    Lead Developer
    Lead Developer

    Hi Jay,

    Re-working our documentation and just added a section on changing the logo/header using a filter: http://docs.generatepress.com/article/adding-header-logo/

    Let me know if that’s what you’re after πŸ™‚

    #257157
    Jay Martin

    I looked at the code, Tom, but while I didn’t try it out, on the surface it doesn’t appear to achieve the requirement I have. Perhaps I wasn’t quite clear in explaining the execution context of this situation, so let me try again…

    My BuddyPress-controlled Registration page is part of a website that is seriously restricted from access by non-logged-in users. The page is a simple rendering of the usual BP registration form, but no artifacts of the restricted content are to be rendered. That means:

    • No site-wide default header
    • No menus or navigation components whatsoever

    The BuddyPress Registration page is not a normal page (or post) in the sense we’re used to — it does not exist as an item in the “Pages” list, nor the “Post” list, so I can’t use GP’s great features to apply the necessary characteristics to achieve my goals. BuddyPress “catches” the URI (“register”) used to render the page, and then applies its template hierarchy rules to derive which template will be used to drive the construction of the page.

    While there are a number of ways to create a tempalate that BP can find, I have elected to use the “index-register.php” template, as documented in BP’s hierarchy documentation. And, as I mentioned earlier, I manage the location of that file in the BP theme-compatible tree within my child theme at:

    /wp-content/themes/generatepress-child/buddypress/members/index-register.php

    In my specialized index-register.php file (which was cloned from GP’s page.php), it appears I need to execute get_header() (in all of its bloody glory, complete with no fewer than 8 action hooks) in order to get the page CSS files enqueued so the rest of the page renders properly.

    As it turns out, I may have been trying to pound a square peg into a round hole with regard to getting the equivalent of a Page Header Image into the top of the page. Since I have full control over the custom template, I can simply craft the necessary HTML directly into the template. I have made that change, and it works fine, so I am almost there. Almost.

    Naively, I assumed that if I simply commented-out the call to get_header() that everything would be fine. Yeah, pretty naive, for sure. There was no CSS applied to the primary content area (where the text and registration form reside).

    Apparently, at least *some* of the functionality of get_header() must be performed in order for the enqueuing of the CSS files. So this task is all that’s left for me to accomplish in order to meet my goals.

    So it comes down to this: What is the best way to effect the enqueuing of the necessary CSS files so that the primary content area (the div#primary container) is rendered with the theme-based CSS stylings?

    Thanks for your patience and support. πŸ˜‰

    #257215
    Tom
    Lead Developer
    Lead Developer

    get_header() calls the header.php file in the theme.

    So I suppose you could leave out the get_header() call in that template, and copy the code from the header.php file to include in your template.

    If you want no header at all, you would delete everything after the opening element that comes in the header.php file.

    Let me know if you need more info πŸ™‚

    #257313
    Jay Martin

    I must respectfully ask you to read the last 4 paragraphs of my previous reply, as your response leads me to believe you might not have read that far into the response.

    Copying header.php into my template serves no useful purpose at all. (Please read my last response as to why.)

    If you want no header at all, you would delete everything after the opening element that comes in the header.php file.

    I can only think you had a long hard day yesterday to actually propose this. πŸ˜‰

    Please go back and re-read my last response. Thanks, Tom.

    #257409
    Tom
    Lead Developer
    Lead Developer

    I did read it – just read it again and as far as I understand my answer still stands.

    What’s your end goal? Not having a header in that template?

    You need certain parts of get_header() (which simply calls the header.php file), so removing or commenting out get_header() isn’t going to work.

    However, in your template, you can remove the get_header() function, and then manually place what you need from header.php, which I’m assuming is everything up until the beginning of the header element.

    #257528
    Jay Martin

    While it is certainly possible for one to go through the myriad of code executed as part of the get_header() process, this just seemed to be an inelegant and rather painful approach.

    What I needed was the functional equivalent of injecting the definitions of the page defined for Registration into the post process such that GP would use that configuration to render the page as needed, in this case:

    • No header
    • No menus or navigation of any kind
    • Full-width content (instead of the site-wide blog default of content-sidebar)
    • Insertion of the image file specified in the Page Header section

    All of these specifications were easily defined in the page’s edit page…thanks to the wonder that is GeneratePress Premium. (Shameless plug for you, Tom. πŸ˜‰ )

    After considerable reverse-engineering, I found a rather simple and almost complete solution to getting what I need. Just before the call to get_header(), I do a database fetch on the page having the requisite definitions, and then assign that (single) post to the global $post variable:

    // Fetch the official Registration page and force it to be the $post
    // so that GeneratePress uses that page's definition to effect the presentation.
    $args = array(
    	'post_type' => array( 'page' ),
    	'pagename'  => 'register',
    );
    $reg_query = new WP_Query( $args );
    $post = $reg_query->post;
    
    get_header();

    And voila! No header, no menus, full-width content, and the display of the defined Page Header image.

    But wait… Houston, we have a problem…

    Even though the target page is defined such that “Sidebar Layout” is “Content (no sidebars)”, GP rendered the page such that the site-wide sidebar was rendered below the full-width content of the registration form!

    Very odd, indeed. Fortunately, the simple solution was to simply remove the call to do_action(‘generate_sidebars’) that exists just above the call to get_footer(). An alternative approach would be to hook into GP’s ‘generate_sidebar_layout’ filter hook and declare “no sidebars”, as follows:

    // Cause the page to be rendered as full-width content (no sidebars)
    function generate_register_page_sidebar_layout( $layout ) {
    return ‘no-sidebar’;
    }
    add_filter( ‘generate_sidebar_layout’,’generate_register_page_sidebar_layout’ );

    So, this is how one can totally leverage the power and simplicity of GeneratePress to control the presentation of a BuddyPress (or similar) page in a simple data-driven manner without having to resort to a mind-numbing code-intensive solution.

    Apologies for the long-winded exchange. Hope this helps others trying to achieve the same solution.

    #257529
    Jay Martin

    Quick followup:

    While the solution presented earlier certainly works for my scenario (aside from the weird sidebar rendition thing), there is something that should be added to the solution for real completeness, namely, adding important dynamically-added properties to the new $post, those that are not defined from the database fetch:

    // Fetch the official Registration page and force it to be the $post
    // so that GeneratePress uses that page's definition to effect the presentation.
    $args = array(
    	'post_type' => array( 'page' ),
    	'pagename'  => 'register',
    );
    $reg_query = new WP_Query( $args );
    $reg_post = $reg_query->post;
    
    // Update the db post instance with fields from $post that don't exist in the db version
    $reg_post->is_404     = $post->is_404;
    $reg_post->is_page    = $post->is_page;
    $reg_post->is_single  = $post->is_single;
    $reg_post->is_archive = $post->is_archive;
    $reg_post->is_tax     = $post->is_tax;
    
    $post = $reg_post;
    
    get_header();

    There may be other fields that also may have to be assigned. Post a reply if you can add to this discussion.

    I was hoping that injecting these additional properties to the $post (WP_Post object) would fix the sidebar oddities described in the last reply, but alas, it did not. Oh well.

    #257572
    Tom
    Lead Developer
    Lead Developer

    Glad you found a solution that works! It seems a little complex – personally I would have just removed the <header> element, but if it works then that’s great.

    Thanks for the posting your solution! Happy Holidays πŸ™‚

    #257652
    Jay Martin

    …I would have just removed the <header> element…

    Boy, I would have liked to have seen this recommendation early on. That certainly would have been an option, one that could work for lots of people.

    But let me explain why I am electing to not pursue that alternative (aside from having a solution that already works).

    You may prefer a different approach when it comes to engineering philosophy and discipline, but over the last 30 years many have found that a “data-driven” approach is much preferred over a “code-driven” approach. In this particular scenario, I chose to pursue a data-driven approach that leveraged the design specification capabilities available for rendering a known page; that is, use GP’s many theme customization capabilities to specify the page rendition (and let the stock theme templates drive the page construction), rather than code the page rendition by hand.

    If I followed your suggestion of “simply removing the <header> element”, that would have required the cloning of the stock GP header.php file into a header-register.php file (in which the <header> element is removed). While that may seem simple (and it is), that would have resulted in an extra artifact to be maintained, solely for the purpose of precluding the standard header rendition process. Sure, that can work, and it’s probably a more palatable approach for “non-coders”.

    However, what if later down the line I wanted to use a different Page Header image? Using your approach would require a manual modification of a PHP file. Using my approach, one would simply edit the target page’s definition using any number of GP controls to effect the desired change. This is a prime example of “data-driven” vs “code-driven” scenario.

    I appreciate the time you’ve taken to engage with me on this topic. I love GeneratePress and all that it offers, and continue to promote it to my fellow developers. πŸ˜‰

    Oh yeah, and Merry Christmas.

    #257667
    Tom
    Lead Developer
    Lead Developer

    I totally see your point, and you’re right πŸ™‚ Glad you found a solution that works for you.

    Merry Christmas!

    #257677
    Jay Martin

    Dear Santa,

    I realize I’ve just missed this Christmas season (by a few hours) to get this Christmas Wish onto your list, but maybe next year?

    I wish, I wish, I wish…

    That GeneratePress provided a new filter hook (let’s call it ‘applied-post-id’) that allows for the specification of a specific post to be used in generating the theme-specific page elements.

    The hook function would be passed the current $post->ID, and upon receiving the return value of the function, the GP code would determine if the returned ID differs from the one passed to the hook function, and if different, fetches the corresponding post and resets the global $post variable with the fetched post.

    Hey, a guy has to dream, no? πŸ˜‰

Viewing 13 posts - 1 through 13 (of 13 total)
  • You must be logged in to reply to this topic.