IDENTIFICATION DIVISION.
PROGRAM-ID. TEMPLATE-SCREEN.
*>
*>  Example CobCurses Action Mode Screen :
*>  Warren W. Gay
*>
*>  $Id: template_screen.cob,v 1.12 2007/10/30 13:05:20 ve3wwg Exp $
*>
*>  THIS IS AN EXAMPLE COBOL SCREEN MODULE. IT IS EXPECTED
*>  THAT THE CALLING PROGRAM (OR MAIN PROGRAM) HAS ALREADY
*>  CALLED NC-OPEN TO MAKE THE TERMINAL INTERFACE READY.
*>
*>  HERE WE MUST RECEIVE THE GLOBALS IN THE LINKAGE SECTION
*>  FROM THE PROGRAM THAT PERFORMED NC-OPEN (NC-COBCURSES).
*>  BEYOND THAT, YOU CAN ADD OTHER LINKAGE PARAMETERS AS
*>  NECESSARY.
*>
*>  THIS IS OTHERWISE JUST A SIMPLE INDEXED SEQUENTIAL
*>  FILE "MAINTENANCE SCREEN", ALLOWING THE USER TO ADD,
*>  UPDATE, FIND OR DELETE RECORDS.
*>
ENVIRONMENT DIVISION.
INPUT-OUTPUT SECTION.
FILE-CONTROL.

    SELECT DATA-FILE
        ASSIGN TO TEMPLATE-FILE-NAME
        ORGANIZATION IS INDEXED
        ACCESS IS DYNAMIC
        RECORD KEY IS DTA-KEY.

DATA DIVISION.
FILE SECTION.

    FD  DATA-FILE.
    01  DATA-RECORD.
        COPY TEMPDATA.

WORKING-STORAGE SECTION.

    COPY COBCATTR.                                      *> DEFINES TERMINAL ATTRIBUTES
    COPY COBCCOLOUR.                                    *> DEFINES TERMINAL COLOURS
    COPY COBCURSL.                                      *> DEFINES LOCAL FIELD AREAS FOR SCREEN

    COPY TEMPLATE-WS.                                   *> GENERATED WS DATA AREAS FOR SCREEN

    77  FILE-NAME-LENGTH                    PIC 9999.   *> USED FOR CALL TO "COBCURSES-INIT-PATHNAME"
    01  TEMPLATE-FILE-NAME                  PIC X(512)  *> THIS IS THE UNSUBSTITUTED FILE'S PATHNAME
        VALUE "${COBCURSES_DATADIR}/TEMPLATE.X".        *> COBCURSES-INIT-PATHNAME WILL UPDATE THIS

    01  RECORD-STATE-FLAGS.                             *> THESE HELP MAINTAIN 'RECORD STATE'
        10  RECORD-DEFINED-FLAG             PIC X.      *> Y MEANS WE HAVE EXISTING OR A NEW RECORD
            88  DEFINED-RECORD              VALUE 'Y' FALSE IS 'N'.
        10  RECORD-NEW-FLAG                 PIC X.       *> Y MEANS THIS RECORD HAS NOT BEEN ADDED YET
            88  NEW-RECORD                  VALUE 'Y' FALSE IS 'N'.
        10  RECORD-CHANGES-FLAG             PIC X.       *> Y MEANS THAT THIS RECORD HAS BEEN ALTERED (BUT NOT SAVED)
            88  UNSAVED-CHANGES             VALUE 'Y' FALSE IS 'N'.

LINKAGE SECTION.

    COPY COBCURSG.                                      *> COBCURSES GLOBAL VALUES

PROCEDURE DIVISION
    USING NC-COBCURSES.                                 *> PASSED FROM THE MAIN PROGRAM THAT DID NC-OPEN

MAIN-PROGRAM.
    PERFORM 1000-INITIALIZATION.                        *> INITIALIZE THIS SCREEN
    PERFORM 5000-PROCESS.                               *> PERFORM ALL SCREEN PROCESSING
    PERFORM 9000-FINALIZE.                              *> CLEAN UP FOR SCREEN EXIT
    GOBACK.                                             *> RETURN TO CALLER

