Pass parameters to Presenters (fuelphp) - fuelphp

How does one pass a parameters to a Presenter? Reading the documentation there doesn't seem to be a way.
https://fuelphp.com/docs/general/presenters.html
Controller
$points = Presenter::forge('points', 'viewmy');
$points->set('id', 5);
Presenter class or view (I tried both):
var_dump($id);
var_dump($this->id);
Both var_dumps generate an undeclared variable error
This in the Presenter class also did not work:
$id = $this->get('id');

From the page you linked:
In your code, Views and Presenters are interchangeable. You can return Presenters from your controller actions, you can set a Presenter as a Theme partial, or assign it to a section of your page template. The basic API of the Presenter is compatible with the View. This makes it easy to swap a View for a Presenter in your code without having to do a major code overhaul.
They have the exact same interface as regular View objects.
So as per https://fuelphp.com/docs/general/views.html you can do things like using the set() method or passing the parameters in the forge() method.

I finally got to the bottom of this issue. I was using the setview function in my Presenter to change based on condition. This was meaning that any values that I had set were getting lost.
Passing the view into the 4th parameter of forge and not setting it in the presenter fixed this issue.

Related

Display two partial views in one view page at once

I am creating a web based software using Asp.net MVC 5 with EF framework on Visual Studio 2013.
I have a view page which needs to display two partial views at a given time. The partial views are associated with 2 model classes thus will be be from two Controllers. How to specify which frame the partial view should be displayed?
I'm new to MVC 5 so I am unable to provide a more detailed description. Any suggestion that can get me the result below would be helpful
At least a couple of options:
1 #Html.Action
Just use #Html.Action (twice) to render the partial views using separate controller calls:
e.g.
#Html.Action("action1", "Controller", new { id = Model.idOfPart1 }
#Html.Action("action2", "Controller", new { id = Model.idOfPart2 }
Where the id's are the key/lookup values you would normally pass to a control if they were full views.
Action() causes a full call to the action of the controller specified and renders the result in-place in the parent view.
2 #Html.Render
If instead you wish to pass a combined ViewModel to the parent view, and send parts of the model to each partial view, you can use #Html.Partial:
#Html.Render("ParialView1", Model.model1);
#Html.Render("PartialView2", Model.model2 }
This version passes specific models requesting each partial view render with it.
Render() is probably the most common model for passing data to partial views, but it really depends on how you want to pass the data around and how your controllers are structured. I always use Action when I think a partial view should be able to function as a view as well as a partial view.

How to implement a site wide class and functions that can be called from anywhere in a Zend Framework Application?

I know there are view controllers and action controllers. I think that view helpers can be used from views and action helpers used from actions in controllers.
I need a class that at bootstrap or wherever, it initializes a number of configuration options, arrays for things like convert month numbers to their names and role numbers to their names.
How can this be achieved?
Put them in a model and use it anywhere you like by instantiating it and calling its helper methods. All model files are auto loaded whenever you call them.
Have a model Constants.php:
<?php
class Constants {
public static function convertMonth($month) {
doLogic();
return $something;
}
}
?>
In your controller or view:
Constants::convertMonth(12);
You could build a Resource Plugin and then add it to yout bootstrap class.
The Constants class or Resource approaches both work nicely. However, I recently had to undo/upgrade a Constants class based solution to meet new requirements, so you might want to consider your future plans before going down those paths.
Specifically, if you ever intend to support multiple languages, or even different words for the constants in different contexts, check out Zend_Translate API docs, Zend_Translate example, or this blog post.

Using layouts from others classes in vaadin

Is there any idea wich allows me using layouts declared in MyApplication.java from other classes and functions.
I tried put them in parameters it works but it becomes very complicated
For example xhen callin a function named Y in function X I have to pass all layouts on parameters like this:
X(layout1,layout2,layout3,layout4)
{
Y(a,b,c,layout1,layout2,layout3,layout4)
}
I tried to use a class named uiHelper but it didn't works
You can take a look at Blackboard addon for vaadin.
https://vaadin.com/addon/blackboard
From that page:
Sometimes, having a deep component hierarchy poses a problem, when you need to inform a component high up in the tree that something happened deep down below. You normally have one of two choices - either pass the listener all the way down the hierarchy, leading to more coupled code, or let each component in between be a listener/notifier, passing the event all the way back up. With the Blackboard, you can register any listener to listen for any event, and when that event is fired, all the listeners for that event are triggered. This keeps your components clean and rid of unnecessary boilerplate code.
For your example, you can create a LayoutChangeListener and LayoutChangeEvent.
MyApplication can then implements LayoutChangeListener and when a LayoutChangeEvent is fired, you can change your layout without passing it around.

Initiating objects in Zend Framework?

