VBNET: Parent Control > Child Control - nested

SUMMARY
One main form which contains a usercontrol(Child), which in turn contains another user control(Child_1) like so: MAIN(FORM) -> Child(USERCONTROL) -> Child_1(USERCONTROL).
On Child there is a DGV control with some rows. Also there are two public readonly properties (IdBase and IdUser) who get their data from Child -> DGV.CurrentRow.
What i need: On Child_1 to be able to access the two properties on Child (IdBase and IdUser).

What i have working but i'm not sure if it's correct:
On each Usercontrol (Child and Child_1):
i have set a variable as fMain
i have a public property SetParent() which sets the Variable fMain as Main which i call when MAIN loads Child;
On usercontrol Child_1
i have set a variable as fChild
i have a public property SetChild() which sets the Variable fChild as Child when Child loads Child_1.
This way i can access both MAIN's and Child's properties and controls

Related

WPFExtendedToolkit PropertyGrid Standard Values

I'm trying to display XmlElement's attributes in Xceed PropertyGrid. For that purpose I defined custom wrapper class. It wraps XmlElement, iterates over XmlAttributes and creates custom PropertyDescriptor for each XmlAttribute. All "virtual" properties' type is String. All works fine.
Now I want to have drop-down list of possible attribute values for every attribute that has restricted set of values. In Xceed's PropertyGrid, there is ItemsSourceAttribute for that. But it has to be applied as follows:
ItemsSourceAttribute(typeof(MyCustomItemsSource))
And here is the problem - I can not provide proper argument for MyCustomItemsSource constructor. What can I do about this?
It seems that there is another possibility - to define a TypeConverter, override GetStandardValues, and supply this converter to "virtual" property. But PropertyGrid just ignores this attribute.
How this simple task can be done with Xceed PropertyGrid?
Solved. I implemented custom editor
public class AttributeValuesEditor: Xceed.Wpf.Toolkit.PropertyGrid.Editors.ComboBoxEditor
{
protected override IEnumerable CreateItemsSource(PropertyItem propertyItem)
{
var property = propertyItem.PropertyDescriptor as XmlAttributePropertyDescriptor;
Debug.Assert(property!=null);
return property.GetCompletionValues();
}
}
Here, the context is passed into method in the form of PropertyItem. Now it is possible to differentiate between different attributes and return appropriate items.

Can't Able to add two FrameLayout Objects in LinearLayout programmatically

while adding two FrameLayout Objects in LinearLayout Object Programmatically, getting the following exception on adding second FrameLayout object to LinearLayout object. Can anyone help.
Java.Lang.IllegalStateException: The specified child already has a parent. You must call removeView() on the child's parent first.
here is the code
ViewGroup.LayoutParams param = new ViewGroup.LayoutParams(
ViewGroup.LayoutParams.WrapContent,
ViewGroup.LayoutParams.WrapContent);
MainView = new LinearLayout(_context);
MainView.LayoutParameters = new ViewGroup.LayoutParams(
ViewGroup.LayoutParams.MatchParent,
ViewGroup.LayoutParams.MatchParent);
MainView.Orientation = Orientation.Vertical;
MainView.SetVerticalGravity(GravityFlags.Center);
MainView.SetHorizontalGravity(GravityFlags.Center);
_currentSwipableItemReflectionFrameLayout = _currentSwipableItemFrameLayout;
_currentSwipableItemReflectionFrameLayout.RotationX = 180;
_currentSwipableItemReflectionFrameLayout.Alpha = 0.3f;
MainView.AddView(_currentSwipableItemFrameLayout,param);
MainView.AddView(_currentSwipableItemReflectionFrameLayout,param);
AddView(MainView);
The exception says it all. One of the Views you are trying to add using AddView already has been added as a child somewhere in the View hierarchy. Hence you must remove it from its parent first before adding it elsewhere.
From the code you have posted it would seem that either or both _currentSwipableItemFrameLayout or _currentSwipableItemReflectionFrameLayout already has a parent.

