Home page Home page Home page Home page
Pixel
Pixel Header R1 C1 Pixel
Pixel Header R2 C1 Pixel
Pixel Header R3 C1 Pixel
Pixel
By Sprezz | Sunday, 10 February 2013 05:29 | 2 Comments
Putting the finishing touches to an order entry system this week, we were frustrated by the apparent unwillingness of one symbolic to update, whilst those around it had no such qualms.


Looking at the dictionary items nothing stood out; they were all multivalued, they all derived their values based upon the code entry. So we decided to go for the sledgehammer to crack a nut approach and added a quickevent to the POSCHANGED event. Column 4 doesn't want to update - we'll tell it to update every single time the user moves cells.


This was sort of successful - but not entirely. Sometimes it worked, sometimes the price column was the only one updated.

In the Sprezz world, "Sort of" doesn't cut it. So just as we were about to start coding a POSCHANGED in the commuter routine to update ALL of the columns we reviewed our options. As is often the way when discussing problems rather than thinking about problems the solution becamse obvious. RTI have optimised the semantic logic layer in such a way that the only symbolics recalculated by default are those that rely on the column that has just changed.

How do they do that?

We can't know the exact mechanism but it's safe to guess that they look at the formula for the symbolic in some way and see if it references the changed column. They doubtless do this once at Window compilation time then cache the results. And what was the formula of the non-updating column?


Because the calculation was reused elsewhere, we'd moved it off into a function - which worked well BUT confused the semantic logic layer as now, as far as it was concerned, the formula was NOT dependent on the code column. The initial solution - as inelegant as it seems, was simply to ensure that the formula contained a reference to the code column so -


et voila now all the symbolics update without any further user intervention.


But that still didn't really satisfy us  ΜΆΜΆ  why should we have to pollute our dictionary items just to make dependencies within the window work? Especially as we have an increasing tendency on new systems to move all symbolic calculations into a control commuter for the table. So we decided to work out how OI was dealing with these dependencies and manipulate them ourselves on the form CREATE event.

The first place to look when trying to establish this sort of information is always the additional features documentation provided by Revelation - or the SYSPROG Inserts as they're more commonly known - OIWIN_EQUATES in this case. Opening this, the area that we're specifically interested in is the equates for the Control Semantics which are associated with the Control Map. Scanning this we come to the rubric "* list of controls to send recalcs to on change" next to column position 14 - CS_RECALC$.

Given that we're dealing with an edit table here, the information is going to be somewhat nested! We could have several data columns which in turn are depended upon by several other symbolics.  Describing the structure in English first - column X of controlSemantics@ contains the controlSemantic information for the control we have located at X in the controlMap@.

Value14 of controlSemantics@ contains a subvalued list of information - each subvalue corresponding to the equivalent data column in the edit table. So if the data control that was depended upon was in column 3 of the data table, the corresponding information would be in controlSemantics@. Now there could be multiple columns dependent on this data column so their details would be text mark delimited. So the details of the first dependent column would be in controlSemantics@ the second in controlSemantics@ etc. Finally the identification of the data that is dependent consists on the control name value, and in the case of an edit table the column value. In the case of an edit control that is not multivalued this is always 1. The two values are in turn delimited by sub text marks. So if the control in question were dependent on the 3rd column of the editable and it was the EDT_PRODUCTS control column 4 then the structure would be

controlSemantics@< X, 14, 3, 4, 1> = "ENQUIRIES.EDT_PRODUCTS"
controlSemantics@< X, 14, 3, 4, 2> = "4"

So finally a code sample showing how we achieved the result we wanted without having to change our dictionary columns.



  /*
    ensure controlSemantics@ is updated to adjust the selling price
    when the product code changes. The product code is tn column 2 of
    the edit table and the selling price is In column 4
  */


  Equ editTable$    To atWindow : ".EDT_PRODUCTS"
  Equ sellingPrice$ To editTable$ : @Stm : 4
  Equ codeColumn$   To 2

  Locate editTable$ In controlMap@ using @Fm setting controlPos Then

    dependsInfo = controlSemantics@< controlPos, CS_RECALC$ >
    colInfo     = dependsInfo<0, 0, codeColumn$>
 
    Locate sellingPrice$ In colInfo using @Tm setting thereAlready Else
      colInfo := @Tm : sellingPrice$
      dependsInfo<0, 0, codeColumn$> = colInfo
      controlSemantics@< controlPos, CS_RECALC$ > = dependsInfo
    End

  End
    

This worked perfectly and lent itself to encapsulation in a function to tweak recalculation dependencies as we saw fit.

2 Comments:

  • Nice article. We ran into the very same issue because we manage our calculated column logic in the same way as well. It always looked funny to us to introduce a throw away variable just to satisfy the column dependency logic. ;-) Like you we have our own encapsulation processes but we have not yet resolved whether this should be hard-coded, soft-coded, or handled differently. Trying to manage dependencies away from the calculated column itself requires discipline. How are you tackling this?

    By Blogger Don Bakke, At 15 February 2013 at 00:31  

  • As tempting as it was to ask our framework author to work it out for himself at create time by a combination of naming conventions and tab order it seemed more elegant for the programmer to set a custom property on the CREATE event of the window which in turn is interrogated by the POSTCREATE promoted event to set the actual labelled common. This is pretty similar to what we do with our OPTIONCOLS property which we set on the CREATE event to tell the framework which edittable columns should be hyperlinked.

    By Blogger Sprezz, At 15 February 2013 at 00:38  

Post a comment

Subscribe to Post Comments [Atom]



<< Home

Pixel
Pixel Footer R1 C1 Pixel
Pixel
Pixel
Pixel