Montura Consulting   Research & Development
SAS/AF Combobox

 

Calendar Widget
A Working Example

 

Combobox #1: Month

class combobox1 extends sashelp.classes.combobox_c.class;           
public list gPipe / (sendEvent='N', autocreate='N');
public list items / (state='o', initialValue={
'01-Jan',
'02-Feb',
'03-Mar',
'04-Apr',
'05-May',
'06-Jun',
'07-Jul',
'08-Aug',
'09-Sep',
'10-Oct',
'11-Nov',
'12-Dec'
});

_init: method / (state='o');
_super();
_addEventHandler(frameID, 'reset cursor', 'runCursor');
_addEventHandler(frameID, 'calendar present', 'runStartup');

gPipe=getniteml(envlist('G'), 'pipe');
_cursor();
endmethod;

runStartup: method;
selectedItem=getitemc(items, getnitemn(gPipe, 'month'));
frameid._sendEvent('reset day');
endmethod;

_select: method / (state='o');
_super();

setnitemn(gPipe, selectedIndex, 'month');
frameid._sendEvent('reset day');
frameid._sendEvent('reset worddate');
endmethod;

runCursor: method;
_cursor();
endmethod;
endclass;


Combobox #2: Day
The full ranges of values are dependent on which month is selected from Combobox #1.

class combobox2 extends sashelp.classes.combobox_c.class;      
public list gPipe / (sendEvent='N', autocreate='N');
public list items / (state='o', initialValue={});
public num workDate / (sendEvent='N');

_init: method / (state='o');
_super();
_addEventHandler(frameID, 'reset day', 'runInterface');

gPipe=getniteml(envlist('G'), 'pipe');
endmethod;

_select: method / (state='o');
_super();

setnitemn(gPipe, selectedIndex, 'day');
frameid._sendEvent('reset worddate');
endmethod;

runInterface: method;
dcl num xDay xSelect daystart dayend;
_refresh();

workDate=mdy(getnitemn(gPipe, 'month'),
1,
getnitemn(gPipe, 'year')
);

daystart=day(intnx('Month', workDate, 0, 'BEGINNING'));
dayend=day(intnx('Month', workDate, 0, 'END'));

clearlist(items);
do xDay=daystart to dayend;
insertc(items, put(xDay, z2.), -1);
end;
_refresh();

if nameditem(gPipe, 'day')
then xSelect=getnitemn(gPipe, 'day');
else xSelect=day(today());

if xSelect GT listlen(items) then
xSelect=listlen(items);

if xSelect then
selectedItem=getitemc(items, xSelect);

setnitemn(gPipe, xSelect, 'day');
_refresh();

frameid._sendEvent('reset date');
endmethod;
endclass;

Combobox #3: Year
Selection list is limited to a fifty year span.

class combobox3 extends sashelp.classes.combobox_c.class;           
public list gPipe / (sendEvent='N', autocreate='N');
public list items / (state='o', initialValue={});

_init: method / (state='o');
_super();
_addEventHandler(frameID, 'calendar present', 'runStartup');

gPipe=getniteml(envlist('G'), 'pipe');
endmethod;

runStartup: method;
dcl num xYear calendarYear;

calendarYear=getnitemn(gPipe, 'year');

clearlist(items);
_refresh();
do xYear=(calendarYear-25) to (calendarYear+25);
insertn(items, xYear, -1);
end;
_refresh();

selectedIndex=searchn(items, calendarYear);
endmethod;

_select: method / (state='o');
_super();

setnitemn(gPipe, input(selectedItem, 4.), 'year');
frameid._sendEvent('reset worddate');
endmethod;
endclass;

 

Display the user-selected date name

class textentry1 extends sashelp.classes.textentry_c.class;         
public list gPipe / (sendEvent='N', autocreate='N');

_init: method / (state='o');
_super();
_addEventHandler(frameID, 'calendar present', 'runStartup');

gPipe=getniteml(envlist('G'), 'pipe');
_setTabbable('OFF');
editable='No';
endmethod;

