001: /*
002: *******************************************************************************
003: * Copyright (C) 1997-2006, International Business Machines Corporation and *
004: * others. All Rights Reserved. *
005: *******************************************************************************
006: */
007:
008: package com.ibm.icu.dev.demo.calendar;
009:
010: import java.awt.Button;
011: import java.awt.Checkbox;
012: import java.awt.CheckboxGroup;
013: import java.awt.Choice;
014: import java.awt.Component;
015: import java.awt.Container;
016: import java.awt.FlowLayout;
017: import java.awt.Font;
018: import java.awt.Frame;
019: import java.awt.GridLayout;
020: import java.awt.Label;
021: import java.awt.Panel;
022: import java.awt.TextField;
023: import java.awt.event.ActionEvent;
024: import java.awt.event.ActionListener;
025: import java.awt.event.ItemEvent;
026: import java.awt.event.ItemListener;
027: import java.awt.event.KeyEvent;
028: import java.awt.event.WindowEvent;
029: import java.text.ParsePosition;
030: import java.util.Date;
031: import java.util.Locale;
032:
033: import javax.swing.JTextField;
034:
035: import com.ibm.icu.dev.demo.impl.DemoApplet;
036: import com.ibm.icu.dev.demo.impl.DemoUtility;
037: import com.ibm.icu.text.DateFormat;
038: import com.ibm.icu.text.SimpleDateFormat;
039: import com.ibm.icu.util.BuddhistCalendar;
040: import com.ibm.icu.util.Calendar;
041: import com.ibm.icu.util.GregorianCalendar;
042: import com.ibm.icu.util.HebrewCalendar;
043: import com.ibm.icu.util.IslamicCalendar;
044: import com.ibm.icu.util.JapaneseCalendar;
045: import com.ibm.icu.util.TimeZone;
046:
047: /**
048: * CalendarCalc demonstrates how Date/Time formatter works.
049: */
050: public class CalendarCalc extends DemoApplet {
051: /**
052: * The main function which defines the behavior of the MultiCalendarDemo
053: * applet when an applet is started.
054: */
055: public static void main(String argv[]) {
056: new CalendarCalc().showDemo();
057: }
058:
059: /**
060: * This creates a CalendarCalcFrame for the demo applet.
061: */
062: public Frame createDemoFrame(DemoApplet applet) {
063: return new CalendarCalcFrame(applet);
064: }
065: }
066:
067: /**
068: * A Frame is a top-level window with a title. The default layout for a frame
069: * is BorderLayout. The CalendarCalcFrame class defines the window layout of
070: * MultiCalendarDemo.
071: */
072: class CalendarCalcFrame extends Frame implements ActionListener {
073: static final Locale[] locales = DemoUtility.getG7Locales();
074:
075: private DemoApplet applet;
076: private long time = System.currentTimeMillis();
077:
078: private static final RollAddField kRollAddFields[] = {
079: new RollAddField(Calendar.YEAR, "Year"),
080: new RollAddField(Calendar.MONTH, "Month"),
081: new RollAddField(Calendar.WEEK_OF_MONTH, "Week of Month"),
082: new RollAddField(Calendar.WEEK_OF_YEAR, "Week of Year"),
083: new RollAddField(Calendar.DAY_OF_MONTH, "Day of Month"),
084: new RollAddField(Calendar.DAY_OF_WEEK, "Day of Week"),
085: new RollAddField(Calendar.DAY_OF_WEEK_IN_MONTH,
086: "Day of Week in Month"),
087: new RollAddField(Calendar.DAY_OF_YEAR, "Day of Year"),
088: new RollAddField(Calendar.AM_PM, "AM/PM"),
089: new RollAddField(Calendar.HOUR_OF_DAY, "Hour of day"),
090: new RollAddField(Calendar.HOUR, "Hour"),
091: new RollAddField(Calendar.MINUTE, "Minute"),
092: new RollAddField(Calendar.SECOND, "Second"), };
093:
094: /**
095: * Constructs a new CalendarCalcFrame that is initially invisible.
096: */
097: public CalendarCalcFrame(DemoApplet applet) {
098: super ("Multiple Calendar Demo");
099: this .applet = applet;
100: init();
101: start();
102: }
103:
104: /**
105: * Initializes the applet. You never need to call this directly, it
106: * is called automatically by the system once the applet is created.
107: */
108: public void init() {
109: buildGUI();
110:
111: patternText.setText(calendars[0].toPattern());
112:
113: // Force an update of the display
114: cityChanged();
115: millisFormat();
116: enableEvents(KeyEvent.KEY_RELEASED);
117: enableEvents(WindowEvent.WINDOW_CLOSING);
118: }
119:
120: //------------------------------------------------------------
121: // package private
122: //------------------------------------------------------------
123: void addWithFont(Container container, Component foo, Font font) {
124: if (font != null)
125: foo.setFont(font);
126: container.add(foo);
127: }
128:
129: /**
130: * Called to start the applet. You never need to call this method
131: * directly, it is called when the applet's document is visited.
132: */
133: public void start() {
134: // do nothing
135: }
136:
137: TextField patternText;
138:
139: Choice dateMenu;
140: Choice localeMenu;
141:
142: Button up;
143: Button down;
144:
145: Checkbox getRoll;
146: Checkbox getAdd;
147:
148: public void buildGUI() {
149: setBackground(DemoUtility.bgColor);
150: setLayout(new FlowLayout()); // shouldn't be necessary, but it is.
151:
152: // TITLE
153: Label label1 = new Label("Calendar Converter", Label.CENTER);
154: label1.setFont(DemoUtility.titleFont);
155: add(label1);
156: add(DemoUtility.createSpacer());
157:
158: // IO Panel
159: Panel topPanel = new Panel();
160: topPanel.setLayout(new FlowLayout());
161:
162: CheckboxGroup group1 = new CheckboxGroup();
163:
164: // Set up the controls for each calendar we're demonstrating
165: for (int i = 0; i < calendars.length; i++) {
166: Label label = new Label(calendars[i].name, Label.RIGHT);
167: label.setFont(DemoUtility.labelFont);
168: topPanel.add(label);
169:
170: topPanel.add(calendars[i].text);
171:
172: final int j = i;
173: calendars[i].text.addActionListener(new ActionListener() {
174: public void actionPerformed(ActionEvent e) {
175: textChanged(j);
176: }
177: });
178:
179: calendars[i].rollAdd.setCheckboxGroup(group1);
180: topPanel.add(calendars[i].rollAdd);
181: }
182: calendars[0].rollAdd.setState(true); // Make the first one selected
183:
184: Label label4 = new Label("Pattern", Label.RIGHT);
185: label4.setFont(DemoUtility.labelFont);
186: topPanel.add(label4);
187:
188: patternText = new TextField(FIELD_COLUMNS);
189: patternText.setFont(DemoUtility.editFont);
190: topPanel.add(patternText);
191: topPanel.add(new Label(""));
192:
193: DemoUtility.fixGrid(topPanel, 3);
194: add(topPanel);
195: add(DemoUtility.createSpacer());
196:
197: // ROLL / ADD
198: Panel rollAddPanel = new Panel();
199: {
200: rollAddPanel.setLayout(new FlowLayout());
201:
202: Panel rollAddBoxes = new Panel();
203: {
204: rollAddBoxes.setLayout(new GridLayout(2, 1));
205: CheckboxGroup group2 = new CheckboxGroup();
206: getRoll = new Checkbox("Roll", group2, false);
207: getAdd = new Checkbox("Add", group2, true);
208:
209: rollAddBoxes.add(getRoll);
210: rollAddBoxes.add(getAdd);
211: }
212:
213: Label dateLabel = new Label("Date Fields");
214: dateLabel.setFont(DemoUtility.labelFont);
215:
216: dateMenu = new Choice();
217: dateMenu.setBackground(DemoUtility.choiceColor);
218: for (int i = 0; i < kRollAddFields.length; i++) {
219: dateMenu.addItem(kRollAddFields[i].name);
220: if (kRollAddFields[i].field == Calendar.MONTH) {
221: dateMenu.select(i);
222: }
223: }
224:
225: Panel upDown = new Panel();
226: {
227: upDown.setLayout(new GridLayout(2, 1));
228:
229: // *** If the images are not found, we use the label.
230: up = new Button("^");
231: down = new Button("v");
232: up.setBackground(DemoUtility.bgColor);
233: down.setBackground(DemoUtility.bgColor);
234: upDown.add(up);
235: upDown.add(down);
236: up.addActionListener(this );
237: down.addActionListener(this );
238: }
239:
240: rollAddPanel.add(dateLabel);
241: rollAddPanel.add(dateMenu);
242: rollAddPanel.add(rollAddBoxes);
243: rollAddPanel.add(upDown);
244:
245: }
246: Panel localePanel = new Panel();
247: {
248: // Make the locale popup menus
249: localeMenu = new Choice();
250: Locale defaultLocale = Locale.getDefault();
251: int bestMatch = -1, this Match = -1;
252: int selectMe = 0;
253:
254: for (int i = 0; i < locales.length; i++) {
255: if (i > 0
256: && locales[i].getLanguage().equals(
257: locales[i - 1].getLanguage())
258: || i < locales.length - 1
259: && locales[i].getLanguage().equals(
260: locales[i + 1].getLanguage())) {
261: localeMenu.addItem(locales[i].getDisplayName());
262: } else {
263: localeMenu.addItem(locales[i].getDisplayLanguage());
264: }
265:
266: this Match = DemoUtility.compareLocales(locales[i],
267: defaultLocale);
268:
269: if (this Match >= bestMatch) {
270: bestMatch = this Match;
271: selectMe = i;
272: }
273: }
274:
275: localeMenu.setBackground(DemoUtility.choiceColor);
276: localeMenu.select(selectMe);
277:
278: Label localeLabel = new Label("Display Locale");
279: localeLabel.setFont(DemoUtility.labelFont);
280:
281: localePanel.add(localeLabel);
282: localePanel.add(localeMenu);
283: DemoUtility.fixGrid(localePanel, 2);
284:
285: localeMenu.addItemListener(new ItemListener() {
286: public void itemStateChanged(ItemEvent e) {
287: Locale loc = locales[localeMenu.getSelectedIndex()];
288: System.out.println("Change locale to "
289: + loc.getDisplayName());
290:
291: for (int i = 0; i < calendars.length; i++) {
292: calendars[i].setLocale(loc);
293: }
294: millisFormat();
295: }
296: });
297: }
298: add(rollAddPanel);
299: add(DemoUtility.createSpacer());
300: add(localePanel);
301: add(DemoUtility.createSpacer());
302:
303: // COPYRIGHT
304: Panel copyrightPanel = new Panel();
305: addWithFont(copyrightPanel, new Label(DemoUtility.copyright1,
306: Label.LEFT), DemoUtility.creditFont);
307: DemoUtility.fixGrid(copyrightPanel, 1);
308: add(copyrightPanel);
309: }
310:
311: /**
312: * This function is called when users change the pattern text.
313: */
314: public void setFormatFromPattern() {
315: String timePattern = patternText.getText();
316:
317: for (int i = 0; i < calendars.length; i++) {
318: calendars[i].applyPattern(timePattern);
319: }
320:
321: millisFormat();
322: }
323:
324: /**
325: * This function is called when it is necessary to parse the time
326: * string in one of the formatted date fields
327: */
328: public void textChanged(int index) {
329: String rightString = calendars[index].text.getText();
330:
331: ParsePosition status = new ParsePosition(0);
332:
333: if (rightString.length() == 0) {
334: errorText("Error: no input to parse!");
335: return;
336: }
337:
338: try {
339: Date date = calendars[index].format.parse(rightString,
340: status);
341: time = date.getTime();
342: } catch (Exception e) {
343: for (int i = 0; i < calendars.length; i++) {
344: if (i != index) {
345: calendars[i].text.setText("ERROR");
346: }
347: }
348: errorText("Exception: " + e.getClass().toString()
349: + " parsing: " + rightString);
350: return;
351: }
352:
353: int start = calendars[index].text.getSelectionStart();
354: int end = calendars[index].text.getSelectionEnd();
355:
356: millisFormat();
357:
358: calendars[index].text.select(start, end);
359: }
360:
361: /**
362: * This function is called when it is necessary to format the time
363: * in the "Millis" text field.
364: */
365: public void millisFormat() {
366: String out = "";
367:
368: for (int i = 0; i < calendars.length; i++) {
369: try {
370: out = calendars[i].format.format(new Date(time));
371: calendars[i].text.setText(out);
372: } catch (Exception e) {
373: calendars[i].text.setText("ERROR");
374: errorText("Exception: " + e.getClass().toString()
375: + " formatting " + calendars[i].name + " "
376: + time);
377: }
378: }
379: }
380:
381: /**
382: * This function is called when users change the pattern text.
383: */
384: public void patternTextChanged() {
385: setFormatFromPattern();
386: }
387:
388: /**
389: * This function is called when users select a new representative city.
390: */
391: public void cityChanged() {
392: TimeZone timeZone = TimeZone.getDefault();
393:
394: for (int i = 0; i < calendars.length; i++) {
395: calendars[i].format.setTimeZone(timeZone);
396: }
397: millisFormat();
398: }
399:
400: /**
401: * This function is called when users select a new time field
402: * to add or roll its value.
403: */
404: public void dateFieldChanged(boolean up) {
405: int field = kRollAddFields[dateMenu.getSelectedIndex()].field;
406:
407: for (int i = 0; i < calendars.length; i++) {
408: if (calendars[i].rollAdd.getState()) {
409: Calendar c = calendars[i].calendar;
410: c.setTime(new Date(time));
411:
412: if (getAdd.getState()) {
413: c.add(field, up ? 1 : -1);
414: } else {
415: c.roll(field, up);
416: }
417:
418: time = c.getTime().getTime();
419: millisFormat();
420: break;
421: }
422: }
423: }
424:
425: /**
426: * Print out the error message while debugging this program.
427: */
428: public void errorText(String s) {
429: if (true) {
430: System.out.println(s);
431: }
432: }
433:
434: /**
435: * Called if an action occurs in the CalendarCalcFrame object.
436: */
437: public void actionPerformed(ActionEvent evt) {
438: // *** Button events are handled here.
439: Object obj = evt.getSource();
440: System.out.println("action " + obj);
441: if (obj instanceof Button) {
442: if (evt.getSource() == up) {
443: dateFieldChanged(false);
444: } else if (evt.getSource() == down) {
445: dateFieldChanged(true);
446: }
447: }
448: }
449:
450: /**
451: * Handles the event. Returns true if the event is handled and should not
452: * be passed to the parent of this component. The default event handler
453: * calls some helper methods to make life easier on the programmer.
454: */
455: protected void processKeyEvent(KeyEvent evt) {
456: System.out.println("key " + evt);
457: if (evt.getID() == KeyEvent.KEY_RELEASED) {
458: if (evt.getSource() == patternText) {
459: patternTextChanged();
460: } else {
461: for (int i = 0; i < calendars.length; i++) {
462: if (evt.getSource() == calendars[i].text) {
463: textChanged(i);
464: }
465: }
466: }
467: }
468: }
469:
470: protected void processWindowEvent(WindowEvent evt) {
471: System.out.println("window " + evt);
472: if (evt.getID() == WindowEvent.WINDOW_CLOSING
473: && evt.getSource() == this ) {
474: this .hide();
475: this .dispose();
476:
477: if (applet != null) {
478: applet.demoClosed();
479: } else
480: System.exit(0);
481: }
482: }
483:
484: /*
485: protected void processEvent(AWTEvent evt)
486: {
487: if (evt.getID() == AWTEvent. Event.ACTION_EVENT && evt.target == up) {
488: dateFieldChanged(true);
489: return true;
490: }
491: else if (evt.id == Event.ACTION_EVENT && evt.target == down) {
492: dateFieldChanged(false);
493: return true;
494: }
495: }
496: */
497:
498: private static final int FIELD_COLUMNS = 35;
499:
500: class CalendarRec {
501: public CalendarRec(String nameStr, Calendar cal) {
502: name = nameStr;
503: calendar = cal;
504: rollAdd = new Checkbox();
505:
506: text = new JTextField("", FIELD_COLUMNS);
507: text.setFont(DemoUtility.editFont);
508:
509: format = DateFormat.getDateInstance(cal, DateFormat.FULL,
510: Locale.getDefault());
511: //format.applyPattern(DEFAULT_FORMAT);
512: }
513:
514: public void setLocale(Locale loc) {
515: String pattern = toPattern();
516:
517: format = DateFormat.getDateInstance(calendar,
518: DateFormat.FULL, loc);
519: applyPattern(pattern);
520: }
521:
522: public void applyPattern(String pattern) {
523: if (format instanceof SimpleDateFormat) {
524: ((SimpleDateFormat) format).applyPattern(pattern);
525: //hey {al} -
526: // } else if (format instanceof java.text.SimpleDateFormat) {
527: // ((java.text.SimpleDateFormat)format).applyPattern(pattern);
528: }
529: }
530:
531: private String toPattern() {
532: if (format instanceof SimpleDateFormat) {
533: return ((SimpleDateFormat) format).toPattern();
534: //hey {al} -
535: // } else if (format instanceof java.text.SimpleDateFormat) {
536: // return ((java.text.SimpleDateFormat)format).toPattern();
537: }
538: return "";
539: }
540:
541: Calendar calendar;
542: DateFormat format;
543: String name;
544: JTextField text;
545: Checkbox rollAdd;
546: }
547:
548: private final CalendarRec[] calendars = {
549: new CalendarRec("Gregorian", new GregorianCalendar()),
550: new CalendarRec("Hebrew", new HebrewCalendar()),
551: new CalendarRec("Islamic (civil)", makeIslamic(true)),
552: new CalendarRec("Islamic (true)", makeIslamic(false)),
553: new CalendarRec("Buddhist", new BuddhistCalendar()),
554: new CalendarRec("Japanese", new JapaneseCalendar()),
555: // new CalendarRec("Chinese", new ChineseCalendar()),
556: };
557:
558: static private final Calendar makeIslamic(boolean civil) {
559: IslamicCalendar cal = new IslamicCalendar();
560: cal.setCivil(civil);
561: return cal;
562: }
563: }
564:
565: class RollAddField {
566: RollAddField(int field, String name) {
567: this .field = field;
568: this .name = name;
569: }
570:
571: int field;
572: String name;
573: }
|