Page code:
{% partial 'content/main' %}
Partial:
[services]
{% component 'services' %}
Component:
public function prepareVars()
{
$this->page['servicesList'] = $this->getProperty(); // function returns 123
}
Component template:
{{ servicesList }} //does not display anything =(
Why is not the variable being passed?
Hmm seems something odd, not sure about your onRun method in component
prepareVars will not call automatically we need to call it manually.
did you add prepareVars inside onRun as when page life-cycle called , onRun is called automatically so we need to add prepareVars there as well, so its code get executed.
public function onRun()
{
$this->prepareVars();
}
public function prepareVars()
{
$this->page['servicesList'] = $this->getProperty(); // function returns 123
}
if you are already doing this then please notify it in comment so we can look further.
Related
I have a PHP code to add a new class for my Twig template in my common controller in: "opencart\htdocs\catalog\controller\common\cart.php"
The code should check if the Device is Mobile or not.
function onStart()
{
// Anonymous Class only working on PHP7
$this['code'] = new class {
public function MobileDetect() {
return preg_match("/(android|avantgo|blackberry|bolt|boost|cricket|docomo
|fone|hiptop|mini|mobi|palm|phone|pie|tablet|up\.browser|up\.link|webos|wos)/i"
, $_SERVER["HTTP_USER_AGENT"]);
}
};
}
But now I don´t know how to address that function correctly from my twig side at:
opencart\htdocs\catalog\view\theme\default\template\common\cart.twig
I tried something like this, but it didn´t seem to work:
{% if code.MobileDetect() is defined %}
If a device is mobile I want to use a completely different HTML construct.
What you need to do is create your own Twig function:
https://twig.symfony.com/doc/3.x/advanced.html#functions
So using their examples you should be able to do something like
$function = new \Twig\TwigFunction('MobileDetect', function () {
return preg_match("/(android|avantgo|blackberry|bolt|boost|cricket|docomo
|fone|hiptop|mini|mobi|palm|phone|pie|tablet|up\.browser|up\.link|webos|wos)/i"
, $_SERVER["HTTP_USER_AGENT"]);
});
$twig->addFunction($filter);
Then call it like
{% if MobileDetect() %}
I'm trying to generate EasyAdmin3 url inside my template with some params, but for some reason they are not present in a controller.
Twig template:
xxx
yyy
Error with missing EA context:
zzz
Controller:
/**
* #Route("/admin/something/{id}", name="rounte_name")
*/
public function xyz($id = null, Request $request, AdminContext $context)
{
dd($_GET['id'], $request->request->all(), $context->getRequest()->request->all());
...
}
The $_GET['id'] works, but request and context are empty [].
Any idea how to generate route by name with params?
Thanks
I don't think you need the ea_url() helper function if you are just generating regular named routes in twig. You should be able to use the path() twig extension provided by Symfony.
{{ path(route_name, route_parameters = [], relative = false) }}
If you are trying to create a link to an EasyAdmin controller action, then you can use the ea_url() helper, but you have to specify the controller and action as well. Try something like:
{% set url = ea_url()
.setController('App\\Controller\\Admin\\FoobarCrudController')
.setAction('customFooAction')
.setEntityId(entity.instance.id)
.set('myParam', 'baz') %}
Custom Foobar Action
Then in your controller, everything should be available as per usual via the $context variable...
public function customFooAction(AdminContext $context)
{
$entity = $context->getEntity()->getInstance();
$myParam = $context->getRequest()->get('myParam');
}
This works for me, I hope it helps. 🙂
i would put a controller for my navbar and i would use a query to get a variable from my database..
I don't have a controller and i create it in this way:
<?php
namespace Dt\EcBundle\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
use Symfony\Component\HttpFoundation\Request;
class NavbarController extends Controller {
public function navbarAction(Request $request) {
$prova = "ciao";
return $this->render('DtEcBundle:Header:navbar.html.twig',array(
"prova" => $prova,
));
}
}
Now i put my render controller in the body of : "{# app/Resources/views/base.html.twig #}"
{{ render(controller('DtEcBundle:Navbar:navbar', { 'prova': prova })) }}
I follow this but i don t understand the error: "http://symfony.com/doc/current/book/templating.html#embedding-controllers"
I Get this error Variable "prova" does not exist in DtEcBundle:Header:navbar.html.twig at line 5 but if i write the code in navbar.html.twig give me equals error..
If i remove the variable and i write only
{{ render(controller('DtEcBundle:Navbar:navbar')) }}
Give me a server error number 500 o.o..
How can i do for use my controller only in navbar.html.twig??
navbarAction doesn't take prova variable as a parameter, so why are you passing it there in a base template?
I think that action should fetch these data from db.
In that case, using:
{{ render(controller('DtEcBundle:Navbar:navbar')) }}
seems to be ok, and error is somewhere else.
If you get a 500, check logs to tell us what's exactly wrong.
And format your code, it's barely readable.
The error is the code:
{{ render(controller('DtEcBundle:Navbar:navbar', { 'prova': prova })) }}
the prova variable doesn't exists in twig, the controller is fine.
I if you want put the var from twig to controller:
/**
* #Route("/prova/{prova}", name="prova")
*/
public function navbarAction(Request $request,$prova) {
return $this->render('DtEcBundle:Header:navbar.html.twig',array(
"prova" => $prova,
));
}
and twig:
{% set prova = 'foo' %}
{{ render(controller('DtEcBundle:Navbar:navbar', { 'prova': prova })) }}
I'm using OctoberCms and trying to return a page content from an ajax request. For example, when clicking some internal link, i want to get from ajax the page object like the twig {% page %}.
public function onInternalLink(){
$href = post('href');
return [
'title'=>'', //here i want {{ page.title }}
'content' => '', //and here {% page %} like this variable in layout.
];
}
}
my js code is
$.request('onInternalLink', {
data: {href: u}, // var u is the requested url to return
success: function() {
console.log('Almost october');
}
})
}
I tried to create new CmsObject and try to use parseMarkup() method, and try pageCycle() with no success.
I didn't find a way to get the {% page %} object from the php script, is there way to do something like this?
in your PHP, you can use $this->page to access the current page. So your php would become:
public function onInternalLink() {
$href = post('href');
return [
'title'=> $this->page->title,
'content' => $this->getContentsFromFile($this->page->baseFileName),
];
}
All you would need after this would be to write the logic to fetch html content from the baseFileName of the page (I have wrapped this as $this->getContentsFromFile() in the example above).
There are more variables provided by $this-> page - Read about them here - https://octobercms.com/docs/cms/pages#page-variables
I fully edited this post after doing research:
I'd like to realize a sidebar in the admin section which is integrated in every page, f.e. http://example.com/admin/index/:
class MyController extends Controller {
protected $modules = array();
public function __construct(){
$this->modules[] = "ModuleController:mainAction";
$this->modules[] = "OtherModuleController:mainAction";
}
public function indexAction(Request $request){
// do stuff here
return $this->render("MyBundle:My:index.html.twig",$data);
}
}
In the view should happen something like:
{% block modules %}
{% for module in modules %}
{% render module %}
{% endfor %}
{% endblock %}
So far so good, but these modules can contain forms which send post requests. I'd like to stay on the same page (http://example.com/admin/index/), so the action attribute of the form stays empty. The problem is: The post request will never be recognized by the Modules. So one idea was to hide a field in the according form that contains the name of the route, transform it to the according uri and send a sub request (in MyController):
public function indexAction(Request $request){
if($request->request->has('hidden_module_route')){
// collect all parameters via $request->request->keys()
$uri = $router->generate($request->request->get('hidden_module_route'), $parameters);
// 1: resolve the uri to the according controller and replace the target in the $this->modules array
// or 2: (after step 1)
$req = $request->create($uri, 'POST');
$subresponse = $this->get('kernel')->handle($req,HttpKernelInterface::SUB_REQUEST);
// inject the response into the modules and handle it in the view
}
[...]
}
That would work for me, but I'm not happy to have these responsibilities in the controller and it feels like there should be a better solution (one Idea is to register a kernel.controller listener that handles sub requests and injects the paths to the controller (which perhaps is marked via interface...)).
What do you think?
You could try to send the main request to your modules, so that they can bind the form with it.
{% block modules %}
{% for module in modules %}
{% render module with {'mainRequest': app.request} %}
{% endfor %}
{% endblock %}
And the module:
public function moduleAction(Request $request, Request $mainRequest)
{
$form = ...;
if ($mainRequest->isMethod('POST')) {
$form->bindRequest($mainRequest);
if ($form->isValid()) {
// You can have a beer, that worked
}
}
}