I'm trying to update the view model template to a template in a custom structure.
First, I merged the following view_manager config
into the service manager config
with this code:
$config = ArrayUtils::merge($config,$selConf);
$this->serviceManager->setAllowOverride(true);
$this->serviceManager->setService('Config',$config);
$this->serviceManager->setAllowOverride(false);
This is what was merged, with the request being publicweb
as the module, index
as the controller, and index
as the action:
array (size=1)
'view_manager' =>
array (size=2)
'template_map' =>
array (size=1)
'publicweb/index/index' => string '/srv/app/client/design/gopher/publicweb/index/index/template.phtml' (length=95)
'template_path_stack' =>
array (size=1)
0 => string '/srv/app/client/design/gopher' (length=58)
Finally, I executed this code:
$view = $e->getViewModel();
$view->setTemplate('publicweb/index/index');
And the results are not correct.
I also tried :
$view = $e->getViewModel();
$view->setTemplate('publicweb/index/index/template');
And the results are not correct, throwing exception Unable to render template
I pushed the template path stack /srv/app/client/design/gopher
onto the beginning of the template_stack_path array
so it can find that first and its still not working correctly.
Not sure whats going on. Also to note, this is being executed as an event with:
$events->getSharedManager()->attach('Zend\Mvc\Controller\AbstractController',
MvcEvent::EVENT_DISPATCH,[$this,'assignTemplates'],500);
from the Application Module
It should be noted im also adding JS and CSS Files from the view helper within the renderer within the viewhelperpluginmanager from this event:
$events->getSharedManager()->attach('Zend\Mvc\Controller\AbstractController',
MvcEvent::EVENT_DISPATCH,[$this,'hydrateJsAssets'],500);
And Also id need to make sure i can also use a custom layout from that directory.
UPDATE
I was able to get it working by:
public function onMergeConfig(ModuleEvent $event){
parent::onMergeConfig($event);
$configListener = $event->getConfigListener();
$sm = $event->getParam('ServiceManager');
$config = $configListener->getMergedConfig(false);
$selConf = [
'view_manager' => [
'template_map'=>[
'publicweb/index/index' => '/srv/app/client/design/gopher/publicweb/index/index/template.phtml',
]
]
];
$config = ArrayUtils::merge($config,$selConf);
$configListener->setMergedConfig($config);
$event->setConfigListener($configListener);
$sm->setAllowOverride(true);
$sm->setService('Config',$config);
$sm->setAllowOverride(false);
}
Via
public function init(ModuleManager $moduleManager) {
$events = $moduleManager->getEventManager();
$events->attach(ModuleEvent::EVENT_MERGE_CONFIG,[$this,'onMergeConfig']);
}
But the issue is this is hardcoded and i dont have access to the request so i cannot get the module,controller,action
Your updated solution is not needed, you can provide configuration from the module using config provider feature, it will be picked up by module manager and merged on merge config event:
namespace Foo;
use Zend\Mvc\Controller\AbstractActionController;
use Zend\Mvc\MvcEvent;
class Module
{
public function getConfig()
{
return [
'view_manager' => [
'template_map' => [
// change to application root relative paths
'publicweb/index/index' => '/srv/app/client/design/gopher/publicweb/index/index/template.phtml',
],
],
];
}
/**
* Register layout listener
*/
public function onBootstrap(MvcEvent $e)
{
$e->getApplication()
->getEventManager()
->getSharedManager()
->attach(AbstractActionController::class, 'dispatch', function($e) {
$controller = $e->getTarget();
$controllerClass = get_class($controller);
$config = $e->getApplication()
->getServiceManager()
->get('config');
// do your logic here, you have controller class and config
if ($logic) {
$controller->layout($layout);
}
}, 100);
}
}
Nice article about changing layouts, applies to zf3 as well https://www.masterzendframework.com/views/change-layout-controllers-actions-zend-framework-2/