1000-INITIALIZATION.
    PERFORM 1005-PATHNAMES-INIT.                        *> INITIALIZE ALL FILE PATHNAMES
    PERFORM 9010-OPEN-FILES.                            *> OPEN ALL FILES REQUIRED BY THIS SCREEN
    PERFORM 1010-RECORD-INIT.                           *> INITIALIZE RECORD STATUS
    PERFORM 1020-COBCURSES-INIT.                        *> INITIALIZE TERMINAL SCREEN
    MOVE FNO-ACTION TO NC-FSEQ-STATE.                   *> START SCREEN IN THE "ACTION FIELD"
EXIT.

1005-PATHNAMES-INIT.
    MOVE LENGTH OF TEMPLATE-FILE-NAME TO FILE-NAME-LENGTH.
    CALL "COBCURSES-INIT-PATHNAME" USING                *> SUBSTITUTE ENVIRONMENT VARIABLES IN PATHNAME
        TEMPLATE-FILE-NAME,                             *> THIS IS THE PATHNAME
        FILE-NAME-LENGTH.                               *> THE PATHNAME'S LENGTH
    EXIT.

1010-RECORD-INIT.
    SET DEFINED-RECORD TO FALSE.                        *> THERE IS NO "CURRENT RECORD"
    SET NEW-RECORD TO FALSE.                            *> THERE IS NO "NEWLY CREATED RECORD"
    SET UNSAVED-CHANGES TO FALSE.                       *> THERE ARE NO UNSAVED CHANGES
    EXIT.

1020-COBCURSES-INIT.
    PERFORM NC-INIT.                                    *> INITIALIZE LOCAL COBCURSES WS AREAS
    PERFORM NC-CLEAR.                                   *> CLEAR THE SCREEN
    PERFORM 1030-SCREEN-INIT.                           *> DRAW THE SCREEN BACKGROUND AND FIELDS
    PERFORM 5100-ACTION-C.                              *> PERFORM C-LEAR ACTION AS INITIALIZATION
    EXIT.

1030-SCREEN-INIT.
    COPY TEMPLATE-PD.                                   *> GENERATED INITIALIZATION CODE FOR THIS SCREEN
    PERFORM 1040-DRAW-SCREEN.                           *> DRAW THE SCREEN AND FIELDS
    EXIT.

1040-DRAW-SCREEN.
    PERFORM NC-DRAW-SCREEN.                             *> DRAW THE SCREEN BACKGROUND
    PERFORM NC-DRAW-FIELDS.                             *> DRAW THE SCREEN FIELDS
    EXIT.

4000-MOVE-TO-RECORD.
    MOVE FLD-KEY TO DTA-KEY.                            *> COPY SCREEN FIELDS TO DATA RECORD
    MOVE FLD-DATA TO DTA-DATA.
    MOVE FLD-DESC TO DTA-DESC.
    MOVE FLD-TEST-COMP TO DTA-COMP-2.
    EXIT.

4100-MOVE-FROM-RECORD.
    MOVE DTA-KEY TO FLD-KEY.                            *> COPY DATA RECORD FIELDS TO SCREEN FIELDS
    MOVE DTA-DATA TO FLD-DATA.
    MOVE DTA-DESC TO FLD-DESC.
    MOVE DTA-COMP-2 TO FLD-TEST-COMP.
    EXIT.

5000-PROCESS.
    PERFORM NC-FIELD-STATE-MACHINE.                     *> INVOKE THE COBCURSES ACTION MODE FIELD STATE MACHINE
    EXIT.

