Example #1
0
gboolean
recurrenceListIsSemiMonthly(GList *recurrences)
{
    if (g_list_length(recurrences) != 2)
        return FALSE;

    // should be a "semi-monthly":
    {
        Recurrence *first = (Recurrence*)g_list_nth_data(recurrences, 0);
        Recurrence *second = (Recurrence*)g_list_nth_data(recurrences, 1);
        PeriodType first_period, second_period;
        first_period = recurrenceGetPeriodType(first);
        second_period = recurrenceGetPeriodType(second);

        if (!((first_period == PERIOD_MONTH
                || first_period == PERIOD_END_OF_MONTH
                || first_period == PERIOD_LAST_WEEKDAY)
                && (second_period == PERIOD_MONTH
                    || second_period == PERIOD_END_OF_MONTH
                    || second_period == PERIOD_LAST_WEEKDAY)))
        {
            /*g_error("unknown 2-recurrence composite with period_types first [%d] second [%d]",
              first_period, second_periodD);*/
            return FALSE;
        }
    }
    return TRUE;
}
Example #2
0
static int
_get_monthly_combobox_index(Recurrence *r)
{
    GDate recurrence_date = recurrenceGetDate(r);
    int week = 0;
    int day_of_month_index = g_date_get_day(&recurrence_date) - 1;
    if (recurrenceGetPeriodType(r) == PERIOD_END_OF_MONTH)
    {
        day_of_month_index = LAST_DAY_OF_MONTH_OPTION_INDEX;
    }
    else if (recurrenceGetPeriodType(r) == PERIOD_LAST_WEEKDAY)
    {
        day_of_month_index
        = LAST_DAY_OF_MONTH_OPTION_INDEX
          + g_date_get_weekday(&recurrence_date);
    }
    else if (recurrenceGetPeriodType(r) == PERIOD_NTH_WEEKDAY)
    {
        week = day_of_month_index / 7 > 3 ? 3 : day_of_month_index / 7;
        if (week > 0 && day_of_month_index % 7 == 0)
            --week;
        day_of_month_index = LAST_DAY_OF_MONTH_OPTION_INDEX + 7 +
                             g_date_get_weekday(&recurrence_date) + 7 * week;


    }
    /* else { default value } */
    return day_of_month_index;
}
Example #3
0
static void
_monthly_append_when(Recurrence *r, GString *buf)
{
    GDate date = recurrenceGetDate(r);
    if (recurrenceGetPeriodType(r) == PERIOD_LAST_WEEKDAY)
    {
        gchar day_name_buf[abbrev_day_name_bufsize];

        gnc_dow_abbrev(day_name_buf, abbrev_day_name_bufsize, g_date_get_weekday(&date) % 7);

        /* translators: %s is an already-localized form of the day of the week. */
        g_string_append_printf(buf, _("last %s"), day_name_buf);
    }
    else if (recurrenceGetPeriodType(r) == PERIOD_NTH_WEEKDAY)
    {
        int week = 0;
        int day_of_month_index = 0;
        const char *numerals[] = {N_("1st"), N_("2nd"), N_("3rd"), N_("4th")};
        gchar day_name_buf[abbrev_day_name_bufsize];

        gnc_dow_abbrev(day_name_buf, abbrev_day_name_bufsize, g_date_get_weekday(&date) % 7);
        day_of_month_index = g_date_get_day(&date) - 1;
        week = day_of_month_index / 7 > 3 ? 3 : day_of_month_index / 7;
        if (week > 0 && day_of_month_index % 7 == 0)
            --week;
        /* translators: %s is the string 1st, 2nd, 3rd and so on, and
         * %s is an already-localized form of the day of the week. */
        g_string_append_printf(buf, _("%s %s"), _(numerals[week]), day_name_buf);
    }
    else
    {
        /* translators: %u is the day of month */
        g_string_append_printf(buf, "%u", g_date_get_day(&date));
    }
}
Example #4
0
static void
_fixup_recurrence_start_dates(const GDate *sx_start_date, GList *schedule)
{
    GList *iter;
    for (iter = schedule; iter != NULL; iter = iter->next)
    {
        Recurrence *r;
        GDate start, next;

        r = (Recurrence*)iter->data;

        start = *sx_start_date;
        g_date_subtract_days(&start, 1);

        g_date_clear(&next, 1);

        recurrenceNextInstance(r, &start, &next);
        g_return_if_fail(g_date_valid(&next));

        {
            gchar date_str[128];
            gchar *sched_str;

            g_date_strftime(date_str, 127, "%x", &next);
            sched_str = recurrenceToString(r);
            g_debug("setting recurrence [%s] start date to [%s]",
                    sched_str, date_str);
            g_free(sched_str);
        }

        recurrenceSet(r,
                      recurrenceGetMultiplier(r),
                      recurrenceGetPeriodType(r),
                      &next,
                      recurrenceGetWeekendAdjust(r));
    }

    if (g_list_length(schedule) == 1
            && recurrenceGetPeriodType((Recurrence*)g_list_nth_data(schedule, 0)) == PERIOD_ONCE)
    {
        char date_buf[128];
        Recurrence *fixup = (Recurrence*)g_list_nth_data(schedule, 0);
        g_date_strftime(date_buf, 127, "%x", sx_start_date);
        recurrenceSet(fixup, 1, PERIOD_ONCE, sx_start_date, WEEKEND_ADJ_NONE);
        g_debug("fixed up period=ONCE Recurrence to date [%s]", date_buf);
    }
}
Example #5
0
static /*@ null @*/ gpointer
get_recurrence_period_type( gpointer pObject )
{
    recurrence_info_t* pInfo = (recurrence_info_t*)pObject;

    g_return_val_if_fail( pObject != NULL, NULL );
    g_return_val_if_fail( pInfo->pRecurrence != NULL, NULL );

    return (gpointer)recurrencePeriodTypeToString(
               recurrenceGetPeriodType( pInfo->pRecurrence ) );
}
Example #6
0
int
recurrenceCmp(Recurrence *a, Recurrence *b)
{
    PeriodType period_a, period_b;
    int a_order_index, b_order_index;

    g_return_val_if_fail(a != NULL && b != NULL, 0);
    g_return_val_if_fail(a != NULL, 1);
    g_return_val_if_fail(b != NULL, -1);

    period_a = recurrenceGetPeriodType(a);
    period_b = recurrenceGetPeriodType(b);

    a_order_index = cmp_order_indexes[period_a];
    b_order_index = cmp_order_indexes[period_b];
    if (a_order_index != b_order_index)
    {
        return a_order_index - b_order_index;
    }
    else if (a_order_index == cmp_order_indexes[PERIOD_MONTH])
    {
        // re-order intra-month options:
        a_order_index = cmp_monthly_order_indexes[period_a];
        b_order_index = cmp_monthly_order_indexes[period_b];
        g_assert(a_order_index != -1 && b_order_index != -1);
        if (a_order_index != b_order_index)
            return a_order_index - b_order_index;
    }
    /* else { the basic periods are equal; compare the multipliers } */

    {
        int a_mult, b_mult;
        a_mult = recurrenceGetMultiplier(a);
        b_mult = recurrenceGetMultiplier(b);

        return a_mult - b_mult;
    }
}
Example #7
0
gboolean
recurrenceListIsWeeklyMultiple(const GList *recurrences)
{
    const GList *r_iter;

    for (r_iter = recurrences; r_iter != NULL; r_iter = r_iter->next)
    {
        Recurrence *r = (Recurrence*)r_iter->data;
        if (recurrenceGetPeriodType(r) != PERIOD_WEEK)
        {
            return FALSE;
        }
    }
    return TRUE;
}
Example #8
0
static void
_monthly_append_when(Recurrence *r, GString *buf)
{
    GDate date = recurrenceGetDate(r);
    if (recurrenceGetPeriodType(r) == PERIOD_LAST_WEEKDAY)
    {
        gchar day_name_buf[abbrev_day_name_bufsize];

        gnc_dow_abbrev(day_name_buf, abbrev_day_name_bufsize, g_date_get_weekday(&date) % 7);

        /* translators: %s is an already-localized form of the day of the week. */
        g_string_append_printf(buf, _("last %s"), day_name_buf);
    }
    else
    {
        /* translators: %u is the day of month */
        g_string_append_printf(buf, "%u", g_date_get_day(&date));
    }
}
Example #9
0
/* Mult of zero is usually not valid, but it gets regularized to 1, so
   the effect is just that we end up testing mult of 1 twice, plus the
   regularization. */
