why does the wxPanel constructor have a default WindowID but the wxBookCtrl constructor doesn't? - wxwidgets

Do you know why the wxPanel constructor have a default WindowID but the wxBookCtrl default constructor requires an explicit WindowID? I mean it's not consistent the way you create a control object in wxWidgets. For example
wxPanel* panel = new wxPanel(parent)
but
wxBookCtrl* book = new wxBookCtrl(parent, wxID_ANY)
Are there any advantages to or requirents of doing this?
Thank you.

It is still somewhat consistent in the sense that writing new wxPanel(parent, wxID_ANY) works too, but wxPanel is an exception in allowing to omit wxID_ANY entirely. This is due to the fact that you basically never want to bind to the events of the panel by its ID, so you never care about its value, while it's more useful for the other controls, including wxBookCtrl.

Related

How to access a component bound to a property in QML

It's come up several times that I have wanted to access a property of a component which is bound to another property. I've spent days trying to figure out how to do this and failed. Below is a simple example of what I'm trying to do.
TabView {
Component.onCompleted: console.log(style.frameOverlap)
// OR tvStyle.frameOverlap
style: TabViewStyle {
id: tvStyle
frameOverlap: 5
}
}
Nothing like this works. I'm completely baffled about how to access these members either statically or as an instance. Can someone please explain to me whether something like this is possible?
Thanks.
The short answer is that you need to write:
Component.onCompleted: console.log(__styleItem.frameOverlap)
The longer answer is that the 'style' property is a Component. Component is something that remembers a tree of declarations, and can create objects as needed. However, it does not expose that remembered declaration, so when you try to access the frameOverlap property, it's not there.
In theory, you can call style.createObject to create an object, and examine its properties, but that would create another unnecessary instance, so you can look at TabView.qml, notice that it creates an instance already using Loader, and stores that in a property called __styleItem, and so use the code I gave above.
Of course, accessing internal properties is not a particularly good idea, but might be OK in practice. Ideally, one should be able to instantiate TabViewStyle and bind the instance to the style property, with TabView figuring out whether it's Component or object, but I'm not sure it's possible.

Is it possible to HIDE Javascript Object's prototype! What's the MYSTERY behind this?

I'm using openui5. There is a constructor Function for UI control Button,unable to see the prototype properties of the Button but the same thing when executed in browser console, shows up!
sap.m.Button.prototype.Move = function(){
console.log('Move');
}
var oButton = new sap.m.Button({text:"Hello"});
oButton.Move(); // throws undefined function!
The same code when executed browser in console, it works!
jsbin --> http://jsbin.com/tepum/1/edit
After running the code I find that creating the first instance of sap.m.Button causes script to change the prototype of sap.m.Button. It's valid in JavaScript but not very smart if you ask me.
A first creation causes a synchronous request (no no as well) to fetch library-parameters.json.
If you run the code the second time it will have prototype.move because creating an instance of Button will not change the Button.prototype.
The capital M in Move would suggest a constructor function so I would advice changing it to lower case.
Since fetching the parameters is synchronous you can create the first instance and then set the prototype:
console.log("First Button creation changes Button.prototype");
var oButton = new sap.m.Button({text:"Hello"});
sap.m.Button.prototype.move = function(){
console.log('Move');
}
oButton.placeAt('content');
oButton.move(); // logs Move
My guess is that this is done to lazy load controls, if a Button is never created then the json config files are never loaded for these unused controls. It has a couple of drawbacks though.
You have to create an instance first before you can set the prototype.
The config files are synchronously loaded so when creating first instance of many controls with a slow connection would cause the app to be unresponsive.
A better way would be for a factory function to return a promise so you create the control the same way every time and the config files can be fetched asynchronously.
[update]
Looking at the config it seems to be config for the whole gui library so I can't see any reason why this is loaded only after creating a first instance. A library that changes it's object definitions when creating instances is not very easy to extend because it's unpredictable. If it only changes prototype on first creation then it should be fine but it looks like the makers of the library didn't want people to extend it or they would not make the object definition unpredictable. If there is an api documentation available then maybe try to check that.
[update]
It seems the "correct" way to extend controls is to use extend.
#HMR is right the correct way to extend a control is by using the extend function provided by UI5 managed objects, see http://jsbin.com/linob/1/edit
in the example below when debugging as mentoned by others you will notice that the control is lazy loaded when required, any changes you make prior are lost when loaded
jQuery.sap.declare("my.Button");
jQuery.sap.require("sap.m.Button");
sap.m.Button.extend("my.Button", {
renderer: {}
});
my.Button.prototype.Move = function() {
console.log('Move');
};
var oButton = new my.Button({
text: "Hello"
});
oButton.placeAt('content');
oButton.Move();
It's not hiding the prototype per se. If a constructor function exits normally then you get that function's prototype. But, if a constructor function actually returns some other object then you get that other object's prototype, so it's not valid to assume that just because you added to the Button prototype that when you call new Button() that you will see your method on whatever you get back. I'm sure if you de-obfuscate that code you'll find that the constructor you are calling has a "return new SomeOtherInstanceOfButton()" or similar at the end of it.
Edit: Ok it's a bit difficult to see what's really going on in that sap code but, it looks like they have code that overwrites the prototypes of controls to add features to them, such as: sap.ui.core.EnabledPropagator, and those things aren't run until you actually instantiate a button. So if you change your code to instantiate the button on the page, then add to it's prototype, then construct and call the method, it works fine. Like so:
http://jsbin.com/benajuko/2/edit
So I guess my answer is, when you run it from console it's finished mucking around with that prototype, whereas in your test you were adding to the prototype, then constructing the button for the first time (which changes the prototype again) then trying to call your old one, which is no longer there.