runStartup: method;
if nameditem(gPipe, 'calendar name') then
text=getnitemc(gPipe, 'calendar name');
endmethod;

_onClick: method / (state='o');
_super();
frameid._sendEvent('reset cursor');
endmethod;

_onDoubleClick: method / (state='o');
_super();
frameid._sendEvent('reset cursor');
endmethod;
endclass;

Display the user-selected date in WEEKDATE format.

class textentry4 extends sashelp.classes.textentry_c.class;            
public num targetDate / (sendEvent='N');
public list items / (initialValue={
'January',
'February',
'March',
'April',
'May',
'June',
'July',
'August',
'September',
'October',
'November',
'December'
});



_init: method / (state='o');
_super();
_addEventHandler(frameID, 'reset worddate', 'runInterface');
_addEventHandler(frameID, 'calendar present', 'runInterface');

_setTabbable('OFF');
editable='No';
endmethod;

runInterface: method;
dcl list gPipe=getniteml(envlist('G'), 'pipe');

if nameditem(gPipe, 'month') then do;
targetDate=mdy(
getnitemn(gPipe, 'month'),
getnitemn(gPipe, 'day'),
getnitemn(gPipe, 'year')
);
end;

if targetDate then do;
text=left(put(targetDate, weekdate37.));
setnitemn(gPipe, targetDate, 'calendar date');
end;
else do;
text='';
setnitemn(gPipe, targetDate, 'calendar date');
end;

_refresh();
endmethod;

_onClick: method / (state='o');
_super();
frameid._sendEvent('reset cursor');
endmethod;

_onDoubleClick: method / (state='o');
_super();
frameid._sendEvent('reset cursor');
endmethod;
endclass;

Delete from the global list if the CANCEL button is used.
No data was applied, just exit the the screen.

class pushbutton2 extends sashelp.classes.pushbutton_c.class;
public char label / (state='o', initialValue='Cancel');

_onClick: method / (state='o');
_super();
frameid._setStatus('H');
endmethod;
endclass;
GUI startup
Never assume raw data is complete or in any way reliable.
class controller;                                                                            
public list gPipe / (sendEvent='N', autocreate='N');
public list gEdit / (sendEvent='N', autocreate='N');

_init: method / (state='o');
_super();
_addEventHandler(frameID, 'controller startup', 'runInterface');

gPipe=getniteml(envlist('G'), 'pipe');
gEdit=getniteml(envlist('G'), 'edit');
endmethod;

runInterface: method;
dcl num calendarDate xChar;
dcl char guiDate;

if nameditem(gPipe, 'data name') then
guiDate=getnitemc(gEdit, getnitemc(gPipe, 'data name'));

do xChar=1 to length(guiDate);
if substr(guiDate, xChar, 1) not in('1','2','3','4','5','6','7','8','9','0') then
substr(guiDate, xChar, 1)=' ';
end;

calendarDate=mdy(input(substr(guiDate,1,2), best.),
input(substr(guiDate,4,2), best.),
input(substr(guiDate,7) , best.));

if calendarDate=. then
calendarDate=today();

setnitemn(gPipe, calendarDate, 'calendar date');
setnitemn(gPipe, month(calendarDate), 'month');
setnitemn(gPipe, day(calendarDate), 'day');
setnitemn(gPipe, year(calendarDate), 'year');

frameid._sendEvent('calendar present');
endmethod;
endclass;

Clinical Trials with the Marijuana Widget
Implementing CDISC standards with sensitive, regulated data.

A programming technique pioneered in San Francisco shows the ideal way to begin clinical trials of a certain substance. The first step is to implement administrative software that restricts knowledge such a study even exists. This proven strategy will effectively minimize those who ask to be included in the study as a late-arrival subject, in accordance with FDA regulations.

Build a Tree

class tree;                                                                            
public list ndv / (sendEvent='N');
public list groupWork / (sendEvent='N', initialValue={0});
public list groupKeys / (sendEvent='N');