5100-ACTION-C.
*>
*>  ACTION C-LEAR :
*>
*>      1. CLEAR ALL FIELDS
*>      2. CLEAR ALL RECORD STATUS TO "NO CURRENT RECORD"
*>      3. CLEAR "UNSAVED CHANGES" STATUS
*>
    PERFORM NC-CLEAR-FIELDS.                            *> BLANK OUT ALL FIELDS
    PERFORM NC-RESET-CHANGES.                           *> RESET ALL FIELD "CHANGED" STATUS FLAGS
    PERFORM 1010-RECORD-INIT.                           *> RESET RECORD STATUS
    PERFORM 6100-UPDATE-SCREEN.                         *> UPDATE THE SCREEN
    EXIT.

5200-ACTION-N.
*>
*>  ACTION N-EW :
*>
*>      1. CHECK IF THERE ARE UNSAVED CHANGES
*>      2. PERFORM "ACTION C-LEAR"
*>      3. MOVE USER TO FIRSTS OF SERIES OF DATA ENTRY FIELDS FOR "NEW RECORD"
*>
    IF UNSAVED-CHANGES THEN
        PERFORM 8010-WARNING-UNSAVED-CHANGES            *> REJECT : THERE ARE UNSAVED CHANGES
    ELSE
        PERFORM 5100-ACTION-C                           *> CLEAR SCREEN AND RECORD
        MOVE 1 TO NC-FSEQ-NEXT                          *> START WITH FIELD 1 (STATE 1) FOR DATA-ENTRY
    END-IF.
    EXIT.

5300-ACTION-E.
*>
*>  ACTION E-ND :
*>
*>      1. CHECK IF THERE ARE UNSAVED CHANGES
*>      2. SIGNAL TO FSM THAT WE WANT TO EXIT
*>
    IF UNSAVED-CHANGES THEN
        PERFORM 8010-WARNING-UNSAVED-CHANGES            *> REJECT : THERE ARE UNSAVED CHANGES
    ELSE
        MOVE 9999 TO NC-FSEQ-NEXT                       *> SIGNAL TO FSM THAT WE WANT IT TO EXIT
    END-IF.
    EXIT.

5400-ACTION-S.
*>
*>  ACTION S-AVE :
*>
*>      1. CHECK IF WE HAVE AN EXISTING RECORD OR A NEWLY ENTERED ONE.
*>      2. IF IT IS NEW, ADD THE RECORD, ELSE UPDATE IT.
*>
    IF DEFINED-RECORD THEN                              *> DO WE HAVE A "CURRENT RECORD"?
        IF NEW-RECORD THEN                              *> YES, BUT IS IT NEW (NOT YET ADDED)?
            PERFORM 5410-ADD-RECORD                     *> YES, THEN GO ADD IT TO THE FILE
        ELSE
            PERFORM 5420-UPDATE-RECORD                  *> EXISTING RECORD NEEDS UPDATE (REWRITE)
        END-IF
    ELSE
        MOVE "No record to save." TO NC-MSGBUF          *> THERE IS NO CURRENT RECORD
        PERFORM NC-PUT-ERROR-OVERRIDE
    END-IF.
    EXIT.

5410-ADD-RECORD.
    PERFORM 4000-MOVE-TO-RECORD                         *> COPY FIELD DATA TO RECORD AREA
    WRITE DATA-RECORD                                   *> ADD THIS RECORD TO THE INDEXED FILE
        INVALID KEY                                     *> OOPS-- PROBABLY DUPLICATE KEY
            MOVE "Error: Adding a new record." TO NC-MSGBUF
            PERFORM NC-PUT-ERROR-OVERRIDE               *> USE THIS MESSAGE IN PLACE OF FIELD HELP MSG
        NOT INVALID KEY
            SET UNSAVED-CHANGES TO FALSE                *> THE CHANGES HAVE BEEN SAVED
            SET NEW-RECORD TO FALSE                     *> THE RECORD NOW EXISTS ON FILE (NO LONGER NEW)
            MOVE "A new record was added (saved)." TO NC-MSGBUF
            PERFORM NC-PUT-MESSAGE-OVERRIDE             *> USE THIS MSG IN PLACE OF ACTION HELP MSG
    END-WRITE.
    IF NOT NEW-RECORD THEN
        PERFORM 9030-FLUSH-FILES
    END-IF.
    EXIT.