How to restore an object in Silverlight 5

I have created an application by using Silverlight 5. There are many two-way databind in it. I want to retore a change in UI by restoring the object behind. For example:
I have an object behind which contains properties double Left, Right, I inherited it from INotifyPropertyChanged. In UI, I created tow button (ButtonLeft and ButtonRight) and their parent a Canvas Control, ButtonLeft bind Left property in two-way mode and ButtonRight bind Right property in two-way mode. It works very well, if I drag ButtonLeft, then the Left property will be updated with the new Left Value, same for ButtonRight.
Is there any way to restore the old value after the change of UI. Actually, the relation of class in my application is very complicated, I have already knew that retore the value of property in object will restore the UI, so is there any way (more general and loose-coupling) to restore all the objects that need to be restored.
I have thought of creating an interface IRestorable (inside Store(), Restore()) for objects that need to save and restore state. An attribute Restorable for property which need to be restored. For me, the use of AOP could be a good idea, each time when an instance of IRestorable is created, AOP will call a method for saving the current state (properties which is marked an [Restorable]) of object. I don't know if I was on the right way. If not, any advice will be appreciated.
Use of memeno design pattern.
http://www.codeproject.com/Articles/18025/Generic-Memento-Pattern-for-Undo-Redo-in-C

Extjs configoptions vs properties

A Java class has properties and methods for manipulating those properties. An ExtJS class has properties, methods and configOptions.
Conceptually, what is the difference between configOptions and properties? Why we need both?
As per my understanding…
configs - are passed in the constructor, which defines behavior of the class, configs should not be changed at run-time because it will not have any effect, suppose you need to specify a title for the panel then you can add a config e.g. { title : 'some title' } that will be used by panel to set title of the panel at render time, but after that, even if you try to change title, you can't alter the property by simply changing that config option.
properties - are used to store information which is useful for that class, this is normally not passed through constructor but should have getter and setter methods, you can change property at run-time (if setter method is defined) and class object should detect this change, there can be read only properties also which are modified by class object only we shouldn't change it all.
More Info
Sencha: Properties vs Configs, in the Ext 4 Documentation
My answer to this question is a little simplistic and idealistic. I'm afraid trying to give a full answer that covers all the subtleties is more likely to add to the confusion rather than clarifying the situation.
Config options are used to configure an object when it is created. Trying to set them as properties on the object after it has been instantiated will often have no effect.
Ext.create('Ext.panel.Panel', {
// config options go here
});
An object will have lots of properties but only the ones listed in the Properties section should be considered public properties. While there's nothing to stop you accessing the private properties you should only do it as a last resort, try to use the documented methods to manipulate them instead where possible.
// rendered is a public property used to indicate whether the panel has been rendered
if (panel.rendered) {
// could just do panel.el but that isn't a public property, so use getEl instead
var el = panel.getEl();
...
}
One reason why the lines get blurred is that objects generally copy their configs onto themselves like this:
Ext.apply(this, config);
This results in all the config options becoming private properties, at least initially. Internally classes can then manipulate those properties as appropriate but externally accessing those properties is a breach of encapsulation and should be avoided.

MVVM combobox binding issue

I have a project with a number of comboboxes, all binding correctly. Since installing SL5 I started experiencing all sorts of binding issues as well as the debugger being crippled. The problem is that when you switch from SL4 to SL5 and then back to SL4, not all the references are reset. Long story sort, I had to reinstall vs2010 to fix those issues. Now I am testing the dev environment and although I can get a textbox to bind from the VM, I cannot get a combobox to bind.
What I would like to know is what is the absolute minimum requirements for a combobox to bind. My ViewModel's property SET is getting its data.I have the comboboxes ItemSource set and the DisplayMemberPath set.I have tried using the ItemTemplate syntax but nothing works. The RaisePropertyChanged is being fired. Could this be a UI threading issue? The only difference between this combobox and the others is that there is a call to the database that collects values that are then used in a second call to the database. Those results are then passed to the property in the VM which raises the RaisePropertychanged event, but the binding doesnt render. I have mocked an entity in the class constructor and the binding works, but when I load the entities from the database it doesnt work.
I found the issue. This might be helpful to others. I was instantiating a ViewModels ObservableCollecion in the Completed event of the method and then looping through the collection from the database and addng it to the collection. Binding was not happening. I moved the instantiation of the ObservableCollection to the ViewModels constructor instead and the Binding started working. Still a bit puzzled as to why the newing up of the ObservableCollection has to be in the ViewModels constructor and not in the Completed event of the method fetching the data.