How to reference one element of an array property from another class

Hello,

I need to add a new property ("Injection") to an existing database.  The existing database contains, in part:

An "ImageStudy" which contains one or more "ImageFiles"  defined as follows:

Class PET.ImageStudy Extends (%Persistent) 
{
Relationship ImageFiles as PET.ImageFile [cardinality=children,inverse=Study]
...
}
Class PET.ImageFile Extends (%Persistent)
Relationship Study as PET.ImageStudy [cardinality=parent,inverse=ImagFiles]
...
}

The requirements for the Injection are that 1)an ImageStudy can have one or more Injections; 2)an ImageFile is associated with a single Injection; 3)More than one ImageFile can be associated with a single Injection; 4)the Injection does not need to be persistent, it can be embedded in the ImageStudy.  I am planning to define the Injection as a %SerialObject containing RadioTracer, Dose and Time properties, and then include the Injection in the ImageStudy Class as

Property Injection As array of Injection;

My questions are

1) Is this a good way to define the Injection property?

2)What is the best way to associate the ImageFile with a single Injection?  Would I just add a property to the ImageFile to store the array key for the associated Injection?

Thanks and apologies for the extremely elementary questions -- I have very little experience with databases.

  • 0
  • 0
  • 279
  • 5
  • 2

Answers

Hi,

You can create Injection as a %SerialObject and add to Study as a list

`` `
Property Injection As list Of PET.Injection;
```

OK, thanks.

Is there a good reason to define the Injection property as a list, rather than an array, as I had been planning?

In either case, how do I associate a single element of the Injection property with an ImageFile (ie, should I just store the array key as a property in the ImageFile, or is there a better mechanism)?

Sorry for delay...

You can use both, as a list you will use the insert method like a relationship

Set inj = ##class(PET.Injection).%New(), inj.Desc = "blabla "_i
Do study.Injection.Insert(inj)

It will add a column with the list

You can use an array, but you must use SetAt:

Do study.InjectionArr.SetAt(inj,i)

And it will create another table with the name of the property

OK, thanks!

So then if I store the Injection element_key (in the case of an array), as a property in the ImageFile object which references the injection, I will be able to get to the various Injection properties from the ImageFile instance?

What would I store in the ImageFile in the case of a list?

Thanks for your help!

"So then if I store the Injection element_key (in the case of an array), as a property in the ImageFile object which references the injection, I will be able to get to the various Injection properties from the ImageFile instance? "

Sure, just to pay attention to manage the array key, that will be like your ID

"What would I store in the ImageFile in the case of a list? "

You can use list like a collection, could be of %SerialObjects or other types like %Strings, in the table will be save like $Piece in the column

Something to play with:

===========================================================================================