5420-UPDATE-RECORD.
    PERFORM 4000-MOVE-TO-RECORD                         *> COPY SCREEN FIELDS TO RECORD AREA
    REWRITE DATA-RECORD                                 *> UPDATE INDEXED FILE WITH NEW RECORD CONTENTS
        INVALID KEY                                     *> THIS SHOULD NOT HAPPEN
            MOVE "Error: Updating the screen record." TO NC-MSGBUF
            PERFORM NC-PUT-ERROR-OVERRIDE
        NOT INVALID KEY                                 *> UPDATE WAS SUCCESSFUL
            SET UNSAVED-CHANGES TO FALSE                *> THE CHANGES HAVE BEEN SAVED
            MOVE "Your record was updated (saved)." TO NC-MSGBUF
            PERFORM NC-PUT-MESSAGE-OVERRIDE             *> THIS MSG REPLACES NORMAL ACTION FIELD HELP MSG
    END-REWRITE.
    IF NOT UNSAVED-CHANGES THEN
        PERFORM 9030-FLUSH-FILES
    END-IF.
    EXIT.

5500-ACTION-D.
    IF DEFINED-RECORD AND NOT NEW-RECORD THEN           *> DO WE HAVE AN EXISTING RECORD TO DELETE?
        INITIALIZE DATA-RECORD                          *> YES..
        MOVE FLD-KEY TO DTA-KEY                         *> INITIALIZE RECORD KEY AREA
        DELETE DATA-FILE                                *> DELETE THIS RECORD FROM THE INDEXED FILE
            INVALID KEY                                 *> KEY DOES NOT EXIST (DELETED BY ANOTHER USER?)
                MOVE "Error: Unable to delete this record." TO NC-MSGBUF
                PERFORM NC-PUT-ERROR-OVERRIDE
            NOT INVALID KEY                             *> RECORD SUCCESSFULLY DELETED
                PERFORM 5100-ACTION-C                   *> CLEAR SCREEN AND RECORD STATUS
                MOVE "The record was deleted." TO NC-MSGBUF
                PERFORM NC-PUT-MESSAGE-OVERRIDE         *> INFORM THE USER
        END-DELETE
        IF NOT DEFINED-RECORD THEN
            PERFORM 9030-FLUSH-FILES
        END-IF
    ELSE
        MOVE "There is no current record to delete." TO NC-MSGBUF
        PERFORM NC-PUT-ERROR-OVERRIDE
    END-IF.
    EXIT.

5600-ACTION-F.
*>
*>  ACTION F-IND :
*>
*>  1. CHECK IF THERE ARE UNSAVED CHANGES
*>  2. ISSUE F-IND HELP MESSAGE
*>  3. REQUEST FSM TO ENTER "FIND STATE" (FSEQ-FIND)
*>  4. MODIFY FSEQ-FIND STATE TO USE FIELD # 1
*>  5. RETURN TO FSM TO TAKE IT FROM HERE
*>
    IF UNSAVED-CHANGES AND DEFINED-RECORD THEN
        PERFORM 8010-WARNING-UNSAVED-CHANGES
    ELSE
        MOVE "Enter search value + CR, or cursor up/down to browse." TO NC-MSGBUF
        PERFORM NC-PUT-MESSAGE-OVERRIDE                 *> ISSUE HELPFUL MSG TO USER
        MOVE FSEQ-FIND TO NC-FSEQ-NEXT                  *> TELL FSM TO GO TO THIS STATE (FSEQ-FIND)
        MOVE FNO-KEY TO NC-FSEQ-FIELD-NO(NC-FSEQ-NEXT)  *> MODIFY THAT STATE TO USE FIELD # FNO-KEY
    END-IF.
    EXIT.