static void test_all()
{
    Recurrence r;
    GDate d_start, d_start_reg;
    GDate d_ref, d_next;
    guint16 mult, mult_reg;
    PeriodType pt, pt_reg;
    WeekendAdjust wadj, wadj_reg;
    gint32 j1, j2;
    gint i_ref;

    for (pt = PERIOD_ONCE; pt < NUM_PERIOD_TYPES; pt++)
    {
        for (wadj = WEEKEND_ADJ_NONE; wadj < NUM_WEEKEND_ADJS; wadj++)
        {
            for (j1 = JULIAN_START; j1 < JULIAN_START + NUM_DATES_TO_TEST; j1++)
            {
                g_date_set_julian(&d_start, j1);
                for (i_ref = 0; i_ref < NUM_DATES_TO_TEST_REF; i_ref++)
                {
                    j2 = (guint32) get_random_int_in_range(1, 1 << 19);
                    g_date_set_julian(&d_ref, j2);

                    for (mult = 0; mult < NUM_MULT_TO_TEST; mult++)
                    {
                        recurrenceSet(&r, mult, pt, &d_start, wadj);
                        pt_reg = recurrenceGetPeriodType(&r);
                        d_start_reg = recurrenceGetDate(&r);
                        mult_reg = recurrenceGetMultiplier(&r);
                        wadj_reg = recurrenceGetWeekendAdjust(&r);

                        recurrenceNextInstance(&r, &d_ref, &d_next);
                        check_valid(&d_next, &d_ref, &d_start_reg,
                                    mult_reg, pt_reg, wadj_reg);

                    }
                }
            }
        }
    }
}
Example #10
0
void
gnc_recurrence_set(GncRecurrence *gr, const Recurrence *r)
{
    PeriodType pt;
    guint mult;
    GDate start;

    g_return_if_fail(gr && r);
    pt = recurrenceGetPeriodType(r);
    mult = recurrenceGetMultiplier(r);
    start = recurrenceGetDate(r);

    gtk_spin_button_set_value(gr->gsb_mult, (gdouble) mult);

    // is there some better way?
    {
        time64 t;
        t = gnc_time64_get_day_start_gdate (&start);
        gnc_date_edit_set_time (GNC_DATE_EDIT(gr->gde_start), t);
    }

    set_pt_ui(gr, pt);
}
Example #11
0
void
gnc_frequency_setup(GncFrequency *gf, GList *recurrences, const GDate *start_date)
{
    gboolean made_changes = FALSE;

    // setup start-date, if present
    if (start_date != NULL
            && g_date_valid(start_date))
    {
        gnc_date_edit_set_gdate(gf->startDate, start_date);
        made_changes = TRUE;
    }

    if (recurrences == NULL)
    {
        goto maybe_signal;
        // return...
    }

    if (g_list_length(recurrences) > 1)
    {
        if (recurrenceListIsWeeklyMultiple(recurrences))
        {
            for (; recurrences != NULL; recurrences = recurrences->next)
            {
                _setup_weekly_recurrence(gf, (Recurrence*)recurrences->data);
            }

            gtk_notebook_set_current_page(gf->nb, PAGE_WEEKLY);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_WEEKLY);
        }
        else if (recurrenceListIsSemiMonthly(recurrences))
        {
            Recurrence *first, *second;
            GtkWidget *multiplier_spin;
            GtkWidget *dom_combobox;

            first = (Recurrence*)g_list_nth_data(recurrences, 0);
            second = (Recurrence*)g_list_nth_data(recurrences, 1);

            multiplier_spin = glade_xml_get_widget(gf->gxml, "semimonthly_spin");
            gtk_spin_button_set_value(GTK_SPIN_BUTTON(multiplier_spin), recurrenceGetMultiplier(first));

            dom_combobox = glade_xml_get_widget(gf->gxml, "semimonthly_first");
            gtk_combo_box_set_active(GTK_COMBO_BOX(dom_combobox), _get_monthly_combobox_index(first));
            dom_combobox = glade_xml_get_widget(gf->gxml, "semimonthly_first_weekend");
            gtk_combo_box_set_active(GTK_COMBO_BOX(dom_combobox), recurrenceGetWeekendAdjust(first));
            dom_combobox = glade_xml_get_widget(gf->gxml, "semimonthly_second");
            gtk_combo_box_set_active(GTK_COMBO_BOX(dom_combobox), _get_monthly_combobox_index(second));
            dom_combobox = glade_xml_get_widget(gf->gxml, "semimonthly_second_weekend");
            gtk_combo_box_set_active(GTK_COMBO_BOX(dom_combobox), recurrenceGetWeekendAdjust(second));

            gtk_notebook_set_current_page(gf->nb, PAGE_SEMI_MONTHLY);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_SEMI_MONTHLY);
        }
        else
        {
            g_error("unknown composite recurrence with [%d] entries", g_list_length(recurrences));
        }
    }
    else
    {
        Recurrence *r = (Recurrence*)recurrences->data;
        g_debug("recurrence period [%d]", recurrenceGetPeriodType(r));
        switch (recurrenceGetPeriodType(r))
        {
        case PERIOD_ONCE:
        {
            GDate recurrence_date = recurrenceGetDate(r);
            if (g_date_compare(start_date, &recurrence_date) != 0)
            {
                char start_date_str[128], recur_date_str[128];
                g_date_strftime(start_date_str, 127, "%x", start_date);
                g_date_strftime(recur_date_str, 127, "%x", &recurrence_date);
                g_critical("start_date [%s] != recurrence_date [%s]", start_date_str, recur_date_str);
            }

            gtk_notebook_set_current_page(gf->nb, PAGE_ONCE);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_ONCE);
        }
        break;
        case PERIOD_DAY:
        {
            guint multiplier;
            GtkWidget *spin_button;

            multiplier = recurrenceGetMultiplier(r);
            spin_button = glade_xml_get_widget(gf->gxml, "daily_spin");
            gtk_spin_button_set_value(GTK_SPIN_BUTTON(spin_button), multiplier);
            made_changes = TRUE;

            gtk_notebook_set_current_page(gf->nb, PAGE_DAILY);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_DAILY);
        }
        break;
        case PERIOD_WEEK:
        {
            _setup_weekly_recurrence(gf, r);
            gtk_notebook_set_current_page(gf->nb, PAGE_WEEKLY);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_WEEKLY);
        }
        break;
        case PERIOD_END_OF_MONTH:
        case PERIOD_MONTH:
        case PERIOD_YEAR:
        case PERIOD_LAST_WEEKDAY:
        case PERIOD_NTH_WEEKDAY:
        {
            guint multiplier;
            GtkWidget *multipler_spin, *day_of_month, *weekend_mode;

            multipler_spin = glade_xml_get_widget(gf->gxml, "monthly_spin");
            multiplier = recurrenceGetMultiplier(r);
            if (recurrenceGetPeriodType(r) == PERIOD_YEAR)
                multiplier *= 12;
            gtk_spin_button_set_value(GTK_SPIN_BUTTON(multipler_spin), multiplier);

            day_of_month = glade_xml_get_widget(gf->gxml, "monthly_day");
            gtk_combo_box_set_active(GTK_COMBO_BOX(day_of_month), _get_monthly_combobox_index(r));
            weekend_mode = glade_xml_get_widget(gf->gxml, "monthly_weekend");
            gtk_combo_box_set_active(GTK_COMBO_BOX(weekend_mode), recurrenceGetWeekendAdjust(r));

            gtk_notebook_set_current_page(gf->nb, PAGE_MONTHLY);
            gtk_combo_box_set_active(gf->freqComboBox, PAGE_MONTHLY);
        }
        break;
        default:
            g_error("unknown recurrence period type [%d]", recurrenceGetPeriodType(r));
            break;
        }
    }

