Openui5: Change renderer for component during runtime? - sapui5

I'm investigating some novel approaches to extending openui5.
Particularly I'm playing around with the idea of implementing material design with openui5 (through material design lite https://github.com/google/material-design-lite). Normally, you would extend existing components with new ones, but I want to avoid this if possible.
One approach would be to dynamically change the renderer of a component during runtime. I want to change the renderer for a particular instance of a component and not all instances.
I've found that through the MetaData of the control, I can change overwrite the render function
myComponent.getMetadata().getRenderer().render = function(oRm, oControl) {
...
};
myComponent.rerender();
This gives the intended effect. However, using this approach changes the renderer for all instances of the component class.
Is there some way of only changing the renderer for a particular instance?

Well, in the standard controls that come as part of the framework, the *Renderer for each control is a static class - this is why the control instance is passed in to the render() method. This is why re-defining the render method, as you did it, affects all control instances of this type.
Sneaking into metadata.getRenderer() and returning something different for this instance would cause similar issues, as ElementMetadata is also one instance for the entire control class. Cloning the metadata and modifying it for certain instances would be an option, but I think not a nice one.
Maybe a simple solution is the best choice here?
Mark the control instances to be rendered differently with a flag and overwrite the render method to either do the normal thing or do the special handling, depending on this flag.
Something like this:
http://jsbin.com/yabujigitu/edit?html,output

Related

Good practices for menu heavy games (in Unity3D)

I'm working on a game (in Unity3D) which consists of a dozen menus and no real 2d/3d game world. From a programmer's perspective it is just a bunch of buttons, labels and images.
To not have everything inside of one big menu class, I decided to split the code in parts for every menu. The result is that I've got a dozen classes which themselves have all the references to their gameobjects and e.g. the button methods.
My problem is that almost everything in my project is static by now, because these menus do not get instantiated multiple times and I have to access variables and methods from one menu with the script of another menu.
Thus my question is what the best practice would be for this situation. I've got a couple of ideas, how I could do it, but unfortunately I didn't get to learn what to do in such a situation.
So if you straight up want to suggest something, feel free to do so. :)
My ideas:
1) Make a controller which has static instances of all menus. A button-method in class 'A' could then call Controller.B.x. This does work, but I dislike putting "Controller" everywhere so often, because most classes access methods and variables from other classes so often, that it's just ugly.
2) Make these menus all be singletons. Afaik are singletons "ok" for something like this, but aren't they just shifting the static instance to their own class instead of one controller? When I switched from option 1) to this with one class, basically Controller.A.x became A.instance.x, where "instance" is the static instance of the class inside the class.
3) Keeping everything the way it is, having variables and method being static whenever I need to access them statically from another class, otherwise make them private.
The game is probably not a "bunch of buttons, labels and images".
I suggest to forget about the menus for a second, focus on the model of your game, create classes strictly for that. You don't put things like "how much of a currency does the player have" in any menu, it should exist in a Player class or similar (the model).
Once you can manipulate your model from a single test controller class, and simply log the results in debug console, you're ready to do the same with menus.
After that, you can much easily create user interfaces to read /display (creating labels and images on the fly) and write (hook button events into) the model beneath. These UI classes will probably have so much in common after that.
You can use UnityEvent class for communication between UI and model, they are nicely shown in the Inspector (the same events used in UI Events and Event Triggers).
Fore more general info, Google on some design patterns like MVC, MVP, MVVM, or VIPER.
My recommendation is to strongly consider why you have statics. I understand your reasoning that they are singletons but I don't think that is a good enough reason.
I hope you are using the Unity GUI features properly.
I would just write a base "Menu" component. Then you can add references into the sub classes. For example.
You have a "StartMenu" class derived from "Menu" which is derived from "MonoBehavior". In "StartMenu" you write a method "ShowCharacterCreationMenu()". Then add a button component and hook the method up to that button press. StartMenu will have to have a reference to Character menu. This is the classical OOP approach.
I would do this a little differently though. Unity's strength lies in component based design so I would lean towards that. I would probably create a "Transition" component class that listens for a button press. When that button is pressed it goes to the next menu.
Hope that makes some sense.

