source: extensions/net.sf.basedb.reggie/trunk/resources/samplereportgenerator.jsp @ 1766

Last change on this file since 1766 was 1766, checked in by olle, 10 years ago

Fixes #443. Sample count report generator updated to allow the user to select sample type "no specimen" for the report.

  • Property svn:eol-style set to native
  • Property svn:keywords set to Id
File size: 70.9 KB
Line 
1<%@ page
2  pageEncoding="UTF-8"
3  session="false"
4  import="net.sf.basedb.core.User"
5  import="net.sf.basedb.core.DbControl"
6  import="net.sf.basedb.core.SessionControl"
7  import="net.sf.basedb.core.Application"
8  import="net.sf.basedb.clients.web.Base" 
9  import="net.sf.basedb.clients.web.extensions.ExtensionsControl"
10%>
11<%@ taglib prefix="base" uri="/WEB-INF/base.tld" %>
12<%@ taglib prefix="p" uri="/WEB-INF/path.tld" %>
13<%
14final SessionControl sc = Base.getExistingSessionControl(request, true);
15final String ID = sc.getId();
16final float scale = Base.getScale(sc);
17final String home = ExtensionsControl.getHomeUrl("net.sf.basedb.reggie");
18DbControl dc = null;
19try
20{
21  dc = sc.newDbControl();
22  final User user = User.getById(dc, sc.getLoggedInUserId());
23  %>
24<base:page type="default" >
25<base:head scripts="ajax.js" styles="path.css">
26  <link rel="stylesheet" type="text/css" href="css/reggie.css">
27  <script language="JavaScript" src="reggie.js" type="text/javascript" charset="UTF-8"></script>
28   
29   
30  <script language="JavaScript">
31  var currentStep = 1;
32  var debug = false;
33  var numCols;
34  var unknownSite = 0;
35  var unknownCreation;
36  var numPatientsNoSamples = 0;
37 
38  var month=new Array(12);
39    month[0]="Jan";
40    month[1]="Feb";
41    month[2]="Mar";
42    month[3]="Apr";
43    month[4]="May";
44    month[5]="Jun";
45    month[6]="Jul";
46    month[7]="Aug";
47    month[8]="Sep";
48    month[9]="Oct";
49    month[10]="Nov";
50    month[11]="Dec";
51 
52  var intervalIsValid = true;
53 
54  function goNext()
55  {
56    if (currentStep == 1)
57    {
58      gotoStep2();
59    }
60  }
61 
62  function gotoStep2()
63  {
64    var frm = document.forms['reggie'];
65    frm.reporttype.disabled = true;
66    // Hide report period input fields
67    document.getElementById("reportPeriodSubSection02").style.display = 'none';
68    // Hide sample type pop-up menu
69    document.getElementById("sampleTypeSubSection01").style.display = 'none';
70    document.getElementById("sampleTypeSubSection02").style.display = 'none';
71    document.getElementById("sampleTypeSubSection04").style.display = 'none';
72    if (frm.reporttype[frm.reporttype.selectedIndex].value == 'samplecount')
73    {
74      // Show report period input fields
75      document.getElementById("reportPeriodSubSection01Header").innerHTML="Report period";
76      document.getElementById("reportPeriodSubSection02").style.display = 'block';
77      document.getElementById("reportPeriodSubSection04HelpText").innerHTML="Define which period the report should cover. Empty fields will include all tubes.";
78      // Set item name for report time step text
79      document.getElementById("items02").innerHTML="samples";
80      document.getElementById("items03").innerHTML="samples";
81      document.getElementById("items04").innerHTML="samples";
82      document.getElementById("items05").innerHTML="samples";
83      // Show view type pop-up menu
84      document.getElementById("viewTypeSubSection01").style.display = 'block';
85      document.getElementById("viewTypeSubSection02").style.display = 'block';
86      document.getElementById("viewTypeSubSection04").style.display = 'block';
87      // Show sample type pop-up menu
88      document.getElementById("sampleTypeSubSection01").style.display = 'block';
89      document.getElementById("sampleTypeSubSection02").style.display = 'block';
90      document.getElementById("sampleTypeSubSection04").style.display = 'block';
91    }
92    else if (frm.reporttype[frm.reporttype.selectedIndex].value == 'consentcount')
93    {
94      // Show report period input fields
95      document.getElementById("reportPeriodSubSection01Header").innerHTML="Report period";
96      document.getElementById("reportPeriodSubSection02").style.display = 'block';
97      document.getElementById("reportPeriodSubSection04HelpText").innerHTML="Define which period the report should cover. Empty fields will include all consents.";
98      // Hide view type pop-up menu
99      document.getElementById("viewTypeSubSection01").style.display = 'none';
100      document.getElementById("viewTypeSubSection02").style.display = 'none';
101      document.getElementById("viewTypeSubSection04").style.display = 'none';
102    }
103    else if (frm.reporttype[frm.reporttype.selectedIndex].value == 'patientcount')
104    {
105      // Show report period input fields
106      document.getElementById("reportPeriodSubSection01Header").innerHTML="Report period";
107      document.getElementById("reportPeriodSubSection02").style.display = 'block';
108      document.getElementById("reportPeriodSubSection04HelpText").innerHTML="Define which period the report should cover. Empty fields will include all patients.";
109      // Set item name for report time step text
110      document.getElementById("items02").innerHTML="patients";
111      document.getElementById("items03").innerHTML="patients";
112      document.getElementById("items04").innerHTML="patients";
113      document.getElementById("items05").innerHTML="patients";
114      // Show view type pop-up menu
115      document.getElementById("viewTypeSubSection01").style.display = 'block';
116      document.getElementById("viewTypeSubSection02").style.display = 'block';
117      document.getElementById("viewTypeSubSection04").style.display = 'block';
118    }
119    else if (frm.reporttype[frm.reporttype.selectedIndex].value == 'overviewreport')
120    {
121      // Set parameters (report period) help text
122      document.getElementById("reportPeriodSubSection01Header").innerHTML="No report parameters";
123      document.getElementById("reportPeriodSubSection04HelpText").innerHTML="Overview report will be generated irrespective of date for items.";
124      // Hide view type pop-up menu
125      document.getElementById("viewTypeSubSection01").style.display = 'none';
126      document.getElementById("viewTypeSubSection02").style.display = 'none';
127      document.getElementById("viewTypeSubSection04").style.display = 'none';
128    }
129    Main.show('itemCountSection');
130       
131    Main.show('gocreate');   
132    Main.hide('gonext');
133    frm.fromdate.focus();
134    currentStep = 2;
135  }
136 
137  function dateOnChange()
138  {
139    var frm = document.forms['reggie'];   
140    var fdate;
141    var tdate;
142   
143    intervalIsValid = false;
144    setInputStatus('displayInterval','','valid');
145    if (frm.fromdate.value != null && frm.fromdate.value != '')
146    {
147      frm.fromdate.value = autoFillDate(frm.fromdate.value);     
148      if (!Dates.isDate(frm.fromdate.value, 'yyyyMMdd'))
149      {
150        setInputStatus('displayInterval','Not a valid from-date', 'invalid');
151        return;
152      }
153      else
154      {
155        fdate = frm.fromdate.value;
156        fdate = new Date(fdate.substr(0,4), parseInt(fdate.substr(4,2), 10)-1, fdate.substr(6,2));
157      }
158    }
159   
160    if (frm.todate.value != null && frm.todate.value != '')
161    {
162      frm.todate.value = autoFillDate(frm.todate.value);
163      if (!Dates.isDate(frm.todate.value, 'yyyyMMdd'))
164      {
165        setInputStatus('displayInterval', 'Not a valid to-date', 'invalid');
166        return;
167      }
168      else
169      {
170        tdate = frm.todate.value;
171        tdate = new Date(tdate.substr(0,4), parseInt(tdate.substr(4,2), 10)-1, tdate.substr(6,2));
172      }
173    }
174   
175    if (tdate != null && fdate != null)
176    {
177      if (fdate > tdate)
178      {
179        setInputStatus('displayInterval', 'Invalid period', 'invalid')
180        return;
181      }     
182    }
183    intervalIsValid = true;
184  }
185 
186  function goCreate()
187  {
188    if (!intervalIsValid) return;
189    var cellElement = document.getElementById('reportcell');
190    var frm = document.forms['reggie'];   
191    var reportType = frm.reporttype[frm.reporttype.selectedIndex].value;   
192    frm.fromdate.disabled = true;
193    frm.todate.disabled = true;
194    var sampleType = frm.sampletype[frm.sampletype.selectedIndex].value;   
195    if (reportType == 'samplecount')
196    {
197      frm.viewtype.disabled = true;
198      frm.sampletype.disabled = true;
199    }
200    if (reportType == 'patientcount')
201    {
202      frm.viewtype.disabled = true;
203    }
204    Main.hide('gocreate');
205    Main.show('reportSection');
206    var url = 'SampleReport.servlet?ID=<%=ID%>&cmd='+reportType;   
207   
208    if (frm.fromdate.value != null) url += '&fdate='+frm.fromdate.value;
209    if (frm.todate.value != null) url += '&tdate='+frm.todate.value;
210    if (reportType == 'samplecount')
211    {     
212      if (frm.viewtype.value != null) url += '&vtype='+frm.viewtype.value;
213      if (frm.sampletype.value != null) url += '&stype='+frm.sampletype.value;
214    }
215    if (reportType == 'patientcount')
216    {     
217      if (frm.viewtype.value != null) url += '&vtype='+frm.viewtype.value;
218    }
219   
220    var request = Ajax.getXmlHttpRequest();
221    request.open("GET", url, false);
222    request.send(null);
223   
224    if (debug) Main.debug(request.responseText);   
225    var response = JSON.parse(request.responseText); 
226    if (response.status != 'ok')
227    {
228      setFatalError(response.message);
229      return false;
230    }
231    var report = response.report;
232    var reportTable;
233   
234    if (report != null)
235    {
236      if ('samplecount' == reportType)
237      {     
238        reportTable = createItemCountReport(report, reportType);
239      }
240      else if ('consentcount' == reportType)
241      {     
242        reportTable = createConsentCountReport(report);
243      }
244      else if ('patientcount' == reportType)
245      {     
246        reportTable = createItemCountReport(report, reportType);
247      }
248      else if ('overviewreport' == reportType)
249      {     
250        reportTable = createOverviewReport(report);
251      }
252    }
253    else
254    {
255      var messageCell = getTableCellElement('No values could be found during given period', 'reportheader');
256      var messageRow = document.createElement('tr');
257      messageRow.appendChild(messageCell);     
258      var messageTable = getReportTable();
259      messageTable.appendChild(messageRow);
260      reportTable = messageTable;     
261    }
262    setInnerHTML('reportcell', '');
263    cellElement.appendChild(reportTable);
264    // Optional extra tables
265    if ('consentcount' == reportType)
266    {
267      var spacer = document.createElement('text');
268      spacer.innerHTML = "<BR>";
269      cellElement.appendChild(spacer);
270      var unknownDateTable = createConsentCountUnknownDateTable(report);
271      cellElement.appendChild(unknownDateTable);
272    }
273    else if ('overviewreport' == reportType)
274    {
275      var spacer = document.createElement('text');
276      spacer.innerHTML = "<BR>";
277      cellElement.appendChild(spacer);
278      var patientDetailedTable = createOverviewPatientDetailedTable(report);
279      cellElement.appendChild(patientDetailedTable);
280    }
281    // Summary list
282    var summaryList = document.createElement('ul');
283    if (unknownSite == null) unknownSite = 0;
284    if (unknownCreation == null) unknownCreation = 0;
285    if ('samplecount' == reportType)
286    {
287      var samples = 'specimens';
288      if ('nospecimen' == sampleType)
289      {
290        samples = '"no specimens"';
291      }
292      else if ('blood' == sampleType)
293      {
294        samples = 'blood samples';
295      }
296      summaryList.appendChild(getListElement(unknownSite + ' ' + samples + ' registered to unknown sites.'));
297      summaryList.appendChild(getListElement(unknownCreation + ' ' + samples + ' without creation date. These are included in the \'Total\' column.'));
298    }
299    else if ('consentcount' == reportType)
300    {
301      var numDuplicates = 0;
302      if (report != null)
303      {
304        var statistics = report.statistics;
305        numDuplicates = statistics.duplicateKey;
306      }
307      if (numDuplicates == null)
308      {
309        numDuplicates = 0;
310      }
311      summaryList.appendChild(getListElement(unknownSite + ' consents registered to unknown sites.'));
312      summaryList.appendChild(getListElement(unknownCreation + ' consents without known date. These are included in the \'Total\' column.'));
313      summaryList.appendChild(getListElement(numDuplicates + ' duplicates ignored.'));
314
315      var patientsWithMultipleDates = statistics.patientsWithMultipleDatesKey;
316      var counter = 0;
317      for (var key in patientsWithMultipleDates)
318      {
319        counter++;
320      }
321      var patientsWithMultipleDatesText = counter + ' patients with multiple dates.';
322      summaryList.appendChild(getListElement(patientsWithMultipleDatesText));
323    }
324    else if ('patientcount' == reportType)
325    {
326      summaryList.appendChild(getListElement(unknownSite + ' patients registered to unknown sites.'));
327      summaryList.appendChild(getListElement(unknownCreation + ' patients without creation date. These are included in the \'Total\' column.'));
328    }
329    else if ('overviewreport' == reportType)
330    {
331      summaryList.appendChild(getListElement(unknownSite + ' patients registered to unknown sites.'));
332      summaryList.appendChild(getListElement(numPatientsNoSamples + ' patients with no samples.'));
333      summaryList.appendChild(getListElement('Note: Consents of type "Yes" include consents without patient id (PAT#) or date.'));
334    }
335    cellElement.appendChild(summaryList);
336    if ('consentcount' == reportType)
337    {
338      // Add table with patients with consents with multiple dates
339      var multipleDatesTable = createConsentTablePatientsWithMultipleDates(report);
340      cellElement.appendChild(multipleDatesTable);
341    }
342    Main.show('gorestart');   
343  }
344 
345  function createItemCountReport(report, reportType)
346  {
347    var reportTable = getReportTable();
348    var sdString = report.beginDate;
349    var edString = report.endDate;
350    var psdString = report.periodBeginDate;
351    var ldString = report.latestDate;
352    var startDate = new Date();
353    startDate.setYear(sdString.substr(0,4));
354    startDate.setMonth(sdString.substr(4,2)-1);
355    startDate.setDate(sdString.substr(6));
356    var endDate = new Date();
357    endDate.setYear(edString.substr(0,4));
358    endDate.setMonth(edString.substr(4,2)-1);
359    endDate.setDate(edString.substr(6));
360    var periodStartDate = new Date();
361    periodStartDate.setYear(psdString.substr(0,4));
362    periodStartDate.setMonth(psdString.substr(4,2)-1);
363    periodStartDate.setDate(psdString.substr(6));
364    var latestDate;
365    if (ldString != null)
366    {
367      latestDate = new Date();
368      latestDate.setYear(ldString.substr(0,4));
369      latestDate.setMonth(ldString.substr(4,2)-1);
370      latestDate.setDate(ldString.substr(6));
371    }   
372   
373    var viewType = report.viewType;   
374    var sampleType = report.sampleType;
375 
376    var headerRow = document.createElement('tr');   
377    var subHeaderRowYear = document.createElement('tr');
378    var columnHeaderRow = document.createElement('tr');
379   
380    var headerText = '# Items by ';
381    if ('samplecount' == reportType)
382    {
383      headerText = '# Specimens by ';
384      if ('nospecimen' == sampleType)
385      {
386        headerText = '# "No specimens" by ';
387      }
388      else if ('blood' == sampleType)
389      {
390        headerText = '# Blood samples by ';
391      }
392    }
393    else if ('patientcount' == reportType)
394    {
395      headerText = '# Patients by ';
396    }
397    if (viewType == 'WEEK')
398    {
399      var startWeek = getISOWeekNumber(periodStartDate);
400      var endWeek = getISOWeekNumber(endDate);
401      var tempDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate()-periodStartDate.getDay()+1);
402      numCols = 0;
403      while (tempDate < endDate)
404      {
405        numCols++;
406        tempDate.setDate(tempDate.getDate()+7);
407      }
408      headerText += 'week';
409    }
410    else if (viewType == 'MONTH')
411    {
412      numCols = (endDate.getFullYear()-periodStartDate.getFullYear())*12 + endDate.getMonth()-periodStartDate.getMonth()+1;
413      headerText += 'month';
414    }
415    else if (viewType == 'QUARTER')
416    {
417      // First year (from start quarter to end of year)
418      numCols = 4 - Math.floor(periodStartDate.getMonth()/3);
419      // Last year (from start of year to end quarter) 
420      numCols += Math.floor(endDate.getMonth()/3)+1;
421      // If first and last year is the same, subtract 4 quarters
422      if (endDate.getFullYear() - periodStartDate.getFullYear() == 0)
423      {
424        numCols -= 4;
425      }
426      // Full years between start and end dates
427      if((endDate.getFullYear() - periodStartDate.getFullYear()) > 1)
428      {
429        numCols += 4 * (endDate.getFullYear() - periodStartDate.getFullYear()-1);
430      }
431      headerText += 'quarter';
432    }
433    else
434    {
435      numCols = endDate.getFullYear() - periodStartDate.getFullYear() + 1;
436      headerText += 'year';
437    }
438     
439    // Set table header
440    headerText += ' (between ' + startDate.getFullYear()+'-';
441    if ((startDate.getMonth()+1) < 10)
442    {
443      headerText += '0' + (startDate.getMonth()+1);
444    }
445    else
446    {
447      headerText += (startDate.getMonth()+1);
448    }
449    headerText += '-';
450    if (startDate.getDate() < 10)
451    {
452      headerText += '0' + startDate.getDate();
453    }
454    else
455    {
456      headerText += startDate.getDate();
457    }
458    headerText += ' and ';
459    headerText += endDate.getFullYear()+'-';
460    if ((endDate.getMonth()+1) < 10)
461    {
462      headerText += '0' + (endDate.getMonth()+1);
463    }
464    else
465    {
466      headerText += (endDate.getMonth()+1);
467    }
468    headerText += '-';
469    if (endDate.getDate() < 10)
470    {
471      headerText += '0' + endDate.getDate();
472    }
473    else
474    {
475      headerText += endDate.getDate();
476    }
477    headerText += ')';
478    if (latestDate != null)
479    {
480      headerText += '\nLast registration ' + latestDate.getFullYear();
481      headerText += '-';
482      if ((latestDate.getMonth()+1) < 10)
483      {
484        headerText += '0';
485      }
486      headerText += (latestDate.getMonth()+1);
487      headerText += '-';
488      if (latestDate.getDate()<10)
489      {
490        headerText += '0';
491      }
492      headerText += latestDate.getDate();
493    }   
494    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', (numCols+5)));
495   
496    // Sub headers
497    // Only if each datacol is less then a year
498    if (viewType != 'YEAR')
499    {
500      subHeaderRowYear.appendChild(getTableCellElement('', 'reportsubheader', 3));
501      addYearSubHeaders(periodStartDate, endDate, subHeaderRowYear, viewType);     
502      subHeaderRowYear.appendChild(getTableCellElement('', 'reportsubheader', 2));
503    }   
504         
505    // Columnsheader   
506    var siteHeader = getTableCellElement('Site', 'reportsubheader');     
507    var startDateHeader = getTableCellElement('Start date','reportsubheader');
508    var latestDateHeader = getTableCellElement('Latest date','reportsubheader');
509    columnHeaderRow.appendChild(siteHeader);
510    columnHeaderRow.appendChild(startDateHeader); 
511    columnHeaderRow.appendChild(latestDateHeader); 
512   
513    if (viewType == 'MONTH') addMonthColumnHeaders(columnHeaderRow, periodStartDate);
514    else if (viewType == 'WEEK') addWeekColumnHeaders(columnHeaderRow, periodStartDate);
515    else if (viewType == 'QUARTER') addQuarterColumnHeaders(columnHeaderRow, periodStartDate);
516    else if (viewType == 'YEAR') addYearSubHeaders(periodStartDate, endDate, columnHeaderRow, viewType);
517   
518   
519    columnHeaderRow.appendChild(getTableCellElement('Sum', 'reportsubheader'));
520    columnHeaderRow.appendChild(getTableCellElement('Total', 'reportsubheader'));
521
522    // Build table     
523    reportTable.appendChild(headerRow);
524    reportTable.appendChild(subHeaderRowYear);
525    reportTable.appendChild(columnHeaderRow);
526         
527    // Data rows     
528    addDataRowsToTable(report, reportTable);
529     
530    // Add a row with the combined numbers for all sites for each period
531    var sitesCombinedRow = document.createElement('tr');
532    sitesCombinedRow.appendChild(getTableCellElement('Sites combined', 'colsummary'));
533    sitesCombinedRow.appendChild(getTableCellElement('', 'colsummary', 2));
534    // Get combined numbers for all sites for each period
535    var statistics = report.statistics;
536    var sitesCombined = statistics.sitesCombinedKey;   
537    var sortedKeyArray = createSortedPeriodArray(report, numCols);
538    var key;
539    for (arrayIndex in sortedKeyArray)
540    {
541      key = sortedKeyArray[arrayIndex];
542      var data = getJSONData(sitesCombined, key, 0);
543      // Add entry with sample sum for site for selected time period
544      sitesCombinedRow.appendChild(getTableCellElement(data,'colsummary'));
545    }
546    // Get total number of samples for site for the selected time period
547    var sum = getJSONData(statistics, 'sumKey', 0);
548    // Add entry with total number of samples for site for the selected time period
549    sitesCombinedRow.appendChild(getTableCellElement(sum, 'colsummary'));
550    // Get total number of samples for all sites, regardless of creation date
551    var total = getJSONData(statistics, 'totalKey', 0);
552    // Add entry with total number of samples for all sites, regardless of creation date
553    sitesCombinedRow.appendChild(getTableCellElement(total, 'colsummary'));
554    reportTable.appendChild(sitesCombinedRow); 
555
556    return reportTable;
557  }
558 
559  function createConsentCountReport(report)
560  {
561    var reportTable = getReportTable();
562    var sdString = report.beginDate;
563    var edString = report.endDate;
564/*
565    var psdString = report.periodBeginDate;
566*/
567    var ldString = report.latestDate;
568    var startDate = new Date();
569    startDate.setYear(sdString.substr(0,4));
570    startDate.setMonth(sdString.substr(4,2)-1);
571    startDate.setDate(sdString.substr(6));
572    var endDate = new Date();
573    endDate.setYear(edString.substr(0,4));
574    endDate.setMonth(edString.substr(4,2)-1);
575    endDate.setDate(edString.substr(6));
576/*
577    var periodStartDate = new Date();
578    periodStartDate.setYear(psdString.substr(0,4));
579    periodStartDate.setMonth(psdString.substr(4,2)-1);
580    periodStartDate.setDate(psdString.substr(6));
581*/
582    var latestDate;
583    if (ldString != null)
584    {
585      latestDate = new Date();
586      latestDate.setYear(ldString.substr(0,4));
587      latestDate.setMonth(ldString.substr(4,2)-1);
588      latestDate.setDate(ldString.substr(6));
589    }   
590
591/*   
592    var viewType = report.viewType; 
593*/ 
594 
595    var headerRow = document.createElement('tr');   
596    var subHeaderRow = document.createElement('tr');
597    var columnHeaderRow = document.createElement('tr');
598   
599    var numCols = 5;
600    var numDecimals = 0;
601    var headerText = '# Consent forms of different types for cases and blood samples';
602    var startDateStr = addHyphensToDateString(sdString);
603    var endDateStr = addHyphensToDateString(edString);
604    var latestDateStr = addHyphensToDateString(ldString);
605    headerText += ' (betweeen ' + startDateStr + ' and ' + endDateStr + ')';
606    if (latestDate != null)
607    {
608        headerText += '\nLast registration ' + latestDateStr;
609    }
610    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', (numCols+5)));
611   
612    // Subheader   
613    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 3));
614   
615    subHeaderRow.appendChild(getTableCellElement('Yes', 'reportsubheader'));
616    subHeaderRow.appendChild(getTableCellElement('Yes', 'reportsubheader'));
617    subHeaderRow.appendChild(getTableCellElement('No', 'reportsubheader'));
618    subHeaderRow.appendChild(getTableCellElement('Not asked', 'reportsubheader'));
619    subHeaderRow.appendChild(getTableCellElement('Unknown date', 'reportsubheader'));
620    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 2));
621
622    // Columnsheader   
623    var siteHeader = getTableCellElement('Site', 'reportsubheader');     
624    var startDateHeader = getTableCellElement('Start date','reportsubheader');
625    var latestDateHeader = getTableCellElement('Latest date','reportsubheader');
626    columnHeaderRow.appendChild(siteHeader);
627    columnHeaderRow.appendChild(startDateHeader); 
628    columnHeaderRow.appendChild(latestDateHeader); 
629   
630    columnHeaderRow.appendChild(getTableCellElement('(has PAT#)', 'reportsubheader'));
631    columnHeaderRow.appendChild(getTableCellElement('(no PAT#)', 'reportsubheader'));
632    columnHeaderRow.appendChild(getTableCellElement('(has date)', 'reportsubheader'));
633    columnHeaderRow.appendChild(getTableCellElement('(has date)', 'reportsubheader'));
634    columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
635    columnHeaderRow.appendChild(getTableCellElement('Sum', 'reportsubheader'));
636    columnHeaderRow.appendChild(getTableCellElement('Total', 'reportsubheader'));
637
638    // Build table     
639    reportTable.appendChild(headerRow);
640    reportTable.appendChild(subHeaderRow);
641    reportTable.appendChild(columnHeaderRow);
642         
643    // Data rows     
644    addDataRowsToConsentTable(report, reportTable);
645     
646    // Add a row with the combined numbers for all sites for each period
647    var sitesCombinedRow = document.createElement('tr');
648    sitesCombinedRow.appendChild(getTableCellElement('Sites combined', 'colsummary'));
649    sitesCombinedRow.appendChild(getTableCellElement('', 'colsummary', 2));
650    // Get combined numbers for all sites for each period
651    var noDateKey = 'noDate';
652    var sumKey = 'sumKey';
653    var statistics = report.statistics;
654    var sitesCombined = statistics.sitesCombinedKey;
655    if (sitesCombined != null)
656    {
657      data = getJSONDataWithPercent(sitesCombined, 'yesPatient', sumKey, numDecimals);
658      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
659      data = getJSONDataWithPercent(sitesCombined, 'yesNoPatient', sumKey, numDecimals);
660      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
661      data = getJSONDataWithPercent(sitesCombined, 'no', sumKey, numDecimals);
662      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
663      data = getJSONDataWithPercent(sitesCombined, 'notAsked', sumKey, numDecimals);
664      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
665      data = getJSONDataWithPercent(sitesCombined, noDateKey, sumKey, numDecimals);
666      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
667    }
668    // Add entry with total number of consents with chosen restrictions
669    data = getJSONData(sitesCombined, sumKey, 0);
670    sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
671    // Add entry with total number of consents, regardless of restrictions
672    var totalKey = 'totalKey';
673    data = getJSONData(sitesCombined, totalKey, 0);
674    sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
675    reportTable.appendChild(sitesCombinedRow); 
676
677    return reportTable;
678  }
679 
680  function createConsentCountUnknownDateTable(report)
681  {
682    var reportTable = getReportTable();
683    var headerRow = document.createElement('tr');   
684    var subHeaderRow = document.createElement('tr');
685    var columnHeaderRow = document.createElement('tr');
686   
687    var numCols = 4;
688    var numDecimals = 0;
689    var headerText = '# Consent forms of different types for cases and blood samples, unknown consent date';
690    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', (numCols+5)));
691   
692    // Subheader   
693    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 3));
694   
695    subHeaderRow.appendChild(getTableCellElement('Yes', 'reportsubheader'));
696    subHeaderRow.appendChild(getTableCellElement('No', 'reportsubheader'));
697    subHeaderRow.appendChild(getTableCellElement('Not asked', 'reportsubheader'));
698    subHeaderRow.appendChild(getTableCellElement('Missing', 'reportsubheader'));
699    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 2));
700
701    // Columnsheader   
702    var siteHeader = getTableCellElement('Site', 'reportsubheader');     
703    var startDateHeader = getTableCellElement('Start date','reportsubheader');
704    var latestDateHeader = getTableCellElement('Latest date','reportsubheader');
705    columnHeaderRow.appendChild(siteHeader);
706    columnHeaderRow.appendChild(startDateHeader); 
707    columnHeaderRow.appendChild(latestDateHeader); 
708   
709    columnHeaderRow.appendChild(getTableCellElement('(no date)', 'reportsubheader'));
710    columnHeaderRow.appendChild(getTableCellElement('(no date)', 'reportsubheader'));
711    columnHeaderRow.appendChild(getTableCellElement('(no date)', 'reportsubheader'));
712    columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
713    columnHeaderRow.appendChild(getTableCellElement('Sum', 'reportsubheader'));
714    columnHeaderRow.appendChild(getTableCellElement('Total', 'reportsubheader'));
715
716    // Build table     
717    reportTable.appendChild(headerRow);
718    reportTable.appendChild(subHeaderRow);
719    reportTable.appendChild(columnHeaderRow);
720         
721    // Data rows     
722    addDataRowsToConsentTableUnknownDate(report, reportTable);
723     
724    // Add a row with the combined numbers for all sites
725    var sitesCombinedRow = document.createElement('tr');
726    sitesCombinedRow.appendChild(getTableCellElement('Sites combined', 'colsummary'));
727    sitesCombinedRow.appendChild(getTableCellElement('', 'colsummary', 2));
728    // Get combined numbers for all sites
729    var sumKey = 'sumKey';
730    var statistics = report.statistics;
731    var sitesCombined = statistics.sitesCombinedKey;
732    if (sitesCombined != null)
733    {
734      data = getJSONDataWithPercent(sitesCombined, 'yesNoDate', sumKey, numDecimals);
735      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
736      data = getJSONDataWithPercent(sitesCombined, 'noNoDate', sumKey, numDecimals);
737      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
738      data = getJSONDataWithPercent(sitesCombined, 'notAskedNoDate', sumKey, numDecimals);
739      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
740      data = getJSONDataWithPercent(sitesCombined, 'missing', sumKey, numDecimals);
741      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
742    }
743    // Add entry with total number of consents with chosen restrictions
744    var noDateKey = 'noDate';
745    data = getJSONData(sitesCombined, noDateKey, 0);
746    sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
747    // Add entry with total number of consents, regardless of restrictions
748    var totalKey = 'totalKey';
749    data = getJSONData(sitesCombined, totalKey, 0);
750    sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
751    reportTable.appendChild(sitesCombinedRow); 
752
753    return reportTable;
754  }
755 
756  function createOverviewReport(report)
757  {
758    var reportTable = getReportTable();
759    var sdString = report.beginDate;
760    var edString = report.endDate;
761    var ldString = report.latestDate;
762    var startDate = new Date();
763    startDate.setYear(sdString.substr(0,4));
764    startDate.setMonth(sdString.substr(4,2)-1);
765    startDate.setDate(sdString.substr(6));
766    var endDate = new Date();
767    endDate.setYear(edString.substr(0,4));
768    endDate.setMonth(edString.substr(4,2)-1);
769    endDate.setDate(edString.substr(6));
770    var latestDate;
771    if (ldString != null)
772    {
773      latestDate = new Date();
774      latestDate.setYear(ldString.substr(0,4));
775      latestDate.setMonth(ldString.substr(4,2)-1);
776      latestDate.setDate(ldString.substr(6));
777    }   
778 
779    var headerRow = document.createElement('tr');   
780    var subHeaderRow = document.createElement('tr');
781    var subHeader2Row = document.createElement('tr');
782    var columnHeaderRow = document.createElement('tr');
783   
784    var numCols = 6;
785    var numDecimals = 0;
786    var headerText = 'Number of items of different kinds';
787    var startDateStr = addHyphensToDateString(sdString);
788    var endDateStr = addHyphensToDateString(edString);
789    var latestDateStr = addHyphensToDateString(ldString);
790    headerText += ' (betweeen ' + startDateStr + ' and ' + endDateStr + ')';
791    if (latestDate != null)
792    {
793        headerText += '\nLast registration ' + latestDateStr;
794    }
795    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', (numCols+3)));
796   
797    // Subheader
798    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 3));
799   
800    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
801    subHeaderRow.appendChild(getTableCellElement('Blood', 'reportsubheader'));
802    subHeaderRow.appendChild(getTableCellElement('Specimens', 'reportsubheader'));
803    subHeaderRow.appendChild(getTableCellElement('No specimens', 'reportsubheader'));
804    subHeaderRow.appendChild(getTableCellElement('Consents', 'reportsubheader'));
805    subHeaderRow.appendChild(getTableCellElement('Consents', 'reportsubheader'));
806
807    // Columnsheader   
808    var siteHeader = getTableCellElement('Site', 'reportsubheader');     
809    var startDateHeader = getTableCellElement('Start date','reportsubheader');
810    var latestDateHeader = getTableCellElement('Latest date','reportsubheader');
811    columnHeaderRow.appendChild(siteHeader);
812    columnHeaderRow.appendChild(startDateHeader); 
813    columnHeaderRow.appendChild(latestDateHeader); 
814   
815    columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
816    columnHeaderRow.appendChild(getTableCellElement('samples', 'reportsubheader'));
817    columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
818    columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
819    columnHeaderRow.appendChild(getTableCellElement('(Yes)', 'reportsubheader'));
820    columnHeaderRow.appendChild(getTableCellElement('missing', 'reportsubheader'));
821
822    // Build table     
823    reportTable.appendChild(headerRow);
824    reportTable.appendChild(subHeaderRow);
825    reportTable.appendChild(subHeader2Row);
826    reportTable.appendChild(columnHeaderRow);
827         
828    // Data rows     
829    addDataRowsToOverviewTable(report, reportTable);
830     
831    // Add a row with the combined numbers for all sites for each period
832    var sitesCombinedRow = document.createElement('tr');
833    sitesCombinedRow.appendChild(getTableCellElement('Sites combined', 'colsummary'));
834    sitesCombinedRow.appendChild(getTableCellElement('', 'colsummary', 2));
835    // Get combined numbers for all sites for each period
836    var noDateKey = 'noDate';
837    var sumKey = 'sumKey';
838    var statistics = report.statistics;
839    // Get values for use in summary section
840    numPatientsNoSamples = statistics.patientNoSamples;
841    var sitesCombined = statistics.sitesCombinedKey;
842    if (sitesCombined != null)
843    {
844      data = getJSONData(sitesCombined, 'patient');
845      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
846      data = getJSONData(sitesCombined, 'bloodSample');
847      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
848      data = getJSONData(sitesCombined, 'specimen');
849      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
850      data = getJSONData(sitesCombined, 'noSpecimen');
851      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
852      data = getJSONData(sitesCombined, 'consentYes');
853      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
854      data = getJSONData(sitesCombined, 'consentMissing');
855      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
856    }
857    reportTable.appendChild(sitesCombinedRow); 
858
859    return reportTable;
860  }
861 
862  function createOverviewPatientDetailedTable(report)
863  {
864    var reportTable = getReportTable();
865    var sdString = report.beginDate;
866    var edString = report.endDate;
867    var ldString = report.latestDate;
868    var startDate = new Date();
869    startDate.setYear(sdString.substr(0,4));
870    startDate.setMonth(sdString.substr(4,2)-1);
871    startDate.setDate(sdString.substr(6));
872/*
873    var endDate = new Date();
874    endDate.setYear(edString.substr(0,4));
875    endDate.setMonth(edString.substr(4,2)-1);
876    endDate.setDate(edString.substr(6));
877*/
878    var latestDate;
879    if (ldString != null)
880    {
881      latestDate = new Date();
882      latestDate.setYear(ldString.substr(0,4));
883      latestDate.setMonth(ldString.substr(4,2)-1);
884      latestDate.setDate(ldString.substr(6));
885    }   
886 
887    var headerRow = document.createElement('tr');   
888    var subHeaderRow = document.createElement('tr');
889    var subHeader2Row = document.createElement('tr');
890    var columnHeaderRow = document.createElement('tr');
891   
892    var numCols = 8;
893    var numDecimals = 0;
894    var headerText = 'Patient records of different kinds';
895    var startDateStr = addHyphensToDateString(sdString);
896    var endDateStr = addHyphensToDateString(edString);
897    var latestDateStr = addHyphensToDateString(ldString);
898    headerText += ' (betweeen ' + startDateStr + ' and ' + endDateStr + ')';
899/*
900    if (latestDate != null)
901    {
902        headerText += '\nLast registration ' + latestDateStr;
903    }
904*/
905    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', (numCols+2)));
906   
907    // Subheader
908    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader', 2));
909   
910    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
911    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
912    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
913    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
914    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
915    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
916    subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
917    //subHeaderRow.appendChild(getTableCellElement('Patients', 'reportsubheader'));
918    subHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
919
920    // Subheader 2
921    subHeader2Row.appendChild(getTableCellElement('', 'reportsubheader', 2));
922   
923    subHeader2Row.appendChild(getTableCellElement('(blood', 'reportsubheader'));
924    subHeader2Row.appendChild(getTableCellElement('(spec.', 'reportsubheader'));
925    subHeader2Row.appendChild(getTableCellElement('(no spec.', 'reportsubheader'));
926    subHeader2Row.appendChild(getTableCellElement('(blood and', 'reportsubheader'));
927    subHeader2Row.appendChild(getTableCellElement('(blood and', 'reportsubheader'));
928    subHeader2Row.appendChild(getTableCellElement('(spec. and', 'reportsubheader'));
929    subHeader2Row.appendChild(getTableCellElement('(blood, spec.,', 'reportsubheader'));
930    //subHeader2Row.appendChild(getTableCellElement('(no samples)', 'reportsubheader'));
931    subHeader2Row.appendChild(getTableCellElement('', 'reportsubheader'));
932
933    // Columnsheader   
934    var siteHeader = getTableCellElement('Site', 'reportsubheader');     
935    var startDateHeader = getTableCellElement('Start date','reportsubheader');
936    //var latestDateHeader = getTableCellElement('Latest date','reportsubheader');
937    columnHeaderRow.appendChild(siteHeader);
938    columnHeaderRow.appendChild(startDateHeader); 
939    //columnHeaderRow.appendChild(latestDateHeader); 
940   
941    columnHeaderRow.appendChild(getTableCellElement('only)', 'reportsubheader'));
942    columnHeaderRow.appendChild(getTableCellElement('only)', 'reportsubheader'));
943    columnHeaderRow.appendChild(getTableCellElement('only)', 'reportsubheader'));
944    columnHeaderRow.appendChild(getTableCellElement('specimens)', 'reportsubheader'));
945    columnHeaderRow.appendChild(getTableCellElement('no spec.)', 'reportsubheader'));
946    columnHeaderRow.appendChild(getTableCellElement('no spec.)', 'reportsubheader'));
947    columnHeaderRow.appendChild(getTableCellElement('and no spec.)', 'reportsubheader'));
948    //columnHeaderRow.appendChild(getTableCellElement('', 'reportsubheader'));
949
950    columnHeaderRow.appendChild(getTableCellElement('Sum', 'reportsubheader'));
951
952    // Build table     
953    reportTable.appendChild(headerRow);
954    reportTable.appendChild(subHeaderRow);
955    reportTable.appendChild(subHeader2Row);
956    reportTable.appendChild(columnHeaderRow);
957         
958    // Data rows     
959    addDataRowsToOverviewPatientDetailedTable(report, reportTable);
960     
961    // Add a row with the combined numbers for all sites
962    var sitesCombinedRow = document.createElement('tr');
963    sitesCombinedRow.appendChild(getTableCellElement('Sites combined', 'colsummary'));
964    sitesCombinedRow.appendChild(getTableCellElement('', 'colsummary'));
965    // Get combined numbers for all sites
966    var noDateKey = 'noDate';
967    var sumKey = 'sumKey';
968    var statistics = report.statistics;
969    // Get values for use in summary section
970    numPatientsNoSamples = statistics.patientNoSamples;
971    var sitesCombined = statistics.sitesCombinedKey;
972    if (sitesCombined != null)
973    {
974      data = getJSONData(sitesCombined, 'patientBloodSampleOnly');
975      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
976      data = getJSONData(sitesCombined, 'patientSpecimenOnly');
977      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
978      data = getJSONData(sitesCombined, 'patientNoSpecimenOnly');
979      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
980      data = getJSONData(sitesCombined, 'patientBloodSampleAndSpecimen');
981      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
982      data = getJSONData(sitesCombined, 'patientBloodSampleAndNoSpecimen');
983      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
984      data = getJSONData(sitesCombined, 'patientSpecimenAndNoSpecimen');
985      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
986      data = getJSONData(sitesCombined, 'patientBloodSampleAndSpecimenAndNoSpecimen');
987      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
988      //data = getJSONData(sitesCombined, 'patientNoSamples');
989      //sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
990      data = getJSONData(sitesCombined, 'sumKey');
991      sitesCombinedRow.appendChild(getTableCellElement(data, 'colsummary'));
992    }
993    reportTable.appendChild(sitesCombinedRow); 
994
995    return reportTable;
996  }
997 
998  function addHyphensToDateString(yyyymmddStr)
999  {
1000    var dateWithHyphensStr = '????-??-??';
1001    if (yyyymmddStr != null)
1002    {
1003      var yyyyStr = yyyymmddStr.substr(0,4);
1004      var mmStr   = yyyymmddStr.substr(4,2);
1005      var ddStr = yyyymmddStr.substr(6);
1006      dateWithHyphensStr = yyyyStr + '-' + mmStr + '-' + ddStr;
1007    }
1008    return dateWithHyphensStr;
1009  }
1010
1011  function createConsentTablePatientsWithMultipleDates(report)
1012  {
1013    var multipleDatesTable = getReportTable();
1014    var headerRow = document.createElement('tr');   
1015    var columnHeaderRow = document.createElement('tr');
1016   
1017    // Table header
1018    var numCols = 3;
1019    var headerText = 'Consent forms with multiple dates for same patient';
1020    headerRow.appendChild(getTableCellElement(headerText, 'reportheader', numCols));
1021   
1022    // Columnsheader
1023    columnHeaderRow.appendChild(getTableCellElement('Patient ID', 'reportsubheader'));
1024    columnHeaderRow.appendChild(getTableCellElement('Date 1', 'reportsubheader'));
1025    columnHeaderRow.appendChild(getTableCellElement('Date 2', 'reportsubheader'));
1026
1027    // Build table     
1028    multipleDatesTable.appendChild(headerRow);
1029    multipleDatesTable.appendChild(columnHeaderRow);
1030         
1031    // Data rows
1032    if (report != null)
1033    {
1034      var statistics = report.statistics;
1035      var sessionId = statistics.sessionIdKey;
1036      var patientsWithMultipleDates = statistics.patientsWithMultipleDatesKey;
1037      var patientnamePatientid = statistics.patientnamePatientidKey;
1038      for (var patientName in patientsWithMultipleDates)
1039      {
1040        var tableRow = document.createElement('tr');
1041        // Add patient name to table
1042        var patientIdStr = patientnamePatientid[patientName];
1043        var columnCell = document.createElement('td');
1044        var patientLinkStr = createLinkStr(patientName, patientIdStr, 'BIOSOURCE', 'View this sample', sessionId);
1045        var tableCol = createTableCellElementHtml(patientLinkStr, 'reportdata');
1046        tableRow.appendChild(tableCol);
1047        // Add dates to table in chronological order
1048        var dateSet = patientsWithMultipleDates[patientName];
1049        var dateStr1 = '';
1050        var dateStr2 = '';
1051        for (var key in dateSet)
1052        {
1053          var dateStr = dateSet[key];
1054          if (dateStr1 == '')
1055          {
1056            dateStr1 = dateStr;
1057          }
1058          else if (dateStr > dateStr1)
1059          {
1060            dateStr2 = dateStr;
1061          }
1062          else
1063          {
1064            dateStr2 = dateStr1;
1065            dateStr1 = dateStr;
1066          }
1067        }
1068        var dateCol = '';
1069        dateCol = getTableCellElement(dateStr1, 'reportdata');
1070        tableRow.appendChild(dateCol);
1071        dateCol = getTableCellElement(dateStr2, 'reportdata');
1072        tableRow.appendChild(dateCol);
1073        multipleDatesTable.appendChild(tableRow);
1074      }
1075    }
1076
1077    return multipleDatesTable;
1078  }
1079 
1080  function addDataRowsToConsentTable(report, reportTable, numDecimals)
1081  {
1082    var sites = report.sites;   
1083    var statistics = report.statistics;
1084    unknownCreation = statistics.noDate;
1085    unknownSite = statistics.unknownSite;
1086    var siteOrderList = report.siteOrderListKey;
1087    for (var siteOrderIndex in siteOrderList)
1088    {
1089      var namePrefix = siteOrderList[siteOrderIndex];   
1090      if (!sites.hasOwnProperty(namePrefix)) continue;       
1091      var site = sites[namePrefix];
1092      var siteName = site.name;       
1093      var year = site.startDate.substr(0,4);
1094      var month = site.startDate.substr(5,2);
1095      var date = site.startDate.substr(8,2);     
1096      var siteStartDate = new Date(year, month-1, date);
1097     
1098      var siteData = statistics[namePrefix];     
1099      var siteLatestDate = siteData['latestDateKey'];
1100      var siteLatestDateYear = siteLatestDate.substr(0,4);
1101      var siteLatestDateMonth = siteLatestDate.substr(4,2);
1102      var siteLatestDateDate = siteLatestDate.substr(6,2);
1103      var siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1104      var tableRow = document.createElement('tr');
1105      var tableCol = getTableCellElement(siteName, 'rowtitle');
1106      tableRow.appendChild(tableCol);
1107      tableRow.appendChild(getTableCellElement(year+'-'+(month)+'-'+date, 'reportdata'));
1108      tableRow.appendChild(getTableCellElement(siteLatestDateStr, 'reportdata'));
1109      //var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1110      var noDateKey = 'noDate';
1111      var sumKey = 'sumKey';
1112      var totalKey = 'totalKey';
1113      if (siteData != null)
1114      {
1115        data = getJSONDataWithPercent(siteData, 'yesPatient', sumKey, numDecimals);
1116        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1117        data = getJSONDataWithPercent(siteData, 'yesNoPatient', sumKey, numDecimals);
1118        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1119        data = getJSONDataWithPercent(siteData, 'no', sumKey, numDecimals);
1120        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1121        data = getJSONDataWithPercent(siteData, 'notAsked', sumKey, numDecimals);
1122        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1123        data = getJSONDataWithPercent(siteData, noDateKey, sumKey, numDecimals);
1124        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1125        // Add column with summed values for site
1126        var siteSum = getJSONData(siteData, sumKey, 0);
1127        tableRow.appendChild(getTableCellElement(siteSum, 'rowsummary'));
1128      }
1129      // Add column with total number of samples for site, regardless of creation date
1130      var siteTotal = getJSONData(siteData, totalKey, 0);
1131      tableRow.appendChild(getTableCellElement(siteTotal, 'rowsummary'));
1132      reportTable.appendChild(tableRow);
1133    }
1134  }
1135
1136  function addDataRowsToConsentTableUnknownDate(report, reportTable, numDecimals)
1137  {
1138    var sites = report.sites;   
1139    var statistics = report.statistics;
1140    unknownCreation = statistics.noDate;
1141    unknownSite = statistics.unknownSite;
1142    var siteOrderList = report.siteOrderListKey;
1143    for (var siteOrderIndex in siteOrderList)
1144    {
1145      var namePrefix = siteOrderList[siteOrderIndex];   
1146      if (!sites.hasOwnProperty(namePrefix)) continue;       
1147      var site = sites[namePrefix];
1148      var siteName = site.name;
1149      var year = site.startDate.substr(0,4);
1150      var month = site.startDate.substr(5,2);
1151      var date = site.startDate.substr(8,2);     
1152      var siteStartDate = new Date(year, month-1, date);
1153     
1154      var siteData = statistics[namePrefix];     
1155      var siteLatestDate = siteData['latestDateKey'];
1156      var siteLatestDateYear = siteLatestDate.substr(0,4);
1157      var siteLatestDateMonth = siteLatestDate.substr(4,2);
1158      var siteLatestDateDate = siteLatestDate.substr(6,2);
1159      var siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1160      var tableRow = document.createElement('tr');
1161      var tableCol = getTableCellElement(siteName, 'rowtitle');
1162      tableRow.appendChild(tableCol);
1163      tableRow.appendChild(getTableCellElement(year+'-'+(month)+'-'+date, 'reportdata'));
1164      tableRow.appendChild(getTableCellElement(siteLatestDateStr, 'reportdata'));
1165      //var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1166      var noDateKey = 'noDate';
1167      var sumKey = 'sumKey';
1168      var totalKey = 'totalKey';
1169      if (siteData != null)
1170      {
1171        data = getJSONDataWithPercent(siteData, 'yesNoDate', sumKey, numDecimals);
1172        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1173        data = getJSONDataWithPercent(siteData, 'noNoDate', sumKey, numDecimals);
1174        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1175        data = getJSONDataWithPercent(siteData, 'notAskedNoDate', sumKey, numDecimals);
1176        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1177        data = getJSONDataWithPercent(siteData, 'missing', sumKey, numDecimals);
1178        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1179        // Add column with summed values for site
1180        var siteSum = getJSONData(siteData, noDateKey, 0);
1181        tableRow.appendChild(getTableCellElement(siteSum, 'rowsummary'));
1182      }
1183      // Add column with total number of samples for site, regardless of creation date
1184      var siteTotal = getJSONData(siteData, totalKey, 0);
1185      tableRow.appendChild(getTableCellElement(siteTotal, 'rowsummary'));
1186      reportTable.appendChild(tableRow);
1187    }
1188  }
1189
1190  function addDataRowsToOverviewTable(report, reportTable)
1191  {
1192    var sites = report.sites;   
1193    var statistics = report.statistics;
1194    unknownCreation = statistics.noDate;
1195    unknownSite = statistics.unknownSite;
1196    var siteOrderList = report.siteOrderListKey;
1197    for (var siteOrderIndex in siteOrderList)
1198    {
1199      var namePrefix = siteOrderList[siteOrderIndex];   
1200      if (!sites.hasOwnProperty(namePrefix)) continue;       
1201      var site = sites[namePrefix];
1202      var siteName = site.name;       
1203      var year = site.startDate.substr(0,4);
1204      var month = site.startDate.substr(5,2);
1205      var date = site.startDate.substr(8,2);     
1206      var siteStartDate = new Date(year, month-1, date);
1207     
1208      var siteData = statistics[namePrefix];     
1209      var siteLatestDate = siteData['latestDateKey'];
1210      var siteLatestDateYear = siteLatestDate.substr(0,4);
1211      var siteLatestDateMonth = siteLatestDate.substr(4,2);
1212      var siteLatestDateDate = siteLatestDate.substr(6,2);
1213      var siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1214      var tableRow = document.createElement('tr');
1215      var tableCol = getTableCellElement(siteName, 'rowtitle');
1216      tableRow.appendChild(tableCol);
1217      tableRow.appendChild(getTableCellElement(year+'-'+(month)+'-'+date, 'reportdata'));
1218      tableRow.appendChild(getTableCellElement(siteLatestDateStr, 'reportdata'));
1219      //var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1220      var noDateKey = 'noDate';
1221      var sumKey = 'sumKey';
1222      var totalKey = 'totalKey';
1223      if (siteData != null)
1224      {
1225        data = getJSONData(siteData, 'patient');
1226        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1227        data = getJSONData(siteData, 'bloodSample');
1228        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1229        data = getJSONData(siteData, 'specimen');
1230        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1231        data = getJSONData(siteData, 'noSpecimen');
1232        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1233        data = getJSONData(siteData, 'consentYes');
1234        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1235        data = getJSONData(siteData, 'consentMissing');
1236        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1237      }
1238      reportTable.appendChild(tableRow);
1239    }
1240  }
1241
1242  function addDataRowsToOverviewPatientDetailedTable(report, reportTable)
1243  {
1244    var sites = report.sites;   
1245    var statistics = report.statistics;
1246    unknownCreation = statistics.noDate;
1247    unknownSite = statistics.unknownSite;
1248    var siteOrderList = report.siteOrderListKey;
1249    for (var siteOrderIndex in siteOrderList)
1250    {
1251      var namePrefix = siteOrderList[siteOrderIndex];   
1252      if (!sites.hasOwnProperty(namePrefix)) continue;       
1253      var site = sites[namePrefix];
1254      var siteName = site.name;       
1255      var year = site.startDate.substr(0,4);
1256      var month = site.startDate.substr(5,2);
1257      var date = site.startDate.substr(8,2);     
1258      var siteStartDate = new Date(year, month-1, date);
1259     
1260      var siteData = statistics[namePrefix];
1261/*   
1262      var siteLatestDate = siteData['latestDateKey'];
1263      var siteLatestDateYear = siteLatestDate.substr(0,4);
1264      var siteLatestDateMonth = siteLatestDate.substr(4,2);
1265      var siteLatestDateDate = siteLatestDate.substr(6,2);
1266      var siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1267*/
1268      var tableRow = document.createElement('tr');
1269      var tableCol = getTableCellElement(siteName, 'rowtitle');
1270      tableRow.appendChild(tableCol);
1271      tableRow.appendChild(getTableCellElement(year+'-'+(month)+'-'+date, 'reportdata'));
1272/*
1273      tableRow.appendChild(getTableCellElement(siteLatestDateStr, 'reportdata'));
1274*/
1275      //var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1276      var noDateKey = 'noDate';
1277      var sumKey = 'sumKey';
1278      var totalKey = 'totalKey';
1279      if (siteData != null)
1280      {
1281        data = getJSONData(siteData, 'patientBloodSampleOnly');
1282        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1283        data = getJSONData(siteData, 'patientSpecimenOnly');
1284        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1285        data = getJSONData(siteData, 'patientNoSpecimenOnly');
1286        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1287        data = getJSONData(siteData, 'patientBloodSampleAndSpecimen');
1288        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1289        data = getJSONData(siteData, 'patientBloodSampleAndNoSpecimen');
1290        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1291        data = getJSONData(siteData, 'patientSpecimenAndNoSpecimen');
1292        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1293        data = getJSONData(siteData, 'patientBloodSampleAndSpecimenAndNoSpecimen');
1294        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1295        //data = getJSONData(siteData, 'patientNoSamples');
1296        //tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1297        data = getJSONData(siteData, 'sumKey');
1298        tableRow.appendChild(getTableCellElement(data, 'rowsummary'));
1299      }
1300      reportTable.appendChild(tableRow);
1301    }
1302  }
1303
1304  function createLinkStr(linkName, idStr, itemTypeStr, titleStr, sessionId)
1305  {
1306    var linkStr = '<span class="link" onclick="Main.itemOnClick(event, \'' + sessionId + '\', \'' + itemTypeStr + '\', ' + idStr + ', false)" title="' + titleStr + '">' + linkName + '</span>';
1307    return linkStr;
1308  }
1309
1310  function createTableCellElementHtml(html, clazz, colspan, rowspan)
1311  {
1312    var htmlStr = new String(html);
1313    var cellElement = document.createElement('td');
1314    cellElement.innerHTML = htmlStr;
1315    cellElement.setAttribute('class', clazz);
1316    if (colspan != null) cellElement.setAttribute('colspan', colspan);
1317    if (rowspan != null) cellElement.setAttribute('rowspan', rowspan);
1318   
1319    return cellElement;
1320  }
1321 
1322  function getJSONDataWithPercent(jsonObject, key, sumKey, numDecimals)
1323  {
1324    var dataNum = getJSONData(jsonObject, key);
1325    var dataSum = getJSONData(jsonObject, sumKey);
1326    var dataPct = '0';
1327    if (dataSum != null || dataSum != 0)
1328    {
1329      dataPct = 100*dataNum/dataSum;
1330      dataPct = dataPct.toFixed(numDecimals);
1331    }
1332    var data = dataNum + ' (' + dataPct + '%)';
1333    return data;
1334  }
1335
1336  function getJSONData(jsonObject, key)
1337  {
1338    var data = getJSONData(jsonObject, key, '');
1339    return data;
1340  }
1341
1342  function getJSONData(jsonObject, key, defaultChoice)
1343  {
1344    var data = defaultChoice;
1345    if (jsonObject != null)
1346    {
1347      if (jsonObject[key] != null)
1348      {
1349        data = jsonObject[key];
1350      }
1351    }
1352    /*
1353    else
1354    {
1355      data = 'jsonObject==null';
1356    }
1357    */
1358    return data;
1359  }
1360
1361  function addQuarterColumnHeaders(columnHeaderRow, startDate)
1362  {
1363    var currentDate = startDate;
1364    for (var i=0;i<numCols;i++)
1365    {
1366      var quarter = Math.floor(currentDate.getMonth()/3)+1;
1367      var columnText = 'Q'+quarter;
1368      var quarterHeader = getTableCellElement(columnText, 'reportsubheader');
1369      columnHeaderRow.appendChild(quarterHeader); 
1370      currentDate.setMonth(currentDate.getMonth()+3);     
1371    }
1372  }
1373 
1374  function addWeekColumnHeaders(columnHeaderRow, startDate)
1375  {
1376    var currentDate = startDate;
1377    var day = currentDate.getDay()-1;
1378    day = day>=0 ? day: day + 7;
1379    currentDate.setDate(currentDate.getDate()-day);
1380    for (var i=0;i<numCols;i++)
1381    {     
1382      var weekNum = getISOWeekNumber(currentDate);
1383      var columnText = weekNum;
1384      if (weekNum < 10) columnText = '0'+columnText;     
1385      columnHeaderRow.appendChild(getTableCellElement(columnText, 'reportsubheader'));
1386      currentDate.setDate(currentDate.getDate()+7);     
1387    }
1388  }
1389 
1390  function addMonthColumnHeaders(columnHeaderRow, startDate)
1391  {   
1392    var currentDate = new Date(startDate.getFullYear(), startDate.getMonth());
1393    for (var i=0;i<numCols;i++)
1394    {             
1395      var monthHeader = getTableCellElement(month[currentDate.getMonth()], 'reportsubheader');
1396      columnHeaderRow.appendChild(monthHeader);       
1397      currentDate.setMonth(currentDate.getMonth() +1);
1398    }   
1399  }
1400 
1401  function addYearSubHeaders(startDate, endDate, subHeaderRowYear, vt)
1402  {   
1403    var currentYear = startDate.getFullYear(); 
1404   
1405    var columnCounter = 0;   
1406    do
1407    {
1408      var colspan;
1409      var headerText = currentYear;
1410      if (vt == "MONTH")
1411      {
1412        if (currentYear == startDate.getFullYear())
1413        {
1414          colspan =  11-startDate.getMonth()+1;
1415          if (endDate.getFullYear() == currentYear)
1416          {
1417            colspan = colspan - (11-endDate.getMonth());
1418          }
1419        }
1420        else if (currentYear == endDate.getFullYear()) 
1421          colspan = endDate.getMonth()+1;
1422        else
1423          colspan = 12;
1424      }
1425      else if (vt == "WEEK")
1426      { 
1427        if (startDate.getFullYear() == endDate.getFullYear())
1428        {
1429          colspan = numCols;
1430        }
1431        else if (currentYear == startDate.getFullYear())
1432        {
1433          var startWeek = getISOWeekNumber(startDate);
1434          var lastDay = new Date(startDate.getFullYear(), 11, 31);
1435          var endWeek = getISOWeekNumber(lastDay);
1436          if (endWeek == 1)
1437          {
1438            lastDay.setDate(lastDay.getDate()-7);
1439            endWeek = getISOWeekNumber(lastDay);
1440          }
1441          colspan = endWeek - startWeek +1;
1442        }
1443        else if (currentYear == endDate.getFullYear())
1444        {
1445          var endWeek = getISOWeekNumber(endDate);
1446          colspan = endWeek;
1447        }
1448        else
1449        {
1450          var dateInLastWeek = new Date(currentYear, 11, 31);
1451          var endWeek = getISOWeekNumber(dateInLastWeek);
1452          if (endWeek == 1)
1453          {
1454            dateInLastWeek.setDate(dateInLastWeek.getDate()-7);
1455            endWeek = getISOWeekNumber(dateInLastWeek);
1456          }
1457          colspan = endWeek;
1458        }               
1459      }
1460      else if (vt == "QUARTER")
1461      {
1462        if (currentYear == startDate.getFullYear())
1463        {
1464          if (startDate.getFullYear() == endDate.getFullYear())
1465          {
1466            colspan = Math.floor((endDate.getMonth()-startDate.getMonth())/3)+1;
1467          }
1468          else
1469          {
1470            colspan = Math.floor((11-startDate.getMonth())/3) +1;
1471          }
1472        }
1473        else if(currentYear == endDate.getFullYear())
1474        {
1475          colspan = Math.floor(endDate.getMonth()/3)+1;
1476        }
1477        else 
1478        {
1479          colspan = 4;
1480        }
1481      }
1482      else if (vt == "YEAR")
1483      {
1484        colspan = 1;       
1485      }
1486      columnCounter += colspan;           
1487      subHeaderRowYear.appendChild(getTableCellElement(headerText, 'reportsubheader', colspan));
1488    }while(!(++currentYear>endDate.getFullYear()));
1489  }
1490 
1491  function addDataRowsToTable(report, reportTable)
1492  {
1493    var fdString = report.beginDate;
1494    var ldString = report.endDate;
1495    var psdString = report.periodBeginDate;
1496    var startDate = new Date();
1497    startDate.setYear(fdString.substr(0,4));
1498    startDate.setMonth(fdString.substr(4,2)-1);
1499    startDate.setDate(fdString.substr(6));
1500    var endDate = new Date();
1501    endDate.setYear(ldString.substr(0,4));
1502    endDate.setMonth(ldString.substr(4,2)-1);
1503    endDate.setDate(ldString.substr(6));
1504    var periodStartDate = new Date();
1505    periodStartDate.setYear(psdString.substr(0,4));
1506    periodStartDate.setMonth(psdString.substr(4,2)-1);
1507    periodStartDate.setDate(psdString.substr(6));
1508    var viewType = report.viewType;   
1509    var sites = report.sites;   
1510    var statistics = report.statistics;
1511    unknownCreation = statistics.noDate;
1512    unknownSite = statistics.unknownSite;
1513    var siteOrderList = report.siteOrderListKey;
1514    for (var siteOrderIndex in siteOrderList)
1515    {
1516      var namePrefix = siteOrderList[siteOrderIndex];   
1517      if (!sites.hasOwnProperty(namePrefix)) continue;
1518      var site = sites[namePrefix];
1519      var siteName = site.name;   
1520      var year = site.startDate.substr(0,4);
1521      var month = site.startDate.substr(5,2);
1522      var date = site.startDate.substr(8,2);     
1523      var siteStartDate = new Date(year, month-1, date);
1524     
1525      var siteData = statistics[namePrefix];
1526      var siteLatestDate = siteData['latestDateKey'];
1527      var siteLatestDateStr = '????-??-??';
1528      if (siteLatestDate != null)
1529      {
1530        var siteLatestDateYear = siteLatestDate.substr(0,4);
1531        var siteLatestDateMonth = siteLatestDate.substr(4,2);
1532        var siteLatestDateDate = siteLatestDate.substr(6,2);
1533        siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1534      }
1535/*
1536      var siteLatestDateYear = siteLatestDate.substr(0,4);
1537      var siteLatestDateMonth = siteLatestDate.substr(4,2);
1538      var siteLatestDateDate = siteLatestDate.substr(6,2);
1539      var siteLatestDateStr = siteLatestDateYear + '-' + siteLatestDateMonth + '-' + siteLatestDateDate;
1540*/
1541      var tableRow = document.createElement('tr');
1542      var tableCol = getTableCellElement(siteName, 'rowtitle');
1543      tableRow.appendChild(tableCol);
1544      tableRow.appendChild(getTableCellElement(year+'-'+(month)+'-'+date, 'reportdata'));
1545      tableRow.appendChild(getTableCellElement(siteLatestDateStr, 'reportdata'));
1546      var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1547      var columnCounter = 0;
1548      do
1549      {
1550        var data = 0;
1551        var keyIndex;
1552        var yearIndex = currentDate.getFullYear();
1553       
1554        if (viewType == 'YEAR')
1555        {
1556          keyIndex = yearIndex;
1557          if (siteData != null)
1558          {
1559            if (siteData[keyIndex] != null) data = siteData[keyIndex];
1560          }
1561          if ( (currentDate.getFullYear() < siteStartDate.getFullYear()))
1562          {
1563            data = '';
1564          }
1565          currentDate.setFullYear(currentDate.getFullYear()+1);
1566        }
1567        else if (viewType == 'QUARTER')
1568        {
1569          var qIndex = Math.floor(currentDate.getMonth()/3) + 1;
1570          var startQuarter = Math.floor(siteStartDate.getMonth()/3)+1;
1571          keyIndex = yearIndex + '' + qIndex;
1572          if (siteData != null)
1573          {
1574            if (siteData[keyIndex] != null) data = siteData[keyIndex];           
1575          }         
1576          if ( (currentDate.getFullYear() <= siteStartDate.getFullYear()) && qIndex<startQuarter)
1577          {
1578            data = '';
1579          }
1580          currentDate.setMonth(currentDate.getMonth()+3);         
1581        }
1582        else if (viewType == 'MONTH')
1583        {
1584          var monthIndex = currentDate.getMonth()+1;
1585          var rowFill = monthIndex < 10 ? '0' : '';
1586          keyIndex = yearIndex + rowFill + monthIndex;
1587          if (siteData != null)
1588          {
1589            if (siteData[keyIndex] != null) data = siteData[keyIndex];
1590          }
1591          if (currentDate.getFullYear() <= siteStartDate.getFullYear() && (monthIndex-1) < siteStartDate.getMonth())
1592          {
1593            data = '';
1594          }
1595         
1596         
1597          currentDate.setMonth(currentDate.getMonth()+1);
1598        }
1599        else if (viewType == 'WEEK')
1600        {
1601          var weekIndex = getISOWeekNumber(currentDate);
1602          keyIndex = yearIndex + '' + weekIndex;
1603          if (siteData != null)
1604          {
1605            if (siteData[keyIndex] != null) data = siteData[keyIndex];
1606          }
1607          if (currentDate.getFullYear() <= siteStartDate.getFullYear() && getISOWeekNumber(currentDate) < getISOWeekNumber(siteStartDate))
1608          {
1609            data = '';
1610          }
1611          currentDate.setDate(currentDate.getDate()+7);
1612        }
1613       
1614        tableRow.appendChild(getTableCellElement(data, 'reportdata'));
1615        columnCounter++;       
1616      } while (columnCounter < numCols)
1617      // Add column with sample sum for site for the selected time period
1618      var siteSum = 0;
1619      if (siteData != null)
1620      {
1621        var sumSiteKey = 'sumSiteKey';
1622        if (siteData[sumSiteKey] != null)
1623        {
1624          siteSum = siteData[sumSiteKey];
1625        }
1626      }
1627      tableRow.appendChild(getTableCellElement(siteSum, 'rowsummary'));
1628      // Add column with total number of samples for site, regardless of creation date
1629      var siteTotal = 0;
1630      if (siteData != null)
1631      {
1632        var totalSiteKey = 'totalSiteKey';
1633        if (siteData[totalSiteKey] != null)
1634        {
1635          siteTotal = siteData[totalSiteKey];
1636        }
1637      }
1638      tableRow.appendChild(getTableCellElement(siteTotal, 'rowsummary'));
1639      reportTable.appendChild(tableRow);
1640    }
1641  }
1642 
1643  function createSortedPeriodArray(report, numberOfColumns)
1644  {
1645    var psdString = report.periodBeginDate;
1646    var periodStartDate = new Date();
1647    periodStartDate.setYear(psdString.substr(0,4));
1648    periodStartDate.setMonth(psdString.substr(4,2)-1);
1649    periodStartDate.setDate(psdString.substr(6));
1650    var viewType = report.viewType;   
1651    var sortedPeriodArray = Array(numberOfColumns);
1652    var currentDate = new Date(periodStartDate.getFullYear(), periodStartDate.getMonth(), periodStartDate.getDate());     
1653    var columnCounter = 0;
1654    do
1655    { 
1656      var keyIndex;
1657      var yearIndex = currentDate.getFullYear();
1658       
1659      if (viewType == 'YEAR')
1660      {
1661        keyIndex = yearIndex;
1662        currentDate.setFullYear(currentDate.getFullYear()+1);
1663      }
1664      else if (viewType == 'QUARTER')
1665      {
1666        var qIndex = Math.floor(currentDate.getMonth()/3) + 1;
1667        keyIndex = yearIndex + '' + qIndex;
1668        currentDate.setMonth(currentDate.getMonth()+3);         
1669      }
1670      else if (viewType == 'MONTH')
1671      {
1672        var monthIndex = currentDate.getMonth()+1;
1673        var rowFill = monthIndex < 10 ? '0' : '';
1674        keyIndex = yearIndex + rowFill + monthIndex;
1675        currentDate.setMonth(currentDate.getMonth()+1);
1676      }
1677      else if (viewType == 'WEEK')
1678      {
1679        var weekIndex = getISOWeekNumber(currentDate);
1680        keyIndex = yearIndex + '' + weekIndex;
1681        currentDate.setDate(currentDate.getDate()+7);
1682      }
1683      sortedPeriodArray[columnCounter] = keyIndex;
1684      columnCounter++;       
1685    } while (columnCounter < numberOfColumns)
1686    return sortedPeriodArray;
1687  }
1688 
1689  function getReportTable()
1690  {
1691      var reportTable = document.createElement('table');
1692      reportTable.setAttribute('class','reporttable');
1693      reportTable.setAttribute('border','1');     
1694      return reportTable;
1695  }
1696 
1697  function getTableCellElement(text, clazz, colspan, rowspan)
1698  {
1699    var cellElement = document.createElement('td');
1700    text = new String(text);   
1701    var textArray = text.split("\n");   
1702    if (textArray.length > 1)
1703    {
1704      for (var i=0;i<textArray.length;i++)
1705      {       
1706        if (i>0)cellElement.appendChild(document.createElement('br'));
1707        cellElement.appendChild(document.createTextNode(textArray[i]));
1708      }     
1709    }
1710    else
1711    {
1712      cellElement.appendChild(document.createTextNode(text));
1713    }
1714    cellElement.setAttribute('class', clazz);
1715    if (colspan != null) cellElement.setAttribute('colspan', colspan);
1716    if (rowspan != null) cellElement.setAttribute('rowspan', rowspan);
1717   
1718    return cellElement;
1719  }
1720 
1721  function getListElement(itemText)
1722  {
1723    var listElement = document.createElement('li');
1724    var textNode = document.createTextNode(itemText);
1725    listElement.appendChild(textNode);
1726    return listElement;
1727  }
1728
1729  /*
1730   * Get the ISO week number for a given date
1731   *
1732   * Based on code at http://stackoverflow.com/questions/6117814/get-week-of-year-in-javascript-like-in-php
1733   */
1734  function getISOWeekNumber(date)
1735  {
1736    tmpDate = new Date(date);
1737    tmpDate.setHours(0,0,0);
1738    // Set to nearest Thursday: current date + 4 - current day number
1739    // Make Sunday day number 7
1740    tmpDate.setDate(tmpDate.getDate() + 4 - (tmpDate.getDay() || 7));
1741    // Get first day of year
1742    var yearStart = new Date(tmpDate.getFullYear(), 0, 1);
1743    // Calculate full weeks to nearast Thursday (86400000 = 24*60*60*1000 number of ms in a day)
1744    var weekNo = Math.ceil(( ( (tmpDate - yearStart) / 86400000) + 1)/7);
1745    return weekNo;
1746  }
1747
1748  </script>
1749 
1750 
1751  </base:head>
1752  <base:body onload="init()">
1753    <p:path><p:pathelement 
1754      title="Reggie" href="<%="index.jsp?ID="+ID%>" 
1755      /><p:pathelement title="Report generator" 
1756      /></p:path>
1757    <div class="content">
1758    <%
1759    if (sc.getActiveProjectId() == 0)
1760    {
1761      %>
1762      <div class="messagecontainer note" style="width: 950px; margin-left: 20px; margin-bottom: 20px; margin-right: 0px; font-weight: bold; color: #cc0000;">
1763        No project has been selected. You may proceed with the report generation but
1764        only your own items will be included in the report.
1765      </div>
1766      <%
1767    }
1768    %>
1769 
1770    <form name="reggie" onsubmit="return false;">
1771      <!-- 1. Report type-->
1772      <table border="0" cellspacing="0" cellpadding="0" class="stepform">
1773      <tr>
1774        <td rowspan="3" class="stepno">1</td>
1775        <td class="steptitle">Report type</td>
1776      </tr>
1777      <tr>
1778        <td class="stepfields">
1779          <table border="0" cellspacing="0" cellpadding="0" width="100%">
1780          <tr valign="top">
1781            <td class="prompt">Report</td>
1782            <td class="input">
1783              <select name="reporttype">
1784                <option value="samplecount" selected="yes">Sample count report</option>
1785                <option value="consentcount">Consent count report</option>
1786                <option value="patientcount">Patient count report</option>
1787                <option value="overviewreport">Overview report</option>
1788              </select>
1789            </td>
1790            <td class="status" id="report.status"></td>
1791            <td class="help">
1792              <span id="report.message" class="message" style="display: none;"></span>
1793              Select which report to generate.
1794            </td>
1795          </tr>
1796          </table>
1797        </td>
1798      </tr>
1799      </table>
1800     
1801      <div id="itemCountSection" style="display:none;">
1802        <p></p>
1803        <!-- 2. Report parameters-->
1804        <table border="0" cellspacing="0" cellpadding="0" class="stepform">
1805        <tr>
1806          <td rowspan="3" class="stepno">2</td>
1807          <td class="steptitle">Report parameters</td>
1808        </tr>
1809        <tr>
1810          <td class="stepfields">
1811            <table border="0" cellspacing="0" cellpadding="0" width="100%">           
1812            <tr>
1813              <td valign="top" class="prompt">
1814                <text id="reportPeriodSubSection01Header">Report period</text>
1815              </td>
1816              <td valign="top" class="input">
1817                <div id="reportPeriodSubSection02" style="display:none;">
1818                  From<input type="text" onChange="dateOnChange()" size=7 name="fromdate"/>&nbsp;
1819                  To<input type="text" onChange="dateOnChange()" size=7 name="todate" />
1820                </div>
1821              </td>
1822              <td valign="top" class="status" id="displayInterval.status"></td>
1823              <td class="help">
1824                <span id="displayInterval.message" class="message" style="display: none;"></span>
1825                <!--
1826                Define which period the report should cover. Empty fields will include all <text id="items01">items</text>.<br>
1827                -->
1828                <text id="reportPeriodSubSection04HelpText">Parameter help text</text><br>
1829              </td>
1830            </tr> 
1831            <tr>
1832              <td valign="top" class="prompt">
1833                <div id="viewTypeSubSection01" style="display:none;">
1834                  View type
1835                </div>
1836              </td>
1837              <td valign="top" class="input">
1838                <div id="viewTypeSubSection02" style="display:none;">
1839                  <select name="viewtype">
1840                    <option value="AUTO" selected="yes">Auto</option>
1841                    <option value="WEEK">Week</option>
1842                    <option value="MONTH">Month</option>
1843                    <option value="QUARTER">Quarter</option>
1844                    <option value="YEAR">Year</option>
1845                  </select>
1846                </div>
1847              </td>
1848              <td valign="top" class="status" id="displayViewType.status"></td>
1849              <td class="help">
1850                <div id="viewTypeSubSection04" style="display:none;">
1851                  <span id="displayViewType.message" class="message" style="display: none;"></span>
1852                  Auto will adjust the report depending on the size of the period.
1853                  <ul>
1854                    <li>Period shorter than 3 months - <text id="items02">items</text> per week</li>
1855                    <li>Period shorter than 13 months - <text id="items03">items</text> per month</li>
1856                    <li>Period shorter than 3 years - <text id="items04">items</text> per quarter</li>
1857                    <li>Period is 3 years or greater - <text id="items05">items</text> per year</li>
1858                  </ul>                 
1859                </div>
1860              </td>
1861            </tr>
1862            <tr>
1863              <td valign="top" class="prompt">
1864                <div id="sampleTypeSubSection01" style="display:none;">
1865                  Sample type
1866                </div>
1867              </td>
1868              <td valign="top" class="input">
1869                <div id="sampleTypeSubSection02" style="display:none;">
1870                  <select name="sampletype">
1871                    <option value="specimen" selected="yes">Specimen</option>
1872                    <option value="nospecimen">No specimen</option>
1873                    <option value="blood">Blood</option>
1874                  </select>
1875                </div>
1876              </td>
1877              <td valign="top" class="status" id="displaySampleType.status"></td>
1878              <td class="help">
1879                <div id="sampleTypeSubSection04" style="display:none;">
1880                  <span id="displaySampleType.message" class="message" style="display: none;"></span>
1881                  Select sample type for report.
1882                </div>
1883              </td>
1884            </tr>
1885            </table>
1886          </td>
1887        </tr>
1888        </table>
1889      </div>
1890     
1891      <div id="reportSection" style="display:none;">
1892        <p></p>
1893        <table border="0" cellspacing="0" cellpadding="0" class="stepform">
1894        <tr>
1895          <td rowspan="3" class="stepno">3</td>
1896          <td class="steptitle">Generated report</td>
1897        </tr>
1898        <tr>
1899          <td id="reportcell" class="stepfields">
1900            <i>Generating report...</i>
1901          </td>
1902        </tr>
1903        </table>
1904      </div> 
1905     
1906      <div class="messagecontainer error" id="errorMessage" style="display: none; width: 950px; margin-left: 20px; margin-bottom: 0px;"></div>   
1907       
1908      <table style="margin-left: 20px; margin-top: 10px;" class="navigation">
1909        <tr>
1910          <td><base:button id="gocancel" title="Cancel" onclick="goRestart(false)" style="display: none;"/></td>
1911          <td><base:button id="gonext" title="Next" image="<%=home+"/images/gonext.png"%>" onclick="goNext(true)" /></td>
1912          <td><base:button id="gocreate" title="Generate" image="<%=home+"/images/gonext.png"%>" onclick="goCreate()" style="display: none;"/></td>         
1913          <td><base:button id="gorestart" title="Restart" image="<%=home+"/images/goback.png"%>" onclick="goRestart(true)" style="display: none;"/></td>
1914          <td id="gonext.message" class="message"></td>
1915        </tr>
1916      </table>     
1917    </form>
1918    </div>
1919   
1920  </base:body>
1921  </base:page>
1922  <%
1923}
1924finally
1925{
1926  if (dc != null) dc.close();
1927}
1928%>
Note: See TracBrowser for help on using the repository browser.