We launched new forums in March 2019—join us there. In a hurry for help with your website? Get Help Now!
    • 23264
    • 2 Posts
    I have added a grep callback handler to the wayfinder snippet so that I can programatically remove a document resource from the output. It is very simple: the snippet call is extended to include the grep function, and the grep function returns TRUE or FALSE.

    At first I modified the core wayfinder snippet code like this
    if (class_exists('Wayfinder')) {
       // extend wayfinder here
       class WayfinderGrep extends Wayfinder
       {
        function renderRow(&$resource,$numChildren) {
            if ($this->_config['grep']){
                if (!call_user_func($this->_config['grep'],$resource))
                    return '';
            }
            return parent::renderRow(&$resource,$numChildren);
          }
       }
       $wf = new WayfinderGrep();
    } else {
        return 'error: Wayfinder class not found';
    }
    

    Then I moved my changes into a new snippet called WayfinderGrep. So the snippet call looks something like:

    [[WayfinderGrep? &startId=`0` &grep=`myGrepFunction`]]

    But I dont see it being called that way. Since the grep function needs a home, it is more convenient to create a specialised snippet and call WayfinderGrep from within
    <?php
    // myGrepSnippet can include whatever extra params I need 
    
    return $modx->runSnippet("wayfindergrep",Array("startId"=>$startId,"grep"=>"grep"));
    
    function grep($resource){
       // return TRUE or FALSE
    }
    ?>
    

    It all works nicely and Wayfinder is unchanged. But I had to copy the entire wayfinder snippet to wayfinderGrep which I wasn’t so happy with. But maybe that’s OK. Does anybody think this is a good way to extend core addons, or is there a better way?

    BTW: I’m no wayfinder expert so if this functionality already exists, please view this post as a simple query about extending addons.
      • 4310
      • 2,310 Posts
      If you want to remove certain documents why not use the &excludeDocs parameter?
        • 23264
        • 2 Posts
        Quote from: bunk58 at Nov 25, 2009, 11:30 AM

        If you want to remove certain documents why not use the &excludeDocs parameter?
        &excludeDocs is not always flexible enough. Callbacks give you almost unlimited ways to filter the results. You can filter on any of the built-in TVs for example, a little snippet to select all documents with "xyz" in the long title:

        [[xyz? &startId=`0`]]
        <?php //xyz
        
        return $modx->runSnippet("wayfindergrep",Array("startId"=>$startId,"grep"=>"grep"));
        
        function grep($resource){
           // only show documents that contain 'xyz' in the longtitle???
           return strstr($resource['longtitle'],'xyz')!=FALSE;
        }
        ?>
        

        Im using a similar function to support multiple document groups. In this scheme, a document can be in any number of different groups. The client gets to add the group(s) via a custom TV. When displayed, the document page contains a related items list generated by the wayfinder callback. All the callback needs to do is compare the current page group with the page group returned by wayfinder. The client now has the means to group together any documents from anywhere on the site. Because Wayfinder is unchanged, the Administrator has the power to restrict any documents in the usual ways.

        If anybody thinks they might have a use for this then:
        duplicate the Wayfinder snippet and rename to WayfinderGrep
        edit WayfinderGrep and..
        add the class extension code listed previously
        add the following line to the end of the config array
        ’grep’ => isset($grep) ? $grep : FALSE,

        To use the function:
        create a new snippet that contains the WayfinderGrep call and the callback function
        place the new snippet where you would have placed the original wayfinder reference