Class PET.ImageStudy Extends (%Persistent, %ZEN.DataModel.Adaptor) [ Inheritance = right ]
{

Property Code As %String [ Required ];

Property Name As %String [ Required ];

Relationship ImageFiles As PET.ImageFile [ Cardinality = children, Inverse = Study ];
-------------------------------------------------------------------------------------------------------------------------------------------------

Class PET.ImageFile Extends (%Persistent, %ZEN.DataModel.Adaptor) [ Inheritance = right ]
{

Property Code1 As %String [ Required ];

Property Name1 As %String [ Required ];

Property Image As %Stream.FileBinary;

Property Path As %String(MAXLEN = 100);

Relationship Study As PET.ImageStudy [ Cardinality = parent, Inverse = ImageFiles ];
--------------------------------------------------------------------------------------------------------------------------------------------------

Class PET.TestA Extends %ZEN.Component.page
{

Parameter APPLICATION;

Parameter PAGENAME;

Parameter DOMAIN;

XData Style
{
<style type="text/css">
</style>
}

XData Contents [ XMLNamespace = "http://www.intersystems.com/zen]
{
<page xmlns="http://www.intersystems.com/zentitle="" >
<hgroup valign="top">
<pane paneName="Study" />
<pane paneName="Image" />
</hgroup>
</page>
}

XData Study [ XMLNamespace = "http://www.intersystems.com/zen]
{
<pane xmlns="http://www.intersystems.com/zentitle="" align="left"  width="400" valign="top">
<fieldSet legend="Study">
<dataController modelId="" id="ctrlParent" modelClass="PET.ImageStudy"/>
<form id="frmId" controllerId="ctrlParent" labelPosition="left">
 <tableNavigatorBar showPageSize="true" id="nav" tablePaneId="table" />
<vgroup valign="top">
<tablePane width="400px" id="table"
    tableName="PET.ImageStudy"
     maxRows="1000" pageSize="5"
     showZebra="true" useSnapshot="true"
     valueColumn="ID"
     onselectrow="zenPage.rowSelected(zenThis,which);">
    <column colName="ID" hidden="true"/>
   <column header="Code" colName="Code" width="30%" />
   <column header="Name" colName="Name" width="70%" />
</tablePane>
</vgroup> <spacer width="15px"/>
<vgroup valign="top">
<text label="Code:" id="Code" name="Code" dataBinding="Code" size="15" required="true"/>
<text label="Name:" id="Name" name="Name" dataBinding="Name" size="30" required="true"/>
<spacer height="10"/>
<hgroup>
<button caption="New" onclick="zenPage.newRecord();/>
<button caption="Save" onclick="zenPage.saveRecord();/>
<button caption="Cancel" onclick="zenPage.cancelRecord();/>
<button caption="Delete" onclick="zenPage.deleteRecord();/>
</hgroup>
</vgroup>
</form>
</fieldSet>
</pane>
}

XData Image [ XMLNamespace = "http://www.intersystems.com/zen]
{
<pane xmlns="http://www.intersystems.com/zentitle="" valign="top" >
<fieldSet legend="FileImage">
<dataController id="ctrlChildren1" modelClass="PET.ImageFilemodelId=""/>
<form id="frmIdChild1" controllerId="ctrlChildren1" labelPosition="left">
 <tableNavigatorBar showPageSize="true" id="nav1" tablePaneId="Table1" />
<hgroup>
<vgroup valign="top">
 <tablePane width="400px" id="Table1"
  tableName="PET.ImageFile"
     whereClause="Study=?" 
     maxRows="1000" pageSize="5" showZebra="true" 
     useSnapshot="true"
     valueColumn="ID"
     onselectrow="zenPage.rowSelectedChild1(zenThis);">
    <column colName="ID" hidden="true"/>
   <column header="Code" colName="Code1" width="10%" />
    <column header="Name" colName="Name1" width="20%"/>
<column colName="Path" header="Path" width="25%" hidden="true"/>
<column colName="Image" header="Image" width="45%" OnDrawCell="DrawCell"/>
<parameter value="zen('ctrlParent').getProperty('modelId');"/>
</tablePane>
</vgroup>
<spacer height="15px"/> <spacer width="15px"/>
<vgroup>
 <text label="Id:" id="Id" name="Id" readOnly="true" dataBinding="%id" hidden="true"/>
  <text label="Code:" id="Code1" name="Code1" dataBinding="Code1" size="15" required="true"/>
  <text label="Name:" id="Name1" name="Name1" dataBinding="Name1" size="30" required="true"/>
 <text label="File name:" id="Path" name="Path" dataBinding="Path" size="60" />
<button id="buttonF" caption="Browse" onclick="zenPage.fileSelect();"/>
  <spacer height="10"/>
 <image id="image" width="100" height="100"/>
 <spacer height="10px"/>
<hgroup>
<button caption="New" onclick="zenPage.newChildRecord1();/>
<button caption="Save" onclick="zenPage.saveChildRecord1();/>
<button caption="Cancel" onclick="zenPage.cancelChildRecord1();/>
<button caption="Delete" onclick="zenPage.deleteChildRecord1();/>
</hgroup>
</vgroup>
</hgroup>
</form>
</fieldSet>
</pane>
}

Method DrawCell(pTable As %ZEN.Component.tablePane, pName As %String, pSeed As %String) As %Status
{
  Set id=%query("ID")
    Set obj=##class(PET.ImageFile).%OpenId(id)
    If (obj)
    filename=%query("Path")
Set stream=##class(%FileBinaryStream).%New()
Do stream.LinkToFile(filename)
Set oid=stream.%Oid()
&html<<image src="%25CSP.StreamServer.cls?STREAMOID=#(..Encrypt(oid))#">
        
   Quit $$$OK
}

Method Image(id As %String) As %Status [ ZenMethod ]
{
    set img=..%GetComponentById("image")
    Set obj=##class(PET.ImageFile).%OpenId(id)
    If (obj)
    filename=obj.Path
    filename=$tr(filename,"\","/")
Set stream=##class(%FileBinaryStream).%New()
Do stream.LinkToFile(filename)
Set oid=stream.%Oid()
set img.streamId=oid
        
   Quit $$$OK
}

Method ShowImage(id As %String, filename As %String) As %Status [ ZenMethod ]
{
    set img=..%GetComponentById("image")
    filename=$tr(filename,"\","/")
Set stream=##class(%FileBinaryStream).%New()
Do stream.LinkToFile(filename)
set img.streamId=stream.%Oid()
   Quit $$$OK
}

ClientMethod fileSelect() [ Language = javascript ]
{
  var Dir='c:/InterSystems/TryCache/csp/broker/';
  var wildcard='';
  zenLaunchPopupWindow('%ZEN.Dialog.fileSelect.cls?Dir='+encodeURIComponent(Dir)+'&wildcard='+wildcard,'FileSelect','resizable,width=600,height=700');
}

ClientMethod onPopupAction(popupName, action, value) [ Language = javascript ]
{
 
  switch(popupName){
  case 'FileSelect':
  if (action == "ok") {
  var id zen('Table1').getValue();
zen('ctrlChildren1').setDataByName('Path',value);
  zen("Path").setValue(value);
var x=this.ShowImage(id,value);
zen('image').refreshContents();
  }
  }
}

ClientMethod resetTable1() [ Language = javascript ]
{
var table1 zen('Table1');
table1.setProperty('initialExecute',false);
table1.executeQuery(true);
zen('frmIdChild1').reset();
}

ClientMethod rowSelected(table, which) [ Language = javascript ]
{
 var controller zen('ctrlParent');
   if (controller.getModelId()==table.getValue()) { return; }
    else{
    if (('keypress' == which)||(zenRefreshMode==1)) {
        // defer this action in case the user is arrowing through aCode of items
        var id table.getValue();
        var action new Function("zen('ctrlParent').setProperty('modelId','"+id+"' );");
        zenSetDeferredAction(action,200);
     }
    else {
        var id table.getValue();
        controller.setProperty('modelId',id);
    
// Update the child section
var Table1 zen('Table1');
Table1.setProperty('parameters',1,id);
Table1.selectRow(-1);
zen('frmIdChild1').reset();
}
}
}

ClientMethod rowSelectedChild1(table1, which) [ Language = javascript ]
{
  var controller1 zen('ctrlChildren1');
    if (controller1.getModelId()==table1.getValue()) { return; }
    else {
    if (('keypress' == which)||(zenRefreshMode==1)) {
        // defer this action in case the user is arrowing through a Code of items
        var childid1 table1.getValue();
        var action new Function("zen('ctrlChildren1').setProperty('modelId','"+childid1+"' );");
        zenSetDeferredAction(action,200);
    }
    else {
        var childid1 table1.getValue();
controller1.setProperty("modelId",childid1);
var x=this.Image(childid1);
zen('image').refreshContents();
}
}
}

ClientMethod newRecord() [ Language = javascript ]
{
this.resetTable1();
zen('ctrlParent').setProperty('modelId','');
}

ClientMethod newChildRecord1() [ Language = javascript ]
{
var controller zen('ctrlParent');
var id controller.getModelId();

if ('' == id) {alert('Nothing selected!'+'\n'+'Please select row in Parent table!');}
else {zen('ctrlChildren1').setProperty('modelId','');}
}

ClientMethod saveRecord() [ Language = javascript ]
{
zen('frmId').save();
zen('table').executeQuery(true);
zen('ctrlParent').setProperty('modelId','');
this.resetTable1();
}

ClientMethod saveChildRecord1() [ Language = javascript ]
{
var controller zen('ctrlParent');
var id controller.getModelId();

if ('' == id) {alert('Nothing selected!'+'\n'+'Please select row in Parent table!');}
else {
zen('ctrlChildren1').setDataByName('Study',zen('ctrlParent').getProperty('modelId'));
zen('frmIdChild1').save();
zen('Table1').executeQuery(true);
zen('ctrlChildren1').setProperty('modelId','');
zen('Table1').selectRow(-1);
zen('frmIdChild1').reset();
}
}

/// cancel the current action
ClientMethod cancelRecord() [ Language = javascript ]
{
zen('table').selectRow(-1);
zen('frmId').reset();

var table1 zen('Table1');
table1.setProperty('initialExecute',true);
zen('Table1').selectRow(-1);
}

ClientMethod cancelChildRecord1() [ Language = javascript ]
{
zen('Table1').selectRow(-1);
zen('frmIdChild1').reset();
}

/// Delete current item from database
ClientMethod deleteRecord() [ Language = javascript ]
{
var controller zen('ctrlParent');
var id controller.getModelId();

if ('' == id) {alert('Nothing selected.');}
else if (confirm('Are you sure you want to delete the record?')){
controller.deleteId(id);
zen('frmId').reset();
zen('table').executeQuery(true);
this.resetTable1();
}
}

/// Delete current item from database
ClientMethod deleteChildRecord1() [ Language = javascript ]
{
var controller1 zen('ctrlChildren1');
var childid1 controller1.getModelId();

if ('' == childid1) {alert('Nothing selected.');}
else if (confirm('Are you sure you want to delete the record?')){
controller1.deleteId(childid1);
zen('frmIdChild1').reset();
zen('Table1').executeQuery(true);
}
}

}
=======================================================================================================