How to pass a View to my ViewModel so an I*Service can use that View to do something

https://github.com/brianchance/MvvmCross-UserInteraction is a very nice plugin for showing cross platform Alerts!
But for this question, can we assume it can not use a UIAlertView (or some other top level MessageBox type call on other platforms) but needs to show a Message within a given subsection of the screen (i.e. on IPhone you would need to supply a UIView to the plugin which it will use to show the message within).
So, how would you set this up so the ViewModel knows what View to use as its display container?
As a specific example, if I wanted an Error Service, as so -
public interface IErrorPFService
{
void Show();
void Hide();
void SetErrors(List<Error> errors);
}
and I create a platform specific implementation for it.
If I inject this into my ViewModel so it can control Error Show/Hide/Set how do I tell it the UIView (or equivalent) that I want my Errors to show within?
Can I just expose the IErrorPFService field as a public property and do -
MyViewModel.ErrorPFService = new ErrorPFService(View);
in my ViewDidLoad ...
Or is this coupled incorrectly vs Mvvm Practice?
I would expect the ViewModel to subscribe itself to the ErrorService.
When receiving a message it would expose it in a collection(?) and the View would bind to that collection.
This way the View is unknown to the service and the ViewModel has the chance to influence the View contrary to your solution.
It would help if you could give an example for the scenario you are describing.
Sometimes, the way you visually want to display something might not be the best way, so if it's possible for you, you might find a different and simpler way, which spares you from having to find a solution regarding what you are describing.
Generally, I always do the best I can to avoid the idea of having to actually pass a 'view' or an abstraction of it, from the view-model to view. Also, cross-platform wise, things can work very different in terms of UI interaction. You can find yourself in a situation when things are complicated just because UI works differently than what you expected.
But let's try find another perspective:
At any given point, the view knows what data \ feature it's displaying. So when you are calling from the view-model an user interaction action (by a service, property change, event, etc) the view should 'expect' it.
For example, the platform specific user interaction implementation is able to get the currently displayed top-view and interact it in a platform specific manner or based a relationship. In your example, the message-box can be displayed in a specific sub-view of the top level view.
In advanced scenarios, I guess you could try to create a cross-platform approach for this, but you should try to put in balance all the abstraction you want to create just for that. Think about doing this as a plan ... Z. If possible. Again, giving an example might help.

What is a CQ5 overlay component?

I've been asked to create a CQ5 "overlay" component by simply copying the out-of-box component from /libs/foundation/components/flash to /apps/myproject/components/flash. My question is: what happens to the original - is it just ignored?
a CQ5 "overlay" leverages sling rules for resource resolving. if /libs/foundation/components/flash needs an overlay, you "overlay" the corresponding file at location /apps/foundation/components/flash/filename This will CHANGE how the foundation component behaves in all instances. And the existing sidekick component remains, but behaves differently.
If you have a NEW component at /apps/myproject/components/flash, it can inherit from the foundation component via sling:resourceSuperType on the new component. In that case, you have a new component in the sidekick. In your new component, you could use the same values for jcr:title, componentGroup, or you could change them to distinguish your component in the sidekick. If the title, componentGroups are the same, the sidekick can distinguish them with parenthesis around the webapp (foundation) vs (myproject). However, I have seen situations where it is impossible as an author to distinguish them.
It is not ignored. Both components can show up in the authors' sidekick -- one will say flash (foundation), the other flash (myproject). When one of these is used by an author CQ will instantiate appropriately. The usual rules apply for what shows up in the sidekick (group name, selected in design mode, etc.)
Just to clarify: overlay and flash are two different things.
Sample of overlay implementation: http://jquerytools.org/documentation/overlay/index.html
So if you were asked to create an Overlay component, copying a Flash one might not be the best idea.

GWT Editors for readonly and edit mode

