I'm trying to pass an object to the partial() view helper. While working with normal variables workes fine, I'm not able to pass object to this function.
For example, this workes fine when using $this->test in partial:
$this->partial("module/folder/partial.phtml", array(
"test" => "foo",
));
But doing the same with an object will result in nothing in partial:
$this->partial("module/folder/partial.phtml", array(
"test" => $this,
));
I've even tried using setObjectKey, what didn't woked too:
$this->partial()->setObjectKey("test");
$this->partial("module/folder/partial.phtml", $this);
Is there a way to pass an object to an single partial in ZF2?
I want to do this, because my view actually contains many informations the partial needs. I could add them all line-by-line to the partial, but that would just be overhead ...
When you pass the parent Zend\View\Renderer\PhpRenderer to your partial it will overwrite/replaces the $test variable with the Zend\View\Renderer\PhpRenderer of your partial, like it is re-using the class. So resulting in a object that is empty as your partial PhpRenderer has no other variables included.
If you want the variables from the parent PhpRender use the following:
$this->partial('folder/partial', ['vars' => $this->vars()->getArrayCopy()]);
// Or so, so you don't need to store the originals within the vars key
$this->partial('folder/partial', $this->vars()->getArrayCopy());
Now within your partial.phtml:
$this->vars['foo']
To confirm this, let your controller return some variable ['foo' => 'bar'] or setup a ViewModel with some test variables. Now setup your partial:
$this->partial('folder/partial.phtml', ['test' => 'abc' 'render' => $this].
And when you debug or var_dump() your PhpRenders variable you'll see that $render containts the variable $test with a value of abc and not the key 'foo' with 'bar' as its value. So it looks like the PhpRenderer is being reused so passing the parent PhpRenderer is not possible.
Related
I have an object that stores another subObject in it's data attribute. The subObject in the data attribute can be called vie a magic method like this:
$object->subObject. The subObject also has a data attribute in which it's value is stored. Currently when I do $object->subObject it automatically returns the value stored in the data attribute of the subObject. So basically the whole structure looks somewhat like this:
object [
data => subObject [
data => 'value'
]
]
$object->subObject //returns 'value'
I hope that this is understandable so far. Now I want to have the ability to execute someFunc() on the subObject: $object->subObject->someFunc(). That is generally not a problem. But I also want that, if I don't call a method on the subObject at all, the value of it's data attribute is returned ('value'). Is it possible to figure out within an object/a class if a method is called on it or not and act accordingly?
This is not possible. When you access a value, you get the same result regardless of what is going to be done with that value. It can't be different depending on whether you're going to call another method on it.
Remember that
$object->subObject->someFunc();
is essentially equivalent to
$temp = $object->subObject;
$temp->someFunc();
If the $object->subObject returned 'value', the first line would set $temp = 'value', and then $temp->someFunc() wouldn't work.
I have this function that receives a "user" model by parameter , I want to collect the properties of that object, for this I do it this way, the code works for me but the editor "phpstorm" complained to me with this error and it was to know what would be the best way to do this.
Thank you
public function sendEmail(User $user)
{
$params = [
'name' => "{$user->completeName}",
'language' => "{$user->locale}",
'user_id' => "{$user->id}"
];
}
Field accessed via magic method less... (Ctrl+F1)
Inspection info: Referenced field is not found in subject class. Note: Check is not performed on objects of type "stdClass" or derived.
Thanxs,
maybe this is simpler
$params = $user->toArray();
or
$params = $user->toJson();
That's because in Laravel your model does not actually have the properties defined.
In PHP there is the concept of magic methods though ( http://php.net/manual/en/language.oop5.overloading.php#object.get ), where the __get() method allows you to basically intercept the access to an otherwise inaccessible (or non-existing) property.
This is what happens behind the scenes in Laravel. All your property accesses are "intercepted" and Laravel looks if your database contains a column which is named like the property you are trying to access (very simplified speaking).
In a Laravel context you can savely ignore this warning.
Suppose I have a blade template:
// resources/views/fragments/foo.blade.php
<p>{{ $foo }}</p>
(This is obviously a very stripped-down version of my question. I can't see why I'd ever need to test a blade template that simple.) In my controller, I would normally populate that template like this:
// app/Http/Controllers/FooController.php
$parameters = ['foo' => ''];
return view('fragments.foo', $parameters);
The problem is I'd like to write a phpunit test to ensure that template renders successfully when I pass it a specific value for $foo, but I can't figure out how to send data to the view when running the unit test. I tried this:
// tests/TestFooController.php
$this->withSession(['foo' => 'bar'])->visit('/foo')->assertViewHas('foo', 'bar');
but that test failed. How can I pass my own data to the view from within my test?
Finally googled around enough to get a workaround:
// tests/TestFooController.php
$parameters = ['foo' => 'bar'];
view()->composer('fragments.foo', function ($view) use ($parameters) {
$view->with($parameters);
});
$this->visit('/foo')
->assertViewHasAll([
'foo' => 'bar',
]);
The cool thing (depending on how much independence you like when testing) is that if my FooController passes other variables, but I only override one of them in the test's view composer, the other non-overridden values will still be there.
I am using Twig a few days, and it's very nice, but now I am in a situation where I need to render a template without passing any array to the render() method.
I am using:
echo $template->render();
but Twig raises an exception because I NEED to pass some array to the render. So I tried:
echo $template->render(array(''=>''));
and it works, but it's so ugly.
Any tips about this? Thanks!
Instead of passing an array that contains an empty string element, you should also be able to pass the template an empty array:
echo $template->render(array());
Apart from that, you are probably using Twig this way:
$template = $twig->loadTemplate('index.html.twig');
echo $template->render(array('the' => 'variables', 'go' => 'here'));
The Twig documentation suggests an easier way to do the same:
echo $twig->render('index.html.twig', array('the' => 'variables', 'go' => 'here'));
The additional benefit is that the render method of the Twig_Environment class allows you to omit the second argument (it defaults to an empty array), so now you can simply do this:
echo $twig->render('index.twig.html');
I have in my view a partial containing a partialLoop.
But when I run the page I have the following error message:
Call to a member function countComments() on a non-object in ...'_loop.phtml'
This is how I call my partial from within my view:
echo $this->partial('_post.phtml',$this->post);
where $this->post is a DB retrieved row
This is my partial's content:
MY simplified Partial!
echo $post->countComments();//the count number is correctly output..
echo $this->partialLoop('_loop.phtml',$this->object);
This is my partialLoop's content:
echo $this->object->countComments();//no output!
In the bootstrap I have set:
$view->partial()->setObjectKey('object');
$view->partialLoop()->setObjectKey('object');
Is this the right way to call partialLoops from within partials??
P.s. I var_dumped $this->object inside my partial and it is a PostRow OBJECT.I var dumped $this->object into _loop.phtml and I have 5 NULLS (standing for id,title,text,author,datetime fields of my post)
thanks
Luca
I think that the reason is that when you pass $this->post into partial view helper like this:
$this->partial('_post.phtml',$this->post);
partial view helper will execute its toArray() method. Hence, your $this->object is an array and you are passing an array to your partialLoop. So, in your partialLoop you are trying to execute countComments() on an array representing your row post object, rather than actual row object.
To avoid this, I would recommend passing variables to partial and partialLoop view helpers using array notation, e.g:
$this->partial('_post.phtml',array('post' => $this->post));
Hope this helps.
This error is caused by the default behaviour of the partial and partialLoop view helpers as Marcin said above.
Although it is confusing the manual does explain this here
Object implementing toArray() method. If an object is passed an has a
toArray() method, the results of toArray() will be assigned to the
view object as view variables.
The solution is to explicitly tell the partial to pass the object. As the manual explains:
// Tell partial to pass objects as 'model' variable
$view->partial()->setObjectKey('model');
// Tell partial to pass objects from partialLoop as 'model' variable
// in final partial view script:
$view->partialLoop()->setObjectKey('model');
This technique is particularly useful when passing
Zend_Db_Table_Rowsets to partialLoop(), as you then have full access
to your row objects within the view scripts, allowing you to call
methods on them (such as retrieving values from parent or dependent
rows).