Master of threads under DigitalMicrograph

I have created two threads in DigitalMicrograph and they are executed as soon as the script is executed.
I want something different.
Let's imagine two buttons for the threads (start and stop thread).
How can I add code to activate the threads only when I push buttons ?
It would be very helpful if you had a code exemple for me.
There are a couple of things to consider:
You can not allocate new objects from within the UIframe object. (To be more precise: From a method invoked by a UI action. You can allocate f.e. in the constructor or with an Init() method at start.) Therefore you allocate them beforehand and then let the UIframe object know about them.
You often want the UIframe object to be aware of the thread object, but also the thread-object to be aware of the UIframe object. (So that the UI can change if something in the thread object wants it to.)
Having objects as member variables of objects is a bit dangerous, because those objects can only be released once the 'keeping' object gets released to. If two objects hold each-other as member variables, you're in a dead-locked situation! For this reason, it is save to use weak referencing: Keep only the objectID numbers as member variables and look objects up on need.
The following code-example should give you a starting point. It consists of 2 classes and a main call. The code is split in this answer, just copy & paste it into a single script file for testing.
First the thread object:
class myThread:Thread
{
number linkedDLG_ID
number externalBreak
myThread( object self )
{
result( self.ScriptObjectGetID() + " created.\n" )
}
~myThread( object self )
{
result( self.ScriptObjectGetID() + " destroyed.\n" )
}
void SetLinkedDialogID( object self, number ID ) { linkedDLG_ID = ID; }
void InterruptAtNextChance( object self ) { externalBreak = 1; }
void RunThread( object self )
{
number maxLoop = 30
object callDLG = GetScriptObjectFromID( linkedDLG_ID )
externalBreak = 0
for( number i=0; i<maxLoop; i++ )
{
sleep( 0.1 )
Result( i + "\n" )
if ( callDLG.ScriptObjectIsValid() )
{
callDLG.DLGSetProgress( "progress", (i+1)/maxLoop )
callDLG.ValidateView()
}
if ( externalBreak )
break;
}
// Cleanup at end of thread
if ( callDLG.ScriptObjectIsValid() )
{
callDLG.DLGSetProgress( "progress", 0 )
callDLG.LookUpElement( "DBevel" ).DLGValue( 0 )
callDLG.ValidateView( )
}
}
}
Any threading class is derived from the class Thread.
The class has two member variables. One will hold the ID of the UI-object, the other is a simple Boolean to allow 'outside' calls to stop a running thread.
The first two methods are the constructor and the destructor. They are not really needed in this example, but it is good practice to put them in during script development, because they will indicate in the results-window when an object of that class gets created and when it gets destroyed. That helps tracking memory leaks and dead-lock situations.
The next two methods allow 'outside' calls to set the two member variables.
The RunThread method is the heart of any Thread class. It has to be of exactly this signature because it overrides the according method of the parent class Thread from which we derive our class MyThread. The RunThread method gets launched into a separate background thread, when the method StartThread() is called. ( StartThread() is a method of the class Thread. )
The actual code in RunThread is in two parts:
An 'action-loop' doing anything you want but allowing a quick-exit if the Boolean variable changes value. This is how external calls can interrupt. This is discussed a bit further down.
A 'clean-up' part where the object can influence the UI object, discussed below as well.
Next is the UI class:
class myDialog:UIframe
{
object callThread
myDialog( object self )
{
result( self.ScriptObjectGetID() + " created.\n" )
}
~myDialog( object self )
{
result( self.ScriptObjectGetID() + " destroyed.\n")
}
TagGroup CreateDLG( object self )
{
image i := IntegerImage( "", 1, 0, 25, 25)
i = 0; i[ 2 , 2 , 23 , 23 ] = 1;
image onImage, offImage
onImage = RGB( 0*i , 200*i , 0*i )
offImage = RGB( 200*i , 0*i , 0*i )
TagGroup tgItems, tg, button, label, progress
tg = DLGCreateDialog("Dialog",tgItems)
button = DLGCreateDualStateBevelButton( "DBevel", onImage, offImage, "StartPressed" )
progress = DLGCreateProgressBar( "progress" ).DLGfill( "X" )
label = DLGCreateLabel( "start/stop" )
tgItems.DLGAddElement( DLGGroupItems( button , label ).DLGTableLayout( 2 , 1 , 0 ) )
tgItems.DLGAddElement( progress )
return tg
}
object Init(object self, number callThreadID )
{
// Assign thread-object via weak-reference
callThread = GetScriptObjectFromID( callThreadID )
if ( !callThread.ScriptObjectIsvalid() )
Throw( "Invalid thread object passed in! Object of given ID not found." )
// Pass weak-reference to thread object
callThread.SetLinkedDialogID( self.ScriptObjectGetID() )
return self.super.init( self.CreateDLG() )
}
void StartPressed( object self )
{
number active = self.LookupElement( "DBevel" ).DLGGetValue()
if ( active )
callThread.StartThread()
else
callThread.InterruptAtNextChance()
}
}
Any dialog (UI) class is derived from the class UIframe.
This class has only one member variable: An object, which will be the thread-object.
Again there are a constructor/destructor method for easier debugging.
The CreateDLG method builds the tagGroup describing the dialog. I will not go into details here, but essentially it creates the following dialog when displayed:
The Init() method initializes the object. The Init() method of the base class UIframe requires a descriptive TagGroup and returns the UI object itself. We call on this in the last line of our extended Init() method, and use our class-method to create the tagGroup:
return self.super.init( self.CreateDLG() )
The code before is what links our thread-object to the UI-object. We pass in a number, which is the object-ID of our thread-object. We now get the according object from memory and assign it to our local member variable. (NB: The variable now holds the object itself, not a copy or clone of it! )
callThread = GetScriptObjectFromID( callThreadID )
Right away, we check if the lookup was successful and actually returned a valid object. If not, we stop our script with a thrown exception. From now on, the UI-object 'contains' the thread-object and can use it.
Now comes the back-link. Now that the UI object has been allocated, it also has an object-ID. We feed this number into our thread-object.
callThread.SetLinkedDialogID( self.ScriptObjectGetID() )
From now on, the thread object is nicely linked to the UI-object. Looking back to the myThread class, you will notice that we use the same trick of looking up and locally storing the object in the RunThread() method.
StartPressed() is the method linked to our dialog button. This button is a bevel button, so we query its state, which is the state after the bevel-button changed, and act accordingly. We either launch the RunThread() method of our thread object as a background-thread, or invoke the according 'interrupt' method, which simply sets the Boolean variable
Finally the main script:
void StartScript()
{
object threadObject = alloc( myThread )
object dlgObject = alloc( myDialog ).Init( threadObject.ScriptObjectGetID() )
dlgObject.display( "Dialog" )
}
StartScript()
Not a lot going on here. We first create the threadObject of the myThread class, and then the dialog UI object.
We initialize the dialog object with the ID of the existing threadObject, and then display it as a modeless dialog.
Some points to notice:
Whenever you use object variables in DigitalMicrograph scripting, you should put them into a structure block. This ensures that the objects get out-of-scope and deleted, when the structure block is left. Object variables defined and allocated in the main script are not destructed at the end of the script. For this reason, we have encapsulated the main script in a method itself.
We have used two different methods of linking in this example:
Direct: The myDialog class really keeps the thread-object itself as a member variable. Although we initialized it with the ID only, we immediately linked the object to a member variable.
Weak reference: The myThread class only holds the object-ID of the dialog-object as a member variable.
Why have we done this? If the myThread class would keep the dialog-object as a member, then the two objects would hold each-other in a dead-lock situation. Neither can be destructed because of the other. But why have we not used the same for the myDialog class? Because we want to display the dialog as a modeless dialog in a background thread itself!
Think of the main-script:
We create the thread-object
We create the dialog-object
We display the dialog-object (But we don't stop script execution here!)
The script ends
But when the script ends, the object variables threadObject and dlgObject go out of scope! They will be immediately destructed, unless something keeps them in memory. The dlgObject stays in memory, because we displayed it as modeless dialog. It will be released, when the according dialog window is closed. But what keeps the threadObject? Nothing! Once the RunThread() method has finished, it would be released and subsequently destructed. However, because it is a member of the dlgObject it will not be destructed.

Xpage extlib Dialog keepComponents true and JSF component

i have a problem with the Dialog control from the Extention library:
I have created a java custom control wich searches some views, collects some data and displays it. This works nice if i place it on a XPage.
But i want to display the data in a Dialog so i used the Dialog control from the extention library. Using the Dialog control without any configuration also works fine but it takes some time for my control to search the views and display the data every time i open the dialog.So to reduce the waiting time for the user i wanted to use the option "keepComponents="true" from the Dialog control.
Now if i open the Dialog for the first time everything is perfekt but if i open it a secound time it displays the content from the first opening in addition to an error from my controlRenderer wich tells me that it could not get the viewName from the control. This error stacks up for every time i open and close the dialog.
I found a Post on OpenNtf from somebody who had the same issue with multiple content in his dialog when using this option but he didnt get any answers to his question.
Is this a bug of the component? Should i forget this option and cache my data in a bean? Why can't the renderer get the Viewname from the component?
The answer that follows assumes that the phrase "java custom control" in your question refers to a JSF component you developed; in XPages, the term "custom control" usually refers to an instance of a Custom Control design element, which is IBM's implementation of the JSF notion of "composite components".
You've stated that the component initially behaves as intended but fails on subsequent requests. This typically indicates that the restoreState and saveState methods of the component have not been properly implemented.
When the default serialization options are enabled for an application, all component state is written to disk at the end of each request, and read back into memory at the beginning of the next. These two operations are handled, respectively, by the saveState and restoreState methods of each component.
For example, suppose you defined a component for adding HTML canvas tags to an XPage, and decided to support the gesture and touch events associated with that element. So your component class would contain fields to store any code bound to those events:
private String ongesturechange;
private String ongestureend;
private String ongesturestart;
private String ontouchcancel;
private String ontouchend;
private String ontouchmove;
private String ontouchstart;
Each of those fields would typically then have an associated "getter" and "setter" method:
public String getOngesturechange() {
return getStringProperty("ongesturechange", this.ongesturechange);
}
public void setOngesturechange(String ongesturechange) {
this.ongesturechange = ongesturechange;
}
When an instance of that component is initialized, the "setter" method associated with each attribute that is defined for that component instance will be passed the value defined for that attribute. For the remainder of the initial page request, then, the private field for each defined attribute will store the value that was set. At the end of the request, the saveState method writes the values of these fields to disk. A typical saveState method looks similar to the following:
#Override
public Object saveState(FacesContext context) {
Object[] properties = new Object[8];
int idx = 0;
properties[idx++] = super.saveState(context);
properties[idx++] = this.ongesturechange;
properties[idx++] = this.ongestureend;
properties[idx++] = this.ongesturestart;
properties[idx++] = this.ontouchcancel;
properties[idx++] = this.ontouchend;
properties[idx++] = this.ontouchmove;
properties[idx++] = this.ontouchstart;
return properties;
}
The call to super.saveState() executes the same method, but using the version of the method defined in the parent class. So the on-disk representation of each component is essentially a nested array: each layer in the hierarchy stores all the properties it inherits from its parent class in the first element of the array, then stores all the properties that it defines in additional array elements.
When the component tree is restored on subsequent requests, each component uses its restoreState method to reconstitute the values of all its fields. A typical restoreState method looks similar to the following:
#Override
public void restoreState(FacesContext context, Object state) {
Object[] properties = (Object[]) state;
int idx = 0;
super.restoreState(context, properties[idx++]);
this.ongesturechange = ((String) properties[idx++]);
this.ongestureend = ((String) properties[idx++]);
this.ongesturestart = ((String) properties[idx++]);
this.ontouchcancel = ((String) properties[idx++]);
this.ontouchend = ((String) properties[idx++]);
this.ontouchmove = ((String) properties[idx++]);
this.ontouchstart = ((String) properties[idx++]);
}
This hierarchically reads the on-disk data back in: each class passes a set of properties to the parent class, then assigns the remaining array elements to the fields they were associated with when the component state was saved.
This process provides an easy way to maintain component state across requests -- each layer of inheritance need only concern itself with the new properties that layer defines -- but these state maintenance methods are easy to forget to implement. If either method is omitted from the component implementation, then the page "forgets" the property values on subsequent requests, because either they were never written to disk, or were not loaded back into memory, or both.
Assuming that this is the root cause of your problem, the reason the problem does not occur when the component is inside a dialog with the default (false) value for keepComponents is because the default dialog behavior is to remove its children from the component tree entirely when the dialog is closed. This behavior is for performance reasons: there's theoretically no benefit to be gained from storing a server-side representation of components that only exist inside a dialog that the user is not currently interacting with. When the dialog is opened again, a new instance of each child component is created using the original property values. In this scenario, it wouldn't matter that your component isn't saving its state, because each time it's used, a new instance is created. But if the dialog is told to keep its children in the component tree, now the component must properly maintain its own state... otherwise its property values are discarded at the end of each request and subsequent requests are unaware of the previous values.
In summary, yes, the data you're displaying should be cached in a bean (or data source) if the data is unlikely to change enough between requests to justify obtaining the data again during every single event. But the reason for the specific behavior you're describing is most likely because your component implementation is not properly maintaining its own state.

Resharper create property with backing field

How do you create property with a backing field in Resharper?
This is the first thing you would want to do with a class and I cannot find how to it.
Its so simple.
Within the body of the class, type prop and hit Tab. Supply the property's type and name. This will create an autoproperty (these days, it is typically one of these you would want to create).
Then, with the cursor on the property name, hit Alt+Enter and choose To property with backing field.
The quickest way I've found is to type your property as if it exists already:
this.MyProperty = "hello";
Then Alt-Return on the property name, and choose Create Property 'MyProperty' then hit tab to choose between auto-property, managed backing field, or default member body.
I believe this is quicker than using the prop shortcut, hitting tab, specifying the property type, hitting tab twice, specifying the name, and then pressing Alt-Return on the property name and choosing the 'to property with backing field' selection.
You could also create a Live Template so that there is slightly less work, e.g:
/// <summary>
/// Private backing field for $Property$ property
/// </summary>
private $Type$ $BackingField$;
public $Type$ $Property$
{
get
{
return this.$BackingField$;
}
set
{
this.$BackingField$ = value;
}
}
The parameter $BackingField$ can be generated automatically from $Property$ by the "first character in lower case" macro of the template editor and setting it to "Not editable".
But I believe the first method is the quickest and easiest.
If you already have a property with a getter and setter, sometimes you will find that the backing field you used is no longer available because you changed the base class for the current class or you made other changes. For example, in the LinesMax property below, the backing field Height is available from an inherited class:
public int LinesMax
{
get { return ConvertValGet(AdjustMetricEnum.Height, Height); }
set { Height = ConvertValSet(AdjustMetricEnum.Height, value); }
}
If the above code works but I decide afterwards no longer to inherit the class that exposes the Height property, the two Height variable names will turn red in the IDE to indicate that they're no longer available to the code.
At that point, I may want to create a private backing field. To easily create that, I can first modify the Height name to _height, then place the cursor on either _height name, hit Alt-Enter then choose Create field '_height'. A backing field will be created.

Resources