GWT's Editor framework is really handy and it can not only be used for editing POJOs but also for read-only display.
However I am not entirely sure what the best practice is for doing inline edits.
Let's assume I have a PersonProxy and I have one Presenter-View pair for displaying and editing the PersonProxy. This Presenter-View should by default display the PersonProxy in read-only mode and if the user presses on a edit button it should allow the user to edit the PersonProxy object.
The solution I came up with was to create two Editors (PersonEditEditor and PersonDisplayEditor) that both added via UiBinder to the View. The PersonEditEditor contains
ValueBoxEditorDecorators and the PersonDisplayEditor contains normal Labels.
Initially I display the PersonDisplayEditor and hide PersonEditEditor.
In the View I create two RequestFactoryEditorDriver for each Editor and make it accessable from the Presenter via the View interface. I also define a setState() method in the View interface.
When the Presenter is displayed for the first time I call PersonDisplayDriver.display() and setState(DISPLAYING).
When the user clicks on the Edit button I call PersonEditDriver.edit() and setState(EDITING) from my Presenter.
setState(EDITING) will hide the PersonDisplayEditor and make the PersonEditEditor visible.
I am not sure if this is the best approach. If not what's the recommended approach for doing inline edits? What's the best way to do unit-testing on the Editors?
If you can afford developing 2 distinct views, then go with it, it gives you the most flexibility.
What we did in our app, where we couldn't afford the cost of developing and maintaining two views, was to bake the two states down into our editors, e.g. a custom component that can be either a label or a text box (in most cases, we simply set the text box to read-only and applied some styling to hide the box borders).
To detect which mode we're in, because we use RequestFactoryEditorDriver (like you do), we have our editors implement HasRequestContext: receiving a null value here means the driver's display() method was used, so we're in read-only mode. An alternative would be to use an EditorVisitor along with some HasReadOnly interface (which BTW is exactly what RequestFactoryEditorDriver does to pass the RequestContext down to HasRequestContext editors).
Yes,Presenter-View pair should be. But Here two ways to achieve this feature if you like to go with:
1) Integrate Edit/View code design in one ui.xml i.e.Edit code in EDitHorizonatlPanel and View code in ViewHorizontalPanel.The panel has different id. By using id, show/hide panel with display method. if getView().setState() ==Displaying then show ViewHorizontalPanel and if getView().setState()==Editing then show EditHorizontalPanel.
2) Instead of using labels, Use textboxes only. set Enable property is false when you need it in view mode otherwise true
You have created two Presenter/view but I think if Edit/View function has similar code so no need to rewrite similar code again and again for view purpose.
If a big project has so many Edit/View function and you will create such type of multiple View/Presenter than your project size become so huge unnecessary.
I think that whatever I have suggest that might be not good approach but a way should be find out which help to avoid code replication.

How do I use an SWT Control to render the content of an SWT/JFace table?

I have a JFace TableViewer with an SWT Table, and I would like to custom render the content of some cells. I would like to use an SWT Control to render the cell content.
I would prefer to have only one instance of the Control doing the rendering, but if I have to instantiate one for each row, that would be acceptable.
Next, the solution MUST be compatible with the ContentProvider/LabelProvider approach (I am using EMF). This means that I cannot use the solution described in Sniplet 126 (http://dev.eclipse.org/viewcvs/index.cgi/org.eclipse.swt.snippets).
Next, I though about using custom drawing. But here the catch is, that I have to send individual drawing operations to the graphics context. I was trying to have the Control render the content for me by calling redraw() or print(GC) upon SWT.PaintItem, but that just lead to uncontrollable flickering.
At this point, my best guess is to use SWT.PaintItem to do the drawing. This will result in duplicate code, as I already have a Control that can render the content the way I'd like it. I'd like to prevent this redundancy.
Any help is appreciated!
Well, after banging my head against a wall several times I made some progress. Specifically, I found this formu entry:
http://www.eclipsezone.com/eclipse/forums/t115489.html
It actually offers two solutions: The first solution actually uses widgets (not recommended due to performance, but I knew that before). I will try this out, and may post here how it goes.
The second solution suggests using StyledCellLabelProvider. I looked into this before, but it isn't powerful enough for my purposes. At least that's what I think right now.