5610-ACTION-F-CONTD.
*>
*>  THIS CODE IS INVOKED WHEN THE FSM IS IN STATE FSEQ-FIND, AND A FIELD
*>  EXIT EVENT HAS OCCURRED :
*>
    PERFORM 1010-RECORD-INIT                            *> INIT RECORD STATUS (TO START A FIND OPERATION)
    INITIALIZE DATA-RECORD                              *> CLEAR OUT RECORD AREA
    MOVE FLD-KEY TO DTA-KEY                             *> COPY FIND FIELD (FLD-KEY) TO RECORD'S KEY AREA
    EVALUATE TRUE
        WHEN NC-FIELD-EXIT-CU                           *> IF USER DID CURSOR UP..
            PERFORM 5620-LT-SEARCH                      *> THEN SEARCH FOR PRIOR RECORDS
        WHEN NC-FIELD-EXIT-CR OR NC-FIELD-EXIT-TAB      *> IF USER DID "ENTER"
            PERFORM 5630-GE-SEARCH                      *> THEN SEARCH FOR KEY >= CURRENT FIELD DATA
            MOVE FSEQ-ACTION TO NC-FSEQ-NEXT            *> GO TO ACTION FIELD TO END "FIND MODE"
        WHEN NC-FIELD-EXIT-CD                           *> IF USER DID "CURSOR DOWN" THEN..
            PERFORM 5640-GT-SEARCH                      *> THEN SEARCH FOR KEY > CURRENT FIELD DATA
    END-EVALUATE.
    EXIT.

5620-LT-SEARCH.
    IF DTA-KEY = SPACES THEN
        MOVE HIGH-VALUES TO DTA-KEY                     *> START AT END OF FILE
    END-IF.
    START DATA-FILE KEY IS < DTA-KEY                    *> START SEARCH FOR KEY < THAN GIVEN KEY
        INVALID KEY
            PERFORM 1010-RECORD-INIT                    *> NO RECORD EXISTS, CLEAR STATUS
            MOVE SPACES TO FLD-KEY
        NOT INVALID KEY
            SET DEFINED-RECORD TO TRUE                  *> JUST FLAG FOR "READ NEXT" OPERATION (WE HAVE NO RECD YET)
    END-START.
    PERFORM 5650-NEXT-RECORD.                           *> DO A "READ NEXT" OPERATION
    EXIT.

5630-GE-SEARCH.
    START DATA-FILE KEY IS >= DTA-KEY                   *> START SEARCH FOR KEY >= GIVEN KEY
        INVALID KEY
            PERFORM 1010-RECORD-INIT                    *> NO RECORD EXISTS, CLEAR STATUS
        NOT INVALID KEY
            SET DEFINED-RECORD TO TRUE                  *> JUST FLAG FOR "READ NEXT" OPERATION
    END-START.
    PERFORM 5650-NEXT-RECORD.                           *> DO A "READ NEXT"
    EXIT.

5640-GT-SEARCH.
    START DATA-FILE KEY IS > DTA-KEY                    *> START A SEARCH FOR KEY > GIVEN KEY
        INVALID KEY
            PERFORM 1010-RECORD-INIT                    *> NONE EXITS, CLEAR STATUS
        NOT INVALID KEY
            SET DEFINED-RECORD TO TRUE                  *> JUST FLAG FOR "READ NEXT"
    END-START.
    PERFORM 5650-NEXT-RECORD.                           *> DO "READ NEXT"
    EXIT.