public list actionNode / (sendEvent='N');
public list rootNodes / (sendEvent='N');
public list serialNodes / (sendEvent='N');
public num nodeToggle / (sendEvent='N');
public num rootToggle / (sendEvent='N', initialValue=0);
public num countFile / (sendEvent='N', initialValue=0);

public char nameTree / (sendEvent='N', initialValue='miwork.tree');
public char nameKey / (sendEvent='N', initialValue='key_id');
public char nameText / (sendEvent='N', initialValue='text');
public char nameGroup / (sendEvent='N', initialValue='object_group');
public char nameChild / (sendEvent='N', initialValue='object_child');

public list transfer / (sendEvent='N');

runInterface: method;
dcl list gVector=getniteml(getniteml(envlist('G'), 'mpar'), 'config');

do while (listlen(groupWork));
call send(_self_, 'groupKeys');

do while (listlen(groupKeys));
call send(_self_, 'nodeParameter1');
call send(_self_, 'nodeParameter2');
call send(_self_, 'nodeParameter3');
call send(_self_, 'nodeParameter4');

delitem(groupKeys);
clearlist(actionNode);
clearlist(ndv);
end;

call send(_self_, 'nodeChildren');
delitem(groupWork);
end;

savelist('catalog', 'miwork.domain.tree.slist', rootNodes);
endmethod;

groupKeys: method;
dcl list gVector=getniteml(getniteml(envlist('G'), 'mpar'), 'config');

dcl num thisValue=getitemn(groupWork);
dcl num rc dset;

dset=open(nameTree, 'i');
rc=where(dset, nameGroup||'='||put(thisValue, best.));
do while (fetch(dset)=0);
insertc(groupKeys, getvarc(dset, varnum(dset, nameKey)), -1);
end;
close(dset);

countFile+listlen(groupKeys);
endmethod;

nodeParameter1: method;
dcl num dset i rc;
dcl char collective;
dcl char thisValue=getitemc(groupKeys);

dset=open(nameTree, 'i');
rc=where(dset, nameKey||'='||quote(thisValue));

if fetch(dset)=0 then do;
do i=1 to attrn(dset, 'nvars');
if varType(dset, i)='C'
then insertc(ndv, getvarc(dset, i), -1, varname(dset, i));
else insertn(ndv, getvarn(dset, i), -1, varname(dset, i));
end;

copylist(ndv, 'Y', actionNode);
nodeToggle=getvarn(dset, varnum(dset, nameGroup));

if nodeToggle EQ 0 then
collective='root';

if length(collective) then
insertc(actionNode, collective, -1, 'collective');
end;
close(dset);
endmethod;

nodeParameter2: method;
if listlen(actionNode)=0 then return;

dcl char text=upcase(getnitemc(ndv, nameText));
dcl char suffix=substr(text, length(text)-index(reverse(text), '.')+2);
dcl num iconID=0;

if getnitemn(ndv,'object_type')=1 then iconID=19;

if rootToggle=0 then do;
insertc(actionNode, 'yes', -1, 'showChildren');
rootToggle=1;
end;
else insertc(actionNode, 'no', -1, 'showChildren');

insertc(actionNode, 'yes', -1, 'expandable');
insertn(actionNode, 510, -1, 'iconOpen');

if iconID=0 then do;
iconID=104;

if suffix='PDF' then iconID=743;
else if suffix='LST' then iconID=124;
else if suffix='SAS' then iconID=995;
else if suffix='LOG' then iconID=992;
else if suffix in('HTM', 'HTML') then iconID=696;
else if suffix='SAS7BDAT' then iconID=212;
else if suffix='XLS' then iconID=782;
else if suffix='DOC' then iconID=384;
end;

insertn(actionNode, iconID, -1, 'iconClosed');

if getnitemn(ndv, nameChild) then
insertl(actionNode, {}, -1, 'children');
endmethod;

nodeParameter3: method;
if listlen(actionNode)=0 then return;
if nodeToggle NE 0 then return;

