home *** CD-ROM | disk | FTP | other *** search
/ Programmer's ROM - The Computer Language Library / programmersrom.iso / ada / manage / tracker.src < prev    next >
Encoding:
Text File  |  1988-05-03  |  446.1 KB  |  13,074 lines

  1. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  2. --calendars.ada
  3. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4. generic
  5.   DAYS_IN_WEEK : positive := 5;
  6.   HOURS_IN_DAY : float := 8.0;
  7.   DAYS_OFF_IN_YEAR : natural := 0;
  8.  
  9. package WORK_CALENDAR is
  10.   subtype YEAR_NUMBER is integer range 1901..2099;
  11.   subtype MONTH_NUMBER is integer range 1..12;
  12.   subtype DAY_NUMBER is integer range 1..31;
  13.   subtype HOUR_NUMBER is float range 0.0..HOURS_IN_DAY;
  14.   type DATE_TYPE is record
  15.     MONTH : month_number;
  16.     DAY : day_number;
  17.     YEAR : year_number;
  18.   end record;
  19.  
  20.   NULL_DATE : constant date_type := (2,31,1902);
  21.   UNDERFLOW_DATE : constant date_type := (2,30,1901);
  22.  
  23.   function "+"  (DATE : in date_type; HOURS : in float) return DATE_TYPE;
  24.   function "+"  (HOURS : in float; DATE : in date_type) return DATE_TYPE;
  25.   function "-"  (DATE : in date_type; HOURS : in float) return DATE_TYPE;
  26.   function "-"  (DATE1, DATE2 : in date_type) return float;
  27.   function "<"  (DATE1, DATE2 : in date_type) return boolean;
  28.   function "<=" (DATE1, DATE2 : in date_type) return boolean;
  29.   function ">"  (DATE1, DATE2 : in date_type) return boolean;
  30.   function ">=" (DATE1, DATE2 : in date_type) return boolean;
  31.   function VALID (MONTH, DAY, YEAR : in integer) return boolean;
  32. end WORK_CALENDAR;
  33. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  34. --calendarb.ada
  35. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  36. with TEXT_IO; use TEXT_IO;
  37. with FLOAT_TEXT_IO; use FLOAT_TEXT_IO;
  38. with INTEGER_TEXT_IO; use INTEGER_TEXT_IO;
  39.  
  40. Package body WORK_CALENDAR is
  41. ----------------------------------------------------------------------
  42. --| NAME: WORK_CALENDAR
  43. --|
  44. --| OVERVIEW:
  45. --|   This package provides functions for manipulating time in a 
  46. --|   work week.  It assumes that the date entered is the last day of
  47. --|   the work week.  This implies that when you are adding hours to a 
  48. --|   date, time for the weekend is added before the time for work.
  49. --|
  50. --| HISTORY:
  51. --|   written by   Bonnie Burkhardt    March 1985
  52. --|
  53. --| EXCEPTIONS HANDLED: 
  54. --|   none
  55. ----------------------------------------------------------------------
  56.  
  57.   DAYS_IN_MONTH : array (1..12) of integer 
  58.     := (31,28,31,30,31,30,31,31,30,31,30,31);
  59.   VACATION_FACTOR : float := float(52 * DAYS_IN_WEEK - DAYS_OFF_IN_YEAR) 
  60.                  / float(52 * DAYS_IN_WEEK);
  61.  
  62.   procedure CALC_DAYS (YEAR : in year_number) is
  63.   begin
  64.     -- check if leap year
  65.     if (YEAR mod 400 = 0) or ((YEAR mod 100 /= 0) and (YEAR mod 4 = 0)) then
  66.       DAYS_IN_MONTH(2) := 29;
  67.     else
  68.       DAYS_IN_MONTH(2) := 28;
  69.     end if;
  70.   end CALC_DAYS;
  71.  
  72.   function "+" (DATE : in date_type; DAY : in integer) return DATE_TYPE is
  73.     TOTAL_DAYS : integer := DATE.day + DAY;
  74.     SUM_DATE : date_type := DATE;
  75.   begin
  76.     loop
  77.       -- check if leap year
  78.       CALC_DAYS(SUM_DATE.year);
  79.       -- compute the final date
  80.       if TOTAL_DAYS <= DAYS_IN_MONTH (SUM_DATE.month) then
  81.     SUM_DATE.day := TOTAL_DAYS;
  82.     return SUM_DATE;
  83.  
  84.       else       -- move into next month
  85.     TOTAL_DAYS := TOTAL_DAYS - DAYS_IN_MONTH (SUM_DATE.month);
  86.     if SUM_DATE.month < 12 then
  87.       SUM_DATE.month := SUM_DATE.month + 1;
  88.     else    -- move into next year
  89.       SUM_DATE.month := 1;
  90.       SUM_DATE.year := SUM_DATE.year + 1;
  91.     end if;
  92.       end if;
  93.     end loop;
  94.   end "+";
  95.  
  96.   function "-" (DATE : in date_type; DAY : in integer) return DATE_TYPE is
  97.     TOTAL_DAYS : integer := DAY;
  98.     DIF_DATE : date_type := DATE;
  99.   begin
  100.     loop
  101.       -- check if leap year
  102.       CALC_DAYS(DIF_DATE.year);
  103.       -- compute the final date
  104.       if DIF_DATE.day - TOTAL_DAYS > 0 then
  105.     DIF_DATE.day := DIF_DATE.day - TOTAL_DAYS;
  106.     return DIF_DATE;
  107.  
  108.       else       -- move into previous month
  109.     TOTAL_DAYS := TOTAL_DAYS - DAYS_IN_MONTH (DIF_DATE.month);
  110.     if DIF_DATE.month > 1 then
  111.       DIF_DATE.month := DIF_DATE.month - 1;
  112.     else     -- move into previous year
  113.       DIF_DATE.month := 12;
  114.       DIF_DATE.year := DIF_DATE.year - 1;
  115.     end if;
  116.     DIF_DATE.day := DAYS_IN_MONTH (DIF_DATE.month);
  117.       end if;
  118.     end loop;
  119.   end "-";
  120.  
  121.   function "+" (DAY : in integer; DATE : in date_type) return DATE_TYPE is
  122.   begin
  123.     return DATE + DAY;
  124.   end "+";
  125.  
  126.  
  127.   function "+" (DATE : in date_type; HOURS : in float) return DATE_TYPE is
  128.     TOTAL_DAYS : integer := 0;
  129.   begin
  130.     -- if the number of hours is negative, add the positive number of hours
  131.     -- to the date
  132.     if HOURS < 0.0 then
  133.       return DATE - (-1.0 * HOURS);
  134.     end if;
  135.     -- calculate the number of days to be added
  136.     -- the next four lines were added instead of the following commented line
  137.     -- TOTAL_DAYS := truncate(HOURS / (HOURS_IN_DAY * VACATION_FACTOR) ) + 1;
  138.     TOTAL_DAYS := integer(HOURS / (HOURS_IN_DAY * VACATION_FACTOR));
  139.     if (HOURS/(HOURS_IN_DAY*VACATION_FACTOR)) > float(TOTAL_DAYS) then
  140.       TOTAL_DAYS := TOTAL_DAYS + 1;
  141.     end if;
  142.     -- plus weekends
  143.     TOTAL_DAYS := TOTAL_DAYS + (7 - DAYS_IN_WEEK) * 
  144.         ( (TOTAL_DAYS - DAYS_IN_WEEK/2) / DAYS_IN_WEEK + 1);  
  145.     -- calculate the final date
  146.     return DATE + TOTAL_DAYS;
  147.   end "+";
  148.  
  149.  
  150.   function "+" (HOURS : in float; DATE : in date_type) return DATE_TYPE is
  151.   begin
  152.     return DATE + HOURS;
  153.   end "+";
  154.  
  155.  
  156.   function "-"  (DATE : in date_type; HOURS : in float) return DATE_TYPE is
  157.     TOTAL_DAYS : integer   := 0;
  158.   begin
  159.     -- if HOURS is negative, add the positive number of hours to the date
  160.     if HOURS < 0.0 then
  161.       return DATE + (-1.0 * HOURS);
  162.     end if;
  163.     -- calculate the number of days to be subtracted
  164.       -- the next four lines were added instead of the following commented line
  165.       -- TOTAL_DAYS := truncate(HOURS / (HOURS_IN_DAY * VACATION_FACTOR) );
  166.     TOTAL_DAYS := integer(HOURS / (HOURS_IN_DAY * VACATION_FACTOR));
  167.     if (HOURS/(HOURS_IN_DAY*VACATION_FACTOR)) < float(TOTAL_DAYS) then
  168.       TOTAL_DAYS := TOTAL_DAYS - 1;
  169.     end if;
  170.     -- add in the days in the weekends
  171.     TOTAL_DAYS := TOTAL_DAYS + (7 - DAYS_IN_WEEK) * 
  172.         (TOTAL_DAYS-1) / DAYS_IN_WEEK;  
  173.     return DATE - TOTAL_DAYS;
  174.   end "-";
  175.  
  176.  
  177.  
  178.   function "-"  (DATE1, DATE2 : in date_type) return FLOAT is
  179.     HOUR     : float     := 0.0;
  180.     DAY      : integer   := 0;
  181.     DATE_1   : date_type := DATE1;
  182.     DATE_2   : date_type := DATE2;
  183.     NEGATIVE : boolean   := false;
  184.   begin
  185.     -- if the subtraction of the dates will result in a negative amount of
  186.     -- hours, switch the dates and attach the negative sign at the end
  187.     if DATE_1 < DATE_2 then
  188.       DATE_1 := DATE2; 
  189.       DATE_2 := DATE1;
  190.       NEGATIVE := true;
  191.     end if;
  192.     -- calculate time difference of years and months in days
  193.     CALC_DAYS (DATE_2.year);
  194.     If DATE_1.year = DATE_2.year and DATE_1.month = DATE_2.month then
  195.       DAY := DATE_1.day - DATE_2.day;
  196.     else
  197.       DAY := DAYS_IN_MONTH(DATE_2.month) - DATE_2.day + 1;
  198.       DATE_2 := DATE_2 + DAY;
  199.       while DATE_1.year /= DATE_2.year or DATE_1.month /= DATE_2.month loop
  200.     CALC_DAYS(DATE_2.year);
  201.     DAY := DAY + DAYS_IN_MONTH(DATE_2.month);
  202.     DATE_2 := DATE_2 + DAYS_IN_MONTH(DATE_2.month);
  203.       end loop;
  204.       DAY := DAY + DATE_1.day - DATE_2.day;
  205.     end if;
  206.     -- subtract out the number of days on the weekend 
  207.     DAY := DAY - (7 - DAYS_IN_WEEK) * ( (DAY - 4) / 7 + 1 ); 
  208.                     -- number of weekends
  209.     -- compute the total difference in hours
  210.     if NEGATIVE then
  211.       return - float(DAY) * HOURS_IN_DAY * VACATION_FACTOR;
  212.     else
  213.       return float(DAY) * HOURS_IN_DAY * VACATION_FACTOR;
  214.     end if;
  215.   end "-";
  216.  
  217.  
  218.   function "<"  (DATE1, DATE2 : in date_type) return boolean is
  219.   begin
  220.     if DATE1.year < DATE2.year then
  221.       return TRUE;
  222.     elsif (DATE1.year = DATE2.year) and (DATE1.month < DATE2.month) then
  223.       return TRUE;
  224.     elsif (DATE1.year = DATE2.year) and (DATE1.month = DATE2.month) and
  225.     (DATE1.day < DATE2.day) then
  226.       return TRUE;
  227.     else
  228.       return FALSE;
  229.     end if;
  230.   end "<";
  231.  
  232.  
  233.   function "<=" (DATE1, DATE2 : in date_type) return boolean is
  234.   begin
  235.     return not (DATE1 > DATE2);
  236.   end "<=";
  237.  
  238.  
  239.   function ">"  (DATE1, DATE2 : in date_type) return boolean is
  240.   begin
  241.     if DATE1.year > DATE2.year then
  242.       return TRUE;
  243.     elsif (DATE1.year = DATE2.year) and (DATE1.month > DATE2.month) then
  244.       return TRUE;
  245.     elsif (DATE1.year = DATE2.year) and (DATE1.month = DATE2.month) and
  246.     (DATE1.day > DATE2.day) then
  247.       return TRUE;
  248.     else
  249.       return FALSE;
  250.     end if;
  251.   end ">";
  252.  
  253.  
  254.   function ">=" (DATE1, DATE2 : in date_type) return boolean is
  255.   begin
  256.     return not (DATE1 < DATE2);
  257.   end ">=";
  258.  
  259.  
  260.   function VALID (MONTH, DAY, YEAR : in integer) return boolean is
  261.   begin
  262.     if YEAR in YEAR_NUMBER and MONTH in MONTH_NUMBER and 
  263.     DAY in DAY_NUMBER then
  264.       CALC_DAYS (YEAR);
  265.       if DAY <= DAYS_IN_MONTH(MONTH) then
  266.         return true;
  267.       end if;
  268.     end if;
  269.     return false;
  270.   end VALID;
  271.  
  272. end WORK_CALENDAR;
  273. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  274. --listpkgs.ada
  275. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  276. generic
  277.   type key is private;    -- private means generic param to be instantiated
  278.   type data is private;
  279.  
  280. package LIST_PKG is
  281.   type list_type is private;
  282.   procedure ADD ( list : in out list_type; rec_key : in key; rec_ptr : in data);
  283.   function EMPTY_LIST( list : in list_type) return boolean;
  284.   procedure START_WALK ( list : in out list_type );
  285.   procedure WALK ( list : in out list_type; rec_ptr : out data;  
  286.                    end_list : out boolean);
  287.   procedure FIND ( list : in out list_type; rec_key : in key; rec_ptr : out data; 
  288.                    found : in out boolean);
  289.   procedure CHANGE_LIST_KEY ( list : in out list_type; old_key : in key;
  290.                      new_key : in key );
  291.   procedure CHANGE_LIST_DATA( list : in out list_type; a_key : in key;
  292.                      new_data : in data );
  293.   procedure DELETE ( list : in out list_type; rec_key : in key; 
  294.                      successful : out boolean);
  295. private
  296.   type list_element;
  297.   type list_ptr is access list_element;
  298.   type list_element is
  299.     record
  300.       search_key  : key;
  301.       rec_data    : data;
  302.       next        : list_ptr;
  303.     end record;
  304.   type list_type is 
  305.     record
  306.       head, tail : list_ptr;
  307.       current_ptr : list_ptr;
  308.       prev_ptr : list_ptr;
  309.     end record;
  310. end LIST_PKG;
  311. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  312. --listpkgb.ada
  313. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  314. with text_io; use text_io;
  315. with unchecked_deallocation;
  316.  
  317. package body LIST_PKG is
  318.  
  319. ----------------------------------------------------------------------
  320. --|  NAME:  LIST_PKG
  321. --|  
  322. --|  OVERVIEW:
  323. --|    This package defines the generic list used for all data types
  324. --|    and the actions that can be performed on them.  In TRACKER, each 
  325. --|    data type will have its own linked list instantiated in the 
  326. --|    respective data package.  The rec_data field is a pointer to
  327. --|    a record of data.
  328. --|
  329. --|    For the generic case, the resulting data structure looks like this:
  330. --||
  331. --||              prev_ptr      current_ptr
  332. --||                  .             .
  333. --||                  |             |
  334. --||                  V             V
  335. --||              _________      _________      _________ <-- tail
  336. --||     head -->|  next +-|--->|  next +-|--->|  next +-|---> null
  337. --||             |_________|    |_________|    |_________|
  338. --||             | rec_key |    | rec_key |    | rec_key |
  339. --||             |_________|    |_________|    |_________|
  340. --||             | rec_data|    | rec_data|    | rec_data|
  341. --||             |_________|    |_________|    |_________|
  342. --||
  343. --|
  344. --|  EXCEPTIONS HANDLED:
  345. --|    none
  346. --|
  347. --|  HISTORY:
  348. --|    written by   May Lee   February 1985
  349. --|
  350. ----------------------------------------------------------------------
  351.  
  352.   procedure FREE is new unchecked_deallocation( list_element, list_ptr);
  353.  
  354.   procedure ADD ( list : in out list_type; 
  355.           rec_key : in key; rec_ptr : in data) is
  356.   ----------------------------------------------------------------------
  357.   --|
  358.   --|  NAME:  ADD
  359.   --|  
  360.   --|  OVERVIEW:
  361.   --|    This procedure adds a new list record onto the end of the
  362.   --|    linked list.  This feature provides a simple method by which
  363.   --|    you could sort the list;  DELETE the list elements in the order
  364.   --|    you want the list to be sorted.  Once you have DELETEd it, ADD it 
  365.   --|    back onto the end of the list.  Loop until the list is sorted.
  366.   --|  
  367.   --|  EXCEPTIONS HANDLED:
  368.   --|    none
  369.   --|
  370.   --|  HISTORY:
  371.   --|    written by   May Lee   February 1985
  372.   --|
  373.   ----------------------------------------------------------------------
  374.  
  375.   temp : list_ptr;
  376.  
  377.   begin
  378.     temp := new list_element;
  379.     temp.search_key := rec_key;
  380.     temp.rec_data := rec_ptr;
  381.     temp.next := null;
  382.     if list.head = null then
  383.       list.head := temp;
  384.       list.tail := temp;
  385.     else
  386.       list.tail.next := temp;
  387.       list.tail := list.tail.next;
  388.       list.tail.next := null;
  389.     end if;
  390.   end ADD;
  391.  
  392.   function EMPTY_LIST( list : in list_type ) return boolean is
  393.   ----------------------------------------------------------------------
  394.   --|
  395.   --|  NAME:  EMPTY_LIST
  396.   --|  
  397.   --|  OVERVIEW:
  398.   --|    This function determines if the list is empty by checking the
  399.   --|    pointer to the head of the list.  If it is null, true is returned.
  400.   --|    Otherwise, the list is not empty.
  401.   --|  
  402.   --|  EXCEPTIONS HANDLED:
  403.   --|    none
  404.   --|
  405.   --|  HISTORY:
  406.   --|    written by   May Lee   March 1985
  407.   --|
  408.   ----------------------------------------------------------------------
  409.   begin
  410.     if list.head = null then  
  411.       return true;
  412.     else
  413.       return false;
  414.     end if;
  415.   end EMPTY_LIST;
  416.  
  417.  
  418.   procedure FIND ( list : in out list_type; rec_key : in key;
  419.                    rec_ptr : out data; found : in out boolean) is
  420.   ----------------------------------------------------------------------
  421.   --|
  422.   --|  NAME:  FIND
  423.   --|  
  424.   --|  OVERVIEW:
  425.   --|    This procedure searches the entire list for a record by the 
  426.   --|    rec_key and returns the record. Found = true if the record 
  427.   --|    is found and false otherwise.  If the record is found, it
  428.   --|    is pointed to by list.current_ptr.
  429.   --|  
  430.   --|  EXCEPTIONS HANDLED:
  431.   --|    none
  432.   --|
  433.   --|  HISTORY:
  434.   --|    written by   May Lee   February 1985
  435.   --|
  436.   ----------------------------------------------------------------------
  437.  
  438.   begin
  439.     -- list.current_ptr points to the current element
  440.     -- If the record is found, it will be referenced by list.current_ptr
  441.     found       := false;
  442.     list.prev_ptr    := null;  -- points to record before the one we want
  443.     list.current_ptr := list.head;
  444.  
  445.     if list.current_ptr = null then  -- empty list, exit procedure
  446.       found := false;
  447.  
  448.     elsif list.current_ptr.search_key = rec_key then  -- check list.head of list
  449.       found   := true;
  450.       rec_ptr := list.current_ptr.rec_data;
  451.  
  452.     else  -- not list.head, search rest of list
  453.       list.prev_ptr    := list.current_ptr;
  454.       list.current_ptr := list.current_ptr.next;
  455.       while not found and list.current_ptr /= null loop
  456.  
  457.         if list.current_ptr.search_key = rec_key then
  458.           found   := true;
  459.           rec_ptr := list.current_ptr.rec_data;
  460.         else
  461.           list.prev_ptr    := list.current_ptr;
  462.           list.current_ptr := list.current_ptr.next;
  463.         end if;
  464.  
  465.       end loop;
  466.     end if;
  467.   end FIND;
  468.  
  469.   procedure CHANGE_LIST_KEY( list : in out list_type; old_key : in key;
  470.                              new_key : in key ) is
  471.   ----------------------------------------------------------------------
  472.   --|
  473.   --|  NAME:  CHANGE_LIST_KEY
  474.   --|  
  475.   --|  OVERVIEW:
  476.   --|    This procedure will change the old_key to the new_key for a list_type.
  477.   --|    Since this is a generic package, the programmer would otherwise
  478.   --|    not be able to access the key directly from the program.
  479.   --|  
  480.   --|  EXCEPTIONS HANDLED:
  481.   --|    none
  482.   --|
  483.   --|  HISTORY:
  484.   --|    written by   May Lee   February 1985
  485.   --|
  486.   ----------------------------------------------------------------------
  487.   found   : boolean;
  488.   rec_ptr : data;
  489.  
  490.   begin
  491.     -- find old key
  492.     FIND ( list, old_key, rec_ptr, found );
  493.     if found then -- change the old_key to the new_key
  494.       list.current_ptr.search_key := new_key;
  495.     end if;
  496.   end CHANGE_LIST_KEY;
  497.  
  498.  
  499.   procedure CHANGE_LIST_DATA( list : in out list_type; a_key : in key;
  500.                              new_data : in data ) is
  501.   ----------------------------------------------------------------------
  502.   --|
  503.   --|  NAME:  CHANGE_LIST_DATA
  504.   --|  
  505.   --|  OVERVIEW:
  506.   --|    This procedure will find a record and change the old_data to
  507.   --|    the new_data for a list type.  Since this is a generic package, 
  508.   --|    the programmer would otherwise not be able to access the data
  509.   --|    directly from the program.
  510.   --|  
  511.   --|  EXCEPTIONS HANDLED:
  512.   --|    none
  513.   --|
  514.   --|  HISTORY:
  515.   --|    written by   May Lee   March 1985
  516.   --|
  517.   ----------------------------------------------------------------------
  518.   found    : boolean;
  519.   old_data : data;
  520.  
  521.   begin
  522.     -- find the record 
  523.     FIND ( list, a_key, old_data, found );
  524.     if found then -- change the data
  525.       list.current_ptr.rec_data := new_data;
  526.     end if;
  527.   end CHANGE_LIST_DATA;
  528.  
  529.  
  530.   procedure DELETE ( list : in out list_type; rec_key : in key; 
  531.                      successful : out boolean) is
  532.   ----------------------------------------------------------------------
  533.   --|
  534.   --|  NAME:  DELETE
  535.   --|  
  536.   --|  OVERVIEW:
  537.   --|    This procedure deletes a record from the linked list by 
  538.   --|    removing the links to that record.  The record is first
  539.   --|    found by calling FIND. If it is found, the record is
  540.   --|    pointed to by list.current_ptr.  The empty list record is
  541.   --|    deallocated by calling FREE.
  542.   --|  
  543.   --|  EXCEPTIONS HANDLED:
  544.   --|    none
  545.   --|
  546.   --|  HISTORY:
  547.   --|    written by   May Lee   February 1985
  548.   --|
  549.   ----------------------------------------------------------------------
  550.  
  551.   found   : boolean := false;  -- if record found in list
  552.   rec_ptr : data;
  553.  
  554.   begin
  555.  
  556.     FIND ( list, rec_key, rec_ptr, found );
  557.     if found then
  558.       if list.prev_ptr = null then     -- delete list.head
  559.         if list.head = list.tail then  -- one element list
  560.           -- after deletion, it is a null list 
  561.           -- list.head and list.tail are null
  562.           FREE( list.head );
  563.           list.head := null;
  564.           list.tail := null;
  565.         else
  566.           list.head := list.head.next;
  567.           FREE( list.current_ptr );
  568.         end if;
  569.  
  570.       else  -- not list.head of list, delete from the middle or end of list
  571.         list.prev_ptr.next := list.current_ptr.next;    
  572.         FREE( list.current_ptr );
  573.         if list.prev_ptr.next = null then -- just deleted the list.tail
  574.           list.tail := list.prev_ptr; -- reassign the list.tail
  575.         end if;
  576.       end if;
  577.  
  578.       successful := true;  -- successfully deleted record
  579.      
  580.     else
  581.       successful := false;  -- record not found, so not deleted
  582.     end if;
  583.   end DELETE;
  584.  
  585.   procedure START_WALK (list : in out list_type) is
  586.   ----------------------------------------------------------------------
  587.   --|
  588.   --|  NAME:  START_WALK
  589.   --|  
  590.   --|  OVERVIEW:
  591.   --|    Start the pointer at the head of the list.
  592.   --|  
  593.   --|  EXCEPTIONS HANDLED:
  594.   --|    none
  595.   --|
  596.   --|  HISTORY:
  597.   --|    written by   May Lee   February 1985
  598.   --|
  599.   ----------------------------------------------------------------------
  600.  
  601.   begin
  602.     list.current_ptr := list.head;
  603.   end START_WALK;
  604.  
  605.   procedure WALK ( list : in out list_type; rec_ptr : out data; 
  606.                    end_list : out boolean) is
  607.   ----------------------------------------------------------------------
  608.   --|
  609.   --|  NAME:  WALK
  610.   --|  
  611.   --|  OVERVIEW:
  612.   --|    This procedure walks a linked list one link at a time, returning
  613.   --|    the contents of that links data in rec_ptr.  It can be used to
  614.   --|    write a linked list to file or to print the contents of the list's
  615.   --|    data.
  616.   --|  
  617.   --|  EXCEPTIONS HANDLED:
  618.   --|    none
  619.   --|
  620.   --|  HISTORY:
  621.   --|    written by   May Lee   February 1985
  622.   --|
  623.   ----------------------------------------------------------------------
  624.   
  625.   begin
  626.     if list.current_ptr = null then
  627.       end_list := true;
  628.     else
  629.       end_list := false;
  630.       rec_ptr := list.current_ptr.rec_data;
  631.       list.current_ptr := list.current_ptr.next;
  632.     end if;
  633.   end WALK;
  634.  
  635. end LIST_PKG;
  636. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  637. --datapkg.ada
  638. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  639. with TEXT_IO; with WORK_CALENDAR; with list_pkg;
  640. use TEXT_IO;
  641.  
  642. package DATA_PKG is
  643. --------------------------------------------------------------------------------
  644. --|  NAME:  DATA_PKG
  645. --|
  646. --|  OVERVIEW:
  647. --|    This package defines the five basic data types used in tracker:
  648. --|    activity, element, milestone, personnel, and subsystem.
  649. --|    Each one is a record with a pointer pointing to that record.
  650. --|    The values for the fields are obtained by prompt/response sessions
  651. --|    with the user.  Milestone, personnel, and subsystem data each have
  652. --|    as a field of their record, a pointer to the element list.  This
  653. --|    field is the list of elements to which that data belongs.  The 
  654. --|    List_Pkg instantiations for each data type is also in this package.
  655. --|
  656. --|    In addition to the data types, this package contains the global
  657. --|    variables used in the Global_Package and the counters for each data
  658. --|    type.
  659. --|
  660. --|    Since most of the other packages with this package, instantiation of
  661. --|    the Calendar_Package and other frequently needed packages is done
  662. --|    in the data package to reduce the number of instantiations throughout
  663. --|    the TRACKER modules.
  664. --|
  665. --|  EXCEPTIONS HANDLED:
  666. --|    none
  667. --|
  668. --|  HISTORY:
  669. --|    written by   May Lee            February 1985
  670. --|    written by   Bonnie Burkhardt   March 1985
  671. --|
  672. --|  NOTES:
  673. --|    The function CONVERT, which is contained in this package, is only
  674. --|    there to correct a quirk in Ada when dealing with enumeration
  675. --|    types that are single characters.  We have declared an enumeration
  676. --|    type act_phase_char_set, which is a subset of the ascii character
  677. --|    set.  This enumeration type must appear with quotes around it when
  678. --|    getting it from a file or a user, and will be printed with quotes
  679. --|    when put to the screen.  We want to be able to declare 1 as a member
  680. --|    of act_phase_char_set, but it is handled literally as '1' (including
  681. --|    the quotes).
  682. --------------------------------------------------------------------------------
  683.  
  684.   -- data constants
  685.   act_name_max_len   : constant natural := 10;
  686.   el_key_max_len     : constant natural :=  6;
  687.   max_num_activities : constant natural := 10;
  688.   pr_name_max_len    : constant natural := 20;
  689.   pr_init_max_len    : constant natural :=  2;
  690.   sub_name_max_len   : constant natural := 10;
  691.  
  692.   package INTEGER_TEXT_IO is new INTEGER_IO(integer); use INTEGER_TEXT_IO;
  693.   package FLOAT_TEXT_IO is new FLOAT_IO(float); use FLOAT_TEXT_IO;
  694.   package BOOLEAN_TEXT_IO is new ENUMERATION_IO(boolean); use BOOLEAN_TEXT_IO;
  695.  
  696.   -- instantiate generic work calendar package
  697.   days_in_work_week     : constant integer := 5;
  698.   hours_in_work_day     : constant float   := 8.0;
  699.   work_days_off_in_year : constant integer := 10;
  700.   package CALENDAR is new WORK_CALENDAR 
  701.     (days_in_work_week, hours_in_work_day, work_days_off_in_year);
  702.   use CALENDAR;
  703.  
  704.   subtype ms_num_type is integer range 1..99;
  705.   subtype pr_init_type is string(1..pr_init_max_len );
  706.   subtype ss_name_type is string(1..sub_name_max_len);
  707.   type act_phase_char_set is 
  708.     ('0','1','2','3','4','5','6','7','8','9',' ','d','D');
  709.   type activity_phase_percent is array(1..10) of act_phase_char_set;
  710.   AC_PCT_VALUE : constant array (act_phase_char_set) of float
  711.     := (0.0,10.0,20.0,30.0,40.0,50.0,60.0,70.0,80.0,90.0,0.0,100.0,100.0);
  712.  
  713.   --  element data type
  714.   subtype el_key_type        is string (1..el_key_max_len);
  715.   type dates_done_type        is array (1..max_num_activities) of date_type;
  716.   type hours_left_type        is array (1..max_num_activities) of float;
  717.   type people_initials_type is array (1..max_num_activities) of pr_init_type;
  718.   type element_type (two_or_more_people : boolean := false);
  719.   type element_pointer        is access element_type;
  720.   type element_type (two_or_more_people : boolean := false) is
  721.     record 
  722.       description           : string(1..35) := (others => ' ');
  723.       desc_key              : el_key_type   := (others => ' ');
  724.       subsystem_name        : ss_name_type  := (others => ' ');
  725.       milestone_num         : ms_num_type := 1;
  726.       priority              : ms_num_type := 1;
  727.       original_size         : integer range 0..99_999 := 0;
  728.       size_done_at_start    : integer range 0..99_999 := 0;
  729.       current_size          : integer range 0..99_999 := 0;
  730.       complexity            : float range 0.1..9.9 := 1.0;
  731.       activity_completeness : activity_phase_percent := (others => ' ');
  732.       hours_to_complete     : float := 0.0;
  733.       date_done             : date_type := null_date;
  734.       prev_date_done        : date_type := null_date;
  735.       date_size_verified    : date_type := null_date;
  736.       more_than_one_person  : boolean := two_or_more_people;
  737.       case two_or_more_people is
  738.         when FALSE =>
  739.       person_initials   : pr_init_type := "  ";
  740.         when TRUE =>
  741.       dates_done        : dates_done_type := (others => null_date);
  742.       hours_left        : hours_left_type := (others => 0.0);
  743.       people_initials   : people_initials_type := (others => "  ");
  744.       end case;      
  745.     end record;
  746.  
  747.   -------------
  748.  
  749.   -- instantiate generic element list handler
  750.   package el_list_pkg is
  751.     new list_pkg (key=> el_key_type, data => element_pointer);
  752.  
  753.   -------------
  754.  
  755.   --  activity phase data
  756.   subtype ac_name_type is string(1..act_name_max_len);
  757.   type activity_type;
  758.   type activity_pointer is access activity_type;
  759.   type activity_type is
  760.     record
  761.       name             : ac_name_type := (others => ' ');
  762.       percent_tot_proj : float range 0.0..100.0 := 0.0;
  763.       priority         : integer range 1..10 := 1;
  764.       consider_in_calc : boolean := true;
  765.       percent_at_start : float range 0.0..100.0 := 0.0;
  766.     end record;
  767.  
  768.   ------------
  769.  
  770.   -- instantiate generic activity list handler
  771.   package ac_list_pkg is
  772.     new list_pkg (key=> ac_name_type, data => activity_pointer);
  773.  
  774.   ------------
  775.  
  776.   --  milestone data type
  777.   type milestone_type;
  778.   type milestone_pointer is access milestone_type;
  779.     type milestone_type    is
  780.     record
  781.       number            : ms_num_type := 1;
  782.       completion_number : ms_num_type := 1;
  783.       due_date          : date_type := null_date;
  784.       description       : string(1..50) := (others => ' ');
  785.       element_list      : el_list_pkg.list_type;
  786.     end record;
  787.  
  788.   ------------
  789.  
  790.   -- instantiate generic milestone list handler
  791.   package ms_list_pkg is
  792.     new list_pkg (key=> ms_num_type, data => milestone_pointer);
  793.  
  794.   ------------
  795.  
  796.   --  personnel data type
  797.   type dates_list is array(1..3) of date_type;
  798.   type personnel_type;
  799.   type personnel_pointer is access personnel_type;
  800.   type personnel_type    is
  801.     record
  802.       name            : string(1..pr_name_max_len ) := (others => ' ');
  803.       initials        : pr_init_type := "  ";
  804.       production_rate : float range 0.01..99.99 := 1.0;
  805.       hours_per_week  : integer range 1..84 := 40;
  806.       start_dates     : dates_list := (others => null_date);
  807.       stop_dates      : dates_list := (others => null_date);
  808.       element_list    : el_list_pkg.list_type;
  809.     end record;
  810.  
  811.   ------------
  812.  
  813.   -- instantiate generic personnel list handler
  814.   package pr_list_pkg is
  815.     new list_pkg (key=> pr_init_type, data => personnel_pointer);
  816.  
  817.   ------------
  818.  
  819.   --  subsystem data type
  820.   type task_numbers_type is array (1..max_num_activities) 
  821.                 of integer range 0..9999;
  822.   type subsystem_type;
  823.   type subsystem_pointer is access subsystem_type;
  824.   type subsystem_type    is
  825.     record
  826.       name            : ss_name_type :=  (others => ' ');
  827.       percent_at_start: float range 0.0..100.0 := 0.0;
  828.       task_numbers    : task_numbers_type := (others => 0);
  829.       element_list    : el_list_pkg.list_type;
  830.     end record;
  831.  
  832.   ------------
  833.  
  834.   -- instantiate generic subsystem list handler
  835.   package ss_list_pkg is
  836.     new list_pkg (key=> ss_name_type, data => subsystem_pointer);
  837.  
  838.   -----------
  839.  
  840.   -- make data lists visible to the report generator
  841.   ac_list : ac_list_pkg.list_type;
  842.   el_list : el_list_pkg.list_type;
  843.   ms_list : ms_list_pkg.list_type;
  844.   pr_list : pr_list_pkg.list_type;
  845.   ss_list : ss_list_pkg.list_type;
  846.  
  847.   -----------
  848.  
  849.   project_name      : string(1..30) := (others => ' ');
  850.   project_number    : integer range 0..999 := 0;
  851.   manager_name      : string(1..30) := (others => ' ');
  852.   date              : date_type := (month => 1, day => 1, year => 1980);
  853.   num_of_activities : integer := 0;
  854.   num_of_elements   : integer := 0;
  855.   num_of_milestones : integer := 0;
  856.   num_of_people     : integer := 0;
  857.   num_of_subsystems : integer := 0;
  858.  
  859.   -----------
  860.  
  861.   function CONVERT (char : character) return act_phase_char_set;
  862.   function CONVERT (quote_char : act_phase_char_set) return character;
  863.  
  864. end DATA_PKG;  
  865.  
  866.  
  867.  
  868. with text_io;  use text_io;
  869. package body DATA_PKG is 
  870.  
  871.   package QUOTE_IO is new ENUMERATION_IO(act_phase_char_set); 
  872.   use QUOTE_IO;
  873.  
  874.   function CONVERT (char : character) return act_phase_char_set is 
  875.     ASTRING : string (1..3) := "' '";
  876.     quote_char : act_phase_char_set := ' ';
  877.     dumb : integer := 1;  -- returns the number of the last char read
  878.   begin
  879.     astring (2) := char;
  880.     -- read astring and return the enumeration value in quote_char 
  881.     get(astring,quote_char,dumb);  
  882.     return quote_char;
  883.   end CONVERT;
  884.  
  885.   function CONVERT (quote_char : act_phase_char_set) return character is 
  886.     ASTRING : string (1..3) := "' '";
  887.     char : character := ' ';
  888.   begin
  889.     -- output the value of quote_char to astring
  890.     put(astring,quote_char);
  891.     char := astring (2);
  892.     return char;
  893.   end CONVERT;
  894.  
  895. end DATA_PKG;
  896. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  897. --vt100s.ada
  898. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  899. with DATA_PKG; use DATA_PKG;
  900. package VT100 is
  901.   print_report : array(1..12) of boolean := (others => false);
  902.   procedure CLEAR_SCREEN;
  903.   function PRINT_REPORT_MENU return integer;
  904.   function PRINT_DATA_MENU return integer;
  905.   function PRINT_GLOBAL_MENU return integer;
  906.   function PRINT_OPERATION_MENU return integer;
  907.   function PRINT_EL_OPERATION_MENU return integer;
  908.   function PRINT_EL_GROUPS return integer;
  909.   function PRINT_AC_MENU (AC_PTR : in activity_pointer)  return integer;
  910.   function PRINT_EL_MENU (EL_PTR : in element_pointer)   return integer;
  911.   function PRINT_MS_MENU (MS_PTR : in milestone_pointer) return integer;
  912.   function PRINT_PR_MENU (PR_PTR : in personnel_pointer) return integer;
  913.   function PRINT_SS_MENU (SS_PTR : in subsystem_pointer) return integer;
  914.   procedure TRACKER_INTRO;
  915.   procedure GOODBYE_MESSAGE;
  916. end VT100;
  917. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  918. --vt100b.ada
  919. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  920. with DATA_PKG; use DATA_PKG;
  921. with text_io; use text_io;
  922.  
  923. package body VT100 is
  924. ----------------------------------------------------------------------
  925. --|
  926. --|  NAME:  VT100
  927. --|
  928. --|  OVERVIEW:
  929. --|    This package maintains actions that affect the screen display.
  930. --|    Various menus can be displayed by passing the appropriate 
  931. --|    parameter to the function PRINT.  The user's selection from
  932. --|    the displayed menu is returned.
  933. --|
  934. --|  EXCEPTIONS HANDLED:
  935. --|    none
  936. --|
  937. --|  HISTORY:
  938. --|    written by   May Lee   March 1985
  939. --|  
  940. ----------------------------------------------------------------------
  941.  
  942.   use CALENDAR;
  943.   use FLOAT_TEXT_IO;
  944.   use INTEGER_TEXT_IO;
  945.   use BOOLEAN_TEXT_IO;
  946.  
  947.   response : integer;
  948.  
  949.   procedure CLEAR_SCREEN     is separate;
  950.   function PRINT_REPORT_MENU       return integer is separate;
  951.   function PRINT_DATA_MENU         return integer is separate;
  952.   function PRINT_GLOBAL_MENU       return integer is separate;
  953.   function PRINT_OPERATION_MENU    return integer is separate;
  954.   function PRINT_EL_OPERATION_MENU return integer is separate;
  955.   function PRINT_EL_GROUPS         return integer is separate;
  956.   function PRINT_AC_MENU (AC_PTR : in activity_pointer)  return integer 
  957.     is separate;
  958.   function PRINT_EL_MENU (EL_PTR : in element_pointer)   return integer
  959.     is separate;
  960.   function PRINT_MS_MENU (MS_PTR : in milestone_pointer) return integer
  961.     is separate;
  962.   function PRINT_PR_MENU (PR_PTR : in personnel_pointer) return integer
  963.     is separate;
  964.   function PRINT_SS_MENU (SS_PTR : in subsystem_pointer) return integer
  965.     is separate;
  966.   procedure TRACKER_INTRO       is separate;
  967.   procedure GOODBYE_MESSAGE     is separate;
  968.  
  969. end VT100;
  970.  
  971.   separate( VT100 )
  972.   procedure CLEAR_SCREEN is
  973.   ----------------------------------------------------------------------
  974.   --|
  975.   --|  NAME:  CLEAR_SCREEN
  976.   --|
  977.   --|  OVERVIEW:
  978.   --|    This procedure clears the screen on a vt100 using an escape code
  979.   --|    sequence.
  980.   --|
  981.   --|  EXCEPTIONS HANDLED:
  982.   --|    none
  983.   --|
  984.   --|  HISTORY:
  985.   --|    written by   May Lee   March 1985
  986.   --|  
  987.   ----------------------------------------------------------------------
  988.     escape : constant character := ascii.esc;
  989.     l_bracket : constant character := ascii.l_bracket;
  990.     clear_screen  : string(1..80);
  991.   begin
  992.     put(escape);
  993.     put(l_bracket);
  994.     put('H');
  995.     put(escape);
  996.     put(l_bracket);
  997.     put('J');
  998.   end CLEAR_SCREEN;
  999.  
  1000.     separate( VT100 )
  1001.     function PRINT_REPORT_MENU return integer is
  1002.     ----------------------------------------------------------------------
  1003.     --|
  1004.     --|  NAME:  PRINT_REPORT_MENU
  1005.     --|
  1006.     --|  OVERVIEW:
  1007.     --|    The report menu consists of the various reports a user is allowed
  1008.     --|    to print.
  1009.     --|
  1010.     --|  EXCEPTIONS HANDLED:
  1011.     --|    others   the user is reprompted
  1012.     --|
  1013.     --|  HISTORY:
  1014.     --|    written by   May Lee   March 1985
  1015.     --|  
  1016.     ----------------------------------------------------------------------
  1017.  
  1018.     begin
  1019.       loop
  1020.         begin
  1021.           CLEAR_SCREEN;
  1022.           put_line("                         REPORT  MENU  ");
  1023.           put_line("==============================================================");
  1024.           new_line;
  1025.           put_line("Choose the number of the report that you would like generated.");
  1026.           put_line("  The star(s) indicate that you have already requested that ");
  1027.           put_line("  report to be generated.  ");
  1028.           new_line(2);
  1029.  
  1030.           if print_report(1) then
  1031.             put_line("        *  1)  Parameter Data List");
  1032.           else
  1033.             put_line("           1)  Parameter Data List");
  1034.           end if;
  1035.  
  1036.           if print_report(2) then
  1037.             put_line("        *  2)  Comments File ");
  1038.           else
  1039.             put_line("           2)  Comments File ");
  1040.           end if;
  1041.  
  1042.           if print_report(3) then
  1043.             put_line("        *  3)  All Element Status Report");
  1044.           else
  1045.             put_line("           3)  All Element Status Report");
  1046.           end if;
  1047.  
  1048.           if print_report(4) then
  1049.             put_line("        *  4)  List By Subsystem");
  1050.           else
  1051.             put_line("           4)  List By Subsystem");
  1052.           end if;
  1053.  
  1054.           if print_report(5) then
  1055.             put_line("        *  5)  List By Milestone   ");
  1056.           else
  1057.             put_line("           5)  List By Milestone   ");
  1058.           end if;
  1059.  
  1060.           if print_report(6) then
  1061.             put_line("        *  6)  List By Person");
  1062.           else
  1063.             put_line("           6)  List By Person");
  1064.           end if;
  1065.  
  1066.           if print_report(7) then
  1067.             put_line("        *  7)  Subsystem Summary");
  1068.           else
  1069.             put_line("           7)  Subsystem Summary");
  1070.           end if;
  1071.  
  1072.           if print_report(8) then
  1073.             put_line("        *  8)  Milestone Summary");
  1074.           else
  1075.             put_line("           8)  Milestone Summary");
  1076.           end if;
  1077.  
  1078.           if print_report(9) then
  1079.             put_line("        *  9)  Work Units Per Subsystem ");
  1080.           else
  1081.             put_line("           9)  Work Units Per Subsystem ");
  1082.           end if;
  1083.  
  1084.           if print_report(10) then
  1085.             put_line("        * 10)  Percent Completion Of Work Within Subsystem ");
  1086.           else
  1087.             put_line("          10)  Percent Completion Of Work Within Subsystem ");
  1088.           end if;
  1089.  
  1090.           if print_report(11) then
  1091.             put_line("        * 11)  Distribution Of Remaining Work Within Subsystems");
  1092.           else
  1093.             put_line("          11)  Distribution Of Remaining Work Within Subsystems");
  1094.           end if;
  1095.   
  1096.           if print_report(12) then
  1097.             put_line("        * 12)  Completion Date For Milestones");
  1098.           else
  1099.             put_line("          12)  Completion Date For Milestones");
  1100.           end if;
  1101.  
  1102.           put_line("          13)  All Of The Above and EXIT ");
  1103.           new_line;
  1104.  
  1105.           put_line("          14)  EXIT FROM TRACKER ");
  1106.  
  1107.           get(response); 
  1108.           skip_line;
  1109.           return response;
  1110.         exception
  1111.           when others =>
  1112.             skip_line;
  1113.            new_line;
  1114.         put_line(" Please enter a number between 1 and 14. ");
  1115.             delay 1.0;
  1116.         end;
  1117.       end loop;
  1118.     end PRINT_REPORT_MENU;
  1119.  
  1120.  
  1121.     separate( VT100 )
  1122.     function PRINT_DATA_MENU return integer is
  1123.     ----------------------------------------------------------------------
  1124.     --|
  1125.     --|  NAME:  PRINT_DATA_MENU
  1126.     --|
  1127.     --|  OVERVIEW:
  1128.     --|    This procedure displays the different types of data that can be
  1129.     --|    manipulated.
  1130.     --|
  1131.     --|  EXCEPTIONS HANDLED:
  1132.     --|    others   the user is reprompted
  1133.     --|
  1134.     --|  HISTORY:
  1135.     --|    written by   May Lee   March 1985
  1136.     --|  
  1137.     ----------------------------------------------------------------------
  1138.   
  1139.     begin
  1140.       loop
  1141.         begin
  1142.           CLEAR_SCREEN;
  1143.           put_line("                      DATA  MENU  ");
  1144.           put_line("=======================================================");
  1145.           new_line(3); 
  1146.           put_line("Choose the number of one of the following data types ");
  1147.           put_line("that you would like to manipulate: ");
  1148.           new_line(2);
  1149.           put_line("           1)  Global       ");
  1150.           put_line("           2)  Activity     ");
  1151.           put_line("           3)  Personnel    ");
  1152.           put_line("           4)  Milestones   ");
  1153.           put_line("           5)  Subsystem    ");
  1154.           put_line("           6)  Element      ");
  1155.           new_line;
  1156.           put_line("           7)  Done With Data - EXIT from Data Menu");
  1157.  
  1158.           get(response);
  1159.           skip_line;
  1160.            new_line(2);
  1161.           return response;
  1162.         exception
  1163.           when others =>
  1164.             skip_line;
  1165.            new_line;
  1166.         put_line(" Please enter a number between 1 and 7. ");
  1167.             delay 1.0;
  1168.         end;
  1169.       end loop;
  1170.     end PRINT_DATA_MENU;
  1171.  
  1172.  
  1173.     separate( VT100 )
  1174.     function PRINT_GLOBAL_MENU return integer is
  1175.     ----------------------------------------------------------------------
  1176.     --|
  1177.     --|  NAME:  PRINT_GLOBAL_MENU
  1178.     --|
  1179.     --|  OVERVIEW:
  1180.     --|    This procedure displays the global variables that can be manipulated.
  1181.     --|
  1182.     --|  EXCEPTIONS HANDLED:
  1183.     --|    others   the user is reprompted
  1184.     --|
  1185.     --|  HISTORY:
  1186.     --|    written by   May Lee   March 1985
  1187.     --|  
  1188.     ----------------------------------------------------------------------
  1189.     begin
  1190.       loop
  1191.         begin
  1192.           CLEAR_SCREEN;
  1193.           put_line("                    GLOBAL  DATA  MENU  ");
  1194.           put_line("=======================================================");
  1195.           new_line(3); 
  1196.           put_line("Choose the number of one of the following global ");
  1197.           put_line("variables that you would like to modify: ");
  1198.           new_line(2); 
  1199.           put(" 1)  Project Name            "); put(project_name); new_line;
  1200.           put(" 2)  Project Number          "); put(project_number,3); new_line;
  1201.           put(" 3)  Project Manager's Name  "); put(manager_name); new_line;
  1202.           put(" 4)  Date the TRACKER Run is Valid for  ");
  1203.           if date = null_date then
  1204.             put(" null date ");
  1205.           else
  1206.             put( date.month,2 ); put("/");
  1207.             put( date.day  ,2 ); put("/");
  1208.             put( date.year ,4 );
  1209.           end if;
  1210.           new_line(2);
  1211.           put_line(" 5)  Done With Data - EXIT from Global Data Menu");
  1212.  
  1213.           get(response);
  1214.           skip_line;
  1215.           new_line(2);
  1216.           return response;
  1217.         exception
  1218.           when others =>
  1219.             skip_line;
  1220.            new_line;
  1221.         put_line(" Please enter a number between 1 and 5. ");
  1222.             delay 1.0;
  1223.         end;
  1224.       end loop;
  1225.     end PRINT_GLOBAL_MENU;
  1226.  
  1227.  
  1228.     separate( VT100 )
  1229.     function PRINT_OPERATION_MENU return integer is
  1230.     ----------------------------------------------------------------------
  1231.     --|
  1232.     --|  NAME:  PRINT_OPERATION_MENU
  1233.     --|
  1234.     --|  OVERVIEW:
  1235.     --|    This procedure displays the operations that can be performed on
  1236.     --|    a data type.
  1237.     --|
  1238.     --|  EXCEPTIONS HANDLED:
  1239.     --|    others   the user is reprompted
  1240.     --|
  1241.     --|  HISTORY:
  1242.     --|    written by   May Lee   March 1985
  1243.     --|  
  1244.     ----------------------------------------------------------------------
  1245.     begin
  1246.       loop
  1247.         begin
  1248.           CLEAR_SCREEN;
  1249.           put_line("                 OPERATIONS  MENU  ");
  1250.           put_line("=======================================================");
  1251.           new_line(3); 
  1252.       put_line("Choose the number of one of the following operations ");
  1253.           put_line("that you would like to perform: ");
  1254.           new_line(2); 
  1255.           put_line("           1)  Add          ");
  1256.           put_line("           2)  Delete       ");
  1257.           put_line("           3)  Modify       ");
  1258.           put_line("           4)  Display the Current Data");
  1259.           new_line;
  1260.           put_line("           5)  Done With Data - EXIT from Operations Menu");
  1261.  
  1262.           get(response);
  1263.           skip_line;
  1264.           new_line(2);
  1265.           return response;
  1266.         exception
  1267.           when others =>
  1268.             skip_line;
  1269.            new_line;
  1270.         put_line(" Please enter a number between 1 and 5. ");
  1271.             delay 1.0;
  1272.         end;
  1273.       end loop;
  1274.     end PRINT_OPERATION_MENU;
  1275.  
  1276.  
  1277.     separate( VT100 )
  1278.     function PRINT_EL_OPERATION_MENU return integer is
  1279.     ----------------------------------------------------------------------
  1280.     --|
  1281.     --|  NAME:  PRINT_EL_OPERATION_MENU
  1282.     --|
  1283.     --|  OVERVIEW:
  1284.     --|    This procedure displays the operations that can be performed on
  1285.     --|    an element data type.
  1286.     --|
  1287.     --|  EXCEPTIONS HANDLED:
  1288.     --|    others   the user is reprompted
  1289.     --|
  1290.     --|  HISTORY:
  1291.     --|    written by   May Lee   March 1985
  1292.     --|  
  1293.     ----------------------------------------------------------------------
  1294.     begin
  1295.       loop
  1296.         begin
  1297.           CLEAR_SCREEN;
  1298.           put_line("             ELEMENT DATA OPERATIONS  MENU  ");
  1299.           put_line("=======================================================");
  1300.           new_line(3); 
  1301.       put_line("Choose the number of one of the following operations ");
  1302.           put_line("that you would like to perform: ");
  1303.           new_line(2); 
  1304.           put_line("        1)  Add          ");
  1305.           put_line("        2)  Delete       ");
  1306.           put_line("        3)  Modify       ");
  1307.           put_line("        4)  Display the Current Data");
  1308.           put_line("        5)  Quick Update of the Current Size");
  1309.           put_line("        6)  Quick Update of the Activity Percent Complete");
  1310.           new_line;
  1311.           put_line("        7)  Done With Data - EXIT from Operations Menu");
  1312.  
  1313.           get(response);
  1314.           skip_line;
  1315.           new_line(2);
  1316.           return response;
  1317.         exception
  1318.           when others =>
  1319.             skip_line;
  1320.            new_line;
  1321.         put_line(" Please enter a number between 1 and 7. ");
  1322.             delay 1.0;
  1323.         end;
  1324.       end loop;
  1325.     end PRINT_EL_OPERATION_MENU;
  1326.  
  1327.  
  1328.  
  1329.     separate( VT100 )
  1330.     function PRINT_EL_GROUPS         return integer is 
  1331.     ----------------------------------------------------------------------
  1332.     --|
  1333.     --|  NAME:  PRINT_EL_GROUPS
  1334.     --|
  1335.     --|  OVERVIEW:
  1336.     --|    This procedure displays the different groups of element data that
  1337.     --|    can be updated with the quick update.
  1338.     --|
  1339.     --|  EXCEPTIONS HANDLED:
  1340.     --|    others   the user is reprompted
  1341.     --|
  1342.     --|  HISTORY:
  1343.     --|    written by   May Lee   March 1985
  1344.     --|  
  1345.     ----------------------------------------------------------------------
  1346.     begin
  1347.       loop
  1348.         begin
  1349.           CLEAR_SCREEN;
  1350.           put_line("               ELEMENT DATA GROUPS MENU  ");
  1351.           put_line("=======================================================");
  1352.           new_line(3); 
  1353.       put_line("Choose the number of one of the following groups of");
  1354.           put_line("element data that you would like do a quick update on : ");
  1355.           new_line(2); 
  1356.           put_line("           1)  All Elements  ");
  1357.           put_line("           2)  Elements belonging to a Milestone ");
  1358.           put_line("           3)  Elements belonging to a Person    ");
  1359.           put_line("           4)  Elements belonging to a Subsystem ");
  1360.           new_line;
  1361.           put_line("           5)  Done With Data - EXIT from Operations Menu");
  1362.  
  1363.           get(response);
  1364.           skip_line;
  1365.           new_line(2);
  1366.           return response;
  1367.         exception
  1368.           when others =>
  1369.             skip_line;
  1370.            new_line;
  1371.         put_line(" Please enter a number between 1 and 5. ");
  1372.             delay 1.0;
  1373.         end;
  1374.       end loop;
  1375.     end PRINT_EL_GROUPS;
  1376.  
  1377.  
  1378. separate( VT100 )
  1379. function PRINT_AC_MENU (AC_PTR : in activity_pointer) return integer is
  1380. ----------------------------------------------------------------------
  1381. --|
  1382. --|  NAME:  PRINT_AC_MENU
  1383. --|
  1384. --|  OVERVIEW:
  1385. --|    This procedure displays the fields that can be changed on 
  1386. --|    an activity type.
  1387. --|
  1388. --|  EXCEPTIONS HANDLED:
  1389. --|    others   the user is reprompted
  1390. --|
  1391. --|  HISTORY:
  1392. --|    written by   May Lee   March 1985
  1393. --|  
  1394. ----------------------------------------------------------------------
  1395. begin
  1396.   loop
  1397.     begin
  1398.       CLEAR_SCREEN;
  1399.       put_line("                  ACTIVITY  DATA  MENU  ");
  1400.       put_line("==========================================================");
  1401.       new_line(3); 
  1402.       put_line("Choose the number of one of the following activity fields ");
  1403.       put_line("that you would like to modify: ");
  1404.       new_line(2); 
  1405.       put(" 1)  Activity Name                    "); put(ac_ptr.name); 
  1406.       new_line;
  1407.       put(" 2)  Percentage of the Total Project  ");
  1408.         put(ac_ptr.percent_tot_proj, 3, 1, 0 ); put("%"); new_line;
  1409.       put(" 3)  Priority                          "); put(ac_ptr.priority, 2);
  1410.       new_line;
  1411.       put(" 4)  Consider In Calculations         "); 
  1412.         put(ac_ptr.consider_in_calc); new_line;
  1413.       put(" 5)  Percent At Start                 "); 
  1414.         put(ac_ptr.percent_at_start, 3, 1, 0); put("%"); new_line;
  1415.       new_line;
  1416.       put_line(" 6)  Done With Data - EXIT from Activity Data Menu");
  1417.       get(response);
  1418.       skip_line;
  1419.       new_line(2);
  1420.       return response;
  1421.     exception
  1422.       when others =>
  1423.         skip_line;
  1424.         new_line;
  1425.         put_line(" Please enter a number between 1 and 13. ");
  1426.         delay 1.0;
  1427.     end;
  1428.   end loop;
  1429. end PRINT_AC_MENU;
  1430.  
  1431.  
  1432.  
  1433. separate( VT100 )
  1434. function PRINT_EL_MENU (EL_PTR : in element_pointer) return integer is
  1435. ----------------------------------------------------------------------
  1436. --|
  1437. --|  NAME:  PRINT_EL_MENU
  1438. --|
  1439. --|  OVERVIEW:
  1440. --|    This procedure displays the fields that can be changed on 
  1441. --|    an element type.
  1442. --|
  1443. --|  EXCEPTIONS HANDLED:
  1444. --|    others   the user is reprompted
  1445. --|
  1446. --|  HISTORY:
  1447. --|    written by   May Lee   March 1985
  1448. --|  
  1449. ----------------------------------------------------------------------
  1450. begin
  1451.   loop
  1452.     begin
  1453.       CLEAR_SCREEN;
  1454.       put_line("                  ELEMENT  DATA  MENU  ");
  1455.       put_line("==========================================================");
  1456.       new_line(3); 
  1457.       put_line("Choose the number of one of the following element fields ");
  1458.       put_line("that you would like to modify: ");
  1459.       new_line(2); 
  1460.       put("  1)  Element Description       "); put(el_ptr.description); new_line;
  1461.       put("  2)  Description Abbreviation  "); put(el_ptr.desc_key); new_line;
  1462.       put("  3)  Subsystem Name            "); put(el_ptr.subsystem_name); 
  1463.       new_line;
  1464.       if not el_ptr.more_than_one_person then
  1465.     put("  4)  Person's Initials         "); 
  1466.     put(el_ptr.person_initials);
  1467.       else
  1468.     put("  4)  People's Initials         "); 
  1469.     for ac_index in 1..num_of_activities loop
  1470.       put (el_ptr.people_initials(ac_index));
  1471.       if ac_index < num_of_activities then
  1472.         put(',');
  1473.       end if;
  1474.     end loop;
  1475.       end if;
  1476.       new_line;
  1477.       put("  5)  Milestone Number               "); put(el_ptr.milestone_num,2);
  1478.       new_line;
  1479.       put("  6)  Element Priority               "); put(el_ptr.priority,2); 
  1480.       new_line;
  1481.       put("  7)  Current Size              "); put(el_ptr.current_size,7);
  1482.       new_line;
  1483.       put("  8)  Complexity                      "); put(el_ptr.complexity,1,2,0);
  1484.       new_line;
  1485.       put("  9)  Activity Completeness           '"); 
  1486.         for i in 1..num_of_activities loop
  1487.           put( CONVERT( el_ptr.activity_completeness(i) ));
  1488.         end loop;
  1489.       put("'");
  1490.       new_line;
  1491.       put(" 10)  More than one person assigned   "); put(el_ptr.more_than_one_person);
  1492.       new_line;
  1493.       new_line(2);
  1494.       put_line(" 11)  Done With Data - EXIT from Element Data Menu");
  1495.       get(response); skip_line;
  1496.       new_line(2);
  1497.       return response;
  1498.     exception
  1499.       when others =>
  1500.         skip_line;
  1501.         new_line;
  1502.         put_line(" Please enter a number between 1 and 10. ");
  1503.         delay 1.0;
  1504.     end;
  1505.   end loop;
  1506. end PRINT_EL_MENU;
  1507.  
  1508.  
  1509.  
  1510. separate( VT100 )
  1511. function PRINT_MS_MENU (MS_PTR : in milestone_pointer) return integer is
  1512. ----------------------------------------------------------------------
  1513. --|
  1514. --|  NAME:  PRINT_MS_MENU
  1515. --|
  1516. --|  OVERVIEW:
  1517. --|    This procedure displays the fields that can be changed on 
  1518. --|    a milestone type.
  1519. --|
  1520. --|  EXCEPTIONS HANDLED:
  1521. --|    others   the user is reprompted
  1522. --|
  1523. --|  HISTORY:
  1524. --|    written by   May Lee   March 1985
  1525. --|  
  1526. ----------------------------------------------------------------------
  1527. begin
  1528.   loop
  1529.     begin
  1530.       CLEAR_SCREEN;
  1531.       put_line("                MILESTONE  DATA  MENU  ");
  1532.       put_line("=============================================================");
  1533.       new_line(3); 
  1534.       put_line("Choose the number of one of the following milestone fields ");
  1535.       put_line("that you would like to modify: ");
  1536.       new_line(2); 
  1537.       put(" 1)  Milestone Number    "); put(MS_ptr.number,2); new_line;
  1538.       put(" 2)  Completion Number   "); put(ms_ptr.completion_number,2); new_line;
  1539.       put(" 3)  Due Date            "); 
  1540.         if ms_ptr.due_date = null_date then
  1541.           put("null date ");
  1542.         else
  1543.           put(ms_ptr.due_date.month,2); put("/");
  1544.           put(ms_ptr.due_date.day,2);   put("/");
  1545.           put(ms_ptr.due_date.year,4);  
  1546.         end if;
  1547.         new_line;
  1548.       put(" 4)  Description         "); put(ms_ptr.description); new_line;
  1549.       new_line;
  1550.       put_line(" 5)  Done With Data - EXIT from Milestone Data Menu");
  1551.       get(response);
  1552.       skip_line;
  1553.       new_line(2);
  1554.       return response;
  1555.     exception
  1556.       when others =>
  1557.         skip_line;
  1558.         new_line;
  1559.         put_line(" Please enter a number between 1 and 5. ");
  1560.         delay 1.0;
  1561.     end;
  1562.   end loop;
  1563. end PRINT_MS_MENU;
  1564.  
  1565.  
  1566. separate( VT100 )
  1567. function PRINT_PR_MENU (PR_PTR : in personnel_pointer) return integer is
  1568. ----------------------------------------------------------------------
  1569. --|
  1570. --|  NAME:  PRINT_PR_MENU
  1571. --|
  1572. --|  OVERVIEW:
  1573. --|    This procedure displays the fields that can be changed on 
  1574. --|    a personnel type.
  1575. --|
  1576. --|  EXCEPTIONS HANDLED:
  1577. --|    others   the user is reprompted
  1578. --|
  1579. --|  HISTORY:
  1580. --|    written by   May Lee   March 1985
  1581. --|  
  1582. ----------------------------------------------------------------------
  1583. begin
  1584.   loop
  1585.     begin
  1586.       CLEAR_SCREEN;
  1587.       put_line("                PERSONNEL  DATA  MENU  ");
  1588.       put_line("==========================================================");
  1589.       new_line(3); 
  1590.       put_line("Choose the number of one of the following personnel fields ");
  1591.       put_line("that you would like to modify: ");
  1592.       new_line(2); 
  1593.       put(" 1)  Person's Name       "); put(pr_ptr.name); new_line;
  1594.       put(" 2)  Person's Initials   "); put(pr_ptr.initials); new_line;
  1595.       put(" 3)  Production Rate     "); put(pr_ptr.production_rate, 2, 3, 0); 
  1596.       new_line;
  1597.       put(" 4)  Hours Per Week      "); put(pr_ptr.hours_per_week,2); new_line;
  1598.       put(" 5)  First Start/Stop Date         "); 
  1599.         if pr_ptr.start_dates(1) = null_date then
  1600.           put("null date ");
  1601.         else
  1602.           put(pr_ptr.start_dates(1).month,2); put("/");
  1603.           put(pr_ptr.start_dates(1).day,2);   put("/");
  1604.           put(pr_ptr.start_dates(1).year,4);  
  1605.         end if;
  1606.         put("   ");
  1607.         if pr_ptr.stop_dates(1) = null_date then
  1608.           put("null date ");
  1609.         else
  1610.           put(pr_ptr.stop_dates(1).month,2); put("/");
  1611.           put(pr_ptr.stop_dates(1).day,2);    put("/");
  1612.           put(pr_ptr.stop_dates(1).year,4);   
  1613.         end if;
  1614.         new_line;
  1615.       put(" 6)  Second Start/Stop Date        "); 
  1616.         if pr_ptr.start_dates(2) = null_date then
  1617.           put("null date ");
  1618.         else
  1619.           put(pr_ptr.start_dates(2).month,2); put("/");
  1620.           put(pr_ptr.start_dates(2).day,2);   put("/");
  1621.           put(pr_ptr.start_dates(2).year,4);  
  1622.         end if;
  1623.         put("   ");
  1624.         if pr_ptr.stop_dates(2) = null_date then
  1625.           put("null date ");
  1626.         else
  1627.           put(pr_ptr.stop_dates(2).month,2); put("/");
  1628.           put(pr_ptr.stop_dates(2).day,2);    put("/");
  1629.           put(pr_ptr.stop_dates(2).year,4);   
  1630.         end if;
  1631.         new_line;
  1632.       put(" 7)  Third Start/Stop Date         "); 
  1633.         if pr_ptr.start_dates(3) = null_date then
  1634.           put("null date ");
  1635.         else
  1636.           put(pr_ptr.start_dates(3).month,2); put("/");
  1637.           put(pr_ptr.start_dates(3).day,2);   put("/");
  1638.           put(pr_ptr.start_dates(3).year,4);  
  1639.         end if;
  1640.         put("   ");
  1641.         if pr_ptr.stop_dates(3) = null_date then
  1642.           put("null date ");
  1643.         else
  1644.           put(pr_ptr.stop_dates(3).month,2); put("/");
  1645.           put(pr_ptr.stop_dates(3).day,2);    put("/");
  1646.           put(pr_ptr.stop_dates(3).year,4);   
  1647.         end if;
  1648.         new_line(2);
  1649.       put_line(" 8)  Done With Data - EXIT from Personnel Data Menu");
  1650.       get(response);
  1651.       skip_line;
  1652.       new_line(2);
  1653.       return response;
  1654.     exception
  1655.       when others =>
  1656.         skip_line;
  1657.         new_line;
  1658.         put_line(" Please enter a number between 1 and 8. ");
  1659.         delay 1.0;
  1660.     end;
  1661.   end loop;
  1662. end PRINT_PR_MENU;
  1663.  
  1664.  
  1665. separate( VT100 )
  1666. function PRINT_SS_MENU (SS_PTR : in subsystem_pointer) return integer is
  1667. ----------------------------------------------------------------------
  1668. --|
  1669. --|  NAME:  PRINT_SS_MENU
  1670. --|
  1671. --|  OVERVIEW:
  1672. --|    This procedure displays the fields that can be changed on 
  1673. --|    a subsystem type.
  1674. --|
  1675. --|  EXCEPTIONS HANDLED:
  1676. --|    others   the user is reprompted
  1677. --|
  1678. --|  HISTORY:
  1679. --|    written by   May Lee   March 1985
  1680. --|  
  1681. ----------------------------------------------------------------------
  1682. begin
  1683.   loop
  1684.     begin
  1685.       CLEAR_SCREEN;
  1686.       put_line("                SUBSYSTEM  DATA  MENU  ");
  1687.       put_line("==========================================================");
  1688.       new_line(3); 
  1689.       put_line("Choose the number of one of the following subsystem fields ");
  1690.       put_line("that you would like to modify: ");
  1691.       new_line(2); 
  1692.       put(" 1)  Subsystem Name     "); put(ss_ptr.name); new_line;
  1693.       put(" 2)  Task Numbers       "); new_line;
  1694.       put(" 3)  Percent At Start   "); put(ss_ptr.percent_at_start,3,1,0); 
  1695.       put("%");
  1696.       new_line(2);
  1697.       put_line(" 4)  Done With Data - EXIT from Subsystem Data Menu");
  1698.       get(response);
  1699.       skip_line;
  1700.       new_line(2);
  1701.       return response;
  1702.     exception
  1703.       when others =>
  1704.         skip_line;
  1705.         new_line;
  1706.         put_line(" Please enter a number between 1 and 4. ");
  1707.         delay 1.0;
  1708.     end;
  1709.   end loop;
  1710. end PRINT_SS_MENU;
  1711.  
  1712. separate( VT100 )
  1713. procedure TRACKER_INTRO is
  1714. ----------------------------------------------------------------------
  1715. --|
  1716. --|  NAME:  TRACKER_INTRO
  1717. --|
  1718. --|  OVERVIEW:
  1719. --|    This procedure prints the TRACKER banner introduction on the
  1720. --|    terminal screen.  
  1721. --|
  1722. --|  EXCEPTIONS HANDLED: 
  1723. --|    none
  1724. --|
  1725. --|  HISTORY:
  1726. --|    written by   May Lee   March 1985
  1727. --|  
  1728. ----------------------------------------------------------------------
  1729.    begin
  1730.       CLEAR_SCREEN;
  1731.       new_line(6); 
  1732.       put_line("                    +-----------------------+ ");
  1733.       put_line("                    |  T  R  A  C  K  E  R  | ");
  1734.       put_line("                    +-----------------------+ ");
  1735.       new_line;
  1736.       put_line("                        Ada  Version 1.0 ");
  1737.       delay 1.0;
  1738.       CLEAR_SCREEN;
  1739.    end TRACKER_INTRO;
  1740.  
  1741.  
  1742.     separate( VT100 )
  1743.     procedure GOODBYE_MESSAGE is
  1744.     ----------------------------------------------------------------------
  1745.     --|
  1746.     --|  NAME:  GOODBYE_MESSAGE
  1747.     --|
  1748.     --|  OVERVIEW:
  1749.     --|    This procedure prints the TRACKER exit message on the
  1750.     --|    terminal screen.  
  1751.     --|
  1752.     --|  EXCEPTIONS HANDLED: 
  1753.     --|    none
  1754.     --|
  1755.     --|  HISTORY:
  1756.     --|    written by   May Lee   March 1985
  1757.     --|  
  1758.     ----------------------------------------------------------------------
  1759.     begin
  1760.       new_line(15); 
  1761.       put_line("                                    BYE");
  1762.       new_line(15); 
  1763.     end GOODBYE_MESSAGE;
  1764. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  1765. --prompts.ada
  1766. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  1767. with DATA_PKG;     use DATA_PKG;
  1768. with TEXT_IO;      use TEXT_IO;
  1769.  
  1770. package PROMPT_PKG is
  1771.   use CALENDAR;
  1772.  
  1773.   function  PROJECT_NAME         return string;
  1774.   function  PROJECT_NUM          return integer;
  1775.   function  TASK_NUMBERS( ss_record : in subsystem_pointer ) 
  1776.                                  return task_numbers_type;
  1777.   function  TASK_NUMBER_BY_AC( ss_record : in subsystem_pointer ) 
  1778.                  return integer;
  1779.   function  MANAGER_NAME         return string;
  1780.   function  ELE_DESCRIPTION      return string;
  1781.   procedure DISPLAY_ELEMENT_DATA;
  1782.   procedure EXISTING_ELE_KEY     ( abort_proc : out boolean; 
  1783.                                    key : out el_key_type );
  1784.   function  NEW_ELE_KEY          return el_key_type;
  1785.   procedure DISPLAY_SUBSYSTEM_DATA;
  1786.   procedure EXISTING_SUBSYS_NAME ( abort_proc : out boolean; 
  1787.                                    key : out ss_name_type );
  1788.   function  NEW_SUBSYS_NAME      return ss_name_type;
  1789.   procedure DISPLAY_PERSONNEL_DATA;
  1790.   procedure EXISTING_PERSON_INITIALS ( abort_proc : out boolean; 
  1791.                                  key : out pr_init_type );
  1792.   function  NEW_PERSON_INITIALS  return pr_init_type;
  1793.   procedure DISPLAY_MILESTONE_DATA;
  1794.   procedure EXISTING_MILSTONE_NUMBER ( abort_proc : out boolean; 
  1795.                                        key : out ms_num_type );
  1796.   function  NEW_MILSTONE_NUMBER  return ms_num_type;
  1797.   function  MILESTONE_COMPLETION_NUMBER (default : in ms_num_type)
  1798.                  return ms_num_type;
  1799.   function  ELEMENT_PRIORITY (default : in ms_num_type) return ms_num_type;
  1800.   function  CURRENT_SIZE_EST     return integer;
  1801.   function  ORIG_SIZE_EST (default : in integer := 0) return integer;
  1802.   function  UPDATE_CURRENT_SIZE (old_size : in integer) return integer;
  1803.   function  COMPLEXITY_FACTOR    return float;
  1804.   function  ACTIV_COMPLETENESS   return ACTIVITY_PHASE_PERCENT;
  1805.   function  UPDATE_ACTIV_COMPLETENESS 
  1806.         (old_pct_complete : in activity_phase_percent) 
  1807.         return ACTIVITY_PHASE_PERCENT;
  1808.   procedure DISPLAY_ACTIVITY_DATA;
  1809.   procedure EXISTING_ACTIV_NAME  ( abort_proc : out boolean; 
  1810.                                    key : out ac_name_type );
  1811.   function  NEW_ACTIV_NAME       return ac_name_type;
  1812.   function  ACTIV_PRIORITY       return integer;
  1813.   function  CONSIDER_AC_IN_CALC  return boolean;
  1814.   function  MS_DESCRIPTION       return string;
  1815.   function  PERSONS_NAME         return string;
  1816.   function  PR_PRODUCTION_RATE   return float;
  1817.   function  PR_HRS_PER_WEEK      return integer;
  1818.   function  PERCENT              return float;
  1819.   function  DATE                 return DATE_TYPE;
  1820. end PROMPT_PKG;
  1821. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  1822. --promptb.ada
  1823. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  1824. with DATA_PKG;     use DATA_PKG;
  1825. with TEXT_IO;      use TEXT_IO;
  1826.  
  1827. package body PROMPT_PKG is
  1828. ----------------------------------------------------------------------
  1829. --|
  1830. --|  NAME:  PROMPT_PKG
  1831. --|
  1832. --|  OVERVIEW:
  1833. --|    This package contains the user prompt messages that will be displayed
  1834. --|    on the screen.  The prompts will only return valid data.  The user is
  1835. --|    trapped until a valid entry is received.   If the data being requested
  1836. --|    has a default value, the user may respond with a carriage return. If, 
  1837. --|    the user responds with '?' ( or anything else that causes an exception),
  1838. --|    then the prompt will be expanded to give the user more information on 
  1839. --|    the type of data to enter.  For data that does not have a default value,
  1840. --|    a carriage return or '?' will display the extended prompt.  Otherwise,
  1841. --|    the data is received from the user and processed accordingly.  If the
  1842. --|    data is invalid, the user will be prompted again until valid data
  1843. --|    can be returned.
  1844. --|
  1845. --|  EXCEPTIONS HANDLED:
  1846. --|    others        any illegal input from the user
  1847. --|
  1848. --|  HISTORY:
  1849. --|    written by   May Lee   March 1985
  1850. --|
  1851. --|  NOTES:
  1852. --|    The search key for each data type has two types of prompts : 
  1853. --|    one for an existing key, and one for a new key that is not
  1854. --|    already in the list.
  1855. --|
  1856. --|    This package also provides procedures to display the keys of each
  1857. --|    data list to the screen.
  1858. ----------------------------------------------------------------------
  1859.  
  1860.   use INTEGER_TEXT_IO;
  1861.   use FLOAT_TEXT_IO;
  1862.  
  1863.   -- instantiation of generic list handler is done in data_pkg
  1864.   use AC_LIST_PKG;                 -- to get the activity completeness
  1865.   use EL_LIST_PKG;
  1866.   use MS_LIST_PKG;
  1867.   use PR_LIST_PKG;
  1868.   use SS_LIST_PKG;
  1869.  
  1870.   line_lngth  : integer := 1;
  1871.   line        : string (1..132) := (others => ' ');
  1872.   tab         : constant character := ascii.ht;
  1873.  
  1874.   -- to convert the enumeration type activity_phase_percent to character
  1875.   -- for read and write into the file only
  1876.   type ac_phase_char_type is array(1..10) of character;
  1877.   char_ac_completeness  : ac_phase_char_type := (others => ' ');
  1878.  
  1879.  
  1880.  
  1881.  
  1882.   function  PROJECT_NAME return string is
  1883.   begin
  1884.     -- blank out the input line
  1885.     line := (others => ' ');
  1886.  
  1887.     -- ask abbreviated question
  1888.     put(" Project Name : ");
  1889.  
  1890.     loop
  1891.       while end_of_line loop
  1892.         skip_line;
  1893.         new_line;
  1894.         put_line(" What is the name of the project in 30 characters or less?");
  1895.         new_line;
  1896.         put(" Project Name : ");
  1897.       end loop;
  1898.       
  1899.       -- get the record field
  1900.       get_line(line,line_lngth);
  1901.       new_line(2);
  1902.       exit when line(1) /= '?';
  1903.  
  1904.       put_line(" What is the name of the project in 30 characters or less?");
  1905.       new_line;
  1906.       put(" Project Name : ");
  1907.     end loop;
  1908.     return line(1..DATA_PKG.project_name'last);
  1909.   end PROJECT_NAME;
  1910.  
  1911.   function PROJECT_NUM return integer is 
  1912.     ---------------------------------
  1913.     -- Project Number
  1914.     ---------------------------------
  1915.   an_integer  : integer range 0..999;
  1916.   valid_input : boolean := false;  -- if user input was valid
  1917.  
  1918.   begin
  1919.     while not valid_input loop
  1920.       begin
  1921.         -- ask abbreviated question
  1922.         put (" Project Number : ");
  1923.  
  1924.         while end_of_line loop -- keep asking question if the user hits <cr>
  1925.           skip_line;
  1926.           new_line;
  1927.           put_line(" What is the 3 digit project number? ");
  1928.           put_line(" Enter an integer in the range 0 to 999  ");
  1929.           new_line;
  1930.           put (" Project Number : ");
  1931.         end loop;
  1932.         get( an_integer ); skip_line;
  1933.         new_line(2);
  1934.         valid_input := true;
  1935.       exception
  1936.         when others =>  
  1937.           skip_line;
  1938.           new_line;
  1939.           put_line(" What is the 3 digit project number? ");
  1940.           put_line(" Enter an integer in the range 0 to 999  ");
  1941.           new_line;
  1942.       end;
  1943.     end loop;
  1944.     return an_integer;
  1945.   end PROJECT_NUM;
  1946.  
  1947.  
  1948.   function TASK_NUMBERS( ss_record : in subsystem_pointer ) return 
  1949.                          task_numbers_type is
  1950.     ac_record    : activity_pointer;  
  1951.     blanks       : constant string (1..sub_name_max_len+2) := (others => ' ');
  1952.     end_list     : boolean := true;
  1953.     input_line   : string (1..80) := ( others => ' ');
  1954.     last_char    : integer := 0;
  1955.     last         : integer := 0;
  1956.     new_task_num : task_numbers_type := (others => 0);
  1957.     num_read     : integer := 0;  --  num of new task numbers read
  1958.     tasknum_end  : integer := 1;
  1959.     tasknum_start: integer := 1;
  1960.    
  1961.   begin
  1962.     loop
  1963.       begin
  1964.         put_line(" Enter the new task numbers directly below the old task numbers. ");
  1965.         put_line(" You may enter blanks for the task numbers that you want to leave");
  1966.         put_line(" the same, so that you can change one task number at a time.");
  1967.         put_line(" DO NOT USE TABS!                     [ <cr> = no change ]");
  1968.         new_line;
  1969.         -- print header
  1970.     put(blanks);
  1971.         START_WALK( ac_list );
  1972.         loop
  1973.           WALK( ac_list, ac_record, end_list );
  1974.           exit when end_list;
  1975.           put(ac_record.name(1..4));
  1976.           put("  ");
  1977.         end loop;
  1978.         new_line;
  1979.     put(blanks);
  1980.         for i in 1..num_of_activities loop
  1981.           put ("----  ");
  1982.         end loop;
  1983.         new_line;
  1984.  
  1985.         -- output the task numbers
  1986.         put(ss_record.name); put("  ");
  1987.         for i in 1..num_of_activities loop
  1988.           put (ss_record.task_numbers(i),4);
  1989.           put ("  ");
  1990.         end loop;
  1991.         new_line;
  1992.         put(ss_record.name); put(": ");
  1993.  
  1994.         if end_of_line then
  1995.           skip_line;
  1996.           return ss_record.task_numbers;
  1997.         else
  1998.       tasknum_start := 1;
  1999.           get_line( input_line, last_char );
  2000.           -- parse the line
  2001.           for i in 1..num_of_activities loop
  2002.             exit when tasknum_start > last_char;
  2003.         num_read := num_read + 1;
  2004.         tasknum_end := tasknum_start+3;
  2005.         if tasknum_end > last_char then
  2006.           tasknum_end := last_char;
  2007.         end if;
  2008.             if    input_line(tasknum_start..tasknum_end) = 
  2009.         blanks( 1..tasknum_end - tasknum_start + 1 )then
  2010.               -- default to old task number
  2011.               new_task_num(num_read) := ss_record.task_numbers(num_read);
  2012.             else
  2013.               -- get new task number
  2014.               get( input_line(tasknum_start..tasknum_end), 
  2015.                    new_task_num(num_read), last );
  2016.         end if;          
  2017.             -- skip task num and blank
  2018.             tasknum_start := tasknum_start + 6;  
  2019.           end loop;
  2020.           if num_read < num_of_activities then -- didn't change all task numbers
  2021.             -- leave the rest of the task numbers unchanged
  2022.             new_task_num(num_read+1..num_of_activities) := 
  2023.               ss_record.task_numbers(num_read+1..num_of_activities);
  2024.           end if;
  2025.           return new_task_num;
  2026.         end if;
  2027.       exception
  2028.         when others =>
  2029.           new_line;
  2030.           put_line(" That was not a valid input. Enter the four digit ");
  2031.           put_line(" task number for each activity. ");
  2032.           new_line;
  2033.       end;
  2034.     end loop;
  2035.   end TASK_NUMBERS;
  2036.  
  2037.  
  2038.   function TASK_NUMBER_BY_AC( ss_record : in subsystem_pointer ) return 
  2039.                          integer is
  2040.     ac_record    : activity_pointer;  
  2041.     a_task_num   : integer range 0..9999 := 0;
  2042.     ac_index     : integer := 0;
  2043.     blanks       : constant string (1..sub_name_max_len+2) := (others => ' ');
  2044.     end_list     : boolean := true;
  2045.    
  2046.   begin
  2047.     put_line(" Enter the new task number (range 0 to 9999).");
  2048.     put_line(" DO NOT USE TABS!                [ <cr> = 0 ]");
  2049.     new_line;
  2050.     loop
  2051.       begin
  2052.         -- print header of the last activity
  2053.     put(blanks);
  2054.         START_WALK( ac_list );
  2055.         loop
  2056.           WALK( ac_list, ac_record, end_list );
  2057.           exit when end_list;
  2058.       ac_index := ac_index + 1;
  2059.         end loop;
  2060.  
  2061.         put(ac_record.name(1..4));
  2062.         put("  "); new_line; 
  2063.     put(blanks); put ("----  "); new_line;
  2064.  
  2065.         -- output the task number prompt
  2066.         put(ss_record.name); put(": ");
  2067.  
  2068.         if end_of_line then
  2069.           skip_line; new_line;
  2070.           return a_task_num;
  2071.         else
  2072.       get(a_task_num); 
  2073.           skip_line; new_line;
  2074.           return a_task_num;
  2075.         end if;
  2076.       exception
  2077.         when others => skip_line; new_line;
  2078.           put_line(" Enter the new task number (range 0 to 9999).");
  2079.         put_line(" DO NOT USE TABS!                [ <cr> = 0 ]");
  2080.           new_line;
  2081.       end;
  2082.     end loop;
  2083.   end TASK_NUMBER_BY_AC;
  2084.  
  2085.  
  2086.   function  MANAGER_NAME return string is
  2087.   begin
  2088.     -- blank out the input line
  2089.     line := (others => ' ');
  2090.  
  2091.     -- ask abbreviated question
  2092.     put(" Manager Name : ");
  2093.  
  2094.     loop
  2095.       while end_of_line loop  -- keep asking question if the user hits <cr>
  2096.         new_line;
  2097.         skip_line;
  2098.         put_line(" What is the project manager's name in 30 characters or less?");
  2099.         new_line;
  2100.         put(" Manager Name : ");
  2101.       end loop;
  2102.       
  2103.       -- get the record field
  2104.       get_line(line,line_lngth);
  2105.       new_line(2);
  2106.       exit when line(1) /= '?';
  2107.  
  2108.       put_line(" What is the project manager's name in 30 characters or less?");
  2109.       new_line;
  2110.       put(" Manager Name : ");
  2111.     end loop;
  2112.     return line(1..DATA_PKG.manager_name'last);
  2113.   end MANAGER_NAME;
  2114.  
  2115.  
  2116.   function ELE_DESCRIPTION return string is 
  2117.   ---------------------------------
  2118.   --  Element Description
  2119.   ---------------------------------
  2120.   begin
  2121.     -- blank out the input line
  2122.     line := (others => ' ');
  2123.  
  2124.     loop
  2125.       -- ask abbreviated question
  2126.       put(" Element description : ");
  2127.  
  2128.       while end_of_line loop  -- keep asking question if the user hits <cr>
  2129.         skip_line;
  2130.         new_line;
  2131.         put_line(" What is the description of the element in 35 characters or less?");
  2132.         new_line;
  2133.         put(" Element description : ");
  2134.       end loop;
  2135.       
  2136.       -- get the record field
  2137.       get_line(line,line_lngth);
  2138.       new_line(2);
  2139.       exit when line(1) /= '?';
  2140.  
  2141.       new_line;
  2142.       put_line(" What is the description of the element in 35 characters or less?");
  2143.       new_line;
  2144.     end loop;
  2145.     return line(1..35);
  2146.   end ELE_DESCRIPTION;
  2147.  
  2148.  
  2149.   procedure DISPLAY_ELEMENT_DATA is
  2150.   ------------------------------------------------------------------------------
  2151.   --|
  2152.   --|  NAME:  DISPLAY_ELEMENT_DATA
  2153.   --|
  2154.   --|  OVERVIEW:
  2155.   --|    This procedure walks the list and prints the name of each element
  2156.   --|    to the screen.
  2157.   --|
  2158.   --|  EXCEPTIONS HANDLED:
  2159.   --|    none
  2160.   --|  
  2161.   --|  HISTORY:
  2162.   --|    written by   May Lee   March 1985
  2163.   --|
  2164.   ------------------------------------------------------------------------------
  2165.   tab         : constant character := ascii.ht;
  2166.   el_record   : element_pointer;   -- pointer to the element record
  2167.   end_list    : boolean := false;  -- parameter to WALK
  2168.  
  2169.   begin
  2170.     if not EMPTY_LIST( el_list ) then
  2171.       put_line(" The existing elements are : ");
  2172.       new_line;
  2173.       START_WALK( el_list );
  2174.       end_list := false;
  2175.       loop
  2176.         WALK( el_list, el_record, end_list);
  2177.         exit when end_list;
  2178.         put(el_record.desc_key); put(tab); put(el_record.description); new_line;
  2179.       end loop;
  2180.       new_line;
  2181.     end if;
  2182.   end DISPLAY_ELEMENT_DATA;
  2183.  
  2184.  
  2185.  
  2186.   procedure EXISTING_ELE_KEY( abort_proc : out boolean; key : out el_key_type ) is 
  2187.   ---------------------------------
  2188.   --  Description Key, Abbreviation
  2189.   ---------------------------------
  2190.   -- for modifying and deleting an element
  2191.   a_char      : character;         -- to see if the user wants to abort this function
  2192.   el_record   : element_pointer;   
  2193.   found       : boolean;           -- parameter to FIND
  2194.   valid_input : boolean := false;  -- if user input was valid
  2195.  
  2196.   begin
  2197.     abort_proc  := false;
  2198.  
  2199.     while not valid_input loop  
  2200.       begin
  2201.         -- blank out the input line
  2202.         line := (others => ' ');
  2203.  
  2204.         -- ask abbreviated question
  2205.         put(" Description Abbreviation : ");
  2206.  
  2207.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2208.           skip_line;
  2209.           new_line;
  2210.           put_line(" Enter a unique description key of 6 characters or   ");
  2211.           put_line(" less that abbreviates an existing element description.  ");
  2212.           new_line;
  2213.       DISPLAY_ELEMENT_DATA;
  2214.       new_line;
  2215.           put(" Description Abbreviation: ");
  2216.         end loop;
  2217.  
  2218.         get_line(line,line_lngth);
  2219.         new_line(2);
  2220.  
  2221.     -- check if more information requested
  2222.     if line(1) = '?' then
  2223.           new_line;
  2224.           put_line(" Enter a unique description key of 6 characters or   ");
  2225.           put_line(" less that abbreviates an existing element description.  ");
  2226.           new_line;
  2227.       DISPLAY_ELEMENT_DATA;
  2228.       new_line;
  2229.     else
  2230.           -- checks to see if the element exists or not
  2231.           FIND( el_list, line(1..el_key_max_len), el_record, found );
  2232.           valid_input := found;
  2233.  
  2234.           if not valid_input then  -- warn user, loop again
  2235.             put_line(" Sorry, but that element doesn't exists. ");
  2236.             new_line;
  2237.             put_line(" Press the return key to see the list of existing elements. ");
  2238.             put_line(" Enter 'a' to abort this procedure ");
  2239.             put_line(" Enter any other key to continue. ");
  2240.             if end_of_line then  -- pressed <cr>, show list of desc_key
  2241.               skip_line;
  2242.               DISPLAY_ELEMENT_DATA;
  2243.             else  -- loop again on any input except <cr> or 'a'
  2244.               get(a_char); skip_line;
  2245.               if a_char = 'a' or a_char = 'A' then
  2246.                 abort_proc := true;
  2247.                 valid_input := true;
  2248.               end if;
  2249.             end if;
  2250.       end if;
  2251.         end if;
  2252.  
  2253.       exception
  2254.         when others => skip_line;
  2255.           put_line(" That was not a valid abbreviation.  TRY AGAIN! ");
  2256.           new_line;
  2257.           DISPLAY_ELEMENT_DATA;
  2258.       end;
  2259.     end loop;  -- valid input
  2260.  
  2261.     key := line(1..el_key_max_len);
  2262.   end EXISTING_ELE_KEY;
  2263.  
  2264.  
  2265.  
  2266.   function NEW_ELE_KEY return el_key_type is
  2267.   -- prompt for adding an new element
  2268.   ---------------------------------
  2269.   --  Description Key, Abbreviation
  2270.   ---------------------------------
  2271.   found       : boolean;           -- parameter to FIND
  2272.   el_record   : element_pointer;   
  2273.   valid_input : boolean := false;  -- if user input was valid
  2274.  
  2275.   begin
  2276.     while not valid_input loop  
  2277.       begin
  2278.         -- blank out the input line
  2279.         line := (others => ' ');
  2280.         -- ask abbreviated question
  2281.         put(" Unique abbreviation : ");
  2282.  
  2283.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2284.           skip_line;
  2285.           put_line(" Enter a unique description key of 6 characters or   ");
  2286.           put_line(" less that abbreviates the element description.  ");
  2287.           new_line;
  2288.       DISPLAY_ELEMENT_DATA;
  2289.       new_line;
  2290.           put(" Unique Abbreviation : ");
  2291.         end loop;
  2292.  
  2293.         get_line(line,line_lngth);
  2294.         new_line(2);
  2295.  
  2296.     -- check if more information requested
  2297.     if line(1) = '?' then
  2298.           put_line(" Enter a unique description key of 6 characters or   ");
  2299.           put_line(" less that abbreviates the element description.  ");
  2300.           new_line;
  2301.       DISPLAY_ELEMENT_DATA;
  2302.           new_line;
  2303.     else
  2304.           -- want the element to be unique 
  2305.           FIND( el_list, line(1..el_key_max_len), el_record, found );
  2306.           valid_input := not found;
  2307.   
  2308.           if not valid_input then  -- warn user, loop again
  2309.             put(" Sorry, but element "); 
  2310.             put( line(1..line_lngth) );
  2311.             put(" already exists. "); new_line;
  2312.             put_line(" You must enter a new unique element. ");
  2313.             new_line;
  2314.             put_line(" Press the return key to see the list of existing elements. ");
  2315.             put_line(" Enter any other key to continue. ");
  2316.             if end_of_line then  -- pressed <cr>, show ss list
  2317.               skip_line;
  2318.               DISPLAY_ELEMENT_DATA;
  2319.             else  -- loop again on any input except <cr> 
  2320.               skip_line;
  2321.             end if;
  2322.           end if;
  2323.         end if;
  2324.  
  2325.       exception
  2326.         when others => skip_line;
  2327.           put_line(" That was not a valid abbreviation.  TRY AGAIN! ");
  2328.           new_line;
  2329.       end;
  2330.     end loop;  -- valid input
  2331.  
  2332.     return line(1..el_key_max_len);
  2333.   end NEW_ELE_KEY;
  2334.  
  2335.  
  2336.   procedure DISPLAY_SUBSYSTEM_DATA is
  2337.   ------------------------------------------------------------------------------
  2338.   --|
  2339.   --|  NAME:  DISPLAY_SUBSYSTEM_DATA
  2340.   --|
  2341.   --|  OVERVIEW:
  2342.   --|    This procedure walks the list and prints the name of each subsystem
  2343.   --|    to the screen.
  2344.   --|
  2345.   --|  EXCEPTIONS HANDLED:
  2346.   --|    none
  2347.   --|  
  2348.   --|  HISTORY:
  2349.   --|    Written by   May Lee   March 1985
  2350.   --|
  2351.   ------------------------------------------------------------------------------
  2352.   end_list    : boolean := false;
  2353.   ss_record   : subsystem_pointer;
  2354.  
  2355.   begin
  2356.     if not EMPTY_LIST( ss_list ) then
  2357.       put_line(" The existing subsystems are : ");
  2358.       new_line;
  2359.       START_WALK( ss_list);
  2360.       end_list := false;
  2361.       loop
  2362.         WALK( ss_list, ss_record, end_list);
  2363.         exit when end_list;
  2364.         put(ss_record.name); new_line;
  2365.       end loop;
  2366.       new_line;
  2367.     end if;
  2368.   end DISPLAY_SUBSYSTEM_DATA;
  2369.  
  2370.  
  2371.   procedure EXISTING_SUBSYS_NAME ( abort_proc : out boolean;
  2372.                                    key : out ss_name_type ) is 
  2373.   -- to modify or delete
  2374.   ---------------------------------
  2375.   --  Subsystem Name
  2376.   ---------------------------------
  2377.   a_char      : character;         -- to see if the user wants to abort this function
  2378.   found       : boolean;           -- parameter to FIND
  2379.   ss_record   : subsystem_pointer; 
  2380.   valid_input : boolean := false;  -- if user input was valid
  2381.  
  2382.   begin
  2383.     abort_proc  := false;
  2384.     while not valid_input loop
  2385.       begin
  2386.         -- blank out the input line
  2387.         line := (others => ' ');
  2388.  
  2389.         -- ask abbreviated question
  2390.         put(" Subsystem Name : ");
  2391.  
  2392.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2393.           skip_line;
  2394.           new_line;
  2395.           put_line(" Enter the name of the subsystem, which is a ");
  2396.           put_line(" string of up to 10 characters.");
  2397.           new_line;
  2398.       DISPLAY_SUBSYSTEM_DATA;
  2399.       new_line;
  2400.           put(" Subsystem Name : ");
  2401.         end loop;
  2402.  
  2403.         get_line(line,line_lngth);
  2404.         new_line(2);
  2405.         
  2406.     -- check to see if more information is requested
  2407.     if line(1) = '?' then
  2408.           new_line;
  2409.           put_line(" Enter the name of the subsystem, which is a ");
  2410.           put_line(" string of up to 10 characters.");
  2411.           new_line;
  2412.       DISPLAY_SUBSYSTEM_DATA;
  2413.       new_line;
  2414.     else
  2415.           -- check to see if ss is defined 
  2416.           FIND( ss_list, line(1..sub_name_max_len), ss_record, found );
  2417.  
  2418.           valid_input := found;
  2419.       
  2420.           if not valid_input then  -- warn user, loop again
  2421.             put(" Sorry, but subsystem "); 
  2422.             put( line(1..line_lngth) );
  2423.             put(" does not exist. "); new_line;
  2424.             put_line(" You must enter an existing subsystem.             ");
  2425.             new_line;
  2426.             put_line(" Press the return key to see the list of existing elements. ");
  2427.             put_line(" Enter 'a' to abort this procedure ");
  2428.             put_line(" Enter any other key to continue. ");
  2429.             if end_of_line then  -- pressed <cr>, show ss list
  2430.               skip_line;
  2431.               DISPLAY_SUBSYSTEM_DATA;
  2432.             else  -- loop again on any input except <cr> or 'a'
  2433.               get(a_char); skip_line;
  2434.               if a_char = 'a' or a_char = 'A' then
  2435.                 abort_proc := true;
  2436.                 valid_input := true;
  2437.               end if;
  2438.             end if;
  2439.           end if;
  2440.         end if;
  2441.  
  2442.       exception
  2443.         when others => skip_line;
  2444.           put_line(" That was not a valid name.  TRY AGAIN! ");
  2445.       end;
  2446.     end loop;
  2447.     key := line(1..sub_name_max_len);
  2448.   end EXISTING_SUBSYS_NAME;
  2449.  
  2450.  
  2451.  
  2452.   function NEW_SUBSYS_NAME return ss_name_type is 
  2453.   -- to add a new ss
  2454.   ---------------------------------
  2455.   --  Subsystem Name
  2456.   ---------------------------------
  2457.   found       : boolean;           -- parameter to FIND
  2458.   ss_record   : subsystem_pointer; 
  2459.   valid_input : boolean := false;  -- if user input was valid
  2460.  
  2461.   begin
  2462.     while not valid_input loop
  2463.       begin
  2464.         -- blank out the input line
  2465.         line := (others => ' ');
  2466.  
  2467.         -- ask abbreviated question
  2468.         put(" Subsystem Name : ");
  2469.  
  2470.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2471.           skip_line;
  2472.           new_line;
  2473.           put_line(" Enter the name of the subsystem, which is a ");
  2474.           put_line(" string of up to 10 characters.");
  2475.           new_line;
  2476.       DISPLAY_SUBSYSTEM_DATA;
  2477.       new_line;
  2478.           put(" Subsystem Name : ");
  2479.         end loop;
  2480.         get_line(line,line_lngth);
  2481.         new_line(2);
  2482.         
  2483.     -- check to see if more information is requested
  2484.     if line(1) = '?' then
  2485.           new_line;
  2486.           put_line(" Enter the name of the subsystem, which is a ");
  2487.           put_line(" string of up to 10 characters.");
  2488.           new_line;
  2489.       DISPLAY_SUBSYSTEM_DATA;
  2490.     else
  2491.           --  check to see if this ss is defined 
  2492.           FIND( ss_list, line(1..sub_name_max_len), ss_record, found );
  2493.  
  2494.           valid_input := not found;
  2495.      
  2496.           if not valid_input then  -- warn user, loop again
  2497.             put(" Sorry, but subsystem "); 
  2498.             put( line(1..line_lngth) );
  2499.             put(" already exists. "); new_line;
  2500.             put_line(" You must enter a new unique subsystem.             ");
  2501.             new_line;
  2502.             put_line(" Press the return key to see the list of existing subsystems. ");
  2503.             put_line(" Enter any other key to continue. ");
  2504.             if end_of_line then  -- pressed <cr>, show ss list
  2505.               skip_line;
  2506.               DISPLAY_SUBSYSTEM_DATA;
  2507.             else  -- loop again on any input except <cr> 
  2508.               skip_line;
  2509.             end if;
  2510.           end if;
  2511.         end if;
  2512.       exception
  2513.         when others => skip_line;
  2514.           put_line(" That was not a valid name.  TRY AGAIN! ");
  2515.       end;
  2516.     end loop;
  2517.     return line(1..sub_name_max_len);
  2518.   end NEW_SUBSYS_NAME;
  2519.  
  2520.  
  2521.   procedure DISPLAY_PERSONNEL_DATA is
  2522.   ------------------------------------------------------------------------------
  2523.   --|
  2524.   --|  NAME:  DISPLAY_PERSONNEL_DATA
  2525.   --|
  2526.   --|  OVERVIEW:
  2527.   --|    This procedure walks the list and prints the name of each person
  2528.   --|    to the screen.
  2529.   --|
  2530.   --|  EXCEPTIONS HANDLED:
  2531.   --|    none
  2532.   --|  
  2533.   --|  HISTORY:
  2534.   --|    Written by   May Lee   March 1985
  2535.   --|
  2536.   ------------------------------------------------------------------------------
  2537.   end_list    : boolean := false;
  2538.   pr_record   : personnel_pointer;
  2539.   tab         : constant character := ascii.ht;
  2540.  
  2541.   begin
  2542.     if not EMPTY_LIST( pr_list ) then
  2543.       put_line(" The existing people are : ");
  2544.       new_line;
  2545.       START_WALK( pr_list);
  2546.       end_list := false;
  2547.       loop
  2548.         WALK( pr_list, pr_record, end_list);
  2549.         exit when end_list;
  2550.         put(pr_record.initials); put(tab); put(pr_record.name); new_line;
  2551.       end loop;
  2552.       new_line;
  2553.     end if;
  2554.   end DISPLAY_PERSONNEL_DATA;
  2555.  
  2556.   procedure EXISTING_PERSON_INITIALS ( abort_proc : out boolean; 
  2557.                                        key : out pr_init_type )is 
  2558.   ---------------------------------
  2559.   --       Person's Initials
  2560.   ---------------------------------
  2561.   a_char      : character;         -- to see if the user wants to abort this function
  2562.   found       : boolean;           -- parameter to FIND
  2563.   pr_record   : personnel_pointer; 
  2564.   valid_input : boolean := false;  -- if user input was valid
  2565.  
  2566.   begin
  2567.     abort_proc  := false;
  2568.     while not valid_input loop
  2569.       begin
  2570.         -- blank out the input line
  2571.         line := (others => ' ');
  2572.  
  2573.         -- ask abbreviated question
  2574.         put(" Person's Initials : ");
  2575.  
  2576.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2577.           skip_line;
  2578.           new_line;
  2579.           put_line(" Enter a string of up to 2 characters that represents the initials ");   
  2580.           put_line(" of the person. ");
  2581.           new_line;
  2582.       DISPLAY_PERSONNEL_DATA;
  2583.       new_line;
  2584.           put(" Person's Initials : ");
  2585.         end loop;
  2586.         get_line(line,line_lngth);
  2587.         new_line(2);
  2588.  
  2589.     -- check if more information is requested
  2590.     if line(1) = '?' then
  2591.           new_line;
  2592.           put_line(" Enter a string of up to 2 characters that represents the initials ");   
  2593.           put_line(" of the person. ");
  2594.           new_line;
  2595.       DISPLAY_PERSONNEL_DATA;
  2596.       new_line;
  2597.     else
  2598.           --  check to see if this person exists
  2599.           FIND( pr_list, line(1..pr_init_max_len), pr_record, found );
  2600.           valid_input := found;
  2601.        
  2602.           if not valid_input then  -- warn user, loop again
  2603.             put_line(" Sorry, but no one with those initials exists. "); 
  2604.             put_line(" You must enter an existing person. ");
  2605.             new_line;
  2606.             put_line(" Press the return key to see the list of defined people and their initials. ");
  2607.             put_line(" Enter 'a' to abort this procedure. ");
  2608.             put_line(" Enter any other key to continue. ");
  2609.             if end_of_line then  -- pressed <cr>, show ss list
  2610.               skip_line;
  2611.               DISPLAY_PERSONNEL_DATA;
  2612.             else  -- loop again on any input except <cr> or 'a'
  2613.               get(a_char); skip_line;
  2614.               if a_char = 'a' or a_char = 'A' then
  2615.                 abort_proc := true;
  2616.                 valid_input := true;
  2617.               end if;
  2618.             end if;
  2619.             new_line;
  2620.           end if;
  2621.         end if;
  2622.       exception
  2623.         when others => skip_line;
  2624.           put_line(" That was not a valid value.  TRY AGAIN! ");
  2625.       end;
  2626.     end loop;
  2627.     key := line(1..pr_init_max_len);
  2628.   end EXISTING_PERSON_INITIALS;
  2629.  
  2630.  
  2631.  
  2632.   function NEW_PERSON_INITIALS return pr_init_type is 
  2633.   ---------------------------------
  2634.   --       Person's Initials
  2635.   ---------------------------------
  2636.   found       : boolean;           -- parameter to FIND
  2637.   pr_record   : personnel_pointer; 
  2638.   valid_input : boolean := false;  -- if user input was valid
  2639.  
  2640.   begin
  2641.     while not valid_input loop
  2642.       begin
  2643.         -- blank out the input line
  2644.         line := (others => ' ');
  2645.  
  2646.         -- ask abbreviated question
  2647.         put(" Person's Initials : ");
  2648.  
  2649.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2650.           skip_line;
  2651.           new_line;
  2652.           put_line(" Enter a string of up to 2 characters that represents the initials ");   
  2653.           put_line(" of the person. ");
  2654.           new_line;
  2655.       DISPLAY_PERSONNEL_DATA;
  2656.       new_line;
  2657.           put(" Person's Initials : ");
  2658.         end loop;
  2659.         get_line(line,line_lngth);
  2660.         new_line(2);
  2661.  
  2662.     -- check if more information is requested
  2663.     if line(1) = '?' then
  2664.           new_line;
  2665.           put_line(" Enter a string of up to 2 characters that represents the initials ");   
  2666.           put_line(" of the person. ");
  2667.           new_line;
  2668.       DISPLAY_PERSONNEL_DATA;
  2669.           new_line;
  2670.     else
  2671.           --  check to see if this person exists
  2672.           FIND( pr_list, line(1..pr_init_max_len), pr_record, found );
  2673.           valid_input := not found;
  2674.        
  2675.           if not valid_input then  -- warn user, loop again
  2676.             put(" Sorry, but "); 
  2677.             put( pr_record.initials);
  2678.             put(" already exists. "); new_line;
  2679.             put_line(" You must enter new unique initials. ");
  2680.             new_line;
  2681.         DISPLAY_PERSONNEL_DATA;
  2682.             new_line;
  2683.           end if;
  2684.         end if;
  2685.       exception
  2686.         when others => skip_line;
  2687.           put_line(" That was not a valid value.  TRY AGAIN! ");
  2688.       end;
  2689.     end loop;
  2690.     return line(1..pr_init_max_len);
  2691.   end NEW_PERSON_INITIALS;
  2692.  
  2693.  
  2694.   procedure DISPLAY_MILESTONE_DATA is
  2695.   ------------------------------------------------------------------------------
  2696.   --|
  2697.   --|  NAME:  DISPLAY_MILESTONE_DATA
  2698.   --|
  2699.   --|  OVERVIEW:
  2700.   --|    This procedure walks the list and prints the number of each 
  2701.   --|    milestone to the screen.
  2702.   --|
  2703.   --|  EXCEPTIONS HANDLED:
  2704.   --|    none
  2705.   --|  
  2706.   --|  HISTORY:
  2707.   --|    Written by   May Lee   March 1985
  2708.   --|
  2709.   ------------------------------------------------------------------------------
  2710.   end_list    : boolean := false;
  2711.   ms_record   : milestone_pointer;
  2712.  
  2713.   begin
  2714.     if not EMPTY_LIST( ms_list ) then
  2715.       put_line(" The existing milestones are : ");
  2716.       new_line;
  2717.       START_WALK( ms_list );
  2718.       end_list := false;
  2719.       loop
  2720.         WALK( ms_list, ms_record, end_list);
  2721.         exit when END_LIST;
  2722.         put(ms_record.number,2); put("   "); 
  2723.         put(ms_record.description); new_line;
  2724.       end loop;
  2725.       new_line;
  2726.     end if;
  2727.   end DISPLAY_MILESTONE_DATA;
  2728.  
  2729.  
  2730.   procedure EXISTING_MILSTONE_NUMBER ( abort_proc : out boolean; 
  2731.                                        key : out ms_num_type ) is 
  2732.   ---------------------------------
  2733.   --      Milestone Number
  2734.   ---------------------------------
  2735.   a_char      : character;         -- to see if the user wants to abort this function
  2736.   an_integer  : ms_num_type;
  2737.   found       : boolean;           -- parameter to FIND
  2738.   ms_record   : milestone_pointer; 
  2739.   valid_input : boolean := false;  -- if user input was valid
  2740.  
  2741.   begin
  2742.     abort_proc := false;
  2743.     while not valid_input loop
  2744.       begin
  2745.         -- ask abbreviated question
  2746.         put(" Milestone Number : ");
  2747.  
  2748.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2749.           skip_line;
  2750.           new_line;
  2751.           put_line(" Enter an integer in the range 1..99  ");
  2752.           new_line;
  2753.       DISPLAY_MILESTONE_DATA;
  2754.       new_line;
  2755.           put(" Milestone Number : ");
  2756.         end loop;
  2757.         get( an_integer ); skip_line;
  2758.         new_line(2);
  2759.  
  2760.         -- make sure milestone exists
  2761.         FIND( ms_list, an_integer, ms_record, found );
  2762.         valid_input := found;
  2763.        
  2764.         if not valid_input then  -- warn user, loop again
  2765.           put(" Sorry, but milestone "); 
  2766.           put( an_integer, 2);
  2767.           put(" does not exist. "); new_line;
  2768.           put_line(" You must enter an existing milestone. ");
  2769.           new_line;
  2770.           put_line(" Press the return key to see the list of existing milestones. ");
  2771.           put_line(" Enter 'a' to abort this procedure. ");
  2772.           put_line(" Enter any other key to continue. ");
  2773.           if end_of_line then  -- pressed <cr>, show ms list
  2774.             skip_line;
  2775.             DISPLAY_MILESTONE_DATA;
  2776.           else  -- loop again on any input except <cr> or 'a'
  2777.             get(a_char); skip_line;
  2778.             if a_char = 'a' or a_char = 'A' then
  2779.               abort_proc := true;
  2780.               valid_input := true;
  2781.             end if;
  2782.           end if;
  2783.         end if;
  2784.       exception
  2785.         when others => 
  2786.           skip_line;
  2787.           new_line;
  2788.           put_line(" Enter an integer in the range 1..99  ");
  2789.           new_line;
  2790.       DISPLAY_MILESTONE_DATA;
  2791.       new_line;
  2792.       end;
  2793.     end loop;
  2794.     key := an_integer;
  2795.   end EXISTING_MILSTONE_NUMBER;
  2796.  
  2797.  
  2798.  
  2799.   function NEW_MILSTONE_NUMBER return ms_num_type is 
  2800.   ---------------------------------
  2801.   --      Milestone Number
  2802.   ---------------------------------
  2803.   found       : boolean;           -- parameter to FIND
  2804.   an_integer  : ms_num_type;
  2805.   ms_record   : milestone_pointer; 
  2806.   valid_input : boolean := false;  -- if user input was valid
  2807.  
  2808.   begin
  2809.     while not valid_input loop
  2810.       begin
  2811.         -- ask abbreviated question
  2812.         put(" Milestone Number : ");
  2813.  
  2814.         while end_of_line loop  -- keep asking question if the user hits <cr>
  2815.           skip_line;
  2816.           new_line;
  2817.           put_line(" Enter an integer in the range 1..99  ");
  2818.           new_line;
  2819.       DISPLAY_MILESTONE_DATA;
  2820.       new_line;
  2821.           put(" Milestone Number : ");
  2822.         end loop;
  2823.         get( an_integer ); skip_line;
  2824.         new_line(2);
  2825.  
  2826.         --  check to see if this milestone exists
  2827.         FIND( ms_list, an_integer, ms_record, found );
  2828.         valid_input := not found;
  2829.        
  2830.         if not valid_input then  -- warn user, loop again
  2831.           put(" Sorry, but milestone "); 
  2832.           put( an_integer, 2);
  2833.           put(" already exists. "); new_line;
  2834.           put_line(" You must enter a new unique milestone. ");
  2835.           new_line;
  2836.           put_line(" Press the return key to see the list of existing milestones. ");
  2837.           put_line(" Enter any other key to continue. ");
  2838.           if end_of_line then  -- pressed <cr>, show ms list
  2839.             skip_line;
  2840.             DISPLAY_MILESTONE_DATA;
  2841.           else  -- loop again
  2842.             skip_line;
  2843.           end if;
  2844.         end if;
  2845.       exception
  2846.         when others => 
  2847.           skip_line;
  2848.           new_line;
  2849.           put_line(" Enter an integer in the range 1..99  ");
  2850.           new_line;
  2851.       DISPLAY_MILESTONE_DATA;
  2852.       new_line;
  2853.       end;
  2854.     end loop;
  2855.     return an_integer;
  2856.   end NEW_MILSTONE_NUMBER;
  2857.  
  2858.   function ELEMENT_PRIORITY ( default : in ms_num_type ) return ms_num_type is
  2859.     an_integer : ms_num_type;
  2860.   begin
  2861.     loop
  2862.       begin
  2863.         -- ask abbreviated question
  2864.         put(" Element Priority ( <cr> = milestone number ) : ");
  2865.  
  2866.         if end_of_line then -- default
  2867.           skip_line;
  2868.           new_line(2);
  2869.       return default;
  2870.     end if;
  2871.         get( an_integer ); skip_line;
  2872.         new_line(2);
  2873.         return an_integer;
  2874.       exception
  2875.         when others => 
  2876.           skip_line;
  2877.           new_line;
  2878.           put_line(" Enter an integer in the range 1..99  ");
  2879.           new_line;
  2880.       end;
  2881.     end loop;
  2882.   end ELEMENT_PRIORITY;
  2883.  
  2884.  
  2885.   function MILESTONE_COMPLETION_NUMBER ( default : in ms_num_type ) 
  2886.                                        return ms_num_type is
  2887.     an_integer : ms_num_type;
  2888.   begin
  2889.     loop
  2890.       begin
  2891.         -- ask abbreviated question
  2892.         put(" Milestone Completion Number ( <cr> = milestone number ) : ");
  2893.  
  2894.         if end_of_line then -- default
  2895.       skip_line;
  2896.           new_line(2);
  2897.           return default;
  2898.         end if;
  2899.         get( an_integer ); skip_line;
  2900.         new_line(2);
  2901.         return an_integer;
  2902.       exception
  2903.         when others => 
  2904.           skip_line;
  2905.           new_line(2);
  2906.           put_line(" Enter an integer in the range 1..99  ");
  2907.           new_line;
  2908.       end;
  2909.     end loop;
  2910.   end MILESTONE_COMPLETION_NUMBER;
  2911.  
  2912.  
  2913.  
  2914.   function CURRENT_SIZE_EST return integer is 
  2915.     ---------------------------------
  2916.     -- Current Size Estimate
  2917.     ---------------------------------
  2918.   an_integer  : integer range 0..99_999;
  2919.   valid_input : boolean := false;  -- if user input was valid
  2920.  
  2921.   begin
  2922.     while not valid_input loop
  2923.       begin
  2924.         -- ask abbreviated question
  2925.         put (" Current Size : ");
  2926.  
  2927.         while end_of_line loop -- keep asking question if the user hits <cr>
  2928.           skip_line;
  2929.           new_line;
  2930.           put_line(" What do you currently estimate the size of the element to be ? ");
  2931.           put_line(" Enter an integer in the range 0 to 99_999 ");
  2932.           new_line;
  2933.           put (" Current Size : ");
  2934.         end loop;
  2935.         get( an_integer ); skip_line;
  2936.         new_line(2);
  2937.         valid_input := true;
  2938.       exception
  2939.         when others =>  
  2940.           skip_line;
  2941.           new_line;
  2942.           put_line(" What do you currently estimate the size of the element to be ? ");
  2943.           put_line(" Enter an integer in the range 0 to 99_999 ");
  2944.           new_line;
  2945.       end;
  2946.     end loop;
  2947.     return an_integer;
  2948.   end CURRENT_SIZE_EST;
  2949.  
  2950.  
  2951.  
  2952.  
  2953.   function ORIG_SIZE_EST (default : in integer := 0) return integer is
  2954.     ---------------------------------
  2955.     -- Original Size Estimate
  2956.     ---------------------------------
  2957.   an_integer : integer range 0..99_999;
  2958.  
  2959.   begin
  2960.     loop
  2961.       begin
  2962.         -- ask abbreviated question
  2963.         put (" Original size ( <cr> = current size) : ");
  2964.  
  2965.         if end_of_line then -- default
  2966.           skip_line;
  2967.           new_line(2);
  2968.       return default;
  2969.     end if;
  2970.         get( an_integer ); skip_line;
  2971.         new_line(2);
  2972.         return an_integer;
  2973.       exception
  2974.         when others =>  
  2975.           skip_line;
  2976.           new_line(2);
  2977.           put_line(" What do you estimate the original size of the element to be ? ");
  2978.           put_line(" Enter an integer in the range 0 to 99_999  ");
  2979.           new_line;
  2980.       end;
  2981.     end loop;
  2982.   end ORIG_SIZE_EST;
  2983.  
  2984.   function  UPDATE_CURRENT_SIZE (old_size : in integer) return integer is 
  2985.     an_integer : integer range 0..99_999;
  2986.     
  2987.   begin
  2988.     loop
  2989.       begin
  2990.         -- ask abbreviated question
  2991.         set_col(51); put (" [ <cr> = no change ]"); new_line;
  2992.     put("     Old current size = ");
  2993.         put(old_size,1); new_line;
  2994.     put("     New current size : ");
  2995.  
  2996.         if end_of_line then  -- don't change the value
  2997.           skip_line;
  2998.           new_line(2);
  2999.           return old_size;
  3000.         else
  3001.           get( an_integer ); skip_line;
  3002.           new_line(2);
  3003.           return an_integer;
  3004.         end if;
  3005.       exception
  3006.         when others =>  skip_line;
  3007.           put_line(" Try something in the range 0 to 99_999. ");
  3008.           new_line;
  3009.       end;
  3010.     end loop;
  3011.   end UPDATE_CURRENT_SIZE;
  3012.  
  3013.   function COMPLEXITY_FACTOR return float is 
  3014.     ---------------------------------
  3015.     --  Complexity
  3016.     ---------------------------------
  3017.   a_float : float range 0.01..5.0 := 0.01;
  3018.  
  3019.   begin
  3020.     loop
  3021.       begin
  3022.         -- ask abbreviated question
  3023.         put (" Complexity [ <cr> = 1.0 ] : ");
  3024.  
  3025.         if end_of_line then -- default
  3026.       skip_line;
  3027.       a_float := 1.0;
  3028.           new_line(2);
  3029.       return a_float;
  3030.         end if;
  3031.         get( a_float ); skip_line;
  3032.         new_line(2);
  3033.     return a_float;
  3034.       exception
  3035.         when others =>  
  3036.           skip_line;
  3037.           new_line;
  3038.           put_line(" Enter a real number in the range 0.01 to 5.00 ");
  3039.           new_line;
  3040.       end;
  3041.     end loop;
  3042.   end COMPLEXITY_FACTOR;
  3043.  
  3044.  
  3045.  
  3046.   function ACTIV_COMPLETENESS return ACTIVITY_PHASE_PERCENT is 
  3047.     ---------------------------------
  3048.     --  Activity Completeness
  3049.     ---------------------------------
  3050.     a_char        : character := ' ';
  3051.     ac_record     : activity_pointer;  
  3052.     count         : integer   := 1;
  3053.     end_list      : boolean := false;  -- parameter to WALK
  3054.     ac_comp_array : activity_phase_percent := (others => ' ');  
  3055.             -- array of activity percents
  3056.     valid_input   : boolean := false;  -- if user input was valid
  3057.  
  3058.   begin
  3059.     begin
  3060.       -- ask abbreviated question, assuming the format is known.
  3061.       -- any fields not entered default to ' ' or 0
  3062.       put(" Activity Completeness : ");
  3063.  
  3064.       -- describe the input line in detail
  3065.       if end_of_line then  -- default
  3066.     skip_line;
  3067.     ac_comp_array := (others => ' ');  
  3068.     return ac_comp_array;
  3069.       end if;
  3070.  
  3071.       -- parse the input
  3072.       count := 1;
  3073.       while not end_of_line and count <= num_of_activities loop
  3074.         get( a_char ); 
  3075.         ac_comp_array(count) := convert(A_CHAR); 
  3076.         count := count + 1;
  3077.       end loop;
  3078.       skip_line;
  3079.       new_line(2);
  3080.       return ac_comp_array;
  3081.     exception -- ask expanded question
  3082.       when others =>
  3083.         ac_comp_array := (others => ' ');  
  3084.         skip_line;
  3085.         new_line(2);
  3086.         put_line(" For each activity, enter one character (0 through 9 or ' ', or 'd') ");
  3087.         put_line(" indicating that activity's completeness.  Put all the data on");
  3088.         put_line(" one input line.  ");
  3089.         new_line;
  3090.         put_line(" For Example:  ");
  3091.         put_line("      If you have 5 activities: HLD, DD, CD, UT, and I, ");
  3092.         put_line("      and you enter  ");
  3093.         new_line;
  3094.         put_line(" Activity Completeness :   d86 1 ");
  3095.         new_line;
  3096.         put_line("      HLD is 100% done.   DD is 80% done.  CD is 60% done. ");
  3097.         put_line("      UT  is 0%   done.   I  is 10% done.                  ");
  3098.         new_line;
  3099.         put_line(" Enter '?' if you would still like more help on how to ");
  3100.         put_line(" enter this data.  Otherwise, enter the data as described. ");
  3101.         new_line;
  3102.         put(" Activity Completeness :   ");
  3103.     end;
  3104.  
  3105.     -- prompt with the expanded question
  3106.     begin
  3107.       if end_of_line then  -- default
  3108.     skip_line;
  3109.     ac_comp_array := (others => ' ');  
  3110.     return ac_comp_array;
  3111.       end if;
  3112.       count := 1;
  3113.       while not end_of_line and count <= num_of_activities loop
  3114.         get( a_char ); 
  3115.         ac_comp_array(count) := convert(A_CHAR); 
  3116.         count := count + 1;
  3117.       end loop;
  3118.       skip_line;
  3119.       new_line(2);
  3120.       return ac_comp_array;
  3121.     exception
  3122.       when others =>
  3123.        -- prompt for each activity separately rather than on one line of input
  3124.         ac_comp_array := (others => ' ');  
  3125.         skip_line;
  3126.         new_line(2);
  3127.         put_line("You will be prompted for the completeness of each activity. ");
  3128.         new_line;
  3129.     end;
  3130.  
  3131.     -- prompt for the individual activities 
  3132.     START_WALK( ac_list );
  3133.     for i in 1..num_of_activities loop
  3134.       valid_input := false;
  3135.       WALK( ac_list, ac_record, end_list);
  3136.       while not end_list and not valid_input loop
  3137.         begin
  3138.           put(" How complete is activity ");  
  3139.           put(ac_record.name); put(" : ");
  3140.           if end_of_line then
  3141.             skip_line;
  3142.             valid_input := false;
  3143.           else
  3144.             get(a_char); 
  3145.             ac_comp_array(i) := CONVERT(a_char); 
  3146.         skip_line;
  3147.         valid_input := true;
  3148.       end if;
  3149.           new_line(2);
  3150.         exception
  3151.           when others => skip_line;
  3152.             ac_comp_array(i) := ' ';
  3153.             new_line(2);
  3154.             put_line(" That was not a valid value.  TRY AGAIN! ");
  3155.             put_line("  Enter a number from 0 to 9, or ' ', or 'd' to indicate the percent complete. ");
  3156.             put_line("  'd' or 'D' means it is 100% complete or Done.               ");
  3157.             put_line("  ' ' or '0' means it is 0% complete.                         ");
  3158.             put_line("  '1' means it is 10% complete.               ");
  3159.             put_line("  '2' means it is 20% complete.      etc.     ");
  3160.             new_line;
  3161.             valid_input := false;
  3162.         end;
  3163.       end loop;
  3164.     end loop;
  3165.  
  3166.     return ac_comp_array;
  3167.   end ACTIV_COMPLETENESS;
  3168.  
  3169.  
  3170.   function  UPDATE_ACTIV_COMPLETENESS 
  3171.         (old_pct_complete : in activity_phase_percent) 
  3172.         return ACTIVITY_PHASE_PERCENT is
  3173.   a_char      : character := ' ';
  3174.   count       : integer   := 1;
  3175.   ac_comp_array : activity_phase_percent := (others => ' ');  
  3176.         -- array of activity percents
  3177.  
  3178.   begin
  3179.     loop
  3180.       begin
  3181.         -- ask abbreviated question
  3182.  
  3183.         set_col(50); put (" [ <cr> = no change ]"); new_line;
  3184.     put("     Old percent complete = ");
  3185.         for i in 1..num_of_activities loop
  3186.           put( CONVERT(old_pct_complete(i)) );
  3187.         end loop;
  3188.         new_line;
  3189.     put("     New percent complete : ");
  3190.  
  3191.         if end_of_line then  -- don't change the value
  3192.           skip_line;
  3193.           new_line(2);
  3194.           return old_pct_complete;
  3195.         else
  3196.           while not end_of_line and count <= num_of_activities loop
  3197.             get( a_char ); 
  3198.             ac_comp_array(count) := convert(A_CHAR); 
  3199.             count := count + 1;
  3200.           end loop;
  3201.           skip_line;
  3202.           new_line(2);
  3203.           return ac_comp_array;
  3204.         end if;
  3205.       exception
  3206.         when others =>  skip_line;
  3207.           ac_comp_array := ( others => ' ');
  3208.           put_line("  That was not a valid value.  ");
  3209.           put_line("  Enter a number from 0 to 9, or ' ', or 'd' ");
  3210.           put_line("  to indicate the percent complete for each activity. ");
  3211.           new_line;
  3212.       end;
  3213.     end loop;
  3214.   end UPDATE_ACTIV_COMPLETENESS;
  3215.  
  3216.  
  3217.   ----------------------------------------------------------------------------
  3218.   --                      ACTIVITY DATA PROMPTS                             --
  3219.   ----------------------------------------------------------------------------
  3220.   procedure DISPLAY_ACTIVITY_DATA is
  3221.   ------------------------------------------------------------------------------
  3222.   --|
  3223.   --|  NAME:  DISPLAY_ACTIVITY_DATA
  3224.   --|
  3225.   --|  OVERVIEW:
  3226.   --|    This procedure walks the list and prints the name of each activity
  3227.   --|    to the screen.
  3228.   --|
  3229.   --|  EXCEPTIONS HANDLED:
  3230.   --|    none
  3231.   --|  
  3232.   --|  HISTORY:
  3233.   --|    Written by   May Lee   March 1985
  3234.   --|
  3235.   ------------------------------------------------------------------------------
  3236.   end_list  : boolean := false;
  3237.   ac_record : activity_pointer;
  3238.  
  3239.   begin
  3240.     if not EMPTY_LIST( ac_list ) then
  3241.       put_line(" The existing activities are : ");
  3242.       new_line;
  3243.       START_WALK( ac_list );
  3244.       end_list := false;
  3245.       loop
  3246.         WALK( ac_list, ac_record, end_list);
  3247.         exit when end_list;
  3248.         put(ac_record.name); new_line;
  3249.       end loop;
  3250.       new_line;
  3251.     end if;
  3252.   end DISPLAY_ACTIVITY_DATA;
  3253.  
  3254.   procedure EXISTING_ACTIV_NAME ( abort_proc : out boolean;
  3255.                             key : out ac_name_type ) is 
  3256.   -- want to modify or delete and existing activity
  3257.   ---------------------------------
  3258.   --  Activity Name
  3259.   ---------------------------------
  3260.   a_char      : character;         -- to see if the user wants to abort this function
  3261.   ac_record   : activity_pointer;  
  3262.   found       : boolean;           -- parameter to FIND
  3263.   valid_input : boolean := false;  -- if user input was valid
  3264.  
  3265.   begin
  3266.     abort_proc  := false;
  3267.     while not valid_input loop
  3268.       begin
  3269.         -- blank out the input line
  3270.         line := (others => ' ');
  3271.  
  3272.         -- ask abbreviated question
  3273.         put(" Activity Name : ");
  3274.  
  3275.         while end_of_line loop -- keep asking question if the user hits <cr>
  3276.           skip_line;
  3277.           new_line;
  3278.           put_line(" Enter the name of the activity which is a ");
  3279.           put_line(" string of up to 10 characters.");
  3280.           new_line;
  3281.       DISPLAY_ACTIVITY_DATA;
  3282.       new_line;
  3283.           put(" Activity Name : ");
  3284.         end loop;
  3285.  
  3286.         get_line(line,line_lngth);
  3287.         new_line(2);
  3288.         
  3289.     if line(1) = '?' then
  3290.           new_line;
  3291.           put_line(" Enter the name of the activity which is a ");
  3292.           put_line(" string of up to 10 characters.");
  3293.           new_line;
  3294.       DISPLAY_ACTIVITY_DATA;
  3295.       new_line;
  3296.     else
  3297.           -- check to see if this activity exists
  3298.           FIND( ac_list, line(1..act_name_max_len), ac_record, found );
  3299.           valid_input := found;
  3300.       
  3301.           if not valid_input then  -- warn user, loop again
  3302.             put(" Sorry, but activity "); 
  3303.             put( line(1..line_lngth) );
  3304.             put(" does not exist. "); new_line;
  3305.             put_line(" You must enter an existing activity. ");
  3306.             new_line;
  3307.             put_line(" Press the return key to see the list of existing activities. ");
  3308.             put_line(" Enter 'a' to abort this procedure ");
  3309.             put_line(" Enter any other key to continue. ");
  3310.             if end_of_line then  -- pressed <cr>, show ac list
  3311.               skip_line;
  3312.               DISPLAY_ACTIVITY_DATA;
  3313.             else  -- loop again on any input except <cr> or 'a'
  3314.               get(a_char); skip_line;
  3315.               if a_char = 'a' or a_char = 'A' then
  3316.                 abort_proc := true;
  3317.                 valid_input := true;
  3318.               end if;
  3319.             end if;
  3320.           end if;
  3321.         end if;
  3322.  
  3323.       exception
  3324.         when others => 
  3325.           skip_line;
  3326.           new_line;
  3327.           put_line(" Enter the name of the activity which is a ");
  3328.           put_line(" string of up to 10 characters.");
  3329.           new_line;
  3330.       DISPLAY_ACTIVITY_DATA;
  3331.       new_line;
  3332.       end;
  3333.     end loop;
  3334.  
  3335.     key := line(1..act_name_max_len);
  3336.   end EXISTING_ACTIV_NAME;
  3337.  
  3338.  
  3339.  
  3340.   function NEW_ACTIV_NAME return ac_name_type is 
  3341.   ---------------------------------
  3342.   --  Activity Name
  3343.   ---------------------------------
  3344.   found       : boolean;           -- parameter to FIND
  3345.   ac_record   : activity_pointer;  
  3346.   valid_input : boolean := false;  -- if user input was valid
  3347.  
  3348.   begin
  3349.     while not valid_input loop
  3350.       begin
  3351.         -- blank out the input line
  3352.         line := (others => ' ');
  3353.  
  3354.         -- ask abbreviated question
  3355.         put(" Activity Name : ");
  3356.  
  3357.         while end_of_line loop  -- keep asking question if the user hits <cr>
  3358.           skip_line;
  3359.           new_line;
  3360.           put_line(" Enter the name of the activity which is a ");
  3361.           put_line(" string of up to 10 characters.");
  3362.           new_line;
  3363.       DISPLAY_ACTIVITY_DATA;
  3364.       new_line;
  3365.           put(" Activity Name : ");
  3366.         end loop;
  3367.         get_line(line,line_lngth);
  3368.         new_line(2);
  3369.         
  3370.     if line(1) = '?' then
  3371.           new_line;
  3372.           put_line(" Enter the name of the activity which is a ");
  3373.           put_line(" string of up to 10 characters.");
  3374.           new_line;
  3375.       DISPLAY_ACTIVITY_DATA;
  3376.       new_line;
  3377.     else
  3378.           --  check to see if this ac is defined
  3379.           FIND( ac_list, line(1..act_name_max_len), ac_record, found );
  3380.           valid_input := not found;
  3381.       
  3382.           if not valid_input then  -- warn user, loop again
  3383.             put(" Sorry, but activity "); 
  3384.             put( line(1..line_lngth) );
  3385.             put(" already exists. "); new_line;
  3386.             put_line(" You must enter a new unique activity. ");
  3387.             new_line;
  3388.             put_line(" Press the return key to see the list of existing activities. ");
  3389.             put_line(" Enter any other key to continue. ");
  3390.             if end_of_line then  -- pressed <cr>, show aclist
  3391.               skip_line;
  3392.               DISPLAY_ACTIVITY_DATA;
  3393.             else  -- loop again on any input except <cr> 
  3394.               skip_line;
  3395.             end if;
  3396.           end if;
  3397.         end if;
  3398.  
  3399.       exception
  3400.         when others => 
  3401.           skip_line;
  3402.           new_line;
  3403.           put_line(" Enter the name of the activity which is a ");
  3404.           put_line(" string of up to 10 characters.");
  3405.           new_line;
  3406.       end;
  3407.     end loop;
  3408.     return line(1..act_name_max_len);
  3409.   end NEW_ACTIV_NAME;
  3410.  
  3411.  
  3412.  
  3413.   function ACTIV_PRIORITY return integer is 
  3414.   ---------------------------------
  3415.   -- Activity Priority
  3416.   ---------------------------------
  3417.   an_integer : integer range 1..10;
  3418.  
  3419.   begin
  3420.     loop
  3421.       begin
  3422.         -- ask abbreviated question
  3423.         put (" Priority : ");
  3424.  
  3425.         while end_of_line loop  -- keep asking question if the user hits <cr>
  3426.           skip_line;
  3427.           new_line;
  3428.           put_line(" Enter the priority of the activity on a scale of 1 to 10. ");
  3429.           new_line;
  3430.           put (" Priority : ");
  3431.         end loop;
  3432.         get( an_integer ); skip_line;
  3433.         new_line(2);
  3434.         exit;
  3435.       exception
  3436.         when others =>  
  3437.           skip_line;
  3438.           new_line;
  3439.           put_line(" Enter the priority of the activity on a scale of 1 to 10. ");
  3440.           new_line;
  3441.       end;
  3442.     end loop;
  3443.     return an_integer;
  3444.   end ACTIV_PRIORITY;
  3445.  
  3446.  
  3447.  
  3448.   function CONSIDER_AC_IN_CALC return boolean is 
  3449.   ---------------------------------
  3450.   --  Consider this activity in the Tracker calculations
  3451.   ---------------------------------
  3452.   a_char   : character := 'y';
  3453.  
  3454.   begin
  3455.     loop
  3456.       begin
  3457.         -- ask abbreviated question
  3458.         put (" Consider [ y or n  <cr>=y ] : ");
  3459.  
  3460.         if end_of_line then  -- keep asking question if the user hits <cr>
  3461.           skip_line;
  3462.           new_line(2);
  3463.           return true;
  3464.         end if;
  3465.         get( a_char); skip_line;
  3466.         new_line(2);
  3467.         if a_char = 'Y' or a_char = 'y' then
  3468.           return true;
  3469.         elsif a_char = 'N' or a_char = 'n' then
  3470.           return false;
  3471.         end if;
  3472.         put(" Do you want to consider this activity in the ");
  3473.         put_line("Tracker calculations? ");
  3474.         new_line;
  3475.       exception
  3476.         when others =>  
  3477.           skip_line;
  3478.           new_line(2);
  3479.           put(" Do you want to consider this activity in the ");
  3480.           put_line("Tracker calculations? ");
  3481.           new_line;
  3482.         end;
  3483.     end loop;
  3484.   end CONSIDER_AC_IN_CALC;
  3485.  
  3486.  
  3487.  
  3488. ----------------------------------------------------------------------------
  3489. --                          MILESTONE DATA
  3490. ----------------------------------------------------------------------------
  3491.  
  3492.  
  3493.   function MS_DESCRIPTION return string is 
  3494.   ---------------------------------
  3495.   --  Milestone Description
  3496.   ---------------------------------
  3497.   begin
  3498.     loop
  3499.       -- blank out the input line
  3500.       line := (others => ' ');
  3501.  
  3502.       -- ask abbreviated question
  3503.       put_line(" Milestone description : ");
  3504.       new_line;
  3505.  
  3506.       while end_of_line loop  -- keep asking question if the user hits <cr>
  3507.         skip_line;
  3508.         put_line(" Enter the description of the milestone in 50 characters or less : ");
  3509.         new_line;
  3510.       end loop;
  3511.       
  3512.       -- get the record field
  3513.       get_line(line,line_lngth);
  3514.       new_line(2);
  3515.       if line(1) = '?' then
  3516.         put_line(" Enter the description of the milestone in 50 characters or less : ");
  3517.         new_line;
  3518.       else 
  3519.         return line(1..50);
  3520.       end if;
  3521.     end loop;
  3522.   end MS_DESCRIPTION;
  3523.  
  3524.  
  3525. ----------------------------------------------------------------------------
  3526. --                   PERSONNEL DATA PROMPTS
  3527. ----------------------------------------------------------------------------
  3528.  
  3529.  
  3530.   function PERSONS_NAME return string is 
  3531.   ---------------------------------
  3532.   --  Person's Name
  3533.   ---------------------------------
  3534.   begin
  3535.     loop
  3536.       -- blank out the input line
  3537.       line := (others => ' ');
  3538.   
  3539.       -- ask abbreviated question
  3540.       put(" Person's Name : ");
  3541.  
  3542.       while end_of_line loop  -- keep asking question if the user hits <cr>
  3543.         skip_line;
  3544.         new_line;
  3545.         put_line(" Enter the name of the person in 20 characters or less. ");
  3546.         put_line(" Anything longer will be truncated. ");
  3547.         new_line;
  3548.         put(" Person's Name : ");
  3549.       end loop;
  3550.       
  3551.       -- get the record field
  3552.       get_line(line,line_lngth);
  3553.       new_line(2);
  3554.       if line(1) = '?' then
  3555.         new_line;
  3556.         put_line(" Enter the name of the person in 20 characters or less. ");
  3557.         put_line(" Anything longer will be truncated. ");
  3558.         new_line;
  3559.       else
  3560.         return line(1..20);
  3561.       end if;
  3562.     end loop;
  3563.   end PERSONS_NAME;
  3564.  
  3565.  
  3566.  
  3567.   function PR_PRODUCTION_RATE return float is 
  3568.   ---------------------------------
  3569.   --  Person's production rate
  3570.   ---------------------------------
  3571.   a_float : float range 0.01..99.99 := 1.00;
  3572.  
  3573.   begin
  3574.     loop
  3575.       begin
  3576.         -- ask abbreviated question
  3577.         put (" Production Rate ( <cr> = 1.0) : ");
  3578.  
  3579.         if end_of_line then -- default
  3580.           skip_line;
  3581.           new_line(2);
  3582.       return 1.0;
  3583.         end if;
  3584.         get( a_float ); skip_line;
  3585.         new_line(2);
  3586.         return a_float;
  3587.       exception  -- default value
  3588.         when others =>  
  3589.           skip_line;
  3590.           new_line(2);
  3591.           put_line(" How many units of work can this person complete per hour ? ");
  3592.           put_line(" Enter a float in the range 0.01..99.99  "); 
  3593.           new_line;          
  3594.       end;
  3595.     end loop;
  3596.   end PR_PRODUCTION_RATE;
  3597.  
  3598.  
  3599.  
  3600.   function PR_HRS_PER_WEEK return integer is 
  3601.   ---------------------------------
  3602.   -- Hours per week the person works
  3603.   ---------------------------------
  3604.   an_integer : integer range 1..84 := 40;
  3605.  
  3606.   begin
  3607.     loop
  3608.       begin
  3609.         -- ask abbreviated question
  3610.         put (" Hours Per Week ( <cr> = 40) : ");
  3611.  
  3612.         if end_of_line then -- default
  3613.       skip_line;
  3614.           new_line(2);
  3615.           return 40;
  3616.         end if;
  3617.         get( an_integer ); skip_line;
  3618.         new_line(2);
  3619.         return an_integer;
  3620.       exception  -- default value
  3621.         when others =>  
  3622.           skip_line;
  3623.           new_line;
  3624.           put_line(" How many hours per week (1..84) does this person work ? ");
  3625.           put_line(" The default is 40 hours.  Press <cr> for the default. ");
  3626.           new_line;
  3627.       end;
  3628.     end loop;
  3629.   end PR_HRS_PER_WEEK;
  3630.  
  3631.  
  3632.  
  3633.   function PERCENT return float is 
  3634.   ---------------------------------
  3635.   --  Percent value
  3636.   ---------------------------------
  3637.   a_float : float range 0.0..100.0 := 0.0;
  3638.  
  3639.   begin
  3640.     loop
  3641.       begin
  3642.         -- ask abbreviated question
  3643.         put (" Percent ( <cr> = 0.0) : ");
  3644.  
  3645.         if end_of_line then -- default
  3646.       skip_line;
  3647.           a_float     := 0.0;
  3648.           new_line(2);
  3649.         else
  3650.           get( a_float ); skip_line;
  3651.           new_line(2);
  3652.         end if;
  3653.         exit;
  3654.       exception  -- keep prompting the user until he enters a valid number
  3655.         when others =>  
  3656.           skip_line;
  3657.           new_line;
  3658.           put_line(" Enter a number in the range 0.0 .. 100.0  ");
  3659.           new_line;
  3660.       end;
  3661.     end loop;
  3662.     return a_float;
  3663.   end PERCENT;
  3664.  
  3665.  
  3666.  
  3667.   function DATE return DATE_TYPE is
  3668.   -----------------------------------
  3669.   --          DATE
  3670.   -----------------------------------
  3671.   -- This function prompts for and returns a valid date (month, day and year).
  3672.  
  3673.     day_integer    : integer := 0;     -- user input date on one line
  3674.     default        : boolean := false; -- if the user chooses the default date
  3675.     dummy_char     : character;        -- character to separate date '/'
  3676.     month_integer  : integer := 0;     -- user input date on one line
  3677.     user_input     : boolean := false; -- if the user entered date on one line
  3678.     valid_date     : date_type;        -- the date returned
  3679.     valid_day      : DAY_NUMBER;       -- day from detailed item prompt
  3680.     valid_input    : boolean := false; -- if input is within type range
  3681.     valid_month    : MONTH_NUMBER;     -- month from detailed item prompt
  3682.     valid_year     : YEAR_NUMBER;      -- year from detailed item prompt
  3683.     year_integer   : integer := 0;     -- user input date on one line
  3684.    
  3685.  
  3686.  
  3687.   function MONTH return MONTH_NUMBER is
  3688.   ---------------------------------
  3689.   -- Month for type date_type
  3690.   ---------------------------------
  3691.  
  3692.   begin
  3693.     valid_input := false;
  3694.     while not valid_input loop
  3695.       begin
  3696.         -- ask abbreviated question
  3697.         put (" Month (1..12) : ");
  3698.  
  3699.         while end_of_line loop  -- keep asking question if the user hits <cr>
  3700.           skip_line;
  3701.           put (" Enter the month (1..12) : ");
  3702.         end loop;
  3703.         get( valid_month ); skip_line;
  3704.         new_line(2);
  3705.         valid_input := true;
  3706.       exception
  3707.         when others =>  
  3708.           skip_line;
  3709.           put_line (" What is the number of the month?");
  3710.           new_line;
  3711.           valid_input := false;
  3712.       end;
  3713.     end loop;
  3714.     return valid_month;
  3715.   end MONTH;
  3716.  
  3717.  
  3718.  
  3719.   function DAY return DAY_NUMBER is
  3720.   ---------------------------------
  3721.   -- Day in date_type
  3722.   ---------------------------------
  3723.  
  3724.   begin
  3725.     valid_input := false;
  3726.     while not valid_input loop
  3727.       begin
  3728.         -- ask abbreviated question
  3729.         put (" Day (1..31) : ");
  3730.  
  3731.         while end_of_line loop  -- keep asking question if the user hits <cr>
  3732.           skip_line;
  3733.           new_line;
  3734.           put (" Enter the day of the month (1..31) : ");
  3735.         end loop;
  3736.         get( valid_day ); skip_line;
  3737.         new_line(2);
  3738.         valid_input := true;
  3739.       exception
  3740.         when others =>  skip_line;
  3741.           new_line;
  3742.           put_line (" What is the day of the month? ");
  3743.           new_line;
  3744.           valid_input := false;
  3745.       end;
  3746.     end loop;
  3747.     return valid_day;
  3748.   end DAY;
  3749.  
  3750.  
  3751.  
  3752.   function YEAR return YEAR_NUMBER is
  3753.   ---------------------------------
  3754.   -- Year in date_type
  3755.   ---------------------------------
  3756.  
  3757.   begin
  3758.     valid_input := false;
  3759.     while not valid_input loop
  3760.       begin
  3761.         -- ask abbreviated question
  3762.         put (" Year (1901..2099) : ");
  3763.  
  3764.         while end_of_line loop  -- keep asking question if the user hits <cr>
  3765.           skip_line;
  3766.           new_line;
  3767.           put (" Enter is the year (1901..2099) : ");
  3768.         end loop;
  3769.         get( valid_year ); skip_line;
  3770.         new_line(2);
  3771.         valid_input := true;
  3772.       exception
  3773.         when others =>  skip_line;
  3774.           valid_input := false;
  3775.           new_line;
  3776.           put_line (" What is the year ? ");
  3777.           new_line;
  3778.       end;
  3779.     end loop;
  3780.     return valid_year;
  3781.   end YEAR;
  3782.  
  3783.   begin
  3784.     loop
  3785.       put(" e.g. 12/6/1985  ( <cr> = null date) : ");
  3786.       if end_of_line then
  3787.         skip_line;
  3788.         new_line(2);
  3789.         return null_date;
  3790.       else
  3791.         begin
  3792.           -- get the date
  3793.           get( month_integer ); 
  3794.           if not end_of_line then
  3795.             get( dummy_char );  -- the slash between numbers
  3796.           end if;
  3797.           if not end_of_line then
  3798.             get( day_integer ); 
  3799.           end if;
  3800.           if not end_of_line then
  3801.             get( dummy_char );  -- the slash between numbers
  3802.           end if;
  3803.           if not end_of_line then
  3804.             get( year_integer ); 
  3805.           end if;
  3806.           skip_line;
  3807.           new_line(2);
  3808.  
  3809.           if not VALID( month_integer, day_integer, year_integer ) then
  3810.             put_line(" That was not a valid date! ");
  3811.             loop
  3812.               valid_month := MONTH;
  3813.               valid_day   := DAY;
  3814.               valid_year  := YEAR;
  3815.               if VALID( valid_month, valid_day, valid_year ) then
  3816.                 return ( valid_month, valid_day, valid_year );
  3817.               end if;
  3818.               put_line(" That was not a valid date! ");
  3819.             end loop;
  3820.          end if;
  3821.         return ( month_integer, day_integer, year_integer );
  3822.         exception
  3823.           when others => -- user wants more information
  3824.             skip_line;
  3825.             put_line(" Enter month/day/year where the month is 1..12, the day ");
  3826.            put_line(" is 1..31, and the year is 1901..2099 ");
  3827.             new_line;
  3828.         end;
  3829.       end if;
  3830.     end loop;
  3831.   end DATE;
  3832.  
  3833. end PROMPT_PKG;
  3834. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  3835. --tracker.ada
  3836. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  3837. with vt100;              use VT100;
  3838. with text_io;            use text_io;
  3839. with data_pkg;           use data_pkg;
  3840.  
  3841. procedure TRACKER is
  3842. ----------------------------------------------------------------------
  3843. --|  NAME:  TRACKER  - Main
  3844. --|
  3845. --|  OVERVIEW:
  3846. --|    TRACKER is an ADA conversion of the original INPREP and TRACKR 
  3847. --|    programs written in IFTRAN.  The Ada version of TRACKER is one
  3848. --|    program that combines the two previous Iftran programs.  It is
  3849. --|    written under the VAX/VMS Version 4.0 environment.
  3850. --|
  3851. --|    The TRACKER program is a management tool used for estimating 
  3852. --|    project cost and scheduling requirements, and tracking progress
  3853. --|    within projects by calculating dates of completion, amount of time
  3854. --|    required, amount of code, and other variable data.
  3855. --|    Reports can be produced that will show the status of the project
  3856. --|    from several different perspectives.
  3857. --|
  3858. --|  EXCEPTIONS HANDLED:
  3859. --|    name_error            error message is printed and program terminates
  3860. --|    ERROR_IN_INPUT_FILE   error message is printed and program terminates
  3861. --|
  3862. --|  HISTORY:
  3863. --|    written by   May Lee   March 1985
  3864. --|
  3865. ----------------------------------------------------------------------
  3866.  
  3867.   -- instantiate I/O packages
  3868.   use FLOAT_TEXT_IO;
  3869.   use INTEGER_TEXT_IO;
  3870.  
  3871.   -- user response line
  3872.   max_line_lngth : natural := 200;       
  3873.   line           : string(1..max_line_lngth) := (others=>' ');  
  3874.   line_lngth     : natural;
  3875.  
  3876.   error_in_input_file : exception;
  3877.  
  3878.   report_file,                -- internal filename for the tracker output
  3879.                               -- file of reports generated
  3880.   tracker_file,               -- internal filename for the tracker input
  3881.                               -- file (in_file)
  3882.   output_file : file_type;    -- internal filename for output file(out_file)
  3883.                               -- it is the same name as the input file.
  3884.   
  3885.   report_filename  : string(1..80) := (others => ' ');
  3886.   -- external name of the VAX tracker report file.  It will be the same name
  3887.   -- as the input file with a ".rpt" extension instead.
  3888.  
  3889.   tracker_filename : string(1..80) := (others => ' ');
  3890.   -- external name of the VAX tracker file.  This is the name for the input
  3891.   -- file and the output file, the output file being a new version of the input.
  3892.  
  3893.   filename_lngth      : natural;   -- length of the tracker filename
  3894.  
  3895.   -- package specifications
  3896.   package global_pkg is
  3897.     procedure GL_SET_UP;
  3898.     procedure GL_INITIALIZE;
  3899.     procedure GL_SAVE;
  3900.   end global_pkg;
  3901.  
  3902.   package activity_pkg is
  3903.     procedure AC_SET_UP;
  3904.     procedure AC_INITIALIZE;
  3905.     procedure AC_ADD;
  3906.     procedure AC_DELETE;
  3907.     procedure AC_MODIFY;
  3908.     procedure AC_SAVE;
  3909.  end activity_pkg;
  3910.  
  3911.   package element_pkg is
  3912.     procedure EL_SET_UP;
  3913.     procedure EL_INITIALIZE;
  3914.     procedure UPDATE_CURRENT;
  3915.     procedure UPDATE_PCT_DONE;
  3916.     procedure EL_ADD;
  3917.     procedure EL_DELETE;
  3918.     procedure EL_MODIFY;
  3919.     procedure EL_SAVE;
  3920.  end element_pkg;
  3921.  
  3922.   package milestone_pkg is
  3923.     procedure MS_SET_UP;
  3924.     procedure MS_INITIALIZE;
  3925.     procedure MS_ADD;
  3926.     procedure MS_DELETE;
  3927.     procedure MS_MODIFY;
  3928.     procedure MS_SAVE;
  3929.   end milestone_pkg;
  3930.  
  3931.   package personnel_pkg is
  3932.     procedure PR_SET_UP;
  3933.     procedure PR_INITIALIZE;
  3934.     procedure PR_ADD;
  3935.     procedure PR_DELETE;
  3936.     procedure PR_MODIFY;
  3937.     procedure PR_SAVE;
  3938.   end personnel_pkg;
  3939.  
  3940.   package subsystem_pkg is
  3941.     procedure SS_SET_UP;
  3942.     procedure SS_INITIALIZE;
  3943.     procedure SS_ADD;
  3944.     procedure SS_DELETE;
  3945.     procedure SS_MODIFY;
  3946.     procedure SS_SAVE;
  3947.   end subsystem_pkg;
  3948.  
  3949.   package body global_pkg    is separate;
  3950.   package body activity_pkg  is separate;
  3951.   package body element_pkg   is separate;
  3952.   package body milestone_pkg is separate;
  3953.   package body personnel_pkg is separate;
  3954.   package body subsystem_pkg is separate;
  3955.  
  3956.   procedure WRITE_DATA_TO_FILE      is separate;
  3957.   procedure SET_UP_TRACKER_DATA     is separate;
  3958.   procedure INITIALIZE_TRACKER_DATA is separate;
  3959.   procedure DATA_MENU_DRIVER        is separate;
  3960.   procedure GET_DATA                is separate;
  3961.   procedure MANIPULATE_DATA         is separate;
  3962.   procedure REPORT_GENERATOR        is separate;
  3963.  
  3964.   use CALENDAR;
  3965.  
  3966. begin
  3967.   TRACKER_INTRO;
  3968.   GET_DATA;
  3969.   MANIPULATE_DATA;
  3970.   WRITE_DATA_TO_FILE;
  3971.  
  3972.   --              TRACKER     --
  3973.   -- if answer to "Do you want to change or modify data?" was No
  3974.   -- or if already manipulated data (done with INPREP) ...
  3975.   -- then go to report menu (TRACKR part).
  3976.   REPORT_GENERATOR; 
  3977.  
  3978. exception
  3979.   when name_error =>
  3980.     new_line(2); 
  3981.     put("Sorry, TRACKER file ");put(tracker_filename(1..filename_lngth));
  3982.     put(" cannot be opened.");
  3983.     new_line(2); 
  3984.     put("    * * *  EXECUTION TERMINATED  * * * ");
  3985.     new_line(2); 
  3986.   when ERROR_IN_INPUT_FILE => 
  3987.     put("Sorry, error reading TRACKER file ");
  3988.     put(tracker_filename(1..filename_lngth));
  3989.     new_line(2); 
  3990.     put("    * * *  EXECUTION TERMINATED  * * * ");
  3991. end TRACKER;
  3992. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  3993. --inittr.ada
  3994. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  3995. with text_io; use text_io;
  3996. separate(tracker)
  3997.  
  3998. procedure INITIALIZE_TRACKER_DATA is
  3999. --------------------------------------------------------------------------------
  4000. --|
  4001. --|  NAME:  INITIALIZE_TRACKER_DATA
  4002. --|
  4003. --|  OVERVIEW:
  4004. --|    This procedure calls the individual data initialize procedures in
  4005. --|    a specific order to obtain the tracker information needed to make a
  4006. --|    complete tracker file.  The internal data structures are created
  4007. --|    and the data is written to the tracker file.  The name of the output 
  4008. --|    file is obtained in this procedure, but the file is actually created 
  4009. --|    just before the write in the procedure WRITE_DATA_TO_FILE.
  4010. --|
  4011. --|  EXCEPTIONS HANDLED:
  4012. --|    none
  4013. --| 
  4014. --|  HISTORY:
  4015. --|    Written by   May Lee   March 1985
  4016. --|
  4017. --------------------------------------------------------------------------------
  4018. begin
  4019.   VT100.CLEAR_SCREEN;
  4020.   put_line("Please enter the TRACKER filename you want created");
  4021.   get_line(tracker_filename,filename_lngth); 
  4022.   new_line;
  4023.   GLOBAL_PKG.GL_INITIALIZE;
  4024.   ACTIVITY_PKG.AC_INITIALIZE;
  4025.   MILESTONE_PKG.MS_INITIALIZE;
  4026.   PERSONNEL_PKG.PR_INITIALIZE;
  4027.   SUBSYSTEM_PKG.SS_INITIALIZE;
  4028.   ELEMENT_PKG.EL_INITIALIZE;
  4029.   CLEAR_SCREEN;
  4030. end INITIALIZE_TRACKER_DATA;
  4031. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4032. --setuptr.ada
  4033. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4034. with text_io; use text_io;
  4035.  
  4036. separate(tracker)
  4037. procedure SET_UP_TRACKER_DATA is
  4038. ----------------------------------------------------------------------
  4039. --|
  4040. --|  NAME:  SET_UP_TRACKER_DATA
  4041. --|
  4042. --|  OVERVIEW:
  4043. --|    This procedure opens the tracker input file and calls the 
  4044. --|    individual data set_up procedures in a specified order to 
  4045. --|    read in the tracker data from the file and set up the 
  4046. --|    internal data structures.
  4047. --|
  4048. --|  EXCEPTIONS HANDLED:
  4049. --|    name_error   if the given file can't be opened
  4050. --|    .            raised to the calling routine
  4051. --|    others       ERROR_IN_INPUT_FILE is raised
  4052. --|  
  4053. --|  HISTORY:
  4054. --|    Written by   May Lee   March 1985
  4055. --|
  4056. ----------------------------------------------------------------------
  4057.  
  4058.   bad_data : boolean := false;
  4059.  
  4060. begin
  4061.   VT100.CLEAR_SCREEN;
  4062.   put_line("Please enter the TRACKER filename: ");
  4063.   get_line(tracker_filename,filename_lngth);
  4064.   open(tracker_file, in_file, tracker_filename, "");
  4065.   new_line;
  4066.   put_line(" Reading the data from file ....  ");
  4067.   new_line;
  4068.   begin
  4069.     GLOBAL_PKG.GL_SET_UP;
  4070.   exception
  4071.     when others => bad_data := true;
  4072.   end;
  4073.  
  4074.   begin
  4075.     ACTIVITY_PKG.AC_SET_UP;
  4076.   exception
  4077.     when others => bad_data := true;
  4078.   end;
  4079.  
  4080.   begin
  4081.     MILESTONE_PKG.MS_SET_UP;
  4082.   exception
  4083.     when others => bad_data := true;
  4084.   end;
  4085.  
  4086.   begin
  4087.     PERSONNEL_PKG.PR_SET_UP;
  4088.   exception
  4089.     when others => bad_data := true;
  4090.   end;
  4091.  
  4092.   begin
  4093.     SUBSYSTEM_PKG.SS_SET_UP;
  4094.   exception
  4095.     when others => bad_data := true;
  4096.   end;
  4097.  
  4098.   begin
  4099.     ELEMENT_PKG.EL_SET_UP;
  4100.   exception
  4101.     when others => bad_data := true;
  4102.   end;
  4103.  
  4104.   close(tracker_file);
  4105.   if bad_data then
  4106.     raise ERROR_IN_INPUT_FILE;
  4107.   end if;
  4108. exception
  4109.   when NAME_ERROR =>   raise;
  4110.   when others     =>   
  4111.         if IS_OPEN(tracker_file) then
  4112.           close(tracker_file);
  4113.         end if;
  4114.     raise ERROR_IN_INPUT_FILE;
  4115. end SET_UP_TRACKER_DATA;
  4116. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4117. --mandata.ada
  4118. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4119. separate (TRACKER)
  4120. procedure MANIPULATE_DATA is
  4121. ----------------------------------------------------------------------
  4122. --|  NAME:  MANIPULATE_DATA 
  4123. --|
  4124. --|  OVERVIEW:
  4125. --|    This is the main driver for manipulating and adding data.
  4126. --|    This procedure calls the menu driver and the other necessary
  4127. --|    routines to validate the data and calculate data needed to
  4128. --|    print reports before the data is written to file.
  4129. --|
  4130. --|  EXCEPTIONS HANDLED:
  4131. --|    none
  4132. --|
  4133. --|  HISTORY:
  4134. --|    written by   May Lee   March 1985
  4135. --|    written by   Bonnie Burkhardt   March 1985
  4136. ----------------------------------------------------------------------
  4137.  
  4138.   char_input          : character;         -- user response character
  4139.   valid_response      : boolean := false;  --  if user response to prompt is legal
  4140.  
  4141.   procedure CHECK_AC_PERCENT is separate;
  4142.   procedure GROUP_DATA_FIXES is separate;
  4143.   procedure PRIORITIZE is separate;
  4144.   procedure CALC_TIME_DONE is separate;
  4145.  
  4146. begin
  4147.   while not valid_response loop
  4148.     put_line(" Would you like to modify the TRACKER data? ");
  4149.     put(" [ Y or N, <cr>=Y ] : ");
  4150.     begin
  4151.       if end_of_line then  -- pressed return, default is yes
  4152.         skip_line;
  4153.         DATA_MENU_DRIVER;
  4154.         CHECK_AC_PERCENT;        
  4155.     GROUP_DATA_FIXES;
  4156.         valid_response := true;
  4157.       else
  4158.         get( char_input ); skip_line;
  4159.         if char_input = 'Y' or char_input = 'y' then
  4160.           DATA_MENU_DRIVER;
  4161.           CHECK_AC_PERCENT;        
  4162.       GROUP_DATA_FIXES;
  4163.           valid_response := true;
  4164.         elsif char_input = 'N' or char_input = 'n' then
  4165.           -- no changes, print the reports
  4166.           CHECK_AC_PERCENT;        
  4167.           valid_response := true;
  4168.         else
  4169.           -- invalid entry
  4170.           put_line("Please enter 'Y' or 'N' ");
  4171.           delay 0.7;
  4172.           CLEAR_SCREEN;
  4173.         end if;
  4174.       end if;
  4175.     exception
  4176.       when name_error => raise;
  4177.       when ERROR_IN_INPUT_FILE => raise;
  4178.       when others => 
  4179.         skip_line;
  4180.         -- invalid entry
  4181.         put_line("Please enter 'Y' or 'N' ");
  4182.         delay 0.7;
  4183.         CLEAR_SCREEN;
  4184.     end;
  4185.   end loop;
  4186.   PRIORITIZE;
  4187.   CALC_TIME_DONE;
  4188. end MANIPULATE_DATA;
  4189. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4190. --prior.ada
  4191. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4192. separate(TRACKER.MANIPULATE_DATA)
  4193. procedure PRIORITIZE is
  4194. --------------------------------------------------------------------------------
  4195. --|
  4196. --|  NAME:  PRIORITIZE 
  4197. --|
  4198. --|  OVERVIEW:
  4199. --|    This procedure sorts the element lists according to milestone completion
  4200. --|    number and then element priority.
  4201. --|  
  4202. --|  EXCEPTIONS HANDLED:
  4203. --|    others   an error message is printed and execution continues
  4204. --|
  4205. --|  HISTORY:
  4206. --|    written by   Bonnie Burkhardt   March 1985
  4207. --------------------------------------------------------------------------------
  4208.   use MS_LIST_PKG; use PR_LIST_PKG;
  4209.  
  4210.   COMPLETE_NUM  : integer range ms_num_type'first..ms_num_type'last+1 := 100;
  4211.   END_LIST      : boolean := false;
  4212.   IN_SORTED_LIST: boolean := false;
  4213.   LO_MS_PTR     : milestone_pointer;
  4214.   LO_MS     : ms_num_type := 1;
  4215.   HI_MS     : ms_num_type := 1;
  4216.   MS_PTR        : milestone_pointer;
  4217.   MS_PTR2       : milestone_pointer;
  4218.   MS_INDEX      : integer := 0;
  4219.   PR_PTR    : personnel_pointer;
  4220.   SORTED_MS_LIST: ms_list_pkg.list_type;
  4221.   SUCCEED    : boolean := false;
  4222.  
  4223.   procedure SORT_EL_IN_MS is separate;
  4224.   procedure SORT_EL_IN_PR is separate;
  4225.  
  4226. begin
  4227.   -- sort the milestone list by completion sequence number
  4228.   for MS_INDEX in 1..num_of_milestones loop
  4229.     start_walk(MS_LIST);
  4230.     COMPLETE_NUM := 100;
  4231.  
  4232.     loop
  4233.       walk(MS_LIST, MS_PTR, END_LIST);
  4234.       exit when END_LIST;
  4235.       find(SORTED_MS_LIST, MS_PTR.number, MS_PTR2, IN_SORTED_LIST);
  4236.       if not IN_SORTED_LIST and (MS_PTR.completion_number < COMPLETE_NUM) then
  4237.     COMPLETE_NUM := MS_PTR.completion_number;
  4238.     LO_MS_PTR := MS_PTR;
  4239.       end if;
  4240.     end loop;
  4241.  
  4242.     ADD (SORTED_MS_LIST, LO_MS_PTR.number, LO_MS_PTR);
  4243.   end loop;
  4244.  
  4245.   -- sort the element list for each milestone by priority number
  4246.   start_walk(SORTED_MS_LIST);
  4247.   loop
  4248.     walk(SORTED_MS_LIST, MS_PTR, END_LIST);
  4249.     exit when END_LIST;
  4250.     SORT_EL_IN_MS;
  4251.   end loop;
  4252.  
  4253.   -- sort the element list for each person according to the milestone and 
  4254.   -- element lists created
  4255.   start_walk(PR_LIST);
  4256.   loop
  4257.     walk(PR_LIST, PR_PTR, END_LIST);
  4258.     exit when END_LIST;
  4259.     SORT_EL_IN_PR;
  4260.   end loop;
  4261.  
  4262. exception
  4263.   when others => put_line("exception raise in PRIORITIZE");  
  4264. end PRIORITIZE;
  4265.  
  4266.  
  4267.  
  4268. separate (TRACKER.MANIPULATE_DATA.PRIORITIZE)
  4269. procedure SORT_EL_IN_MS is 
  4270. --------------------------------------------------------------------------------
  4271. --|
  4272. --|  NAME:  SORT_EL_IN_MS
  4273. --|
  4274. --|  OVERVIEW:
  4275. --|    This procedure sorts the elements belonging to a given milestone by
  4276. --|    element priority.  If all elements have the same priority, no sorting
  4277. --|    takes place.  Otherwise, sorting is done by deleting the lowest 
  4278. --|    priority elements and adding them to the end of the element list.
  4279. --|  
  4280. --|  EXCEPTIONS HANDLED:
  4281. --|    others   an error message is printed and execution continues
  4282. --|
  4283. --|  HISTORY:
  4284. --|    written by   Bonnie Burkhardt   March 1985
  4285. --------------------------------------------------------------------------------
  4286.  
  4287.   use EL_LIST_PKG; 
  4288.  
  4289.   ELE_PTR       : element_pointer;
  4290.   END_LIST      : boolean := false;
  4291.   HI_MS         : ms_num_type := 1;
  4292.   LO_MS         : ms_num_type := 1;
  4293.   SORTED_EL_LIST: el_list_pkg.list_type;
  4294.   SUCCEED       : boolean := false;
  4295.  
  4296. begin
  4297.   LO_MS := MS_PTR.number;
  4298.   HI_MS := MS_PTR.number;
  4299.  
  4300.   -- find the lowest and highest element priority
  4301.   start_walk(MS_PTR.element_list);
  4302.   loop
  4303.     walk(MS_PTR.element_list, ELE_PTR, END_LIST);
  4304.     exit when END_LIST;
  4305.     if ELE_PTR.priority < LO_MS then
  4306.       LO_MS := ELE_PTR.priority;
  4307.     end if;
  4308.     if ELE_PTR.priority > HI_MS then
  4309.       HI_MS := ELE_PTR.priority;
  4310.     end if;
  4311.   end loop;
  4312.  
  4313.   -- if elements have different priorities, sort them
  4314.   if LO_MS < HI_MS then
  4315.     for PRIORITY in LO_MS..HI_MS loop
  4316.  
  4317.       start_walk(MS_PTR.element_list);
  4318.       loop
  4319.         walk(MS_PTR.element_list, ELE_PTR, END_LIST);
  4320.         exit when END_LIST;
  4321.         if ELE_PTR.priority = PRIORITY then
  4322.       ADD (SORTED_EL_LIST, ELE_PTR.desc_key, ELE_PTR);
  4323.         end if;    
  4324.       end loop;
  4325.  
  4326.     end loop;
  4327.     MS_PTR.element_list := SORTED_EL_LIST;
  4328.   end if;
  4329.  
  4330. exception
  4331.   when others => put_line("exception raised in SORT_EL_IN_MS.");
  4332. end SORT_EL_IN_MS;
  4333.  
  4334.  
  4335. separate (TRACKER.MANIPULATE_DATA.PRIORITIZE)
  4336. procedure SORT_EL_IN_PR is 
  4337. --------------------------------------------------------------------------------
  4338. --|
  4339. --|  NAME:  SORT_EL_IN_PR
  4340. --|
  4341. --|  OVERVIEW:
  4342. --|    This procedure sorts the elements belonging to a given person using the
  4343. --|    milestones sorted by completion sequence and the milestone's elements
  4344. --|    sorted by element priority.  Sorting is done by walking down each 
  4345. --|    milestone's element list and deleting and adding any elements which 
  4346. --|    belong to this person.
  4347. --|  
  4348. --|  EXCEPTIONS HANDLED:
  4349. --|    others   an error message is printed and execution continues
  4350. --|
  4351. --|  HISTORY:
  4352. --|    written by   Bonnie Burkhardt   March 1985
  4353. --------------------------------------------------------------------------------
  4354.  
  4355.   use EL_LIST_PKG;
  4356.  
  4357.   ELE_PTR       : element_pointer;
  4358.   ELE_PTR2      : element_pointer;
  4359.   END_LIST      : boolean := false;
  4360.   PR_INITIALS   : string (1..pr_init_max_len) := PR_PTR.initials;
  4361.   SORTED_EL_LIST: el_list_pkg.list_type;
  4362.   FOUND         : boolean := false;
  4363.  
  4364. begin
  4365.   -- check each milestone's element list for elements that belong to this person
  4366.   start_walk(SORTED_MS_LIST);
  4367.   loop
  4368.     walk(SORTED_MS_LIST, MS_PTR, END_LIST);
  4369.     exit when END_LIST;
  4370.  
  4371.     -- examine the milestone's list of elements for any elements belonging
  4372.     -- to this person
  4373.     start_walk(MS_PTR.element_list);
  4374.     loop
  4375.       walk(MS_PTR.element_list, ELE_PTR, END_LIST);
  4376.       exit when END_LIST;
  4377.  
  4378.       if ELE_PTR.more_than_one_person then
  4379.         for ac_index in 1..num_of_activities loop
  4380.           if ELE_PTR.people_initials(ac_index) = PR_INITIALS then
  4381.         FIND (SORTED_EL_LIST, ELE_PTR.desc_key, ELE_PTR2, FOUND);
  4382.         if not FOUND then
  4383.           ADD (SORTED_EL_LIST, ELE_PTR.desc_key, ELE_PTR);
  4384.         end if;
  4385.       end if;
  4386.         end loop;
  4387.  
  4388.       else -- only one person assigned
  4389.     if ELE_PTR.person_initials = PR_INITIALS then
  4390.       ADD (SORTED_EL_LIST, ELE_PTR.desc_key, ELE_PTR);
  4391.     end if;
  4392.       end if;
  4393.  
  4394.     end loop;
  4395.   end loop;
  4396.   PR_PTR.element_list := SORTED_EL_LIST;
  4397.  
  4398. exception
  4399.   when others => put_line("exception raised in SORT_EL_IN_PR.");
  4400. end SORT_EL_IN_PR;
  4401. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4402. --calctime.ada
  4403. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4404. separate(TRACKER.MANIPULATE_DATA)
  4405. procedure CALC_TIME_DONE is
  4406. --------------------------------------------------------------------------------
  4407. --|
  4408. --|  NAME:  CALC_TIME_DONE
  4409. --|
  4410. --|  OVERVIEW:
  4411. --|    This procedure calculates the date each element will be completed
  4412. --|    and the total number of hours left to completion.
  4413. --|  
  4414. --|  EXCEPTIONS HANDLED:
  4415. --|    others   an error message is printed and execution continues
  4416. --|
  4417. --|  HISTORY:
  4418. --|    written by   Bonnie Burkhardt   March 1985
  4419. --|
  4420. --|  NOTES:
  4421. --|    The activities used in the calculations include all activities
  4422. --|    that were marked as being considered in the calculations and all 
  4423. --|    activities whose priority is less than or equal to any activity
  4424. --|    marked as being considered.
  4425. --|    
  4426. --------------------------------------------------------------------------------
  4427.   use CALENDAR;
  4428.   use EL_LIST_PKG; use PR_LIST_PKG; use AC_LIST_PKG; 
  4429.  
  4430.   AC_PTR          : activity_pointer;
  4431.   AC_INDEX        : integer := 0;
  4432.   AC_PRIORITIES   : array (1..max_num_activities) of integer range 1..10 
  4433.     := (others => 1);
  4434.   BEGIN_DATE      : date_type := null_date;
  4435.   BEGIN_DATE_USED : integer range 1..3 := 1;
  4436.   END_LIST        : boolean := false;
  4437.   HI_AC_PRIORITY  : integer := 1;
  4438.   PCT_TOT_PROJ    : array (1..max_num_activities) of float range 0.0..100.0
  4439.     := (others => 0.0);
  4440.   PR_PTR          : personnel_pointer;
  4441.   TEST_PRIORITY   : integer := 1;
  4442.   TOTAL_TIME      : float := 0.0;
  4443.  
  4444.   procedure GET_EL_TIME is separate;
  4445.  
  4446. begin
  4447.   -- calculate the highest priority activity considered and 
  4448.   -- initialize the PCT_TOT_PROJ array
  4449.   start_walk(AC_LIST);
  4450.   AC_INDEX := 0;
  4451.   loop
  4452.     walk(AC_LIST, AC_PTR, END_LIST);
  4453.     exit when END_LIST;
  4454.     AC_INDEX := AC_INDEX + 1;
  4455.     PCT_TOT_PROJ (AC_INDEX) := AC_PTR.percent_tot_proj;
  4456.     AC_PRIORITIES(AC_INDEX) := AC_PTR.priority;
  4457.     if AC_PTR.consider_in_calc and AC_PTR.priority > HI_AC_PRIORITY then
  4458.       HI_AC_PRIORITY := AC_PTR.priority;
  4459.     end if;
  4460.   end loop;
  4461.  
  4462.   -- compute each person's amount of work remaining and date completed
  4463.   start_walk(PR_LIST);
  4464.   loop
  4465.     walk(PR_LIST, PR_PTR, END_LIST);
  4466.     exit when END_LIST;
  4467.  
  4468.     -- compute the beginning date
  4469.     if  (PR_PTR.start_dates(3) /= null_date) and 
  4470.     (PR_PTR.stop_dates(2) < DATE) then     -- starting in third time span
  4471.       BEGIN_DATE_USED := 3;
  4472.       if PR_PTR.start_dates(3) > DATE then
  4473.     BEGIN_DATE := PR_PTR.start_dates(3);
  4474.       else
  4475.         BEGIN_DATE := DATE;
  4476.       end if;
  4477.     elsif (PR_PTR.start_dates(2) /= null_date) and 
  4478.       (PR_PTR.stop_dates(1) < DATE) then    -- starting in second time span
  4479.       BEGIN_DATE_USED := 2;
  4480.       if PR_PTR.start_dates(2) > DATE then
  4481.     BEGIN_DATE := PR_PTR.start_dates(2);
  4482.       else
  4483.         BEGIN_DATE := DATE;
  4484.       end if;
  4485.     else    -- starting in first time span
  4486.       BEGIN_DATE_USED := 1;
  4487.       if (PR_PTR.start_dates(1) /= null_date) and
  4488.          (PR_PTR.start_dates(1) > DATE) then
  4489.     BEGIN_DATE := PR_PTR.start_dates(1);
  4490.       else
  4491.     BEGIN_DATE := DATE;
  4492.       end if;
  4493.     end if;
  4494.  
  4495.     -- compute the completion date for each person's elements
  4496.     TOTAL_TIME := 0.0;
  4497.     for TEST in 1..HI_AC_PRIORITY loop
  4498.       TEST_PRIORITY := TEST;
  4499.       GET_EL_TIME;
  4500.     end loop;
  4501.   end loop;
  4502.  
  4503. exception
  4504.   when others => put_line("exception raise in CALC_TIME_DONE");  
  4505. end CALC_TIME_DONE;
  4506.  
  4507.  
  4508.  
  4509. separate (TRACKER.MANIPULATE_DATA.CALC_TIME_DONE)
  4510. procedure GET_EL_TIME is
  4511. --------------------------------------------------------------------------------
  4512. --|
  4513. --|  NAME:  GET_EL_TIME
  4514. --|
  4515. --|  OVERVIEW:
  4516. --|    This procedure computes the total amount of time needed to complete
  4517. --|    the activities with TEST_PRIORITY of each element assigned to the
  4518. --|    current programmer, PR_PTR.  It then adds this time to the total
  4519. --|    time the programmer works and to the total number of hours needed
  4520. --|    to complete the element, ELE_PTR.hours_to_complete. It also calculates 
  4521. --|    the date this amount of work will be completed.  The completion date 
  4522. --|    is stored in the element field, DATE_DONE.
  4523. --|  
  4524. --|  EXCEPTIONS HANDLED:
  4525. --|    others   an error message is printed and execution continues
  4526. --|
  4527. --|  HISTORY:
  4528. --|    written by   Bonnie Burkhardt   March 1985
  4529. --------------------------------------------------------------------------------
  4530.  
  4531.   use DATA_PKG;
  4532.  
  4533.   BIASED_TOTAL_TIME   : float        := 0.0;
  4534.   DATE_DONE           : date_type   := null_date;
  4535.   DATE_CALCULATED     : boolean        := false;
  4536.   ELE_PTR             : element_pointer;
  4537.   ELE_SIZE            : integer range 0..999_000;
  4538.   END_LIST            : boolean        := false;
  4539.   PROJECTED_DATE_DONE : date_type   := null_date;
  4540.   TIME_SPAN_USED     : integer range 1..3 := BEGIN_DATE_USED;
  4541.   STARTING_DATE          : date_type   := BEGIN_DATE;
  4542.   STANDARD_WORKWEEK   : boolean        := false;
  4543.   TIME_FOR_1_AC       : float        := 0.0;
  4544.   TIME_FOR_ELE        : float        := 0.0;
  4545.  
  4546. begin
  4547.   STANDARD_WORKWEEK := float(PR_PTR.hours_per_week) = HOURS_IN_WORK_DAY 
  4548.     * float(DAYS_IN_WORK_WEEK);
  4549.   start_walk(PR_PTR.element_list);
  4550.   loop
  4551.     walk(PR_PTR.element_list, ELE_PTR, END_LIST);
  4552.     exit when END_LIST;
  4553.  
  4554.     ELE_SIZE := ELE_PTR.current_size - ELE_PTR.size_done_at_start;
  4555.     TIME_FOR_ELE := 0.0;
  4556.  
  4557.     -- calculate the amount of time needed to complete this element's activities
  4558.     for AC_INDEX in 1..num_of_activities loop
  4559.       if AC_PRIORITIES(AC_INDEX) = TEST_PRIORITY then
  4560.  
  4561.     if not ELE_PTR.more_than_one_person then
  4562.           TIME_FOR_1_AC := ELE_PTR.complexity * float(ELE_SIZE) 
  4563.         * (PCT_TOT_PROJ(AC_INDEX) / 100.0) * ((100.0 - 
  4564.         AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX))) /100.0)
  4565.         / PR_PTR.production_rate;
  4566.  
  4567.     elsif ELE_PTR.people_initials(AC_INDEX) = PR_PTR.initials then
  4568.             TIME_FOR_1_AC := ELE_PTR.complexity * float(ELE_SIZE) 
  4569.         * (PCT_TOT_PROJ(AC_INDEX) / 100.0) * ((100.0 - 
  4570.         AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX))) /100.0)
  4571.         / PR_PTR.production_rate;
  4572.         ELE_PTR.hours_left(AC_INDEX) := TIME_FOR_1_AC;
  4573.     end if;
  4574.  
  4575.         TIME_FOR_ELE := TIME_FOR_ELE + TIME_FOR_1_AC;
  4576.       end if;
  4577.     end loop;
  4578.     TOTAL_TIME := TOTAL_TIME + TIME_FOR_ELE;
  4579.     ELE_PTR.hours_to_complete := ELE_PTR.hours_to_complete + TIME_FOR_ELE;
  4580.  
  4581.     -- calculate the date this element is completed
  4582.     if STANDARD_WORKWEEK then
  4583.       BIASED_TOTAL_TIME := TOTAL_TIME;
  4584.     else
  4585.       BIASED_TOTAL_TIME := TOTAL_TIME * float(DAYS_IN_WORK_WEEK) 
  4586.         * HOURS_IN_WORK_DAY / float(PR_PTR.hours_per_week);
  4587.     end if;
  4588.     PROJECTED_DATE_DONE := STARTING_DATE + BIASED_TOTAL_TIME;
  4589.  
  4590.     STARTING_DATE   := BEGIN_DATE;
  4591.     time_span_used := BEGIN_DATE_USED;
  4592.     DATE_CALCULATED := false;
  4593.     while not DATE_CALCULATED loop
  4594.       case time_span_used is
  4595.         when 1 | 2 =>
  4596.       -- it fits in the time span
  4597.       if  (PR_PTR.stop_dates(time_span_used) = null_date) or
  4598.           (PR_PTR.stop_dates(time_span_used) >= PROJECTED_DATE_DONE) then
  4599.         DATE_DONE := PROJECTED_DATE_DONE;
  4600.         DATE_CALCULATED := true;
  4601.       -- another set of start/stop dates doesn't exits
  4602.       elsif PR_PTR.start_dates(time_span_used+1) = null_date then
  4603.         DATE_DONE := underflow_date;
  4604.         DATE_CALCULATED := true;
  4605.       else  -- move on to next set of completion dates
  4606.         -- add in the total amount of work missed to the biased total time
  4607.         -- (the vacation is from this stop date to the next start date)
  4608.         BIASED_TOTAL_TIME := BIASED_TOTAL_TIME + 
  4609.             (PR_PTR.start_dates(time_span_used+1) - 
  4610.              PR_PTR.stop_dates(time_span_used));
  4611.         TIME_SPAN_USED := TIME_SPAN_USED + 1;
  4612.         PROJECTED_DATE_DONE := STARTING_DATE + BIASED_TOTAL_TIME;
  4613.       end if;
  4614.     when 3 =>
  4615.       -- it fits in the time span
  4616.       if (PR_PTR.stop_dates(time_span_used) = null_date) or
  4617.          (PR_PTR.stop_dates(time_span_used) >= PROJECTED_DATE_DONE) then
  4618.         DATE_DONE := PROJECTED_DATE_DONE;
  4619.         DATE_CALCULATED := true;
  4620.       else  -- no time to finish the work
  4621.         DATE_DONE := underflow_date;
  4622.         DATE_CALCULATED := true;
  4623.       end if;
  4624.       end case;
  4625.     end loop;
  4626.  
  4627.     -- assign the newly completed completion date to the fields in the element
  4628.     if  (ELE_PTR.date_done = null_date) or 
  4629.     (ELE_PTR.date_done < DATE_DONE) or
  4630.     (DATE_DONE = underflow_date) then
  4631.       ELE_PTR.date_done := DATE_DONE;
  4632.     end if;
  4633.     if ELE_PTR.more_than_one_person then 
  4634.       for AC_INDEX in 1..num_of_activities loop
  4635.     if (AC_PRIORITIES(AC_INDEX) = TEST_PRIORITY) and
  4636.        (ELE_PTR.people_initials (AC_INDEX) = PR_PTR.initials) then
  4637.       ELE_PTR.dates_done(AC_INDEX) := DATE_DONE;
  4638.     end if;
  4639.       end loop;
  4640.     end if;
  4641.   end loop;
  4642.  
  4643. exception
  4644.   when others => put_line("exception raised in GET_EL_TIME.");
  4645. end GET_EL_TIME;
  4646. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4647. --chkpct.ada
  4648. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4649. separate ( TRACKER.MANIPULATE_DATA )
  4650. procedure CHECK_AC_PERCENT is 
  4651. ----------------------------------------------------------------------
  4652. --|  NAME:  CHECK_AC_PERCENT
  4653. --|
  4654. --|  OVERVIEW:
  4655. --|    This procedure checks to see that the activity percent of project
  4656. --|    adds up to 100.0%.
  4657. --|
  4658. --|  EXCEPTIONS HANDLED:
  4659. --|    none
  4660. --|
  4661. --|  HISTORY:
  4662. --|    written by   May Lee   March 1985
  4663. ----------------------------------------------------------------------
  4664.     use AC_LIST_PKG;
  4665.     ac_record     : activity_pointer;
  4666.     end_list      : boolean;
  4667.     total_percent : float := 0.0;
  4668.   begin
  4669.     loop  -- until the activity percent = 100
  4670.       total_percent := 0.0;
  4671.       START_WALK( ac_list );
  4672.       loop  -- walk the activity list and compute total percent
  4673.         WALK( ac_list, ac_record, end_list );
  4674.         exit when end_list;
  4675.         total_percent := total_percent + ac_record.percent_tot_proj ;
  4676.       end loop;
  4677.       if total_percent > 100.01 or total_percent < 99.99 then
  4678.         put_line(" The total of each activity's percent of the total project ");
  4679.         put_line(" does not add up to 100.0%.");
  4680.     put_line(" You must go back and change the activity data. ");
  4681.     new_line;
  4682.         START_WALK( ac_list );
  4683.         loop  -- walk the activity list and compute total percent
  4684.           WALK( ac_list, ac_record, end_list );
  4685.           exit when end_list;
  4686.       put(ac_record.name); put("       ");
  4687.       put(ac_record.percent_tot_proj,3,1,0); put_line("%");
  4688.         end loop;
  4689.         put_line ("                 -------"); 
  4690.         put(" Total percent ="); put(total_percent,4,1,0); 
  4691.     new_line(2);
  4692.     put_line(" Press <cr> to return to the Data Menu.");
  4693.     skip_line;
  4694.         DATA_MENU_DRIVER;
  4695.       else
  4696.         exit;
  4697.       end if;      
  4698.     end loop;
  4699.   end CHECK_AC_PERCENT;
  4700. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4701. --fixdata.ada
  4702. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4703. separate(TRACKER.MANIPULATE_DATA)
  4704. procedure GROUP_DATA_FIXES is
  4705. --------------------------------------------------------------------------------
  4706. --|
  4707. --|  NAME:  GROUP_DATA_FIXES
  4708. --|
  4709. --|  OVERVIEW:
  4710. --|    This procedure is the driver for making changes to the entire set of
  4711. --|    element data.  Two types of changes are possible, updating the original
  4712. --|    estimate to equal the current estimate or starting the project at this
  4713. --|    point and using this run as the starting point for the project.
  4714. --|
  4715. --|  EXCEPTIONS HANDLED:
  4716. --|    none
  4717. --|
  4718. --|  HISTORY:
  4719. --|    written by   Bonnie Burkhardt   March 1985
  4720. --------------------------------------------------------------------------------
  4721.  
  4722.   input_char : character := ' ';
  4723.  
  4724.   procedure UPDATE_ORIGINAL is separate;
  4725.   procedure RESET_DATA      is separate;
  4726.  
  4727. begin
  4728.   -- ask the user if he wants to re-originalize his data
  4729.   new_line;
  4730.   put_line(" Would you like to update the original size estimates for all");
  4731.   put_line(" the elements to reflect the current size estimate?");
  4732.   new_line;
  4733.   put(" Y or N  ( <cr>=N ) : ");
  4734.   loop
  4735.     begin
  4736.       if END_OF_LINE then
  4737.     skip_line;
  4738.     new_line(2);
  4739.     exit;
  4740.       else
  4741.         get (input_char);
  4742.         if (input_char = 'n') or (input_char = 'N') then
  4743.       skip_line;
  4744.       new_line(2);
  4745.       exit;
  4746.         elsif (input_char = 'y') or (input_char = 'Y') then
  4747.       skip_line;
  4748.       new_line(2);
  4749.       UPDATE_ORIGINAL;
  4750.       exit;
  4751.         else -- give more information 
  4752.       skip_line;
  4753.       new_line(2);
  4754.       put_line(" Tracker will step through each element and assign the");
  4755.           put_line(" original size to equal the current size.");
  4756.       put_line(" Would you like to update the original size?");
  4757.           new_line;
  4758.       put(" [ Y or N  <cr>=N ] : ");
  4759.         end if;
  4760.       end if;
  4761.     exception
  4762.       when others => 
  4763.     skip_line;
  4764.     new_line(2);
  4765.     put_line(" Tracker will step through each element and assign the");
  4766.         put_line(" original size to equal the current size.");
  4767.     put_line(" Would you like to update the original size?");
  4768.         new_line;
  4769.     put(" [ Y or N ] : ");
  4770.     end;
  4771.   end loop;
  4772.  
  4773.   -- determine if the user wants to 'reset' his data file
  4774.   new_line;
  4775.   put_line(" Do you want to start tracking the project from this point onwards");
  4776.   put_line(" and use the current percent complete as the starting point?");
  4777.   new_line;
  4778.   put(" [ Y or N  <cr>=N ] : ");
  4779.   loop
  4780.     begin
  4781.       if END_OF_LINE then
  4782.     skip_line;
  4783.     new_line(2);
  4784.     exit;
  4785.       else
  4786.         get(input_char);    
  4787.     if (input_char = 'n') or (input_char = 'N') then
  4788.       skip_line;
  4789.       new_line(2);
  4790.       exit;
  4791.     elsif (input_char = 'y') or (input_char = 'Y') then
  4792.       skip_line;
  4793.       RESET_DATA;
  4794.       new_line(2);
  4795.       exit;
  4796.     else -- give more information 
  4797.       skip_line;
  4798.           new_line;
  4799.       put_line(" Tracker will step through each element and compute the ");
  4800.           put_line(" amount of work that is completed on the element.  It then");
  4801.       put_line(" subtracts this amount from the current size to obtain the");
  4802.       put_line(" EQUIVALENT NEW SIZE estimate.  The percent complete for ");
  4803.       put_line(" that element is erased and set to '   '.");
  4804.       put_line(" Do you want to start tracking the project from this point?");
  4805.           new_line;
  4806.       put(" [ Y or N  <cr>=N ] : ");
  4807.     end if;
  4808.       end if;
  4809.     exception
  4810.       when others => 
  4811.     skip_line;
  4812.         new_line;
  4813.     put_line(" Tracker will step through each element and compute the ");
  4814.         put_line(" amount of work that is completed on the element.  It then");
  4815.     put_line(" subtracts this amount from the current size to obtain the");
  4816.     put_line(" EQUIVALENT NEW SIZE estimate.  The percent complete for ");
  4817.     put_line(" that element is erased and set to '   '.");
  4818.     put_line(" Do you want to start tracking the project from this point?");
  4819.         new_line;
  4820.     put(" [ Y or N  <cr>=N ] : ");
  4821.     end;
  4822.   end loop;
  4823.  
  4824. end GROUP_DATA_FIXES;
  4825. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4826. --fixreset.ada
  4827. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4828. separate(TRACKER.MANIPULATE_DATA.GROUP_DATA_FIXES)
  4829. procedure RESET_DATA is
  4830. --------------------------------------------------------------------------------
  4831. --|
  4832. --|  NAME:  RESET_DATA
  4833. --|
  4834. --|  OVERVIEW:
  4835. --|    For each element, this procedure calculates the amount of work 
  4836. --|    completed and stores this value in the SIZE_DONE_AT_START field.
  4837. --|    After this calculation, it erases the percent complete field in the 
  4838. --|    element by setting it equal to "    ".
  4839. --|  
  4840. --|  EXCEPTIONS HANDLED:
  4841. --|    others   an error message is printed and execution continues
  4842. --|
  4843. --|  HISTORY:
  4844. --|    written by   Bonnie Burkhardt   March 1985
  4845. --|
  4846. --|  NOTE:
  4847. --------------------------------------------------------------------------------
  4848.  
  4849.   use EL_LIST_PKG; use AC_LIST_PKG; use SS_LIST_PKG;
  4850.  
  4851.   AC_PTR        : activity_pointer;
  4852.   AC_INDEX      : integer := 0;
  4853.   ELE_PTR       : element_pointer;
  4854.   ELE_DONE      : float range 0.0..999_999.0;
  4855.   ELE_SIZE      : float range 0.0..999_999.0;
  4856.   ELE_START     : float range 0.0..999_999.0;
  4857.   END_LIST      : boolean := false;
  4858.   GR_TOT_SIZE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  4859.         := (others => 0.0);
  4860.   GR_TOT_DONE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0
  4861.         := (others => 0.0);
  4862.   GR_TOT_START : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  4863.         := (others => 0.0);
  4864.   DONE      : float range 0.0..9_999_999.0 := 0.0;
  4865.   NONE_COMPLETE : activity_phase_percent := (others => ' ');
  4866.   SIZE      : float range 0.0..9_999_999.0 := 0.0;
  4867.   START     : float range 0.0..9_999_999.0 := 0.0;
  4868.   SS_PTR    : subsystem_pointer;
  4869.  
  4870.   SS_TOT_SIZE  : float range 0.0..999_999.0 := 0.0;
  4871.   SS_TOT_DONE  : float range 0.0..999_999.0 := 0.0;
  4872.   SS_TOT_START : float range 0.0..999_999.0 := 0.0;
  4873.  
  4874. begin
  4875.   start_walk(SS_LIST);
  4876.   loop
  4877.     walk(SS_LIST, SS_PTR, END_LIST);
  4878.     exit when END_LIST;
  4879.  
  4880.     -- reset subsystem totals
  4881.     SS_TOT_SIZE := 0.0;
  4882.     SS_TOT_DONE := 0.0;
  4883.     SS_TOT_START := 0.0;
  4884.  
  4885.     -- set through each subsystem's element list and calculate each element
  4886.     start_walk(SS_PTR.element_list);
  4887.     loop
  4888.       walk(SS_PTR.element_list, ELE_PTR, END_LIST);
  4889.       exit when END_LIST;
  4890.   
  4891.       ELE_DONE  := 0.0;
  4892.       ELE_START := float(ELE_PTR.size_done_at_start);
  4893.       ELE_SIZE  := float(ELE_PTR.current_size) - ELE_START;
  4894.       SS_TOT_SIZE := SS_TOT_SIZE + ELE_SIZE * ELE_PTR.complexity;
  4895.       SS_TOT_START := SS_TOT_START + ELE_START * ELE_PTR.complexity;
  4896.  
  4897.       -- calculate the amount of work done for each activity in this element
  4898.       --| The SIZE_DONE_AT_START is equal to the old SIZE_DONE_AT_START plus
  4899.       --| any work that has been completed since the start of the project.  
  4900.       --| This means that the data can be 'reset' or 'restarted' as many times 
  4901.       --| as necessary with no loss in accuracy.
  4902.       start_walk(AC_LIST);
  4903.       AC_INDEX := 0;
  4904.       loop
  4905.         walk(AC_LIST, AC_PTR, END_LIST);
  4906.         exit when END_LIST;
  4907.         AC_INDEX := AC_INDEX + 1;
  4908.         SIZE := ELE_PTR.complexity * ELE_SIZE * AC_PTR.percent_tot_proj / 100.0;
  4909.         START:= ELE_PTR.complexity * ELE_START * AC_PTR.percent_tot_proj / 100.0;
  4910.         DONE := SIZE * AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX)) / 100.0;
  4911.         GR_TOT_SIZE(AC_INDEX) := GR_TOT_SIZE(AC_INDEX) + SIZE;
  4912.         GR_TOT_DONE(AC_INDEX) := GR_TOT_DONE(AC_INDEX) + DONE;
  4913.         GR_TOT_START(AC_INDEX) := GR_TOT_START(AC_INDEX) + START;
  4914.     ELE_DONE := ELE_DONE + DONE;
  4915.         SS_TOT_DONE := SS_TOT_DONE + DONE;
  4916.       end loop;
  4917.  
  4918.       ELE_PTR.activity_completeness := NONE_COMPLETE;
  4919.       ELE_PTR.size_done_at_start := ELE_PTR.size_done_at_start 
  4920.                     + integer(ELE_DONE);
  4921.       -- adjust for round off error
  4922.       if ELE_PTR.size_done_at_start > ELE_PTR.current_size then
  4923.         ELE_PTR.size_done_at_start := ELE_PTR.current_size;
  4924.       end if;
  4925.     end loop;
  4926.  
  4927.     -- compute the percent complete at start for this subsystem
  4928.     if SS_TOT_SIZE + SS_TOT_START = 0.0 then
  4929.       SS_PTR.percent_at_start := 0.0;
  4930.     elsif SS_TOT_DONE <= SS_TOT_SIZE then
  4931.       SS_PTR.percent_at_start := 100.0 * (SS_TOT_DONE + 
  4932.     SS_TOT_START) / (SS_TOT_START + SS_TOT_SIZE);
  4933.     else
  4934.       SS_PTR.percent_at_start := 100.0;
  4935.     end if;
  4936.   end loop;
  4937.  
  4938.   -- calculate the percent complete at start by activity
  4939.   AC_INDEX := 0;
  4940.   start_walk(AC_LIST);
  4941.   loop
  4942.     walk(AC_LIST, AC_PTR, END_LIST);
  4943.     exit when END_LIST;
  4944.     AC_INDEX := AC_INDEX + 1;
  4945.     if GR_TOT_START(AC_INDEX) + GR_TOT_SIZE(AC_INDEX) = 0.0 then
  4946.       AC_PTR.percent_at_start := 0.0;
  4947.     elsif GR_TOT_DONE(AC_INDEX) <= GR_TOT_SIZE(AC_INDEX) then
  4948.       AC_PTR.percent_at_start := 100.0 * (GR_TOT_START(AC_INDEX) 
  4949.         + GR_TOT_DONE(AC_INDEX)) / (GR_TOT_START(AC_INDEX) 
  4950.         + GR_TOT_SIZE(AC_INDEX));
  4951.     else
  4952.       AC_PTR.percent_at_start := 100.0;
  4953.     end if;
  4954.   end loop;
  4955.  
  4956. exception
  4957.   when others => put_line("exception raise in RESET_DATA");  
  4958. end RESET_DATA;
  4959. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4960. --fixorig.ada
  4961. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4962. separate(TRACKER.MANIPULATE_DATA.GROUP_DATA_FIXES)
  4963. procedure UPDATE_ORIGINAL is
  4964. --------------------------------------------------------------------------------
  4965. --|
  4966. --|  NAME:  UPDATE_ORIGINAL
  4967. --|
  4968. --|  OVERVIEW:
  4969. --|    This procedure walks through the element data and for each element
  4970. --|    sets the original size estimate equal to the current size estimate.
  4971. --|  
  4972. --|  EXCEPTIONS HANDLED:
  4973. --|    others   an error message is printed and execution continues
  4974. --|
  4975. --|  HISTORY:
  4976. --|    written by   Bonnie Burkhardt   March 1985
  4977. --------------------------------------------------------------------------------
  4978.   use EL_LIST_PKG; 
  4979.  
  4980.   EL_PTR      : element_pointer;
  4981.   END_LIST     : boolean := false;
  4982.  
  4983. begin
  4984.   start_walk (EL_LIST);
  4985.   loop
  4986.     walk (EL_LIST, EL_PTR, END_LIST);
  4987.     exit when END_LIST;
  4988.     EL_PTR.original_size := EL_PTR.current_size;
  4989.   end loop;
  4990.  
  4991. exception
  4992.   when others => put_line("exception raised in UPDATE_ORIGINAL.");
  4993. end UPDATE_ORIGINAL;
  4994. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4995. --wrdata.ada
  4996. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  4997. with text_io; use text_io;
  4998.  
  4999. separate(tracker)
  5000. procedure WRITE_DATA_TO_FILE is
  5001. --------------------------------------------------------------------------------
  5002. --|  
  5003. --|  NAME:  WRITE_DATA_TO_FILE
  5004. --|
  5005. --|  OVERVIEW:
  5006. --|    This procedure writes all of the tracker data to a text file by
  5007. --|    calling the save procedures of each data type in a specified order.
  5008. --|    If the file already exists, then the output text file is a new 
  5009. --|    VAX_VMS version of any existing tracker input file.
  5010. --|
  5011. --|    The information is stored in a sequential text file.  All of the 
  5012. --|    data is read in at the beginning of the program, manipulated, 
  5013. --|    and then written back out to the new file.
  5014. --|
  5015. --|    The data is stored in the file in the following order:
  5016. --||              +-----------------------+
  5017. --||              |      Global Data      |          
  5018. --||              +-----------------------+
  5019. --||              |     Activity  Data    |
  5020. --||              +-----------------------+
  5021. --||              |     Milestone Data    |
  5022. --||              +-----------------------+
  5023. --||              |     Personnel Data    |
  5024. --||              +-----------------------+
  5025. --||              |     Subsystem Data    |
  5026. --||              +-----------------------+
  5027. --||              |      Element Data     |
  5028. --||              +-----------------------+
  5029. --|
  5030. --|  EXCEPTIONS HANDLED:
  5031. --|    name_error    tracker file can't be created, raised to calling routine
  5032. --|
  5033. --|  HISTORY:
  5034. --|    Written by   May Lee   March 1985
  5035. --| 
  5036. --------------------------------------------------------------------------------
  5037. begin
  5038.   new_line;
  5039.   put_line(" Writing the data to file.... ");
  5040.   new_line;
  5041.   -- create the output file to write the data to
  5042.   create (output_file, out_file, tracker_filename, "");
  5043.   GLOBAL_PKG.GL_SAVE;
  5044.   ACTIVITY_PKG.AC_SAVE;
  5045.   MILESTONE_PKG.MS_SAVE;
  5046.   PERSONNEL_PKG.PR_SAVE;
  5047.   SUBSYSTEM_PKG.SS_SAVE;
  5048.   ELEMENT_PKG.EL_SAVE;  
  5049.   close (output_file);
  5050. exception
  5051.   when name_error =>
  5052.     new_line(2); 
  5053.     put("Sorry, tracker file "); put(tracker_filename(1..filename_lngth));
  5054.     put(" cannot be created. ");
  5055.     new_line(2); 
  5056.     raise;
  5057. end WRITE_DATA_TO_FILE;
  5058. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5059. --menudr.ada
  5060. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5061. with PROMPT_PKG;
  5062. with text_io; use text_io;
  5063.  
  5064. separate(tracker)
  5065.  
  5066. procedure DATA_MENU_DRIVER is
  5067. --------------------------------------------------------------------------------
  5068. --|
  5069. --|  NAME:  DATA_MENU_DRIVER
  5070. --|
  5071. --|  OVERVIEW:
  5072. --|    This procedure gets all the TRACKER data by controlling the printing 
  5073. --|    of the data menus, and resolving the selections to those menus.  
  5074. --| 
  5075. --|    The data menu displays different types of data.  When a data type
  5076. --|    is chosen, an operations submenu appears, which allows the user
  5077. --|    to manipulate the data.  Since the only operation that can be 
  5078. --|    performed on global data is modification, the user is prompted 
  5079. --|    for the new data, which is assigned directly to the global 
  5080. --|    variable rather than calling a modify procedure in global_data.
  5081. --|
  5082. --|  EXCEPTIONS HANDLED:
  5083. --|    none
  5084. --|
  5085. --|  HISTORY:
  5086. --|    Written by   May Lee   March 1985
  5087. --|
  5088. --------------------------------------------------------------------------------
  5089.  
  5090. use VT100; use CALENDAR;
  5091. use SS_LIST_PKG;      -- to get task numbers
  5092.  
  5093. exit_data_menu : boolean := false;
  5094. exit_submenu   : boolean := false;
  5095.  
  5096. last                : natural;  -- used for getting an integer from a string
  5097. data_menu_selection : integer;
  5098. menu_selection      : integer;
  5099. found               : boolean := false;  -- parameter to find
  5100. ss_name             : ss_name_type := (others => ' '); -- used to get task num
  5101. ss_record           : subsystem_pointer;  -- used to get task numbers
  5102.  
  5103. begin
  5104.   while not exit_data_menu loop
  5105.     exit_submenu := false;
  5106.     data_menu_selection := PRINT_DATA_MENU;
  5107.  
  5108.     case data_menu_selection is 
  5109.  
  5110.       when 1   => 
  5111.         while not exit_submenu loop  
  5112.           menu_selection := PRINT_GLOBAL_MENU;
  5113.  
  5114.           case menu_selection is
  5115.             when 1 =>
  5116.               put(" The current project name is "); put(project_name); 
  5117.               new_line(2); 
  5118.               put_line(" What would you like to change the project name to? ");
  5119.               project_name := PROMPT_PKG.PROJECT_NAME;
  5120.             when 2 =>
  5121.               put(" The current project number is "); put(project_number,3); 
  5122.               new_line(2); 
  5123.               put_line(" What would you like to change the project number to? ");
  5124.               project_number := PROMPT_PKG.PROJECT_NUM;
  5125.             when 3 => 
  5126.               put(" The current manager is "); put(manager_name); new_line;
  5127.               new_line(2); 
  5128.               put_line(" Who would you like to be the new manager? ");
  5129.               manager_name := PROMPT_PKG.MANAGER_NAME;
  5130.             when 4 => 
  5131.               put(" The current date is "); 
  5132.               if date = null_date then
  5133.                 put("a null date ");
  5134.               else
  5135.                 put(date.month,2); put('/');
  5136.                 put(date.day,2);   put('/');
  5137.                 put(date.year,4); 
  5138.               end if;
  5139.               new_line(2);
  5140.               put_line(" What would you like to change the date to? ");
  5141.           loop
  5142.                 date := PROMPT_PKG.DATE;
  5143.         exit when date /= null_date;
  5144.         put_line(" The date of this run cannot be a null date.");
  5145.         put_line(" Try Again!");
  5146.           end loop;
  5147.             when 5 => exit_submenu := true;
  5148.             when others => 
  5149.               new_line;
  5150.               put_line("Please enter a number between 1 and 5. ");
  5151.               delay 1.0;
  5152.           end case;
  5153.         end loop;
  5154.  
  5155.       when 2   => 
  5156.         while not exit_submenu loop
  5157.           menu_selection := PRINT_OPERATION_MENU;
  5158.  
  5159.           case menu_selection is
  5160.             when 1 => ACTIVITY_PKG.AC_ADD;
  5161.             when 2 => ACTIVITY_PKG.AC_DELETE;
  5162.             when 3 => ACTIVITY_PKG.AC_MODIFY;
  5163.             when 4 => CLEAR_SCREEN;
  5164.             PROMPT_PKG.DISPLAY_ACTIVITY_DATA;
  5165.             new_line(2);
  5166.             put_line(" Press <cr> to continue");
  5167.             skip_line;
  5168.             new_line;
  5169.             when 5 => exit_submenu := true;
  5170.             when others => 
  5171.                 new_line;
  5172.                 put_line("Please enter a number between 1 and 5. ");
  5173.                 delay 1.0;
  5174.           end case;
  5175.         end loop;
  5176.  
  5177.       when 3   => 
  5178.         while not exit_submenu loop
  5179.           menu_selection := PRINT_OPERATION_MENU;
  5180.  
  5181.           case menu_selection is
  5182.             when 1 => PERSONNEL_PKG.PR_ADD;
  5183.             when 2 => PERSONNEL_PKG.PR_DELETE;
  5184.             when 3 => PERSONNEL_PKG.PR_MODIFY;
  5185.             when 4 => CLEAR_SCREEN;
  5186.             PROMPT_PKG.DISPLAY_PERSONNEL_DATA;
  5187.             new_line(2);
  5188.             put_line(" Press <cr> to continue");
  5189.             skip_line;
  5190.             new_line;
  5191.             when 5 => exit_submenu := true;
  5192.             when others => 
  5193.                   new_line;
  5194.                   put_line("Please enter a number between 1 and 5. ");
  5195.                   delay 1.0;
  5196.           end case;
  5197.         end loop;
  5198.  
  5199.       when 4   => 
  5200.         while not exit_submenu loop
  5201.           menu_selection := PRINT_OPERATION_MENU;
  5202.  
  5203.           case menu_selection is
  5204.             when 1 => MILESTONE_PKG.MS_ADD;
  5205.             when 2 => MILESTONE_PKG.MS_DELETE;
  5206.             when 3 => MILESTONE_PKG.MS_MODIFY;
  5207.             when 4 => CLEAR_SCREEN;
  5208.             PROMPT_PKG.DISPLAY_MILESTONE_DATA;
  5209.             new_line(2);
  5210.             put_line(" Press <cr> to continue");
  5211.             skip_line;
  5212.             new_line;
  5213.             when 5 => exit_submenu := true;
  5214.             when others => 
  5215.                   new_line;
  5216.                   put_line("Please enter a number between 1 and 5. ");
  5217.                   delay 1.0;
  5218.           end case;
  5219.         end loop;
  5220.  
  5221.       when 5   => 
  5222.         while not exit_submenu loop
  5223.           menu_selection := PRINT_OPERATION_MENU;
  5224.  
  5225.           case menu_selection is
  5226.             when 1 => SUBSYSTEM_PKG.SS_ADD;
  5227.             when 2 => SUBSYSTEM_PKG.SS_DELETE;
  5228.             when 3 => SUBSYSTEM_PKG.SS_MODIFY;
  5229.             when 4 => CLEAR_SCREEN;
  5230.             PROMPT_PKG.DISPLAY_SUBSYSTEM_DATA;
  5231.             new_line(2);
  5232.             put_line(" Press <cr> to continue");
  5233.             skip_line;
  5234.             new_line;
  5235.             when 5 => exit_submenu := true;
  5236.             when others => 
  5237.               new_line;
  5238.               put_line("Please enter a number between 1 and 5. ");
  5239.               delay 1.0;
  5240.           end case;
  5241.         end loop;
  5242.  
  5243.       when 6   =>
  5244.         while not exit_submenu loop
  5245.           menu_selection := PRINT_EL_OPERATION_MENU;
  5246.  
  5247.           case menu_selection is
  5248.             when 1 => ELEMENT_PKG.EL_ADD;
  5249.             when 2 => ELEMENT_PKG.EL_DELETE;
  5250.             when 3 => ELEMENT_PKG.EL_MODIFY;
  5251.             when 4 => CLEAR_SCREEN;
  5252.             PROMPT_PKG.DISPLAY_ELEMENT_DATA;
  5253.             new_line(2);
  5254.             put_line(" Press <cr> to continue");
  5255.             skip_line;
  5256.             new_line;
  5257.             when 5 => ELEMENT_PKG.UPDATE_CURRENT;
  5258.             when 6 => ELEMENT_PKG.UPDATE_PCT_DONE;
  5259.             when 7 => exit_submenu := true;
  5260.             when others => 
  5261.                   new_line;
  5262.                   put_line("Please enter a number between 1 and 7. ");
  5263.                   delay 1.0;
  5264.           end case;
  5265.         end loop;
  5266.  
  5267.       when 7   => VT100.CLEAR_SCREEN;
  5268.                   exit_data_menu := true; --exit to report menu
  5269.  
  5270.       when others  =>  
  5271.         new_line;
  5272.         put_line("Please enter a number between 1 and 7. ");
  5273.         delay 1.0;
  5274.     end case;
  5275.  
  5276.   end loop;
  5277.  
  5278. end DATA_MENU_DRIVER;
  5279. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5280. --getdata.ada
  5281. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5282. separate( TRACKER )
  5283. procedure GET_DATA is
  5284. ----------------------------------------------------------------------
  5285. --|  NAME:  GET_DATA
  5286. --|
  5287. --|  OVERVIEW:
  5288. --|    The user is asked whether or not he has an existing TRACKER file.
  5289. --|    This procedure either calls INITIALIZE_TRACKER_DATA if the user
  5290. --|    does not have an existing TRACKER file, or calls SET_UP_TRACKER_DATA
  5291. --|    if the user does have a file.
  5292. --|
  5293. --|  EXCEPTIONS HANDLED:
  5294. --|    name_error   raised to the calling procedure
  5295. --|    ERROR_IN_INPUT_FILE   raised to the calling procedure
  5296. --|    others   indicates invalid user response so user reprompted
  5297. --|
  5298. --|  HISTORY:
  5299. --|    written by   May Lee   March 1985
  5300. --|
  5301. ----------------------------------------------------------------------
  5302. valid_response : boolean := false;
  5303. char_input     : character := ' ';
  5304.  
  5305. begin
  5306.   while not valid_response loop
  5307.     put_line("Do you have an existing TRACKER file that you ");
  5308.     new_line;
  5309.     put_line("would like to use for this run?  ");
  5310.     put(" [Y  or  N, <cr>=N] : ");
  5311.     begin
  5312.       if end_of_line then  -- pressed return, default is no
  5313.     skip_line; new_line;
  5314.         valid_response := true;
  5315.         INITIALIZE_TRACKER_DATA;
  5316.       else
  5317.         get( char_input ); 
  5318.         if char_input = 'Y' or char_input = 'y' then
  5319.         skip_line; new_line;
  5320.           valid_response := true;
  5321.           SET_UP_TRACKER_DATA;
  5322.         elsif char_input = 'N' or char_input = 'n' then
  5323.         skip_line; new_line;
  5324.           valid_response := true;
  5325.           INITIALIZE_TRACKER_DATA;
  5326.         else
  5327.         skip_line; new_line;
  5328.           put_line("Please enter 'Y' or 'N' ");
  5329.           delay 0.7;
  5330.           CLEAR_SCREEN;
  5331.         end if;
  5332.       end if;
  5333.     exception
  5334.       when name_error => raise;
  5335.       when ERROR_IN_INPUT_FILE => raise;
  5336.       when others => 
  5337.     skip_line; new_line;
  5338.         -- invalid entry
  5339.         put_line("Please enter 'Y' or 'N' ");
  5340.         delay 0.7;
  5341.         CLEAR_SCREEN;
  5342.     end;
  5343.   end loop;
  5344.  
  5345. end GET_DATA;
  5346. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5347. --global.ada
  5348. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5349. with PROMPT_PKG;
  5350.  
  5351. separate (TRACKER)
  5352. package body GLOBAL_PKG is
  5353. ----------------------------------------------------------------------
  5354. --|
  5355. --|  NAME:  GLOBAL_PKG
  5356. --|
  5357. --|  OVERVIEW:
  5358. --|    This package defines the global data and the actions that
  5359. --|    can be performed on them.
  5360. --|
  5361. --|  EXCEPTIONS HANDLED:
  5362. --|    none
  5363. --|  
  5364. --|  HISTORY:
  5365. --|    written by   May Lee   March 1985
  5366. --|
  5367. ----------------------------------------------------------------------
  5368.  
  5369.   use CALENDAR;
  5370.  
  5371.   procedure GL_INITIALIZE is
  5372.   ----------------------------------------------------------------------
  5373.   --|
  5374.   --|  NAME:  GL_INITIALIZE
  5375.   --|
  5376.   --|  OVERVIEW:
  5377.   --|    This procedure prompts for global data by calling the Prompt_Pkg
  5378.   --|    functions, which returns valid data only. 
  5379.   --|
  5380.   --|  EXCEPTIONS HANDLED:
  5381.   --|    none
  5382.   --|
  5383.   --|  HISTORY:
  5384.   --|    written by   May Lee   March 1985
  5385.   --|
  5386.   ----------------------------------------------------------------------
  5387.   begin
  5388.     project_name  := PROMPT_PKG.PROJECT_NAME;
  5389.     project_number:= PROMPT_PKG.PROJECT_NUM;
  5390.     manager_name  := PROMPT_PKG.MANAGER_NAME;
  5391.     loop
  5392.       put_line(" The tracker calculations are based on the last day of a work week. ");
  5393.       put_line(" What is the date for this run? ");
  5394.       date        := PROMPT_PKG.DATE;
  5395.       exit when date /= null_date;
  5396.       put_line(" You cannot use a null date.  Try Again! ");
  5397.       new_line;
  5398.     end loop;
  5399.   end GL_INITIALIZE;
  5400.  
  5401.   procedure GL_SET_UP is
  5402.   ----------------------------------------------------------------------
  5403.   --|
  5404.   --|  NAME:  GL_SET_UP
  5405.   --|
  5406.   --|  OVERVIEW:
  5407.   --|    This procedure sets up the global variables read in from an input file.
  5408.   --|    The global data line is read in from the input file, and broken down 
  5409.   --|    into the respective global variables.  The data is read in the order 
  5410.   --|    specified by the GL_SAVE procedure.
  5411.   --|
  5412.   --|  EXCEPTIONS HANDLED:
  5413.   --|    others     error reading the global data
  5414.   --|    .        raises ERROR_IN_INPUT_FILE
  5415.   --|
  5416.   --|  HISTORY:
  5417.   --|    written by   May Lee   March 1985
  5418.   --|
  5419.   ----------------------------------------------------------------------
  5420.   begin
  5421.     get(tracker_file, project_name);
  5422.     get(tracker_file, project_number, width => 3 );
  5423.     get(tracker_file, manager_name);
  5424.     get(tracker_file, date.month, width => 2);
  5425.     get(tracker_file, date.day  , width => 2);
  5426.     get(tracker_file, date.year , width => 4);
  5427.     get(tracker_file, num_of_activities, width => 2 );  -- integer
  5428.     get(tracker_file, num_of_milestones, width => 2 );
  5429.     get(tracker_file, num_of_people,     width => 2 );
  5430.     get(tracker_file, num_of_subsystems, width => 2 );
  5431.     get(tracker_file, num_of_elements,   width => 4 );
  5432.     skip_line(tracker_file);
  5433.     loop
  5434.       put_line(" The tracker calculations are based on the last day of a work week. ");
  5435.       put_line(" What is the date for this run? ");
  5436.       date          := PROMPT_PKG.DATE;
  5437.       exit when date /= null_date;
  5438.       put_line(" You cannot use a null date.  Try Again! ");
  5439.       new_line;
  5440.     end loop;
  5441.   exception
  5442.     when others => put_line(" Error reading global data.");
  5443.     raise ERROR_IN_INPUT_FILE;
  5444.   end GL_SET_UP;
  5445.  
  5446.   procedure GL_SAVE is
  5447.   ----------------------------------------------------------------------
  5448.   --|
  5449.   --|  NAME:  GL_SAVE
  5450.   --|
  5451.   --|  OVERVIEW:
  5452.   --|    This procedure will save the global data to an output file.
  5453.   --|    The global data is composed of different types of variables.
  5454.   --|    The variables are written to the first line of the output file 
  5455.   --|    in the following format:
  5456.   --||
  5457.   --||   +--------------+--------+---------------+--+--+----+--+--+--+--+----+
  5458.   --||   | project_name |proj_num| manager_name  |mo|dy| yr |ac|ms|pr|ss| el |
  5459.   --||   +--------------+--------+---------------+--+--+----+--+--+--+--+----+
  5460.   --||
  5461.   --|    See DATA_PKG for the full names and types of each variable.
  5462.   --|
  5463.   --|  EXCEPTIONS HANDLED:
  5464.   --|    none
  5465.   --|
  5466.   --|  HISTORY:
  5467.   --|    written by   May Lee   March 1985
  5468.   --|
  5469.   ----------------------------------------------------------------------
  5470.  
  5471.     begin
  5472.       put(output_file, project_name);
  5473.       put(output_file, project_number, width => 3 );
  5474.       put(output_file, manager_name);
  5475.       put(output_file, date.month, width => 2);
  5476.       put(output_file, date.day  , width => 2);
  5477.       put(output_file, date.year , width => 4);
  5478.       put(output_file, num_of_activities, width => 2 );
  5479.       put(output_file, num_of_milestones, width => 2 );
  5480.       put(output_file, num_of_people,     width => 2 );
  5481.       put(output_file, num_of_subsystems, width => 2 );
  5482.       put(output_file, num_of_elements,   width => 4 );
  5483.       new_line(output_file);
  5484.   end GL_SAVE;
  5485.  
  5486. end GLOBAL_PKG;
  5487. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5488. --ac.ada
  5489. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  5490. with PROMPT_PKG;   
  5491.  
  5492. separate(tracker)
  5493. package body ACTIVITY_PKG is
  5494.  
  5495. --------------------------------------------------------------------------------
  5496. --|  NAME:  ACTIVITY_PKG
  5497. --|
  5498. --|  OVERVIEW:  
  5499. --|    This package defines the actions that can be performed on an
  5500. --|    activity (defined in DATA_PKG). 
  5501. --|
  5502. --|  EXCEPTIONS HANDLED:
  5503. --|    none
  5504. --| 
  5505. --|  HISTORY:
  5506. --|    written by   May Lee   March 1985
  5507. --|
  5508. -------------------------------------------------------------------------------
  5509.  
  5510.   --  instantiation of generic list handler done in DATA_PKG
  5511.   use EL_LIST_PKG;
  5512.   use AC_LIST_PKG;
  5513.   use SS_LIST_PKG;
  5514.   use BOOLEAN_TEXT_IO;
  5515.  
  5516.   procedure AC_ADD        is separate;
  5517.   procedure AC_INITIALIZE is separate;
  5518.   procedure AC_SET_UP     is separate;
  5519.   procedure AC_DELETE     is separate;
  5520.   procedure AC_MODIFY     is separate;
  5521.   procedure AC_SAVE       is separate;
  5522.  
  5523. end ACTIVITY_PKG;
  5524.  
  5525. --*****************************************************************************
  5526.  
  5527.   separate( TRACKER.ACTIVITY_PKG )
  5528.   procedure AC_ADD is
  5529.   ------------------------------------------------------------------------------
  5530.   --|
  5531.   --|  NAME:  AC_ADD
  5532.   --|
  5533.   --|  OVERVIEW:
  5534.   --|    This procedure sets up the record to be added to the list by
  5535.   --|    user prompt/response.  The prompts are called from the Prompt_pkg,
  5536.   --|    which returns a valid response.  The complete record is then added 
  5537.   --|    to the linked list by calling the generic List_pkg procedure ADD.
  5538.   --|
  5539.   --|  EXCEPTIONS HANDLED:
  5540.   --|    none
  5541.   --|  
  5542.   --|  HISTORY:
  5543.   --|    written by   May Lee   March 1985
  5544.   --|
  5545.   --|  NOTES:
  5546.   --|    A check is made to insure that the maximum number of activities
  5547.   --|    is not exceeded.
  5548.   --|
  5549.   --|    The number of activities is incremented in this procedure.
  5550.   ------------------------------------------------------------------------------
  5551.   a_char    : character := ' ';
  5552.   ac_record : activity_pointer;
  5553.   el_record : element_pointer;
  5554.   end_list  : boolean := false;
  5555.   ss_record : subsystem_pointer;
  5556.  
  5557.   begin
  5558.     new_line;
  5559.     -- check if num of activities is > max num of activities
  5560.     if num_of_activities > max_num_activities then
  5561.       put_line(" You are not allowed to add another activity because ");
  5562.       put(" you already have "); put(max_num_activities,1); put(" activities, ");
  5563.       new_line;
  5564.       put_line(" which is the most you are allowed to have. ");
  5565.  
  5566.     else
  5567.       -- create a pointer to an activity record
  5568.       ac_record := new activity_type;
  5569.  
  5570.       put_line(" If you would like more information on the type of data ");
  5571.       put_line(" to enter for any of the following questions, enter '?'. ");
  5572.       put_line(" Otherwise, enter the data requested.      ");
  5573.       new_line(2);
  5574.  
  5575.       -- get the record fields
  5576.       ac_record.name              := PROMPT_PKG.NEW_ACTIV_NAME;
  5577.       put_line(" What is this activity's percent of the project? "); 
  5578.       ac_record.percent_tot_proj  := PROMPT_PKG.PERCENT;
  5579.       ac_record.priority          := PROMPT_PKG.ACTIV_PRIORITY;
  5580.       ac_record.consider_in_calc  := PROMPT_PKG.CONSIDER_AC_IN_CALC;
  5581.       put_line(" What percentage is available at start? "); 
  5582.       ac_record.percent_at_start  := PROMPT_PKG.PERCENT;
  5583.  
  5584.       -- add the record to the linked list by calling the generic add
  5585.       ADD ( ac_list, ac_record.name(1..act_name_max_len), ac_record);
  5586.  
  5587.       -- increment number of activities
  5588.       num_of_activities := num_of_activities + 1;
  5589.  
  5590.       -- walk ss list and prompt for extra task number
  5591.       START_WALK( ss_list );
  5592.       loop
  5593.         WALK( ss_list, ss_record, end_list );
  5594.         exit when end_list;
  5595.         ss_record.task_numbers(num_of_activities)
  5596.         := PROMPT_PKG.TASK_NUMBER_BY_AC( ss_record );
  5597.       end loop;
  5598.       new_line(2);
  5599.  
  5600.       -- Walk the element list and check each element.
  5601.       -- If multiple people on an element, default the person's initials
  5602.       -- for the new activity to be the person working on the previous ac
  5603.       START_WALK( el_list );
  5604.       loop
  5605.         WALK( el_list, el_record, end_list );
  5606.         exit when end_list;
  5607.         -- check if multiple people
  5608.         if el_record.more_than_one_person then
  5609.           el_record.people_initials( num_of_activities ) := 
  5610.             el_record.people_initials( num_of_activities - 1 );
  5611.         end if;
  5612.       end loop;
  5613.       
  5614.       new_line;
  5615.       put(" The number of activities = "); put( num_of_activities,1); 
  5616.       new_line(2);
  5617.       delay 1.0;
  5618.  
  5619.     end if;  -- allowed to add another activity
  5620.   end AC_ADD;
  5621.  
  5622.  
  5623.   separate( TRACKER.ACTIVITY_PKG )
  5624.   procedure AC_INITIALIZE is
  5625.   ------------------------------------------------------------------------------
  5626.   --|
  5627.   --|  NAME:  AC_INITIALIZE
  5628.   --|
  5629.   --|  OVERVIEW:
  5630.   --|    This procedure is called only when a new TRACKER file has to
  5631.   --|    be created.  It is part of a forced user response to fill in
  5632.   --|    the necessary data to make TRACKER a complete report.  The
  5633.   --|    procedure AC_ADD is called to gather the information and put it
  5634.   --|    into a linked list.
  5635.   --|
  5636.   --|  EXCEPTIONS HANDLED:
  5637.   --|    none
  5638.   --|  
  5639.   --|  HISTORY:
  5640.   --|    written by   May Lee   March 1985
  5641.   --|
  5642.   ------------------------------------------------------------------------------
  5643.   add_another :  character := 'N';
  5644.   done        :  boolean   := false;
  5645.  
  5646.   begin
  5647.     --  get the data for the record and add to linked list
  5648.     while not done loop
  5649.       -- force the user to add at least one activity
  5650.       AC_ADD; -- data to the record and the record to the list
  5651.       loop
  5652.         put_line("Would you like to add another activity?  ");
  5653.         put("  [ Y or N, <cr>=N ]  :  ");
  5654.         if end_of_line then -- pressed return, default to no
  5655.           skip_line;
  5656.           new_line(2);
  5657.           done := true;    
  5658.           exit;
  5659.         else      
  5660.           get(add_another); skip_line;
  5661.           new_line(2);
  5662.           if add_another = 'N' or add_another = 'n' then
  5663.             done := true;    
  5664.             exit;
  5665.           elsif add_another = 'Y' or add_another = 'y' then
  5666.             exit;
  5667.           else
  5668.             put_line(" Please enter y or n. "); 
  5669.           end if;
  5670.         end if;
  5671.       end loop;
  5672.     end loop;
  5673.   end AC_INITIALIZE;
  5674.  
  5675.  
  5676.   separate( TRACKER.ACTIVITY_PKG )
  5677.   procedure AC_SET_UP is
  5678.   ------------------------------------------------------------------------------
  5679.   --|
  5680.   --|  NAME:  AC_SET_UP
  5681.   --|
  5682.   --|  OVERVIEW:
  5683.   --|    This procedure is only called if there is an existing input file.
  5684.   --|    The activity record is read from the input file by calling AC_READ.
  5685.   --|    Each record is added to the linked list by calling the generic List_Pkg
  5686.   --|    procedure ADD until there are no more activity records.  
  5687.   --|
  5688.   --|  EXCEPTIONS HANDLED:
  5689.   --|    others        Error reading the record from the file.
  5690.   --|    .        This exception raises ERROR_IN_INPUT_FILE.
  5691.   --|  
  5692.   --|  HISTORY:
  5693.   --|    written by   May Lee   March 1985
  5694.   --|
  5695.   --|  NOTES:
  5696.   --|    The number of activities records read in is determined by the
  5697.   --|    global variable num_of_activities.
  5698.   --|
  5699.   --|    If an error is detected reading the data, the rest of the input line
  5700.   --|    is skipped and reading the rest of the data continues.  All errors
  5701.   --|    found are reported.  Execution is not terminated until the entire
  5702.   --|    input file has been read.
  5703.   --|
  5704.   ------------------------------------------------------------------------------
  5705.   ac_record  : activity_pointer;
  5706.   ac_num     : integer := 1;       -- number of current activity
  5707.   bad_data   : boolean := false;
  5708.  
  5709.   procedure AC_READ is separate;
  5710.  
  5711.   begin
  5712.     for i in 1..num_of_activities loop
  5713.       begin
  5714.         ac_num := i;
  5715.         -- create a null activity record
  5716.         ac_record := new activity_type;
  5717.         --   read the activity from the file
  5718.         AC_READ;
  5719.         --   add it to the linked list
  5720.         ADD(ac_list, ac_record.name, ac_record); 
  5721.       exception
  5722.         when others =>
  5723.           skip_line(tracker_file);
  5724.           put(" Error reading activity record "); put( ac_num,1); 
  5725.           put(" from the tracker file. "); new_line;
  5726.           bad_data := true;
  5727.       end;
  5728.     end loop;
  5729.     if bad_data then
  5730.       raise ERROR_IN_INPUT_FILE;
  5731.     end if;
  5732.   end AC_SET_UP;
  5733.  
  5734.  
  5735.     separate( TRACKER.ACTIVITY_PKG.AC_SET_UP )
  5736.     procedure AC_READ is
  5737.     --|
  5738.     --|  NAME:  AC_READ
  5739.     --|
  5740.     --|  OVERVIEW:
  5741.     --|    This procedure reads a record from the file.  One line of data is
  5742.     --|    read at a time and broken down into the fields of the
  5743.     --|    activity record, which is made visible to the calling routine
  5744.     --|    AC_SET_UP.  The data is read in the format specified by the AC_WRITE
  5745.     --|    procedure.
  5746.     --|
  5747.     --|  EXCEPTIONS HANDLED:
  5748.     --|    none
  5749.     --|
  5750.     --|  HISTORY:
  5751.     --|    written by   May Lee   March 1985
  5752.     --|
  5753.     --|  NOTES:
  5754.     --|    Any exceptions raised here are handled by AC_SET_UP.
  5755.     begin
  5756.       get( tracker_file, ac_record.name );
  5757.       get( tracker_file, ac_record.percent_tot_proj, 5 );   -- real type
  5758.       get( tracker_file, ac_record.priority, 2 );           -- integer type
  5759.       get( tracker_file, ac_record.percent_at_start, 5 );   -- real type
  5760.       get( tracker_file, ac_record.consider_in_calc );      -- boolean
  5761.       skip_line(tracker_file);
  5762.     end AC_READ;
  5763.  
  5764.  
  5765.   separate( TRACKER.ACTIVITY_PKG )
  5766.   procedure AC_DELETE is
  5767.   ------------------------------------------------------------------------------
  5768.   --|
  5769.   --|  NAME:  AC_DELETE
  5770.   --|
  5771.   --|  OVERVIEW:
  5772.   --|    This procedure is used to delete a record from the list by calling
  5773.   --|    the generic procedure DELETE.  The user is prompted for an existing
  5774.   --|    activity to delete by a call to Prompt_pkg.  When an activity is 
  5775.   --|    deleted, its completeness information, which is stored as a field 
  5776.   --|    in the element record, must also be deleted by calling the 
  5777.   --|    procedure DELETE_AC_COMPLETENESS.
  5778.   --|
  5779.   --|  EXCEPTIONS HANDLED:
  5780.   --|    none
  5781.   --|  
  5782.   --|  HISTORY:
  5783.   --|    written by   May Lee   March 1985
  5784.   --|
  5785.   --|  NOTES:
  5786.   --|    The number of activities is decremented if the delete is successful.
  5787.   --|
  5788.   --|    A check is made to insure the last activity is not deleted.  There
  5789.   --|    must be at least one activity at all times.
  5790.   ------------------------------------------------------------------------------
  5791.   abort_proc   : boolean;           -- abort getting an existing AC
  5792.   ac_number    : integer := 0;      -- number of the activity we are deleting
  5793.   ac_record    : activity_pointer;  -- activity record
  5794.   end_list     : boolean;           -- parameter to walk
  5795.   found        : boolean;           -- parameter to find
  5796.   key          : ac_name_type;      -- name of activity looking for
  5797.   new_number   : ac_name_type;      -- replacement ac
  5798.   successful   : boolean := false;  -- if key found in list
  5799.  
  5800.   procedure DELETE_AC_COMPLETENESS is separate;
  5801.   procedure DELETE_SS_TASK_NUM     is separate;
  5802.   procedure DELETE_MULTIPLE_PEOPLE is separate;
  5803.  
  5804.   begin
  5805.     if num_of_activities > 1 then  -- have to have at least one activity
  5806.       put_line("Which activity would you like to delete? ");
  5807.       -- get the name
  5808.       PROMPT_PKG.EXISTING_ACTIV_NAME( abort_proc, key );
  5809.  
  5810.       if not abort_proc then
  5811.         -- get the number of the activity so we can delete it from the
  5812.         -- activity completeness array and subsystem task number array
  5813.         START_WALK( ac_list );
  5814.         loop
  5815.           WALK( ac_list, ac_record, end_list );
  5816.           ac_number := ac_number + 1;
  5817.           if ac_record.name = key then
  5818.             exit;
  5819.           end if;
  5820.         end loop;
  5821.  
  5822.         --  delete the activity from the list
  5823.         DELETE( ac_list, key, successful );
  5824.  
  5825.         if successful then -- activity was found and deleted from the list
  5826.           --  delete activity completeness information from element data
  5827.           DELETE_AC_COMPLETENESS;
  5828.           DELETE_SS_TASK_NUM;
  5829.           -- if multiple people on an element, delete person's initials from ac
  5830.           DELETE_MULTIPLE_PEOPLE;
  5831.           --  decrement num of activities counter
  5832.           num_of_activities := num_of_activities - 1;
  5833.  
  5834.       new_line;
  5835.           put(" The number of activities = "); put(num_of_activities,1); 
  5836.       new_line(2);
  5837.           delay 1.0;
  5838.  
  5839.         end if;
  5840.     
  5841.       end if; -- not abort
  5842.     else
  5843.       put_line(" You must have at least one activity at all times. ");
  5844.       put_line(" Since you only have one activity at this time, you ");
  5845.       put_line(" cannot delete it. ");        
  5846.     end if;
  5847.   end AC_DELETE;
  5848.  
  5849.  
  5850.   separate( TRACKER.ACTIVITY_PKG.AC_DELETE )
  5851.   procedure DELETE_AC_COMPLETENESS is
  5852.   -----------------------------------------------------------------------------
  5853.   --|
  5854.   --|  NAME: DELETE_AC_COMPLETENESS
  5855.   --|
  5856.   --|  OVERVIEW:
  5857.   --|    This procedure is called when an activity is deleted from the
  5858.   --|    activity list.  When an activity is deleted, the element list is
  5859.   --|    walked and the activity completeness is deleted in each element
  5860.   --|    to account for the missing activity.  Since the activity completeness 
  5861.   --|    is stored as an array in a field of the element, the array cell 
  5862.   --|    corresponding to the number of the activity in the activity list 
  5863.   --|    is deleted.  The remaining array cells are moved up one cell space.
  5864.   --|    The number of the cell to be deleted is ac_number.
  5865.   --| 
  5866.   --|  EXCEPTIONS HANDLED:
  5867.   --|    none 
  5868.   --|
  5869.   --|  HISTORY:
  5870.   --|    written by   May Lee   March 1985 
  5871.   --|
  5872.   -----------------------------------------------------------------------------
  5873.   end_list  : boolean;
  5874.   el_record : element_pointer;
  5875.  
  5876.   begin
  5877.     START_WALK( el_list );
  5878.     loop
  5879.       WALK( el_list, el_record, end_list );
  5880.       exit when end_list;
  5881.       if ac_number = max_num_activities then      
  5882.         -- last activity
  5883.         el_record.activity_completeness( ac_number ) := ' ';
  5884.       else
  5885.         -- delete ac from the activty completeness and move the rest up one
  5886.         el_record.activity_completeness( ac_number..max_num_activities - 1) :=
  5887.           el_record.activity_completeness( ac_number + 1..max_num_activities);
  5888.         -- blank out last activity completeness
  5889.         el_record.activity_completeness( max_num_activities ) := ' ';
  5890.       end if;
  5891.     end loop;
  5892.   end DELETE_AC_COMPLETENESS;
  5893.  
  5894.  
  5895.   separate( TRACKER.ACTIVITY_PKG.AC_DELETE )
  5896.   procedure DELETE_SS_TASK_NUM is
  5897.   -----------------------------------------------------------------------------
  5898.   --|
  5899.   --|  NAME: DELETE_SS_TASK_NUM
  5900.   --|
  5901.   --|  OVERVIEW:
  5902.   --|    This procedure is called when an activity is deleted from the
  5903.   --|    activity list.  When an activity is deleted, the subsystem list is
  5904.   --|    walked and the task number associated with that activity is deleted 
  5905.   --|    from each subsystem's task number field array.  Since the task number
  5906.   --|    is stored as an array in a field of the subsystem, the array cell 
  5907.   --|    corresponding to the number of the activity in the activity list 
  5908.   --|    is deleted.  The remaining array cells are moved up one cell space.
  5909.   --|    The number of the cell to be deleted is ac_number.
  5910.   --| 
  5911.   --|  EXCEPTIONS HANDLED:
  5912.   --|    none 
  5913.   --|
  5914.   --|  HISTORY:
  5915.   --|    written by   May Lee   March 1985 
  5916.   --|
  5917.   -----------------------------------------------------------------------------
  5918.   end_list  : boolean;
  5919.   ss_record : subsystem_pointer;
  5920.  
  5921.   begin
  5922.     START_WALK( ss_list );
  5923.     loop
  5924.       WALK( ss_list, ss_record, end_list );
  5925.       exit when end_list;
  5926.       if ac_number = max_num_activities then      
  5927.         -- last activity
  5928.         ss_record.task_numbers( ac_number ) := 0;
  5929.       else
  5930.         -- delete task number from the array and move the rest up one
  5931.         ss_record.task_numbers( ac_number..max_num_activities - 1) :=
  5932.           ss_record.task_numbers( ac_number + 1..max_num_activities);
  5933.         -- zero out last task number
  5934.         ss_record.task_numbers( max_num_activities ) := 0;
  5935.       end if;
  5936.     end loop;
  5937.   end DELETE_SS_TASK_NUM;
  5938.  
  5939.   separate( TRACKER.ACTIVITY_PKG.AC_DELETE )
  5940.   procedure DELETE_MULTIPLE_PEOPLE is 
  5941.   -----------------------------------------------------------------------------
  5942.   --|
  5943.   --|  NAME: DELETE_MULTIPLE_PEOPLE 
  5944.   --|
  5945.   --|  OVERVIEW:
  5946.   --|    This procedure is called when an activity is deleted from the
  5947.   --|    activity list.  The element list is walked. If it is a multiple person
  5948.   --|    element, the person's inititals associated with that activity is 
  5949.   --|    deleted from that element record's people_initials variant field.
  5950.   --|    Since the person's initials are stored as an array, the array cell 
  5951.   --|    corresponding to the number of the activity in the activity list 
  5952.   --|    is deleted.  The remaining array cells are moved up one cell space.
  5953.   --|    The number of the cell to be deleted is ac_number.
  5954.   --| 
  5955.   --|  EXCEPTIONS HANDLED:
  5956.   --|    none 
  5957.   --|
  5958.   --|  HISTORY:
  5959.   --|    written by   May Lee   March 1985 
  5960.   --|
  5961.   -----------------------------------------------------------------------------
  5962.   end_list  : boolean;
  5963.   el_record : element_pointer;
  5964.  
  5965.   begin
  5966.     START_WALK( el_list );
  5967.     loop
  5968.       WALK( el_list, el_record, end_list );
  5969.       exit when end_list;
  5970.       -- check if multiple element
  5971.       if el_record.more_than_one_person then
  5972.         if ac_number = max_num_activities then      
  5973.           -- last activity
  5974.           el_record.people_initials( ac_number ) := "  ";
  5975.         else
  5976.           -- delete person's initials from the array and move the rest up one
  5977.           el_record.people_initials( ac_number..max_num_activities - 1) :=
  5978.             el_record.people_initials( ac_number + 1..max_num_activities);
  5979.           -- blank out last person's initials
  5980.           el_record.people_initials( max_num_activities ) := "  ";
  5981.         end if;
  5982.       end if;
  5983.     end loop;
  5984.   end DELETE_MULTIPLE_PEOPLE;
  5985.  
  5986.   separate( TRACKER.ACTIVITY_PKG )
  5987.   procedure AC_MODIFY is
  5988.   ------------------------------------------------------------------------------
  5989.   --|
  5990.   --|  NAME:  AC_MODIFY
  5991.   --|
  5992.   --|  OVERVIEW:
  5993.   --|    This procedure allows the user to modify an existing record.
  5994.   --|    The user is prompted for an existing activity record by calling
  5995.   --|    the appropriate Prompt_Pkg function.  The generic FIND is used to 
  5996.   --|    get the record.  The user is then allowed to change the fields by
  5997.   --|    choosing a menu selection.  The record fields are modified directly.
  5998.   --|    If the activity name is modified, MODIFY_AC_KEY is called.
  5999.   --|
  6000.   --|  EXCEPTIONS HANDLED:
  6001.   --|    none     
  6002.   --|  
  6003.   --|  HISTORY:
  6004.   --|    written by   May Lee   March 1985     
  6005.   --|
  6006.   ------------------------------------------------------------------------------
  6007.   abort_proc      : boolean := false;  -- abort getting existing ac
  6008.   activity_name   : ac_name_type;      -- name of activity looking for
  6009.   ac_record       : activity_pointer;
  6010.   exit_field_menu : boolean := false;  -- exit activity field menu
  6011.   field_selection : integer;           -- selection from activity field menu
  6012.   found           : boolean := false;  -- if the record was found in the list
  6013.   key             : ac_name_type;      -- num of milestone looking for
  6014.  
  6015.  
  6016.   procedure MODIFY_AC_KEY is separate;
  6017.  
  6018.   begin
  6019.     put_line("Which activity would you like to modify?");
  6020.     PROMPT_PKG.EXISTING_ACTIV_NAME( abort_proc, key );
  6021.  
  6022.     if not abort_proc then 
  6023.       -- set pointer to that activity, returned in ac_record
  6024.       FIND( ac_list, key, ac_record, found);
  6025.  
  6026.       while not exit_field_menu loop
  6027.         field_selection := VT100.PRINT_AC_MENU( ac_record );
  6028.         case field_selection is 
  6029.  
  6030.           when 1 =>  -- get activity name, change key
  6031.             put(" The current activity name is : "); 
  6032.             put( ac_record.name(1..act_name_max_len) ); new_line(2);
  6033.             put_line(" What would you like to change the activity name to? ");
  6034.             MODIFY_AC_KEY;
  6035.  
  6036.  
  6037.           when 2 =>  -- Get percentage of total project
  6038.             put(" The current percentage of the total project is : "); 
  6039.             put( ac_record.percent_tot_proj, 3,1,0 ); new_line(2);
  6040.             put_line(" What would you like to change the percentage to? ");
  6041.             ac_record.percent_tot_proj := PROMPT_PKG.PERCENT;
  6042.  
  6043.           when 3 =>  -- Get priority
  6044.             put(" The current priority is : "); 
  6045.             put( ac_record.priority, 2 ); new_line(2);
  6046.             put_line(" What would you like to change the priority to? ");
  6047.             ac_record.priority  := PROMPT_PKG.ACTIV_PRIORITY;
  6048.  
  6049.           when 4 =>  -- Get consider in calculations
  6050.             if ac_record.consider_in_calc then
  6051.               put(" This activity is being considered ");
  6052.               put("in the tracker calculations. "); new_line(2);
  6053.               put_line(" Do you still want it to be considered ? ");
  6054.             else
  6055.               put(" This activity is not being considered ");
  6056.               put("in the tracker calculations. "); new_line(2);
  6057.               put_line(" Do you want it to be considered ? ");
  6058.             end if;
  6059.             ac_record.consider_in_calc := PROMPT_PKG.CONSIDER_AC_IN_CALC;
  6060.  
  6061.           when 5 =>  -- Get percent at start
  6062.             put(" The current percentage at start is : "); 
  6063.             put( ac_record.percent_at_start, 3,1,0 ); new_line(2);
  6064.             put_line(" What would you like to change the percentage to? ");
  6065.             ac_record.percent_at_start := PROMPT_PKG.PERCENT;
  6066.  
  6067.           when 6 =>  exit_field_menu := true;
  6068.  
  6069.           when others => put_line("Please enter a number beween 1 and 6.");
  6070.         end case;
  6071.       end loop;    
  6072.     end if;     
  6073.  
  6074.   end AC_MODIFY;
  6075.  
  6076.  
  6077.     separate ( TRACKER.ACTIVITY_PKG.AC_MODIFY )
  6078.     procedure MODIFY_AC_KEY is 
  6079.     ---------------------------------------------------------------------------
  6080.     --|
  6081.     --|  NAME:  MODIFY_AC_KEY
  6082.     --|
  6083.     --|  OVERVIEW:
  6084.     --|    This procedure is called if the activity name is modified.  
  6085.     --|    The name must be changed in the list search key by calling
  6086.     --|    the List_pkg procedure CHANGE_LIST_KEY, as well as in the
  6087.     --|    record data.
  6088.     --|
  6089.     --|  EXCEPTIONS HANDLED:
  6090.     --|    none     
  6091.     --|  
  6092.     --|  HISTORY:
  6093.     --|    written by   May Lee   March 1985     
  6094.     --|
  6095.     ---------------------------------------------------------------------------
  6096.       new_name : ac_name_type;
  6097.     begin
  6098.       new_name := PROMPT_PKG.NEW_ACTIV_NAME;
  6099.       -- change the search key in the activity list 
  6100.       CHANGE_LIST_KEY( ac_list, ac_record.name, new_name );
  6101.       -- change the name in the record
  6102.       ac_record.name := new_name;
  6103.     end MODIFY_AC_KEY;
  6104.  
  6105.  
  6106.  
  6107.   separate( TRACKER.ACTIVITY_PKG )
  6108.   procedure AC_SAVE is
  6109.   ------------------------------------------------------------------------------
  6110.   --|
  6111.   --|  NAME:  AC_SAVE
  6112.   --|
  6113.   --|  OVERVIEW:
  6114.   --|    This procedure saves a record to file by calling the AC_WRITE 
  6115.   --|    procedure.  The generic procedures START_WALK and WALK are called
  6116.   --|    to walk the linked list allowing one record at a time to be written.
  6117.   --|
  6118.   --|  EXCEPTIONS HANDLED:
  6119.   --|    none
  6120.   --|  
  6121.   --|  HISTORY:
  6122.   --|    written by   May Lee   March 1985
  6123.   --|
  6124.   ------------------------------------------------------------------------------
  6125.   end_list    : boolean := false;
  6126.   ac_record   : activity_pointer;
  6127.  
  6128.   procedure AC_WRITE is separate;
  6129.   
  6130.   begin
  6131.     START_WALK( ac_list);
  6132.     loop
  6133.       WALK( ac_list, ac_record, end_list);
  6134.       exit when end_list;
  6135.       AC_WRITE;
  6136.     end loop;
  6137.   end AC_SAVE;
  6138.  
  6139.     separate( TRACKER.ACTIVITY_PKG.AC_SAVE )
  6140.     procedure AC_WRITE is
  6141.     --|
  6142.     --|  NAME:  AC_WRITE
  6143.     --|
  6144.     --|  OVERVIEW:
  6145.     --|    This procedure is passed in a record pointer.  The record is written
  6146.     --|    to one line of the output file in the following format:  
  6147.     --||
  6148.     --||           +----------+-----+--+----+-----+
  6149.     --||           | name     |p_tot|pr|cons|pc_st| 
  6150.     --||           +----------+-----+--+----+-----+
  6151.     --||
  6152.     --|
  6153.     --|    See DATA_PKG for the full names of the fields and their types.
  6154.     --|    The activity records are the second type of data to be written to the
  6155.     --|    output file.
  6156.     --|
  6157.     --|  EXCEPTIONS HANDLED:
  6158.     --|    none
  6159.     --|
  6160.     --|  HISTORY:
  6161.     --|    written by   May Lee   March 1985
  6162.     --|
  6163.  
  6164.     begin
  6165.       put( output_file, ac_record.name );
  6166.       put( output_file, ac_record.percent_tot_proj, 
  6167.            fore => 3, aft => 1, exp => 0 );             -- real type
  6168.       put( output_file, ac_record.priority, 2 );        -- integer type
  6169.       put( output_file, ac_record.percent_at_start,
  6170.            fore => 3, aft => 1, exp => 0 );             -- real type
  6171.       put( output_file, ac_record.consider_in_calc, 5 );-- boolean
  6172.       new_line(output_file);
  6173.     end AC_WRITE;
  6174. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  6175. --ms.ada
  6176. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  6177. with PROMPT_PKG;   
  6178.  
  6179. separate(tracker)
  6180. package body milestone_pkg is
  6181. -------------------------------------------------------------------------------
  6182. --|
  6183. --|  NAME:  MILESTONE_PKG
  6184. --|
  6185. --|  OVERVIEW:
  6186. --|    This package defines the actions that can be performed on 
  6187. --|    milestone data types (defined in DATA_PKG).
  6188. --|
  6189. --|  EXCEPTIONS HANDLED:
  6190. --|    none 
  6191. --|  
  6192. --|  HISTORY:
  6193. --|    written by   May Lee   March 1985
  6194. --|
  6195. -------------------------------------------------------------------------------
  6196.  
  6197.   --  instantiation of generic list handler done in DATA_PKG
  6198.   use EL_LIST_PKG;
  6199.   use MS_LIST_PKG;
  6200.   
  6201.   procedure CHANGE_MS_IN_EL( ms_record  : in milestone_pointer;
  6202.                              new_number : in MS_NUM_TYPE ) is separate;
  6203.   procedure MS_ADD        is separate;
  6204.   procedure MS_INITIALIZE is separate;
  6205.   procedure MS_SET_UP     is separate;
  6206.   procedure MS_DELETE     is separate;
  6207.   procedure MS_MODIFY     is separate;
  6208.   procedure MS_SAVE       is separate;
  6209.  
  6210. end MILESTONE_PKG;
  6211.  
  6212. --*****************************************************************************
  6213.  
  6214. separate( TRACKER.MILESTONE_PKG )
  6215.   procedure CHANGE_MS_IN_EL ( ms_record : in milestone_pointer;
  6216.                               new_number : in ms_num_type ) is
  6217.   -----------------------------------------------------------------------------
  6218.   --|
  6219.   --|  NAME: CHANGE_MS_IN_EL
  6220.   --|
  6221.   --|  OVERVIEW:
  6222.   --|    This procedure is called when a milestone is deleted from or modified
  6223.   --|    in the milestone list.  Before either of these actions can be taken,
  6224.   --|    the element list that contains milestones with the same number is 
  6225.   --|    walked.  This list is a field of the milestone data record.
  6226.   --|    The milestone number field of each element record is reassigned
  6227.   --|    the new milestone number.
  6228.   --|
  6229.   --|  EXCEPTIONS HANDLED:
  6230.   --|    none 
  6231.   --|
  6232.   --|  HISTORY:
  6233.   --|    written by   May Lee   March 1985 
  6234.   --|
  6235.   -----------------------------------------------------------------------------
  6236.   el_record       : element_pointer;   -- ms element list
  6237.   end_list        : boolean;
  6238.  
  6239.   begin
  6240.     -- change the ms number field in el_record of the milestone's el list
  6241.     START_WALK( ms_record.element_list );
  6242.     loop
  6243.       WALK( ms_record.element_list, el_record, end_list );
  6244.       exit when end_list;
  6245.       el_record.milestone_num := new_number;
  6246.     end loop;
  6247.   end CHANGE_MS_IN_EL;
  6248.  
  6249.   separate( TRACKER.MILESTONE_PKG )
  6250.   procedure MS_ADD is
  6251.   -----------------------------------------------------------------------------
  6252.   --|
  6253.   --|  NAME:  MS_ADD
  6254.   --|
  6255.   --|  OVERVIEW:
  6256.   --|    This procedure sets up the record to be added to the list by
  6257.   --|    user prompt/response.  The function calls to Prompt_Pkg return
  6258.   --|    only valid existing data.  The complete record is 
  6259.   --|    then added to the linked list by calling the generic list procedure
  6260.   --|    ADD.
  6261.   --|
  6262.   --|  EXCEPTIONS HANDLED:
  6263.   --|    none
  6264.   --|  
  6265.   --|  HISTORY:
  6266.   --|    written by   May Lee   March 1985
  6267.   --|
  6268.   --|  NOTES:
  6269.   --|    The number of milestones is incremented in this procedure.
  6270.   -----------------------------------------------------------------------------
  6271.   ms_record  : milestone_pointer;  -- pointer to ms data
  6272.  
  6273.   begin
  6274.     -- create a null milestone record
  6275.     ms_record := new milestone_type;
  6276.  
  6277.     new_line;
  6278.     put_line(" If you would like more information on the type of data ");
  6279.     put_line(" to enter for any of the following questions, enter a '?'");
  6280.     put_line(" Otherwise, enter the data requested.      ");
  6281.     new_line(2);
  6282.  
  6283.     -- get the record fields
  6284.     ms_record.number       := PROMPT_PKG.NEW_MILSTONE_NUMBER;
  6285.     ms_record.completion_number := 
  6286.     PROMPT_PKG.MILESTONE_COMPLETION_NUMBER (default => ms_record.number);
  6287.     put_line(" What is the due date? "); 
  6288.     ms_record.due_date     := PROMPT_PKG.DATE;
  6289.     ms_record.description  := PROMPT_PKG.MS_DESCRIPTION;
  6290.  
  6291.     -- add the record to the linked list by calling the generic add
  6292.     ADD ( ms_list, ms_record.number, ms_record);
  6293.  
  6294.     -- increment milestone counter
  6295.     num_of_milestones := num_of_milestones + 1;
  6296.  
  6297.     new_line;
  6298.     put(" The number of milestones = "); put( num_of_milestones,1); 
  6299.     new_line(2);
  6300.     delay 1.0;
  6301.   end MS_ADD;
  6302.  
  6303.  
  6304.   separate( TRACKER.MILESTONE_PKG )
  6305.   procedure MS_INITIALIZE is
  6306.   -----------------------------------------------------------------------------
  6307.   --|
  6308.   --|  NAME:  MS_INITIALIZE
  6309.   --|
  6310.   --|  OVERVIEW:
  6311.   --|    This procedure is called only when a new TRACKER file has to
  6312.   --|    be created.  It is part of a forced user response to fill in
  6313.   --|    the necessary data to make TRACKER a complete report.  The
  6314.   --|    procedure MS_ADD is called to gather the information and put it
  6315.   --|    into a linked list.
  6316.   --|
  6317.   --|  EXCEPTIONS HANDLED:
  6318.   --|    none
  6319.   --|  
  6320.   --|  HISTORY:
  6321.   --|    written by   May Lee   March 1985
  6322.   --|
  6323.   --|  NOTES:
  6324.   --|    The user is forced to add at least one milestone record and then
  6325.   --|    is prompted to add another or not.
  6326.   -----------------------------------------------------------------------------
  6327.   add_another : character := 'N';
  6328.   done        : boolean   := false;
  6329.  
  6330.   begin
  6331.     while not done loop
  6332.       -- force the user to add at least one milestone
  6333.       MS_ADD; -- data to the record and the record to the list
  6334.       loop
  6335.         put_line("Would you like to add another milestone? ");
  6336.         put("  [ Y or N, <cr>=N ]  :  ");
  6337.         if end_of_line then -- pressed return, default to no
  6338.           skip_line;
  6339.           new_line(2);
  6340.           done := true;    
  6341.           exit;
  6342.         else      
  6343.           get(add_another); skip_line;
  6344.           new_line(2);
  6345.           if add_another = 'N' or add_another = 'n' then
  6346.             done := true;    
  6347.             exit;
  6348.           elsif add_another = 'Y' or add_another = 'y' then
  6349.             exit;
  6350.           else
  6351.             put_line(" Please enter y or n. ");
  6352.           end if;
  6353.         end if;
  6354.       end loop;
  6355.     end loop;
  6356.   end MS_INITIALIZE;
  6357.  
  6358.   separate( TRACKER.MILESTONE_PKG )
  6359.   procedure MS_SET_UP is
  6360.   -----------------------------------------------------------------------------
  6361.   --|
  6362.   --|  NAME:  MS_SET_UP
  6363.   --|
  6364.   --|  OVERVIEW:
  6365.   --|    This procedure is only called if there is an existing input file.
  6366.   --|    The milestone list is set up by reading the milestone record
  6367.   --|    from the input file by calling MS_READ, and adding it to the linked 
  6368.   --|    list by calling the generic procedure ADD until there are no more 
  6369.   --|    milestone records.
  6370.   --|
  6371.   --|  EXCEPTIONS HANDLED:
  6372.   --|    others        Error reading the record from the file.
  6373.   --|    .        This exception raises ERROR_IN_INPUT_FILE.
  6374.   --|  
  6375.   --|  HISTORY:
  6376.   --|    written by   May Lee   March 1985
  6377.   --|
  6378.   --|  NOTES:
  6379.   --|    The number of milestone records read in is determined by the
  6380.   --|    global variable num_of_milestones.
  6381.   --|
  6382.   --|    If an error is detected reading the data, the rest of the input line
  6383.   --|    is skipped and reading of the rest of the data continues.  All errors
  6384.   --|    found are reported.  Execution is not terminated until the entire
  6385.   --|    input file has been read.
  6386.   --|
  6387.   -----------------------------------------------------------------------------
  6388.   ms_num     : integer := 1;       -- number of current milestone
  6389.   ms_record  : milestone_pointer;
  6390.   bad_data   : boolean := false;
  6391.  
  6392.   procedure MS_READ is separate;
  6393.  
  6394.   begin
  6395.     for i in 1..num_of_milestones loop
  6396.       begin 
  6397.     ms_num := i;
  6398.     -- create a null milestone record
  6399.     ms_record := new milestone_type;
  6400.     -- read the milestone
  6401.     MS_READ;
  6402.     -- add it to the linked list
  6403.     ADD( ms_list, ms_record.number, ms_record); 
  6404.       exception
  6405.         when others =>
  6406.         bad_data := true;
  6407.         skip_line (tracker_file);
  6408.         put(" Error reading milestone "); put(ms_num,1); 
  6409.         put(" from the tracker file. "); new_line;
  6410.       end;
  6411.     end loop;
  6412.     if BAD_DATA then
  6413.       raise ERROR_IN_INPUT_FILE;
  6414.     end if;
  6415.   end MS_SET_UP;
  6416.  
  6417.     separate( TRACKER.MILESTONE_PKG.MS_SET_UP )
  6418.     procedure MS_READ is
  6419.     --|
  6420.     --|  NAME:  MS_READ
  6421.     --|
  6422.     --|  OVERVIEW:
  6423.     --|    This procedure reads a record from the file.  One line of data is
  6424.     --|    read at a time and broken down into the fields of the
  6425.     --|    milestone record, which is made visible to the calling routine
  6426.     --|    MS_SET_UP.  The data is read in the format specified by the MS_WRITE
  6427.     --|    procedure.
  6428.     --|
  6429.     --|
  6430.     --|  EXCEPTIONS HANDLED:
  6431.     --|    none
  6432.     --|
  6433.     --|  HISTORY:
  6434.     --|    written by   May Lee   March 1985
  6435.     --|
  6436.     --|  NOTES:
  6437.     --|    Any exceptions raised here are handled by MS_SET_UP.
  6438.     begin
  6439.       get( tracker_file, ms_record.number, 2 );  -- integer
  6440.       get( tracker_file, ms_record.completion_number, 2 );  -- integer
  6441.       get( tracker_file, ms_record.due_date.month, 2 );
  6442.       get( tracker_file, ms_record.due_date.day,   2 );
  6443.       get( tracker_file, ms_record.due_date.year,  4 );
  6444.       get( tracker_file, ms_record.description(1..50) );  -- string
  6445.       skip_line (tracker_file);
  6446.     end MS_READ;
  6447.  
  6448.  
  6449.   separate( TRACKER.MILESTONE_PKG )
  6450.   procedure MS_DELETE is
  6451.   -----------------------------------------------------------------------------
  6452.   --|
  6453.   --|  NAME:  MS_DELETE
  6454.   --|
  6455.   --|  OVERVIEW:
  6456.   --|    This procedure is used to delete a milestone from the list by calling
  6457.   --|    the List_Pkg procedure DELETE.  When a milestone is deleted from the
  6458.   --|    milestone list, the milestone number must also be changed in every
  6459.   --|    element to which it belonged by calling the procedure
  6460.   --|    CHANGE_MS_IN_EL.
  6461.   --|
  6462.   --|  EXCEPTIONS HANDLED:
  6463.   --|    none
  6464.   --|  
  6465.   --|  HISTORY:
  6466.   --|    written by   May Lee   March 1985
  6467.   --|
  6468.   --|  NOTES:
  6469.   --|    The number of milestones is decremented after the record is deleted.
  6470.   --|
  6471.   --|    A check is made to insure the last milestone is not deleted.  There
  6472.   --|    must be at least one milestone at all times.
  6473.   --|
  6474.   -----------------------------------------------------------------------------
  6475.  
  6476.   abort_proc   : boolean;           -- abort getting an existing ms
  6477.   end_list     : boolean := false;
  6478.   ele_ptr      : element_pointer;
  6479.   found        : boolean;           -- parameter to find
  6480.   ms_record    : milestone_pointer; -- pointer to milestone record
  6481.   new_ms_record: milestone_pointer; -- pointer to new milestone record
  6482.   new_number   : ms_num_type;       -- replacement ms
  6483.   successful   : boolean := false;  -- parameter to delete
  6484.   key          : ms_num_type;       -- num of milestone looking for
  6485.  
  6486.  
  6487.   begin
  6488.     if num_of_milestones > 1 then  -- have to have at least one milestone
  6489.       put_line("Which milestone would you like to delete? [ give milestone number] ");
  6490.  
  6491.       -- get the milestone number
  6492.       PROMPT_PKG.EXISTING_MILSTONE_NUMBER( abort_proc, key );
  6493.  
  6494.       if not abort_proc then
  6495.         --point to that record in the list
  6496.         FIND( ms_list, key, ms_record, found );
  6497.  
  6498.         -- delete the milestone from the list
  6499.         DELETE( ms_list, key, successful);
  6500.  
  6501.         -- check to see if this ms belonged to any elements
  6502.         START_WALK( ms_record.element_list );
  6503.         WALK( ms_record.element_list, ele_ptr, end_list );
  6504.  
  6505.         if not end_list then
  6506.           -- change milestone number in element data
  6507.           put(" When milestone "); put(ms_record.number, 1); put(" is deleted, "); new_line;
  6508.           put_line(" what milestone would you like to use in its place in the element data? ");
  6509.           -- prompt for new number
  6510.          loop
  6511.             PROMPT_PKG.EXISTING_MILSTONE_NUMBER( abort_proc, new_number );
  6512.         exit when not abort_proc;
  6513.         put_line(" You cannot abort the procedure at this time. ");
  6514.          put_line(" You must enter a valid milestone number.");
  6515.         new_line;
  6516.       end loop;
  6517.           FIND( ms_list, new_number, new_ms_record, found );
  6518.  
  6519.           -- change the milestone number in the element data
  6520.           CHANGE_MS_IN_EL( ms_record, new_number );
  6521.  
  6522.         -- append these elements to the new milestone's element list
  6523.       start_walk (ms_record.element_list);
  6524.       loop
  6525.           walk (ms_record.element_list, ele_ptr, end_list);
  6526.         exit when end_list;
  6527.         add (new_ms_record.element_list, ele_ptr.desc_key, ele_ptr);
  6528.       end loop;
  6529.         end if;
  6530.  
  6531.         -- decrement counter
  6532.         num_of_milestones := num_of_milestones - 1;
  6533.  
  6534.         new_line;
  6535.         put(" The number of milestones = "); put(num_of_milestones,1); 
  6536.         new_line(2);
  6537.         delay 1.0;
  6538.  
  6539.       end if; -- not abort
  6540.  
  6541.     else
  6542.       put_line(" You must have at least one milestone at all times. ");
  6543.       put_line(" Since you only have one milestone at this time, you ");
  6544.       put_line(" cannot delete it. ");        
  6545.       delay 2.0;
  6546.     end if;
  6547.   end MS_DELETE;
  6548.  
  6549.  
  6550.   separate( TRACKER.MILESTONE_PKG )
  6551.   procedure MS_MODIFY is
  6552.   -----------------------------------------------------------------------------
  6553.   --|
  6554.   --|  NAME:  MS_MODIFY
  6555.   --|
  6556.   --|  OVERVIEW:
  6557.   --|    This procedure allows the user to modify an existing milestone record.
  6558.   --|    The user is prompted for an existing milestone record by calling
  6559.   --|    the appropriate Prompt_Pkg function.  The generic FIND is used to 
  6560.   --|    get the record.  The user is then allowed to change the fields by
  6561.   --|    choosing a menu selection.  The record fields are modified directly.
  6562.   --|    When a milestone number is modified in the milestone record, the 
  6563.   --|    milestone number must also be changed in every element to 
  6564.   --|    which it belonged by calling the procedure MODIFY_MILESTONE_KEY.
  6565.   --|
  6566.   --|  EXCEPTIONS HANDLED:
  6567.   --|    none
  6568.   --|  
  6569.   --|  HISTORY:
  6570.   --|    written by   May Lee   March 1985
  6571.   --|
  6572.   -----------------------------------------------------------------------------
  6573.  
  6574.   use CALENDAR;
  6575.  
  6576.   abort_proc      : boolean;           -- abort getting existing ms
  6577.   exit_field_menu : boolean := false;  -- exit milestone field menu
  6578.   field_selection : integer;           -- selection from milestone field menu
  6579.   ms_record       : milestone_pointer; -- pointer to milestone data record
  6580.   key             : ms_num_type;       -- num of milestone looking for
  6581.   found           : boolean := false;  -- if the record was found in the list
  6582.   
  6583.   procedure MODIFY_MILESTONE_KEY is separate;
  6584.  
  6585.   begin
  6586.     new_line;
  6587.     put_line("What is the number of the milestone you would like to modify?");
  6588.     PROMPT_PKG.EXISTING_MILSTONE_NUMBER( abort_proc, key );
  6589.  
  6590.     -- set pointer to that milstone, returned in ms_record
  6591.     FIND( ms_list, key, ms_record, found );
  6592.  
  6593.     if not abort_proc then 
  6594.       while not exit_field_menu loop
  6595.         field_selection := VT100.PRINT_MS_MENU( ms_record );
  6596.         case field_selection is 
  6597.           when 1 =>  -- get milestone number..change the key
  6598.             put(" The current milestone number is "); put( ms_record.number, 2);
  6599.             new_line;
  6600.             put_line(" What would you like to change it to? ");
  6601.             MODIFY_MILESTONE_KEY;
  6602.  
  6603.           when 2 =>  -- get milestone completion number
  6604.             put(" The current milestone completion sequence number is "); 
  6605.         put( ms_record.completion_number, 2);
  6606.             new_line;
  6607.             put_line(" What would you like to change it to? ");
  6608.         ms_record.completion_number := 
  6609.         PROMPT_PKG.MILESTONE_COMPLETION_NUMBER 
  6610.         (default => ms_record.number);
  6611.  
  6612.           when 3 =>  -- get the due date
  6613.             put(" The current due date is "); 
  6614.             if ms_record.due_date = null_date then
  6615.               put("a null date. ");
  6616.             else
  6617.               put( ms_record.due_date.month,2 );
  6618.               put('/'); put( ms_record.due_date.day,2 ); put('/') ; 
  6619.               put( ms_record.due_date.year,4 ); 
  6620.             end if;
  6621.             new_line;
  6622.             put_line(" What would you like to change it to? ");
  6623.             ms_record.due_date := PROMPT_PKG.DATE;
  6624.           when 4 =>  -- Getting new description 
  6625.             put_line(" The current description is : ");
  6626.             put_line( ms_record.description(1..50) );
  6627.             new_line;
  6628.             put_line(" What would you like to change it to? ");
  6629.             ms_record.description := PROMPT_PKG.MS_DESCRIPTION;
  6630.           when 5 =>  exit_field_menu := true;
  6631.           when others => put_line(" Please enter a number beween 1 and 5.");
  6632.         end case;
  6633.       end loop;    
  6634.  
  6635.     end if;
  6636.   end MS_MODIFY;
  6637.  
  6638.     separate( TRACKER.MILESTONE_PKG.MS_MODIFY )
  6639.     procedure MODIFY_MILESTONE_KEY is
  6640.     --|
  6641.     --|  NAME:  MODIFY_MILESTONE_KEY
  6642.     --|
  6643.     --|  OVERVIEW:
  6644.     --|    This procedure is called when the milestone number is modified.
  6645.     --|    The user is prompted for a new unique key by calling the Prompt_Pkg
  6646.     --|    function.  The milestone number must be changed in the milestone
  6647.     --|    record, the search key for the milestone list, and the field of the
  6648.     --|    element record for each element in the milestone's element list.
  6649.     --|
  6650.     --|  EXCEPTIONS HANDLED:
  6651.     --|    none 
  6652.     --|  
  6653.     --|  HISTORY:
  6654.     --|    written by   May Lee   March 1985 
  6655.     --|
  6656.     ---------------------------------------------------------------------------
  6657.       blank_key     : ms_num_type;         -- to blank out the key
  6658.       new_number    : ms_num_type;         -- replacement ms
  6659.  
  6660.     begin            
  6661.       -- Change the key in the milestone list...
  6662.  
  6663.       -- get the new ms number
  6664.       new_number := PROMPT_PKG.NEW_MILSTONE_NUMBER;
  6665.  
  6666.       -- change milestone num in each element record of the ms_el_list
  6667.       CHANGE_MS_IN_EL( ms_record, new_number );
  6668.  
  6669.       -- change the search key in the milestone list 
  6670.       CHANGE_LIST_KEY( ms_list, ms_record.number, new_number );
  6671.  
  6672.       -- change number in the milestone record
  6673.       ms_record.number := new_number;
  6674.  
  6675.     end MODIFY_MILESTONE_KEY;
  6676.  
  6677.  
  6678.   separate( TRACKER.MILESTONE_PKG )
  6679.   procedure MS_SAVE is
  6680.   -----------------------------------------------------------------------------
  6681.   --|
  6682.   --|  NAME:  MS_SAVE
  6683.   --|
  6684.   --|  OVERVIEW:
  6685.   --|    This procedure saves a record to file by calling the MS_WRITE 
  6686.   --|    procedure.  The generic procedures START_WALK and WALK are called
  6687.   --|    to walk the linked list allowing one record at a time to be written.
  6688.   --|
  6689.   --|  EXCEPTIONS HANDLED:
  6690.   --|    none 
  6691.   --|  
  6692.   --|  HISTORY:
  6693.   --|    written by   May Lee   March 1985 
  6694.   --|
  6695.   -----------------------------------------------------------------------------
  6696.   end_list    : boolean := false;
  6697.   ms_record   : milestone_pointer;
  6698.  
  6699.   procedure MS_WRITE is separate;
  6700.  
  6701.   begin
  6702.     START_WALK( ms_list);
  6703.     --  walk the list one milestone at a time and write it to the file
  6704.     loop
  6705.       WALK( ms_list, ms_record, end_list);
  6706.       exit when end_list;
  6707.       MS_WRITE;
  6708.     end loop;
  6709.   end MS_SAVE;
  6710.  
  6711.     separate( TRACKER.MILESTONE_PKG.MS_SAVE )
  6712.     procedure MS_WRITE is
  6713.     --|
  6714.     --|  NAME:  MS_WRITE
  6715.     --|
  6716.     --|  OVERVIEW:
  6717.     --|    This procedure references the current record pointer.  The record
  6718.     --|    is written to one line of the output file in the following format:
  6719.     --||
  6720.     --||   +--+--+--+--+----+-------------------------+
  6721.     --||   |ms|cp|mm|dd|year|      description        |
  6722.     --||   +--+--+--+--+----+-------------------------+
  6723.     --||
  6724.     --|    See DATA_PKG for the full names of the fields and their types.
  6725.     --|    The milestone records are the third type of data to be written to the
  6726.     --|    output file.
  6727.     --|
  6728.     --|  EXCEPTIONS HANDLED:
  6729.     --|    none
  6730.     --|
  6731.     --|  HISTORY:
  6732.     --|    written by   May Lee   March 1985
  6733.     --|
  6734.     begin
  6735.       put( output_file, ms_record.number, 2 );  -- integer
  6736.       put( output_file, ms_record.completion_number, 2 );  -- integer
  6737.       put( output_file, ms_record.due_date.month, 2 );
  6738.       put( output_file, ms_record.due_date.day,   2 );
  6739.       put( output_file, ms_record.due_date.year,  4 );
  6740.       put( output_file, ms_record.description );  -- string
  6741.       new_line( output_file );
  6742.     end MS_WRITE;
  6743.       
  6744. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  6745. --pr.ada
  6746. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  6747. with PROMPT_PKG;
  6748.  
  6749. separate(tracker)
  6750. package body PERSONNEL_PKG is
  6751. --------------------------------------------------------------------------------
  6752. --|
  6753. --|  NAME:  PERSONNEL_PKG
  6754. --|
  6755. --|  OVERVIEW:
  6756. --|    This package defines the actions that can be performed on a
  6757. --|    personnel type (defined in DATA_PKG).
  6758. --|
  6759. --|  EXCEPTIONS HANDLED:
  6760. --|    none
  6761. --|
  6762. --|  HISTORY:
  6763. --|    written by   May Lee   March 1985
  6764. --|
  6765. --------------------------------------------------------------------------------
  6766.   -- instantiation of generic list handler done in DATA_PKG
  6767.   use EL_LIST_PKG;
  6768.   use PR_LIST_PKG;
  6769.   use CALENDAR;
  6770.  
  6771.  
  6772.   procedure CHANGE_PR_IN_EL( pr_record    : in personnel_pointer;
  6773.                              new_initials : in PR_INIT_TYPE ) is separate;
  6774.   procedure PR_ADD        is separate;
  6775.   procedure PR_INITIALIZE is separate;
  6776.   procedure PR_SET_UP     is separate;
  6777.   procedure PR_DELETE     is separate;
  6778.   procedure PR_MODIFY     is separate;
  6779.   procedure PR_SAVE       is separate;
  6780.  
  6781. end PERSONNEL_PKG;
  6782.  
  6783. --******************************************************************************
  6784.  
  6785.   separate( TRACKER.PERSONNEL_PKG )
  6786.   procedure CHANGE_PR_IN_EL( pr_record    : in personnel_pointer;
  6787.                              new_initials : in PR_INIT_TYPE ) is 
  6788.   -----------------------------------------------------------------------------
  6789.   --|
  6790.   --|  NAME: CHANGE_PR_IN_EL
  6791.   --|
  6792.   --|  OVERVIEW:
  6793.   --|    This procedure is called when a person is deleted from or modified 
  6794.   --|    in the personnel list.  Before either of these actions can be taken,
  6795.   --|    the element list that contains people with the same name is walked.
  6796.   --|    This list is a field of the personnel data record.
  6797.   --|    The person's initials field of each element record is reassigned
  6798.   --|    the new person.
  6799.   --|
  6800.   --|  EXCEPTIONS HANDLED:
  6801.   --|    none
  6802.   --|
  6803.   --|  HISTORY:
  6804.   --|    Written by   May Lee   March 1985 
  6805.   --|
  6806.   -----------------------------------------------------------------------------
  6807.  
  6808.   el_record       : element_pointer;   -- pr element list
  6809.   end_list        : boolean;
  6810.  
  6811.   begin
  6812.     -- change the pr number field in el_record of the person's el list
  6813.     START_WALK( pr_record.element_list );
  6814.     loop
  6815.       WALK( pr_record.element_list, el_record, end_list );
  6816.       exit when end_list;
  6817.       if el_record.more_than_one_person then
  6818.         for ac_index in 1..num_of_activities loop
  6819.       if el_record.people_initials(ac_index) = pr_record.initials then
  6820.         el_record.people_initials(ac_index) := new_initials;
  6821.       end if;
  6822.     end loop;
  6823.       else
  6824.     el_record.person_initials := new_initials;
  6825.       end if;
  6826.     end loop;
  6827.   end CHANGE_PR_IN_EL;
  6828.  
  6829.  
  6830.   separate( TRACKER.PERSONNEL_PKG )
  6831.   procedure PR_ADD is
  6832.   ------------------------------------------------------------------------------
  6833.   --|
  6834.   --|  NAME:  PR_ADD
  6835.   --|
  6836.   --|  OVERVIEW:
  6837.   --|    This procedure sets up the record to be added to the list by
  6838.   --|    user prompt/response.  The function calls to Prompt_Pkg return
  6839.   --|    only valid existing data.  The complete record is 
  6840.   --|    then added to the linked list by calling the generic list procedure
  6841.   --|    ADD.
  6842.   --|
  6843.   --|  EXCEPTIONS HANDLED:
  6844.   --|    none
  6845.   --|  
  6846.   --|  HISTORY:
  6847.   --|    written by   May Lee   March 1985
  6848.   --|
  6849.   --|  NOTES:
  6850.   --|    The number of people is incremented in this procedure.
  6851.   --|
  6852.   ------------------------------------------------------------------------------
  6853.   a_char    : character := ' ';
  6854.   pr_record : personnel_pointer;
  6855.  
  6856.   begin
  6857.     -- create a null personnel record
  6858.     pr_record := new personnel_type;
  6859.  
  6860.     new_line;
  6861.     put_line(" If you would like more information on the type of data ");
  6862.     put_line(" to enter for any of the following questions, enter a '?'");
  6863.     put_line(" Otherwise, enter the data requested.      ");
  6864.     new_line(2);
  6865.  
  6866.     --  get the record fields
  6867.     pr_record.name            := PROMPT_PKG.PERSONS_NAME;
  6868.     pr_record.initials        := PROMPT_PKG.NEW_PERSON_INITIALS;
  6869.     pr_record.production_rate := PROMPT_PKG.PR_PRODUCTION_RATE;
  6870.     pr_record.hours_per_week  := PROMPT_PKG.PR_HRS_PER_WEEK;
  6871.     put_line(" What is this person's start date? ");
  6872.     pr_record.start_dates(1)  := PROMPT_PKG.DATE;
  6873.  
  6874.     -- Get stop date  
  6875.     loop  -- until valid stop date
  6876.       new_line;
  6877.       put_line(" What is this person's stop date? ");
  6878.       pr_record.stop_dates(1)   := PROMPT_PKG.DATE;
  6879.  
  6880.       -- check if valid stop date
  6881.       if pr_record.stop_dates(1) = null_date then 
  6882.         for i in dates_list'first+1..dates_list'last loop
  6883.           pr_record.start_dates(i) := null_date;
  6884.           pr_record.stop_dates(i) := null_date;
  6885.         end loop;
  6886.         exit;
  6887.       elsif (pr_record.stop_dates(1) /= null_date) and 
  6888.          (pr_record.start_dates(1) /= null_date) and 
  6889.          (pr_record.stop_dates(1) < pr_record.start_dates(1) ) then
  6890.         put_line(" That is not a valid stop date.  The stop date must be ");
  6891.         put_line(" a later date than the start date.  TRY AGAIN!  ");
  6892.         put(" The start date is "); 
  6893.         put( pr_record.start_dates(1).month,2 );
  6894.         put('/'); put( pr_record.start_dates(1).day,2 ); put('/') ; 
  6895.         put( pr_record.start_dates(1).year, 4 ); 
  6896.         new_line;
  6897.       else
  6898.         exit;
  6899.       end if;
  6900.     end loop;
  6901.  
  6902.     -- if not null, ask if user wants to add more start/stop dates
  6903.     if pr_record.stop_dates(1) /= null_date then
  6904.       START_STOP_DATES_LOOP:
  6905.       for i in dates_list'first + 1..dates_list'last loop
  6906.         new_line;
  6907.         put_line(" Would you like to add another set of start/stop dates? ");
  6908.         put(" [y or n, <cr>=n] : ");
  6909.         if end_of_line then
  6910.           skip_line;
  6911.           exit START_STOP_DATES_LOOP;
  6912.         else
  6913.           get( a_char ); skip_line;
  6914.           if a_char = 'y' or a_char = 'Y' then
  6915.             START_DATE_LOOP:
  6916.             loop -- until valid start date
  6917.           new_line;
  6918.               put_line(" What is this person's start date? ");
  6919.               pr_record.start_dates(i)  := PROMPT_PKG.DATE;
  6920.               -- check if valid start date
  6921.               if pr_record.start_dates(i) = null_date then
  6922.                 for j in i..dates_list'last loop
  6923.                   pr_record.start_dates(j) := null_date;
  6924.                   pr_record.stop_dates(j)  := null_date;
  6925.                 end loop;
  6926.                 exit START_STOP_DATES_LOOP;
  6927.               elsif pr_record.start_dates(i) < pr_record.stop_dates(i-1) then
  6928.                 put_line(" That is not a valid start date.  The start date must be ");
  6929.                 put_line(" a later date than the previous stop date.  TRY AGAIN!  ");
  6930.                 put(" The previous stop date is "); 
  6931.                 put( pr_record.stop_dates(i-1).month,2 );
  6932.                 put('/'); put( pr_record.stop_dates(i-1).day,2 ); put('/') ; 
  6933.                 put( pr_record.stop_dates(i-1).year, 4 ); 
  6934.         new_line;
  6935.               else -- valid start date
  6936.                 exit START_DATE_LOOP;
  6937.               end if;
  6938.             end loop START_DATE_LOOP;
  6939.  
  6940.             -- get stop date
  6941.             STOP_DATE_LOOP:
  6942.             loop  -- until valid stop date
  6943.               new_line;
  6944.               put_line(" What is this person's stop date? ");
  6945.               pr_record.stop_dates(i)   := PROMPT_PKG.DATE;
  6946.               -- check if valid stop date
  6947.               if pr_record.stop_dates(i) = null_date then
  6948.                 for j in i+1..dates_list'last loop
  6949.                   pr_record.start_dates(j) := null_date;
  6950.                   pr_record.stop_dates(j)  := null_date;
  6951.                 end loop;
  6952.                 exit START_STOP_DATES_LOOP;
  6953.               elsif pr_record.stop_dates(i) < pr_record.start_dates(i) then
  6954.                 put_line(" That is not a valid stop date.  The stop date must be ");
  6955.                 put_line(" a later date than the start date.  TRY AGAIN!  ");
  6956.                 put(" The start date is "); 
  6957.                 put( pr_record.start_dates(i).month,2 );
  6958.                 put('/'); put( pr_record.start_dates(i).day,2 ); put('/') ; 
  6959.                 put( pr_record.start_dates(i).year, 4 ); 
  6960.                 new_line;
  6961.               else -- non-null and valid stop date
  6962.                 exit STOP_DATE_LOOP;
  6963.               end if;
  6964.             end loop STOP_DATE_LOOP;
  6965.  
  6966.           else  -- don't want to add another start/stop date
  6967.             exit START_STOP_DATES_LOOP;
  6968.           end if; 
  6969.         end if;  -- pressed <cr>
  6970.       end loop START_STOP_DATES_LOOP;  
  6971.     end if;  -- not null date
  6972.       
  6973.  
  6974.     -- add the record to the linked list by calling the generic add
  6975.     ADD ( pr_list, pr_record.initials, pr_record);
  6976.  
  6977.     -- increment people counter
  6978.     new_line;
  6979.     num_of_people := num_of_people + 1;
  6980.  
  6981.     new_line;
  6982.     put(" The number of people = "); put( num_of_people,2 ); new_line(2);
  6983.     delay 1.0;
  6984.   end PR_ADD;
  6985.  
  6986.  
  6987.   separate( TRACKER.PERSONNEL_PKG )
  6988.   procedure PR_INITIALIZE is
  6989.   ------------------------------------------------------------------------------
  6990.   --|
  6991.   --|  NAME:  PR_INITIALIZE
  6992.   --|
  6993.   --|  OVERVIEW:
  6994.   --|    This procedure is called only when a new TRACKER file has to
  6995.   --|    be created.  It is part of a forced user response to fill in
  6996.   --|    the necessary data to make TRACKER a complete report.  The
  6997.   --|    procedure PR_ADD is called to gather the information and put it
  6998.   --|    into a linked list.
  6999.   --|
  7000.   --|  EXCEPTIONS HANDLED:
  7001.   --|    none
  7002.   --|  
  7003.   --|  HISTORY:
  7004.   --|    written by   May Lee   March 1985
  7005.   --|
  7006.   --|  NOTES:
  7007.   --|    The user is forced to add at least one person record and then
  7008.   --|    is prompted to add another or not.
  7009.   --|
  7010.   ------------------------------------------------------------------------------
  7011.   add_another :  character := 'N'; 
  7012.   done        :  boolean   := false;
  7013.  
  7014.   begin
  7015.     while not done loop
  7016.       -- force the user to add at least one person
  7017.       PR_ADD; -- data to the recrd and the record to the list
  7018.       loop  -- until y or n
  7019.         put_line("Would you like to add another person? ");
  7020.         put("  [ Y or N, <cr>=N ]  :  ");
  7021.         if end_of_line then -- pressed return, default to no
  7022.       skip_line;
  7023.           done := true;    
  7024.           exit;
  7025.         else      
  7026.           get(add_another); skip_line;
  7027.           if add_another = 'N' or add_another = 'n' then
  7028.             done := true;    
  7029.             exit;
  7030.           elsif add_another = 'Y' or add_another = 'y' then
  7031.             exit;
  7032.           else
  7033.             put_line(" Please enter y or n. ");
  7034.           end if;
  7035.         end if;
  7036.       end loop;
  7037.       new_line;
  7038.     end loop;
  7039.   end PR_INITIALIZE;
  7040.  
  7041.  
  7042.   separate( TRACKER.PERSONNEL_PKG )
  7043.   procedure PR_SET_UP is
  7044.   ------------------------------------------------------------------------------
  7045.   --|
  7046.   --|  NAME:  PR_SET_UP
  7047.   --|
  7048.   --|  OVERVIEW:
  7049.   --|    This procedure is only called if there is an existing input file.
  7050.   --|    The people list is set up by reading the personnel record
  7051.   --|    from the input file by calling PR_READ, and adding it to the linked 
  7052.   --|    list by calling the generic procedure ADD until there are no more 
  7053.   --|    people records.
  7054.   --|
  7055.   --|  EXCEPTIONS HANDLED:
  7056.   --|    others        Error reading the record from the file.
  7057.   --|    .        This exception raises ERROR_IN_INPUT_FILE.
  7058.   --|  
  7059.   --|  HISTORY:
  7060.   --|    written by   May Lee   March 1985
  7061.   --|
  7062.   --|  NOTES:
  7063.   --|    The number of people records read in is determined by the
  7064.   --|    global variable num_of_people.
  7065.   --|
  7066.   --|    If an error is detected reading the data, the rest of the input line
  7067.   --|    is skipped and reading of the rest of the data continues.  All errors
  7068.   --|    found are reported.  Execution is not terminated until the entire
  7069.   --|    input file has been read.
  7070.   --|
  7071.   --|
  7072.   -----------------------------------------------------------------------------
  7073.   pr_num    : integer := 1;      -- number of person record in file
  7074.   pr_record : personnel_pointer;
  7075.   bad_data  : boolean := false;
  7076.  
  7077.   procedure PR_READ is separate;
  7078.  
  7079.   begin
  7080.     for i in 1..num_of_people loop
  7081.       begin
  7082.         pr_num := i;
  7083.  
  7084.         -- create a null person record
  7085.         pr_record := new personnel_type;
  7086.  
  7087.         -- read the person
  7088.         PR_READ;
  7089.  
  7090.         -- add it to the linked list
  7091.         ADD( pr_list, pr_record.initials, pr_record);
  7092.       exception
  7093.         when others =>
  7094.           skip_line( tracker_file);
  7095.           put(" Error in reading person "); put(pr_num); 
  7096.           put(" from the tracker file. "); new_line;
  7097.           bad_data := true;
  7098.       end;
  7099.     end loop;
  7100.     if bad_data then
  7101.       raise ERROR_IN_INPUT_FILE;
  7102.     end if;
  7103.   end PR_SET_UP;
  7104.  
  7105.     separate( TRACKER.PERSONNEL_PKG.PR_SET_UP )
  7106.     procedure PR_READ is
  7107.     ----------------------------------------------------------------------------
  7108.     --|
  7109.     --|  NAME:  PR_READ
  7110.     --|
  7111.     --|  OVERVIEW:
  7112.     --|    This procedure reads a record from the file.  One line of data is
  7113.     --|    read at a time and broken down into the fields of the
  7114.     --|    personnel record, which is made visible to the calling routine
  7115.     --|    PR_SET_UP.  The data is read in the format specified by the PR_WRITE
  7116.     --|    procedure.
  7117.     --|
  7118.     --|  EXCEPTIONS HANDLED:
  7119.     --|    none
  7120.     --|
  7121.     --|  HISTORY:
  7122.     --|    written by   May Lee   March 1985
  7123.     --|
  7124.     --|  NOTES:
  7125.     --|    Any exceptions raised here are handled by PR_SET_UP.
  7126.     ----------------------------------------------------------------------------
  7127.     begin
  7128.       get( tracker_file, pr_record.name );    -- string
  7129.       get( tracker_file, pr_record.initials ); 
  7130.       get( tracker_file, pr_record.production_rate, 7 );    -- real
  7131.       get( tracker_file, pr_record.hours_per_week,  width => 2 ); -- integer
  7132.       for i in dates_list'first..dates_list'last loop 
  7133.         -- get the sets of start/stop dates
  7134.         get( tracker_file, pr_record.start_dates(i).month,width => 2 );
  7135.         get( tracker_file, pr_record.start_dates(i).day,  width => 2 );
  7136.         get( tracker_file, pr_record.start_dates(i).year, width => 4 );
  7137.         get( tracker_file, pr_record.stop_dates(i).month, width => 2 );
  7138.         get( tracker_file, pr_record.stop_dates(i).day,   width => 2 );
  7139.         get( tracker_file, pr_record.stop_dates(i).year,  width => 4 );
  7140.       end loop;
  7141.       skip_line( tracker_file);
  7142.     end PR_READ;
  7143.  
  7144.  
  7145.   separate( TRACKER.PERSONNEL_PKG )
  7146.   procedure PR_DELETE is
  7147.   ------------------------------------------------------------------------------
  7148.   --|
  7149.   --|  NAME:  PR_DELETE
  7150.   --|
  7151.   --|  OVERVIEW:
  7152.   --|    This procedure is used to delete a record from the list by calling
  7153.   --|    the List_Pkg procedure delete.  When a person is deleted from the
  7154.   --|    personnel list, his initials also have to be changed in every 
  7155.   --|    element to which he belonged in the element list by calling the
  7156.   --|    procedure CHANGE_PR_IN_EL.
  7157.   --|
  7158.   --|  EXCEPTIONS HANDLED:
  7159.   --|    none
  7160.   --|  
  7161.   --|  HISTORY:
  7162.   --|    written by   May Lee   March 1985
  7163.   --|
  7164.   --|  NOTES:
  7165.   --|    The number of people is decremented after the record is deleted.
  7166.   --|
  7167.   --|    A check is made to insure that the last person is not deleted.  There
  7168.   --|    must be at least one person at all times.
  7169.   --|
  7170.   -----------------------------------------------------------------------------
  7171.  
  7172.   abort_proc   : boolean;           -- abort getting an existing pr
  7173.   end_list     : boolean := false;
  7174.   el_record    : element_pointer;
  7175.   ele_ptr      : element_pointer;
  7176.   found        : boolean;           -- parameter to find
  7177.   key          : pr_init_type;      -- initials of the person looking for
  7178.   new_initials : pr_init_type;      -- replacement pr
  7179.   pr_record    : personnel_pointer; -- person record
  7180.   new_pr_record: personnel_pointer; -- new person's record
  7181.   successful   : boolean := false;  -- if key found in list
  7182.  
  7183.   begin
  7184.     if num_of_people > 1 then  -- have to have at least one person
  7185.       put_line("Which person would you like to delete? ");
  7186.  
  7187.       -- get the person's initials
  7188.       PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, key );
  7189.  
  7190.       if not abort_proc then
  7191.         --point to that record in the list
  7192.         FIND( pr_list, key, pr_record, found );
  7193.  
  7194.         -- delete the person from the list
  7195.         DELETE( pr_list, key, successful);
  7196.  
  7197.         -- check to see if person belonged to an element
  7198.         START_WALK( pr_record.element_list );
  7199.         WALK( pr_record.element_list, ele_ptr, end_list );
  7200.         if not end_list then
  7201.           -- change person's initials in element data
  7202.           put(" When person "); put(pr_record.initials); put(" is deleted, "); new_line;
  7203.           put_line(" who would you like to use in his place in the element data? ");
  7204.           -- prompt for new number
  7205.           loop
  7206.             PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, new_initials );
  7207.           exit when not abort_proc;
  7208.             put_line(" You cannot abort the procedure at this time. ");
  7209.             put_line(" You must enter valid initials. ");
  7210.       end loop;
  7211.           FIND( pr_list, new_initials, new_pr_record, found );
  7212.  
  7213.           -- change the person's initials in the element data
  7214.           CHANGE_PR_IN_EL( pr_record, new_initials );
  7215.  
  7216.       -- move these elements to the new person's element list
  7217.         start_walk (pr_record.element_list);
  7218.       loop
  7219.           walk(pr_record.element_list, ele_ptr, end_list);
  7220.         exit when end_list;
  7221.         -- add the element to the person's list only if it isn't already
  7222.         -- in the person's element list.  This could happen if the element 
  7223.         -- was assigned to several people.
  7224.         find(new_pr_record.element_list, ele_ptr.desc_key, el_record, found);
  7225.         if not found then
  7226.           add (new_pr_record.element_list, ele_ptr.desc_key, ele_ptr);
  7227.         end if;
  7228.       end loop;
  7229.         end if;
  7230.  
  7231.         -- decrement the person counter
  7232.         num_of_people := num_of_people - 1;
  7233.  
  7234.         new_line;
  7235.         put(" The number of people = "); put(num_of_people,1); new_line(2);
  7236.         delay 1.0;
  7237.       end if; -- not abort
  7238.  
  7239.     else
  7240.       put_line(" You must have at least one person at all times. ");
  7241.       put_line(" Since you only have one person at this time, you ");
  7242.       put_line(" cannot delete. ");        
  7243.       delay 2.0;
  7244.     end if;
  7245.   end PR_DELETE;
  7246.  
  7247.  
  7248.   separate( TRACKER.PERSONNEL_PKG )
  7249.   procedure PR_MODIFY is
  7250.   ------------------------------------------------------------------------------
  7251.   --|
  7252.   --|  NAME:  PR_MODIFY
  7253.   --|
  7254.   --|  OVERVIEW:
  7255.   --|    This procedure allows the user to modify an existing person record.
  7256.   --|    The user is prompted for an existing person record by calling
  7257.   --|    the appropriate Prompt_Pkg function.  The generic FIND is used to 
  7258.   --|    get the record.  The user is then allowed to change the fields by
  7259.   --|    choosing a menu selection.  The record fields are modified directly.
  7260.   --|    When a person's initials are modified in a personnel record,
  7261.   --|    his initials also have to be changed in every element to which 
  7262.   --|    he belonged in the element list by calling the procedure 
  7263.   --|    MODIFY_PERSONNEL_KEY.
  7264.   --|
  7265.   --|
  7266.   --|  EXCEPTIONS HANDLED:
  7267.   --|    none 
  7268.   --|  
  7269.   --|  HISTORY:
  7270.   --|    written by   May Lee   March 1985
  7271.   --|
  7272.   -----------------------------------------------------------------------------
  7273.  
  7274.   use CALENDAR;
  7275.  
  7276.   abort_proc      : boolean;           -- abort getting existing pr
  7277.   exit_field_menu : boolean := false;  -- exit personnel field menu
  7278.   field_selection : integer;           -- selection from personnel field menu
  7279.   pr_record       : personnel_pointer; -- pointer to person data record
  7280.   key             : pr_init_type;      -- initials of person looking for
  7281.   found           : boolean := false;  -- if the record was found in the list
  7282.   
  7283.   procedure MODIFY_PERSONNEL_KEY is separate;
  7284.   procedure MODIFY_START_STOP_DATE ( PAIR : in integer ) is separate;
  7285.  
  7286.   begin
  7287.     new_line;
  7288.     put_line("Which person would you like to modify?");
  7289.     PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, key );
  7290.  
  7291.     -- set pointer to that person, returned in pr_record
  7292.     FIND( pr_list, key, pr_record, found);
  7293.  
  7294.     if not abort_proc then 
  7295.       while not exit_field_menu loop
  7296.         field_selection := VT100.PRINT_PR_MENU( pr_record );
  7297.         case field_selection is 
  7298.           when 1 =>  -- get person's name
  7299.             put(" The current person's name is "); put( pr_record.name );
  7300.             new_line;
  7301.             put_line(" What would you like to change it to? ");
  7302.             pr_record.name := PROMPT_PKG.PERSONS_NAME;
  7303.  
  7304.           when 2 =>  -- Getting new person's initials , change key
  7305.             put(" The current person's initials are "); 
  7306.         put( pr_record.initials );
  7307.             new_line;
  7308.             put_line(" What would you like to change it to? ");
  7309.             MODIFY_PERSONNEL_KEY;
  7310.  
  7311.           when 3 =>  -- Get new production rate 
  7312.             put(" The current production rate is "); 
  7313.             put( pr_record.production_rate, 4 ); new_line;
  7314.             put_line(" What would you like to change it to? ");
  7315.             pr_record.production_rate := PROMPT_PKG.PR_PRODUCTION_RATE;
  7316.  
  7317.           when 4 =>  -- Get new hours per week 
  7318.             put(" The hours per week is "); 
  7319.             put( pr_record.hours_per_week, 2 ); new_line;
  7320.             put_line(" What would you like to change it to? ");
  7321.             pr_record.hours_per_week := PROMPT_PKG.PR_HRS_PER_WEEK;
  7322.  
  7323.           when 5 =>  -- Get new first set of start/stop dates
  7324.         MODIFY_START_STOP_DATE(1);
  7325.  
  7326.           when 6 =>  -- Get new second set of start/stop dates
  7327.         MODIFY_START_STOP_DATE(2);
  7328.  
  7329.           when 7 =>  -- Get new third set of start/stop dates
  7330.         MODIFY_START_STOP_DATE(3);
  7331.  
  7332.           when 8 =>  exit_field_menu := true;
  7333.  
  7334.           when others => put_line("Please enter a number beween 1 and 8.");
  7335.         end case;
  7336.  
  7337.       end loop;    
  7338.     end if;
  7339.   end PR_MODIFY;
  7340.  
  7341.     separate( TRACKER.PERSONNEL_PKG.PR_MODIFY )
  7342.     procedure MODIFY_PERSONNEL_KEY is 
  7343.     ----------------------------------------------------------------------------
  7344.     --|
  7345.     --|  NAME:  MODIFY_PERSONNEL_KEY
  7346.     --|
  7347.     --|  OVERVIEW:
  7348.     --|    This procedure is called when the person's initials are modified.
  7349.     --|    The user is prompted for a new unique key by calling the Prompt_Pkg
  7350.     --|    function.  The person's initials must be changed in the person's
  7351.     --|    record, the search key for the personnel list, and the field of the
  7352.     --|    element record for each element in the person's element list.
  7353.     --|
  7354.     --|  EXCEPTIONS HANDLED:
  7355.     --|    none 
  7356.     --|  
  7357.     --|  HISTORY:
  7358.     --|    Written by   May Lee   March 1985 
  7359.     --|
  7360.     ----------------------------------------------------------------------------
  7361.       blank_key     : pr_init_type;        -- to blank out the key
  7362.       new_initials  : pr_init_type;        -- replacement pr
  7363.  
  7364.     begin            
  7365.       -- Change the key in the personnel list...
  7366.  
  7367.       -- get the new person's initials
  7368.       new_initials := PROMPT_PKG.NEW_PERSON_INITIALS;
  7369.  
  7370.       -- change person's initials in each element record of the pr_el_list
  7371.       CHANGE_PR_IN_EL( pr_record, new_initials );
  7372.  
  7373.       -- change the search key in the personnel list 
  7374.       CHANGE_LIST_KEY( pr_list, pr_record.initials, new_initials );
  7375.  
  7376.       -- change initials in the person's record
  7377.       pr_record.initials := new_initials;
  7378.  
  7379.     end MODIFY_PERSONNEL_KEY;
  7380.  
  7381.  
  7382.  
  7383.  
  7384.  
  7385. separate( TRACKER.PERSONNEL_PKG.PR_MODIFY )
  7386. procedure MODIFY_START_STOP_DATE ( PAIR : in integer ) is 
  7387. ----------------------------------------------------------------------------
  7388. --|
  7389. --|  NAME:  MODIFY_START_STOP_DATE 
  7390. --|
  7391. --|  OVERVIEW:
  7392. --|    This procedure is called when a pair of start/stop dates is to be
  7393. --|    modified for a person.  The user is prompted for a new set of dates
  7394. --|    by calling the Prompt_Pkg.date function.  The date is then compared
  7395. --|    to others start/stop dates to see if it is valid.  If not, the user
  7396. --|    is reprompted.  If any start/stop date is assigned a null value, the
  7397. --|    other future start/stop dates will be modified to also be a null date
  7398. --|    as needed.
  7399. --|
  7400. --|  EXCEPTIONS HANDLED:
  7401. --|    none 
  7402. --|  
  7403. --|  HISTORY:
  7404. --|    Written by   May Lee   March 1985 
  7405. --|    Written by   Bonnie Burkhardt   March 1985 
  7406. --|
  7407. ----------------------------------------------------------------------------
  7408.  
  7409.   valid_start_date : boolean := false;
  7410.  
  7411. begin
  7412.   START_DATES_LOOP:
  7413.   loop
  7414.     -- get new start date
  7415.     put(" The current start date for this set of dates is "); 
  7416.     if pr_record.start_dates(PAIR) = null_date then
  7417.       put("a null date. ");
  7418.     else
  7419.       put( pr_record.start_dates(PAIR).month,2 );
  7420.       put('/'); put( pr_record.start_dates(PAIR).day,2 ); put('/') ; 
  7421.       put( pr_record.start_dates(PAIR).year, 4 ); 
  7422.     end if;
  7423.     new_line;
  7424.  
  7425.     -- check if valid start date
  7426.     if  (PAIR > dates_list'first) and then
  7427.         (pr_record.stop_dates (pair - 1) = null_date) then
  7428.       put_line(" You cannot assign a non null date to the this start ");
  7429.       put_line(" date until you change the previous null stop date. ");
  7430.       valid_start_date := false;
  7431.       delay 1.0;
  7432.       exit START_DATES_LOOP;
  7433.     end if;
  7434.  
  7435.     new_line;
  7436.     put_line(" What would you like to change it to? ");
  7437.     pr_record.start_dates(pair) := PROMPT_PKG.DATE;
  7438.  
  7439.     if PAIR = dates_list'first then 
  7440.       valid_start_date := true;
  7441.       exit START_DATES_LOOP;
  7442.     elsif pr_record.start_dates(pair) = null_date then
  7443.       for j in pair..dates_list'last loop
  7444.         pr_record.start_dates(j) := null_date;
  7445.         pr_record.stop_dates(j)  := null_date;
  7446.       end loop;
  7447.       valid_start_date := false;
  7448.       exit START_DATES_LOOP;
  7449.     elsif pr_record.start_dates(pair) < pr_record.stop_dates (pair - 1) then
  7450.       valid_start_date := false;
  7451.       new_line;
  7452.       put_line(" That is not a valid start date.  The start date must be ");
  7453.       put_line(" a later date than the previous stop date.  TRY AGAIN!  ");
  7454.       put(" The previous stop date is "); 
  7455.       put( pr_record.stop_dates(pair - 1).month,2 );
  7456.       put('/'); put( pr_record.stop_dates(pair - 1).day,2 ); put('/') ; 
  7457.       put( pr_record.stop_dates(pair - 1).year, 4 ); 
  7458.       new_line;
  7459.     else
  7460.       valid_start_date := true;
  7461.       exit START_DATES_LOOP;
  7462.     end if;
  7463.   end loop START_DATES_LOOP;
  7464.  
  7465.   if valid_start_date then
  7466.     STOP_DATES_LOOP:
  7467.     loop
  7468.       -- Get new stop date  
  7469.       put(" The current stop date for the second set of dates is "); 
  7470.       if pr_record.stop_dates(pair) = null_date then
  7471.         put("a null date. ");
  7472.       else
  7473.         put( pr_record.stop_dates(pair).month,2 );
  7474.         put('/'); put( pr_record.stop_dates(pair).day,2 ); put('/') ; 
  7475.         put( pr_record.stop_dates(pair).year, 4 ); 
  7476.       end if;
  7477.       new_line;
  7478.  
  7479.       -- check if valid stop date
  7480.       if  (PAIR > dates_list'first) and then
  7481.           (pr_record.start_dates(pair) = null_date) then
  7482.         put_line(" You cannot assign a non null date to this stop ");
  7483.         put_line(" date until you change the previous null dates. ");
  7484.         delay 1.0;
  7485.         exit STOP_DATES_LOOP;
  7486.       end if;
  7487.  
  7488.       new_line;
  7489.       put_line(" What would you like to change it to? ");
  7490.       pr_record.stop_dates(pair) := PROMPT_PKG.DATE;
  7491.  
  7492.       if pr_record.stop_dates(pair) = null_date then
  7493.         for j in pair+1..dates_list'last loop
  7494.           pr_record.start_dates(j) := null_date;
  7495.           pr_record.stop_dates(j)  := null_date;
  7496.         end loop;
  7497.         exit STOP_DATES_LOOP;
  7498.       elsif pr_record.start_dates(pair) = null_date then 
  7499.         exit STOP_DATES_LOOP;
  7500.       elsif pr_record.stop_dates(pair) < pr_record.start_dates(pair) then
  7501.         put_line(" That is not a valid stop date.  The stop date must be ");
  7502.         put_line(" a later date than the start date.  TRY AGAIN!  ");
  7503.         put(" The start date is "); 
  7504.         put( pr_record.start_dates(pair).month,2 );
  7505.         put('/'); put( pr_record.start_dates(pair).day,2 ); put('/') ; 
  7506.         put( pr_record.start_dates(pair).year, 4 ); 
  7507.         new_line;
  7508.       elsif (pair < dates_list'last) and then 
  7509.             ((pr_record.start_dates(pair+1) /= null_date) and
  7510.              (pr_record.stop_dates(pair) > pr_record.start_dates(pair+1)) ) then
  7511.         put_line(" That is not a valid stop date.  The stop date must be ");
  7512.         put_line(" an earlier date than the next start date.  TRY AGAIN!  ");
  7513.         put(" The next start date is "); 
  7514.         put( pr_record.start_dates(pair+1).month,2 );
  7515.         put('/'); put( pr_record.start_dates(pair+1).day,2 ); put('/') ; 
  7516.         put( pr_record.start_dates(pair+1).year, 4 ); 
  7517.         new_line;
  7518.       else
  7519.         exit STOP_DATES_LOOP;
  7520.       end if;
  7521.     end loop STOP_DATES_LOOP;
  7522.   end if;
  7523. end MODIFY_START_STOP_DATE;
  7524.  
  7525.  
  7526.  
  7527.   separate( TRACKER.PERSONNEL_PKG )
  7528.   procedure PR_SAVE is
  7529.   ------------------------------------------------------------------------------
  7530.   --|
  7531.   --|  NAME:  PR_SAVE
  7532.   --|
  7533.   --|  OVERVIEW:
  7534.   --|    This procedure saves a record to file by calling the PR_WRITE 
  7535.   --|    procedure.  The generic procedures START_WALK and WALK are called
  7536.   --|    to walk the linked list allowing one record at a time to be written.
  7537.   --|
  7538.   --|  EXCEPTIONS HANDLED:
  7539.   --|    none 
  7540.   --|  
  7541.   --|  HISTORY:
  7542.   --|    Written by   May Lee   March 1985 
  7543.   --|
  7544.   ------------------------------------------------------------------------------
  7545.   end_list       : boolean := false;
  7546.   pr_record      : personnel_pointer;
  7547.  
  7548.   procedure PR_WRITE is separate;
  7549.  
  7550.   begin
  7551.     START_WALK( pr_list);
  7552.     -- walk the list one person at a time and write it to the file
  7553.     loop
  7554.       WALK( pr_list, pr_record, end_list);
  7555.       exit when end_list;
  7556.       PR_WRITE;
  7557.     end loop;
  7558.   end PR_SAVE;
  7559.  
  7560.  
  7561.     separate( TRACKER.PERSONNEL_PKG.PR_SAVE )
  7562.     procedure PR_WRITE is
  7563.     --|
  7564.     --|  NAME:  PR_WRITE
  7565.     --|
  7566.     --|  OVERVIEW:
  7567.     --|    This procedure references the current record pointer.  The record
  7568.     --|    is written to one line of the output file in the following format:
  7569.     --||
  7570.     --||   +--------------------+--+-----+--+-----+----+-----+----+-----+----+
  7571.     --||   |      name          |in| rate|hr|start|stop|start|stop|start|stop|
  7572.     --||   +--------------------+--+-----+--+-----+----+-----+----+-----+----+
  7573.     --||
  7574.     --|    See DATA_PKG for the full names of the fields and their types.
  7575.     --|    The personnel records are the fourth type of data to be written to 
  7576.     --|    the output file.
  7577.     --|
  7578.     --|  EXCEPTIONS HANDLED:
  7579.     --|    none
  7580.     --|
  7581.     --|  HISTORY:
  7582.     --|    Written by   May Lee   March 1985
  7583.     --|
  7584.     begin
  7585.       put( output_file, pr_record.name );    -- string
  7586.       put( output_file, pr_record.initials ); 
  7587.       put( output_file, pr_record.production_rate, 3, 3, 0 );    -- real
  7588.       put( output_file, pr_record.hours_per_week,  width => 2 ); -- integer
  7589.       for i in dates_list'first..dates_list'last loop  
  7590.         -- write the sets of start/stop dates
  7591.         put( output_file, pr_record.start_dates(i).month,width => 2 );
  7592.         put( output_file, pr_record.start_dates(i).day,  width => 2 );
  7593.         put( output_file, pr_record.start_dates(i).year, width => 4 );
  7594.         put( output_file, pr_record.stop_dates(i).month, width => 2 );
  7595.         put( output_file, pr_record.stop_dates(i).day,   width => 2 );
  7596.         put( output_file, pr_record.stop_dates(i).year,  width => 4 );
  7597.       end loop;
  7598.       new_line( output_file );
  7599.     end PR_WRITE;
  7600. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  7601. --ss.ada
  7602. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  7603. with PROMPT_PKG;   
  7604.  
  7605. separate(tracker)
  7606. package body SUBSYSTEM_PKG is
  7607. --------------------------------------------------------------------------------
  7608. --|
  7609. --|  NAME:  SUBSYSTEM_PKG
  7610. --|
  7611. --|  OVERVIEW:
  7612. --|    This package defines the actions that can be performed on a
  7613. --|    subsystem (defined in DATA_PKG).
  7614. --|
  7615. --|  EXCEPTIONS HANDLED:
  7616. --|    none
  7617. --|
  7618. --|  HISTORY:
  7619. --|    Written by   May Lee   March 1985
  7620. --|
  7621. --------------------------------------------------------------------------------
  7622.  
  7623.   use EL_LIST_PKG;
  7624.   use SS_LIST_PKG;
  7625.  
  7626.   procedure CHANGE_SS_IN_EL( ss_record : in subsystem_pointer;
  7627.                              new_name  : in ss_name_type ) is separate;
  7628.   procedure SS_ADD        is separate;
  7629.   procedure SS_INITIALIZE is separate;
  7630.   procedure SS_SET_UP     is separate;
  7631.   procedure SS_DELETE     is separate;
  7632.   procedure SS_MODIFY     is separate;
  7633.   procedure SS_SAVE       is separate;
  7634.  
  7635. end SUBSYSTEM_PKG;
  7636.  
  7637. --*****************************************************************************
  7638.  
  7639.   separate(TRACKER.SUBSYSTEM_PKG)
  7640.   procedure SS_ADD is
  7641.   ------------------------------------------------------------------------------
  7642.   --|
  7643.   --|  NAME:  SS_ADD
  7644.   --|
  7645.   --|  OVERVIEW:
  7646.   --|    This procedure sets up the record to be added to the list by
  7647.   --|    user prompt/response.  The function calls to Prompt_Pkg return
  7648.   --|    only valid existing data.  The complete record is 
  7649.   --|    then added to the linked list by calling the generic list procedure
  7650.   --|    ADD.
  7651.   --|
  7652.   --|  EXCEPTIONS HANDLED:
  7653.   --|    none
  7654.   --|  
  7655.   --|  HISTORY:
  7656.   --|    written by   May Lee   March 1985
  7657.   --|
  7658.   --|  NOTES:
  7659.   --|    The number of subsystems is incremented in this procedure.
  7660.   --|
  7661.   ------------------------------------------------------------------------------
  7662.   ss_record : subsystem_pointer;
  7663.  
  7664.   begin
  7665.     -- create a null subsystem record
  7666.     ss_record := new subsystem_type;
  7667.  
  7668.     new_line;
  7669.     put_line(" If you would like more information on the type of data ");
  7670.     put_line(" to enter for any of the following questions, enter a '?' ");
  7671.     put_line(" Otherwise, enter the data requested.      ");
  7672.     new_line(2);
  7673.  
  7674.     -- get the record fields
  7675.     ss_record.name             := PROMPT_PKG.NEW_SUBSYS_NAME;
  7676.     new_line;
  7677.  
  7678.     put_line(" What percentage of the total subsystem is available at start? ");
  7679.     ss_record.percent_at_start := PROMPT_PKG.PERCENT;
  7680.    
  7681.     ss_record.task_numbers := PROMPT_PKG.TASK_NUMBERS( ss_record );
  7682.  
  7683.     -- add the record to the linked list
  7684.     ADD ( ss_list, ss_record.name, ss_record);  
  7685.  
  7686.     -- increment subsystem counter
  7687.     num_of_subsystems := num_of_subsystems + 1;
  7688.  
  7689.     new_line;
  7690.     put(" The number of subsystems = "); put( num_of_subsystems,1); 
  7691.     new_line(2);
  7692.     delay 1.0;
  7693.   end SS_ADD;
  7694.  
  7695.  
  7696.   separate(TRACKER.SUBSYSTEM_PKG)
  7697.   procedure SS_INITIALIZE is
  7698.   ------------------------------------------------------------------------------
  7699.   --|
  7700.   --|  NAME:  SS_INITIALIZE
  7701.   --|
  7702.   --|  OVERVIEW:
  7703.   --|    This procedure is called only when a new TRACKER file has to
  7704.   --|    be created.  It is part of a forced user response to fill in
  7705.   --|    the necessary data to make TRACKER a complete report.  The
  7706.   --|    procedure SS_ADD is called to gather the information and put it
  7707.   --|    into a linked list.
  7708.   --|
  7709.   --|  EXCEPTIONS HANDLED:
  7710.   --|    none
  7711.   --|  
  7712.   --|  HISTORY:
  7713.   --|    written by   May Lee   March 1985
  7714.   --|
  7715.   --|  NOTES:
  7716.   --|    The user is forced to add at least one subsystem record and then
  7717.   --|    is prompted to add another or not.
  7718.   --|
  7719.   ------------------------------------------------------------------------------
  7720.   add_another :  character := 'N';
  7721.   done        :  boolean   := false;
  7722.  
  7723.   begin
  7724.     while not done loop
  7725.       -- force the user to add at least one subsystem
  7726.       SS_ADD; -- data to the record and the record to the list
  7727.       loop
  7728.         put_line("Would you like to add another subsystem? ");
  7729.         put("  [ Y or N, <cr>=N ]  :  ");
  7730.         if end_of_line then -- pressed return, default to no
  7731.           skip_line;
  7732.           new_line(2);
  7733.           done := true;    
  7734.           exit;
  7735.         else      
  7736.           get(add_another); skip_line;
  7737.           new_line(2);
  7738.           if add_another = 'N' or add_another = 'n' then
  7739.             done := true;    
  7740.             exit;
  7741.           elsif add_another = 'Y' or add_another = 'y' then
  7742.             exit;
  7743.           else
  7744.             put_line(" Please enter y or n. ");          
  7745.           end if;
  7746.         end if;
  7747.       end loop;
  7748.     end loop;
  7749.   end SS_INITIALIZE;
  7750.  
  7751.  
  7752.   separate(TRACKER.SUBSYSTEM_PKG)
  7753.   procedure SS_SET_UP is
  7754.   ------------------------------------------------------------------------------
  7755.   --|
  7756.   --|  NAME:  SS_SET_UP
  7757.   --|
  7758.   --|  OVERVIEW:
  7759.   --|    This procedure is only called if there is an existing input file.
  7760.   --|    The subsystem list is set up by reading the subsystem record
  7761.   --|    from the input file by calling SS_READ, and adding it to the linked 
  7762.   --|    list by calling the generic procedure ADD until there are no more 
  7763.   --|    subsystem records.
  7764.   --|
  7765.   --|  EXCEPTIONS HANDLED:
  7766.   --|    others        Error reading the record from the file.
  7767.   --|    .        This exception raises ERROR_IN_INPUT_FILE.
  7768.   --|  
  7769.   --|  HISTORY:
  7770.   --|    written by   May Lee   March 1985
  7771.   --|
  7772.   --|  NOTES:
  7773.   --|    The number of subsystem records read in is determined by the
  7774.   --|    global variable num_of_subsystems.
  7775.   --|
  7776.   --|    If an error is detected reading the data, the rest of the input line
  7777.   --|    is skipped and reading of the rest of the data continues.  All errors
  7778.   --|    found are reported.  Execution is not terminated until the entire
  7779.   --|    input file has been read.
  7780.   --|
  7781.   ------------------------------------------------------------------------------
  7782.     ss_record  : subsystem_pointer;
  7783.     ss_num     : integer := 1;  
  7784.     bad_data   : boolean := false;
  7785.  
  7786.     procedure SS_READ is separate;
  7787.  
  7788.   begin
  7789.     -- create a new subsystem, read it in, and add it to the list
  7790.     for i in 1.. num_of_subsystems loop
  7791.       begin
  7792.         -- counter for exception
  7793.         ss_num := i;
  7794.         -- create null record
  7795.         ss_record := new subsystem_type;
  7796.         -- get a record of data
  7797.         SS_READ;
  7798.         -- add to list
  7799.         ADD ( ss_list, ss_record.name, ss_record);
  7800.       exception
  7801.         when others =>
  7802.           skip_line( tracker_file );
  7803.           put(" Error reading subsystem"); put(ss_num,1); 
  7804.           put(" from the tracker file. "); new_line;
  7805.       bad_data := true;
  7806.       end;
  7807.     end loop;
  7808.     if bad_data then
  7809.       raise ERROR_IN_INPUT_FILE;
  7810.     end if;
  7811.   end SS_SET_UP;
  7812.  
  7813.  
  7814.     separate(TRACKER.SUBSYSTEM_PKG.SS_SET_UP)
  7815.     procedure SS_READ is
  7816.     ---------------------------------------------------------------------------
  7817.     --|
  7818.     --|  NAME:  SS_READ
  7819.     --|
  7820.     --|  OVERVIEW:
  7821.     --|    This procedure reads a record from the file.  One line of data is
  7822.     --|    read at a time and broken down into the fields of the
  7823.     --|    subsystem record, which is made visible to the calling routine
  7824.     --|    SS_SET_UP.  The data is read in the format specified by the SS_WRITE
  7825.     --|    procedure.
  7826.     --|
  7827.     --|
  7828.     --|  EXCEPTIONS HANDLED:
  7829.     --|    none
  7830.     --|
  7831.     --|  HISTORY:
  7832.     --|    written by   May Lee   March 1985
  7833.     --|
  7834.     --|  NOTES:
  7835.     --|    Any exceptions raised here are handled by SS_SET_UP.
  7836.     --|
  7837.     ---------------------------------------------------------------------------
  7838.     begin
  7839.       get( tracker_file, ss_record.name(1..10) );                -- string
  7840.       get( tracker_file, ss_record.percent_at_start, 5 );  -- real
  7841.       for ac_index in 1..num_of_activities loop
  7842.         get( tracker_file, ss_record.task_numbers(ac_index), 4 );
  7843.       end loop;
  7844.       skip_line( tracker_file );
  7845.     end SS_READ;
  7846.  
  7847.  
  7848.   separate(TRACKER.SUBSYSTEM_PKG)
  7849.   procedure SS_DELETE is
  7850.   ------------------------------------------------------------------------------
  7851.   --|
  7852.   --|  NAME:  SS_DELETE
  7853.   --|
  7854.   --|  OVERVIEW:
  7855.   --|  OVERVIEW:
  7856.   --|    This procedure is used to delete a subsystem from the list by calling
  7857.   --|    the List_Pkg procedure DELETE.  When a subsystem is deleted from the
  7858.   --|    subsystem list, the subsystem number must also be changed in every
  7859.   --|    element to which it belonged by calling the procedure
  7860.   --|    CHANGE_SS_IN_EL.
  7861.   --|
  7862.   --|  EXCEPTIONS HANDLED:
  7863.   --|    none
  7864.   --|  
  7865.   --|  HISTORY:
  7866.   --|    written by   May Lee   March 1985
  7867.   --|
  7868.   --|  NOTES:
  7869.   --|    The number of subsystems is decremented after the record is deleted.
  7870.   --|
  7871.   --|    A check is made to insure that the last subsystem is not deleted.  
  7872.   --|    There must be at least one subsystem at all times.
  7873.   --|
  7874.   --|
  7875.   ------------------------------------------------------------------------------
  7876.  
  7877.   abort_proc  : boolean;           -- abort getting an existing ss
  7878.   deleted_ss  : boolean;
  7879.   end_list    : boolean;
  7880.   ele_ptr     : element_pointer;
  7881.   new_name    : ss_name_type := (others => ' ');
  7882.   ss_record   : subsystem_pointer;
  7883.   new_ss_record : subsystem_pointer;
  7884.   successful  : boolean := false;   -- if record was found in the list
  7885.   key         : ss_name_type;       -- name of subsystem looking for
  7886.  
  7887.   begin
  7888.     if num_of_subsystems > 1 then  -- have to have at least one subsystem
  7889.       put_line("Which subsystem would you like to delete? ");
  7890.  
  7891.       -- get the subsystem name
  7892.       PROMPT_PKG.EXISTING_SUBSYS_NAME( abort_proc, key );
  7893.  
  7894.       if not abort_proc then
  7895.         --point to that record in the list
  7896.         FIND( ss_list, key, ss_record, successful);
  7897.  
  7898.         -- delete the subsystem from the list
  7899.         DELETE( ss_list, key, successful);
  7900.  
  7901.     start_walk (ss_record.element_list);
  7902.     walk (ss_record.element_list, ele_ptr, end_list);
  7903.     if not end_list then
  7904.           -- change subsystem name in element data
  7905.           put(" When subsystem "); put(ss_record.name); put(" is deleted, "); new_line;
  7906.           put_line(" what subsystem would you like to use in its place in the element data? ");
  7907.           -- prompt for subsystem name
  7908.       loop
  7909.             PROMPT_PKG.EXISTING_SUBSYS_NAME( abort_proc, new_name );
  7910.           exit when not abort_proc;
  7911.             put_line(" You cannot abort the procedure at this time. ");
  7912.         put_line(" You must enter a valid subsystem name!");
  7913.         new_line;
  7914.       end loop;
  7915.       find (ss_list, new_name, new_ss_record, successful);
  7916.  
  7917.           -- change the subsystem name in the element data
  7918.           CHANGE_SS_IN_EL( ss_record, new_name );
  7919.  
  7920.           -- append this subsystem's elements to the new subsystem's element list
  7921.       start_walk (SS_RECORD.element_list);
  7922.       loop
  7923.         walk(SS_RECORD.element_list, ELE_PTR, END_LIST);
  7924.         exit when END_LIST;
  7925.             ADD ( new_ss_record.element_list, ELE_PTR.desc_key, ELE_PTR);
  7926.       end loop;
  7927.     end if;
  7928.  
  7929.         -- decrement the subsystem counter
  7930.         num_of_subsystems := num_of_subsystems - 1;
  7931.  
  7932.         new_line;
  7933.         put(" The number of subsystems = "); put(num_of_subsystems,1); 
  7934.     new_line(2);
  7935.     delay 1.0;
  7936.       end if; -- not abort
  7937.  
  7938.     else
  7939.       put_line(" You must have at least one subsystem at all times. ");
  7940.       put_line(" Since you only have one subsystem at this time, you ");
  7941.       put_line(" cannot delete it. ");        
  7942.       delay 1.5;
  7943.     end if;
  7944.   end SS_DELETE;
  7945.  
  7946.  
  7947.   separate(TRACKER.SUBSYSTEM_PKG)
  7948.   procedure CHANGE_SS_IN_EL( ss_record : in subsystem_pointer;
  7949.                               new_name : in ss_name_type ) is
  7950.   -----------------------------------------------------------------------------
  7951.   --|
  7952.   --|  NAME: CHANGE_SS_IN_EL
  7953.   --|
  7954.   --|  OVERVIEW:
  7955.   --|    This procedure is called when a subsystem is deleted from or modified
  7956.   --|    in the subsystem list.  Before either of these actions can be taken,
  7957.   --|    the element list that contains subsystems with the same name is walked.
  7958.   --|    This list is a field of the subsystem data record.
  7959.   --|    The subsystem name field of each element record is reassigned
  7960.   --|    the new subsystem.
  7961.   --| 
  7962.   --|  EXCEPTIONS HANDLED:
  7963.   --|    none 
  7964.   --|
  7965.   --|  HISTORY:
  7966.   --|    Written by   May Lee   March 1985 
  7967.   --|
  7968.   -----------------------------------------------------------------------------
  7969.  
  7970.   el_record       : element_pointer;   -- ms element list
  7971.   end_list        : boolean;
  7972.  
  7973.   begin
  7974.     -- change the ss name field in el_record of the subsystem's el list
  7975.     START_WALK( ss_record.element_list );
  7976.     loop
  7977.       WALK( ss_record.element_list, el_record, end_list );
  7978.       exit when end_list;
  7979.       el_record.subsystem_name := new_name;
  7980.     end loop;
  7981.   end CHANGE_SS_IN_EL;
  7982.  
  7983.  
  7984.   separate(TRACKER.SUBSYSTEM_PKG)
  7985.   procedure SS_MODIFY is
  7986.   ------------------------------------------------------------------------------
  7987.   --|
  7988.   --|  NAME:  SS_MODIFY
  7989.   --|
  7990.   --|  OVERVIEW:
  7991.   --|    This procedure allows the user to modify an existing record.
  7992.   --|    The user is prompted for an existing subsystem record by calling
  7993.   --|    the appropriate Prompt_Pkg function.  The generic FIND is used to 
  7994.   --|    get the record.  The user is then allowed to change the fields by
  7995.   --|    choosing a menu selection.  The record fields are modified directly.
  7996.   --|    When a subsystem name is modified in the subsystem record, the 
  7997.   --|    subsystem name must also be changed in every element to 
  7998.   --|    which it belonged by calling the procedure CHANGE_SS_IN_EL.
  7999.   --|
  8000.   --|  EXCEPTIONS HANDLED:
  8001.   --|    none 
  8002.   --|  
  8003.   --|  HISTORY:
  8004.   --|    Written by   May Lee   March 1985 
  8005.   --|
  8006.   ------------------------------------------------------------------------------
  8007.   abort_proc      : boolean;           -- abort getting existing ss
  8008.   exit_field_menu : boolean := false;  -- exit subsystem field menu
  8009.   field_selection : integer;           -- selection from subsystem field menu
  8010.   key          : ss_name_type;      -- name of subsystem looking for
  8011.   new_name        : ss_name_type;      -- new subsystem name 
  8012.   ss_record       : subsystem_pointer; -- pointer to subsystem record
  8013.   length          : natural;           -- length of subsystem name
  8014.   found           : boolean := false;  -- if the record was found in the list
  8015.  
  8016.   begin
  8017.     new_line;
  8018.     put_line("Which subsystem would you like to modify?");
  8019.     PROMPT_PKG.EXISTING_SUBSYS_NAME( abort_proc, key );
  8020.  
  8021.     -- set pointer to that milstone, returned in ms_record
  8022.     FIND( ss_list, key, ss_record, found );
  8023.  
  8024.     if not abort_proc then 
  8025.       while not exit_field_menu loop
  8026.         field_selection := VT100.PRINT_SS_MENU( ss_record );
  8027.         case field_selection is 
  8028.           when 1 =>  -- get subsystem name .. change the key
  8029.             put_line(" The current subsystem name is "); put( ss_record.name);
  8030.             new_line;
  8031.             put_line(" What would you like to change it to? ");
  8032.             new_name := PROMPT_PKG.NEW_SUBSYS_NAME;
  8033.  
  8034.         -- change the key in the element data, subsystem list, and data
  8035.             CHANGE_SS_IN_EL( ss_record, new_name );
  8036.             CHANGE_LIST_KEY( ss_list, ss_record.name, new_name );
  8037.             ss_record.name := new_name;
  8038.  
  8039.           when 2 =>  -- get new task numbers
  8040.             ss_record.task_numbers  := PROMPT_PKG.TASK_NUMBERS( ss_record );
  8041.  
  8042.           when 3 =>  put_line(" The current percent complete at start is: ");
  8043.             put( ss_record.percent_at_start,3,2,0 ); put('%');
  8044.             ss_record.percent_at_start := PROMPT_PKG.PERCENT;
  8045.           when 4 =>  exit_field_menu := true;
  8046.           when others => put_line("Please enter a number beween 1 and 4.");
  8047.         end case;
  8048.       end loop;    
  8049.     end if;
  8050.   end SS_MODIFY;
  8051.  
  8052.  
  8053.   separate(TRACKER.SUBSYSTEM_PKG)
  8054.   procedure SS_SAVE is
  8055.   ------------------------------------------------------------------------------
  8056.   --|
  8057.   --|  NAME:  SS_SAVE
  8058.   --|
  8059.   --|  OVERVIEW:
  8060.   --|    This procedure saves a record to file by calling the SS_WRITE 
  8061.   --|    procedure.  The generic procedures START_WALK and WALK are called
  8062.   --|    to walk the linked list allowing one record at a time to be written.
  8063.   --|
  8064.   --|  EXCEPTIONS HANDLED:
  8065.   --|    none 
  8066.   --|  
  8067.   --|  HISTORY:
  8068.   --|    Written by   May Lee   March 1985 
  8069.   --|
  8070.   ------------------------------------------------------------------------------
  8071.   end_of_list  : boolean := false;
  8072.   ss_record    : subsystem_pointer;
  8073.  
  8074.     procedure SS_WRITE is separate;
  8075.  
  8076.   begin
  8077.     START_WALK( ss_list);
  8078.     -- walk the list one subsystem at a time and write it to the file
  8079.     loop
  8080.       WALK( ss_list, ss_record, end_of_list);
  8081.       exit when end_of_list;
  8082.       SS_WRITE;
  8083.     end loop;
  8084.   end SS_SAVE;
  8085.  
  8086.  
  8087.     separate(TRACKER.SUBSYSTEM_PKG.SS_SAVE)
  8088.     procedure SS_WRITE is
  8089.     ---------------------------------------------------------------------------
  8090.     --|
  8091.     --|  NAME:  SS_WRITE
  8092.     --|
  8093.     --|  OVERVIEW:
  8094.     --|    This procedure is passed in a record pointer.  The record is written
  8095.     --|    to one line of the output file in the following format:
  8096.     --||
  8097.     --||             +----------+-----+------+
  8098.     --||             |   name   | prct|task #| ...
  8099.     --||             +----------+-----+------+
  8100.     --||                                ^
  8101.     --||                                |__ varies from 1..num_of_activities 
  8102.     --||
  8103.     --|    See DATA_PKG for the full names of the fields and their types.
  8104.     --|    The subsystem records are the fifth type of data to be written to the
  8105.     --|    output file.
  8106.     --|
  8107.     --|  EXCEPTIONS HANDLED:
  8108.     --|    none
  8109.     --|
  8110.     --|  HISTORY:
  8111.     --|    Written by   May Lee   March 1985
  8112.     --|
  8113.     ---------------------------------------------------------------------------
  8114.     begin
  8115.       put( output_file, ss_record.name(1..10) );                -- string
  8116.       put( output_file, ss_record.percent_at_start, 3, 1, 0 );  -- real
  8117.       for ac_index in 1..num_of_activities loop
  8118.         put( output_file, ss_record.task_numbers(ac_index), 4 );
  8119.       end loop;
  8120.       new_line( output_file );
  8121.     end SS_WRITE;
  8122. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  8123. --el.ada
  8124. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  8125. with PROMPT_PKG; 
  8126.  
  8127. separate(TRACKER)
  8128. package body ELEMENT_PKG is
  8129. -----------------------------------------------------------------------------
  8130. --|  NAME:  ELEMENT_PKG
  8131. --|
  8132. --|  OVERVIEW:
  8133. --|    This package defines the actions that can be performed on
  8134. --|    element data types (defined in data_pkg).
  8135. --|
  8136. --|  EXCEPTIONS HANDLED:
  8137. --|    none
  8138. --|
  8139. --|  HISTORY:
  8140. --|    written by   May Lee   March 1985
  8141. --|
  8142. -----------------------------------------------------------------------------
  8143.  
  8144.   -- instantiation of generic list handler is done in data_pkg
  8145.   use AC_LIST_PKG;                 -- to get the activity completeness
  8146.   use EL_LIST_PKG;
  8147.   use MS_LIST_PKG;
  8148.   use PR_LIST_PKG;
  8149.   use SS_LIST_PKG;
  8150.  
  8151.   -- to convert the enumeration type activity_phase_percent to character
  8152.   -- for read and write into the file only
  8153.   type ac_phase_char_type is array(1..10) of character;
  8154.   char_ac_completeness  : ac_phase_char_type := (others => ' ');
  8155.  
  8156.   procedure MULTIPLE_PR_EL_RECORD( el_record : in out element_pointer) 
  8157.                    is separate;
  8158.   procedure SINGLE_PR_EL_RECORD( el_record : in out element_pointer)   
  8159.                    is separate;
  8160.   procedure ADD_RECORD_TO_LISTS( el_record : in element_pointer)   is separate;
  8161.   procedure EL_ADD                 is separate;
  8162.   procedure EL_INITIALIZE          is separate;
  8163.   procedure UPDATE_CURRENT         is separate;
  8164.   procedure UPDATE_PCT_DONE        is separate;
  8165.   procedure EL_SET_UP              is separate;
  8166.   procedure EL_DELETE              is separate;
  8167.   procedure EL_MODIFY              is separate;
  8168.   procedure EL_SAVE                is separate;
  8169.  
  8170. end ELEMENT_PKG;
  8171.  
  8172. --****************************************************************************
  8173. separate(TRACKER.ELEMENT_PKG)
  8174. procedure MULTIPLE_PR_EL_RECORD( el_record : in out element_pointer)  is 
  8175.   use CALENDAR;
  8176.   a_record : element_pointer;
  8177. begin
  8178.   a_record := new element_type( true );
  8179.   a_record.all := 
  8180.        (two_or_more_people    => true,
  8181.         description        => el_record.description,
  8182.         desc_key        => el_record.desc_key,
  8183.     subsystem_name        => el_record.subsystem_name,
  8184.         milestone_num        => el_record.milestone_num,
  8185.     priority        => el_record.priority,
  8186.         original_size        => el_record.original_size,
  8187.         size_done_at_start    => el_record.size_done_at_start,
  8188.     current_size            => el_record.current_size,
  8189.         complexity              => el_record.complexity,
  8190.         activity_completeness   => el_record.activity_completeness,
  8191.         hours_to_complete       => el_record.hours_to_complete,
  8192.         date_done               => el_record.date_done,
  8193.         prev_date_done          => el_record.prev_date_done,
  8194.         date_size_verified      => el_record.date_size_verified,
  8195.         more_than_one_person    => true,
  8196.         dates_done        => (others => null_date),
  8197.         hours_left        => (others => 0.0),
  8198.         people_initials        => (others => "  ") );
  8199.   el_record := a_record;
  8200. end MULTIPLE_PR_EL_RECORD;
  8201.  
  8202. separate(TRACKER.ELEMENT_PKG)
  8203. procedure SINGLE_PR_EL_RECORD( el_record : in out element_pointer)  is 
  8204.   a_record : element_pointer;
  8205. begin
  8206.   a_record := new element_type(false);
  8207.   a_record.all := 
  8208.        (two_or_more_people    => false,
  8209.         description        => el_record.description,
  8210.         desc_key        => el_record.desc_key,
  8211.     subsystem_name        => el_record.subsystem_name,
  8212.         milestone_num        => el_record.milestone_num,
  8213.     priority        => el_record.priority,
  8214.         original_size        => el_record.original_size,
  8215.         size_done_at_start    => el_record.size_done_at_start,
  8216.     current_size            => el_record.current_size,
  8217.         complexity              => el_record.complexity,
  8218.         activity_completeness   => el_record.activity_completeness,
  8219.         hours_to_complete       => el_record.hours_to_complete,
  8220.         date_done               => el_record.date_done,
  8221.         prev_date_done          => el_record.prev_date_done,
  8222.         date_size_verified      => el_record.date_size_verified,
  8223.         more_than_one_person    => false,
  8224.     person_initials        => "  ");
  8225.   el_record := a_record;
  8226. end SINGLE_PR_EL_RECORD;
  8227.  
  8228.  
  8229. separate(TRACKER.ELEMENT_PKG)
  8230. procedure ADD_RECORD_TO_LISTS( el_record : in element_pointer ) is 
  8231. -----------------------------------------------------------------------------
  8232. --|  NAME:  ADD_RECORD_TO_LISTS
  8233. --|
  8234. --|  OVERVIEW:
  8235. --|    This procedure is called by EL_SET_UP and EL_ADD.  It
  8236. --|    adds the element record to every data's element list
  8237. --|    by calling the List_Pkg procedures FINDto find the record and
  8238. --|    return the pointer and ADD to append the record to the list.
  8239. --|
  8240. --|  EXCEPTIONS HANDLED:
  8241. --|    none
  8242. --|
  8243. --|  HISTORY:
  8244. --|    written by   May Lee   March 1985
  8245. --|
  8246. --|  NOTES:
  8247. --|    The pointer to the current element record is passed as a parameter.
  8248. -----------------------------------------------------------------------------
  8249.   found       : boolean ;          -- parameter to find
  8250.   el_record2  : element_pointer;
  8251.   ms_record   : milestone_pointer; -- to add the element to the ms_el_list
  8252.   pr_record   : personnel_pointer; -- to add the element to the pr_el_list
  8253.   ss_record   : subsystem_pointer; -- to add the element to the ss_el_list
  8254.  
  8255. begin
  8256.   -- add element to element list
  8257.   ADD( el_list, el_record.desc_key, el_record);
  8258.  
  8259.   -- Every element has every activity, so activity doesn't
  8260.   -- have an element list.  Every other data has to have the
  8261.   -- element added to its own element list.
  8262.  
  8263.   -- find the correct milestone
  8264.   FIND( ms_list, el_record.milestone_num, ms_record, found );
  8265.   -- add element to milestone element list
  8266.   ADD( ms_record.element_list , el_record.desc_key, el_record);
  8267.  
  8268.   -- find the correct person
  8269.   if el_record.more_than_one_person then
  8270.     -- add the element to the person's list, if not already added
  8271.     for ac_index in 1..num_of_activities loop
  8272.       find (pr_list, el_record.people_initials(ac_index), pr_record, found);
  8273.       find (pr_record.element_list, el_record.desc_key, el_record2, 
  8274.             found);
  8275.       if not found then
  8276.         add (pr_record.element_list, el_record.desc_key, el_record);
  8277.       end if;
  8278.     end loop;
  8279.   else
  8280.     FIND( pr_list, el_record.person_initials, pr_record, found );
  8281.     ADD( pr_record.element_list , el_record.desc_key, el_record);
  8282.   end if;
  8283.  
  8284.   -- find the correct subsystem
  8285.   FIND( ss_list, el_record.subsystem_name, ss_record, found );
  8286.   -- add element to subsystem element list
  8287.   ADD( ss_record.element_list , el_record.desc_key, el_record);
  8288. end ADD_RECORD_TO_LISTS;
  8289.  
  8290.  
  8291. separate(TRACKER.ELEMENT_PKG)
  8292.   procedure EL_ADD is
  8293.   -----------------------------------------------------------------------------
  8294.   --|
  8295.   --|  NAME:  EL_ADD
  8296.   --|
  8297.   --|  OVERVIEW:
  8298.   --|    This procedure sets up the record to be added to the list by
  8299.   --|    user prompt/response.  The function calls to Prompt_Pkg return
  8300.   --|    only valid existing data.  The complete record is 
  8301.   --|    then added to the linked list by calling the procedure
  8302.   --|    ADD_RECORD_TO_LISTS.
  8303.   --|
  8304.   --|  EXCEPTIONS HANDLED:
  8305.   --|    none
  8306.   --|  
  8307.   --|  HISTORY:
  8308.   --|    written by   May Lee   March 1985
  8309.   --|
  8310.   --|  NOTES:
  8311.   --|    The number of elements is incremented if the element has been
  8312.   --|    successfully added to all the necessary data lists.
  8313.   -----------------------------------------------------------------------------
  8314.   abort_proc  : boolean := false;  -- parameter to key prompts
  8315.   a_char      : character := ' ';  -- used for getting char input
  8316.   count       : integer := 1;      -- used as a temp loop counter
  8317.   ac_index    : integer := 1;      -- number of the ac being referenced
  8318.   ac_record   : activity_pointer;  -- pointer to ac data record
  8319.   end_list    : boolean := false;  -- indicates the end of list was detected
  8320.   el_record   : element_pointer;   -- pointer to el data record
  8321.   found       : boolean := false;  -- whether or not a person was found on a list
  8322.   ms_key      : ms_num_type;       -- used to get key 
  8323.   pr_record   : personnel_pointer; -- pointer pr ac data record
  8324.   pr_key      : pr_init_type;      -- used to get key 
  8325.   ss_key      : ss_name_type;      -- used to get key 
  8326.  
  8327.   begin
  8328.     -- create a null record
  8329.     el_record := new element_type;    
  8330.  
  8331.     new_line;
  8332.     put_line(" If you would like more information on the type of data ");
  8333.     put_line(" to enter for any of the following questions, enter a '?'.  ");
  8334.     put_line(" Otherwise, enter the data requested.      ");
  8335.     new_line(2);
  8336.  
  8337.     el_record.description := PROMPT_PKG.ELE_DESCRIPTION;
  8338.     el_record.desc_key    := PROMPT_PKG.NEW_ELE_KEY;
  8339.  
  8340.     loop  -- get ss name
  8341.       PROMPT_PKG.EXISTING_SUBSYS_NAME( abort_proc, ss_key ); 
  8342.       if abort_proc then
  8343.         put_line(" You MUST enter an existing subsystem. ");
  8344.         put_line(" You cannot abort the procedure at this time. ");
  8345.       else
  8346.         el_record.subsystem_name := ss_key;
  8347.         exit;
  8348.       end if;
  8349.     end loop;
  8350.  
  8351.     -- multiple people?  determines which element record to use
  8352.     loop  -- until y or n
  8353.       put_line(" Will more than one person be working on this element? ");
  8354.       put(" [y or n, <cr>=n)] : ");
  8355.       if end_of_line then
  8356.         skip_line;
  8357.         exit;
  8358.       else
  8359.         get( a_char ); skip_line;
  8360.         if a_char = 'Y' or a_char = 'y' then
  8361.           -- define the element record
  8362.          MULTIPLE_PR_EL_RECORD( el_record );
  8363.           exit;
  8364.         elsif a_char = '?' then
  8365.           put_line(" Please enter 'y' or 'n'. ");
  8366.           new_line;
  8367.         else
  8368.           exit;
  8369.         end if;
  8370.       end if;
  8371.     end loop;
  8372.  
  8373.     -- prompt for the person or people assigned to the element
  8374.     if el_record.more_than_one_person then
  8375.       put_line(" Enter the initials of the person assigned to each activity");
  8376.       put_line(" of this element... ");
  8377.       new_line;
  8378.       -- prompt for the person working on each activity in the element
  8379.       START_WALK (ac_list);
  8380.       ac_index := 0;
  8381.       loop
  8382.     WALK(ac_list, ac_record, end_list);
  8383.     exit when end_list;
  8384.     ac_index := ac_index + 1;
  8385.     put(" Who is assigned to ");
  8386.     put(ac_record.name); put_line("? "); 
  8387.     loop
  8388.       PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, pr_key );
  8389.       exit when not abort_proc;
  8390.       put_line(" You cannot abort at this point!");
  8391.       put_line(" Enter the initials of a person assigned to the project.");
  8392.     end loop;
  8393.     el_record.people_initials(ac_index) := pr_key;
  8394.       end loop;
  8395.     else -- only one person is assigned
  8396.       put_line(" Enter the initials of the person assigned to this element");
  8397.       new_line;
  8398.       -- get new initials
  8399.       loop
  8400.         PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, pr_key );
  8401.     exit when not abort_proc;
  8402.     put_line(" You cannot abort at this point!");
  8403.     put_line(" Enter the initials of the person assigned to this element.");
  8404.       end loop;
  8405.       el_record.person_initials := pr_key;
  8406.     end if;
  8407.  
  8408.     -- enter the milestone number
  8409.     loop
  8410.      PROMPT_PKG.EXISTING_MILSTONE_NUMBER( abort_proc, ms_key );
  8411.       if abort_proc then
  8412.         put_line(" You MUST enter an existing milestone. ");
  8413.         put_line(" You cannot abort the procedure at this time. ");
  8414.       else
  8415.         el_record.milestone_num := ms_key;
  8416.         exit;
  8417.       end if;
  8418.     end loop;
  8419.  
  8420.     el_record.priority            := 
  8421.         PROMPT_PKG.element_priority ( default => el_record.milestone_num );
  8422.     el_record.current_size          := PROMPT_PKG.CURRENT_SIZE_EST;
  8423.     el_record.date_size_verified    := DATA_PKG.date;
  8424.     el_record.original_size         := 
  8425.        PROMPT_PKG.ORIG_SIZE_EST( default => el_record.current_size );
  8426.     el_record.complexity            := PROMPT_PKG.COMPLEXITY_FACTOR;
  8427.     el_record.activity_completeness := PROMPT_PKG.ACTIV_COMPLETENESS;  
  8428.  
  8429.     -- add data to lists 
  8430.     ADD_RECORD_TO_LISTS( el_record );
  8431.  
  8432.     -- increment number of elements
  8433.     num_of_elements := num_of_elements + 1;
  8434.  
  8435.   end EL_ADD;
  8436.  
  8437.  
  8438.   separate( TRACKER.ELEMENT_PKG )
  8439.   procedure EL_INITIALIZE is
  8440.   -----------------------------------------------------------------------------
  8441.   --|
  8442.   --|  NAME:  EL_INITIALIZE
  8443.   --|
  8444.   --|  OVERVIEW:
  8445.   --|    This procedure is called only when a new TRACKER file has to
  8446.   --|    be created.  It is part of a forced user response to fill in
  8447.   --|    the necessary data to make TRACKER a complete report.  The
  8448.   --|    procedure EL_ADD is called to gather the information and put it
  8449.   --|    into a linked list.
  8450.   --|
  8451.   --|  EXCEPTIONS HANDLED:
  8452.   --|    none
  8453.   --|  
  8454.   --|  HISTORY:
  8455.   --|    written by   May Lee   March 1985
  8456.   --|
  8457.   --|  NOTES:
  8458.   --|    The user is forced to add at least one element record and then
  8459.   --|    is prompted to add another or not.
  8460.   -----------------------------------------------------------------------------
  8461.   add_another :  character := 'N';
  8462.   done        :  boolean := false;
  8463.  
  8464.   begin
  8465.     while not done loop
  8466.       -- force the user to add at least one element
  8467.       EL_ADD;  -- data to the record and the record to the list
  8468.       loop
  8469.         put_line("Would you like to add another element? "); 
  8470.         put("   [ Y or N, <cr>=N ]  :  ");
  8471.         new_line;
  8472.         if end_of_line then
  8473.       skip_line;
  8474.           done := true;
  8475.           exit;
  8476.         else
  8477.           get(add_another); skip_line;
  8478.       if add_another = 'N' or add_another = 'n' then
  8479.             done := true;
  8480.             exit;
  8481.           elsif add_another = 'Y' or add_another = 'y' then
  8482.             exit;  -- add another element
  8483.           else
  8484.             put_line(" Please enter y or n. "); 
  8485.           end if;
  8486.         end if;
  8487.       end loop;
  8488.     end loop;
  8489.   end EL_INITIALIZE;
  8490.  
  8491.   separate ( TRACKER.ELEMENT_PKG )
  8492.   procedure UPDATE_CURRENT is
  8493.   -----------------------------------------------------------------------------
  8494.   --|
  8495.   --|  NAME:  UPDATE_CURRENT
  8496.   --|
  8497.   --|  OVERVIEW:
  8498.   --|    This procedure walks through a group of elements and asks the user
  8499.   --|    to update the current size estimate.  If no change is desired, the
  8500.   --|    user presses <cr>.  Otherwise he enters the new value for current 
  8501.   --|    size.
  8502.   --|
  8503.   --|  EXCEPTIONS HANDLED:
  8504.   --|    none
  8505.   --|  
  8506.   --|  HISTORY:
  8507.   --|    written by   Bonnie Burkhardt   March 1985
  8508.   --|
  8509.   -----------------------------------------------------------------------------
  8510.   selection : integer := 0;
  8511.   QUIT      : boolean := false;
  8512.   EL_PTR    : element_pointer;
  8513.   END_LIST  : boolean := false;
  8514.   MS_PTR    : milestone_pointer;
  8515.   MS_NUM    : ms_num_type := 1;
  8516.   PR_PTR    : personnel_pointer;
  8517.   PR_INITIALS : pr_init_type := (others => ' ');
  8518.   SS_PTR    : subsystem_pointer;
  8519.   SS_NAME   : ss_name_type := (others => ' ');
  8520.   SUCCEED   : boolean := false;
  8521.  
  8522.   procedure FIX_EL_SIZE (EL_PTR : in element_pointer) is separate;
  8523.  
  8524.   begin
  8525.     loop
  8526.       selection := VT100.PRINT_EL_GROUPS;
  8527.       case SELECTION is
  8528.         when 1 => -- all elements
  8529.       start_walk (EL_LIST);
  8530.       loop
  8531.         walk (EL_LIST, EL_PTR, END_LIST);
  8532.         exit when END_LIST;
  8533.         FIX_EL_SIZE (EL_PTR);
  8534.       end loop;
  8535.  
  8536.         when 2 => -- milestone
  8537.       PROMPT_PKG.existing_milstone_number (QUIT, MS_NUM);
  8538.       if not QUIT then
  8539.         find (MS_LIST, MS_NUM, MS_PTR, succeed);
  8540.         start_walk (MS_PTR.element_list);
  8541.         loop
  8542.           walk (MS_PTR.element_list, EL_PTR, END_LIST);
  8543.           exit when END_LIST;
  8544.           FIX_EL_SIZE (EL_PTR);
  8545.         end loop;
  8546.       end if;
  8547.  
  8548.     when 3 => -- person
  8549.       PROMPT_PKG.existing_person_initials (QUIT, PR_INITIALS);
  8550.       if not QUIT then
  8551.         find (PR_LIST, PR_INITIALS, PR_PTR, succeed);
  8552.         start_walk (PR_PTR.element_list);
  8553.         loop
  8554.           walk (PR_PTR.element_list, EL_PTR, END_LIST);
  8555.           exit when END_LIST;
  8556.           FIX_EL_SIZE (EL_PTR);
  8557.         end loop;
  8558.       end if;
  8559.  
  8560.     when 4 => -- subsystem
  8561.       PROMPT_PKG.existing_subsys_name (QUIT, SS_NAME);
  8562.       if not QUIT then
  8563.         find (SS_LIST, SS_NAME, SS_PTR, succeed);
  8564.         start_walk (SS_PTR.element_list);
  8565.         loop
  8566.           walk (SS_PTR.element_list, EL_PTR, END_LIST);
  8567.           exit when END_LIST;
  8568.           FIX_EL_SIZE (EL_PTR);
  8569.         end loop;
  8570.       end if;
  8571.  
  8572.     when 5 => exit;      
  8573.  
  8574.         when others => null;
  8575.       end case;
  8576.  
  8577.     end loop;
  8578.   end UPDATE_CURRENT;
  8579.  
  8580.  
  8581.   separate ( TRACKER.ELEMENT_PKG.UPDATE_CURRENT )
  8582.   procedure FIX_EL_SIZE (EL_PTR : in element_pointer) is 
  8583.   -----------------------------------------------------------------------------
  8584.   --|
  8585.   --|  NAME:  FIX_EL_SIZE
  8586.   --|
  8587.   --|  OVERVIEW:
  8588.   --|    This procedure updates the element's current size.  
  8589.   --|
  8590.   --|  EXCEPTIONS HANDLED:
  8591.   --|    none
  8592.   --|  
  8593.   --|  HISTORY:
  8594.   --|    written by   Bonnie Burkhardt   March 1985
  8595.   --|
  8596.   -----------------------------------------------------------------------------
  8597.  
  8598.   OLD_SIZE  : integer range 0..999_999 := EL_PTR.current_size;
  8599.  
  8600.   begin
  8601.     put(" For "); put(EL_PTR.desc_key);
  8602.     put(" -- "); put(EL_PTR.description); 
  8603.     EL_PTR.current_size := 
  8604.         PROMPT_PKG.update_current_size(EL_PTR.current_size);
  8605.  
  8606.     -- if the current size estimate decreased, then the percent of work
  8607.     -- done at start remains the same but the amount of work done at 
  8608.     -- start decreases
  8609.     if (EL_PTR.current_size = 0) or (old_size = 0) then
  8610.       EL_PTR.size_done_at_start := 0;
  8611.     elsif old_size > EL_PTR.current_size then
  8612.       EL_PTR.size_done_at_start := EL_PTR.size_done_at_start
  8613.         * EL_PTR.current_size / old_size;
  8614.     end if;
  8615.     EL_PTR.date_size_verified := DATA_PKG.date;
  8616.   end FIX_EL_SIZE;
  8617.  
  8618.  
  8619.   separate ( TRACKER.ELEMENT_PKG )
  8620.   procedure UPDATE_PCT_DONE is
  8621.   -----------------------------------------------------------------------------
  8622.   --|
  8623.   --|  NAME:  UPDATE_PCT_DONE 
  8624.   --|
  8625.   --|  OVERVIEW:
  8626.   --|    This procedure steps through a group of elements and updates the
  8627.   --|    percent complete estimate.
  8628.   --|
  8629.   --|  EXCEPTIONS HANDLED:
  8630.   --|    none
  8631.   --|  
  8632.   --|  HISTORY:
  8633.   --|    written by   May Lee            March 1985
  8634.   --|    written by   Bonnie Burkhardt   March 1985
  8635.   --|
  8636.   -----------------------------------------------------------------------------
  8637.  
  8638.   selection : integer := 0;
  8639.   QUIT      : boolean := false;
  8640.   EL_PTR    : element_pointer;
  8641.   END_LIST  : boolean := false;
  8642.   MS_PTR    : milestone_pointer;
  8643.   MS_NUM    : ms_num_type := 1;
  8644.   PR_PTR    : personnel_pointer;
  8645.   PR_INITIALS : pr_init_type := (others => ' ');
  8646.   SS_PTR    : subsystem_pointer;
  8647.   SS_NAME   : ss_name_type := (others => ' ');
  8648.   SUCCEED   : boolean := false;
  8649.  
  8650.   begin
  8651.     loop
  8652.       selection := VT100.PRINT_EL_GROUPS;
  8653.       case SELECTION is
  8654.         when 1 => -- all elements
  8655.       start_walk (EL_LIST);
  8656.       loop
  8657.         walk (EL_LIST, EL_PTR, END_LIST);
  8658.         exit when END_LIST;
  8659.         put(" For "); put(EL_PTR.desc_key);
  8660.         put(" -- "); put(EL_PTR.description); 
  8661.         EL_PTR.activity_completeness := 
  8662.           PROMPT_PKG.update_activ_completeness
  8663.           (EL_PTR.activity_completeness);
  8664.       end loop;
  8665.  
  8666.         when 2 => -- milestone
  8667.       PROMPT_PKG.existing_milstone_number (QUIT, MS_NUM);
  8668.       if not QUIT then
  8669.         find (MS_LIST, MS_NUM, MS_PTR, succeed);
  8670.         start_walk (MS_PTR.element_list);
  8671.         loop
  8672.           walk (MS_PTR.element_list, EL_PTR, END_LIST);
  8673.           exit when END_LIST;
  8674.           put(" For "); put(EL_PTR.desc_key);
  8675.           put(" -- "); put(EL_PTR.description); 
  8676.           EL_PTR.activity_completeness := 
  8677.             PROMPT_PKG.update_activ_completeness
  8678.             (EL_PTR.activity_completeness);
  8679.         end loop;
  8680.       end if;
  8681.  
  8682.     when 3 => -- person
  8683.       PROMPT_PKG.existing_person_initials (QUIT, PR_INITIALS);
  8684.       if not QUIT then
  8685.         find (PR_LIST, PR_INITIALS, PR_PTR, succeed);
  8686.         start_walk (PR_PTR.element_list);
  8687.         loop
  8688.           walk (PR_PTR.element_list, EL_PTR, END_LIST);
  8689.           exit when END_LIST;
  8690.           put(" For "); put(EL_PTR.desc_key);
  8691.           put(" -- "); put(EL_PTR.description); 
  8692.           EL_PTR.activity_completeness := 
  8693.           PROMPT_PKG.update_activ_completeness
  8694.           (EL_PTR.activity_completeness);
  8695.         end loop;
  8696.       end if;
  8697.  
  8698.     when 4 => -- subsystem
  8699.       PROMPT_PKG.existing_subsys_name (QUIT, SS_NAME);
  8700.       if not QUIT then
  8701.         find (SS_LIST, SS_NAME, SS_PTR, succeed);
  8702.         start_walk (SS_PTR.element_list);
  8703.         loop
  8704.           walk (SS_PTR.element_list, EL_PTR, END_LIST);
  8705.           exit when END_LIST;
  8706.           put(" For "); put(EL_PTR.desc_key);
  8707.           put(" -- "); put(EL_PTR.description);
  8708.           EL_PTR.activity_completeness := 
  8709.           PROMPT_PKG.update_activ_completeness
  8710.           (EL_PTR.activity_completeness);
  8711.         end loop;
  8712.       end if;
  8713.  
  8714.     when 5 => exit;      
  8715.  
  8716.         when others => null;
  8717.       end case;
  8718.  
  8719.     end loop;
  8720.   end UPDATE_PCT_DONE;
  8721.  
  8722.  
  8723.  
  8724.   separate ( TRACKER.ELEMENT_PKG )
  8725.   procedure EL_SET_UP is
  8726.   -----------------------------------------------------------------------------
  8727.   --|
  8728.   --|  NAME:  EL_SET_UP
  8729.   --|
  8730.   --|  OVERVIEW:
  8731.   --|    This procedure is only called if there is an existing input file.
  8732.   --|    The element list is set up by reading the element record
  8733.   --|    from the input file by calling EL_READ, and adding it to the linked 
  8734.   --|    list by calling ADD_RECORD_TO_LISTS until there are no more element 
  8735.   --|    records.  
  8736.   --|
  8737.   --|  EXCEPTIONS HANDLED:
  8738.   --|    others        Error reading the record from the file.
  8739.   --|    .        This exception raises ERROR_IN_INPUT_FILE.
  8740.   --|  
  8741.   --|  HISTORY:
  8742.   --|    written by   May Lee   March 1985
  8743.   --|
  8744.   --|  NOTES:
  8745.   --|    The number of element records read in is determined by the
  8746.   --|    global variable num_of_elements.
  8747.   --|
  8748.   --|    If an error is detected reading the data, the rest of the input line
  8749.   --|    is skipped and reading the rest of the data continues.  All errors
  8750.   --|    found are reported.  Execution is not terminated until the entire
  8751.   --|    input file has been read.
  8752.   --|
  8753.   -----------------------------------------------------------------------------
  8754.   el_record : element_pointer;
  8755.   el_num    : integer := 0;
  8756.   bad_data  : boolean := false;
  8757.   
  8758.   procedure EL_READ is separate;
  8759.  
  8760.   begin
  8761.     for i in 1..num_of_elements loop
  8762.       el_num := i;
  8763.       begin
  8764.         -- create a null record
  8765.         el_record := new element_type;    
  8766.  
  8767.         -- read the element
  8768.         EL_READ;
  8769.  
  8770.         -- add the element record to the linked lists
  8771.         ADD_RECORD_TO_LISTS( el_record );
  8772.       exception
  8773.         when others =>
  8774.           skip_line (tracker_file);
  8775.           put(" Error reading element record "); put(el_num,1); 
  8776.       put_line(" from the tracker file. ");
  8777.           bad_data := true;
  8778.       end;
  8779.     end loop;
  8780.     if bad_data then
  8781.       raise ERROR_IN_INPUT_FILE;
  8782.     end if;
  8783.   end EL_SET_UP;
  8784.  
  8785.     separate( TRACKER.ELEMENT_PKG.EL_SET_UP )
  8786.     procedure EL_READ is
  8787.     ----------------------------------------------------------------------------
  8788.     --|
  8789.     --|  NAME:  EL_READ
  8790.     --|
  8791.     --|  OVERVIEW:
  8792.     --|    This procedure reads a record from the file.  One line of data is
  8793.     --|    read at a time and broken down into the fields of the
  8794.     --|    element record, which is made visible to the calling routine
  8795.     --|    EL_SET_UP.  The data is read in the format specified by the EL_WRITE
  8796.     --|    procedure.
  8797.     --|
  8798.     --|
  8799.     --|  EXCEPTIONS HANDLED:
  8800.     --|    none
  8801.     --|
  8802.     --|  HISTORY:
  8803.     --|    written by   May Lee   March 1985
  8804.     --|
  8805.     --|  NOTES:
  8806.     --|    Any exceptions raised here are handled by EL_SET_UP.
  8807.     --|
  8808.     ----------------------------------------------------------------------------
  8809.     multiple_people : character;  -- true or false
  8810.  
  8811.     begin
  8812.       get( tracker_file, el_record.description );  -- string
  8813.       get( tracker_file, el_record.desc_key );
  8814.       get( tracker_file, el_record.subsystem_name );
  8815.       get( tracker_file, el_record.milestone_num, 2 );  -- integer
  8816.       get( tracker_file, el_record.priority, 2 );  -- integer
  8817.       get( tracker_file, el_record.original_size, 7 );
  8818.       get( tracker_file, el_record.size_done_at_start, 7 );
  8819.       get( tracker_file, el_record.current_size, 7 );
  8820.       get( tracker_file, el_record.complexity, 3 );              -- real
  8821.       for i in 1..num_of_activities loop
  8822.         get( tracker_file, char_ac_completeness(i) );            -- character
  8823.         -- convert char to enumeration type act_phase_char_set
  8824.         el_record.activity_completeness(i) := convert( char_ac_completeness(i) );
  8825.       end loop;
  8826.       get( tracker_file, el_record.prev_date_done.month , 2);
  8827.       get( tracker_file, el_record.prev_date_done.day   , 2);
  8828.       get( tracker_file, el_record.prev_date_done.year  , 4);
  8829.       get( tracker_file, el_record.date_size_verified.month , 2);
  8830.       get( tracker_file, el_record.date_size_verified.day   , 2);
  8831.       get( tracker_file, el_record.date_size_verified.year  , 4);
  8832.       get( tracker_file, multiple_people );
  8833.       if multiple_people = 'T' then 
  8834.         MULTIPLE_PR_EL_RECORD( el_record );
  8835.         for i in 1..num_of_activities loop
  8836.           get( tracker_file, el_record.people_initials(i) );
  8837.         end loop;
  8838.       else
  8839.         get( tracker_file, el_record.person_initials );
  8840.       end if;
  8841.       skip_line (tracker_file);
  8842.     end EL_READ;
  8843.  
  8844.   separate ( TRACKER.ELEMENT_PKG )
  8845.   procedure EL_DELETE is
  8846.   -----------------------------------------------------------------------------
  8847.   --|
  8848.   --|  NAME:  EL_DELETE
  8849.   --|
  8850.   --|  OVERVIEW:
  8851.   --|    This procedure is used to delete an element record.  The user is
  8852.   --|    prompted to enter an existing element by a call to the Prompt_Pkg
  8853.   --|    function, which returns a valid key.  The element is deleted from
  8854.   --|    each data's element list to which that element belonged.  The 
  8855.   --|    element is then deleted from the element list by calling the List_pkg
  8856.   --|    procedure DELETE.
  8857.   --|
  8858.   --|  EXCEPTIONS HANDLED:
  8859.   --|    none
  8860.   --|  
  8861.   --|  HISTORY:
  8862.   --|    written by   May Lee   March 1985
  8863.   --|
  8864.   --|  NOTES:
  8865.   --|    The number of elements is decremented if the delete is successful.
  8866.   --|
  8867.   --|    A check is made to insure the last element is not deleted.  There
  8868.   --|    must be at least one element at all times.
  8869.   --|
  8870.   -----------------------------------------------------------------------------
  8871.   abort_proc  : boolean := false;
  8872.   el_record   : element_pointer;
  8873.   found       : boolean;           -- parameter to find
  8874.   ms_record   : milestone_pointer; -- to delete the element from ms_el_list
  8875.   pr_record   : personnel_pointer; -- to delete the element from pr_el_list
  8876.   ss_record   : subsystem_pointer; -- to delete the element from ss_el_list
  8877.   successful  : boolean := false;
  8878.   key         : el_key_type;  -- element description key
  8879.  
  8880.   begin
  8881.     if num_of_elements > 1 then
  8882.       put_line("Which element would you like to delete? ");
  8883.       --  get the element description key
  8884.       PROMPT_PKG.EXISTING_ELE_KEY( abort_proc, key );
  8885.  
  8886.       if not abort_proc then
  8887.         FIND( el_list, key, el_record, found );
  8888.  
  8889.         -- find the milestone belonging to the deleted element
  8890.         FIND( ms_list, el_record.milestone_num, ms_record, found );
  8891.         --  delete the element from the milestone element list
  8892.         DELETE( ms_record.element_list, key, successful );
  8893.   
  8894.         -- find the person belonging to the deleted element
  8895.     if el_record.more_than_one_person then
  8896.       -- delete the element from all the personnel lists
  8897.       for ac in 1..num_of_activities loop
  8898.         find (pr_list, el_record.people_initials(ac), pr_record, found);
  8899.         delete (pr_record.element_list, key, found);
  8900.       end loop;
  8901.     else
  8902.       FIND( pr_list, el_record.person_initials, pr_record, found );
  8903.           DELETE( pr_record.element_list, key, successful );
  8904.     end if;
  8905.   
  8906.         -- find the subsystem belonging to the deleted element
  8907.         FIND( ss_list, el_record.subsystem_name, ss_record, found );
  8908.         --  delete from the subsystem element list
  8909.         DELETE( ss_record.element_list, key, successful );
  8910.  
  8911.         --  delete from the element list
  8912.         DELETE( el_list, key, successful );
  8913.  
  8914.         --  decrement the element counter
  8915.         num_of_elements := num_of_elements - 1;
  8916.         put("Number of elements = "); put(num_of_elements); new_line;
  8917.         delay 1.0;
  8918.       end if;  -- if abort, don't do delete
  8919.     else
  8920.       put_line(" You must have at least one element at all times. ");
  8921.       put_line(" Since you have only one element at this time, you ");
  8922.       put_line(" cannot delete it. ");
  8923.       delay 2.0;
  8924.     end if;
  8925.   end EL_DELETE;
  8926.  
  8927.  
  8928.   separate ( TRACKER.ELEMENT_PKG )
  8929.   procedure EL_MODIFY is
  8930.   -----------------------------------------------------------------------------
  8931.   --|
  8932.   --|  NAME:  EL_MODIFY
  8933.   --|
  8934.   --|  OVERVIEW:
  8935.   --|    This procedure allows the user to modify an existing element record.
  8936.   --|    The user is prompted for an existing element record by calling
  8937.   --|    the appropriate Prompt_Pkg function.  The generic FIND is used to 
  8938.   --|    get the record.  The user is then allowed to change the fields by
  8939.   --|    choosing a menu selection.  The record fields are modified directly.
  8940.   --|    If the element abbreviation is modified, MODIFY_ELEMENT_KEY is called.  
  8941.   --|    If a change is made to a field that affects another data type, then 
  8942.   --|    checks have to be made to insure that the change is valid.  For
  8943.   --|    example, if the person's initials are changed in the element data,
  8944.   --|    checks have to be made to make sure that the new initials belong
  8945.   --|    to a valid pre-defined person.  This is taken care of by the 
  8946.   --|    Prompt_Pkg, which only returns valid values. 
  8947.   --|
  8948.   --|  EXCEPTIONS HANDLED:
  8949.   --|    none 
  8950.   --|  
  8951.   --|  HISTORY:
  8952.   --|    written by   May Lee   March 1985 
  8953.   --|    written by   Bonnie Burkhardt   March 1985 
  8954.   --|
  8955.   -----------------------------------------------------------------------------
  8956.   abort_proc       : boolean := false;  -- don't want to change a field
  8957.   ac_index       : integer := 0;
  8958.   ac_record       : activity_pointer;
  8959.   end_list       : boolean := false;
  8960.   el_record        : element_pointer ;  -- pointer to element record
  8961.   el_record2       : element_pointer;
  8962.   exit_field_menu  : boolean := false;  -- exit element field menu
  8963.   field_selection  : integer;           -- selection from element field menu
  8964.   found            : boolean;           -- parameter to find
  8965.   key              : el_key_type;       -- key to description of element 
  8966.                                         -- we are looking for
  8967.   ms_record        : milestone_pointer; -- to check if the milestone exists
  8968.   new_ms           : ms_num_type;       -- if modify ms
  8969.   new_pr           : pr_init_type;      -- if modify pr
  8970.   new_ss_name      : ss_name_type;      -- if modify ss name
  8971.   old_size       : integer range 0..99_999 := 0;
  8972.   pr_key       : pr_init_type;      -- used to get key 
  8973.   pr_record        : personnel_pointer; -- to check if the person exists
  8974.   ss_record        : subsystem_pointer; -- to check if the subsystem exists
  8975.  
  8976.   procedure MODIFY_ELEMENT_KEY is separate;
  8977.     
  8978.   begin
  8979.     -- get the element key
  8980.     new_line;
  8981.     put_line(" Which element would you like to modify?");
  8982.     PROMPT_PKG.EXISTING_ELE_KEY ( abort_proc, key );
  8983.  
  8984.     -- find the valid key in the list to get the pointer to that record
  8985.     FIND( el_list, key, el_record, found );
  8986.  
  8987.     if not abort_proc then
  8988.       -- display menu
  8989.       while not exit_field_menu loop
  8990.         field_selection := VT100.PRINT_EL_MENU( el_record );
  8991.         case field_selection is
  8992.           when 1 =>  -- get new element description
  8993.             put_line(" The current element description is : ");
  8994.             put_line( el_record.description );
  8995.             new_line;
  8996.             el_record.description := PROMPT_PKG.ELE_DESCRIPTION;
  8997.  
  8998.           when 2 =>  -- Getting new element key 
  8999.             put(" What would you like to change "); put(key); put(" to? ");
  9000.             MODIFY_ELEMENT_KEY;
  9001.  
  9002.           when 3 =>  -- Getting new subsystem name 
  9003.             -- show the old name
  9004.             put(" The current subsystem name is ");
  9005.             put( el_record.subsystem_name ); new_line;
  9006.             put_line(" What would you like to change it to? ");
  9007.             -- get new name
  9008.             PROMPT_PKG.EXISTING_SUBSYS_NAME( abort_proc, new_ss_name );
  9009.             if not abort_proc then
  9010.               el_record.subsystem_name := new_ss_name;
  9011.             end if;
  9012.  
  9013.           when 4 =>  -- Getting new person's initials 
  9014.             -- show the old initials
  9015.         if el_record.more_than_one_person then
  9016.           -- delete the element from all the personnel lists
  9017.           for ac in 1..num_of_activities loop
  9018.         find (pr_list, el_record.people_initials(ac), pr_record, found);
  9019.         delete (pr_record.element_list, el_record.desc_key, found);
  9020.           end loop;
  9021.  
  9022.           -- prompt for the person working on each activity in the element
  9023.           start_walk (ac_list);
  9024.           ac_index := 0;
  9025.           loop
  9026.         walk(ac_list, ac_record, end_list);
  9027.         exit when end_list;
  9028.  
  9029.         ac_index := ac_index + 1;
  9030.         put(" The person assigned to ");
  9031.         put(ac_record.name);
  9032.         put(" is ");
  9033.         put(el_record.people_initials(ac_index));
  9034.         new_line;
  9035.  
  9036.         loop
  9037.           PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, pr_key );
  9038.           exit when not abort_proc;
  9039.           put_line(" You cannot abort at this point!");
  9040.           put_line(" Enter the initials of a person assigned to the project.");
  9041.         end loop;
  9042.         el_record.people_initials(ac_index) := pr_key;
  9043.  
  9044.         -- add the element to the person's list, if not already added
  9045.         find (pr_list, pr_key, pr_record, found);
  9046.         find (pr_record.element_list, el_record.desc_key, el_record2, 
  9047.               found);
  9048.         if not found then
  9049.           add (pr_record.element_list, el_record.desc_key, el_record);
  9050.         end if;
  9051.           end loop;
  9052.         else -- only one person is assigned
  9053.           put(" The current person's initials are ");
  9054.           put( el_record.person_initials ); new_line;
  9055.           put_line(" Who would you like to change it to? ");
  9056.           -- get new initials
  9057.           PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, new_pr );
  9058.           if not abort_proc then
  9059.             el_record.person_initials := new_pr;
  9060.           end if;
  9061.         end if;
  9062.  
  9063.           when 5 =>  -- Getting new milestone number 
  9064.             -- show the old number
  9065.             put(" The current milestone number is ");
  9066.             put( el_record.milestone_num,2 ); new_line;
  9067.             put_line(" What milestone would you like to replace it? ");
  9068.             -- get new number
  9069.             PROMPT_PKG.EXISTING_MILSTONE_NUMBER( abort_proc, new_ms );
  9070.             if not abort_proc then
  9071.               el_record.milestone_num := new_ms;
  9072.             end if;
  9073.  
  9074.           when 6 =>  -- Getting new element priority
  9075.             -- show the old number
  9076.             put(" The current element priority is ");
  9077.             put( el_record.priority, 2 ); new_line;
  9078.             put_line(" What would you like to change it to? ");
  9079.             -- get new priority
  9080.             el_record.priority        := 
  9081.         PROMPT_PKG.element_priority( default => el_record.milestone_num );
  9082.  
  9083.           when 7 =>  -- Getting new current size 
  9084.             -- show the old size
  9085.             put(" The current size is ");
  9086.             put( el_record.current_size, 1); new_line;
  9087.             put_line(" What would you like to change it to? ");
  9088.             -- get new size
  9089.         old_size := el_record.current_size;
  9090.             el_record.current_size := PROMPT_PKG.CURRENT_SIZE_EST;
  9091.  
  9092.         -- if the current size estimate decreased, then the percent of work
  9093.         -- done at start remains the same but the amount of work done at 
  9094.         -- start decreases
  9095.         if (el_record.current_size = 0) or (old_size = 0) then
  9096.           el_record.size_done_at_start := 0;
  9097.         elsif old_size > el_record.current_size then
  9098.           el_record.size_done_at_start := el_record.size_done_at_start
  9099.             * el_record.current_size / old_size;
  9100.         end if;
  9101.         el_record.date_size_verified := DATA_PKG.date;
  9102.  
  9103.           when 8 => -- Getting new complexity 
  9104.             -- show the old complexity
  9105.             put(" The current complexity is ");
  9106.             put( el_record.complexity, 2, 3, 0); new_line;
  9107.             put_line(" What would you like to change it to? ");
  9108.             -- get new complexity
  9109.             el_record.complexity := PROMPT_PKG.COMPLEXITY_FACTOR;
  9110.  
  9111.           when 9 => -- Getting new activity completeness 
  9112.             -- show the old activity completeness
  9113.             put(" The current element's activity completeness is : ");
  9114.             for i in 1..num_of_activities loop
  9115.               put( CONVERT(el_record.activity_completeness(i)) ); 
  9116.             end loop;
  9117.             new_line;
  9118.             put_line(" What would you like to change it to? ");
  9119.             -- get new name
  9120.             el_record.activity_completeness := PROMPT_PKG.ACTIV_COMPLETENESS;
  9121.  
  9122.           when 10 => -- More than one element assigned
  9123.         if el_record.more_than_one_person then
  9124.           -- delete the element from all the personnel lists
  9125.           for ac in 1..num_of_activities loop
  9126.         find (pr_list, el_record.people_initials(ac), pr_record, found);
  9127.         delete (pr_record.element_list, el_record.desc_key, found);
  9128.           end loop;
  9129.  
  9130.           SINGLE_PR_EL_RECORD( el_record );
  9131.           put_line(" The element can now be assigned to one person.");
  9132.           put_line(" Who do you want assigned to this element?");
  9133.           loop
  9134.             PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, new_pr );
  9135.             exit when not abort_proc;
  9136.         put_line(" You cannot abort at this point!");
  9137.         put_line(" Enter the initials of a person assigned to the project.");
  9138.           end loop;
  9139.           el_record.person_initials := new_pr;
  9140.  
  9141.           -- add this element to the person's list
  9142.           find (pr_list, pr_key, pr_record, found);
  9143.           add (pr_record.element_list, el_record.desc_key, el_record);
  9144.  
  9145.         else -- only one person is assigned
  9146.           -- delete the element from the personnel lists
  9147.           find (pr_list, el_record.person_initials, pr_record, found);
  9148.           delete (pr_record.element_list, el_record.desc_key, found);
  9149.  
  9150.           MULTIPLE_PR_EL_RECORD( el_record );
  9151.  
  9152.           -- prompt for the person working on each activity in the element
  9153.           put_line(" The element can now be assigned to several people.");
  9154.           start_walk (ac_list);
  9155.           ac_index := 0;
  9156.           loop
  9157.         walk(ac_list, ac_record, end_list);
  9158.         exit when end_list;
  9159.  
  9160.         ac_index := ac_index + 1;
  9161.         put(" Who is assigned to ");
  9162.         put(ac_record.name); put('?');
  9163.         new_line;
  9164.         loop
  9165.           PROMPT_PKG.EXISTING_PERSON_INITIALS( abort_proc, pr_key );
  9166.           exit when not abort_proc;
  9167.           put_line(" You cannot abort at this point!");
  9168.           put_line(" Enter the initials of a person assigned to the project.");
  9169.         end loop;
  9170.         el_record.people_initials(ac_index) := pr_key;
  9171.  
  9172.         -- add the element to the person's list, if not already added
  9173.         find (pr_list, pr_key, pr_record, found);
  9174.         find (pr_record.element_list, el_record.desc_key, el_record2, 
  9175.               found);
  9176.         if not found then
  9177.           add (pr_record.element_list, el_record.desc_key, el_record);
  9178.         end if;
  9179.           end loop;
  9180.         end if;
  9181.  
  9182.         -- change the element data in the subsystem element list
  9183.         find (ss_list, el_record.subsystem_name, ss_record, found);
  9184.         change_list_data (ss_record.element_list, el_record.desc_key, 
  9185.                 el_record);
  9186.  
  9187.         -- change the element in the milestone element list
  9188.         find (ms_list, el_record.milestone_num, ms_record, found);
  9189.         change_list_data (ms_record.element_list, el_record.desc_key, 
  9190.                 el_record);
  9191.  
  9192.         -- change the element data in the element list
  9193.         change_list_data (el_list, el_record.desc_key, el_record);
  9194.  
  9195.           when 11 => exit_field_menu := true;
  9196.           when others =>  put_line("Please enter a number between 1 and 11. ");
  9197.         end case;
  9198.       end loop;
  9199.     end if;  -- not abort_proc
  9200.   end EL_MODIFY;
  9201.  
  9202.     separate ( TRACKER.ELEMENT_PKG.EL_MODIFY )
  9203.     procedure MODIFY_ELEMENT_KEY is
  9204.     ---------------------------------------------------------------------------
  9205.     --|
  9206.     --|  NAME:  MODIFY_ELEMENT_KEY
  9207.     --|
  9208.     --|  OVERVIEW:
  9209.     --|    This procedure is called when the element description abbreviation
  9210.     --|    is modified.  The user is prompted for a new unique key by calling
  9211.     --|    the Prompt_Pkg function.  The element key must be changed in the
  9212.     --|    element record, the search key for the element list, and the search
  9213.     --|    key for each data type's element list.
  9214.     --|
  9215.     --|  EXCEPTIONS HANDLED:
  9216.     --|    none 
  9217.     --|  
  9218.     --|  HISTORY:
  9219.     --|    written by   May Lee   March 1985 
  9220.     --|
  9221.     --|  NOTES:
  9222.     --|    If an error is detected in finding the element in any of the
  9223.     --|    data's element list, a message is output to the screen only.
  9224.     --|    There is no data recovery or termination performed.
  9225.     ---------------------------------------------------------------------------
  9226.       
  9227.     blank_key        : el_key_type := (others => ' ');  -- to blank out key
  9228.     found            : boolean;     -- found in list
  9229.     new_key          : el_key_type := (others => ' ');  -- to get the new key
  9230.  
  9231.     begin
  9232.       -- Change the key in the element list...
  9233.  
  9234.       -- get the new key ( only a valid unique key will be returned )
  9235.       new_key := PROMPT_PKG.NEW_ELE_KEY;
  9236.  
  9237.       -- change key in element data record
  9238.       el_record.desc_key := new_key;
  9239.  
  9240.       -- got a valid key, change the old_key to the new key in the element list
  9241.       CHANGE_LIST_KEY( el_list, key, new_key );
  9242.  
  9243.       -- change the element key in the milestone's el list for the milestone
  9244.       -- belonging to the modified element
  9245.       FIND( ms_list, el_record.milestone_num, ms_record, found );
  9246.       if found then
  9247.         CHANGE_LIST_KEY( ms_record.element_list, key, new_key );
  9248.       else
  9249.         put_line(" Error in modify element - could not find el in the ms_el list ");
  9250.       end if;
  9251.  
  9252.       -- change the element key in the person's el list for the person
  9253.       -- belonging to the modified element
  9254.       FIND( pr_list, el_record.person_initials, pr_record, found );
  9255.       if found then
  9256.         CHANGE_LIST_KEY( pr_record.element_list, key, new_key );
  9257.       else
  9258.         put_line(" Error in modify element - could not find el in the pr_el list ");
  9259.       end if;
  9260.  
  9261.       -- change the element key in the subsystem's el list for the subsystem
  9262.       -- belonging to the modified element
  9263.       FIND( ss_list, el_record.subsystem_name, ss_record, found );
  9264.       if found then
  9265.         CHANGE_LIST_KEY( ss_record.element_list, key, new_key );
  9266.       else
  9267.         put_line(" Error in modify element - could not find el in the ss_el list ");
  9268.       end if;
  9269.     end MODIFY_ELEMENT_KEY;
  9270.  
  9271.  
  9272.   separate ( TRACKER.ELEMENT_PKG )
  9273.   procedure EL_SAVE is
  9274.   -----------------------------------------------------------------------------
  9275.   --|
  9276.   --|  NAME:  EL_SAVE
  9277.   --|
  9278.   --|  OVERVIEW:
  9279.   --|    This procedure saves a record to file by calling the EL_WRITE 
  9280.   --|    procedure.  The user is first asked which date of completion
  9281.   --|    to save to determine which date to write to the file.  The generic 
  9282.   --|    procedures START_WALK and WALK are called to walk the linked list 
  9283.   --|    allowing one record at a time to be written.
  9284.   --|
  9285.   --|  EXCEPTIONS HANDLED:
  9286.   --|    none 
  9287.   --|  
  9288.   --|  HISTORY:
  9289.   --|    written by   May Lee   March 1985 
  9290.   --|
  9291.   -----------------------------------------------------------------------------
  9292.   a_char      : character := ' ';  -- input character y or n
  9293.   el_record   : element_pointer;   -- pointer to the element record  
  9294.   end_list    : boolean := false;  -- parameter to WALK
  9295.   update      : boolean := true;   -- update the previous date of completion
  9296.  
  9297.   procedure EL_WRITE is separate;
  9298.  
  9299.   begin
  9300.     START_WALK( el_list );
  9301.     -- find out which data to write to the file
  9302.     loop
  9303.       put_line(" Do you want to update the previous date of completion with the ");
  9304.       put_line(" newly computed date of completion?");
  9305.       put(" [Y or N, <cr>=Y] : ");
  9306.       if end_of_line then
  9307.         skip_line;
  9308.         exit;
  9309.       else
  9310.         get( a_char );
  9311.         skip_line;
  9312.         if a_char = 'N' or a_char = 'n' then
  9313.           update := false;        
  9314.           exit;
  9315.         elsif a_char = 'Y' or a_char = 'y' then
  9316.           exit;
  9317.         else
  9318.           new_line;
  9319.           put_line(" When the data is written to the file for the next run of TRACKER,");
  9320.           put_line(" which set of element completion dates would you like stored in the ");
  9321.           put_line(" 'Previous Completion Date' column, the previous completion date ");
  9322.           put_line(" used in this run or the newly computed completion date? "); 
  9323.           new_line;
  9324.         end if;
  9325.       end if;
  9326.     end loop;
  9327.     new_line(2);
  9328.  
  9329.     -- walk the list one element at a time and write it to the file
  9330.     loop
  9331.       WALK(el_list, el_record, end_list);
  9332.       exit when end_list;
  9333.       EL_WRITE;
  9334.     end loop;
  9335.   end EL_SAVE;
  9336.  
  9337.     separate ( TRACKER.ELEMENT_PKG.EL_SAVE )
  9338.     procedure EL_WRITE is
  9339.     ----------------------------------------------------------------------
  9340.     --|
  9341.     --|  NAME:  EL_WRITE
  9342.     --|
  9343.     --|  OVERVIEW:
  9344.     --|    This procedure is passed in a record pointer.  The record is written
  9345.     --|    to one line of the output file in the following format:
  9346.     --||
  9347.     --||   +--------------+------+----------+--+--+--+-------+-------+
  9348.     --||   | description  | key  | ss_name  |pr|ms|pi| bs_ln | sz_st | . . .
  9349.     --||   +--------------+------+----------+--+--+--+-------+-------+
  9350.     --||
  9351.     --||                                 prev_date  date_verif
  9352.     --||         +-------+---+----------+--+--+----+--+--+----+------+
  9353.     --||   . . . | cur_sz|com| ac_cmpltn|mo|dy|year|mo|dy|year|mul_pr| . . .
  9354.     --||         +-------+---+----------+--+--+----+--+--+----+------+
  9355.     --||                      ^ 
  9356.     --||                      this field varies from 1..num_of_activities
  9357.     --||  
  9358.     --||   Since the element record is variant, the remaining data depends on
  9359.     --||   the value of more_than_one_person.
  9360.     --||   If true :  +--+--+--+
  9361.     --||              |pr|pr|pr|...num_of_activities  -- array of initials  
  9362.     --||              +--+--+--+
  9363.     --||   
  9364.     --||   If false:  +--+
  9365.     --||              |pr|      -- only one initial
  9366.     --||              +--+
  9367.     --||
  9368.     --|    The element records are the last type of data to be written to the
  9369.     --|    output file.  There are no extra spaces between the record fields.
  9370.     --|
  9371.     --|  EXCEPTIONS HANDLED:
  9372.     --|    none
  9373.     --|
  9374.     --|  HISTORY:
  9375.     --|    written by   May Lee   March 1985
  9376.     --|
  9377.     --|  NOTES:
  9378.     --|    The boolean value more_than_one_person, is read and written to the
  9379.     --|    file as an integer (1=true, 0=false).  This is due to the problems
  9380.     --|    with the way Ada reads an enumeration type from a file.  The default
  9381.     --|    width cannot be used if additional data follows the boolean value.
  9382.     --|    If the width is used to allow for a trailing blank, then the boolean
  9383.     --|    value can be read, but the following value is incorrect (unless you
  9384.     --|    account for the blank). 
  9385.     --|
  9386.     ----------------------------------------------------------------------
  9387.  
  9388.       is_true  : constant character := 'T';
  9389.       is_false : constant character := 'F';
  9390.  
  9391.     begin
  9392.       put( output_file, el_record.description );  -- string
  9393.       put( output_file, el_record.desc_key );
  9394.       put( output_file, el_record.subsystem_name );
  9395.       put( output_file, el_record.milestone_num, 2 );  -- integer
  9396.       put( output_file, el_record.priority, 2 );  -- integer
  9397.       put( output_file, el_record.original_size, 7 );
  9398.       put( output_file, el_record.size_done_at_start, 7 );
  9399.       put( output_file, el_record.current_size, 7 );
  9400.       put( output_file, el_record.complexity, 1, 1, 0 );
  9401.       for i in 1..num_of_activities loop
  9402.         -- convert enumeration type act_phase_char_set to char for write
  9403.         char_ac_completeness(i) := convert( el_record.activity_completeness(i) );
  9404.         put( output_file, char_ac_completeness(i) ); 
  9405.       end loop;
  9406.       if update then  -- update prev_date_done to date_done 
  9407.         put( output_file, el_record.date_done.month , 2);
  9408.         put( output_file, el_record.date_done.day   , 2);
  9409.         put( output_file, el_record.date_done.year  , 4);
  9410.       else
  9411.         put( output_file, el_record.prev_date_done.month , 2);
  9412.         put( output_file, el_record.prev_date_done.day   , 2);
  9413.         put( output_file, el_record.prev_date_done.year  , 4);
  9414.       end if;
  9415.       put( output_file, el_record.date_size_verified.month , 2);
  9416.       put( output_file, el_record.date_size_verified.day   , 2);
  9417.       put( output_file, el_record.date_size_verified.year  , 4);
  9418.       if el_record.more_than_one_person then
  9419.         put( output_file, is_true );
  9420.         for i in 1..num_of_activities loop
  9421.           put( output_file, el_record.people_initials(i) );
  9422.         end loop;
  9423.       else
  9424.         put( output_file, is_false );
  9425.         put( output_file, el_record.person_initials );
  9426.       end if;
  9427.       new_line(output_file);
  9428.     end EL_WRITE;
  9429. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9430. --report.ada
  9431. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9432. Separate(tracker)
  9433.  
  9434. procedure REPORT_GENERATOR is
  9435. --------------------------------------------------------------------------------
  9436. --|
  9437. --|  NAME:  REPORT_GENERATOR 
  9438. --|
  9439. --|  OVERVIEW:
  9440. --|    This procedure controls the report menu and resolves the selections the
  9441. --|    user makes, allowing the user to print any combination of reports.
  9442. --|  
  9443. --|  EXCEPTIONS HANDLED:
  9444. --|    end_error    invalid user menu response
  9445. --|    data_error       invalid user menu response
  9446. --|
  9447. --|  HISTORY:
  9448. --|    written by   May Lee            February 1985
  9449. --|    written by   Bonnie Burkhardt   March 1985
  9450. --------------------------------------------------------------------------------
  9451.  
  9452.   use VT100;
  9453.  
  9454.   comments_file : file_type;
  9455.   comments_filename : string (1..80) := (others => ' ');
  9456.  
  9457.   type ORIG_OR_CUR_TYPE is (ORIGINAL, CURRENT);
  9458.   type SS_AC_ARRAY is array (1..NUM_OF_SUBSYSTEMS, 1..NUM_OF_ACTIVITIES)
  9459.     of float range 0.0..100.0;
  9460.   type SS_ARRAY is array (1..NUM_OF_SUBSYSTEMS) of float range 0.0..100.0;
  9461.   type AC_ARRAY is array (1..NUM_OF_ACTIVITIES) of float range 0.0..100.0;
  9462.   type MS_ARRAY is array (ms_num_type) of float range 0.0..100.0;
  9463.  
  9464.   type PCT_DONE_TYPE is record
  9465.     BY_SS_AND_AC : SS_AC_ARRAY 
  9466.     := (1..num_of_subsystems => (1..num_of_activities => 0.0));
  9467.     BY_SS        : SS_ARRAY := (others => 0.0);
  9468.     BY_AC        : AC_ARRAY := (others => 0.0);
  9469.     BY_MS        : MS_ARRAY := (others => 0.0);
  9470.     START_BY_SS  : SS_ARRAY := (others => 0.0);
  9471.     START_BY_AC  : AC_ARRAY := (others => 0.0);
  9472.     ENTIRE_BY_SS : SS_ARRAY := (others => 0.0);
  9473.     ENTIRE_BY_AC : AC_ARRAY := (others => 0.0);
  9474.     CONTRACT     : float range 0.0..100.0 := 0.0;
  9475.     START        : float range 0.0..100.0 := 0.0;
  9476.     ENTIRE       : float range 0.0..100.0 := 0.0;
  9477.   end record;
  9478.  
  9479.   MAX_DATA_LINES : constant integer := 43;
  9480.  
  9481.   EXIT_REPORT_MENU  : boolean := false;
  9482.   CURRENT_PCT_DONE  : PCT_DONE_TYPE;
  9483.   ORIGINAL_PCT_DONE : PCT_DONE_TYPE;
  9484.   menu_selection    : integer := 0;
  9485.   a_report_printed  : boolean := false;
  9486.  
  9487.   procedure CALC_PCT_DONE (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE;
  9488.                PCT_DONE    : in out PCT_DONE_TYPE) is separate;
  9489.   procedure START_PAGE (TITLE, SUBTITLE, HEADER1, HEADER2, HEADER_LINES 
  9490.     : in string := "") is separate;
  9491.   procedure PARAMETER_DATA_LIST    is separate;
  9492.   procedure PRINT_COMMENTS is separate;
  9493.   procedure ALL_ELMNT_STATUS_REP   is separate;
  9494.   procedure LIST_BY_SUBSYSTEM      is separate;
  9495.   procedure LIST_BY_MILESTONE      is separate;
  9496.   procedure LIST_BY_PERSON         is separate;
  9497.   procedure SUBSYSTEM_SUMMARY      is separate;
  9498.   procedure MILESTONE_SUMMARY      is separate;
  9499.   procedure WORK_UNITS_PER_SS      is separate;
  9500.   procedure PERCENT_COMPLETION (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE;
  9501.                 PCT_DONE    : in PCT_DONE_TYPE) is separate;
  9502.   procedure DISTRIBUTION_OF_WORK (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE) 
  9503.                         is separate;
  9504.   procedure COMPLETION_DATE_FOR_MS is separate;
  9505.   procedure REPORTS_PRINTED_LIST   is separate;
  9506.  
  9507. begin
  9508.   -- get report file name (input file with ".rpt" extension)
  9509.  
  9510.   -- start at end of filename look right to left for '.' indicating extension
  9511.   while tracker_filename(filename_lngth) /= '.' loop
  9512.     filename_lngth := filename_lngth - 1;
  9513.   end loop;
  9514.  
  9515.   -- filename up to extension including the '.'
  9516.   report_filename(1..filename_lngth) := tracker_filename(1..filename_lngth);
  9517.  
  9518.   -- filename with ".rpt" extension  
  9519.   report_filename(filename_lngth+1..filename_lngth+3) := "rpt";
  9520.   filename_lngth := filename_lngth + 3;
  9521.  
  9522.   create(report_file, out_file, report_filename, "");
  9523.   CALC_PCT_DONE(ORIGINAL, ORIGINAL_PCT_DONE);
  9524.   CALC_PCT_DONE(CURRENT, CURRENT_PCT_DONE);
  9525.   while not exit_report_menu loop
  9526.     REPORT_CASE:
  9527.     begin
  9528.       menu_selection := PRINT_REPORT_MENU;
  9529.     
  9530.       case menu_selection is 
  9531.         when 1  =>  VT100.print_report(1) := true;
  9532.                     PARAMETER_DATA_LIST;
  9533.         when 2  =>  PRINT_COMMENTS;
  9534.             VT100.print_report(2) := true;
  9535.         when 3  =>  VT100.print_report(3) := true;
  9536.                     ALL_ELMNT_STATUS_REP;
  9537.         when 4  =>  VT100.print_report(4) := true;
  9538.                     LIST_BY_SUBSYSTEM;
  9539.         when 5  =>  VT100.print_report(5) := true;
  9540.                     LIST_BY_MILESTONE;
  9541.         when 6  =>  VT100.print_report(6) := true;
  9542.                     LIST_BY_PERSON;
  9543.         when 7  =>  VT100.print_report(7) := true;
  9544.                     SUBSYSTEM_SUMMARY;
  9545.         when 8  =>  VT100.print_report(8) := true;
  9546.                     MILESTONE_SUMMARY;
  9547.         when 9  =>  VT100.print_report(9) := true;
  9548.                     WORK_UNITS_PER_SS;
  9549.         when 10 =>  VT100.print_report(10) := true;
  9550.                     PERCENT_COMPLETION(ORIGINAL, ORIGINAL_PCT_DONE); 
  9551.                     PERCENT_COMPLETION(CURRENT, CURRENT_PCT_DONE); 
  9552.         when 11 =>  VT100.print_report(11) := true;
  9553.             DISTRIBUTION_OF_WORK (ORIGINAL);
  9554.             DISTRIBUTION_OF_WORK (CURRENT);
  9555.         when 12 =>  VT100.print_report(12) := true;
  9556.                     COMPLETION_DATE_FOR_MS;
  9557.         when 13 =>  -- print all reports and exit
  9558.             VT100.print_report := (others => true);
  9559.                     PARAMETER_DATA_LIST;
  9560.             PRINT_COMMENTS;
  9561.                     VT100.CLEAR_SCREEN;
  9562.              new_line(10);
  9563.                     put_line("     Writing reports ... ");
  9564.                     ALL_ELMNT_STATUS_REP;
  9565.                     LIST_BY_SUBSYSTEM;
  9566.                     LIST_BY_MILESTONE;
  9567.                     LIST_BY_PERSON;
  9568.                     SUBSYSTEM_SUMMARY;
  9569.                     MILESTONE_SUMMARY;
  9570.                     WORK_UNITS_PER_SS;
  9571.                     PERCENT_COMPLETION(ORIGINAL, ORIGINAL_PCT_DONE); 
  9572.                     PERCENT_COMPLETION(CURRENT, CURRENT_PCT_DONE); 
  9573.             DISTRIBUTION_OF_WORK (ORIGINAL);
  9574.             DISTRIBUTION_OF_WORK (CURRENT);
  9575.                     COMPLETION_DATE_FOR_MS;
  9576.                     exit_report_menu := true;
  9577.         when 14 =>
  9578.           exit_report_menu := true;
  9579.           CLEAR_SCREEN;
  9580.           GOODBYE_MESSAGE;
  9581.         when others =>
  9582.           put_line("Enter a number between 1 and 14. ");
  9583.           delay(0.8);
  9584.       end case;
  9585.  
  9586.     exception
  9587.       when end_error  =>
  9588.         new_line; new_line;
  9589.         put_line("Enter a number between 1 and 14.");
  9590.         delay(0.8);
  9591.       when data_error =>
  9592.         new_line; new_line;
  9593.         put_line("Enter a number between 1 and 14.");
  9594.         delay(0.8);
  9595.       when NAME_ERROR => null;
  9596.     end REPORT_CASE;
  9597.   end loop;
  9598.  
  9599.   -- determine if any reports were written
  9600.   for i in 1..12 loop
  9601.     a_report_printed := a_report_printed or VT100.print_report(i);
  9602.   end loop;
  9603.  
  9604.   if a_report_printed then
  9605.     -- last report printed will always be a list of the reports generated
  9606.     REPORTS_PRINTED_LIST;
  9607.     close(report_file);
  9608.   else
  9609.     delete( report_file );  
  9610.   end if;
  9611.  
  9612.  
  9613. end REPORT_GENERATOR;
  9614. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9615. --calcpct.ada
  9616. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9617. with DATA_PKG; use DATA_PKG;
  9618.  
  9619. separate(TRACKER.REPORT_GENERATOR)
  9620. procedure CALC_PCT_DONE (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE;
  9621.             PCT_DONE : in out PCT_DONE_TYPE) is
  9622. --------------------------------------------------------------------------------
  9623. --|
  9624. --|  NAME:  CALC_PCT_DONE
  9625. --|
  9626. --|  OVERVIEW:
  9627. --|    This procedure calculates the percent complete by subsystem and 
  9628. --|    activity, total percent done by subsystem and activity, total percent
  9629. --|    available at start by subsystem and activity, and the total percent
  9630. --|    complete on the entire project.  The grand total percent done, percent
  9631. --|    available at start, and percent complete on the entire project are
  9632. --|    also calculated.
  9633. --|    
  9634. --|    The percent complete by milestone is also calculated in a similar 
  9635. --|    manner.
  9636. --|
  9637. --|  EXCEPTIONS HANDLED:
  9638. --|    others   an error message is printed and the execution continues
  9639. --|
  9640. --|  HISTORY:
  9641. --|    written by   Bonnie Burkhardt   March 1985
  9642. --|
  9643. --|  NOTES:
  9644. --|    The percentage calculations are performed one subsystem at a time.
  9645. --|    For each subsystem, its element list is walked and the total size,
  9646. --|    total size available at start, and total amount done is tabulated.
  9647. --|    Grand total accumulators are also updated from the subsystem totals.
  9648. --|    From these totals, the percent complete for the subsystem and for
  9649. --|    the entire project is calculated.  
  9650. --|
  9651. --------------------------------------------------------------------------------
  9652.  
  9653.   use EL_LIST_PKG; use SS_LIST_PKG; use PR_LIST_PKG; use AC_LIST_PKG; 
  9654.  
  9655.   ELE_PTR  : element_pointer;
  9656.   AC_PTR   : activity_pointer;
  9657.   AC_INDEX : integer := 0;
  9658.   SS_PTR   : subsystem_pointer;
  9659.   SS_INDEX : integer := 0;
  9660.   PR_PTR   : personnel_pointer;
  9661.   END_LIST : boolean := false;
  9662.  
  9663.   MS_SIZE : array (ms_num_type) of float range 0.0..999_999.0 
  9664.         := (others => 0.0);
  9665.   MS_DONE : array (ms_num_type) of float range 0.0..999_999.0
  9666.       := (others => 0.0);
  9667.   SS_SIZE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  9668.         := (others => 0.0);
  9669.   SS_DONE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0
  9670.       := (others => 0.0);
  9671.   SS_START : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  9672.       := (others => 0.0);
  9673.   GR_TOT_SIZE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  9674.       := (others => 0.0);
  9675.   GR_TOT_DONE : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0
  9676.       := (others => 0.0);
  9677.   GR_TOT_START : array (1..NUM_OF_ACTIVITIES) of float range 0.0..999_999.0 
  9678.       := (others => 0.0);
  9679.   SS_TOT_SIZE     : float range 0.0..999_999.0 := 0.0;
  9680.   SS_TOT_DONE     : float range 0.0..999_999.0 := 0.0;
  9681.   SS_TOT_START    : float range 0.0..999_999.0 := 0.0;
  9682.   GRAND_TOT_SIZE  : float range 0.0..999_999.0 := 0.0;
  9683.   GRAND_TOT_DONE  : float range 0.0..999_999.0 := 0.0;
  9684.   GRAND_TOT_START : float range 0.0..999_999.0 := 0.0;
  9685.  
  9686.   procedure GET_SS_TOTALS is separate;
  9687.  
  9688. begin
  9689.   start_walk(SS_LIST);
  9690.   SS_INDEX := 0;
  9691.   loop
  9692.     walk(SS_LIST, SS_PTR, END_LIST);
  9693.     exit when END_LIST;
  9694.     SS_INDEX := SS_INDEX + 1;
  9695.  
  9696.     GET_SS_TOTALS;
  9697.  
  9698.     -- calculate the percent complete of each activity in the subsystem
  9699.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  9700.       if (SS_DONE(AC_INDEX) > 0.0) and (SS_SIZE(AC_INDEX) > 0.0) then
  9701.     PCT_DONE.BY_SS_AND_AC(SS_INDEX, AC_INDEX) := 100.0 * 
  9702.         SS_DONE(AC_INDEX) / SS_SIZE(AC_INDEX);
  9703.       else
  9704.     PCT_DONE.BY_SS_AND_AC(SS_INDEX, AC_INDEX) := 0.0;
  9705.       end if;
  9706.     end loop;
  9707.  
  9708.     -- calculate the total percent complete for this subsystem
  9709.     if SS_TOT_SIZE > 0.0 then
  9710.       PCT_DONE.BY_SS(SS_INDEX) := 100.0 * SS_TOT_DONE / SS_TOT_SIZE;
  9711.     elsif ORIG_OR_CUR = CURRENT then
  9712.       PCT_DONE.BY_SS(SS_INDEX) := 0.0;
  9713.     else
  9714.       PCT_DONE.BY_SS(SS_INDEX) := 100.0;
  9715.     end if;
  9716.  
  9717.     -- compute the percent complete on contract for this subsystem
  9718.     if SS_TOT_SIZE + SS_TOT_START = 0.0 then
  9719.       PCT_DONE.ENTIRE_BY_SS(SS_INDEX) := 0.0;
  9720.       PCT_DONE.START_BY_SS(SS_INDEX) := 0.0;
  9721.     elsif PCT_DONE.BY_SS(SS_INDEX) < 100.0 then
  9722.       PCT_DONE.ENTIRE_BY_SS(SS_INDEX) := 100.0 * (SS_TOT_DONE + 
  9723.     SS_TOT_START) / (SS_TOT_START + SS_TOT_SIZE);
  9724.       PCT_DONE.START_BY_SS(SS_INDEX) := 100.0 * SS_TOT_START /
  9725.         (SS_TOT_START + SS_TOT_SIZE);
  9726.     else
  9727.       PCT_DONE.ENTIRE_BY_SS(SS_INDEX) := 100.0;
  9728.       PCT_DONE.START_BY_SS(SS_INDEX) := 100.0 * SS_TOT_START /
  9729.         (SS_TOT_START + SS_TOT_SIZE);
  9730.     end if;
  9731.  
  9732.     -- add total work done and total work for each record to the grand total
  9733.     -- accumulators
  9734.     GRAND_TOT_SIZE := GRAND_TOT_SIZE + SS_TOT_SIZE;
  9735.     GRAND_TOT_DONE := GRAND_TOT_DONE + SS_TOT_DONE;
  9736.     GRAND_TOT_START := GRAND_TOT_START + SS_TOT_START;
  9737.  
  9738.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  9739.       GR_TOT_SIZE(AC_INDEX) := GR_TOT_SIZE(AC_INDEX) + SS_SIZE(AC_INDEX);
  9740.       GR_TOT_DONE(AC_INDEX) := GR_TOT_DONE(AC_INDEX) + SS_DONE(AC_INDEX);
  9741.       GR_TOT_START(AC_INDEX) := GR_TOT_START(AC_INDEX) + SS_START(AC_INDEX);
  9742.     end loop;
  9743.   end loop;
  9744.  
  9745.  
  9746.  
  9747.   -- calculate the total percent complete by milestone
  9748.   for MS_INDEX in ms_num_type loop
  9749.     if MS_SIZE(MS_INDEX) > 0.0 then
  9750.     PCT_DONE.BY_MS(MS_INDEX) := 100.0 * MS_DONE(MS_INDEX) 
  9751.         / MS_SIZE(MS_INDEX);
  9752.     end if;
  9753.   end loop;
  9754.  
  9755.   -- calculate the grand total percents by activity
  9756.   for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  9757.     if (GR_TOT_DONE(AC_INDEX) > 0.0) and (GR_TOT_SIZE(AC_INDEX) > 0.0) then
  9758.       PCT_DONE.BY_AC(AC_INDEX) := 100.0 * GR_TOT_DONE(AC_INDEX) / 
  9759.         GR_TOT_SIZE(AC_INDEX);
  9760.     end if;
  9761.  
  9762.     if GR_TOT_START(AC_INDEX) + GR_TOT_SIZE(AC_INDEX) > 0.0 then
  9763.       PCT_DONE.START_BY_AC(AC_INDEX) := 100.0 * GR_TOT_START(AC_INDEX) / 
  9764.         (GR_TOT_START(AC_INDEX) + GR_TOT_SIZE(AC_INDEX));
  9765.     end if;
  9766.  
  9767.     if GR_TOT_START(AC_INDEX) + GR_TOT_SIZE(AC_INDEX) > 0.0 then
  9768.       PCT_DONE.ENTIRE_BY_AC(AC_INDEX) := 100.0 * (GR_TOT_START(AC_INDEX) 
  9769.         + GR_TOT_DONE(AC_INDEX)) / (GR_TOT_START(AC_INDEX) 
  9770.         + GR_TOT_SIZE(AC_INDEX));
  9771.     end if;
  9772.   end loop;
  9773.  
  9774.   -- calculate the grand total percent complete for all activities
  9775.   if GRAND_TOT_SIZE > 0.0 then
  9776.     PCT_DONE.CONTRACT := 100.0 * GRAND_TOT_DONE / GRAND_TOT_SIZE;
  9777.   end if;
  9778.  
  9779.   if GRAND_TOT_START + GRAND_TOT_SIZE > 0.0 THEN
  9780.     PCT_DONE.START := 100.0 * GRAND_TOT_START / (GRAND_TOT_START 
  9781.         + GRAND_TOT_SIZE);
  9782.   end if;
  9783.  
  9784.   if GRAND_TOT_START + GRAND_TOT_SIZE > 0.0 THEN
  9785.     PCT_DONE.ENTIRE := 100.0 * (GRAND_TOT_DONE + GRAND_TOT_START) /
  9786.         (GRAND_TOT_START + GRAND_TOT_SIZE);
  9787.   end if;
  9788.  
  9789. exception
  9790.   when others => put_line("exception raise in CALC_PCT_DONE");  
  9791. end CALC_PCT_DONE;
  9792.  
  9793.  
  9794.  
  9795. separate (TRACKER.REPORT_GENERATOR.CALC_PCT_DONE)
  9796. procedure GET_SS_TOTALS is
  9797. --------------------------------------------------------------------------------
  9798. --|
  9799. --|  NAME:  GET_SS_TOTALS
  9800. --|
  9801. --|  OVERVIEW:
  9802. --|    This procedure computes the total amount of work, the amount done,
  9803. --|    and the amount available at start for a subsystem.
  9804. --|  
  9805. --|  EXCEPTIONS HANDLED:
  9806. --|    others   error message is printed and execution continues
  9807. --|
  9808. --|  HISTORY:
  9809. --|    written by   Bonnie Burkhardt   March 1985
  9810. --------------------------------------------------------------------------------
  9811.  
  9812.   DONE      : float range 0.0..999_999.0 := 0.0;
  9813.   SIZE      : float range 0.0..999_999.0 := 0.0;
  9814.   START     : float range 0.0..999_999.0 := 0.0;
  9815.   ELE_START : float range 0.0..99_999.0;
  9816.   ELE_SIZE  : float range 0.0..99_999.0;
  9817.   MS_INDEX  : ms_num_type;
  9818.  
  9819. begin
  9820.   -- reset subsystem totals
  9821.   SS_TOT_SIZE := 0.0;
  9822.   SS_TOT_DONE := 0.0;
  9823.   SS_TOT_START := 0.0;
  9824.   SS_SIZE := (others => 0.0);
  9825.   SS_DONE := (others => 0.0);
  9826.   SS_START := (others => 0.0);
  9827.  
  9828.   -- set through each subsystem list and calculate each element
  9829.   start_walk(SS_PTR.element_list);
  9830.   loop
  9831.     walk(SS_PTR.element_list, ELE_PTR, END_LIST);
  9832.     exit when END_LIST;
  9833.     MS_INDEX := ELE_PTR.milestone_num;
  9834.  
  9835.     -- compute the size of this element (original or current)
  9836.     if ORIG_OR_CUR = CURRENT then
  9837.       ELE_START := float(ELE_PTR.size_done_at_start);
  9838.       ELE_SIZE := float(ELE_PTR.current_size) - ELE_START;
  9839.     elsif (ELE_PTR.original_size >= ELE_PTR.current_size)
  9840.       or (ELE_PTR.current_size = 0) then
  9841.       ELE_START := float(ELE_PTR.size_done_at_start);
  9842.       ELE_SIZE := float(ELE_PTR.original_size) - ELE_START;
  9843.     else
  9844.       ELE_START := float(ELE_PTR.original_size) * 
  9845.         float(ELE_PTR.size_done_at_start) / float(ELE_PTR.current_size);
  9846.       ELE_SIZE := float(ELE_PTR.original_size) - ELE_START;
  9847.     end if;
  9848.  
  9849.     -- add the amount to the running totals for the subsystem
  9850.     SS_TOT_SIZE := SS_TOT_SIZE + ELE_SIZE * ELE_PTR.complexity;
  9851.     SS_TOT_START := SS_TOT_START + ELE_START * ELE_PTR.complexity;
  9852.  
  9853.     -- calculate the amount of work done for each activity in the subsystem
  9854.     -- and for each milestone
  9855.     start_walk(AC_LIST);
  9856.     AC_INDEX := 0;
  9857.     loop
  9858.       walk(AC_LIST, AC_PTR, END_LIST);
  9859.       exit when END_LIST;
  9860.       AC_INDEX := AC_INDEX + 1;
  9861.       SIZE  := ELE_PTR.complexity * ELE_SIZE * AC_PTR.percent_tot_proj / 100.0;
  9862.       START := ELE_PTR.complexity * ELE_START * AC_PTR.percent_tot_proj / 100.0;
  9863.       DONE := SIZE * AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX)) / 100.0;
  9864.       SS_SIZE(AC_INDEX)  := SS_SIZE(AC_INDEX) + SIZE;
  9865.       SS_START(AC_INDEX) := SS_START(AC_INDEX) + START;
  9866.       SS_DONE(AC_INDEX)  := SS_DONE(AC_INDEX) + DONE;
  9867.       MS_SIZE(MS_INDEX)  := MS_SIZE(MS_INDEX) + SIZE;
  9868.       MS_DONE(MS_INDEX)  := MS_DONE(MS_INDEX) + DONE;
  9869.     end loop;
  9870.   end loop;
  9871.  
  9872.   -- calculate the total amount of work done
  9873.   for AC_INDEX in 1..num_of_activities loop
  9874.     SS_TOT_DONE := SS_TOT_DONE + SS_DONE(AC_INDEX);
  9875.   end loop;
  9876. exception
  9877.   when others => put_line("exception raised in GET_SS_TOTALS.");
  9878. end GET_SS_TOTALS;
  9879. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9880. --rcomments.ada
  9881. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9882. separate(TRACKER.REPORT_GENERATOR)
  9883. procedure PRINT_COMMENTS is
  9884. ----------------------------------------------------------------------
  9885. --|
  9886. --|  NAME:  PRINT_COMMENTS
  9887. --|
  9888. --|  OVERVIEW:
  9889. --|    This procedure asks for the name of the comments file and copies
  9890. --|    the contents of the comments file to the tracker report file.
  9891. --|
  9892. --|  EXCEPTIONS HANDLED:
  9893. --|    none
  9894. --|
  9895. --|  HISTORY:
  9896. --|    written by   May Lee   March 1985
  9897. --|
  9898. ----------------------------------------------------------------------
  9899.  
  9900.   a_char      : character := ' ';  -- y or n
  9901.   dotted_line : string(1..132) := ( others => '=' );
  9902.  
  9903. begin
  9904.   -- determine if a comments file exists
  9905.   put_line(" Do you have a comments file that you would ");
  9906.   put_line(" like to include? ");
  9907.   put(" [Y or N, default=N] :  ");
  9908.   if end_of_line then -- default = n
  9909.     skip_line;
  9910.   else
  9911.     get( a_char );
  9912.     skip_line;
  9913.     if a_char = 'y' or a_char = 'Y' then
  9914.       put("Please enter the name of the comments file : ");
  9915.       get_line( comments_filename,filename_lngth);
  9916.       new_line;
  9917.       open( comments_file, in_file, comments_filename, "");
  9918.  
  9919.       -- print heading to report file
  9920.       new_page( report_file );
  9921.       set_col( report_file, 58 );
  9922.       put_line( report_file, "TRACKER COMMENTS" );
  9923.       put_line( report_file, dotted_line );
  9924.  
  9925.       -- copy the comments file to the report file
  9926.       while not end_of_file( comments_file ) loop
  9927.         get_line( comments_file, line, line_lngth );
  9928.         put_line( report_file, line(1..line_lngth) );
  9929.       end loop;
  9930.       close( comments_file);
  9931.     end if;
  9932.   end if;
  9933. exception
  9934.   when NAME_ERROR => 
  9935.     put(" Error opening "); put(comments_filename(1..filename_lngth)); new_line;
  9936.     put_line(" File does not exist. ");
  9937.     delay 1.5;
  9938.     raise;
  9939.   when others     => 
  9940.     put(" Error opening "); put(comments_filename(1..filename_lngth)); new_line;
  9941.     put_line(" File does not exist. ");
  9942.     delay 1.5;
  9943.     raise NAME_ERROR;
  9944. end PRINT_COMMENTS;
  9945. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9946. --rdatedone.ada
  9947. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  9948. separate(TRACKER.report_generator)
  9949. procedure COMPLETION_DATE_FOR_MS is
  9950. ----------------------------------------------------------------------
  9951. --|
  9952. --|  NAME:  COMPLETION_DATE_FOR_MS
  9953. --|
  9954. --|  OVERVIEW:
  9955. --|    This report is a matrix showing the finsh date of each person in
  9956. --|    relation to each defined milestone.  The personnel are represented
  9957. --|    on the x-axis and the milestones on the y-axis.  There are four
  9958. --|    possible values for a date : "...." means the person is not assigned
  9959. --|    to any elements with that milestone, "99/99/99" means the person did
  9960. --|    not have enough time to finish his work, "DONE" means the person has
  9961. --|    completed all work assigned to him on this milestone, otherwise, a 
  9962. --|    calculated completion date will appear.  The data in the report 
  9963. --|    includes the date each person will complete a milestone, the latest
  9964. --|    date each person will finish all work, the latest date each of the
  9965. --|    milestones will be finished, and the date that the milestone is due.
  9966. --|    If more than 10 people are assigned to the project, the Completion
  9967. --|    Date for Milestone report is repeated until all people have been
  9968. --|    included on a report.
  9969. --|
  9970. --|  EXCEPTIONS HANDLED:
  9971. --|    others   error message printed and execution continues
  9972. --|
  9973. --|  HISTORY:
  9974. --|    written by   Bonnie Burkhardt   March 1985
  9975. --|
  9976. ----------------------------------------------------------------------
  9977.  
  9978.   use CALENDAR;
  9979.   use AC_LIST_PKG; use EL_LIST_PKG; use MS_LIST_PKG; use PR_LIST_PKG;
  9980.  
  9981.   HEADER1         : string (1..132) := (others => ' ');
  9982.   HEADER2         : string (1..132) := (others => ' ');
  9983.   HEADER_LINES    : string (1..132) := (others => ' ');
  9984.  
  9985.   END_LIST        : boolean := false;
  9986.   MAX_PR_ON_PAGE  : constant integer := 10;
  9987.   MS_PTR          : milestone_pointer;
  9988.   PR_INITIALS     : array (1..num_of_people) of pr_init_type 
  9989.           := (others => "  ");
  9990.   PR_INDEX        : integer := 0;
  9991.   PR_PTR          : personnel_pointer;
  9992.   START_PR        : integer := 1;
  9993.   STOP_PR         : integer := num_of_people;
  9994.   TITLE           : constant string := "COMPLETION DATE FOR MILESTONES";
  9995.   DATE_DONE       : array (1..num_of_people) of date_type 
  9996.           := (others => null_date);
  9997.   TOT_DATE_DONE   : array (1..num_of_people) of date_type 
  9998.           := (others =>  null_date);
  9999.   WORK_IS_LEFT    : array (1..num_of_people) of boolean := (others => false);
  10000.   WORK_IS_LEFT_TOT: array (1..num_of_people) of boolean := (others => false);
  10001.   MS_WORK_LEFT    : boolean := false;
  10002.   TOT_WORK_LEFT   : boolean := false;
  10003.   PREV_DATE_DONE  : date_type := null_date;
  10004.   MS_DATE_DONE    : date_type := null_date;
  10005.   MS_TOT_DATE_DONE: date_type := null_date;
  10006.  
  10007.   procedure CALC_DATE_TOTALS   is separate;
  10008.   procedure INIT_DATE_HEADERS  is separate;
  10009.   procedure PRINT_A_DATE (A_DATE        : in date_type;
  10010.               ANY_WORK_LEFT : in boolean := true) is separate;
  10011.   procedure PRINT_MS_DATES     is separate;
  10012.   procedure PRINT_TOT_MS_DATES is separate;
  10013.  
  10014. begin
  10015.   -- initialize the initials array
  10016.   start_walk(PR_LIST);
  10017.   PR_INDEX := 0;
  10018.   loop
  10019.     walk (PR_LIST, PR_PTR, END_LIST);
  10020.     exit when END_LIST;
  10021.     PR_INDEX := PR_INDEX + 1;
  10022.     PR_INITIALS(PR_INDEX) := PR_PTR.initials;
  10023.   end loop;
  10024.     
  10025.  
  10026.   -- print out the report, only 10 personnel will fit on a page
  10027.   loop
  10028.     if STOP_PR - START_PR >= MAX_PR_ON_PAGE then
  10029.       STOP_PR := START_PR + MAX_PR_ON_PAGE - 1;
  10030.     else
  10031.       STOP_PR := num_of_people;
  10032.     end if;
  10033.     INIT_DATE_HEADERS;
  10034.     START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  10035.  
  10036.     -- print out each milestone's completion dates
  10037.     start_walk(MS_LIST);
  10038.     loop
  10039.       walk(MS_LIST, MS_PTR, END_LIST);
  10040.       exit when END_LIST;
  10041.       CALC_DATE_TOTALS;
  10042.       PRINT_MS_DATES;
  10043.     end loop;
  10044.     PRINT_TOT_MS_DATES;
  10045.  
  10046.     START_PR := START_PR + MAX_PR_ON_PAGE;
  10047.     exit when START_PR > num_of_people;
  10048.   end loop;
  10049.  
  10050. exception
  10051.   when others => put_line("exception raised in LIST BY MILESTONE REPORT");
  10052. end COMPLETION_DATE_FOR_MS;
  10053.  
  10054.  
  10055.  
  10056. separate(TRACKER.report_generator.COMPLETION_DATE_FOR_MS)
  10057. procedure INIT_DATE_HEADERS is
  10058. ----------------------------------------------------------------------
  10059. --|  NAME:  INIT_DATE_HEADERS
  10060. --|
  10061. --|  OVERVIEW:
  10062. --|    This procedure initializes all the headers of the completion
  10063. --|    dates by milestone report.
  10064. --|
  10065. --|  EXCEPTIONS HANDLED:
  10066. --|    none
  10067. --|
  10068. --|  HISTORY:
  10069. --|    written by   Bonnie Burkhardt   March 1985
  10070. ----------------------------------------------------------------------
  10071.  
  10072.   DASHES : constant string(1..15) := (others => '-');
  10073.  
  10074. begin
  10075.   HEADER1 := (others => ' ');
  10076.   HEADER2 := (others => ' ');
  10077.   HEADER_LINES := (others => ' ');
  10078.  
  10079.   HEADER1(2..6)     := "MILE-";
  10080.   HEADER1(102..109) := "PREVIOUS";
  10081.   HEADER1(114..120) := "CURRENT";
  10082.   HEADER1(127..129) := "DUE";
  10083.  
  10084.   HEADER2(2..6)     := "STONE";
  10085.   HEADER2(101..110) := "COMPL DATE";
  10086.   HEADER2(113..122) := "COMPL DATE";
  10087.   HEADER2(127..130) := "DATE";
  10088.  
  10089.   HEADER_LINES (2..6)     := DASHES(1..5);
  10090.   HEADER_LINES (101..110) := DASHES(1..10);
  10091.   HEADER_LINES (113..122) := DASHES(1..10);
  10092.   HEADER_LINES (125..132) := DASHES(1..8);
  10093.  
  10094.   -- insert the person's initials into the headers
  10095.   for PR in 0 .. STOP_PR - START_PR loop
  10096.     HEADER2(12+PR*9..13+PR*9)     := PR_INITIALS(PR+START_PR);
  10097.     HEADER_LINES(9+PR*9..16+PR*9) := DASHES(1..8);
  10098.   end loop;
  10099. end INIT_DATE_HEADERS;
  10100.  
  10101.  
  10102.  
  10103. separate(TRACKER.report_generator.COMPLETION_DATE_FOR_MS)
  10104. procedure CALC_DATE_TOTALS is 
  10105. ----------------------------------------------------------------------
  10106. --|
  10107. --|  NAME:  CALC_DATE_TOTALS 
  10108. --|
  10109. --|  OVERVIEW:
  10110. --|    This procedure calculates the total amount of time left by
  10111. --|    MILESTONE and by person.
  10112. --|
  10113. --|  EXCEPTIONS HANDLED:
  10114. --|    none
  10115. --|
  10116. --|  HISTORY:
  10117. --|    written by   Bonnie Burkhardt   March 1985
  10118. --|
  10119. ----------------------------------------------------------------------
  10120.  
  10121.   END_LIST : boolean := false;
  10122.   ELE_PTR  : element_pointer;
  10123.   PR_INDEX : integer := 0;
  10124.   PR_PTR   : personnel_pointer;
  10125.  
  10126. begin
  10127.   WORK_IS_LEFT := (others => false);
  10128.   MS_WORK_LEFT := false;
  10129.   DATE_DONE := (others => null_date);
  10130.   PREV_DATE_DONE := null_date;
  10131.   MS_DATE_DONE := null_date;
  10132.  
  10133.   PR_INDEX := 0;
  10134.   start_walk(PR_LIST);
  10135.   loop
  10136.     walk(PR_LIST, PR_PTR, END_LIST);
  10137.     exit when END_LIST;
  10138.     PR_INDEX := PR_INDEX + 1;
  10139.  
  10140.     -- find the latest completion date for each element that has
  10141.     -- this milestone and this person
  10142.     start_walk(PR_PTR.element_list);
  10143.     loop
  10144.       walk(PR_PTR.element_list, ELE_PTR, END_LIST);
  10145.       exit when END_LIST;
  10146.  
  10147.       if (ELE_PTR.milestone_num = MS_PTR.number) then
  10148.     -- check if the current date done should be updated
  10149.     if ELE_PTR.more_than_one_person then
  10150.       for AC_INDEX in 1..num_of_activities loop
  10151.         if (ELE_PTR.people_initials(AC_INDEX) = PR_PTR.initials) and
  10152.            ((ELE_PTR.dates_done(AC_INDEX) = underflow_date) or 
  10153.         (DATE_DONE(pr_index) = null_date)    or
  10154.         (ELE_PTR.dates_done(AC_INDEX) > DATE_DONE(pr_index)) ) then
  10155.           DATE_DONE(pr_index) := ELE_PTR.dates_done(AC_INDEX);
  10156.           WORK_IS_LEFT(pr_index) := WORK_IS_LEFT(pr_index) or
  10157.         (ELE_PTR.hours_left(AC_INDEX) > 0.0);
  10158.           MS_WORK_LEFT := MS_WORK_LEFT or WORK_IS_LEFT(pr_index);
  10159.         end if;
  10160.       end loop;
  10161.       -- check if the total milestone completion date should be updated
  10162.       if ELE_PTR.date_done > MS_DATE_DONE then
  10163.         MS_DATE_DONE := ELE_PTR.date_done;
  10164.       end if;
  10165.     elsif (ELE_PTR.date_done = underflow_date) or 
  10166.         (DATE_DONE(pr_index) = null_date)    or
  10167.         (ELE_PTR.date_done > DATE_DONE(pr_index)) then
  10168.         DATE_DONE(pr_index) := ELE_PTR.date_done;
  10169.       -- check if the total milestone completion date should be updated
  10170.       if ELE_PTR.date_done > MS_DATE_DONE then
  10171.         MS_DATE_DONE := ELE_PTR.date_done;
  10172.       end if;
  10173.       WORK_IS_LEFT(pr_index) := WORK_IS_LEFT(pr_index) or
  10174.         (ELE_PTR.hours_to_complete > 0.0);
  10175.       MS_WORK_LEFT := MS_WORK_LEFT or WORK_IS_LEFT(pr_index);
  10176.     end if;
  10177.     -- update the milestone's previous date done
  10178.     if  (ELE_PTR.prev_date_done = underflow_date) or 
  10179.         (PREV_DATE_DONE = null_date) or
  10180.         (ELE_PTR.prev_date_done > PREV_DATE_DONE) then
  10181.         PREV_DATE_DONE := ELE_PTR.prev_date_done;
  10182.     end if;
  10183.       end if;
  10184.     end loop;
  10185.  
  10186.     -- update the grand total work_is_remaining flag for each person
  10187.     WORK_IS_LEFT_TOT(pr_index) := WORK_IS_LEFT_TOT(pr_index) or 
  10188.                   WORK_IS_LEFT(pr_index);
  10189.     TOT_WORK_LEFT := TOT_WORK_LEFT or WORK_IS_LEFT_TOT(pr_index);
  10190.  
  10191.     -- update the grand total date done by person
  10192.     if (DATE_DONE(pr_index) = underflow_date) or 
  10193.        (TOT_DATE_DONE(pr_index) = null_date)  or
  10194.        (DATE_DONE(pr_index) > TOT_DATE_DONE(pr_index)) then
  10195.       TOT_DATE_DONE(pr_index) := DATE_DONE(pr_index);
  10196.       if TOT_DATE_DONE(pr_index) > MS_TOT_DATE_DONE then
  10197.     MS_TOT_DATE_DONE := TOT_DATE_DONE(pr_index);
  10198.       end if;
  10199.     end if;
  10200.   end loop;
  10201. end CALC_DATE_TOTALS;
  10202.  
  10203.  
  10204.  
  10205. separate(TRACKER.report_generator.COMPLETION_DATE_FOR_MS)
  10206. procedure PRINT_A_DATE (A_DATE         : in date_type; 
  10207.             ANY_WORK_LEFT : in boolean := true) is 
  10208. ----------------------------------------------------------------------
  10209. --|  NAME:  PRINT_A_DATE
  10210. --|
  10211. --|  OVERVIEW:
  10212. --|    This procedure prints a date to the report_file.  The string
  10213. --|    "...." is printed for a null date and the string "99/99/99"
  10214. --|    is printed for an underflow date.  If the date is neither an overflow
  10215. --|    date or a null date, the ANY_WORK_LEFT flag is checked to see if this 
  10216. --|    entity is actually completed (ANY_WORK_LEFT = false), and a "DONE" 
  10217. --|    printed instead of the actual completion date.
  10218. --|
  10219. --|  EXCEPTIONS HANDLED:
  10220. --|    none
  10221. --|
  10222. --|  HISTORY:
  10223. --|    written by   Bonnie Burkhardt   March 1985
  10224. ----------------------------------------------------------------------
  10225.  
  10226. begin
  10227.   if A_DATE = null_date then
  10228.     put(report_file, "  ....  "); 
  10229.   elsif A_DATE = underflow_date then
  10230.     put(report_file, "99/99/99"); 
  10231.   elsif not ANY_WORK_LEFT then
  10232.     put(report_file, "  DONE  "); 
  10233.   else
  10234.     put(report_file, A_DATE.month,2); put(report_file, '/'); 
  10235.     put(report_file, A_DATE.day,2);   put(report_file, '/'); 
  10236.     put(report_file, A_DATE.year mod 100,2); 
  10237.   end if;
  10238. end PRINT_A_DATE;
  10239.  
  10240.  
  10241.  
  10242. separate(TRACKER.report_generator.COMPLETION_DATE_FOR_MS)
  10243. procedure PRINT_MS_DATES is
  10244. ----------------------------------------------------------------------
  10245. --|
  10246. --|  NAME:  PRINT_MS_DATES
  10247. --|
  10248. --|  OVERVIEW:
  10249. --|    This procedure prints a milestone completion date line. This line
  10250. --|    includes the date complete for each person in the range
  10251. --|    START_PR..STOP_PR.  If a person is not assigned to an element,
  10252. --|    in the milestone, a "...." is printed.  If there is not enough time 
  10253. --|    for the person to finish working on the milestone, "99/99/99" is
  10254. --|    printed.  If the person is finished working on the mileston, "DONE"
  10255. --|    is printed.  Otherwise the completion date is printed.
  10256. --|
  10257. --|  EXCEPTIONS HANDLED:
  10258. --|    none
  10259. --|
  10260. --|  HISTORY:
  10261. --|    written by   Bonnie Burkhardt   March 1985
  10262. --|
  10263. ----------------------------------------------------------------------
  10264.  
  10265. begin
  10266.   -- print out this milestone 
  10267.   set_col(report_file, 3); put(report_file, MS_PTR.number,3);
  10268.   set_col(report_file, 9);
  10269.   for PR_INDEX in START_PR .. STOP_PR loop
  10270.     PRINT_A_DATE (DATE_DONE(pr_index), WORK_IS_LEFT(pr_index));
  10271.     put(report_file," ");
  10272.   end loop;
  10273.  
  10274.   -- output milestone total dates
  10275.   set_col(report_file, 102); PRINT_A_DATE(PREV_DATE_DONE);
  10276.   set_col(report_file, 114); PRINT_A_DATE(MS_DATE_DONE, MS_WORK_LEFT);
  10277.   set_col(report_file, 125); PRINT_A_DATE(MS_PTR.due_date);
  10278.   new_line(report_file);
  10279. end PRINT_MS_DATES;
  10280.  
  10281.  
  10282.  
  10283. separate(TRACKER.report_generator.COMPLETION_DATE_FOR_MS)
  10284. procedure PRINT_TOT_MS_DATES is 
  10285. ----------------------------------------------------------------------
  10286. --|  NAME:  PRINT_TOT_MS_DATES
  10287. --|
  10288. --|  OVERVIEW:
  10289. --|    This procedure prints the total milestone completion date line. This 
  10290. --|    line includes the date complete for each person in the range
  10291. --|    START_PR..STOP_PR.  If a person is not assigned to an element,
  10292. --|    a "...." is printed.  If there is not enough time to complete the
  10293. --|    milestone, "99/99/99" is printed.  If the person is finished, "DONE"
  10294. --|    is printed, otherwise the completion date is printed.
  10295. --|
  10296. --|  EXCEPTIONS HANDLED:
  10297. --|    none
  10298. --|
  10299. --|  HISTORY:
  10300. --|    written by   Bonnie Burkhardt   March 1985
  10301. ----------------------------------------------------------------------
  10302.  
  10303. begin
  10304.   -- output total dates
  10305.   set_col(report_file, 9); put(report_file, HEADER_LINES(9..132)); 
  10306.   new_line(report_file);
  10307.   set_col(report_file, 2); put(report_file, "TOTAL:");
  10308.   set_col(report_file, 9);
  10309.   for PR_INDEX in START_PR .. STOP_PR loop
  10310.     PRINT_A_DATE (TOT_DATE_DONE(pr_index), WORK_IS_LEFT_TOT(pr_index));
  10311.     put(report_file," ");
  10312.   end loop;
  10313.  
  10314.   set_col(report_file, 114); PRINT_A_DATE(MS_TOT_DATE_DONE, TOT_WORK_LEFT);
  10315.   new_line(report_file,2);
  10316. end PRINT_TOT_MS_DATES;
  10317. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10318. --rlistel.ada
  10319. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10320. separate(TRACKER.report_generator)
  10321. procedure ALL_ELMNT_STATUS_REP is
  10322. ----------------------------------------------------------------------
  10323. --|  NAME:  ALL_ELMNT_STATUS_REP
  10324. --|
  10325. --|  OVERVIEW:
  10326. --|    This report lists all of the element data, including the total 
  10327. --|    original size, the total current size, and the average complexity. 
  10328. --|
  10329. --|  EXCEPTIONS HANDLED:
  10330. --|    others   an error message is printed and execution continues
  10331. --|
  10332. --|  HISTORY:
  10333. --|    written by   Bonnie Burkhardt   March 1985
  10334. ----------------------------------------------------------------------
  10335.  
  10336.   use AC_LIST_PKG; use EL_LIST_PKG;
  10337.  
  10338.   DASHES  : string (1..15)  := (others => '-');
  10339.   HEADER1 : string (1..132) := (others => ' ');
  10340.   HEADER2 : string (1..132) := (others => ' ');
  10341.   HEADER_LINES  : string (1..132) := (others => ' ');
  10342.  
  10343.   AC_INDEX   : integer := 0;
  10344.   AC_PTR     : activity_pointer;
  10345.   END_LIST   : boolean := false;
  10346.   ELE_COUNT  : integer := 0;
  10347.   ELE_PTR    : element_pointer;
  10348.   LINE_COUNT : integer := 0;
  10349.   TITLE      : constant string := "ALL ELEMENT STATUS REPORT";
  10350.   TOT_CURRNT : integer range 0..9_999_999 := 0;
  10351.   TOT_EQ_NEW : integer range 0..9_999_999 := 0;
  10352.   TOT_ORIG   : integer range 0..9_999_999 := 0;
  10353.   TOT_CPXY   : float := 0.0;
  10354.  
  10355.   procedure INIT_EL_HEADERS is separate;
  10356.   procedure PRINT_EL is separate;
  10357.  
  10358. begin
  10359.   INIT_EL_HEADERS;
  10360.     
  10361.   START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  10362.   start_walk(EL_LIST);
  10363.   WALK_ELEMENTS:
  10364.   loop
  10365.     walk(EL_LIST, ELE_PTR, END_LIST);
  10366.     if END_LIST then 
  10367.       -- end of list, write out totals
  10368.       if (ELE_COUNT > 0) then
  10369.         set_col(report_file, 90); put(report_file, HEADER_LINES(90..132));
  10370.         new_line(report_file);
  10371.         set_col(report_file, 74); put(report_file, "TOTALS");
  10372.         set_col(report_file, 90); put(report_file, TOT_ORIG,7);
  10373.         set_col(report_file, 99); put(report_file, TOT_CURRNT,7);
  10374.         set_col(report_file, 108); put(report_file, TOT_EQ_NEW,7);
  10375.         if ELE_COUNT > 0 then
  10376.         set_col(report_file, 127); 
  10377.          put(report_file, TOT_CPXY/float(ELE_COUNT),2,3,0);
  10378.         end if;
  10379.         new_line(report_file);
  10380.       end if;
  10381.       exit WALK_ELEMENTS;
  10382.     end if;
  10383.  
  10384.     -- update running totals
  10385.     ELE_COUNT  := ELE_COUNT + 1;
  10386.     TOT_CURRNT := TOT_CURRNT + ELE_PTR.current_size;
  10387.     TOT_EQ_NEW := TOT_EQ_NEW - ELE_PTR.size_done_at_start + ELE_PTR.current_size;
  10388.     TOT_ORIG   := TOT_ORIG + ELE_PTR.original_size;
  10389.     TOT_CPXY   := TOT_CPXY + ELE_PTR.complexity;
  10390.  
  10391.     PRINT_EL;
  10392.  
  10393.     -- check to see if another page is needed
  10394.     LINE_COUNT := LINE_COUNT + 1;
  10395.     if LINE_COUNT >= MAX_DATA_LINES-2 then
  10396.       START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  10397.       LINE_COUNT := 0;
  10398.     end if;
  10399.   end loop WALK_ELEMENTS;
  10400. exception
  10401.   when others => put_line("exception raised in ALL ELEMENT STATUS REPORT");
  10402. end ALL_ELMNT_STATUS_REP;
  10403.  
  10404.  
  10405.  
  10406.  
  10407. separate(TRACKER.report_generator.ALL_ELMNT_STATUS_REP)
  10408.  
  10409. procedure INIT_EL_HEADERS is 
  10410. ----------------------------------------------------------------------
  10411. --|  NAME:  INIT_EL_HEADERS 
  10412. --|
  10413. --|  OVERVIEW:
  10414. --|    This report initializes the headers for the All Element Status
  10415. --|    report.
  10416. --|
  10417. --|  EXCEPTIONS HANDLED:
  10418. --|    none
  10419. --|
  10420. --|  HISTORY:
  10421. --|    written by   Bonnie Burkhardt   March 1985
  10422. ----------------------------------------------------------------------
  10423.  
  10424. begin
  10425.   -- initialize the headers
  10426.   HEADER1(68..83)   := "** ACTIVITIES **";
  10427.   HEADER1(90..96)   := "ORIGINL";
  10428.   HEADER1(99..105)  := "CURRENT";
  10429.   HEADER1(108..114) := "EQ. NEW";
  10430.   HEADER1(117..124) := "SIZE LST";
  10431.  
  10432.   HEADER2(2..3)     := "MS";
  10433.   HEADER2(5..6)     := "PR";
  10434.   HEADER2(8..16)    := "SUBSYSTEM";
  10435.   HEADER2(20..30)   := "DESCRIPTION";
  10436.   HEADER2(56..60)   := "ABREV";
  10437.   HEADER2(63..64)   := "RP";
  10438.   HEADER2(90..93)   := "SIZE";
  10439.   HEADER2(99..102)  := "SIZE";
  10440.   HEADER2(108..111) := "SIZE";
  10441.   HEADER2(117..124) := "VERIFIED";
  10442.   HEADER2(127..132) := "COMPXY";
  10443.  
  10444.   HEADER_LINES (2..3)     := DASHES(1..2);
  10445.   HEADER_LINES (5..6)     := DASHES(1..2);
  10446.   HEADER_LINES (8..16)    := DASHES(1..9);
  10447.   HEADER_LINES (20..30)   := DASHES(1..11);
  10448.   HEADER_LINES (56..61)   := DASHES(1..6);
  10449.   HEADER_LINES (63..64)   := DASHES(1..2);
  10450.   HEADER_LINES (90..96)   := DASHES(1..7);
  10451.   HEADER_LINES (99..105)  := DASHES(1..7);
  10452.   HEADER_LINES (108..114) := DASHES(1..7);
  10453.   HEADER_LINES (117..124) := DASHES(1..8);
  10454.   HEADER_LINES (127..132) := DASHES(1..6);
  10455.  
  10456.   -- initialize the header for the activity data
  10457.   start_walk(AC_LIST);
  10458.   AC_INDEX := 0;
  10459.   loop
  10460.     walk (AC_LIST, AC_PTR, END_LIST);
  10461.     exit when END_LIST;
  10462.     HEADER2(67+2*AC_INDEX) := AC_PTR.name(1);
  10463.     HEADER_LINES(67+2*AC_INDEX) := '-';
  10464.     AC_INDEX := AC_INDEX + 1;
  10465.   end loop;
  10466. end INIT_EL_HEADERS;
  10467.  
  10468.  
  10469. separate(TRACKER.report_generator.ALL_ELMNT_STATUS_REP)
  10470. procedure PRINT_EL is 
  10471. ----------------------------------------------------------------------
  10472. --|  NAME:  PRINT_EL
  10473. --|
  10474. --|  OVERVIEW:
  10475. --|    This report prints out an element to the report file.  If the 
  10476. --|    element has more than one person assigned to it, one additional
  10477. --|    line is printed for each extra person.  This line lists only the 
  10478. --|    initials of the person assigned and the percent complete by 
  10479. --|    activity.  If the person is not assigned to a particular activity,
  10480. --|    a '*' is printed in that column.
  10481. --|
  10482. --|  EXCEPTIONS HANDLED:
  10483. --|    none
  10484. --|
  10485. --|  HISTORY:
  10486. --|    written by   Bonnie Burkhardt   March 1985
  10487. ----------------------------------------------------------------------
  10488.  
  10489.   ALL_PR_PRINTED    : constant array (1..num_of_activities) of boolean 
  10490.             := (others => true);
  10491.   PR_PRINTING_DONE  : array (1..num_of_activities) of boolean 
  10492.             := (others => false);
  10493.   NEXT_PERSON        : integer range 1..num_of_activities := 1;
  10494.   DONE            : boolean := true;
  10495.  
  10496. begin
  10497.   set_col(report_file, 2);  put(report_file, ELE_PTR.milestone_num,2);
  10498.   set_col(report_file, 5);  put(report_file, ELE_PTR.priority,2);
  10499.   set_col(report_file, 8);  put(report_file, ELE_PTR.subsystem_name);
  10500.   set_col(report_file, 20); put(report_file, ELE_PTR.description);
  10501.   set_col(report_file, 56); put(report_file, ELE_PTR.desc_key);
  10502.   if not ELE_PTR.more_than_one_person then
  10503.     set_col(report_file, 63); put(report_file, ELE_PTR.person_initials);
  10504.     set_col(report_file, 67); 
  10505.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop 
  10506.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10507.       put(report_file,' ');
  10508.     end loop;
  10509.   else  -- print out the first person assigned
  10510.     set_col(report_file, 63); 
  10511.     put(report_file, ELE_PTR.people_initials(1) );
  10512.     set_col(report_file, 67); 
  10513.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  10514.       if ELE_PTR.people_initials(AC_INDEX) = ELE_PTR.people_initials(1) then
  10515.     put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10516.     put(report_file,' ');
  10517.         PR_PRINTING_DONE(AC_INDEX) := true;
  10518.       else
  10519.     put(report_file, "* ");
  10520.       end if;
  10521.     end loop;
  10522.   end if;
  10523.   set_col(report_file, 91);  put(report_file, ELE_PTR.original_size,6);
  10524.   set_col(report_file, 100); put(report_file, ELE_PTR.current_size,6);
  10525.   set_col(report_file, 109); 
  10526.     put(report_file, ELE_PTR.current_size - ELE_PTR.size_done_at_start,6);
  10527.   set_col(report_file, 117); 
  10528.     put(report_file, ELE_PTR.date_size_verified.month,2); 
  10529.     put(report_file,'/'); 
  10530.     put(report_file, ELE_PTR.date_size_verified.day,2); 
  10531.     put(report_file,'/');
  10532.     put(report_file, ELE_PTR.date_size_verified.year mod 100,2);
  10533.   set_col(report_file, 127); put(report_file, ELE_PTR.complexity,2,3,0);
  10534.   new_line(report_file);
  10535.  
  10536.   -- print out additional lines if the element is assigned to more than
  10537.   -- one person
  10538.   if ELE_PTR.more_than_one_person then
  10539.     loop
  10540.       DONE := true;
  10541.       for AC_INDEX in 1..num_of_activities loop
  10542.         DONE := DONE and PR_PRINTING_DONE(AC_INDEX);
  10543.       end loop;
  10544.       exit when DONE;
  10545.  
  10546.       -- find the next person to be printed
  10547.       NEXT_PERSON := 1;
  10548.       while PR_PRINTING_DONE (NEXT_PERSON) loop
  10549.         NEXT_PERSON := NEXT_PERSON + 1;
  10550.       end loop;
  10551.       set_col(report_file, 63); 
  10552.       put(report_file, ELE_PTR.people_initials(NEXT_PERSON) );
  10553.  
  10554.       -- print out the activity percent complete for this person
  10555.       set_col(report_file, 67); 
  10556.       for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  10557.         if ELE_PTR.people_initials(AC_INDEX) = 
  10558.         ELE_PTR.people_initials(NEXT_PERSON) then
  10559.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10560.       put(report_file,' ');
  10561.       PR_PRINTING_DONE(AC_INDEX) := true;
  10562.     else
  10563.       put(report_file, "* ");
  10564.         end if;
  10565.       end loop;
  10566.  
  10567.       LINE_COUNT := LINE_COUNT + 1;
  10568.       new_line(report_file);
  10569.     end loop;
  10570.   end if;
  10571.   PR_PRINTING_DONE := (others => false);
  10572. end PRINT_EL;
  10573. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10574. --rlistms.ada
  10575. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10576. separate(TRACKER.report_generator)
  10577. procedure LIST_BY_MILESTONE is
  10578. ----------------------------------------------------------------------
  10579. --|  NAME:  LIST_BY_MILESTONE
  10580. --|
  10581. --|  OVERVIEW:
  10582. --|    One report is produced for each milestone which lists all the
  10583. --|    elements belonging to that milestone.  The element data includes
  10584. --|    the remaining man-hours of work to complete each entity, the total
  10585. --|    original size, the total current size, the average complexity,
  10586. --|    and the total remaining man-hours of work to complete each
  10587. --|    milestone.  
  10588. --|
  10589. --|  EXCEPTIONS HANDLED:
  10590. --|    others   an error message is printed and execution continues
  10591. --|
  10592. --|  HISTORY:
  10593. --|    written by   Bonnie Burkhardt   March 1985
  10594. ----------------------------------------------------------------------
  10595.  
  10596.   use AC_LIST_PKG; use EL_LIST_PKG; use MS_LIST_PKG; use CALENDAR;
  10597.  
  10598.   HEADER1 : string (1..132) := (others => ' ');
  10599.   HEADER2 : string (1..132) := (others => ' ');
  10600.   HEADER_LINES  : string (1..132) := (others => ' ');
  10601.  
  10602.   AC_INDEX   : integer := 0;
  10603.   AC_PTR     : activity_pointer;
  10604.   DATE_STRING: string (1..8) := "  /  /  ";
  10605.   END_LIST   : boolean := false;
  10606.   ELE_COUNT  : integer := 0;
  10607.   ELE_IN_MS  : integer := 0;
  10608.   ELE_PTR    : element_pointer;
  10609.   LINE_COUNT : integer := 0;
  10610.   MS_INDEX   : integer := 0;
  10611.   MS_PTR     : milestone_pointer;
  10612.   MS_STRING  : string (1..2) := "  ";
  10613.   TITLE      : constant string := "LIST BY MILESTONE REPORT";
  10614.   TOT_CURRNT : integer range 0..9_999_999 := 0;
  10615.   TOT_EQ_NEW : integer range 0..9_999_999 := 0;
  10616.   TOT_ORIG   : integer range 0..9_999_999 := 0;
  10617.   TOT_CPXY   : float := 0.0;
  10618.   TOT_HOURS  : float := 0.0;
  10619.  
  10620.   procedure INIT_HEADERS is separate;
  10621.   procedure PRINT_AN_ELEMENT is separate;
  10622.   procedure PRINT_MS_TOTAL is separate;
  10623.  
  10624. begin
  10625.   INIT_HEADERS;
  10626.     
  10627.   start_walk(MS_LIST);
  10628.   loop
  10629.     walk(MS_LIST, MS_PTR, END_LIST);
  10630.     exit when END_LIST;
  10631.     LINE_COUNT := 0;
  10632.  
  10633.     -- create the subtitle string
  10634.     put (MS_STRING, MS_PTR.NUMBER);
  10635.     if MS_PTR.due_date = null_date then
  10636.       START_PAGE(TITLE, "Milestone # " & MS_STRING & " is due on a null date"
  10637.       & " -- " & MS_PTR.description ,HEADER1,HEADER2,HEADER_LINES);
  10638.     else
  10639.       put (DATE_STRING(1..2), MS_PTR.due_date.month);
  10640.       put (DATE_STRING(4..5), MS_PTR.due_date.day);
  10641.       put (DATE_STRING(7..8), MS_PTR.due_date.year mod 100);
  10642.       START_PAGE(TITLE, "Milestone # " & MS_STRING & " is due " & DATE_STRING 
  10643.       & " -- " & MS_PTR.description ,HEADER1,HEADER2,HEADER_LINES);
  10644.     end if;
  10645.     start_walk(MS_PTR.element_list);
  10646.     ELE_IN_MS := 0;
  10647.     loop
  10648.       walk(MS_PTR.element_list, ELE_PTR, END_LIST);
  10649.   
  10650.       -- if end of list, print out totals
  10651.       if END_LIST then
  10652.         if (ELE_IN_MS > 0) then
  10653.           PRINT_MS_TOTAL;
  10654.         end if;
  10655.         exit;
  10656.       end if;
  10657.  
  10658.       -- update running totals
  10659.       ELE_COUNT  := ELE_COUNT + 1;
  10660.       TOT_CURRNT := TOT_CURRNT + ELE_PTR.current_size;
  10661.       TOT_EQ_NEW := TOT_EQ_NEW - ELE_PTR.size_done_at_start + ELE_PTR.current_size;
  10662.       TOT_ORIG   := TOT_ORIG + ELE_PTR.original_size;
  10663.       TOT_CPXY   := TOT_CPXY + ELE_PTR.complexity;
  10664.       TOT_HOURS  := TOT_HOURS + ELE_PTR.hours_to_complete;
  10665.  
  10666.       PRINT_AN_ELEMENT;
  10667.  
  10668.       ELE_IN_MS := ELE_IN_MS + 1;
  10669.       LINE_COUNT := LINE_COUNT + 1;
  10670.       if LINE_COUNT >= MAX_DATA_LINES-2 then
  10671.     if MS_PTR.due_date = null_date then
  10672.       START_PAGE(TITLE, "Milestone # " & MS_STRING & " is due on a null date"
  10673.           & " -- " & MS_PTR.description ,HEADER1,HEADER2,HEADER_LINES);
  10674.     else
  10675.       START_PAGE(TITLE, "Milestone # " & MS_STRING & " is due " & DATE_STRING 
  10676.           & " -- " & MS_PTR.description ,HEADER1,HEADER2,HEADER_LINES);
  10677.     end if;
  10678.         LINE_COUNT := 0;
  10679.       end if;
  10680.     end loop;
  10681.   end loop;
  10682. exception
  10683.   when others => put_line("exception raised in LIST BY MILESTONE REPORT");
  10684. end LIST_BY_MILESTONE;
  10685.  
  10686.  
  10687.  
  10688. separate(TRACKER.report_generator.LIST_BY_MILESTONE)
  10689. procedure INIT_HEADERS is
  10690. ----------------------------------------------------------------------
  10691. --|  NAME:  INIT_HEADERS
  10692. --|
  10693. --|  OVERVIEW:
  10694. --|    This procedure initializes all the headers of this List by 
  10695. --|    Milestone Report.
  10696. --|
  10697. --|  EXCEPTIONS HANDLED:
  10698. --|    others   an error message is printed and execution continues
  10699. --|
  10700. --|  HISTORY:
  10701. --|    written by   Bonnie Burkhardt   March 1985
  10702. ----------------------------------------------------------------------
  10703.  
  10704.   DASHES  : string (1..15)  := (others => '-');
  10705.  
  10706. begin
  10707.   -- initialize the headers
  10708.   HEADER1(65..80) := "** ACTIVITIES **";
  10709.   HEADER1(84..90) := "ORIGINL";
  10710.   HEADER1(93..99) := "CURRENT";
  10711.   HEADER1(102..108) := "EQ. NEW";
  10712.   HEADER1(110..117) := "SIZE LST";
  10713.   HEADER1(126..132) := "MAN-HRS";
  10714.  
  10715.   HEADER2(2..3) := "PR";
  10716.   HEADER2(5..13) := "SUBSYSTEM";
  10717.   HEADER2(17..27) := "DESCRIPTION";
  10718.   HEADER2(53..57) := "ABREV";
  10719.   HEADER2(60..61) := "RP";
  10720.   HEADER2(85..88) := "SIZE";
  10721.   HEADER2(94..97) := "SIZE";
  10722.   HEADER2(103..106) := "SIZE";
  10723.   HEADER2(110..117) := "VERIFIED";
  10724.   HEADER2(119..124) := "COMPXY";
  10725.   HEADER2(126..132) := "TO COMP";
  10726.  
  10727.   HEADER_LINES (2..3) := DASHES (1..2);
  10728.   HEADER_LINES (5..13) := DASHES (1..9);
  10729.   HEADER_LINES (17..27) := DASHES (1..11);
  10730.   HEADER_LINES (53..58) := DASHES (1..6);
  10731.   HEADER_LINES (60..61) := DASHES (1..2);
  10732.   HEADER_LINES (84..90) := DASHES (1..7);
  10733.   HEADER_LINES (93..99) := DASHES (1..7);
  10734.   HEADER_LINES (102..108) := DASHES (1..7);
  10735.   HEADER_LINES (110..117) := DASHES (1..8);
  10736.   HEADER_LINES (119..124) := DASHES (1..6);
  10737.   HEADER_LINES (126..132) := DASHES (1..7);
  10738.  
  10739.   -- initialize the header for the activity data
  10740.   start_walk(AC_LIST);
  10741.   AC_INDEX := 0;
  10742.   loop
  10743.     walk (AC_LIST, AC_PTR, END_LIST);
  10744.     exit when END_LIST;
  10745.     HEADER2(64+2*AC_INDEX) := AC_PTR.name(1);
  10746.     HEADER_LINES(64+2*AC_INDEX) := '-';
  10747.     AC_INDEX := AC_INDEX + 1;
  10748.   end loop;
  10749. exception
  10750.   when others => put_line("exception raise in MS INIT_HEADERS");
  10751. end INIT_HEADERS;
  10752.  
  10753.  
  10754.  
  10755. separate(TRACKER.report_generator.LIST_BY_MILESTONE)
  10756. procedure PRINT_AN_ELEMENT is
  10757. ----------------------------------------------------------------------
  10758. --|  NAME:  PRINT_AN_ELEMENT
  10759. --|
  10760. --|  OVERVIEW:
  10761. --|    This procedure prints out an element line. This line of data 
  10762. --|    includes the remaining man-hours of work to complete this
  10763. --|    element, the original size, the current size, the complexity, and 
  10764. --|    the remaining man-hours of work to completion.  
  10765. --|
  10766. --|  EXCEPTIONS HANDLED:
  10767. --|    others   an error message is printed and execution continues
  10768. --|
  10769. --|  HISTORY:
  10770. --|    written by   Bonnie Burkhardt   March 1985
  10771. ----------------------------------------------------------------------
  10772.  
  10773.   ALL_PR_PRINTED    : constant array (1..num_of_activities) of boolean 
  10774.             := (others => true);
  10775.   PR_PRINTING_DONE  : array (1..num_of_activities) of boolean 
  10776.             := (others => false);
  10777.   NEXT_PERSON        : integer range 1..num_of_activities := 1;
  10778.   DONE            : boolean := true;
  10779.  
  10780. begin
  10781.   -- print out element
  10782.   set_col(report_file, 2); put(report_file, ELE_PTR.priority,2);
  10783.   set_col(report_file, 5); put(report_file, ELE_PTR.subsystem_name);
  10784.   set_col(report_file, 17); put(report_file, ELE_PTR.description);
  10785.   set_col(report_file, 53); put(report_file, ELE_PTR.desc_key);
  10786.   if not ELE_PTR.more_than_one_person then
  10787.     set_col(report_file, 60); put(report_file, ELE_PTR.person_initials);
  10788.     set_col(report_file, 64); 
  10789.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop 
  10790.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10791.       put(report_file,' ');
  10792.     end loop;
  10793.   else  -- print out the first person assigned
  10794.     set_col(report_file, 60); 
  10795.     put(report_file, ELE_PTR.people_initials(1) );
  10796.     set_col(report_file, 64); 
  10797.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  10798.       if ELE_PTR.people_initials(AC_INDEX) = ELE_PTR.people_initials(1) then
  10799.     put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10800.     put(report_file,' ');
  10801.         PR_PRINTING_DONE(AC_INDEX) := true;
  10802.       else
  10803.     put(report_file, "* ");
  10804.       end if;
  10805.     end loop;
  10806.   end if;
  10807.   set_col(report_file, 85); put(report_file, ELE_PTR.original_size,6);
  10808.   set_col(report_file, 94); put(report_file, ELE_PTR.current_size,6);
  10809.   set_col(report_file, 103); 
  10810.     put(report_file, ELE_PTR.current_size - ELE_PTR.size_done_at_start,6);
  10811.   set_col(report_file, 110); 
  10812.     put(report_file, ELE_PTR.date_size_verified.month,2); 
  10813.     put(report_file,'/'); 
  10814.     put(report_file, ELE_PTR.date_size_verified.day,2); 
  10815.     put(report_file,'/');
  10816.     put(report_file, ELE_PTR.date_size_verified.year mod 100,2);
  10817.   set_col(report_file, 119); put(report_file, ELE_PTR.complexity,3,2,0);
  10818.   set_col(report_file, 126); put(report_file, ELE_PTR.hours_to_complete,5,1,0);
  10819.   new_line(report_file);
  10820.  
  10821.   -- print out additional lines if the element is assigned to more than
  10822.   -- one person
  10823.   if ELE_PTR.more_than_one_person then
  10824.     loop
  10825.       DONE := true;
  10826.       for AC_INDEX in 1..num_of_activities loop
  10827.         DONE := DONE and PR_PRINTING_DONE(AC_INDEX);
  10828.       end loop;
  10829.       exit when DONE;
  10830.  
  10831.       -- find the next person to be printed
  10832.       NEXT_PERSON := 1;
  10833.       while PR_PRINTING_DONE (NEXT_PERSON) loop
  10834.         NEXT_PERSON := NEXT_PERSON + 1;
  10835.       end loop;
  10836.       set_col(report_file, 60); 
  10837.       put(report_file, ELE_PTR.people_initials(NEXT_PERSON) );
  10838.  
  10839.       -- print out the activity percent complete for this person
  10840.       set_col(report_file, 64); 
  10841.       for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  10842.         if ELE_PTR.people_initials(AC_INDEX) = 
  10843.         ELE_PTR.people_initials(NEXT_PERSON) then
  10844.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  10845.       put(report_file,' ');
  10846.       PR_PRINTING_DONE(AC_INDEX) := true;
  10847.     else
  10848.       put(report_file, "* ");
  10849.         end if;
  10850.       end loop;
  10851.  
  10852.       LINE_COUNT := LINE_COUNT + 1;
  10853.       new_line(report_file);
  10854.     end loop;
  10855.   end if;
  10856.   PR_PRINTING_DONE := (others => false);
  10857. exception
  10858.   when others => put_line("exception raised in MS PRINT_AN_ELEMENT");
  10859. end PRINT_AN_ELEMENT;
  10860.  
  10861.  
  10862. separate(TRACKER.report_generator.LIST_BY_MILESTONE)
  10863. procedure PRINT_MS_TOTAL is
  10864. ----------------------------------------------------------------------
  10865. --|  NAME:  PRINT_MS_TOTAL
  10866. --|
  10867. --|  OVERVIEW:
  10868. --|    This procedure prints out the total statics for a milestone. This
  10869. --|    includes the total remaining man-hours of work to complete this
  10870. --|    milestone, the total original size, the total current size, and 
  10871. --|    the average complexity.
  10872. --|
  10873. --|  EXCEPTIONS HANDLED:
  10874. --|    others   an error message is printed and execution continues
  10875. --|
  10876. --|  HISTORY:
  10877. --|    written by   Bonnie Burkhardt   March 1985
  10878. ----------------------------------------------------------------------
  10879.  
  10880. begin
  10881.   -- underline columns
  10882.   set_col(report_file, 84); put(report_file, HEADER_LINES(84..132));
  10883.   new_line(report_file);
  10884.  
  10885.   -- print totals
  10886.   set_col(report_file, 74); put(report_file, "TOTALS");
  10887.   set_col(report_file, 84); put(report_file, TOT_ORIG,7);
  10888.   set_col(report_file, 93); put(report_file, TOT_CURRNT,7);
  10889.   set_col(report_file, 102); put(report_file, TOT_EQ_NEW,7);
  10890.   if ELE_IN_MS > 0 then
  10891.     set_col(report_file, 119); 
  10892.     put(report_file, TOT_CPXY/float(ELE_COUNT),3,2,0);
  10893.   end if;
  10894.   set_col(report_file, 125); put(report_file, TOT_HOURS,6,1,0);
  10895.   new_line(report_file);
  10896.  
  10897.   -- reset counters
  10898.   ELE_COUNT  := 0;
  10899.   TOT_CURRNT := 0;
  10900.   TOT_EQ_NEW := 0;
  10901.   TOT_ORIG   := 0;
  10902.   TOT_CPXY   := 0.0;
  10903.   TOT_HOURS  := 0.0;
  10904. exception
  10905.   when others => put_line("exception raised in PRINT_MS_TOTAL");
  10906. end PRINT_MS_TOTAL;
  10907. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10908. --rlistpr.ada
  10909. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  10910. separate(TRACKER.report_generator)
  10911. procedure LIST_BY_PERSON is
  10912. ----------------------------------------------------------------------
  10913. --|
  10914. --|  NAME:  LIST_BY_PERSON
  10915. --|
  10916. --|  OVERVIEW:
  10917. --|    One report is printed for each person on the project.  Each report
  10918. --|    lists all the elements assigned to that person.  The report includes
  10919. --|    information listed in the List by Milestone Report and also the date
  10920. --|    each element is due (its milestone due date) and the calculated 
  10921. --|    finish date for each element.  The finish date for each element was 
  10922. --|    computed previously by CALC_TIME_DONE and stored in the element data.
  10923. --|
  10924. --|  EXCEPTIONS HANDLED:
  10925. --|    none
  10926. --|
  10927. --|  HISTORY:
  10928. --|    written by   Bonnie Burkhardt   March 1985
  10929. --|
  10930. ----------------------------------------------------------------------
  10931.  
  10932.   use CALENDAR; 
  10933.   use AC_LIST_PKG; use EL_LIST_PKG; use PR_LIST_PKG;
  10934.  
  10935.   HEADER1 : string (1..132) := (others => ' ');
  10936.   HEADER2 : string (1..132) := (others => ' ');
  10937.   HEADER_LINES  : string (1..132) := (others => ' ');
  10938.  
  10939.   AC_INDEX   : integer := 0;
  10940.   AC_PTR     : activity_pointer;
  10941.   END_LIST   : boolean := false;
  10942.   ELE_COUNT  : integer := 0;
  10943.   ELE_IN_PR  : integer := 0;
  10944.   ELE_PTR    : element_pointer;
  10945.   LINE_COUNT : integer := 0;
  10946.   PR_INDEX   : integer := 0;
  10947.   PR_PTR     : personnel_pointer;
  10948.   TITLE      : constant string := "LIST BY PERSON REPORT";
  10949.   TOT_CURRNT : integer range 0..9_999_999 := 0;
  10950.   TOT_EQ_NEW : integer range 0..9_999_999 := 0;
  10951.   TOT_ORIG   : integer range 0..9_999_999 := 0;
  10952.   TOT_CPXY   : float := 0.0;
  10953.   TOT_HOURS  : float := 0.0;
  10954.  
  10955.   procedure INIT_PR_HEADERS is separate;
  10956.   procedure PRINT_PR_ELEMENT is separate;
  10957.   procedure PRINT_PR_TOTAL is separate;
  10958.  
  10959. begin
  10960.   INIT_PR_HEADERS;
  10961.     
  10962.   start_walk(PR_LIST);
  10963.   loop
  10964.     walk(PR_LIST, PR_PTR, END_LIST);
  10965.     exit when END_LIST;
  10966.     LINE_COUNT := 0;
  10967.  
  10968.     -- create the subtitle string
  10969.     START_PAGE(TITLE,PR_PTR.name,HEADER1,HEADER2,HEADER_LINES);
  10970.     start_walk(PR_PTR.element_list);
  10971.     ELE_IN_PR := 0;
  10972.     loop
  10973.       walk(PR_PTR.element_list, ELE_PTR, END_LIST);
  10974.  
  10975.       -- if end of list, print out totals
  10976.       if END_LIST then
  10977.         if (ELE_IN_PR > 0) then
  10978.           PRINT_PR_TOTAL;
  10979.         end if;
  10980.         exit;
  10981.       end if;
  10982.  
  10983.       -- update running totals
  10984.       ELE_COUNT  := ELE_COUNT + 1;
  10985.       TOT_CURRNT := TOT_CURRNT + ELE_PTR.current_size;
  10986.       TOT_EQ_NEW := TOT_EQ_NEW - ELE_PTR.size_done_at_start + ELE_PTR.current_size;
  10987.       TOT_ORIG   := TOT_ORIG + ELE_PTR.original_size;
  10988.       TOT_CPXY   := TOT_CPXY + ELE_PTR.complexity;
  10989.       TOT_HOURS  := TOT_HOURS + ELE_PTR.hours_to_complete;
  10990.  
  10991.       PRINT_PR_ELEMENT;
  10992.  
  10993.       ELE_IN_PR := ELE_IN_PR + 1;
  10994.       LINE_COUNT := LINE_COUNT + 1;
  10995.       if LINE_COUNT >= MAX_DATA_LINES-2 then
  10996.         START_PAGE(TITLE,PR_PTR.name,HEADER1,HEADER2,HEADER_LINES);
  10997.         LINE_COUNT := 0;
  10998.       end if;
  10999.     end loop;
  11000.   end loop;
  11001. exception
  11002.   when others => put_line("exception raised in LIST BY PERSON REPORT");
  11003. end LIST_BY_PERSON;
  11004.  
  11005.  
  11006.  
  11007. separate(TRACKER.report_generator.LIST_BY_PERSON)
  11008. procedure INIT_PR_HEADERS is
  11009. ----------------------------------------------------------------------
  11010. --|
  11011. --|  NAME:  INIT_PR_HEADERS
  11012. --|
  11013. --|  OVERVIEW:
  11014. --|    This procedure initializes all the headers of this person report.
  11015. --|
  11016. --|  EXCEPTIONS HANDLED:
  11017. --|    none
  11018. --|
  11019. --|  HISTORY:
  11020. --|    written by   Bonnie Burkhardt   March 1985
  11021. --|
  11022. ----------------------------------------------------------------------
  11023.  
  11024.   DASHES : constant string (1..15) := (others => '-');
  11025. begin
  11026.   -- initialize the headers
  11027.   HEADER1(65..80) := "** ACTIVITIES **";
  11028.   HEADER1(84..87) := "ORIG";
  11029.   HEADER1(90..95) := "CURRNT";
  11030.   HEADER1(97..102) := "EQ NEW";
  11031.   HEADER1(108..114) := "MAN-HRS";
  11032.   HEADER1(117..122) := "FINISH";
  11033.   HEADER1(127..129) := "DUE";
  11034.  
  11035.   HEADER2(2..3) := "MS";
  11036.   HEADER2(5..6) := "PR";
  11037.   HEADER2(8..16) := "SUBSYSTEM";
  11038.   HEADER2(19..29) := "DESCRIPTION";
  11039.   HEADER2(55..59) := "ABREV";
  11040.   HEADER2(84..87) := "SIZE";
  11041.   HEADER2(91..94) := "SIZE";
  11042.   HEADER2(98..101) := "SIZE";
  11043.   HEADER2(104..106) := "CPX";
  11044.   HEADER2(108..114) := "TO COMP";
  11045.   HEADER2(118..121) := "DATE";
  11046.   HEADER2(127..130) := "DATE";
  11047.   HEADER_LINES (2..3) := DASHES(1..2);
  11048.   HEADER_LINES (5..6) := DASHES(1..2);
  11049.   HEADER_LINES (8..16) := DASHES(1..9);
  11050.   HEADER_LINES (19..29) := DASHES(1..11);
  11051.   HEADER_LINES (55..59) := DASHES(1..5);
  11052.   HEADER_LINES (83..88) := DASHES(1..6);
  11053.   HEADER_LINES (90..95) := DASHES(1..6);
  11054.   HEADER_LINES (97..102) := DASHES(1..6);
  11055.   HEADER_LINES (104..106) := DASHES(1..3);
  11056.   HEADER_LINES (108..114) := DASHES(1..7);
  11057.   HEADER_LINES (116..123) := DASHES(1..8);
  11058.   HEADER_LINES (125..132) := DASHES(1..8);
  11059.  
  11060.   -- initialize the header for the activity data
  11061.   start_walk(AC_LIST);
  11062.   AC_INDEX := 0;
  11063.   loop
  11064.     walk (AC_LIST, AC_PTR, END_LIST);
  11065.     exit when END_LIST;
  11066.     HEADER2(63+2*AC_INDEX) := AC_PTR.name(1);
  11067.     HEADER_LINES(63+2*AC_INDEX) := '-';
  11068.     AC_INDEX := AC_INDEX + 1;
  11069.   end loop;
  11070. end INIT_PR_HEADERS;
  11071.  
  11072.  
  11073.  
  11074. separate(TRACKER.report_generator.LIST_BY_PERSON)
  11075. procedure PRINT_PR_ELEMENT is
  11076. ----------------------------------------------------------------------
  11077. --|
  11078. --|  NAME:  PRINT_PR_ELEMENT
  11079. --|
  11080. --|  OVERVIEW:
  11081. --|    This procedure prints out an element line. This line includes the 
  11082. --|    element data plus the remaining man-hours of work to complete this
  11083. --|    element, the original size, the current size, the complexity, 
  11084. --|    the remaining man-hours of work to complete this element, the due
  11085. --|    date and the projected completion date.  
  11086. --|
  11087. --|  EXCEPTIONS HANDLED:
  11088. --|    none
  11089. --|
  11090. --|  HISTORY:
  11091. --|    written by   Bonnie Burkhardt   March 1985
  11092. --|
  11093. ----------------------------------------------------------------------
  11094.  
  11095.   use MS_LIST_PKG;
  11096.  
  11097.   FOUND            : boolean := false;
  11098.   MS_PTR        : milestone_pointer;
  11099.  
  11100. begin
  11101.   -- print out element
  11102.   set_col(report_file, 2);  put(report_file, ELE_PTR.milestone_num,2);
  11103.   set_col(report_file, 5);  put(report_file, ELE_PTR.priority,2);
  11104.   set_col(report_file, 8);  put(report_file, ELE_PTR.subsystem_name);
  11105.   set_col(report_file, 19); put(report_file, ELE_PTR.description);
  11106.   set_col(report_file, 55); put(report_file, ELE_PTR.desc_key);
  11107.   set_col(report_file, 63); 
  11108.   if not ELE_PTR.more_than_one_person then
  11109.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop 
  11110.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  11111.       put(report_file,' ');
  11112.     end loop;
  11113.   else  -- print out the first person assigned
  11114.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  11115.       if ELE_PTR.people_initials(AC_INDEX) = PR_PTR.initials then
  11116.     put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  11117.     put(report_file,' ');
  11118.       else
  11119.     put(report_file, "* ");
  11120.       end if;
  11121.     end loop;
  11122.   end if;
  11123.   set_col(report_file, 83);  put(report_file, ELE_PTR.original_size,6);
  11124.   set_col(report_file, 90);  put(report_file, ELE_PTR.current_size,6);
  11125.   set_col(report_file, 97); 
  11126.     put(report_file, ELE_PTR.current_size - ELE_PTR.size_done_at_start,6);
  11127.   set_col(report_file, 104); put(report_file, ELE_PTR.complexity,1,1,0);
  11128.   set_col(report_file, 108); put(report_file, ELE_PTR.hours_to_complete,5,1,0);
  11129.   set_col(report_file, 116); 
  11130.   if ELE_PTR.date_done = underflow_date then
  11131.     put(report_file, "99/99/99");
  11132.   elsif (ELE_PTR.hours_to_complete = 0.0) or 
  11133.     (ELE_PTR.date_done = null_date) then
  11134.     put(report_file, "  DONE  ");
  11135.   else
  11136.     put(report_file, ELE_PTR.date_done.month,2); put(report_file,'/'); 
  11137.     put(report_file, ELE_PTR.date_done.day,2); put(report_file,'/');
  11138.     put(report_file, ELE_PTR.date_done.year mod 100,2);
  11139.   end if;
  11140.   find (MS_LIST, ELE_PTR.milestone_num, MS_PTR, FOUND);
  11141.   set_col(report_file, 125); 
  11142.   if MS_PTR.due_date = null_date then
  11143.     put(report_file, " 0/ 0/ 0");
  11144.   else
  11145.     put(report_file, MS_PTR.due_date.month,2); put(report_file,'/'); 
  11146.     put(report_file, MS_PTR.due_date.day,2); put(report_file,'/');
  11147.     put(report_file, MS_PTR.due_date.year mod 100,2);
  11148.   end if;
  11149.   new_line(report_file);
  11150. end PRINT_PR_ELEMENT;
  11151.  
  11152.  
  11153. separate(TRACKER.report_generator.LIST_BY_PERSON)
  11154. procedure PRINT_PR_TOTAL is
  11155.  ----------------------------------------------------------------------
  11156. --|
  11157. --|  NAME:  PRINT_PR_TOTAL
  11158. --|
  11159. --|  OVERVIEW:
  11160. --|    This procedure prints out the total statics for the person. This
  11161. --|    includes the total remaining man-hours of work to complete this
  11162. --|    milestone, the total original size, the total current size, and 
  11163. --|    the average complexity.
  11164. --|
  11165. --|  EXCEPTIONS HANDLED:
  11166. --|    none
  11167. --|
  11168. --|  HISTORY:
  11169. --|    written by   Bonnie Burkhardt   March 1985
  11170. --|
  11171. ----------------------------------------------------------------------
  11172.  
  11173. begin
  11174.   -- underline columns
  11175.   set_col(report_file, 84); put(report_file, HEADER_LINES(84..132));
  11176.   new_line(report_file);
  11177.  
  11178.   -- print totals
  11179.   set_col(report_file, 74); put(report_file, "TOTALS");
  11180.   set_col(report_file, 83); put(report_file, TOT_ORIG,6);
  11181.   set_col(report_file, 90); put(report_file, TOT_CURRNT,6);
  11182.   set_col(report_file, 97); put(report_file, TOT_EQ_NEW,6);
  11183.   if ELE_IN_PR > 0 then
  11184.     set_col(report_file, 104); 
  11185.     put(report_file, TOT_CPXY/float(ELE_COUNT),1,1,0);
  11186.   end if;
  11187.   set_col(report_file, 107); 
  11188.   put(report_file, TOT_HOURS,6,1,0);
  11189.   new_line(report_file);
  11190.  
  11191.   -- reset counters
  11192.   ELE_COUNT  := 0;
  11193.   TOT_CURRNT := 0;
  11194.   TOT_EQ_NEW := 0;
  11195.   TOT_ORIG   := 0;
  11196.   TOT_CPXY   := 0.0;
  11197.   TOT_HOURS  := 0.0;
  11198. end PRINT_PR_TOTAL;
  11199. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11200. --rlistss.ada
  11201. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11202. separate(TRACKER.report_generator)
  11203. procedure LIST_BY_SUBSYSTEM is
  11204. ----------------------------------------------------------------------
  11205. --|  NAME:  LIST_BY_SUBSYSTEM
  11206. --|
  11207. --|  OVERVIEW:
  11208. --|    A separate report is printed for each subsystem.  All of the element 
  11209. --|    data for each subsystem is displayed including the remaining man-hours 
  11210. --|    of work to complete each element, the total original size, the total 
  11211. --|    current size, the average complexity, and the total remaining man-hours 
  11212. --|    of work to complete each subsystem.  
  11213. --|
  11214. --|  EXCEPTIONS HANDLED:
  11215. --|    others   an error message is printed and execution continues
  11216. --|
  11217. --|  HISTORY:
  11218. --|    written by   Bonnie Burkhardt   March 1985
  11219. ----------------------------------------------------------------------
  11220.  
  11221.   use AC_LIST_PKG; use EL_LIST_PKG; use SS_LIST_PKG;
  11222.  
  11223.   HEADER1 : string (1..132) := (others => ' ');
  11224.   HEADER2 : string (1..132) := (others => ' ');
  11225.   HEADER_LINES  : string (1..132) := (others => ' ');
  11226.  
  11227.   AC_INDEX   : integer := 0;
  11228.   AC_PTR     : activity_pointer;
  11229.   END_LIST   : boolean := false;
  11230.   ELE_COUNT  : integer := 0;
  11231.   ELE_IN_SS  : integer := 0;
  11232.   ELE_PTR    : element_pointer;
  11233.   LINE_COUNT : integer := 0;
  11234.   SS_INDEX   : integer := 0;
  11235.   SS_PTR     : SUBSYSTEM_pointer;
  11236.   TITLE      : constant string := "LIST BY SUBSYSTEM REPORT";
  11237.   TOT_CURRNT : integer range 0..9_999_999 := 0;
  11238.   TOT_EQ_NEW : integer range 0..9_999_999 := 0;
  11239.   TOT_ORIG   : integer range 0..9_999_999 := 0;
  11240.   TOT_CPXY   : float := 0.0;
  11241.   TOT_HOURS  : float := 0.0;
  11242.  
  11243.   procedure INIT_SS_HEADERS is separate;
  11244.   procedure PRINT_SS_ELEMENT is separate;
  11245.   procedure PRINT_SS_TOTAL is separate;
  11246.  
  11247. begin
  11248.   INIT_SS_HEADERS;
  11249.     
  11250.   start_walk(SS_LIST);
  11251.   loop
  11252.     walk(SS_LIST, SS_PTR, END_LIST);
  11253.     exit when END_LIST;
  11254.     LINE_COUNT := 0;
  11255.  
  11256.     -- create the subtitle string
  11257.     START_PAGE(TITLE,SS_PTR.name,HEADER1,HEADER2,HEADER_LINES);
  11258.  
  11259.     -- print out each subsystem's list of elements
  11260.     start_walk(SS_PTR.element_list);
  11261.     ELE_IN_SS := 0;
  11262.     loop
  11263.       walk(SS_PTR.element_list, ELE_PTR, END_LIST);
  11264.       -- if end of list, print out totals
  11265.       if END_LIST then
  11266.         if (ELE_IN_SS > 0) then
  11267.           PRINT_SS_TOTAL;
  11268.         end if;
  11269.         exit;
  11270.       end if;
  11271.  
  11272.       -- update running totals
  11273.       ELE_COUNT  := ELE_COUNT + 1;
  11274.       TOT_CURRNT := TOT_CURRNT + ELE_PTR.current_size;
  11275.       TOT_EQ_NEW := TOT_EQ_NEW - ELE_PTR.size_done_at_start + ELE_PTR.current_size;
  11276.       TOT_ORIG   := TOT_ORIG + ELE_PTR.original_size;
  11277.       TOT_CPXY   := TOT_CPXY + ELE_PTR.complexity;
  11278.       TOT_HOURS  := TOT_HOURS + ELE_PTR.hours_to_complete;
  11279.  
  11280.       PRINT_SS_ELEMENT;
  11281.  
  11282.       ELE_IN_SS := ELE_IN_SS + 1;
  11283.       LINE_COUNT := LINE_COUNT + 1;
  11284.       if LINE_COUNT >= MAX_DATA_LINES-2 then
  11285.         START_PAGE(TITLE,SS_PTR.name,HEADER1,HEADER2,HEADER_LINES);
  11286.         LINE_COUNT := 0;
  11287.       end if;
  11288.     end loop;
  11289.   end loop;
  11290. exception
  11291.   when others => put_line("exception raised in LIST BY SUBSYSTEM REPORT");
  11292. end LIST_BY_SUBSYSTEM;
  11293.  
  11294.  
  11295.  
  11296. separate(TRACKER.report_generator.LIST_BY_SUBSYSTEM)
  11297. procedure INIT_SS_HEADERS is
  11298. ----------------------------------------------------------------------
  11299. --|  NAME:  INIT_SS_HEADERS
  11300. --|
  11301. --|  OVERVIEW:
  11302. --|    This procedure initializes all the headers of this subsystem report.
  11303. --|
  11304. --|  EXCEPTIONS HANDLED:
  11305. --|    none
  11306. --|
  11307. --|  HISTORY:
  11308. --|    written by   Bonnie Burkhardt   March 1985
  11309. ----------------------------------------------------------------------
  11310.  
  11311.   DASHES : constant string(1..15) := (others => '-');
  11312.  
  11313. begin
  11314.   -- initialize the headers
  11315.   HEADER1(59..74)   := "** ACTIVITIES **";
  11316.   HEADER1(81..87)   := "ORIGINL";
  11317.   HEADER1(90..96)   := "CURRENT";
  11318.   HEADER1(99..105)  := "EQ. NEW";
  11319.   HEADER1(108..115) := "SIZE LST";
  11320.   HEADER1(126..132) := "MAN-HRS";
  11321.  
  11322.   HEADER2(2..3)     := "MS";
  11323.   HEADER2(5..6)     := "PR";
  11324.   HEADER2(8..18)    := "DESCRIPTION";
  11325.   HEADER2(46..50)   := "ABREV";
  11326.   HEADER2(54..55)   := "RP";
  11327.   HEADER2(81..84)   := "SIZE";
  11328.   HEADER2(90..93)   := "SIZE";
  11329.   HEADER2(99..102)  := "SIZE";
  11330.   HEADER2(108..115) := "VERIFIED";
  11331.   HEADER2(118..123) := "COMPXY";
  11332.   HEADER2(126..132) := "TO COMP";
  11333.  
  11334.   HEADER_LINES (2..3)     := DASHES(1..2);
  11335.   HEADER_LINES (5..6)     := DASHES(1..2);
  11336.   HEADER_LINES (8..18)    := DASHES(1..11);
  11337.   HEADER_LINES (46..50)   := DASHES(1..5);
  11338.   HEADER_LINES (54..55)   := DASHES(1..2);
  11339.   HEADER_LINES (81..87)   := DASHES(1..7);
  11340.   HEADER_LINES (90..96)   := DASHES(1..7);
  11341.   HEADER_LINES (99..105)  := DASHES(1..7);
  11342.   HEADER_LINES (108..115) := DASHES(1..8);
  11343.   HEADER_LINES (118..123) := DASHES(1..6);
  11344.   HEADER_LINES (126..132) := DASHES(1..7);
  11345.  
  11346.   -- initialize the header for the activity data
  11347.   start_walk(AC_LIST);
  11348.   AC_INDEX := 0;
  11349.   loop
  11350.     walk (AC_LIST, AC_PTR, END_LIST);
  11351.     exit when END_LIST;
  11352.     HEADER2(58+2*AC_INDEX) := AC_PTR.name(1);
  11353.     HEADER_LINES(58+2*AC_INDEX) := '-';
  11354.     AC_INDEX := AC_INDEX + 1;
  11355.   end loop;
  11356. end INIT_SS_HEADERS;
  11357.  
  11358.  
  11359.  
  11360.  
  11361. separate(TRACKER.report_generator.LIST_BY_SUBSYSTEM)
  11362. procedure PRINT_SS_ELEMENT is
  11363. ----------------------------------------------------------------------
  11364. --|  NAME:  PRINT_SS_ELEMENT
  11365. --|
  11366. --|  OVERVIEW:
  11367. --|    This procedure prints out an element line. This line includes the 
  11368. --|    element data, the remaining man-hours of work to complete this
  11369. --|    element, the original size, the current size, the complexity, and 
  11370. --|    the remaining man-hours of work until completion.  
  11371. --|
  11372. --|  EXCEPTIONS HANDLED:
  11373. --|    none
  11374. --|
  11375. --|  HISTORY:
  11376. --|    written by   Bonnie Burkhardt   March 1985
  11377. ----------------------------------------------------------------------
  11378.  
  11379.   ALL_PR_PRINTED    : constant array (1..num_of_activities) of boolean 
  11380.             := (others => true);
  11381.   PR_PRINTING_DONE  : array (1..num_of_activities) of boolean 
  11382.             := (others => false);
  11383.   NEXT_PERSON        : integer range 1..num_of_activities := 1;
  11384.   DONE            : boolean := true;
  11385.  
  11386. begin
  11387.   -- print out element
  11388.   set_col(report_file, 2);  put(report_file, ELE_PTR.milestone_num,2);
  11389.   set_col(report_file, 5);  put(report_file, ELE_PTR.priority,2);
  11390.   set_col(report_file, 8);  put(report_file, ELE_PTR.description);
  11391.   set_col(report_file, 46); put(report_file, ELE_PTR.desc_key);
  11392.   -- if the element has more than one person assigned to it, print out
  11393.   -- the first person
  11394.   if not ELE_PTR.more_than_one_person then
  11395.     set_col(report_file, 54); put(report_file, ELE_PTR.person_initials);
  11396.     set_col(report_file, 58); 
  11397.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop 
  11398.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  11399.       put(report_file,' ');
  11400.     end loop;
  11401.   else  -- print out the first person assigned
  11402.     set_col(report_file, 54); 
  11403.     put(report_file, ELE_PTR.people_initials(1) );
  11404.     set_col(report_file, 58); 
  11405.     for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  11406.       if ELE_PTR.people_initials(AC_INDEX) = ELE_PTR.people_initials(1) then
  11407.     put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  11408.     put(report_file,' ');
  11409.         PR_PRINTING_DONE(AC_INDEX) := true;
  11410.       else
  11411.     put(report_file, "* ");
  11412.       end if;
  11413.     end loop;
  11414.   end if;
  11415.   set_col(report_file, 82); put(report_file, ELE_PTR.original_size,6);
  11416.   set_col(report_file, 91); put(report_file, ELE_PTR.current_size,6);
  11417.   set_col(report_file, 100); 
  11418.     put(report_file, ELE_PTR.current_size - ELE_PTR.size_done_at_start,6);
  11419.   set_col(report_file, 108); 
  11420.     put(report_file, ELE_PTR.date_size_verified.month,2); 
  11421.     put(report_file,'/'); 
  11422.     put(report_file, ELE_PTR.date_size_verified.day,2); 
  11423.     put(report_file,'/');
  11424.     put(report_file, ELE_PTR.date_size_verified.year mod 100,2);
  11425.   set_col(report_file, 118); put(report_file, ELE_PTR.complexity,3,2,0);
  11426.   set_col(report_file, 126); put(report_file, ELE_PTR.hours_to_complete,5,1,0);
  11427.  
  11428.  
  11429.   -- print out additional lines if the element is assigned to more than
  11430.   -- one person
  11431.   if ELE_PTR.more_than_one_person then
  11432.     loop
  11433.       DONE := true;
  11434.       for AC_INDEX in 1..num_of_activities loop
  11435.         DONE := DONE and PR_PRINTING_DONE(AC_INDEX);
  11436.       end loop;
  11437.       exit when DONE;
  11438.  
  11439.       -- find the next person to be printed
  11440.       NEXT_PERSON := 1;
  11441.       while PR_PRINTING_DONE (NEXT_PERSON) loop
  11442.         NEXT_PERSON := NEXT_PERSON + 1;
  11443.       end loop;
  11444.       set_col(report_file, 54); 
  11445.       put(report_file, ELE_PTR.people_initials(NEXT_PERSON) );
  11446.  
  11447.       -- print out the activity percent complete for this person
  11448.       set_col(report_file, 58); 
  11449.       for AC_INDEX in 1..NUM_OF_ACTIVITIES loop
  11450.         if ELE_PTR.people_initials(AC_INDEX) = 
  11451.         ELE_PTR.people_initials(NEXT_PERSON) then
  11452.       put(report_file, convert(ELE_PTR.activity_completeness(AC_INDEX))); 
  11453.       put(report_file,' ');
  11454.       PR_PRINTING_DONE(AC_INDEX) := true;
  11455.     else
  11456.       put(report_file, "* ");
  11457.         end if;
  11458.       end loop;
  11459.  
  11460.       LINE_COUNT := LINE_COUNT + 1;
  11461.       new_line(report_file);
  11462.     end loop;
  11463.   end if;
  11464.   PR_PRINTING_DONE := (others => false);
  11465. end PRINT_SS_ELEMENT;
  11466.  
  11467.  
  11468.  
  11469. separate(TRACKER.report_generator.LIST_BY_SUBSYSTEM)
  11470. procedure PRINT_SS_TOTAL is
  11471. ----------------------------------------------------------------------
  11472. --|  NAME:  PRINT_SS_TOTAL
  11473. --|
  11474. --|  OVERVIEW:
  11475. --|    This procedure prints out the total statics for a subsystem. This
  11476. --|    includes the total remaining man-hours of work to complete this
  11477. --|    subsystem, the total original size, the total current size, and 
  11478. --|    the average complexity.
  11479. --|
  11480. --|  EXCEPTIONS HANDLED:
  11481. --|    none
  11482. --|
  11483. --|  HISTORY:
  11484. --|    written by   Bonnie Burkhardt   March 1985
  11485. ----------------------------------------------------------------------
  11486.  
  11487. begin
  11488.   -- underline columns
  11489.   set_col(report_file, 81); put(report_file, HEADER_LINES(81..132));
  11490.   new_line(report_file);
  11491.  
  11492.   -- print totals
  11493.   set_col(report_file, 70); put(report_file, "TOTALS");
  11494.   set_col(report_file, 81); put(report_file, TOT_ORIG,7);
  11495.   set_col(report_file, 90); put(report_file, TOT_CURRNT,7);
  11496.   set_col(report_file, 99); put(report_file, TOT_EQ_NEW,7);
  11497.   if ELE_IN_SS > 0 then
  11498.     set_col(report_file, 118); 
  11499.     put(report_file, TOT_CPXY/float(ELE_COUNT),3,2,0);
  11500.   end if;
  11501.   set_col(report_file, 125); 
  11502.   put(report_file, TOT_HOURS,6,1,0);
  11503.   new_line(report_file);
  11504.  
  11505.   -- reset counters
  11506.   ELE_COUNT  := 0;
  11507.   TOT_CURRNT := 0;
  11508.   TOT_EQ_NEW := 0;
  11509.   TOT_ORIG   := 0;
  11510.   TOT_CPXY   := 0.0;
  11511.   TOT_HOURS  := 0.0;
  11512. end PRINT_SS_TOTAL;
  11513. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11514. --rpage.ada
  11515. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11516. separate(TRACKER.report_generator)
  11517.  
  11518. procedure START_PAGE (TITLE, SUBTITLE, HEADER1, HEADER2, HEADER_LINES 
  11519.         : in string := "") is
  11520. ----------------------------------------------------------------------
  11521. --|
  11522. --|  NAME:  START_PAGE
  11523. --|
  11524. --|  OVERVIEW:
  11525. --|    This routine starts the next report on a new page and prints the 
  11526. --|    globalproject data on the report.  It then centers the title and 
  11527. --|    subtitle on the page.  After leaving two blank lines, it prints
  11528. --|    the headers: HEADER1, HEADER2, and HEADER_LINES.
  11529. --|
  11530. --|  EXCEPTIONS HANDLED:
  11531. --|    others   an error message is printed and execution continues
  11532. --|
  11533. --|  HISTORY:
  11534. --|    written by   Bonnie Burkhardt   March 1985
  11535. --|
  11536. ----------------------------------------------------------------------
  11537.  
  11538. begin
  11539.   -- print out global information
  11540.   new_page(report_file);
  11541.   put(report_file, "Project Name: "); 
  11542.   put(report_file, PROJECT_NAME); new_line(report_file, 2);
  11543.   put(report_file, "Project Manager: "); 
  11544.   put(report_file, MANAGER_NAME); new_line(report_file, 2);
  11545.   put(report_file, "Status Date: "); put(report_file, DATE.month,2); 
  11546.     put(report_file, "/"); put(report_file, DATE.day,2); 
  11547.     put(report_file, "/"); put(report_file, DATE.year mod 100,2); 
  11548.     new_line(report_file, 5);
  11549.  
  11550.   -- print out titles
  11551.   set_col(report_file,(128-TITLE'length)/2); 
  11552.   put(report_file, "*** "); put(report_file, TITLE); put(report_file, " ***"); 
  11553.     new_line(report_file);
  11554.   set_col(report_file,(132-SUBTITLE'length)/2); 
  11555.   put(report_file, SUBTITLE); new_line(report_file,3);
  11556.   put(report_file, HEADER1); new_line(report_file);
  11557.   put(report_file, HEADER2); new_line(report_file);
  11558.   put(report_file, HEADER_LINES); new_line(report_file);
  11559. exception
  11560.   when others => put_line("exception raised in START PAGE");
  11561. end START_PAGE;
  11562. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11563. --rparam.ada
  11564. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11565. separate(TRACKER.report_generator)  
  11566.  
  11567. procedure PARAMETER_DATA_LIST is
  11568. ----------------------------------------------------------------------
  11569. --|
  11570. --|  NAME:  PARAMETER_DATA_LIST
  11571. --|
  11572. --|  OVERVIEW:
  11573. --|    This report prints all of the parameter data including global
  11574. --|    variables, activity data, milestone data, personnel data,
  11575. --|    subsystem data, and the milestone completion sequence.
  11576. --|
  11577. --|  EXCEPTIONS HANDLED:
  11578. --|    others   an error message is printed and execution continues
  11579. --|
  11580. --|  HISTORY:
  11581. --|    written by   Bonnie Burkhardt   March 1985
  11582. --|
  11583. ----------------------------------------------------------------------
  11584.  
  11585.   use CALENDAR;
  11586.   use AC_LIST_PKG; use MS_LIST_PKG; use PR_LIST_PKG; use SS_LIST_PKG;
  11587.  
  11588.   BLANKS : constant string (1..30) := (others => ' ');
  11589.   DASHES : constant string (1..20) := (others => '-');
  11590.   END_LIST : boolean := false;
  11591.   MS_ON_LINE : integer := 0;
  11592.   NUM_OF_BLANKS : integer := 1;
  11593.  
  11594.   AC_PTR : activity_pointer;
  11595.   MS_PTR : milestone_pointer;
  11596.   PR_PTR : personnel_pointer;
  11597.   SS_PTR : subsystem_pointer;
  11598.  
  11599.   procedure PRINT_START_DATE (date : in date_type) is
  11600.   begin
  11601.     if date = null_date then
  11602.       put(report_file, " 0/ 0/ 0");
  11603.     else
  11604.       put(report_file, date.month,2); put(report_file, '/');
  11605.       put(report_file, date.day,2);   put(report_file, '/');
  11606.       put(report_file, date.year,4); 
  11607.     end if;
  11608.   end PRINT_START_DATE;
  11609.  
  11610.   procedure PRINT_STOP_DATE (date : in date_type) is
  11611.   begin
  11612.     if date = null_date then
  11613.       put(report_file, "99/99/99");
  11614.     else
  11615.       put(report_file, date.month,2); put(report_file, '/');
  11616.       put(report_file, date.day,2);   put(report_file, '/');
  11617.       put(report_file, date.year,4); 
  11618.     end if;
  11619.   end PRINT_STOP_DATE;
  11620.  
  11621. begin
  11622.   -- print out global information
  11623.   put(report_file, "Project Name: "); 
  11624.   put(report_file, PROJECT_NAME); 
  11625.   put(report_file, " #"); 
  11626.   put(report_file, project_number,3); 
  11627.   set_col(report_file, 80);
  11628.   put(report_file, "Status Date: "); put(report_file, DATE.month,2); 
  11629.     put(report_file, "/"); put(report_file, DATE.day,2); 
  11630.     put(report_file, "/"); put(report_file, DATE.year,4); 
  11631.     new_line(report_file);
  11632.   put(report_file, "Project Manager: "); 
  11633.   put(report_file, MANAGER_NAME); new_line(report_file);
  11634.  
  11635.   -- output total number of parameters
  11636.   put(report_file, "NUMBER OF ACTIVITIES : ");
  11637.   put(report_file, num_of_activities,4); new_line(report_File);
  11638.   put(report_file, "NUMBER OF MILESTONES : ");
  11639.   put(report_file, num_of_milestones,4); new_line(report_File);
  11640.   put(report_file, "NUMBER OF PERSONNEL  : ");
  11641.   put(report_file, num_of_people,4);     new_line(report_File);
  11642.   put(report_file, "NUMBER OF SUBSYSTEMS : ");
  11643.   put(report_file, num_of_subsystems,4); new_line(report_File);
  11644.   put(report_file, "NUMBER OF ELEMENTS   : ");
  11645.   put(report_file, num_of_elements,4);   new_line(report_File);
  11646.  
  11647.   -- output subsystem data
  11648.   new_line(report_file);
  11649.   set_col(report_file, 2);  put(report_file, "SUBSYSTEM"); 
  11650.   set_col(report_file, 13); put(report_file, "% AVAILABLE AT START"); 
  11651.   new_line(report_file);
  11652.   set_col(report_file, 2);  put(report_file, DASHES(1..9)); 
  11653.   set_col(report_file, 13); put(report_file, DASHES(1..20)); 
  11654.   new_line(report_file); 
  11655.   start_walk (SS_LIST);
  11656.   loop
  11657.     walk (SS_LIST, SS_PTR, END_LIST);
  11658.     exit when END_LIST;
  11659.     put(report_file, SS_PTR.name); 
  11660.     set_col(report_file, 20); put(report_file, SS_PTR.percent_at_start,3,2,0); 
  11661.     put(report_file, '%'); 
  11662.     new_line(report_file);
  11663.   end loop;
  11664.  
  11665.   -- output personnel data
  11666.   new_line(report_file);
  11667.   set_col(report_file, 2);  put(report_file, "PERSON'S NAME"); 
  11668.   set_col(report_file, 23); put(report_file, "INITIALS"); 
  11669.   set_col(report_file, 34); put(report_file, "RATE PER HOUR"); 
  11670.   set_col(report_file, 50); put(report_file, "HOURS PER WEEK"); 
  11671.   set_col(report_file, 67); put(report_file, "START DATE"); 
  11672.   set_col(report_file, 80); put(report_file, "STOP DATE"); 
  11673.   new_line(report_file);
  11674.   set_col(report_file, 2);  put(report_file, DASHES(1..13)); 
  11675.   set_col(report_file, 23); put(report_file, DASHES(1..8));
  11676.   set_col(report_file, 34); put(report_file, DASHES(1..13)); 
  11677.   set_col(report_file, 50); put(report_file, DASHES(1..14)); 
  11678.   set_col(report_file, 67); put(report_file, DASHES(1..10)); 
  11679.   set_col(report_file, 80); put(report_file, DASHES(1..10)); 
  11680.   new_line(report_file);
  11681.   start_walk (PR_LIST);
  11682.   loop
  11683.     walk (PR_LIST, PR_PTR, END_LIST);
  11684.     exit when END_LIST;
  11685.     set_col(report_file, 2);  put(report_file, PR_PTR.name); 
  11686.     set_col(report_file, 26); put(report_file, PR_PTR.initials);  
  11687.     set_col(report_file, 37); put(report_file, PR_PTR.production_rate,3,3,0); 
  11688.     set_col(report_file, 55); put(report_file, PR_PTR.hours_per_week,4); 
  11689.  
  11690.     -- write out all the start/stop dates for this person
  11691.     set_col(report_file, 67);
  11692.     print_start_date (PR_PTR.start_dates(PR_PTR.start_dates'first) );
  11693.     set_col (report_file, 80);
  11694.     print_stop_date (PR_PTR.stop_dates(PR_PTR.stop_dates'first) );
  11695.     new_line (report_file);
  11696.     for I in PR_PTR.start_dates'first+1..PR_PTR.start_dates'last loop
  11697.       if PR_PTR.start_dates(I) = null_date then
  11698.     exit;  -- if there are no more start/stop dates, don't print them
  11699.       else
  11700.         set_col(report_file, 67);
  11701.     print_start_date (PR_PTR.start_dates(I) );
  11702.     set_col (report_file, 80);
  11703.     print_stop_date (PR_PTR.stop_dates(I) );
  11704.     new_line (report_file);
  11705.       end if;
  11706.     end loop;
  11707.   end loop;
  11708.  
  11709.   -- output activity data
  11710.   new_line(report_file);
  11711.   set_col(report_file, 2);  put(report_file, "ACTIVITY NAME"); 
  11712.   set_col(report_file, 17); put(report_file, "% TOTAL PROJECT"); 
  11713.   set_col(report_file, 35); put(report_file, "PRIORITY"); 
  11714.   set_col(report_file, 46); put(report_file, "CONSIDERED");
  11715.   set_col(report_file, 59); put(report_file, "% AVAILABLE AT START"); 
  11716.   new_line(report_file);
  11717.   set_col(report_file, 2);  put(report_file, DASHES(1..13)); 
  11718.   set_col(report_file, 17); put(report_file, DASHES(1..15));  
  11719.   set_col(report_file, 35); put(report_file, DASHES(1..8)); 
  11720.   set_col(report_file, 46); put(report_file, DASHES(1..10)); 
  11721.   set_col(report_file, 59); put(report_file, DASHES(1..20)); 
  11722.   new_line(report_file);
  11723.   start_walk (AC_LIST);
  11724.   loop
  11725.     walk (AC_LIST, AC_PTR, END_LIST);
  11726.     exit when END_LIST;
  11727.     set_col(report_file, 2);  put(report_file, AC_PTR.name); 
  11728.     set_col(report_file, 21); put(report_file, AC_PTR.percent_tot_proj,3,2,0); 
  11729.       put(report_file, '%');
  11730.     set_col(report_file, 37); put(report_file, AC_PTR.priority,3); 
  11731.     set_col(report_file, 49);
  11732.     if AC_PTR.consider_in_calc then 
  11733.       put(report_file, "YES"); 
  11734.     else
  11735.       put(report_file, "NO"); 
  11736.     end if;
  11737.     set_col(report_file, 59); put(report_file, AC_PTR.percent_at_start,3,2,0); 
  11738.       put(report_file, '%');
  11739.     new_line(report_file);
  11740.   end loop;
  11741.   
  11742.   -- output the task numbers
  11743.   new_line(report_file);
  11744.   if num_of_activities > 2 then
  11745.     NUM_OF_BLANKS := NUM_OF_ACTIVITIES * 3 - 4;
  11746.   end if;
  11747.   put (report_file, BLANKS(1..NUM_OF_BLANKS) );
  11748.   put_line(report_file, "TASK NUMBERS");
  11749.   set_col(report_file, 2);  
  11750.   start_walk (AC_LIST);
  11751.   loop
  11752.     walk (AC_LIST, AC_PTR, END_LIST);
  11753.     exit when END_LIST;
  11754.     put(report_file, AC_PTR.name(1..4)); 
  11755.     put (report_file, "  ");
  11756.   end loop;
  11757.   new_line(report_file);
  11758.  
  11759.   set_col(report_file, 2);  
  11760.   for AC_INDEX in 1..num_of_activities loop
  11761.     put (report_file, "----  ");
  11762.   end loop;
  11763.   new_line(report_file);
  11764.  
  11765.   start_walk (SS_LIST);
  11766.   loop
  11767.     walk(SS_LIST, SS_PTR, END_LIST);
  11768.     exit when END_LIST;
  11769.     set_col(report_file, 2);  
  11770.     for AC_INDEX in 1..num_of_activities loop
  11771.       put (report_file, SS_PTR.task_numbers(AC_INDEX),4);
  11772.       put (report_file, "  ");
  11773.     end loop;
  11774.     new_line(report_file);
  11775.   end loop;
  11776.  
  11777.   -- output milestone data
  11778.   new_line(report_file);
  11779.   set_col(report_file, 2);  put(report_file, "MILESTONE"); 
  11780.   set_col(report_file, 14); put(report_file, "DUE DATE"); 
  11781.   set_col(report_file, 26); put(report_file, "DESCRIPTION"); 
  11782.   new_line(report_file);
  11783.   set_col(report_file, 2);  put(report_file, DASHES(1..9)); 
  11784.   set_col(report_file, 13); put(report_file, DASHES(1..10)); 
  11785.   set_col(report_file, 26); put(report_file, DASHES(1..11)); 
  11786.   new_line(report_file);
  11787.   start_walk (MS_LIST);
  11788.   loop
  11789.     walk (MS_LIST, MS_PTR, END_LIST);
  11790.     exit when END_LIST;
  11791.     set_col(report_file, 4); put(report_file, MS_PTR.number,3); 
  11792.     set_col(report_file, 13);
  11793.     if MS_PTR.due_date = null_date then
  11794.       put(report_file, " 0/ 0/ 0");
  11795.     else
  11796.       put(report_file, MS_PTR.due_date.month,2); put(report_file, '/');
  11797.       put(report_file, MS_PTR.due_date.day,2);   put(report_file, '/');
  11798.       put(report_file, MS_PTR.due_date.year,4); 
  11799.     end if;
  11800.     set_col(report_file, 26); put(report_file, MS_PTR.description); 
  11801.     new_line(report_file);
  11802.   end loop;
  11803.  
  11804.   -- write out milestone completion sequence
  11805.   new_line(report_file, 2);
  11806.   set_col(report_file, 2); put(report_file, "MILESTONE COMPLETION SEQUENCE"); 
  11807.   new_line(report_file, 2);
  11808.   MS_ON_LINE := 0;
  11809.   start_walk (MS_LIST);
  11810.   loop
  11811.     walk (MS_LIST, MS_PTR, END_LIST);
  11812.     exit when END_LIST;
  11813.     MS_ON_LINE := MS_ON_LINE + 1;
  11814.     if MS_ON_LINE > 33 then
  11815.       MS_ON_LINE := 0;
  11816.       new_line(report_file);
  11817.     end if;
  11818.     put(report_file, ' '); put(report_file, MS_PTR.number, 2);
  11819.   end loop;
  11820.   new_line(report_file, 2);
  11821.  
  11822. exception
  11823.   when others => put_line("exception raised in PARAMETER DATA LIST");
  11824. end PARAMETER_DATA_LIST;
  11825. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11826. --rpctbyss.ada
  11827. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  11828. separate(TRACKER.report_generator)
  11829. procedure PERCENT_COMPLETION (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE; 
  11830.                   PCT_DONE    : in PCT_DONE_TYPE) is
  11831. ----------------------------------------------------------------------
  11832. --|
  11833. --|  NAME:  PERCENT_COMPLETION
  11834. --|
  11835. --|  OVERVIEW:
  11836. --|    This report actually consists of two separate matrix reports.  It
  11837. --|    shows the percentage complete of each activity in relation to each
  11838. --|    of the subsystems.  One report is based on the original size and
  11839. --|    the other on the current size.  The activities are represented on 
  11840. --|    the x-axis and the subsystems on the y-axis.  The data printed 
  11841. --|    includes the percent completion of work for each activity by 
  11842. --|    subsystem, the total percent completion on the contract for each 
  11843. --|    activity and for each subsystem, the percent available at start for 
  11844. --|    each subsystem and for each activity, and the percent completion of 
  11845. --|    work for the entire project for each subsystem and activity.
  11846. --|
  11847. --|  EXCEPTIONS HANDLED:
  11848. --|    others   an error message is printed and execution continues
  11849. --|
  11850. --|  HISTORY:
  11851. --|    written by   Bonnie Burkhardt   March 1985
  11852. --|
  11853. ----------------------------------------------------------------------
  11854.  
  11855.   use SS_LIST_PKG; use AC_LIST_PKG;
  11856.  
  11857.   HEADER1      : string (1..132) := (others => ' ');
  11858.   HEADER2      : string (1..132) := (others => ' ');
  11859.   HEADER_LINES : string (1..132) := (others => ' ');
  11860.  
  11861.   END_LIST   : boolean := false;
  11862.   AC_PTR     : activity_pointer;
  11863.   SS_INDEX   : integer := 0;
  11864.   SS_PTR     : subsystem_pointer;
  11865.   TITLE      : string (1..54);
  11866.   TITLE_ORIG : constant string 
  11867.     := "ORIGINAL ESTIMATE OF PERCENT COMPLETE WITHIN SUBSYSTEM";
  11868.   TITLE_CUR  : constant string 
  11869.     := "CURRENT ESTIMATE OF PERCENT COMPLETE WITHIN SUBSYSTEM ";
  11870.  
  11871.   procedure INIT_PCT_HEADERS is separate;
  11872.  
  11873. begin
  11874.   INIT_PCT_HEADERS;
  11875.   if ORIG_OR_CUR = CURRENT then
  11876.     TITLE := TITLE_CUR;
  11877.   else
  11878.     TITLE := TITLE_ORIG;
  11879.   end if;
  11880.   START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  11881.  
  11882.   -- print out each line of the report
  11883.   start_walk(SS_LIST);
  11884.   loop
  11885.     walk(SS_LIST, SS_PTR, END_LIST);
  11886.     exit when END_LIST;
  11887.     SS_INDEX := SS_INDEX + 1;
  11888.  
  11889.     -- print out subsystem
  11890.     set_col(report_file, 2); put(report_file, SS_PTR.name);
  11891.     set_col(report_file, 14); 
  11892.     for AC_INDEX in 1..num_of_activities loop
  11893.       put(report_file, PCT_DONE.BY_SS_AND_AC(SS_INDEX,AC_INDEX),3,2,0); 
  11894.       put(report_file,"%  ");
  11895.     end loop;
  11896.  
  11897.     -- print out totals for this subsystem
  11898.     set_col(report_file, 108); 
  11899.     put(report_file, PCT_DONE.BY_SS(SS_INDEX),3,2,0); put(report_file,'%');
  11900.     set_col(report_file, 117); 
  11901.     put(report_file, PCT_DONE.START_BY_SS(SS_INDEX),3,2,0); put(report_file,'%');
  11902.     set_col(report_file, 126); 
  11903.     put(report_file, PCT_DONE.ENTIRE_BY_SS(SS_INDEX),3,2,0); put(report_file,'%');
  11904.     new_line(report_file);
  11905.   end loop;
  11906.  
  11907.   -- print out totals on contract by activity
  11908.   put(report_file, HEADER_LINES);
  11909.   new_line(report_file);
  11910.   set_col(report_file, 2); put(report_file, "TOTALS ON"); new_line(report_file);
  11911.   set_col(report_file, 2); put(report_file, "CONTRACT:"); 
  11912.   set_col(report_file, 14); 
  11913.   for AC_INDEX in 1..num_of_activities loop
  11914.     put(report_file, PCT_DONE.BY_AC(AC_INDEX),3,2,0); 
  11915.     put(report_file,"%  ");
  11916.   end loop;
  11917.  
  11918.   -- print out grand totals for this subsystem
  11919.   set_col(report_file, 108); 
  11920.   put(report_file, PCT_DONE.CONTRACT,3,2,0); put(report_file,'%');
  11921.   set_col(report_file, 117); 
  11922.   put(report_file, PCT_DONE.START,3,2,0); put(report_file,'%');
  11923.   set_col(report_file, 126); 
  11924.   put(report_file, PCT_DONE.ENTIRE,3,2,0); put(report_file,'%');
  11925.   new_line(report_file,2);
  11926.  
  11927.   -- print out totals at start by activity
  11928.   set_col(report_file, 2); put(report_file, "% AVAIL"); new_line(report_file);
  11929.   set_col(report_file, 2); put(report_file, "START:"); 
  11930.   set_col(report_file, 14); 
  11931.   start_walk(AC_LIST);
  11932.   loop
  11933.     walk(AC_LIST, AC_PTR, END_LIST);
  11934.     exit when END_LIST;
  11935.     put(report_file, AC_PTR.percent_at_start,3,2,0); 
  11936.     put(report_file,"%  ");
  11937.   end loop;
  11938.   new_line(report_file,2);
  11939.  
  11940.   -- print out totals on entire project by activity
  11941.   set_col(report_file, 2); put(report_file, "% ENTIRE"); new_line(report_file);
  11942.   set_col(report_file, 2); put(report_file, "PROJECT:"); 
  11943.   set_col(report_file, 14); 
  11944.   for AC_INDEX in 1..num_of_activities loop
  11945.     put(report_file, PCT_DONE.ENTIRE_BY_AC(AC_INDEX),3,2,0); 
  11946.     put(report_file,"%  ");
  11947.   end loop;
  11948.  
  11949. exception
  11950.   when others => put_line("exception raised in PERCENT COMPLETION REPORT");
  11951. end PERCENT_COMPLETION;
  11952.  
  11953.  
  11954. separate(TRACKER.report_generator.percent_completion)
  11955. procedure INIT_PCT_HEADERS is 
  11956. ----------------------------------------------------------------------
  11957. --|
  11958. --|  NAME:  INIT_PCT_HEADERS 
  11959. --|
  11960. --|  OVERVIEW:
  11961. --|    This procedure initalizes the headers for the Percent Complete
  11962. --|    by Subsystem Report.
  11963. --|
  11964. --|  EXCEPTIONS HANDLED:
  11965. --|    none
  11966. --|
  11967. --|  HISTORY:
  11968. --|    written by   Bonnie Burkhardt   March 1985
  11969. --|
  11970. ----------------------------------------------------------------------
  11971.  
  11972.   DASHES   : string (1..15)  := (others => '-');
  11973.   AC_INDEX : integer := 0;
  11974.  
  11975. begin
  11976.   -- initialize the headers
  11977.   HEADER1(108..113) := "% DONE";
  11978.   HEADER1(117..123) := "% AVAIL";
  11979.   HEADER1(126..132) := "%ENTIRE";
  11980.  
  11981.   HEADER2(2..10)    := "SUBSYSTEM";
  11982.   HEADER2(108..115) := "CONTRACT";
  11983.   HEADER2(117..124) := "AT START";
  11984.   HEADER2(126..132) := "PROJECT";
  11985.  
  11986.   HEADER_LINES (2..10)    := DASHES(1..9);
  11987.   HEADER_LINES (108..115) := DASHES(1..8);
  11988.   HEADER_LINES (117..124) := DASHES(1..8);
  11989.   HEADER_LINES (126..132) := DASHES(1..7);
  11990.  
  11991.   -- initialize the header for the activity data
  11992.   start_walk(AC_LIST);
  11993.   loop
  11994.     walk (AC_LIST, AC_PTR, END_LIST);
  11995.     exit when END_LIST;
  11996.     AC_INDEX := AC_INDEX + 1;
  11997.     HEADER2(5+9*AC_INDEX..11+9*AC_INDEX) := AC_PTR.name(1..7);
  11998.     HEADER_LINES(5+9*AC_INDEX..11+9*AC_INDEX) := DASHES(1..7);
  11999.   end loop;
  12000.  
  12001. end INIT_PCT_HEADERS;
  12002. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12003. --rprinted.ada
  12004. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12005. separate(TRACKER.REPORT_GENERATOR)
  12006. procedure REPORTS_PRINTED_LIST is
  12007. ----------------------------------------------------------------------
  12008. --|  NAME:  REPORTS_PRINTED_LIST
  12009. --|
  12010. --|  OVERVIEW:
  12011. --|    This procedure is not on the report menu, but is always the last
  12012. --|    report printed whenever two or more reports are output.  The output
  12013. --|    of this report is simply a listing of all the reports printed in
  12014. --|    the current TRACKER run.
  12015. --|    
  12016. --|  EXCEPTIONS HANDLED:
  12017. --|    none
  12018. --|
  12019. --|  HISTORY:
  12020. --|    written by   May Lee   March 1985
  12021. ----------------------------------------------------------------------
  12022.  
  12023.   use VT100;
  12024.  
  12025.   dotted_line : string(1..132) := (others => '=');
  12026.   type rep_name is array(1..12) of string(1..50);
  12027.   report_name : rep_name;
  12028.  
  12029. begin
  12030.   -- initialize the array of report names
  12031.   report_name(1)  := "  Parameter Data List                             ";
  12032.   report_name(2)  := "  Tracker Comments                                ";
  12033.   report_name(3)  := "  All Element Status Report                       ";
  12034.   report_name(4)  := "  List By Subsystem                               ";
  12035.   report_name(5)  := "  List By Milestone                               ";
  12036.   report_name(6)  := "  List By Person                                  ";
  12037.   report_name(7)  := "  Subsystem Summary                               ";
  12038.   report_name(8)  := "  Milestone Summary                               ";
  12039.   report_name(9)  := "  Work Units Per Subsystem                        ";
  12040.   report_name(10) := "  Percent Completion Of Work Within Subsystem     ";
  12041.   report_name(11) := "  Distribution Of Remaining Work Within Subsystems";
  12042.   report_name(12) := "  Completion Date For Milestones                  ";
  12043.  
  12044.   -- print out the names of the reports printed
  12045.   new_page( report_file );
  12046.   set_col(report_file, 58); -- to center the title
  12047.   put_line(report_file, "REPORTS  PRINTED");
  12048.   put(report_file, dotted_line);
  12049.   new_line(report_file,4); 
  12050.   for i in 1..12 loop
  12051.     if VT100.print_report(i) then
  12052.       put(report_file, report_name(i));
  12053.       new_line(report_file);
  12054.     end if;
  12055.   end loop;
  12056. end REPORTS_PRINTED_LIST;
  12057. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12058. --rsumms.ada
  12059. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12060. separate(TRACKER.report_generator)
  12061. procedure MILESTONE_SUMMARY is
  12062. ----------------------------------------------------------------------
  12063. --|  NAME:  MILESTONE_SUMMARY
  12064. --|
  12065. --|  OVERVIEW:
  12066. --|    This report is a two dimensional matrix that presents a summary
  12067. --|    of the remaining man-hours of work for each person on the project
  12068. --|    in relation to each milestone.  The personnel are on the x-axis
  12069. --|    and the milestones are on the y-axis.  Calculations for man-hours
  12070. --|    are based upon current work units.  The data printed includes
  12071. --|    remaining man-hours of work for each person by milestone, total
  12072. --|    remaining work in man-hours for each person, total remaining
  12073. --|    work in man-hours for each milestone, total remaining work for
  12074. --|    the entire project (sum of milestone totals), the percent complete
  12075. --|    for each milestone, and the percent complete for the entire project.
  12076. --|    If more than 10 people are assigned to the project, the Milestone
  12077. --|    Summary Report is repeated listin 10 people at a time until all
  12078. --|    people have been included on the report.
  12079. --|
  12080. --|  EXCEPTIONS HANDLED:
  12081. --|    others   an error message is printed and execution continues
  12082. --|
  12083. --|  HISTORY:
  12084. --|    written by   Bonnie Burkhardt   March 1985
  12085. ----------------------------------------------------------------------
  12086.  
  12087.   use AC_LIST_PKG; use EL_LIST_PKG; use MS_LIST_PKG; use PR_LIST_PKG;
  12088.  
  12089.   HEADER1 : string (1..132) := (others => ' ');
  12090.   HEADER2 : string (1..132) := (others => ' ');
  12091.   HEADER_LINES  : string (1..132) := (others => ' ');
  12092.  
  12093.   END_LIST    : boolean := false;
  12094.   MAX_PR_ON_PAGE : constant integer := 10;
  12095.   MS_INDEX    : integer := 0;
  12096.   MS_PTR      : MILESTONE_pointer;
  12097.   PR_INITIALS : array (1..num_of_people) of pr_init_type := (others => "  ");
  12098.   PR_INDEX    : integer := 0;
  12099.   PR_PTR      : personnel_pointer;
  12100.   START_PR    : integer := 1;
  12101.   STOP_PR     : integer := num_of_people;
  12102.   TITLE       : constant string := "MILESTONE SUMMARY REPORT";
  12103.   TIME_DONE     : array (1..num_of_people) of float := (others => 0.0);
  12104.   TOT_TIME_DONE : array (1..num_of_people) of float := (others => 0.0);
  12105.   MS_TIME       : float := 0.0;
  12106.   TOT_MS_TIME   : float := 0.0;
  12107.  
  12108.   procedure CALC_SUMMS_TOTALS is separate;
  12109.   procedure INIT_SUMMS_HEADERS is separate;
  12110.   procedure PRINT_SUMMS is separate;
  12111.   procedure PRINT_SUMMS_TOTALS is separate;
  12112.  
  12113. begin
  12114.   -- initialize the initials array
  12115.   start_walk(PR_LIST);
  12116.   PR_INDEX := 0;
  12117.   loop
  12118.     walk (PR_LIST, PR_PTR, END_LIST);
  12119.     exit when END_LIST;
  12120.     PR_INDEX := PR_INDEX + 1;
  12121.     PR_INITIALS(PR_INDEX) := PR_PTR.initials;
  12122.   end loop;
  12123.     
  12124.   -- print out each page of the report, only 10 personnel will fit on a page
  12125.   while START_PR <= num_of_people loop
  12126.     if STOP_PR - START_PR >= MAX_PR_ON_PAGE then
  12127.       STOP_PR := START_PR + MAX_PR_ON_PAGE - 1;
  12128.     else
  12129.       STOP_PR := num_of_people;
  12130.     end if;
  12131.     INIT_SUMMS_HEADERS;
  12132.     START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  12133.  
  12134.     -- print out each milestone's summary
  12135.     start_walk(MS_LIST);
  12136.     loop
  12137.       walk(MS_LIST, MS_PTR, END_LIST);
  12138.       exit when END_LIST;
  12139.       MS_INDEX := MS_INDEX + 1;
  12140.       CALC_SUMMS_TOTALS;
  12141.       PRINT_SUMMS;
  12142.     end loop;
  12143.     PRINT_SUMMS_TOTALS;
  12144.     START_PR := START_PR + MAX_PR_ON_PAGE;
  12145.   end loop;
  12146. exception
  12147.   when others => put_line("exception raised in MILESTONE SUMMARY REPORT");
  12148. end MILESTONE_SUMMARY;
  12149.  
  12150.  
  12151.  
  12152. separate(TRACKER.report_generator.MILESTONE_SUMMARY)
  12153. procedure INIT_SUMMS_HEADERS is
  12154. ----------------------------------------------------------------------
  12155. --|  NAME:  INIT_SUMMS_HEADERS
  12156. --|
  12157. --|  OVERVIEW:
  12158. --|    This procedure initializes all the headers of the MILESTONE summary 
  12159. --|    report.
  12160. --|
  12161. --|  EXCEPTIONS HANDLED:
  12162. --|    none
  12163. --|
  12164. --|  HISTORY:
  12165. --|    written by   Bonnie Burkhardt   March 1985
  12166. ----------------------------------------------------------------------
  12167.  
  12168.   DASHES : constant string(1..15) := (others => '-');
  12169.  
  12170. begin
  12171.   HEADER1 := (others => ' ');
  12172.   HEADER2 := (others => ' ');
  12173.   HEADER_LINES := (others => ' ');
  12174.  
  12175.   -- initialize the headers
  12176.   HEADER1(115..121) := "MAN-HRS";
  12177.   HEADER1(125..131) := "PERCENT";
  12178.  
  12179.   HEADER2(2..10) := "MILESTONE";
  12180.   HEADER2(115..121) := "TO COMP";
  12181.   HEADER2(125..132) := "COMPLETE";
  12182.  
  12183.   HEADER_LINES (2..10) := DASHES(1..9);
  12184.   HEADER_LINES (115..121) := DASHES(1..7);
  12185.   HEADER_LINES (125..132) := DASHES(1..8);
  12186.  
  12187.   -- insert the person's initials into the headers
  12188.   for PR in 0 .. STOP_PR - START_PR loop
  12189.     HEADER2(16+PR*9..17+PR*9) := PR_INITIALS(PR+START_PR);
  12190.     HEADER_LINES(14+PR*9..20+PR*9) := DASHES(1..7);
  12191.   end loop;
  12192. end INIT_SUMMS_HEADERS;
  12193.  
  12194.  
  12195.  
  12196. separate(TRACKER.report_generator.MILESTONE_SUMMARY)
  12197. procedure CALC_SUMMS_TOTALS is 
  12198. ----------------------------------------------------------------------
  12199. --|  NAME:  CALC_SUMMS_TOTALS 
  12200. --|
  12201. --|  OVERVIEW:
  12202. --|    This procedure calculates the total amount of time left by
  12203. --|    MILESTONE and by person.
  12204. --|
  12205. --|  EXCEPTIONS HANDLED:
  12206. --|    none
  12207. --|
  12208. --|  HISTORY:
  12209. --|    written by   Bonnie Burkhardt   March 1985
  12210. ----------------------------------------------------------------------
  12211.  
  12212.   END_LIST   : boolean := false;
  12213.   ELE_PTR    : element_pointer;
  12214.   PR_INDEX   : integer := 0;
  12215.   PR_PTR     : personnel_pointer;
  12216.  
  12217. begin
  12218.   TIME_DONE := (others => 0.0);
  12219.   MS_TIME := 0.0;
  12220.  
  12221.   -- find the totals for this milestone
  12222.   PR_INDEX := 0;
  12223.   start_walk(PR_LIST);
  12224.   loop
  12225.     walk(PR_LIST, PR_PTR, END_LIST);
  12226.     exit when END_LIST;
  12227.     PR_INDEX := PR_INDEX + 1;
  12228.  
  12229.     -- sum the time left to complete for each element that has
  12230.     -- this milestone and this person
  12231.     start_walk(PR_PTR.element_list);
  12232.     loop
  12233.       walk(PR_PTR.element_list, ELE_PTR, END_LIST);
  12234.       exit when END_LIST;
  12235.  
  12236.       if ELE_PTR.milestone_num = MS_PTR.number then
  12237.     if ELE_PTR.more_than_one_person then
  12238.       for AC_INDEX in 1..num_of_activities loop
  12239.         if ELE_PTR.people_initials(AC_INDEX) = PR_PTR.initials then
  12240.           TIME_DONE(PR_INDEX) := TIME_DONE(PR_INDEX) + 
  12241.                      ELE_PTR.hours_left(AC_INDEX);
  12242.         end if;
  12243.       end loop;
  12244.     else
  12245.       TIME_DONE(PR_INDEX) := TIME_DONE(PR_INDEX) + ELE_PTR.hours_to_complete;
  12246.     end if;
  12247.       end if;
  12248.  
  12249.     end loop;
  12250.     TOT_TIME_DONE(PR_INDEX) := TOT_TIME_DONE(PR_INDEX) + TIME_DONE(PR_INDEX);
  12251.     MS_TIME := MS_TIME + TIME_DONE(PR_INDEX);
  12252.   end loop;
  12253.   TOT_MS_TIME := TOT_MS_TIME + MS_TIME;
  12254. end CALC_SUMMS_TOTALS;
  12255.  
  12256.  
  12257.  
  12258. separate(TRACKER.report_generator.MILESTONE_SUMMARY)
  12259. procedure PRINT_SUMMS is
  12260. ----------------------------------------------------------------------
  12261. --|  NAME:  PRINT_SUMMS
  12262. --|
  12263. --|  OVERVIEW:
  12264. --|    This procedure prints out a milestone line. This line includes 
  12265. --|    the amount of time needed to complete the milestone by person,
  12266. --|    the total time needed for the milestone, and the milestone's 
  12267. --|    percent complete.
  12268. --|
  12269. --|  EXCEPTIONS HANDLED:
  12270. --|    none
  12271. --|
  12272. --|  HISTORY:
  12273. --|    written by   Bonnie Burkhardt   March 1985
  12274. ----------------------------------------------------------------------
  12275.  
  12276. begin
  12277.   -- print out the milestone
  12278.   set_col(report_file, 5); put(report_file, MS_PTR.number,3);
  12279.   set_col(report_file, 14);
  12280.   for PR_INDEX in START_PR .. STOP_PR loop
  12281.     put(report_file, TIME_DONE(PR_INDEX),5,1,0); 
  12282.     put(report_file,"  ");
  12283.   end loop;
  12284.  
  12285.   set_col(report_file, 115); put(report_file, MS_TIME,6,1,0);
  12286.   set_col(report_file, 125); 
  12287.   put(report_file, CURRENT_PCT_DONE.BY_MS(MS_INDEX),3,2,0);
  12288.   put(report_file,'%'); new_line(report_file);
  12289. end PRINT_SUMMS;
  12290.  
  12291.  
  12292.  
  12293.  
  12294. separate(TRACKER.report_generator.MILESTONE_SUMMARY)
  12295. procedure PRINT_SUMMS_TOTALS is
  12296. ----------------------------------------------------------------------
  12297. --|  NAME:  PRINT_SUMMS_TOTALS 
  12298. --|
  12299. --|  OVERVIEW:
  12300. --|    This procedure prints out the milestone totals.  This data includes
  12301. --|    the total number of man-hours needed for each person to complete the
  12302. --|    project, the grand total man-hours left on the project, and the
  12303. --|    grand total percent complete on the project.
  12304. --|
  12305. --|  EXCEPTIONS HANDLED:
  12306. --|    none
  12307. --|
  12308. --|  HISTORY:
  12309. --|    written by   Bonnie Burkhardt   March 1985
  12310. ----------------------------------------------------------------------
  12311.  
  12312. begin
  12313.   -- output totals
  12314.   set_col(report_file, 13); put_line(report_file, HEADER_LINES(13..132));
  12315.  
  12316.   set_col(report_file, 2); put(report_file, "TOTALS:");
  12317.   set_col(report_file, 13);
  12318.   for PR_INDEX in START_PR .. STOP_PR loop
  12319.     put(report_file, TOT_TIME_DONE(PR_INDEX),6,1,0); 
  12320.     put(report_file," ");
  12321.   end loop;
  12322.  
  12323.   set_col(report_file, 115); put(report_file, TOT_MS_TIME,6,1,0);
  12324.   set_col(report_file, 125); put(report_file, CURRENT_PCT_DONE.CONTRACT,3,2,0);
  12325.   put(report_file,'%'); new_line(report_file);
  12326. end PRINT_SUMMS_TOTALS;
  12327. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12328. --rsumss.ada
  12329. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12330. separate(TRACKER.report_generator)
  12331. procedure SUBSYSTEM_SUMMARY is
  12332. ----------------------------------------------------------------------
  12333. --|  NAME:  SUBSYSTEM_SUMMARY
  12334. --|
  12335. --|  OVERVIEW:
  12336. --|    This report is a two dimensional matrix that presents a summary
  12337. --|    of the remaining man-hours of work for each person on the project
  12338. --|    in relation to each subsystem.  The personnel are displayed on
  12339. --|    the x-axis and the subsytems on the y-axis.  Man-hour calculations
  12340. --|    are based on current work units.  The data printed includes 
  12341. --|    remaining man-hours of work for each person by subsystem, the 
  12342. --|    total remaining work in man-hours for each person, the total
  12343. --|    remaining work in man-hours to complete each subsystem, the total
  12344. --|    remaining work for the entire project (sum of subsystem totals),
  12345. --|    the percent complete for each subsystem, and the percent complete
  12346. --|    for the entire project.  If more than 10 people are assigned to 
  12347. --|    the project, the subsystem summary report is repeated listing 10 
  12348. --|    people at a time until all people have been included on a report.
  12349. --|
  12350. --|  EXCEPTIONS HANDLED:
  12351. --|    others   an error message is printed and execution continues
  12352. --|
  12353. --|  HISTORY:
  12354. --|    written by   Bonnie Burkhardt   March 1985
  12355. ----------------------------------------------------------------------
  12356.  
  12357.   use AC_LIST_PKG; use EL_LIST_PKG; use SS_LIST_PKG; use PR_LIST_PKG;
  12358.  
  12359.   HEADER1 : string (1..132) := (others => ' ');
  12360.   HEADER2 : string (1..132) := (others => ' ');
  12361.   HEADER_LINES  : string (1..132) := (others => ' ');
  12362.  
  12363.   END_LIST    : boolean := false;
  12364.   MAX_PR_ON_PAGE : constant integer := 10;
  12365.   PR_INITIALS : array (1..num_of_people) of pr_init_type := (others => "  ");
  12366.   PR_INDEX    : integer := 0;
  12367.   PR_PTR      : personnel_pointer;
  12368.   SS_INDEX    : integer := 0;
  12369.   SS_PTR      : subsystem_pointer;
  12370.   START_PR    : integer := 1;
  12371.   STOP_PR     : integer := num_of_people;
  12372.   TITLE       : constant string := "SUBSYSTEM SUMMARY REPORT";
  12373.   TIME_DONE   : array (1..num_of_people) of float := (others => 0.0);
  12374.   TOT_TIME_DONE : array (1..num_of_people) of float := (others => 0.0);
  12375.   SS_TIME       : float := 0.0;
  12376.   TOT_SS_TIME   : float := 0.0;
  12377.  
  12378.   procedure CALC_SUMSS_TOTALS is separate;
  12379.   procedure INIT_SUMSS_HEADERS is separate;
  12380.   procedure PRINT_SUMSS is separate;
  12381.   procedure PRINT_SUMSS_TOTALS is separate;
  12382.  
  12383. begin
  12384.   -- initialize the initials array
  12385.   start_walk(PR_LIST);
  12386.   PR_INDEX := 0;
  12387.   loop
  12388.     walk (PR_LIST, PR_PTR, END_LIST);
  12389.     exit when END_LIST;
  12390.     PR_INDEX := PR_INDEX + 1;
  12391.     PR_INITIALS(PR_INDEX) := PR_PTR.initials;
  12392.   end loop;
  12393.  
  12394.   -- print out each page of the report, only 10 personnel will fit on a page
  12395.   while START_PR <= num_of_people loop
  12396.     if STOP_PR - START_PR >= MAX_PR_ON_PAGE then
  12397.       STOP_PR := START_PR + MAX_PR_ON_PAGE - 1;
  12398.     else
  12399.       STOP_PR := num_of_people;
  12400.     end if;
  12401.     INIT_SUMSS_HEADERS;
  12402.     START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  12403.  
  12404.     -- print out each subsystem's time left
  12405.     SS_INDEX := 0;
  12406.     start_walk(SS_LIST);
  12407.     loop
  12408.       SS_INDEX := SS_INDEX + 1;
  12409.       walk(SS_LIST, SS_PTR, END_LIST);
  12410.       exit when END_LIST;
  12411.       CALC_SUMSS_TOTALS;
  12412.       PRINT_SUMSS;
  12413.     end loop;
  12414.     PRINT_SUMSS_TOTALS;
  12415.     START_PR := START_PR + MAX_PR_ON_PAGE;
  12416.   end loop;
  12417. exception
  12418.   when others => put_line("exception raised in LIST BY SUBSYSTEM REPORT");
  12419. end SUBSYSTEM_SUMMARY;
  12420.  
  12421.  
  12422.  
  12423. separate(TRACKER.report_generator.SUBSYSTEM_SUMMARY)
  12424. procedure INIT_SUMSS_HEADERS is
  12425. ----------------------------------------------------------------------
  12426. --|  NAME:  INIT_SUMSS_HEADERS
  12427. --|
  12428. --|  OVERVIEW:
  12429. --|    This procedure initializes all the headers of the subsystem summary 
  12430. --|    report.
  12431. --|
  12432. --|  EXCEPTIONS HANDLED:
  12433. --|    none
  12434. --|
  12435. --|  HISTORY:
  12436. --|    written by   Bonnie Burkhardt   March 1985
  12437. ----------------------------------------------------------------------
  12438.  
  12439.   DASHES : constant string(1..15) := (others => '-');
  12440.  
  12441. begin
  12442.   HEADER1 := (others => ' ');
  12443.   HEADER2 := (others => ' ');
  12444.   HEADER_LINES := (others => ' ');
  12445.  
  12446.   -- initialize the headers
  12447.   HEADER1(115..121) := "MAN-HRS";
  12448.   HEADER1(125..131) := "PERCENT";
  12449.  
  12450.   HEADER2(2..10) := "SUBSYSTEM";
  12451.   HEADER2(115..121) := "TO COMP";
  12452.   HEADER2(125..132) := "COMPLETE";
  12453.  
  12454.   HEADER_LINES (2..10) := DASHES(1..9);
  12455.   HEADER_LINES (115..121) := DASHES(1..7);
  12456.   HEADER_LINES (125..132) := DASHES(1..8);
  12457.  
  12458.   -- insert the person's initials into the headers
  12459.   for PR in 0 .. STOP_PR - START_PR loop
  12460.     HEADER2(16+PR*9..17+PR*9) := PR_INITIALS(PR+START_PR);
  12461.     HEADER_LINES(14+PR*9..20+PR*9) := DASHES(1..7);
  12462.   end loop;
  12463. end INIT_SUMSS_HEADERS;
  12464.  
  12465.  
  12466.  
  12467. separate(TRACKER.report_generator.SUBSYSTEM_SUMMARY)
  12468. procedure CALC_SUMSS_TOTALS is 
  12469. ----------------------------------------------------------------------
  12470. --|  NAME:  CALC_SUMSS_TOTALS 
  12471. --|
  12472. --|  OVERVIEW:
  12473. --|    This procedure calculates the total amount of time left by
  12474. --|    subsystem and by person.
  12475. --|
  12476. --|  EXCEPTIONS HANDLED:
  12477. --|    none
  12478. --|
  12479. --|  HISTORY:
  12480. --|    written by   Bonnie Burkhardt   March 1985
  12481. ----------------------------------------------------------------------
  12482.  
  12483.   END_LIST   : boolean := false;
  12484.   ELE_PTR    : element_pointer;
  12485.   PR_INDEX   : integer := 0;
  12486.   PR_PTR     : personnel_pointer;
  12487.  
  12488. begin
  12489.   TIME_DONE := (others => 0.0);
  12490.   SS_TIME := 0.0;
  12491.  
  12492.   -- find the totals for each subsystem
  12493.   PR_INDEX := 0;
  12494.   start_walk(PR_LIST);
  12495.   loop
  12496.     walk(PR_LIST, PR_PTR, END_LIST);
  12497.     exit when END_LIST;
  12498.     PR_INDEX := PR_INDEX + 1;
  12499.  
  12500.     -- sum the time left to complete for each element that has
  12501.     -- this subsystem and this person
  12502.     start_walk(PR_PTR.element_list);
  12503.     loop
  12504.       walk(PR_PTR.element_list, ELE_PTR, END_LIST);
  12505.       exit when END_LIST;
  12506.  
  12507.       if ELE_PTR.subsystem_name = SS_PTR.name then
  12508.     if ELE_PTR.more_than_one_person then
  12509.       for AC_INDEX in 1..num_of_activities loop
  12510.         TIME_DONE(PR_INDEX) := TIME_DONE(PR_INDEX) + 
  12511.                     ELE_PTR.hours_left(AC_INDEX);
  12512.       end loop;
  12513.     else
  12514.       TIME_DONE(PR_INDEX) := TIME_DONE(PR_INDEX) + 
  12515.                  ELE_PTR.hours_to_complete;
  12516.     end if;
  12517.       end if;
  12518.  
  12519.     end loop;
  12520.     TOT_TIME_DONE(PR_INDEX) := TOT_TIME_DONE(PR_INDEX) + TIME_DONE(PR_INDEX);
  12521.     SS_TIME := SS_TIME + TIME_DONE(PR_INDEX);
  12522.   end loop;
  12523.   TOT_SS_TIME := TOT_SS_TIME + SS_TIME;
  12524. end CALC_SUMSS_TOTALS;
  12525.  
  12526.  
  12527.  
  12528. separate(TRACKER.report_generator.SUBSYSTEM_SUMMARY)
  12529. procedure PRINT_SUMSS is
  12530. ----------------------------------------------------------------------
  12531. --|  NAME:  PRINT_SUMSS
  12532. --|
  12533. --|  OVERVIEW:
  12534. --|    This procedure prints out an subsystem line. This line includes the 
  12535. --|    the remaining man-hours of work to complete this subsystem by person,
  12536. --|    the current percent complete, and the  total man-hours required to
  12537. --|    complete this subsystem.
  12538. --|
  12539. --|  EXCEPTIONS HANDLED:
  12540. --|    none
  12541. --|
  12542. --|  HISTORY:
  12543. --|    written by   Bonnie Burkhardt   March 1985
  12544. ----------------------------------------------------------------------
  12545.  
  12546. begin
  12547.   -- print out this subsystem
  12548.   set_col(report_file, 2); put(report_file, SS_PTR.name);
  12549.   set_col(report_file, 14);
  12550.   for PR_INDEX in START_PR .. STOP_PR loop
  12551.     put(report_file, TIME_DONE(PR_INDEX),5,1,0); 
  12552.     put(report_file,"  ");
  12553.   end loop;
  12554.  
  12555.   set_col(report_file, 115); put(report_file, SS_TIME,6,1,0);
  12556.   set_col(report_file, 125); 
  12557.     put(report_file, CURRENT_PCT_DONE.BY_SS(SS_INDEX),3,2,0);
  12558.   put(report_file,'%'); new_line(report_file);
  12559. end PRINT_SUMSS;
  12560.  
  12561.  
  12562.  
  12563.  
  12564. separate(TRACKER.report_generator.SUBSYSTEM_SUMMARY)
  12565. procedure PRINT_SUMSS_TOTALS is
  12566. ----------------------------------------------------------------------
  12567. --|  NAME:  PRINT_SUMSS_TOTALS
  12568. --|
  12569. --|  OVERVIEW:
  12570. --|    This procedure prints out a subsystem line. This line includes the 
  12571. --|    the remaining man-hours of work to complete this subsystem by person,
  12572. --|    the current percent complete, and the total man-hours required to
  12573. --|    complete this subsystem.
  12574. --|
  12575. --|  EXCEPTIONS HANDLED:
  12576. --|    none
  12577. --|
  12578. --|  HISTORY:
  12579. --|    written by   Bonnie Burkhardt   March 1985
  12580. ----------------------------------------------------------------------
  12581.  
  12582. begin
  12583.   -- output totals
  12584.   set_col(report_file, 13); put_line(report_file, HEADER_LINES(13..132));
  12585.   set_col(report_file, 2); put(report_file, "TOTALS:");
  12586.   set_col(report_file, 13);
  12587.   for PR_INDEX in START_PR .. STOP_PR loop
  12588.     put(report_file, TOT_TIME_DONE(PR_INDEX),6,1,0); 
  12589.     put(report_file," ");
  12590.   end loop;
  12591.  
  12592.   set_col(report_file, 115); put(report_file, TOT_SS_TIME,6,1,0);
  12593.   set_col(report_file, 125); put(report_file, CURRENT_PCT_DONE.CONTRACT,3,2,0);
  12594.   put(report_file,'%'); new_line(report_file);
  12595. end PRINT_SUMSS_TOTALS;
  12596. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12597. --rworkbyss.ada
  12598. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12599. separate(TRACKER.report_generator)
  12600. procedure WORK_UNITS_PER_SS is
  12601. ----------------------------------------------------------------------
  12602. --|
  12603. --|  NAME:  WORK_UNITS_PER_SS 
  12604. --|
  12605. --|  OVERVIEW:
  12606. --|    This report displays the total amount of original and current size
  12607. --|    units for each defined subsystem in the project.  Total original
  12608. --|    and current size for the project are given as summary data at the
  12609. --|    bottom of the report.
  12610. --|
  12611. --|  EXCEPTIONS HANDLED:
  12612. --|    others   an error message is printed and processing continues
  12613. --|
  12614. --|  HISTORY:
  12615. --|    written by   Bonnie Burkhardt   March 1985
  12616. --|
  12617. ----------------------------------------------------------------------
  12618.  
  12619.   use SS_LIST_PKG; use CALENDAR;
  12620.  
  12621.   HEADER1       : string (1..132) := (others => ' ');
  12622.   HEADER2       : string (1..132) := (others => ' ');
  12623.   HEADER_LINES  : string (1..132) := (others => ' ');
  12624.  
  12625.   END_LIST      : boolean   := false;
  12626.   NEW_DATE      : date_type := null_date;
  12627.   NEW_TOT_DATE  : date_type := null_date;
  12628.   OLD_DATE      : date_type := null_date;
  12629.   OLD_TOT_DATE  : date_type := null_date;
  12630.   SS_INDEX      : integer   := 0;
  12631.   SS_PTR        : subsystem_pointer;
  12632.   SS_ORIG_SIZE  : integer range 0..999_999 := 0;
  12633.   SS_CUR_SIZE   : integer range 0..999_999 := 0;
  12634.   SS_EQ_SIZE    : integer range 0..999_999 := 0;
  12635.   TOT_ORIG_SIZE : integer range 0..999_999 := 0;
  12636.   TOT_CUR_SIZE  : integer range 0..999_999 := 0;
  12637.   TOT_EQ_SIZE   : integer range 0..999_999 := 0;
  12638.   TITLE         : constant string          := "LINES OF CODE PER SUBSYSTEM";
  12639.  
  12640.   procedure INIT_SIZE_HEADERS is separate;
  12641.   procedure CALC_SIZE is separate;
  12642.  
  12643. begin
  12644.   INIT_SIZE_HEADERS;
  12645.   START_PAGE(TITLE,"",HEADER1,HEADER2,HEADER_LINES);
  12646.  
  12647.   -- print out each line of the report
  12648.   start_walk(SS_LIST);
  12649.   loop
  12650.     walk(SS_LIST, SS_PTR, END_LIST);
  12651.     exit when END_LIST;
  12652.     SS_INDEX := SS_INDEX + 1;
  12653.  
  12654.     CALC_SIZE;
  12655.  
  12656.     -- print out subsystem
  12657.     set_col(report_file, 2);  put(report_file, SS_PTR.name);
  12658.     set_col(report_file, 14); put(report_file, SS_ORIG_SIZE,6); 
  12659.     set_col(report_file, 24); put(report_file, SS_CUR_SIZE,6); 
  12660.     set_col(report_file, 34); put(report_file, SS_EQ_SIZE,6); 
  12661.     set_col(report_file, 45); put(report_file, OLD_DATE.month,2); 
  12662.       put(report_file, '/');  put(report_file, OLD_DATE.day,2); 
  12663.       put(report_file, '/');  put(report_file, OLD_DATE.year,4); 
  12664.     set_col(report_file, 59); put(report_file, NEW_DATE.month,2); 
  12665.       put(report_file, '/');  put(report_file, NEW_DATE.day,2); 
  12666.       put(report_file, '/');  put(report_file, NEW_DATE.year,4); 
  12667.     new_line(report_file);
  12668.   end loop;
  12669.  
  12670.  
  12671.   -- print out totals
  12672.   set_col(report_file, 14); put(report_file, HEADER_LINES(14..132)); 
  12673.   new_line(report_file); 
  12674.   set_col(report_file, 2);  put(report_file, "TOTALS: "); 
  12675.   set_col(report_file, 14); put(report_file, TOT_ORIG_SIZE,6); 
  12676.   set_col(report_file, 24); put(report_file, TOT_CUR_SIZE,6); 
  12677.   set_col(report_file, 34); put(report_file, TOT_EQ_SIZE,6); 
  12678.   set_col(report_file, 45); put(report_file, OLD_TOT_DATE.month,2); 
  12679.     put(report_file, '/');  put(report_file, OLD_TOT_DATE.day,2); 
  12680.     put(report_file, '/');  put(report_file, OLD_TOT_DATE.year,4); 
  12681.   set_col(report_file, 59); put(report_file, NEW_TOT_DATE.month,2); 
  12682.     put(report_file, '/');  put(report_file, NEW_TOT_DATE.day,2); 
  12683.     put(report_file, '/');  put(report_file, NEW_TOT_DATE.year,4); 
  12684.   new_line(report_file,2);
  12685.  
  12686. exception
  12687.   when others => put_line("exception raised in WORK DISTRIBUTION REPORT");
  12688. end WORK_UNITS_PER_SS;
  12689.  
  12690.  
  12691. separate(TRACKER.report_generator.WORK_UNITS_PER_SS)
  12692. procedure INIT_SIZE_HEADERS is 
  12693. ----------------------------------------------------------------------
  12694. --|
  12695. --|  NAME:  INIT_SIZE_HEADERS 
  12696. --|
  12697. --|  OVERVIEW:
  12698. --|    This procedure initalizes the headers for the Percent Complete
  12699. --|    by Subsystem Report.
  12700. --|
  12701. --|  EXCEPTIONS HANDLED:
  12702. --|    none
  12703. --|
  12704. --|  HISTORY:
  12705. --|    written by   Bonnie Burkhardt   March 1985
  12706. --|
  12707. ----------------------------------------------------------------------
  12708.  
  12709.   DASHES   : string (1..15)  := (others => '-');
  12710.  
  12711. begin
  12712.   -- initialize the headers
  12713.   HEADER1(14..21) := "ORIGINAL";
  12714.   HEADER1(24..30) := "CURRENT";
  12715.   HEADER1(34..40) := "EQ. NEW";
  12716.   HEADER1(46..51) := "OLDEST";
  12717.   HEADER1(58..68) := "MOST RECENT";
  12718.  
  12719.   HEADER2(2..10)  := "SUBSYSTEM";
  12720.   HEADER2(16..19) := "SIZE";
  12721.   HEADER2(26..29) := "SIZE";
  12722.   HEADER2(36..39) := "SIZE";
  12723.   HEADER2(44..55) := "VERIFICATION";
  12724.   HEADER2(58..69) := "VERIFICATION";
  12725.  
  12726.   HEADER_LINES (2..10)  := DASHES(1..9);
  12727.   HEADER_LINES (14..21) := DASHES(1..8);
  12728.   HEADER_LINES (24..31) := DASHES(1..8);
  12729.   HEADER_LINES (34..41) := DASHES(1..8);
  12730.   HEADER_LINES (44..55) := DASHES(1..12);
  12731.   HEADER_LINES (58..69) := DASHES(1..12);
  12732.  
  12733. end INIT_SIZE_HEADERS;
  12734.  
  12735.  
  12736.  
  12737. separate(TRACKER.report_generator.WORK_UNITS_PER_SS)
  12738. procedure CALC_SIZE is 
  12739. ----------------------------------------------------------------------
  12740. --|
  12741. --|  NAME:  CALC_SIZE 
  12742. --|
  12743. --|  OVERVIEW:
  12744. --|    This procedure calculates the total size of a given subsystem
  12745. --|    and the earliest and most recent verification date.
  12746. --|
  12747. --|  EXCEPTIONS HANDLED:
  12748. --|    none
  12749. --|
  12750. --|  HISTORY:
  12751. --|    written by   Bonnie Burkhardt   March 1985
  12752. --|
  12753. ----------------------------------------------------------------------
  12754.  
  12755.   use EL_LIST_PKG;
  12756.  
  12757.   END_LIST : boolean := false;
  12758.   ELE_PTR  : element_pointer;
  12759.  
  12760. begin
  12761.   SS_ORIG_SIZE  := 0;
  12762.   SS_CUR_SIZE   := 0;
  12763.   SS_EQ_SIZE    := 0;
  12764.  
  12765.   -- compute the totals for each subsystem
  12766.   start_walk(SS_PTR.element_list);
  12767.   loop
  12768.     walk(SS_PTR.element_list, ELE_PTR, END_LIST);
  12769.     exit when END_LIST;
  12770.  
  12771.     SS_ORIG_SIZE := SS_ORIG_SIZE + ELE_PTR.original_size;
  12772.     SS_CUR_SIZE := SS_CUR_SIZE + ELE_PTR.current_size;
  12773.     SS_EQ_SIZE := SS_EQ_SIZE + ELE_PTR.current_size - ELE_PTR.size_done_at_start;
  12774.  
  12775.     if (NEW_DATE = null_date) or (ELE_PTR.date_size_verified > NEW_DATE) then
  12776.       NEW_DATE := ELE_PTR.date_size_verified;
  12777.     end if;
  12778.     if (OLD_DATE = null_date) or (ELE_PTR.date_size_verified < OLD_DATE) then
  12779.       OLD_DATE := ELE_PTR.date_size_verified;
  12780.     end if;
  12781.   end loop;
  12782.  
  12783.   -- update the grand total sizes
  12784.   TOT_ORIG_SIZE := TOT_ORIG_SIZE + SS_ORIG_SIZE;
  12785.   TOT_CUR_SIZE := TOT_CUR_SIZE + SS_CUR_SIZE;
  12786.   TOT_EQ_SIZE := TOT_EQ_SIZE + SS_EQ_SIZE;
  12787.  
  12788.   -- update the grand total oldest and most recent verification date
  12789.   if (NEW_TOT_DATE = null_date) or (NEW_DATE > NEW_TOT_DATE) then
  12790.     NEW_TOT_DATE := NEW_DATE;
  12791.   end if;
  12792.   if (OLD_TOT_DATE = null_date) or (OLD_DATE < OLD_TOT_DATE) then
  12793.     OLD_TOT_DATE := OLD_DATE;
  12794.   end if;
  12795. end CALC_SIZE;
  12796. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12797. --rworkdist.ada
  12798. --::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
  12799. separate(TRACKER.report_generator)
  12800. procedure DISTRIBUTION_OF_WORK (ORIG_OR_CUR : in ORIG_OR_CUR_TYPE) is
  12801. ----------------------------------------------------------------------
  12802. --|
  12803. --|  NAME:  DISTRIBUTION_OF_WORK
  12804. --|
  12805. --|  OVERVIEW:
  12806. --|    This report actually consists of two separate matrix reports.
  12807. --|    It shows the total man-hours of work remaining for each activity
  12808. --|    in relation to each of the subsystems.  One report is based on the
  12809. --|    original size and the other on the current size.  The activities
  12810. --|    are represented on the x-axis and the subsystems on the y-axis.
  12811. --|    The data printed includes remaining man-hours of work for each
  12812. --|    activity by subsystem, the total remaining work in man-hours for 
  12813. --|    each activity and for each subsystem, the percent complete for 
  12814. --|    each subsystem, the grand total remaining work, the grand total
  12815. --|    percent complete, and the percentage of the total work remaining 
  12816. --|    on the entire project by activity.
  12817. --|
  12818. --|  EXCEPTIONS HANDLED:
  12819. --|    others   an error message is printed and processing continues
  12820. --|
  12821. --|  HISTORY:
  12822. --|    written by   Bonnie Burkhardt   March 1985
  12823. --|
  12824. ----------------------------------------------------------------------
  12825.  
  12826.   use SS_LIST_PKG; 
  12827.  
  12828.   HEADER1      : string (1..132) := (others => ' ');
  12829.   HEADER2      : string (1..132) := (others => ' ');
  12830.   HEADER_LINES : string (1..132) := (others => ' ');
  12831.  
  12832.   END_LIST          : boolean := false;
  12833.   SS_INDEX          : integer := 0;
  12834.   SS_PTR            : subsystem_pointer;
  12835.   SS_WORK_BY_AC     : array (1..num_of_activities) of float := (others => 0.0);
  12836.   SS_WORK           : float := 0.0;
  12837.   TOT_SS_WORK_BY_AC : array (1..num_of_activities) of float := (others => 0.0);
  12838.   TOT_SS_WORK       : float := 0.0;
  12839.   SUBTITLE          : constant string := "(in MAN-HOURS)";
  12840.   TITLE             : string (1..56);
  12841.   TITLE_ORIG : constant string 
  12842.          := "ORIGINAL DISTRIBUTION OF WORK REMAINING WITHIN SUBSYSTEM";
  12843.   TITLE_CUR  : constant string 
  12844.          := "CURRENT DISTRIBUTION OF WORK REMAINING WITHIN SUBSYSTEM ";
  12845.  
  12846.   procedure INIT_DIST_HEADERS is separate;
  12847.   procedure CALC_SS_WORK      is separate;
  12848.  
  12849. begin
  12850.   INIT_DIST_HEADERS;
  12851.   if ORIG_OR_CUR = CURRENT then
  12852.     TITLE := TITLE_CUR;
  12853.   else
  12854.     TITLE := TITLE_ORIG;
  12855.   end if;
  12856.   START_PAGE(TITLE,SUBTITLE,HEADER1,HEADER2,HEADER_LINES);
  12857.  
  12858.   -- print out each line of the report
  12859.   start_walk(SS_LIST);
  12860.   loop
  12861.     walk(SS_LIST, SS_PTR, END_LIST);
  12862.     exit when END_LIST;
  12863.     SS_INDEX := SS_INDEX + 1;
  12864.  
  12865.     CALC_SS_WORK;
  12866.  
  12867.     -- print out subsystem
  12868.     set_col(report_file, 2); put(report_file, SS_PTR.name);
  12869.     set_col(report_file, 14); 
  12870.     for AC_INDEX in 1..num_of_activities loop
  12871.       put(report_file, SS_WORK_BY_AC(AC_INDEX),6,1,0); 
  12872.       put(report_file,"  ");
  12873.     end loop;
  12874.  
  12875.     -- print out totals for this subsystem
  12876.     set_col(report_file, 115); put(report_file,SS_WORK,7,1,0);
  12877.     set_col(report_file, 126); 
  12878.     if ORIG_OR_CUR = CURRENT then
  12879.       put(report_file, CURRENT_PCT_DONE.BY_SS(SS_INDEX),3,2,0); 
  12880.       put(report_file,'%');
  12881.     else
  12882.       put(report_file, ORIGINAL_PCT_DONE.BY_SS(SS_INDEX),3,2,0); 
  12883.       put(report_file,'%');
  12884.     end if;
  12885.     new_line(report_file);
  12886.   end loop;
  12887.  
  12888.  
  12889.   -- print out totals on contract by activity
  12890.   set_col(report_file, 14); put(report_file, HEADER_LINES(14..132)); 
  12891.   new_line(report_file); 
  12892.   set_col(report_file, 2);  put(report_file, "TOTALS: "); 
  12893.   set_col(report_file, 13); 
  12894.   for AC_INDEX in 1..num_of_activities loop
  12895.     put(report_file, TOT_SS_WORK_BY_AC(AC_INDEX),7,1,0);
  12896.     put(report_file," ");
  12897.   end loop;
  12898.   set_col(report_file, 115); put(report_file, TOT_SS_WORK,7,1,0);
  12899.   set_col(report_file, 126); 
  12900.   if ORIG_OR_CUR = CURRENT then
  12901.     put(report_file, CURRENT_PCT_DONE.contract,3,2,0);  
  12902.     put(report_file,'%');
  12903.   else
  12904.     put(report_file, ORIGINAL_PCT_DONE.contract,3,2,0); 
  12905.     put(report_file,'%');
  12906.   end if;
  12907.   new_line(report_file,2);
  12908.  
  12909.   -- print out percent of total work left
  12910.   set_col(report_file, 2); put(report_file, "% OF TOTAL:"); 
  12911.   set_col(report_file, 15);
  12912.   for AC_INDEX in 1..num_of_activities loop
  12913.     if TOT_SS_WORK > 0.0 then
  12914.       put(report_file, 100.0 * TOT_SS_WORK_BY_AC(AC_INDEX) / TOT_SS_WORK,3,2,0);
  12915.     else
  12916.       put(report_file, 0.0,3,2,0);
  12917.     end if;
  12918.     if AC_INDEX < num_of_activities then
  12919.       put(report_file,"% + ");
  12920.     end if;
  12921.   end loop;
  12922.   put(report_file,"% = 100.00%");
  12923.   new_line(report_file);
  12924.  
  12925. exception
  12926.   when others => put_line("exception raised in WORK DISTRIBUTION REPORT");
  12927. end DISTRIBUTION_OF_WORK;
  12928.  
  12929.  
  12930. separate(TRACKER.report_generator.distribution_of_work)
  12931. procedure INIT_DIST_HEADERS is 
  12932. ----------------------------------------------------------------------
  12933. --|
  12934. --|  NAME:  INIT_DIST_HEADERS 
  12935. --|
  12936. --|  OVERVIEW:
  12937. --|    This procedure initalizes the headers for the Percent Complete
  12938. --|    by Subsystem Report.
  12939. --|
  12940. --|  EXCEPTIONS HANDLED:
  12941. --|    none
  12942. --|
  12943. --|  HISTORY:
  12944. --|    written by   Bonnie Burkhardt   March 1985
  12945. --|
  12946. ----------------------------------------------------------------------
  12947.  
  12948.   use AC_LIST_PKG;
  12949.  
  12950.   DASHES   : string (1..15)  := (others => '-');
  12951.   AC_PTR   : activity_pointer;
  12952.   AC_INDEX : integer := 0;
  12953.  
  12954. begin
  12955.   -- initialize the headers
  12956.   HEADER1(117..121) := "TOTAL";
  12957.   HEADER1(126..132) := "PERCENT";
  12958.  
  12959.   HEADER2(2..10)    := "SUBSYSTEM";
  12960.   HEADER2(115..123) := "REMAINING";
  12961.   HEADER2(126..132) := "COMPLET";
  12962.  
  12963.   HEADER_LINES (2..10)    := DASHES(1..9);
  12964.   HEADER_LINES (115..123) := DASHES(1..9);
  12965.   HEADER_LINES (126..132) := DASHES(1..7);
  12966.  
  12967.   -- initialize the header for the activity data
  12968.   start_walk(AC_LIST);
  12969.   loop
  12970.     walk (AC_LIST, AC_PTR, END_LIST);
  12971.     exit when END_LIST;
  12972.     HEADER2(14+10*AC_INDEX..21+10*AC_INDEX) := AC_PTR.name(1..8);
  12973.     HEADER_LINES(14+10*AC_INDEX..21+10*AC_INDEX) := DASHES(1..8);
  12974.     AC_INDEX := AC_INDEX + 1;
  12975.   end loop;
  12976.  
  12977. end INIT_DIST_HEADERS;
  12978.  
  12979.  
  12980.  
  12981. separate(TRACKER.report_generator.DISTRIBUTION_OF_WORK)
  12982. procedure CALC_SS_WORK is 
  12983. ----------------------------------------------------------------------
  12984. --|
  12985. --|  NAME:  CALC_SS_WORK 
  12986. --|
  12987. --|  OVERVIEW:
  12988. --|    This procedure calculates the total amount of work left in a 
  12989. --|    subsystem by activity.
  12990. --|
  12991. --|  EXCEPTIONS HANDLED:
  12992. --|    none
  12993. --|
  12994. --|  HISTORY:
  12995. --|    written by   Bonnie Burkhardt   March 1985
  12996. --|
  12997. ----------------------------------------------------------------------
  12998.  
  12999.   use AC_LIST_PKG; use PR_LIST_PKG; use EL_LIST_PKG;
  13000.  
  13001.   AC_PTR       : activity_pointer;
  13002.   AC_INDEX     : integer := 0;
  13003.   END_LIST     : boolean := false;
  13004.   ELE_PTR      : element_pointer;
  13005.   ELE_SIZE     : float range 0.0..99_999.0 := 0.0;
  13006.   FOUND        : boolean := true;
  13007.   PR_PTR       : personnel_pointer;
  13008.   PCT_TOT_PROJ : array (1..max_num_activities) of float range 0.0..100.0
  13009.     := (others => 0.0);
  13010.  
  13011. begin
  13012.   -- initialize the PCT_TOT_PROJ array
  13013.   start_walk(AC_LIST);
  13014.   AC_INDEX := 0;
  13015.   loop
  13016.     walk(AC_LIST, AC_PTR, END_LIST);
  13017.     exit when END_LIST;
  13018.     AC_INDEX := AC_INDEX + 1;
  13019.     PCT_TOT_PROJ (AC_INDEX) := AC_PTR.percent_tot_proj;
  13020.   end loop;
  13021.  
  13022.   SS_WORK_BY_AC := (others => 0.0);
  13023.   SS_WORK       := 0.0;
  13024.   start_walk(SS_PTR.element_list);
  13025.   loop
  13026.     walk(SS_PTR.element_list, ELE_PTR, END_LIST);
  13027.     exit when END_LIST;
  13028.  
  13029.     -- compute the size of this element (original or current)
  13030.     if ORIG_OR_CUR = CURRENT then
  13031.       ELE_SIZE := float(ELE_PTR.current_size - ELE_PTR.size_done_at_start);
  13032.     elsif (ELE_PTR.original_size >= ELE_PTR.current_size) or
  13033.       (ELE_PTR.current_size = 0) then
  13034.       ELE_SIZE := float(ELE_PTR.original_size - ELE_PTR.size_done_at_start);
  13035.     else
  13036.       ELE_SIZE := float(ELE_PTR.original_size) * (1.0 -
  13037.         float(ELE_PTR.size_done_at_start) / float(ELE_PTR.current_size));
  13038.     end if;
  13039.  
  13040.  
  13041.     -- add each element by activity to the totals
  13042.     if not ELE_PTR.more_than_one_person then
  13043.       find(PR_LIST,ELE_PTR.person_initials, PR_PTR, FOUND);
  13044.     end if;
  13045.     AC_INDEX := 0;
  13046.     start_walk(AC_LIST);
  13047.     loop
  13048.       walk(AC_LIST, AC_PTR, END_LIST);
  13049.       exit when END_LIST;
  13050.       AC_INDEX := AC_INDEX + 1;
  13051.       if ELE_PTR.more_than_one_person then
  13052.         find(PR_LIST,ELE_PTR.people_initials(ac_index), PR_PTR, FOUND);
  13053.         SS_WORK_BY_AC(AC_INDEX) := SS_WORK_BY_AC(AC_INDEX) + ELE_PTR.complexity 
  13054.         * float(ELE_SIZE) * (PCT_TOT_PROJ(AC_INDEX) / 100.0) * 
  13055.         (1.0 - AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX))/100.0)
  13056.         / PR_PTR.production_rate;
  13057.       else -- only one person assigned
  13058.         SS_WORK_BY_AC(AC_INDEX) := SS_WORK_BY_AC(AC_INDEX) + ELE_PTR.complexity 
  13059.         * float(ELE_SIZE) * (PCT_TOT_PROJ(AC_INDEX) / 100.0) * 
  13060.         (1.0 - AC_PCT_VALUE(ELE_PTR.activity_completeness(AC_INDEX))/100.0)
  13061.         / PR_PTR.production_rate;
  13062.       end if;
  13063.     end loop;
  13064.   end loop;
  13065.  
  13066.   for AC_INDEX in 1..num_of_activities loop
  13067.     SS_WORK := SS_WORK + SS_WORK_BY_AC(AC_INDEX);
  13068.     TOT_SS_WORK_BY_AC(AC_INDEX) := TOT_SS_WORK_BY_AC(AC_INDEX) 
  13069.         + SS_WORK_BY_AC(AC_INDEX);
  13070.   end loop ;
  13071.   TOT_SS_WORK := TOT_SS_WORK + SS_WORK;
  13072. end CALC_SS_WORK;
  13073.  
  13074.