5650-NEXT-RECORD.
*>
*>  THIS IS A PARAGRAPH COMMON TO 3 SEARCHES :
*>
*>  IN THIS CONTEXT, "DEFINED-RECORD" ONLY TEMPORARILY INDICATES THAT THE "START"
*>  OF THE SEARCH OPERATION WAS SUCCESFUL. BY THE END OF THIS PARAGRAPH, THIS
*>  BOOLEAN FLAG RESTORES ITS TRUE MEANING:
*>
*>      DEFINED-RECORD              A RECORD WAS FOUND AND EXISTS (AND IS NOT "NEW")
*>      NOT DEFINED-RECORD          THERE IS NO "CURRENT RECORD" (NONE WAS FOUND)
*>
    IF DEFINED-RECORD THEN                              *> WAS "START" SUCCESSFUL?
        READ DATA-FILE NEXT RECORD                      *> YES, TRY TO FETCH THE RECORD
            AT END 
                PERFORM 5100-ACTION-C                   *> NOPE- FAILED, SO CLEAR FIELDS & STATUS
            NOT AT END 
                PERFORM 4100-MOVE-FROM-RECORD           *> YES, COPY RECORD'S FIELDS TO SCREEN FIELDS
                SET DEFINED-RECORD TO TRUE              *> WE HAVE A DEFINED RECORD
                SET NEW-RECORD TO FALSE                 *> IT IS NOT A NEW UNSAVED RECORD
                SET UNSAVED-CHANGES TO FALSE            *> THERE ARE NO UNSAVED-CHANGES
                PERFORM 6100-UPDATE-SCREEN              *> UPDATE THE SCREEN
        END-READ
    ELSE
        PERFORM 5100-ACTION-C                           *> CLEAR THE SCREEN AND STATUS
    END-IF.
    EXIT.

