private void subFormat(int patternCharIndex,int count,FieldDelegate delegate,StringBuffer buffer,boolean useDateFormatSymbols){
  int maxIntCount=Integer.MAX_VALUE;
  String current=null;
  int beginOffset=buffer.length();
  int field=PATTERN_INDEX_TO_CALENDAR_FIELD[patternCharIndex];
  int value;
  if (field == CalendarBuilder.WEEK_YEAR) {
    if (calendar.isWeekDateSupported()) {
      value=calendar.getWeekYear();
    }
 else {
      patternCharIndex=PATTERN_YEAR;
      field=PATTERN_INDEX_TO_CALENDAR_FIELD[patternCharIndex];
      value=calendar.get(field);
    }
  }
 else   if (field == CalendarBuilder.ISO_DAY_OF_WEEK) {
    value=CalendarBuilder.toISODayOfWeek(calendar.get(Calendar.DAY_OF_WEEK));
  }
 else {
    value=calendar.get(field);
  }
  int style=(count >= 4) ? Calendar.LONG : Calendar.SHORT;
  if (!useDateFormatSymbols && field < Calendar.ZONE_OFFSET && patternCharIndex != PATTERN_MONTH_STANDALONE) {
    current=calendar.getDisplayName(field,style,locale);
  }
switch (patternCharIndex) {
case PATTERN_ERA:
    if (useDateFormatSymbols) {
      String[] eras=formatData.getEras();
      if (value < eras.length) {
        current=eras[value];
      }
    }
  if (current == null) {
    current="";
  }
break;
case PATTERN_WEEK_YEAR:
case PATTERN_YEAR:
if (calendar instanceof GregorianCalendar) {
if (count != 2) {
  zeroPaddingNumber(value,count,maxIntCount,buffer);
}
 else {
  zeroPaddingNumber(value,2,2,buffer);
}
}
 else {
if (current == null) {
  zeroPaddingNumber(value,style == Calendar.LONG ? 1 : count,maxIntCount,buffer);
}
}
break;
case PATTERN_MONTH:
if (useDateFormatSymbols) {
String[] months;
if (count >= 4) {
months=formatData.getMonths();
current=months[value];
}
 else if (count == 3) {
months=formatData.getShortMonths();
current=months[value];
}
}
 else {
if (count < 3) {
current=null;
}
 else if (forceStandaloneForm) {
current=calendar.getDisplayName(field,style | 0x8000,locale);
if (current == null) {
current=calendar.getDisplayName(field,style,locale);
}
}
}
if (current == null) {
zeroPaddingNumber(value + 1,count,maxIntCount,buffer);
}
break;
case PATTERN_MONTH_STANDALONE:
assert current == null;
if (locale == null) {
String[] months;
if (count >= 4) {
months=formatData.getMonths();
current=months[value];
}
 else if (count == 3) {
months=formatData.getShortMonths();
current=months[value];
}
}
 else {
if (count >= 3) {
current=calendar.getDisplayName(field,style | 0x8000,locale);
}
}
if (current == null) {
zeroPaddingNumber(value + 1,count,maxIntCount,buffer);
}
break;
case PATTERN_HOUR_OF_DAY1:
if (current == null) {
if (value == 0) {
zeroPaddingNumber(calendar.getMaximum(Calendar.HOUR_OF_DAY) + 1,count,maxIntCount,buffer);
}
 else {
zeroPaddingNumber(value,count,maxIntCount,buffer);
}
}
break;
case PATTERN_DAY_OF_WEEK:
if (useDateFormatSymbols) {
String[] weekdays;
if (count >= 4) {
weekdays=formatData.getWeekdays();
current=weekdays[value];
}
 else {
weekdays=formatData.getShortWeekdays();
current=weekdays[value];
}
}
break;
case PATTERN_AM_PM:
if (useDateFormatSymbols) {
String[] ampm=formatData.getAmPmStrings();
current=ampm[value];
}
break;
case PATTERN_HOUR1:
if (current == null) {
if (value == 0) {
zeroPaddingNumber(calendar.getLeastMaximum(Calendar.HOUR) + 1,count,maxIntCount,buffer);
}
 else {
zeroPaddingNumber(value,count,maxIntCount,buffer);
}
}
break;
case PATTERN_ZONE_NAME:
if (current == null) {
if (formatData.locale == null || formatData.isZoneStringsSet) {
int zoneIndex=formatData.getZoneIndex(calendar.getTimeZone().getID());
if (zoneIndex == -1) {
value=calendar.get(Calendar.ZONE_OFFSET) + calendar.get(Calendar.DST_OFFSET);
buffer.append(ZoneInfoFile.toCustomID(value));
}
 else {
int index=(calendar.get(Calendar.DST_OFFSET) == 0) ? 1 : 3;
if (count < 4) {
index++;
}
String[][] zoneStrings=formatData.getZoneStringsWrapper();
buffer.append(zoneStrings[zoneIndex][index]);
}
}
 else {
TimeZone tz=calendar.getTimeZone();
boolean daylight=(calendar.get(Calendar.DST_OFFSET) != 0);
int tzstyle=(count < 4 ? TimeZone.SHORT : TimeZone.LONG);
buffer.append(tz.getDisplayName(daylight,tzstyle,formatData.locale));
}
}
break;
case PATTERN_ZONE_VALUE:
value=(calendar.get(Calendar.ZONE_OFFSET) + calendar.get(Calendar.DST_OFFSET)) / 60000;
int width=4;
if (value >= 0) {
buffer.append('+');
}
 else {
width++;
}
int num=(value / 60) * 100 + (value % 60);
CalendarUtils.sprintf0d(buffer,num,width);
break;
case PATTERN_ISO_ZONE:
value=calendar.get(Calendar.ZONE_OFFSET) + calendar.get(Calendar.DST_OFFSET);
if (value == 0) {
buffer.append('Z');
break;
}
value/=60000;
if (value >= 0) {
buffer.append('+');
}
 else {
buffer.append('-');
value=-value;
}
CalendarUtils.sprintf0d(buffer,value / 60,2);
if (count == 1) {
break;
}
if (count == 3) {
buffer.append(':');
}
CalendarUtils.sprintf0d(buffer,value % 60,2);
break;
default :
if (current == null) {
zeroPaddingNumber(value,count,maxIntCount,buffer);
}
break;
}
if (current != null) {
buffer.append(current);
}
int fieldID=PATTERN_INDEX_TO_DATE_FORMAT_FIELD[patternCharIndex];
Field f=PATTERN_INDEX_TO_DATE_FORMAT_FIELD_ID[patternCharIndex];
delegate.formatted(fieldID,f,f,beginOffset,buffer.length(),buffer);
}