maybe_signal:
    if (made_changes)
        g_signal_emit_by_name(gf, "changed");
}
Example #12
0
gchar*
recurrenceListToCompactString(GList *rs)
{
    GString *buf = g_string_sized_new(16);

    if (g_list_length(rs) == 0)
    {
        g_string_printf(buf, "%s", _("None"));
        goto rtn;
    }

    if (g_list_length(rs) > 1)
    {
        if (recurrenceListIsWeeklyMultiple(rs))
        {
            _weekly_list_to_compact_string(rs, buf);
        }
        else if (recurrenceListIsSemiMonthly(rs))
        {
            Recurrence *first, *second;
            first = (Recurrence*)g_list_nth_data(rs, 0);
            second = (Recurrence*)g_list_nth_data(rs, 1);
            if (recurrenceGetMultiplier(first) != recurrenceGetMultiplier(second))
            {
                g_warning("lying about non-equal semi-monthly recurrence multiplier: %d vs. %d",
                          recurrenceGetMultiplier(first), recurrenceGetMultiplier(second));
            }

            g_string_printf(buf, "%s", _("Semi-monthly"));
            g_string_append_printf(buf, " ");
            if (recurrenceGetMultiplier(first) > 1)
            {
                /* translators: %u is the recurrence multiplier number */
                g_string_append_printf(buf, _(" (x%u)"), recurrenceGetMultiplier(first));
            }
            g_string_append_printf(buf, ": ");
            _monthly_append_when(first, buf);
            g_string_append_printf(buf, ", ");
            _monthly_append_when(second, buf);
        }
        else
        {
            /* translators: %d is the number of Recurrences in the list. */
            g_string_printf(buf, _("Unknown, %d-size list."), g_list_length(rs));
        }
    }
    else
    {
        Recurrence *r = (Recurrence*)g_list_nth_data(rs, 0);
        guint multiplier = recurrenceGetMultiplier(r);

        switch (recurrenceGetPeriodType(r))
        {
        case PERIOD_ONCE:
        {
            g_string_printf(buf, "%s", _("Once"));
        }
        break;
        case PERIOD_DAY:
        {
            g_string_printf(buf, "%s", _("Daily"));
            if (multiplier > 1)
            {
                /* translators: %u is the recurrence multiplier. */
                g_string_append_printf(buf, _(" (x%u)"), multiplier);
            }
        }
        break;
        case PERIOD_WEEK:
        {
            _weekly_list_to_compact_string(rs, buf);
        }
        break;
        case PERIOD_MONTH:
        case PERIOD_END_OF_MONTH:
        case PERIOD_LAST_WEEKDAY:
        {
            g_string_printf(buf, "%s", _("Monthly"));
            if (multiplier > 1)
            {
                /* translators: %u is the recurrence multiplier. */
                g_string_append_printf(buf, _(" (x%u)"), multiplier);
            }
            g_string_append_printf(buf, ": ");
            _monthly_append_when(r, buf);
        }
        break;
        case PERIOD_NTH_WEEKDAY:
        {
            //g_warning("nth weekday not handled");
            //g_string_printf(buf, "@fixme: nth weekday not handled");
            g_string_printf(buf, "%s", _("Monthly"));
            if (multiplier > 1)
            {
                /* translators: %u is the recurrence multiplier. */
                g_string_append_printf(buf, _(" (x%u)"), multiplier);
            }
            g_string_append_printf(buf, ": ");
            _monthly_append_when(r, buf);
        }
        break;
        case PERIOD_YEAR:
        {
            g_string_printf(buf, "%s", _("Yearly"));
            if (multiplier > 1)
            {
                /* translators: %u is the recurrence multiplier. */
                g_string_append_printf(buf, _(" (x%u)"), multiplier);
            }
        }
        break;
        default:
            g_error("unknown Recurrence period %d", recurrenceGetPeriodType(r));
            break;
        }
    }

rtn:
    return g_string_free(buf, FALSE);
}