static Boolean MainFormKeyDown(AppContext* appContext, FormType* form, EventType* event) { Boolean handled = false; if ( HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) { if (FiveWayCenterPressed(appContext, event)) MainFormPressFindButton(form); if (FiveWayDirectionPressed(appContext, event, Up )) DefScrollUp(appContext, appContext->prefs.navButtonScrollType ); if (FiveWayDirectionPressed(appContext, event, Down )) DefScrollDown(appContext, appContext->prefs.navButtonScrollType ); // mark as unhandled so that left/right works in text field for // moving the cursor return false; } switch (event->data.keyDown.chr) { case returnChr: case linefeedChr: MainFormPressFindButton(form); handled = true; break; case pageUpChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { DefScrollUp(appContext, appContext->prefs.hwButtonScrollType); handled = true; break; } case pageDownChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { DefScrollUp(appContext, appContext->prefs.hwButtonScrollType); handled = true; break; } default: if (appContext->lookupStatusBarVisible) handled=true; break; } return handled; }
Boolean CourseListHandleEvent(EventPtr event) { FormPtr frm=FrmGetActiveForm(); Boolean handled = false; ListType *lstP=GetObjectPtr(LIST_courses); Boolean categoryEdited, reDraw=false; UInt16 category, numRecords; ControlType *ctl; UInt32 *recordList; if (event->eType == ctlSelectEvent) { // button handling switch (event->data.ctlSelect.controlID) { case BUTTON_courselist_back: handled=true; FrmGotoForm(FORM_main); break; case BUTTON_courselist_del: handled=true; if (LstGetSelection(lstP) == noListSelection) { FrmAlert(ALERT_clist_noitem); } else { DeleteCourse(gCourseInd[LstGetSelection(lstP)]); CleanupCourselist(); DrawCourses(lstP); FrmDrawForm(FrmGetActiveForm()); } break; case BUTTON_courselist_add: handled=true; gMenuCurrentForm=FORM_courselist; AddCourse(); break; case BUTTON_courselist_edit: handled=true; if (LstGetSelection(lstP) == noListSelection) { FrmAlert(ALERT_clist_noitem); } else { gMenuCurrentForm=FORM_courselist; EditCourse(gCourseInd[LstGetSelection(lstP)]); } break; case BUTTON_courselist_beam: handled=true; if (LstGetSelection(lstP) == noListSelection) { FrmAlert(ALERT_clist_noitem); } else { BeamCourse(gCourseInd[LstGetSelection(lstP)]); } break; case LIST_cl_cat_trigger: handled=true; category=DatabaseGetCat(); numRecords=DmNumRecordsInCategory(DatabaseGetRef(), DELETE_CATEGORY); recordList=(UInt32 *)MemPtrNew(numRecords * sizeof(UInt32)); CatPreEdit(numRecords, recordList); categoryEdited = CategorySelect(DatabaseGetRef(), frm, LIST_cl_cat_trigger, LIST_cl_cat, false, &category, gCategoryName, 0, STRING_cat_edit); // categoryDefaultEditCategoryString if (categoryEdited || (category != DatabaseGetCat())) { reDraw=true; DatabaseSetCat(category); ctl = GetObjectPtr(LIST_cl_cat_trigger); CategoryGetName(DatabaseGetRef(), category, gCategoryName); CategorySetTriggerLabel(ctl, gCategoryName); } CatPostEdit(numRecords, recordList); if (reDraw) { CleanupCourselist(); DrawCourses(lstP); FrmDrawForm(FrmGetActiveForm()); } if (recordList != NULL) MemPtrFree((MemPtr)recordList); break; default: break; } } else if (event->eType == keyDownEvent) { // We have a hard button assigned and it was pressed if (TxtCharIsHardKey(event->data.keyDown.modifiers, event->data.keyDown.chr)) { if (! (event->data.keyDown.modifiers & poweredOnKeyMask)) { FrmGotoForm(FORM_main); handled = true; } } else if (EvtKeydownIsVirtual(event)) { // Up or down keys pressed ListType *lst=GetObjectPtr(LIST_courses); switch (event->data.keyDown.chr) { case vchrPageUp: if (LstGetSelection(lst) == noListSelection) { LstSetSelection(lst, gNumCourses-1); CourseListHandleSelection(); } else if (LstGetSelection(lst) > 0) { LstSetSelection(lst, LstGetSelection(lst)-1); CourseListHandleSelection(); } handled=true; break; case vchrPageDown: if (LstGetSelection(lst) == noListSelection) { LstSetSelection(lst, 0); CourseListHandleSelection(); } else if (LstGetSelection(lst) < (gNumCourses-1)) { LstSetSelection(lst, LstGetSelection(lst)+1); CourseListHandleSelection(); } handled=true; break; default: break; } } } else if (event->eType == lstSelectEvent) { return CourseListHandleSelection(); } else if (event->eType == menuOpenEvent) { return HandleMenuOpenEvent(event); } else if (event->eType == menuEvent) { // forwarding of menu events return HandleMenuEvent(event->data.menu.itemID); } else if (event->eType == frmOpenEvent) { // initializes and draws the form ControlType *ctl; frm = FrmGetActiveForm(); lstP=GetObjectPtr(LIST_courses); FrmDrawForm (frm); DrawCourses(lstP); FrmDrawForm (frm); ctl = GetObjectPtr(LIST_cl_cat_trigger); CategoryGetName (DatabaseGetRef(), DatabaseGetCat(), gCategoryName); CategorySetTriggerLabel (ctl, gCategoryName); WinDrawLine(1, 140, 158, 140); handled = true; } else if (event->eType == frmUpdateEvent) { // redraws the form if needed CleanupCourselist(); DrawCourses(GetObjectPtr(LIST_courses)); FrmDrawForm (frm); WinDrawLine(1, 140, 158, 140); handled = false; } else if (event->eType == frmCloseEvent) { // this is done if form is closed CleanupCourselist(); } return (handled); }
/*********************************************************************** * handling for form and control actions * menu actions are forwarded to MainFormDoCommand ***********************************************************************/ static Boolean MainFormHandleEvent (EventPtr event) { FormType *frm; Boolean handled = false; Boolean categoryEdited, reDraw=false; UInt16 category, numRecords; ControlType *ctl; UInt32 *recordList; if (event->eType == ctlSelectEvent) { // button handling handled = true; switch (event->data.ctlSelect.controlID) { // the ok button - this leaves the application case LIST_cat_trigger: frm = FrmGetActiveForm(); category=DatabaseGetCat(); numRecords=DmNumRecordsInCategory(DatabaseGetRef(), DELETE_CATEGORY); recordList=(UInt32 *)MemPtrNew(numRecords * sizeof(UInt32)); CatPreEdit(numRecords, recordList); categoryEdited = CategorySelect(DatabaseGetRef(), frm, LIST_cat_trigger, LIST_cat, false, &category, gCategoryName, 0, STRING_cat_edit); // categoryDefaultEditCategoryString if (categoryEdited || (category != DatabaseGetCat())) { reDraw=true; DatabaseSetCat(category); ctl = GetObjectPtr(LIST_cat_trigger); CategoryGetName(DatabaseGetRef(), DatabaseGetCat(), gCategoryName); CategorySetTriggerLabel(ctl, gCategoryName); } CatPostEdit(numRecords, recordList); if (reDraw) { GadgetSetNeedsCompleteRedraw(true); FrmDrawForm(frm); } if (recordList != NULL) MemPtrFree((MemPtr)recordList); break; case BUTTON_beam: BeamCourse(GadgetGetHintCourseIndex()); break; case BUTTON_edit: gMenuCurrentForm=FORM_main; EditTime(); break; case BUTTON_next: GadgetDrawHintNext(); break; default: break; } } else if (event->eType == keyDownEvent) { // We have a hard button assigned and it was pressed if (TxtCharIsHardKey(event->data.keyDown.modifiers, event->data.keyDown.chr)) { if (! (event->data.keyDown.modifiers & poweredOnKeyMask)) { GadgetDrawHintNext(); handled = true; } } else if (EvtKeydownIsVirtual(event)) { // Up or down keys pressed switch (event->data.keyDown.chr) { case vchrPageUp: if (event->data.keyDown.modifiers & autoRepeatKeyMask) { if (! gMainRepeat) { GadgetSwitchScreen(); gMainRepeat = true; } } else { GadgetDrawStep(winUp); gMainRepeat = false; } handled=true; break; case vchrPageDown: if (event->data.keyDown.modifiers & autoRepeatKeyMask) { if (! gMainRepeat) { GadgetSwitchScreen(); gMainRepeat = true; } } else { GadgetDrawStep(winDown); gMainRepeat = false; } handled=true; break; case vchrSendData: BeamCourse(GadgetGetHintCourseIndex()); handled=true; break; default: break; } } } else if (event->eType == menuEvent) { // forwarding of menu events return HandleMenuEvent(event->data.menu.itemID); } else if (event->eType == menuOpenEvent) { return HandleMenuOpenEvent(event); } else if (event->eType == frmUpdateEvent) { // redraws the form if needed frm = FrmGetActiveForm(); FrmDrawForm(frm); // GadgetDrawHintNext(); handled = true; } else if (event->eType == frmOpenEvent) { ControlType *ctl; LocalID dbID; UInt16 cardNo; Boolean newKeyP4=false; UInt16 newKeyP2=0xFFFF; // initializes and draws the form at program launch frm = FrmGetActiveForm(); GadgetSet(frm, GADGET_main, GADGET_hint); FrmSetGadgetHandler(frm, FrmGetObjectIndex(frm, GADGET_main), GadgetHandler); FrmSetGadgetHandler(frm, FrmGetObjectIndex(frm, GADGET_hint), GadgetHintHandler); FrmDrawForm(frm); GadgetDrawHintNext(); ctl = GetObjectPtr(LIST_cat_trigger); CategoryGetName (DatabaseGetRef(), DatabaseGetCat(), gCategoryName); CategorySetTriggerLabel (ctl, gCategoryName); DmOpenDatabaseInfo(DatabaseGetRefN(DB_MAIN), &dbID, NULL, NULL, &cardNo, NULL); SysNotifyRegister(cardNo, dbID, sysNotifyLateWakeupEvent, HandleNotification, sysNotifyNormalPriority, NULL); KeyRates(false,&gKeyP1, &gKeyP2, &gKeyP3, &gKeyP4); KeyRates(true, &gKeyP1, &newKeyP2, &gKeyP3, &newKeyP4); handled = true; } else if (event->eType == frmCloseEvent) { // this is done if program is closed LocalID dbID; UInt16 cardNo; DmOpenDatabaseInfo(DatabaseGetRefN(DB_MAIN), &dbID, NULL, NULL, &cardNo, NULL); SysNotifyUnregister(cardNo, dbID, sysNotifyLateWakeupEvent, sysNotifyNormalPriority); // Restore original key rates KeyRates(true, &gKeyP1, &gKeyP2, &gKeyP3, &gKeyP4); } return (handled); }
/*********************************************************************** * * FUNCTION: RepeatHandleEvent * * DESCRIPTION: This routine is the event handler for the "Repeat * Dialog Box". * * PARAMETERS: event - a pointer to an EventType structure * * RETURNED: true if the event was handled and should not be passed * to a higher level handler. * ***********************************************************************/ Boolean RepeatHandleEvent (EventType* event) { Boolean handled = false; if (event->eType == ctlSelectEvent) { switch (event->data.ctlSelect.controlID) { case RepeatOkButton: RepeatApply(); /* Fall through... */ case RepeatCancelButton: /* ...to system */ break; case RepeatNone: case RepeatHourly: case RepeatDaily: case RepeatWeekly: case RepeatMonthly: case RepeatYearly: RepeatChangeType(event); handled = true; break; case RepeatDayOfWeek1PushButton: case RepeatDayOfWeek2PushButton: case RepeatDayOfWeek3PushButton: case RepeatDayOfWeek4PushButton: case RepeatDayOfWeek5PushButton: case RepeatDayOfWeek6PushButton: case RepeatDayOfWeek7PushButton: RepeatChangeRepeatOn(event); handled = true; break; case RepeatByDayPushButton: case RepeatByDatePushButton: RepeatDrawDescription(FrmGetFormPtr(RepeatForm)); handled = true; break; } } else if (event->eType == keyDownEvent && !TxtCharIsHardKey(event->data.keyDown.modifiers, event->data.keyDown.chr) && !EvtKeydownIsVirtual(event)) { const WChar chr = event->data.keyDown.chr; if (TxtCharIsDigit(chr) || TxtCharIsCntrl(chr)) { Boolean noSelection = true; UInt16 startPos = 0; UInt16 endPos = 0; FormType* frm = FrmGetFormPtr(RepeatForm); FieldType* fld = GetObjectPointer(frm, RepeatFrequenceField); FldGetSelection(fld, &startPos, &endPos); noSelection = startPos == endPos; FldHandleEvent(fld, event); /* ** There are 3 ways that the repeat every value can be ** updated ** 1) by the soft keyboard (on silkscreen) ** 2) via graffiti entry in the form with a selection range ** 3) via graffiti entry in the form with no selection range ** (i.e. just an insertion cursor) ** Methods 1 & 2 result in a fldChangedEvent being posted so the ** update will be handled in response to that event. ONLY when ** there is no selection range replacement, do we do the update here ** to avoid a double redraw of the description field. */ if (noSelection) RepeatDrawDescription(frm); } handled = true; } else if (event->eType == fldChangedEvent) { /* ** When the user changes the "repeat every" value via the ** soft keyboard or in the form via a selection replacement ** a fldChangedEvent is posted. Update the description in ** response. */ RepeatDrawDescription(FrmGetFormPtr(RepeatForm)); handled = true; } else if (event->eType == popSelectEvent) { if (event->data.popSelect.listID == RepeatEndOnList) { RepeatSelectEndDate (event); handled = true; } } return handled; }
static Boolean WordsListFormKeyDown(AppContext* appContext, FormType* form, EventType* event) { Boolean handled=false; if (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event)) { if (FiveWayCenterPressed(appContext, event)) { UInt16 selected=LstGetSelectionByListID(form, listProposals); WordsListFormSelectProposal(appContext, selected); handled=true; } else if (FiveWayDirectionPressed(appContext, event, Up )) { WordsListFormScrollList(form, -1); handled=true; } else if (FiveWayDirectionPressed(appContext, event, Down )) { WordsListFormScrollList(form, 1); handled=true; } else if (FiveWayDirectionPressed(appContext, event, Left )) { WordsListFormScrollList(form, -(appContext->dispLinesCount-1)); handled=true; } else if (FiveWayDirectionPressed(appContext, event, Right )) { WordsListFormScrollList(form, (appContext->dispLinesCount-1)); handled=true; } } else { switch (event->data.keyDown.chr) { case returnChr: case linefeedChr: UInt16 selected=LstGetSelectionByListID(form, listProposals); WordsListFormSelectProposal(appContext, selected); handled=true; break; case pageUpChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { WordsListFormScrollList(form, -(appContext->dispLinesCount-1)); handled=true; } break; case pageDownChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { WordsListFormScrollList(form, (appContext->dispLinesCount-1)); handled=true; } break; default: // notify ourselves that a text field is (possibly) updated SendFieldChanged(); // mark as unhandled so that text field will (possibly) get updated handled = false; break; } } return handled; }
static Boolean ResidentBrowseFormKeyDown(AppContext* appContext, FormType* form, EventType* event) { Boolean handled=false; switch (event->data.keyDown.chr) { case returnChr: case linefeedChr: ResidentBrowseFormChooseWord(appContext, form, appContext->selectedWord); handled=true; break; case pageUpChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { ScrollWordListByDx( appContext, form, -(appContext->dispLinesCount-1) ); handled=true; } break; case pageDownChr: if ( ! (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event) ) ) { ScrollWordListByDx( appContext, form, (appContext->dispLinesCount-1) ); handled=true; } break; default: if (HaveFiveWay(appContext) && EvtKeydownIsVirtual(event) && IsFiveWayEvent(appContext, event)) { if (FiveWayCenterPressed(appContext, event)) { ResidentBrowseFormChooseWord(appContext, form, appContext->selectedWord); handled=true; } if (FiveWayDirectionPressed(appContext, event, Left )) { ScrollWordListByDx(appContext, form, -(appContext->dispLinesCount-1)); handled=true; } if (FiveWayDirectionPressed(appContext, event, Right )) { ScrollWordListByDx( appContext, form, (appContext->dispLinesCount-1) ); handled=true; } if (FiveWayDirectionPressed(appContext, event, Up )) { ScrollWordListByDx( appContext, form, -1 ); handled=true; } if (FiveWayDirectionPressed(appContext, event, Down )) { ScrollWordListByDx( appContext, form, 1 ); handled=true; } } else { FieldType* field=NULL; UInt16 index=FrmGetObjectIndex(form, fieldWord); Assert(index!=frmInvalidObjectId); field=(FieldType*)FrmGetObjectPtr(form, index); Assert(field); FldSendChangeNotification(field); } } return handled; }
/*********************************************************************** * * FUNCTION: SelectTimeZone * * DESCRIPTION: Display a form showing a time zone and allow the user * to select a different time zone. This is the time zone * dialog as seen in Date & Dime panel * * PARAMETERS: * ioTimeZoneP <-> pointer to time zone to change * ioLocaleInTimeZoneP <-> Ptr to locale found in time zone. * titleP -> String title for the dialog. * showTimes -> True => show current and new times * anyLocale -> True => ignore ioLocaleInTimeZoneP on entry. * * RETURNED: * true if the OK button was pressed (in which case *ioTimeZoneP and * *ioCountryInTimeZoneP might be changed). * * HISTORY: * 03/02/00 peter Created by Peter Epstein. * 04/03/00 peter Allow NULL currentTimeP. * 04/12/00 peter API changed to get rid of trigger text * 04/14/00 peter Update current & new time as time passes * 07/31/00 kwk Use SysTicksPerSecond() routine vs. sysTicksPerSecond macro. * kwk Re-wrote to use set of resources (name, offset, country), * scrollbar vs. arrows, etc. * 08/01/00 kwk Support scroll-to-key. Fixed scrollbar/list sync bugs. * 08/02/00 kwk New API w/ioCountryInTimeZoneP and anyCountry parameters. * kwk Call FrmHandleEvent _after_ our event handling code has * decided that it doesn't want to handle the event, not before. * 08/03/00 kwk Call LstSetListChoices before calling LstGetVisibleItems, * as otherwise accessing the time zone picker from the * Setup app (when <showTimes> is false) gives you a two- * line high display because LstGetVisibleItems returns 0. * 08/18/00 kwk Play error sound if user writes letter that doesn't * match any entries. * kwk Don't select item if doing scroll-to-view for entry * that matches the letter the user wrote. * 08/21/00 kwk Scroll-to-view with text entry now scrolls to the top * of the list, versus the middle. * 10/09/00 peter Get rid of scroll bar and let list do the scrolling. * 11/17/00 CS Change ioCountryInTimeZoneP to ioLocaleInTimeZoneP, * (and anyCountry to anyLocale, but that doesn't matter), * since CountryType is only a UInt8, and this may * change someday. * ***********************************************************************/ Boolean SelectTimeZone(Int16 *ioTimeZoneP, LmLocaleType* ioLocaleInTimeZoneP, const Char *titleP, Boolean showTimes, Boolean anyLocale) { FormType* originalForm; FormType* dialog; EventType event; Boolean confirmed = false; Boolean done = false; Boolean adjustTimes = false; Boolean foundLocale = false; MemHandle currentTimeHandle, newTimeHandle; ListPtr listP; Int16 oldTimeZone, newTimeZone, testTimeZone; LmLocaleType newTimeZoneLocale; Int16 delta, closestDelta, timeZoneIndex, closestIndex; DateTimeType currentTime, newTime; TimeZoneEntryType* tzArrayP; UInt16 numTimeZones; MemHandle tzNamesH; if (showTimes) { TimSecondsToDateTime(TimGetSeconds(), ¤tTime); } oldTimeZone = *ioTimeZoneP; newTimeZone = oldTimeZone; newTimeZoneLocale = *ioLocaleInTimeZoneP; originalForm = FrmGetActiveForm(); dialog = (FormType *) FrmInitForm (TimeZoneDialogForm); listP = FrmGetObjectPtr (dialog, FrmGetObjectIndex (dialog, TimeZoneDialogTimeZoneList)); if (titleP) { FrmSetTitle (dialog, (Char *) titleP); } FrmSetActiveForm (dialog); // We need to call LstSetListChoices before calling LstSetHeight below, as otherwise // LstGetVisibleItems will return 0. tzArrayP = PrvCreateTimeZoneArray(&tzNamesH, &numTimeZones); LstSetListChoices(listP, (Char**)tzArrayP, numTimeZones); if (showTimes) { currentTimeHandle = MemHandleNew(timeStringLength + 1 + dowLongDateStrLength + 1); ErrFatalDisplayIf (!currentTimeHandle, "Out of memory"); newTimeHandle = MemHandleNew(timeStringLength + 1 + dowLongDateStrLength + 1); ErrFatalDisplayIf (!newTimeHandle, "Out of memory"); PrvSetTimeField(dialog, TimeZoneDialogCurrentTimeField, currentTimeHandle, ¤tTime, false); } else { // Hide the current and new time. FrmHideObject(dialog, FrmGetObjectIndex (dialog, TimeZoneDialogCurrentTimeLabel)); FrmHideObject(dialog, FrmGetObjectIndex (dialog, TimeZoneDialogCurrentTimeField)); FrmHideObject(dialog, FrmGetObjectIndex (dialog, TimeZoneDialogNewTimeLabel)); FrmHideObject(dialog, FrmGetObjectIndex (dialog, TimeZoneDialogNewTimeField)); // Make the list show more items to take up extra the space. LstSetHeight(listP, LstGetVisibleItems(listP) + extraTimeZonesToShowWhenNoTimes); } // Find the time zone in the list closest to the current time zone, and that // matches <*ioLocaleInTimeZoneP> if <anyLocale> is false. closestDelta = hoursInMinutes * hoursPerDay; // so big that all others will be smaller for (timeZoneIndex = 0; timeZoneIndex < numTimeZones; timeZoneIndex++) { Boolean checkDelta = anyLocale; testTimeZone = tzArrayP[timeZoneIndex].tzOffset; delta = Abs(testTimeZone - oldTimeZone); if (!anyLocale) { if (tzArrayP[timeZoneIndex].tzCountry == ioLocaleInTimeZoneP->country) { // If we haven't previously found a matching locale, reset the // delta so that this entry overrides any previous best entry. if (!foundLocale) { foundLocale = true; closestDelta = hoursInMinutes * hoursPerDay; } checkDelta = true; } // If we haven't yet found a matching locale, go for the closest delta. else { checkDelta = !foundLocale; } } // If we want to check the time zone delta, do it now. if (checkDelta && (delta < closestDelta)) { closestIndex = timeZoneIndex; closestDelta = delta; } } // Scroll so that time zone is in the center of the screen and select it if it's an exact match. LstSetTopItem(listP, max(0, closestIndex - (LstGetVisibleItems(listP) / 2))); if ((closestDelta == 0) && (anyLocale || foundLocale)) { LstSetSelection(listP, closestIndex); if (showTimes) { newTime = currentTime; PrvSetTimeField(dialog, TimeZoneDialogNewTimeField, newTimeHandle, &newTime, false); } } else { LstSetSelection(listP, noListSelection); } LstSetDrawFunction(listP, PrvTimeZoneListDrawItem); FrmDrawForm (dialog); while (!done) { Boolean handled = false; EvtGetEvent(&event, SysTicksPerSecond()); // so we can update the current and new time if (SysHandleEvent ((EventType *)&event)) { continue; } if (event.eType == nilEvent) { if (showTimes) { PrvUpdateTimeFields( dialog, ¤tTime, &newTime, currentTimeHandle, newTimeHandle, TimeZoneDialogCurrentTimeField, TimeZoneDialogNewTimeField); } } else if (event.eType == ctlSelectEvent) { handled = true; switch (event.data.ctlSelect.controlID) { case TimeZoneDialogOKButton: // Set the new time zone. *ioTimeZoneP = newTimeZone; *ioLocaleInTimeZoneP = newTimeZoneLocale; done = true; confirmed = true; break; case TimeZoneDialogCancelButton: done = true; break; default: ErrNonFatalDisplay("Unknown control in form"); break; } } // User tapped on a time zone in the list. else if (event.eType == lstSelectEvent) { UInt16 localeIndex; ErrNonFatalDisplayIf(event.data.lstSelect.listID != TimeZoneDialogTimeZoneList, "Unknown list in form"); newTimeZone = tzArrayP[event.data.lstSelect.selection].tzOffset; newTimeZoneLocale.country = tzArrayP[event.data.lstSelect.selection].tzCountry; newTimeZoneLocale.language = lmAnyLanguage; if (LmLocaleToIndex(&newTimeZoneLocale, &localeIndex) == errNone) { if (LmGetLocaleSetting( localeIndex, lmChoiceLocale, &newTimeZoneLocale, sizeof(newTimeZoneLocale))) { ErrNonFatalDisplay("Can\'t get locale"); } } adjustTimes = showTimes; handled = true; } else if (event.eType == keyDownEvent) { if (!TxtCharIsHardKey(event.data.keyDown.modifiers, event.data.keyDown.chr)) { // Hard scroll buttons if (EvtKeydownIsVirtual(&event)) { if (event.data.keyDown.chr == vchrPageUp) { handled = true; LstScrollList(listP, winUp, LstGetVisibleItems(listP) - 1); } else if (event.data.keyDown.chr == vchrPageDown) { handled = true; LstScrollList(listP, winDown, LstGetVisibleItems(listP) - 1); } } else if (TxtCharIsPrint(event.data.keyDown.chr)) { Int16 index; handled = true; index = PrvSearchTimeZoneNames(tzArrayP, numTimeZones, event.data.keyDown.chr); if (index != noListSelection) { Int16 delta = index - listP->topItem; if (delta < 0) { LstScrollList(listP, winUp, -delta); } else if (delta > 0) { LstScrollList(listP, winDown, delta); } } else { SndPlaySystemSound(sndError); } } } } else if (event.eType == appStopEvent) { EvtAddEventToQueue (&event); done = true; break; } // If we didn't handle the event, give the form code a crack at it. // This simulates the "normal" method of installing an event handler // for a form, which gets called, and then if it returns false, the // FrmHandleEvent routine gets called. if (!handled) { FrmHandleEvent(dialog, &event); } // If something changed, and we need to update our time display, // do it now. if (adjustTimes) { adjustTimes = false; newTime = currentTime; TimAdjust(&newTime, (Int32)(newTimeZone - oldTimeZone) * minutesInSeconds); PrvSetTimeField(dialog, TimeZoneDialogNewTimeField, newTimeHandle, &newTime, true); } } // end while true if (showTimes) { FldSetTextHandle(FrmGetObjectPtr (dialog, FrmGetObjectIndex (dialog, TimeZoneDialogCurrentTimeField)), NULL); FldSetTextHandle(FrmGetObjectPtr (dialog, FrmGetObjectIndex (dialog, TimeZoneDialogNewTimeField)), NULL); MemHandleFree(currentTimeHandle); MemHandleFree(newTimeHandle); } FrmEraseForm (dialog); FrmDeleteForm (dialog); FrmSetActiveForm(originalForm); PrvDeleteTimeZoneArray(tzArrayP, tzNamesH); return confirmed; } // SelectTimeZone