To display month dynamically in visual force

apexdynamic-visualforcevisualforce

here is my code. What I want is to display the month in format (Jan, Feb, etc.) in a visual force. My expected output is let's say today is September, so the dropdown value will have Jul, Aug, Sep, Oct, Nov, the default value must be Sep for this month. but I don't get that value. I get Mar until Aug. May I know how to fix the code?

public String SelectedMonth {get; set;}
    public List<SelectOption> getItems() {
        List<SelectOption> options = new List<SelectOption>();
        for(Integer i = System.Today().month() - 3; i < System.Today().month() + 3; i++){
            String previousMonth = DateTime.now().addmonths(i).format('MMM');
            options.add(new SelectOption(String.valueOf(previousMonth), String.valueOf(previousMonth)));
        }
        return options;
    }

    public Month() {
        SelectedMonth = String.valueOf(System.Today().month());
        System.debug('The value is : ' + SelectedMonth);
    }

Best Answer

This code should be counting from -2 to +2. You thought you were setting the month, but you're adding an offset instead. Consider the first month. You end up doing 9 minus 3 to get 6, so then you're adding 6 months to 9, which rolls over to March of next year (9 + 6 = 15, so we modulus 12, to get to month 3, or March).

We fix this by counting from -2 to +2, to give us the previous two months, this month, and the next two months.

List<SelectOption> getItems() {
    List<SelectOption> options = new List<SelectOption>();
    DateTime now = DateTime.now();
    for(Integer i = -2; i <= 2; i++) {
        String month = now.addmonths(i).format('MMM');
        options.add(new SelectOption(month, month));
    }
    return options;
}

Also, you're mapping the three-letter abbreviation to the key, so SelectedMonth needs to read, for example, 'Sep', and not '9', as you're setting it now. I'd advise just using the month number for simplicity:

List<SelectOption> getItems() {
    List<SelectOption> options = new List<SelectOption>();
    DateTime now = DateTime.now();
    for(Integer i = -2; i <= 2; i++) {
        String month = now.addmonths(i).format('MMM');
        options.add(new SelectOption(''+i, month));
    }
    return options;
}

So you can then simply do:

SelectedMonth = ''+System.Today().month();

You'll need to obviously convert back to an Integer before you can operate with it in a Date/DateTime format.

Also note that there's a very obscure race condition if you get really close to midnight of a given day, so we cache DateTime.now() so we avoid this problem. It's a really small window, only a few milliseconds, but I like to avoid such problems when practical.

Related Topic