5900-ACTION-EDIT.
*>
*>  ACTION "EDIT FIELD" :
*>
*>      1. CHECK THAT THERE IS A DEFINED RECORD TO EDIT FIELDS WITH (ELSE NO VALID RESULTS TO EDIT)
*>      2. MAKE SURE THE FIELD # INDICATED BY THE USER IS AN ACCEPTABLE FIELD TO EDIT
*>      3. MODIFY THE FSM STATE SO THAT IT WILL VISIT THAT FIELD FOR EDITING
*>
    IF NOT DEFINED-RECORD THEN
        MOVE "No current record to edit." TO NC-MSGBUF  *> THERE IS NO VALID RECORD TO EDIT ANYTHING FOR
        PERFORM NC-PUT-ERROR-OVERRIDE
    ELSE
        IF NC-FIELD-EDIT-TARGET NOT = 'Y' THEN          *> ARE WE PERMITTED TO EDIT THIS FIELD (EG. CAN'T EDIT KEY FIELD)
            MOVE "You cannot edit that field." TO NC-MSGBUF
            PERFORM NC-PUT-ERROR-OVERRIDE
        ELSE
            MOVE FSEQ-EDIT TO NC-FSEQ-NEXT              *> INDICATE TO FSM THAT WE WANT TO ENTER STATE FSEQ-EDIT
            MOVE NC-FIELD-SEARCH                        *> MODIFY THAT STATE SO THAT IT WILL
                TO NC-FSEQ-FIELD-NO(NC-FSEQ-NEXT)       *>   USE THIS FIELD FOR THE DATA ENTRY
        END-IF
    END-IF.
    EXIT.

6000-LOOKUP-RECORD.
    INITIALIZE DATA-RECORD.                             *> CLEAR THE RECORD AREA
    MOVE FLD-KEY TO DTA-KEY.                            *> ESTABLISH THE KEY AREA OF THE RECORD
    READ DATA-FILE                                      *> LOOK UP THE RECORD IN THE INDEXED FILE
        INVALID KEY
            CONTINUE                                    *> DO NOTHING -- NOT FOUND
        NOT INVALID KEY
            PERFORM 4100-MOVE-FROM-RECORD               *> POPULATE SCREEN FIELDS FROM READ RECORD
            MOVE FNO-ACTION TO NC-FSEQ-NEXT             *> TELL FSM TO ENTER "ACTION FIELD" NEXT.
            SET DEFINED-RECORD TO TRUE                  *> INDICATE THAT WE HAVE AN EXISTING RECORD
            SET NEW-RECORD TO FALSE                     *> THIS IS NOT A NEW & UNSAVED RECORD
            SET UNSAVED-CHANGES TO FALSE                *> THERE ARE NO UNSAVED CHANGES AT THIS TIME
            PERFORM 6100-UPDATE-SCREEN
    END-READ.
    EXIT.

6100-UPDATE-SCREEN.
    PERFORM NC-DRAW-FIELDS.                             *> REDRAW ALL DEFINED VISIBLE FIELDS
    EXIT.

7000-ACTION-EVENT.
    EVALUATE NC-FIELD-ACTION
        WHEN "C"                                        *> C-LEAR
            PERFORM 5100-ACTION-C
        WHEN "N"                                        *> N-EW
            PERFORM 5200-ACTION-N
        WHEN "E"                                        *> E-ND
            PERFORM 5300-ACTION-E
        WHEN "S"                                        *> S-AVE
            PERFORM 5400-ACTION-S
        WHEN "D"                                        *> D-ELETE
            PERFORM 5500-ACTION-D
        WHEN "F"                                        *> F-IND
            PERFORM 5600-ACTION-F
        WHEN " "                                        *> EDIT SPECIFIED FIELD BY #
            PERFORM 5900-ACTION-EDIT
        WHEN OTHER                                      *> UNRECOGNIZED ACTIONS
            PERFORM 8000-ERROR-ACTION
    END-EVALUATE.
    EXIT.

7100-CHANGE-EVENT.
*>
*>  A "FIELD HAS CHANGED" CALLBACK :
*>
*>  NOTE :
*>      HERE WE MUST IGNORE STATES LIKE THE FIND STATE. WE ONLY WANT TO LOG A
*>  'RECORD HAS CHANGED' STATUS IF DATA ENTRY OR A FIELD HAS BEEN EDITED.
*>
    IF NC-FIELD-NUMBER < FNO-ACTION AND NC-FSEQ-STATE NOT = FSEQ-FIND
        SET UNSAVED-CHANGES TO TRUE                     *> AN EDITABLE FIELD HAS CHANGED IN VALUE
    END-IF.
    EXIT.

7200-VERIFY-EVENT.
*>
*>  A "FIELD REQUIRES VALIDATION" CALLBACK.
*>
*>  THIS CALLBACK IS UNUSED IN THIS EXAMPLE PROGRAM. IF IT IS USED, IT MUST
*>  SET NC-FIELD-VERIFIED TO 'Y' IF THE FIELD IS "VALID". OTHERWISE THE FSM
*>  WILL REVISIT THE SAME 'INVALID' FIELD.
*>  
    EXIT.

7500-FIELD-EVENT.
*>
*>  THIS IS THE "FIELD EXIT EVENT" CALLBACK :
*>
    EVALUATE TRUE

        WHEN NC-FIELD-NUMBER = FNO-ACTION               *> WAS THIS FOR THE ACTION FIELD?
            PERFORM 7000-ACTION-EVENT                   *> YES, THEN DISPATCH ACCORDING TO ACTION CODE

        WHEN NC-FSEQ-STATE = FNO-KEY                    *> DATA ENTRY (NEW) STATE, AND KEY FIELD WAS ENTERED
            PERFORM 6000-LOOKUP-RECORD                  *> MAKE SURE THIS KEY DOES NOT ALREADY EXIST

        WHEN NC-FSEQ-STATE = FNO-DESC                   *> END OF DATA ENTRY INPUT FIELDS?
            SET DEFINED-RECORD TO TRUE                  *> YES, WE NOW HAVE A COMPLETE RECORD
            SET NEW-RECORD TO TRUE                      *> AND IT IS A NEW (NOT ADDED) RECORD
            SET UNSAVED-CHANGES TO TRUE                 *> AND IT REPRESENTS UNSAVED CHANGES

        WHEN NC-FSEQ-STATE = FSEQ-FIND                  *> IN THE FIND STATE?
            PERFORM 5610-ACTION-F-CONTD                 *> YES, DISPATCH TO COMPLETE THE FIND OPERATION

        WHEN OTHER
            CONTINUE                                    *> NO SPECIAL HANDLING REQUIRED HERE

    END-EVALUATE.
    EXIT.

7600-MOUSE-EVENT.
*>
*>  A "MOUSE EVENT" CALLBACK :
*>
*>  THIS ONLY WORKS IF MOUSE SUPPORT IS COMPILED INTO COBCURSES. IT IS PROBABLY NOT
*>  VERY USEFUL, AND ONLY SUPPORTED WHEN NCURSES(3X) IS USED UNDERNEATH THE HOOD.
*>  COMPILING IN MOUSE SUPPORT MEANS THAT CUT AND PASTE WILL NO LONGER WORK.
*>
*>  WHEN USED, THE MOUSE CLICK CAN IDENTIFY A FIELD THAT YOU WANT TO EDIT (BUT 
*>  THERE MUST BE A VALID "CURRENT RECORD" ETC.)
*>
    PERFORM 5900-ACTION-EDIT.
    EXIT.

8000-ERROR-ACTION.
    SET NC-MSG-TEXT TO ADDRESS OF INF-ACTION.           *> ISSUE MSG ABOUT VALID ACTIONS
    MOVE LENGTH OF INF-ACTION TO NC-MSG-LENGTH.
    PERFORM NC-ERROR-MESSAGE-OVERRIDE.
    EXIT.

8010-WARNING-UNSAVED-CHANGES.
    MOVE "Warning: You have unsaved changes (Save or Cancel)." TO NC-MSGBUF
    PERFORM NC-PUT-ERROR-OVERRIDE.
    EXIT.

9000-FINALIZE.
    PERFORM 9020-CLOSE-FILES.                           *> CLOSE ALL FILES
    PERFORM NC-CLEAR.                                   *> CLEAR THE SCREEN
    PERFORM NC-FINALIZE.                                *> SCREEN CLEANUP
    EXIT.

9010-OPEN-FILES.
    OPEN I-O DATA-FILE.         
    EXIT.

9020-CLOSE-FILES.
    CLOSE DATA-FILE.
    EXIT.

9030-FLUSH-FILES.
*>
*>  THE BERKELEY DB SEEMS TO RETAIN ADDED/UPDATED/DELETED RECORD INFORMATION IN MEMORY.
*>  THIS CREATES PROBLEMS FOR OTHER COBOL MODULES THAT MAY OPEN THE SAME FILE(S). TO
*>  FORCE CHANGES TO THE FILE(S), CLOSE AND REOPEN. THIS WILL PROVIDE YOUR OTHER COBOL
*>  ROUTINES A CONSISTENT VIEW OF WHAT HAS BEEN UPDATED.
*>
    PERFORM 9020-CLOSE-FILES.
    PERFORM 9010-OPEN-FILES.
    EXIT.

NC-VERIFY-EVENT.
    PERFORM 7200-VERIFY-EVENT.                          *> REDISPATCH CALL TO THIS PARA NAME.
    EXIT.

NC-CHANGE-EVENT.
    PERFORM 7100-CHANGE-EVENT.
    EXIT.

NC-FIELD-EVENT.
    PERFORM 7500-FIELD-EVENT.
    EXIT.

NC-MOUSE-EVENT.
    PERFORM 7600-MOUSE-EVENT.
    EXIT.

NC-STATE-CHANGE-EVENT.
    EXIT.                                               *> NOT USED HERE (A "STATE CHANGE" CALLBACK)

NC-FKEY-EVENT.
    EXIT.                                               *> NOT USED HERE (A FUNCTION KEY PRESSED CALLBACK)

COPY COBCURSQ.                                          *> NC-* PARAGRAPH DEFINITIONS

END PROGRAM TEMPLATE-SCREEN.

*> $Source: /cvsroot/cobcurses/cobcurses/src/test/template_screen.cob,v $