private void subFormat ( int patternCharIndex , int count , FieldDelegate delegate , StringBuffer buffer , boolean useDateFormatSymbols ) { int maxIntCount = Integer . MAX_VALUE ; String current = null ; int beginOffset = buffer . length ( ) ; int field = PATTERN_INDEX_TO_CALENDAR_FIELD [ patternCharIndex ] ; int value ; if ( field == CalendarBuilder . WEEK_YEAR ) { if ( calendar . isWeekDateSupported ( ) ) { value = calendar . getWeekYear ( ) ; } else { patternCharIndex = PATTERN_YEAR ; field = PATTERN_INDEX_TO_CALENDAR_FIELD [ patternCharIndex ] ; value = calendar . get ( field ) ; } } else if ( field == CalendarBuilder . ISO_DAY_OF_WEEK ) { value = CalendarBuilder . toISODayOfWeek ( calendar . get ( Calendar . DAY_OF_WEEK ) ) ; } else { value = calendar . get ( field ) ; } int style = ( count >= 4 ) ? Calendar . LONG : Calendar . SHORT ; if ( ! useDateFormatSymbols && field < Calendar . ZONE_OFFSET && patternCharIndex != PATTERN_MONTH_STANDALONE ) { current = calendar . getDisplayName ( field , style , locale ) ; } switch ( patternCharIndex ) { case PATTERN_ERA : if ( useDateFormatSymbols ) { String [ ] eras = formatData . getEras ( ) ; if ( value < eras . length ) { current = eras [ value ] ; } } if ( current == null ) { current = "" ; } break ; case PATTERN_WEEK_YEAR : case PATTERN_YEAR : if ( calendar instanceof GregorianCalendar ) { if ( count != 2 ) { zeroPaddingNumber ( value , count , maxIntCount , buffer ) ; } else { zeroPaddingNumber ( value , 2 , 2 , buffer ) ; } } else { if ( current == null ) { zeroPaddingNumber ( value , style == Calendar . LONG ? 1 : count , maxIntCount , buffer ) ; } } break ; case PATTERN_MONTH : if ( useDateFormatSymbols ) { String [ ] months ; if ( count >= 4 ) { months = formatData . getMonths ( ) ; current = months [ value ] ; } else if ( count == 3 ) { months = formatData . getShortMonths ( ) ; current = months [ value ] ; } } else { if ( count < 3 ) { current = null ; } else if ( forceStandaloneForm ) { current = calendar . getDisplayName ( field , style | 0x8000 , locale ) ; if ( current == null ) { current = calendar . getDisplayName ( field , style , locale ) ; } } } if ( current == null ) { zeroPaddingNumber ( value + 1 , count , maxIntCount , buffer ) ; } break ; case PATTERN_MONTH_STANDALONE : assert current == null ; if ( locale == null ) { String [ ] months ; if ( count >= 4 ) { months = formatData . getMonths ( ) ; current = months [ value ] ; } else if ( count == 3 ) { months = formatData . getShortMonths ( ) ; current = months [ value ] ; } } else { if ( count >= 3 ) { current = calendar . getDisplayName ( field , style | 0x8000 , locale ) ; } } if ( current == null ) { zeroPaddingNumber ( value + 1 , count , maxIntCount , buffer ) ; } break ; case PATTERN_HOUR_OF_DAY1 : if ( current == null ) { if ( value == 0 ) { zeroPaddingNumber ( calendar . getMaximum ( Calendar . HOUR_OF_DAY ) + 1 , count , maxIntCount , buffer ) ; } else { zeroPaddingNumber ( value , count , maxIntCount , buffer ) ; } } break ; case PATTERN_DAY_OF_WEEK : if ( useDateFormatSymbols ) { String [ ] weekdays ; if ( count >= 4 ) { weekdays = formatData . getWeekdays ( ) ; current = weekdays [ value ] ; } else { weekdays = formatData . getShortWeekdays ( ) ; current = weekdays [ value ] ; } } break ; case PATTERN_AM_PM : if ( useDateFormatSymbols ) { String [ ] ampm = formatData . getAmPmStrings ( ) ; current = ampm [ value ] ; } break ; case PATTERN_HOUR1 : if ( current == null ) { if ( value == 0 ) { zeroPaddingNumber ( calendar . getLeastMaximum ( Calendar . HOUR ) + 1 , count , maxIntCount , buffer ) ; } else { zeroPaddingNumber ( value , count , maxIntCount , buffer ) ; } } break ; case PATTERN_ZONE_NAME : if ( current == null ) { if ( formatData . locale == null || formatData . isZoneStringsSet ) { int zoneIndex = formatData . getZoneIndex ( calendar . getTimeZone ( ) . getID ( ) ) ; if ( zoneIndex == - 1 ) { value = calendar . get ( Calendar . ZONE_OFFSET ) + calendar . get ( Calendar . DST_OFFSET ) ; buffer . append ( ZoneInfoFile . toCustomID ( value ) ) ; } else { int index = ( calendar . get ( Calendar . DST_OFFSET ) == 0 ) ? 1 : 3 ; if ( count < 4 ) { index ++ ; } String [ ] [ ] zoneStrings = formatData . getZoneStringsWrapper ( ) ; buffer . append ( zoneStrings [ zoneIndex ] [ index ] ) ; } } else { TimeZone tz = calendar . getTimeZone ( ) ; boolean daylight = ( calendar . get ( Calendar . DST_OFFSET ) != 0 ) ; int tzstyle = ( count < 4 ? TimeZone . SHORT : TimeZone . LONG ) ; buffer . append ( tz . getDisplayName ( daylight , tzstyle , formatData . locale ) ) ; } } break ; case PATTERN_ZONE_VALUE : value = ( calendar . get ( Calendar . ZONE_OFFSET ) + calendar . get ( Calendar . DST_OFFSET ) ) / 60000 ; int width = 4 ; if ( value >= 0 ) { buffer . append ( '+' ) ; } else { width ++ ; } int num = ( value / 60 ) * 100 + ( value % 60 ) ; CalendarUtils . sprintf0d ( buffer , num , width ) ; break ; case PATTERN_ISO_ZONE : value = calendar . get ( Calendar . ZONE_OFFSET ) + calendar . get ( Calendar . DST_OFFSET ) ; if ( value == 0 ) { buffer . append ( 'Z' ) ; break ; } value /= 60000 ; if ( value >= 0 ) { buffer . append ( '+' ) ; } else { buffer . append ( '-' ) ; value = - value ; } CalendarUtils . sprintf0d ( buffer , value / 60 , 2 ) ; if ( count == 1 ) { break ; } if ( count == 3 ) { buffer . append ( ':' ) ; } CalendarUtils . sprintf0d ( buffer , value % 60 , 2 ) ; break ; default : if ( current == null ) { zeroPaddingNumber ( value , count , maxIntCount , buffer ) ; } break ; } if ( current != null ) { buffer . append ( current ) ; } int fieldID = PATTERN_INDEX_TO_DATE_FORMAT_FIELD [ patternCharIndex ] ; Field f = PATTERN_INDEX_TO_DATE_FORMAT_FIELD_ID [ patternCharIndex ] ; delegate . formatted ( fieldID , f , f , beginOffset , buffer . length ( ) , buffer ) ; }
private member function that does the real date / time formatting .