How can I eliminate to write $object = new Application_Model_Database() in every controller?
For example for an article controller, I have to type $articles = new Application_Model_Articles() for every controller. Should I put it under viewer controller, action helpers, or any other way?
Your question almost sounds like an OOP best practices question as opposed to a Zend Framework specific question. Regardless of whether or not I'm using a framework, and regardless of what framework I choose, I base when and where I create new objects on testability how many times I have to write $object = new My_Random_Object();.
Speaking specifically to the Zend Framework: Objects I'm going to use everywhere, or almost everywhere, get created in Bootstrap.php. These objects generally include a database adapter, logger, view object, and any plugins I might use. To access these across the application, I'll create private properties in the appropriate controllers and assign the objects to those properties in the controller's init() method.
class ExampleController extends Zend_Controller_Action
{
public function init()
{
$bootstrap = $this->getInvokeArg('bootstrap');
$this->_db = $bootstrap->getResource('db');
$this->_log = $bootstrap->getResource('log');
// and so on, and so forth
}
}
Ideally, models, services, daos, etc, will all be relatively tightly grouped by controller and by action. In my experience, and this is speaking generally, if I have the same model or service class showing up across all of the controllers in my application, I have an organization problem. That being said, any model that shows up in only one action gets created in that action. If it's across actions in a controller, it gets created in the init() method and assigned to a property. If it shows up across multiple controllers, it gets created in my Bootstrap.php.
(Ideally, everything gets created in the Bootstrap.php, so you can swap out that bootstrap for testing purposes. Sadly, I don't always do that, and I most often use the principles I outlined above.)
Well do you really need it in every controllers? Because that's pretty much by design. You implement models when you need them. Its not that much code really.
Now if its to be used across actions from a controller you could always:
class MyController extends Zend_Controllers{
$protected $_articleModel;
...
and in your constructor or __init() function initialize it so you can use it in every action thru $this->_articleModel
If you REALLY want it everywhere in your application just initialize it in your bootstrap and store it in the registry.
public function __initModels(){
$articles = new Application_Model_Articles()
Zend_Registry::set('articles', $articles );
}
And access it in your controllers like so:
Zend_Registry::get('articles')->fetchAll();
But then your still writing a couple of characters.
Hope this help!
IF you want to use models in the controllers you must call it..anyway some shortcuts are here
1.You can initialize it in the init section of your controller like
public function init(){
$this->object = new Application_Model_Database();
}
So that the this->object is available in all the actions of that particular controller
2.Use Zend_registry as suggested in the above answer
Another possibility is to use a Dependency Injection container, such as the Symfony DI component. It takes care of instantiating your objects, and you get some additional benefits:
Separation of concerns. You have a component devoted to create your object tree.
Easier testability of the objects.
Last, but not least, the performance benefits given by lazy instantiation (objects are created only when you ask for them). Thus, if some object is not used by the particular controller serving your request, it's not instantiated).
It's a bit more laborious than the above solutions, but much more flexible if you need to maintain and extend your application in the future.
Hope that helps,
If you are using this object to just display data in your view and are using your controller to grab the data and assign it to your view, like so:
//someControllerAction
$object = new Application_Model_Articles();
$object->fetchAll();
//assign to view
$this->view->articles = $object;
You might be better off making a view helper similar to:
//Articles.php put in /application/views/helpers
class Zend_View_Helper_Articles extends Zend_View_Helper_Abstract {
public function Articles() {
$articles = new Application_Model_Articles();
$articles->fetchAll();
//return rowset object
return $articles;
Then in your view (phtml) you could do something like:
//someView.phmtl
<?php $articles = $this->Articles(); ?>
<h1><?php echo $this->escape($articles->title); ?></h1>
<p><?php echo $this->escape($articles->body); ?></p>
building a view helper allows you to bypass the controller completely if you just need to display data from the model. This is a very simple example and can be used with partials and partialLoops.
REF:ZF reference Custom View Helper
ZF partial view helper reference

how to keep view "humble" -using SuggestBox with special Oracle and Suggestion

i learned how to implement my own SuggestionOracle("AuSuggestOracle") and own
Suggestions("AuMultiWordSuggestion"). In my case the suggestion object
is constructed with a DTO. On a selection event i need this dto (or
some fields of it) to react appropriate.
I implemented a widget containing 3 suggest boxes with this special
oracle and some logic between them. Now i want to apply MVP pattern -
split this widget in presenter and view.
At the moment the presenters display interface look like that:
public interface Display {
HasSelectionHandlers<Suggestion> getFedLand();
HasSelectionHandlers<Suggestion> getCounty();
HasSelectionHandlers<Suggestion> getCommunity();
AuSuggestOracle getFedLandOracle();
AuSuggestOracle getCountyOracle();
AuSuggestOracle getCommunityOracle();
void clearCounty();
void clearCommunity();
void activateForm();
Widget asWidget();
}
the problem is the implicit knowledge about my model in methods
returning "AuSuggestOracle". so my question is how to get the view/
interface "humble". in my case the displayed suggestion-strings are
ambiguous and i need at least the "id" of a selected item to know what
DTObject is selected.
The way I got around this is by leaving out the getters for the Oracle since once my presenter sets it my view doesn't need any information about it. So, my interface looked like this:
public interface Display {
...
void setSuggestionOracle(SuggestOracle oracle);
HasSelectionHandlers<SuggestOracle.Suggestion> getSelectionListener();
}
The problem I encountered was being able to add the suggestion to the SuggestBox after it was instantiated. To get around this, I initialized with a blank SuggestBox and then removed it from the view, updated in, and inserted it back into position.
After that, you can write your handler (in the presenter) to check if the suggestion is an instance of your custom suggestion and your presenter can handle the selection and push the relevant information back down to your view.
By doing this, all your view knows is that it will be taking generic suggestions for something, and that at some later time it will be updating with information (which will be as a result of the suggestion, but the view is to 'humble' to know that).