insertl(rootNodes, copylist(actionNode), -1, getnitemc(ndv, nameKey));
endmethod;

nodeParameter4: method;
if listlen(actionNode)=0 then return;
if nodeToggle EQ 0 then return;

dcl num rc dset parentGroup;
dcl char parentKey;
dcl list targetChildren;

dset=open(nameTree, 'i');
rc=where(dset, nameChild||'='||put(nodeToggle, best.));
if (fetch(dset)=0) then do;
parentGroup=getvarn(dset, varnum(dset, nameGroup));
parentKey =getvarc(dset, varnum(dset, nameKey));
end;
close(dset);

if parentGroup=0 then do;
targetChildren=getniteml(getniteml(rootNodes, parentKey), 'children');
insertl(targetChildren, copylist(actionNode), -1, getnitemc(ndv, nameKey));
insertl(serialNodes, copylist(actionNode), -1, getnitemc(ndv, nameKey));
end;

if parentGroup then do;
targetChildren=getniteml(getniteml(serialNodes, parentKey), 'children');
insertl(targetChildren, copylist(actionNode), -1, getnitemc(ndv, nameKey));
insertl(serialNodes, copylist(actionNode), -1, getnitemc(ndv, nameKey));
end;
endmethod;

nodeChildren: method;
dcl num dset rc;
dcl char thisValue=put(getitemn(groupWork), best.);

dset=open(nameTree, 'i');
rc=where(dset, nameGroup||'='||thisValue||' and '||nameChild||' is not null');
do while (fetch(dset)=0);
insertn(groupWork, getvarn(dset, varnum(dset, nameChild)), -1);
end;
close(dset);
endmethod;

_term: method / (state='o');
clearlist(serialNodes, 'D');
_super();
endmethod;
endclass;

Present the Tree Viewer

class treeview extends sashelp.classes.treeview_c.class;                       
public char title / (state='o', initialValue='');
public list rootNodes / (sendEvent='N');
public list fatNode / (sendEvent='N');
public list recentNode / (sendEvent='N');

public char nameKey / (sendEvent='N', initialValue='keyid');
public char nameText / (sendEvent='N', initialValue='text');
public char nameGroup / (sendEvent='N', initialValue='object_group');
public char nameChild / (sendEvent='N', initialValue='object_child');

_init: method / (state='o');
_super();
_cursor();
_addEventHandler(frameID, 'frame execute', 'runInterface');
_addEventHandler(frameID, 'node changed', 'runInterface');
endmethod;

_popup: method arg1 arg2:num / (state='o');
endmethod;

_onDoubleClick: method arg:object / (state='o');
endmethod;

_onClick: method arg:object / (state='o');
_super(arg);

dcl list gVector=getniteml(getniteml(envlist('G'), 'mpar'), 'config');
dcl list tVector=getniteml(selectedNode, '_ATTRS_');
clearlist(gVector);

if nameditem(selectedNode, '_ATTRS_')=0 then return;
if getnitemn(tVector, 'object_type')=1 then return;

setnitemc(gVector, getnitemc(tVector, 'object_path'), 'object_path');
setnitemc(gVector, getnitemc(tVector, 'text'), 'text');

call goto('montura.r6_cdisccontent.frame.frame');
endmethod;

runInterface: method;
if listlen(rootNodes) then do;
clearlist(rootNodes, 'D');

dcl object rootNode;
_getRoot(rootNode);
_deleteChildren(rootNode);
_delete(rootNode);
end;

fillist('catalog', 'montura.m4_cdisctree.p0000.slist', rootNodes);
_addNodes(0, rootNodes, 'firstchild');
endmethod;

_term: method / (state='o');
dellist(rootNodes, 'Y');

_super();
endmethod;
endclass;

COPYRIGHT © 1989 - 2010 Montura, Inc.
All rights reserved. This material may not be published, broadcast, rewritten or redistributed.

Terms & Conditions -- Privacy Policy