We launched new forums in March 2019—join us there. In a hurry for help with your website? Get Help Now!
    • 36926
    • 701 Posts
    Thanks for the reply. I've had no issues with getting the simple example explained in the link you provided above, but what I wanted to get working was the doodles tutorial.

    I'd been playing around with skipping the index.class.php as well and got a sort of success, if you can call it that, as I'm no longer getting a blank white page but instead an blank CMP page but the rest of modx is loading, which it wasn't before.

    I could see that some of the JS and CSS files weren't loading which i'm guessing was due to missing the functions from the index.class.php file. But thats really as far as I've got at the moment.

    I'll try extending the modExtraManagerController like you've done and I'll let you know how I get on.

    Be nice to get a 2.3 update for doodles as can't see there be that much difference.

    Thanks again smiley
      • 3749
      • 24,544 Posts
      FWIW, the Example cmp included with MyComponent *does* use the index.class.php file as described here: http://bobsguides.com/blog.html/2014/03/28/modx-2.2-cmps-an-anatomy-lesson/. I believe it works in 2.3.

      As Susan says, the only real difference in 2.3 CMPs is the ability to access actions files by name rather than by action ID, and that's not a requirement yet -- 2.3 is backward compatible on that issue.

      Here's the example index.class.php file (note that it actually contains two classes):

      abstract class ExampleManagerController extends modExtraManagerController {
          /** @var Example $example */
          public $example = NULL;
       
          /* Initialize the main manager controller.*/
       
          public function initialize() {
              /* Instantiate the Example class in the controller */
              $path = $this->modx->getOption('example.core_path',
                      NULL, $this->modx->getOption('core_path') .
                      'components/example/') . 'model/example/';
              require_once $path . 'example.class.php';
              $this->example = new Example($this->modx);
       
              /* Optional alternative  - install PHP class as a service */
       
              /* $this->example = $this->modx->getService('example',
                   'Example', $path);*/
       
              /* Add the main javascript class and our configuration */
              $this->addJavascript($this->example->config['jsUrl'] .
                  'example.class.js');
              $this->addHtml('<script type="text/javascript">
              Ext.onReady(function() {
                  Example.config = ' . $this->modx->toJSON($this->example->config) . ';
              });
              </script>');
          }
       
          public function getLanguageTopics() {
              return array('example:default');
          }
       
          public function checkPermissions() {
              return true;
          }
       
          public function getTemplateFile() {
              return $this->example->config['templatesPath'] . 'mgr.tpl';
          }
      }
       
      /**
       * The Index Manager Controller is the default one that gets
       * called when no action is present. */
       
      class IndexManagerController extends ExampleManagerController {
       
          /* Defines the name or path to the default controller to load. */
          public static function getDefaultController() {
              return 'home';
          }
      }
        Did I help you? Buy me a beer
        Get my Book: MODX:The Official Guide
        MODX info for everyone: http://bobsguides.com/modx.html
        My MODX Extras
        Bob's Guides is now hosted at A2 MODX Hosting
        • 36926
        • 701 Posts
        Hey Bob,

        Not actually used MyComponent before, but just checked out your tutorial and looks a great and very useful tool.

        I have a few CMP thats aren't packaged up as they are very custom and would be of no use to anyone. So to install them I just manually configure. So put the correct files under the core and assets folder and then add the namespace and menu/action details. This all works fine but if I try and do this within 2.3 but skipping the action part as it's not needed or even possible I get blank page when view the CMP.

        So I've just tried an experiment with your example CMP. So within 2.2.16 i've copied the directories and files of the example CMP to the relevant places. So you have
        assets/components/example
        core/components/example

        I've created the namespace, action and added to the menu.
        Then clicking the menu item the example CMP grid loads and works ok.

        But if I do the above within 2.3 but without creating the action as it's not needed and for the create menu I have:
        parent = extras
        action = index
        namespace = example

        Then when i click the menu item i get a blank white page, not even the modx manager.

        But now if i go into the actual database and manually add a row to modx_actions table for the example CMP. Then amend the menu details to the following.
        parent = extras
        action = 1
        namespace = example

        Then view this everything is actually working fine.

        So there's something within that index.class.php file that will only work when an id is passed, so what do we need to amend in this file to work with the new way.

        Note this is the error i'm getting when view the example CMP within 2.3
        [28-Oct-2014 13:21:44 UTC] PHP Fatal error:  Class 'ExampleIndexManagerController' not found in /Volumes/Sites/cmp/core/model/modx/modmanagerresponse.class.php on line 185
        


          • 3749
          • 24,544 Posts
          I'm guessing, but I think the issue is with the menu item itself. For 2.3, the 'action' field should contain a name rather than a number. For the Example CMP, it's still a number since it has to run in earlier versions and will still run in 2.3 as a number -- as long as you create a modAction for it (which the Example install does):

          $action = $modx->newObject('modAction');
          $action->fromArray( array (
            'namespace' => 'example',
            'controller' => 'index',
            'haslayout' => 1,
            'lang_topics' => 'example:default',
            'assets' => '',
            'help_url' => '',
            'id' => 1,
          ), '', true, true);
          
          $menus[1] = $modx->newObject('modMenu');
          $menus[1]->fromArray( array (
            'text' => 'Example',
            'parent' => 'components',
            'description' => 'ex_menu_desc',
            'icon' => '',
            'menuindex' => 0,
            'params' => '',
            'handler' => '',
            'permissions' => '',
            'id' => 1,
          ), '', true, true);
          $menus[1]->addOne($action);


          The bottom line is that if the menu 'action' field has a number, there has to be a modAction record with that ID, but if it's a string naming the action, the modAction is unnecessary -- at least that's my guess. wink


            Did I help you? Buy me a beer
            Get my Book: MODX:The Official Guide
            MODX info for everyone: http://bobsguides.com/modx.html
            My MODX Extras
            Bob's Guides is now hosted at A2 MODX Hosting
            • 36926
            • 701 Posts
            Quote from: BobRay at Oct 28, 2014, 04:46 PM

            The bottom line is that if the menu 'action' field has a number, there has to be a modAction record with that ID, but if it's a string naming the action, the modAction is unnecessary -- at least that's my guess. wink

            I'm not even able to replicate the simple example here in 2.3:
            http://rtfm.modx.com/revolution/2.x/developing-in-modx/advanced-development/custom-manager-pages
            And have my menu like this:
            parent = extras
            action = index
            namespace = myextra

            Should display something, but this is also producing the blank white page.

            The only success I get is if I skip the index.class.php file and set menu like this:
            parent = extras
            action = home
            namespace = myextra

            So it's now using
            controllers/home.class.php

            But then should i be moving everything from the index class to here also?

              • 3749
              • 24,544 Posts
              Does your index.class.php file have something like this at the end?

              class IndexManagerController extends ExampleManagerController {
               
                  /* Defines the name or path to the default controller to load. */
                  public static function getDefaultController() {
                      return 'home';
                  }
              }
                Did I help you? Buy me a beer
                Get my Book: MODX:The Official Guide
                MODX info for everyone: http://bobsguides.com/modx.html
                My MODX Extras
                Bob's Guides is now hosted at A2 MODX Hosting
                • 36926
                • 701 Posts
                Quote from: BobRay at Oct 28, 2014, 06:34 PM
                Does your index.class.php file have something like this at the end?

                class IndexManagerController extends ExampleManagerController {
                 
                    /* Defines the name or path to the default controller to load. */
                    public static function getDefaultController() {
                        return 'home';
                    }
                }

                Yeah all the CMPs i've tried do. Including the simple example from the RTF, which is:

                <?php
                /**
                 * The abstract Manager Controller.
                 * In this class, we define stuff we want on all of our controllers.
                 */
                
                abstract class MyextraManagerController extends modExtraManagerController {
                    /**
                     * Initializes the main manager controller. You may want to load certain classes,
                     * assets that are shared across all controllers or configuration. 
                     *
                     * All your other controllers in this namespace should extend this one.
                     *
                     * In this case we don't do anything useful, but as you build up more complex
                     * extras, it helps to enforce this structure to make it easier to maintain.
                     */
                    public function initialize() {
                        $this->addHtml('<script type="text/javascript">
                        Ext.onReady(function() {
                            // We could run some javascript here that runs on all of our controllers
                            // for example something that loads your config
                        });
                        </script>');
                    }
                    /**
                     * Defines the lexicon topics to load in our controller.
                     * @return array
                     */
                    public function getLanguageTopics() {
                        return array('namespace:default');
                    }
                    /**
                     * We can use this to check if the user has permission to see this controller
                     * @return bool
                     */
                    public function checkPermissions() {
                        return true;
                    }
                }
                /**
                 * The Index Manager Controller is the default one that gets called when no
                 * &action parameter is passed  We use it to define the default controller
                 * which will then handle the actual processing.
                 *
                 * It is important to name this class "IndexManagerController" and making sure
                 * it extends the abstract class we defined above 
                 */
                class IndexManagerController extends MyextraManagerController {
                    /**
                     * Defines the name or path to the default controller to load.
                     * @return string
                     */
                    public static function getDefaultController() { return 'home'; }
                }
                
                


                And the home.class.php is:
                <?php
                /**
                 * The name of the controller is based on the action (home) and the
                 * namespace. This home controller is loaded by default because of
                 * our IndexManagerController.
                 */
                class MyextraHomeManagerController extends MyextraManagerController {
                    /**
                     * Any specific processing we want to do here. Return a string of html.
                     * @param array $scriptProperties
                     */
                    public function process(array $scriptProperties = array()) {
                        return '<h2 class="modx-page-header">It\'s alive!</h2><p>This is your first custom manager page. You are awesome!</p>';
                    }
                    /**
                     * The pagetitle to put in the <title> attribute.
                     * @return null|string
                     */
                    public function getPageTitle() {
                        return 'My first CMP!';
                    }
                    /**
                     * Register needed assets. Using this method, it will automagically
                     * combine and compress them if that is enabled in system settings.
                     */
                    public function loadCustomCssJs() {
                        $this->addCss('url/to/some/css_file.css');
                        $this->addJavascript('url/to/some/javascript.js');
                        $this->addLastJavascript('url/to/some/javascript_load_last.js');
                        $this->addHtml('<script type="text/javascript">
                        Ext.onReady(function() {
                            // We could run some javascript here
                        });
                        </script>');
                    }
                }
                
                  • 3749
                  • 24,544 Posts
                  I don't know why that wouldn't work. Mark Hamstra could probably tell us. wink
                    Did I help you? Buy me a beer
                    Get my Book: MODX:The Official Guide
                    MODX info for everyone: http://bobsguides.com/modx.html
                    My MODX Extras
                    Bob's Guides is now hosted at A2 MODX Hosting
                    • 36926
                    • 701 Posts
                    Quote from: BobRay at Oct 28, 2014, 06:43 PM
                    I don't know why that wouldn't work. Mark Hamstra could probably tell us. wink
                    Yeah, i'll see if I can pick his brains on this. If all else fails i'll add in manual actions into the modx_actions table as I guess that table will be there for a while still.
                    • When using the new 2.3-style of defining controllers, the index controller is basically made irrelevant. But because your home controller still expects it, you get the fatal error about the IndexManagerController being undefined.

                      Two simple solutions:

                      1) Throw in a require_once before defining your home controller that loads the index.class.php. Quick 'n easy for when you still want the benefits of the central controller that loads assets globally across your controllers.
                      2) Change your home controller to extend modExtraManagerController directly. Works fine for single controller CMPs.

                      If you need to support both 2.2 and 2.3, I find the 2.2 method the easiest for now wink
                        Mark Hamstra • Developer spending his days working on Premium Extras and a MODX Site Dashboard with the ability to remotely upgrade MODX and extras to make the MODX world a little better.

                        Tweet me @mark_hamstra, check my infrequent blog at markhamstra.com, my slightly more frequent ramblings at MODX.today or see code at Github.