Professional UI Solutions
Site Map   /  Register
 
 

Forum

Please Log In to post a new message or reply to an existing one. If you are not registered, please register.

NOTE: Some forums may be read-only if you are not currently subscribed to our technical support services.

Forums » Prof-UIS Tech Support » CExtPropertyItem::Apply Collapse All
Subject Author Date
Suhai Gyorgy Nov 6, 2006 - 8:10 AM

Dear Support,

I’d like to understand some more how CExtPropertyGridCtrl works. Right now I’m mostly interested in method CExtPropertyItem::Apply.

What exactly is the CExtGridCell *pValue parameter in this method? Where is it in the grid? I did some debugging and it’s neither the result of ValueActiveGet, nor the result of ValueDefaultGet methods. If inside Apply method I set a different text for the cell gotten from ValueActiveGet ( calling ValueActiveGet()->TextSet ), the text in the PropertyGrid doesn’t change.

In which cases will the pValue parameter be NULL inside Apply?

In which cases will the text be different in pValue and in ValueActiveGet?

Thank you,
Chris

Technical Support Nov 6, 2006 - 12:36 PM

Any CExtPropertyValue object contains two CExtGridCell grid cell objects: the default value and the current value. if there was only one cell, the user would not be able to reset the current value to the default one. The CExtPropertyGridCtrl window is a container for several child windows including one or more CExtPropertyGridWnd-derived tree grid windows. A tree grid window keeps a copy of each current CExtGridCell object from CExtPropertyValue values. The property grid control never deletes the attached tree data structure containing values and categories (property store). It simply initializes the contents of contained tree grid windows and synchronizes current CExtGridCell grid cell objects inside CExtPropertyValue objects when appropriate grid cell in the active tree grid window changes. The CExtPropertyGridCtrl::Apply() virtual method is invoked in this case and it never receives the NULL pointer value in its parameter. But there are two notifications when the property value changes: one is the CExtPropertyGridCtrl::Apply() virtual method and the second is the CExtPropertyGridCtrl::OnPgcResetValue() virtual method invoked when the user resets the property value from the context menu displayed over the current tree grid window. In both cases, the grid cell kept inside the active tree grid window is used for synchronizing gird cell(s) in inactive grid window(s) and active grid cell inside the CExtPropertyValue object. These issues explain when the data stored inside two grid cells of one the CExtPropertyValue object may be different.

Suhai Gyorgy Nov 7, 2006 - 2:25 AM

I think I understand now, thank you. But I still need your confirmation in one question:

In my Apply method I need to make sure that the new value set by the user is valid (e.g. it’s a unique value among the same property of the other objects), and in case of invalid input I have to "cancel", or in other cases correct the given input and set the old or the corrected value as the new one. Do I understand right that for this to work properly I have to call both pValue->TextSet and ValueActiveGet()->TextSet methods to update the value?

Best regards,
Chris

Technical Support Nov 7, 2006 - 11:08 AM

The CExtPropertyItem::Apply() method is invoked to assign the current cell object from the grid cell with an edited value. This method works simply:

void CExtPropertyItem::Apply(
    CExtGridCell * pValue // = NULL
    )
{
CExtGridCell * pOwnValue = ValueActiveGet();
    pOwnValue->Assign( *pValue );
}
You can implement your own version of this method:
void CYourPropertyValue::Apply(
    CExtGridCell * pValue // = NULL
    )
{
CExtGridCell * pOwnValue = ValueActiveGet();
    if( THE pValue IS CORRECT )
        pOwnValue->Assign( *pValue );
    else
        pValue->Assign( *pOwnValue );
}
The pValue->Assign( *pOwnValue ) code assigns the old value to the cell (i.e. cancels the result of editing).

Suhai Gyorgy Nov 8, 2006 - 2:45 AM

Yes, cancelling the editing is pretty easy like you show above, but I’m more interested in setting and showing something that is neither in pValue cell, nor in pOwnValue cell. To clear it up: I need to verify that position and size of a control is inside a form. That is, if user assigns a new width, but left + new width is greater then width of form, then I have to set a width with which the control stays just inside the form. So I calculate the biggest possible width and I call

pValue->_VarriantAssign( iMaxWidth, VT_I4);
pOwnValue->_VarriantAssign(iMaxWidth, VT_I4);
Well, of course I could go for
pValue->_VarriantAssign( iMaxWidth, VT_I4);
pOwnValue->Assign( *pValue );
, but I think it’s the same. Is this the right solution?

Technical Support Nov 8, 2006 - 12:34 PM

The first code snippet simply puts the numeric values into two grid cells. It’s an acceptable solution. The second snippet assigns grid cells completely including styles, colors, font and cursor. It is also acceptable if you are not using these cell attributes or they are not changing at run time due to some conditions. The third and may be preferable solution is outside the property grid control: you can code your own grid cell class which does not accept input of incorrect values. Or it can verify typed text on-the-fly. The CExtGridCell::OnInplaceControlTextInputVerify() and CExtGridCell::OnInplaceControlTextInputComplete() virtual methods allow to control the text typing in the in-place activated edit control.


Suhai Gyorgy Nov 8, 2006 - 2:35 PM

Yes, I would consider this solution, but as I have many different cells with different verification methods, I should be coding different cell classes to all of them, along with all the PropertyValue classes for them, and this seems to be way too much work for this. If my current solution is acceptable, I think I’ll just stick to that. Thank you very much for the advice!