diff options
Diffstat (limited to 'src/day.c')
-rw-r--r-- | src/day.c | 274 |
1 files changed, 180 insertions, 94 deletions
@@ -110,7 +110,7 @@ day_cmp_start (struct day_item *a, struct day_item *b) else if (b->type <= EVNT) return 1; else - return (a->start < b->start ? -1 : (a->start == b->start ? 0 : 1)); + return a->start < b->start ? -1 : (a->start == b->start ? 0 : 1); } /* Add an appointment in the current day list. */ @@ -148,10 +148,10 @@ day_store_events (long date) llist_item_t *i; int e_nb = 0; - LLIST_FIND_FOREACH (&eventlist, date, event_inday, i) + LLIST_FIND_FOREACH_CONT (&eventlist, date, event_inday, i) { struct event *ev = LLIST_TS_GET_DATA (i); - (void)day_add_event (EVNT, ev->mesg, ev->note, ev->day, ev->id); + day_add_event (EVNT, ev->mesg, ev->note, ev->day, ev->id); e_nb++; } @@ -174,8 +174,7 @@ day_store_recur_events (long date) LLIST_FIND_FOREACH (&recur_elist, date, recur_event_inday, i) { struct recur_event *rev = LLIST_TS_GET_DATA (i); - (void)day_add_event (RECUR_EVNT, rev->mesg, rev->note, rev->day, - rev->id); + day_add_event (RECUR_EVNT, rev->mesg, rev->note, rev->day, rev->id); e_nb++; } @@ -196,11 +195,11 @@ day_store_apoints (long date) int a_nb = 0; LLIST_TS_LOCK (&alist_p); - LLIST_TS_FIND_FOREACH (&alist_p, date, apoint_inday, i) + LLIST_TS_FIND_FOREACH_CONT (&alist_p, date, apoint_inday, i) { struct apoint *apt = LLIST_TS_GET_DATA (i); - (void)day_add_apoint (APPT, apt->mesg, apt->note, apt->start, apt->dur, - apt->state, 0); + day_add_apoint (APPT, apt->mesg, apt->note, apt->start, apt->dur, + apt->state, 0); a_nb++; } LLIST_TS_UNLOCK (&alist_p); @@ -225,10 +224,13 @@ day_store_recur_apoints (long date) LLIST_TS_FIND_FOREACH (&recur_alist_p, date, recur_apoint_inday, i) { struct recur_apoint *rapt = LLIST_TS_GET_DATA (i); - int real_start = recur_apoint_inday (rapt, date); - (void)day_add_apoint (RECUR_APPT, rapt->mesg, rapt->note, real_start, - rapt->dur, rapt->state, a_nb); - a_nb++; + unsigned real_start; + if (recur_apoint_find_occurrence (rapt, date, &real_start)) + { + day_add_apoint (RECUR_APPT, rapt->mesg, rapt->note, real_start, + rapt->dur, rapt->state, a_nb); + a_nb++; + } } LLIST_TS_UNLOCK (&recur_alist_p); @@ -347,14 +349,15 @@ display_item_date (int incolor, struct apoint *i, int type, long date, * Print an item description in the corresponding panel window. */ static void -display_item (int incolor, char *msg, int recur, int note, int len, int y, +display_item (int incolor, char *msg, int recur, int note, int width, int y, int x) { WINDOW *win; int ch_recur, ch_note; - char buf[len]; + char buf[width * UTF8_MAXLEN]; + int i; - if (len <= 0) + if (width <= 0) return; win = apad.ptrwin; @@ -362,12 +365,20 @@ display_item (int incolor, char *msg, int recur, int note, int len, int y, ch_note = (note) ? '>' : ' '; if (incolor == 0) custom_apply_attr (win, ATTR_HIGHEST); - if (strlen (msg) < len) + if (utf8_strwidth (msg) < width) mvwprintw (win, y, x, " %c%c%s", ch_recur, ch_note, msg); else { - (void)strncpy (buf, msg, len - 1); - buf[len - 1] = '\0'; + for (i = 0; msg[i] && width > 0; i++) + { + if (!UTF8_ISCONT (msg[i])) + width -= utf8_width (&msg[i]); + buf[i] = msg[i]; + } + if (i) + buf[i - 1] = 0; + else + buf[0] = 0; mvwprintw (win, y, x, " %c%c%s...", ch_recur, ch_note, buf); } if (incolor == 0) @@ -466,28 +477,28 @@ day_check_if_item (struct date day) const long date = date2sec (day, 0, 0); if (LLIST_FIND_FIRST (&recur_elist, date, recur_event_inday)) - return (1); + return 1; LLIST_TS_LOCK (&recur_alist_p); if (LLIST_TS_FIND_FIRST (&recur_alist_p, date, recur_apoint_inday)) { LLIST_TS_UNLOCK (&recur_alist_p); - return (1); + return 1; } LLIST_TS_UNLOCK (&recur_alist_p); if (LLIST_FIND_FIRST (&eventlist, date, event_inday)) - return (1); + return 1; LLIST_TS_LOCK (&alist_p); if (LLIST_TS_FIND_FIRST (&alist_p, date, apoint_inday)) { LLIST_TS_UNLOCK (&alist_p); - return (1); + return 1; } LLIST_TS_UNLOCK (&alist_p); - return (0); + return 0; } static unsigned @@ -539,7 +550,7 @@ day_chk_busy_slices (struct date day, int slicesno, int *slices) LLIST_TS_UNLOCK (&recur_alist_p); LLIST_TS_LOCK (&alist_p); - LLIST_TS_FIND_FOREACH (&alist_p, date, apoint_inday, i) + LLIST_TS_FIND_FOREACH_CONT (&alist_p, date, apoint_inday, i) { struct apoint *apt = LLIST_TS_GET_DATA (i); long start = get_item_time (apt->start); @@ -558,44 +569,91 @@ day_chk_busy_slices (struct date day, int slicesno, int *slices) } /* Request the user to enter a new time. */ -static char * -day_edit_time (long time) +static int +day_edit_time (int time, unsigned *new_hour, unsigned *new_minute) +{ + char *timestr = date_sec2date_str (time, "%H:%M"); + char *msg_time = _("Enter the new time ([hh:mm]) : "); + char *enter_str = _("Press [Enter] to continue"); + char *fmt_msg = _("You entered an invalid time, should be [hh:mm]"); + + for (;;) + { + status_mesg (msg_time, ""); + if (updatestring (win[STA].p, ×tr, 0, 1) == GETSTRING_VALID) + { + if (parse_time (timestr, new_hour, new_minute) == 1) + { + mem_free (timestr); + return 1; + } + else + { + status_mesg (fmt_msg, enter_str); + wgetch (win[STA].p); + } + } + else + return 0; + } +} + +/* Request the user to enter a new time or duration. */ +static int +day_edit_duration (int start, int dur, unsigned *new_duration) { - char *timestr; - char *msg_time = _("Enter the new time ([hh:mm] or [h:mm]) : "); + char *timestr = date_sec2date_str (start + dur, "%H:%M"); + char *msg_time = _("Enter the new time ([hh:mm]) or duration ([+hh:mm]): "); char *enter_str = _("Press [Enter] to continue"); - char *fmt_msg = _("You entered an invalid time, should be [h:mm] or [hh:mm]"); + char *fmt_msg = _("You entered an invalid time, should be [hh:mm]"); + long newtime; + unsigned hr, mn; - while (1) + for (;;) { status_mesg (msg_time, ""); - timestr = date_sec2date_str (time, "%H:%M"); - updatestring (win[STA].p, ×tr, 0, 1); - if (check_time (timestr) != 1 || strlen (timestr) == 0) + if (updatestring (win[STA].p, ×tr, 0, 1) == GETSTRING_VALID) { - status_mesg (fmt_msg, enter_str); - (void)wgetch (win[STA].p); + if (*timestr == '+' && parse_duration (timestr + 1, + new_duration) == 1) + { + *new_duration *= MININSEC; + break; + } + else if (parse_time (timestr, &hr, &mn) == 1) + { + newtime = update_time_in_date (start + dur, hr, mn); + *new_duration = (newtime > start) ? newtime - start : + DAYINSEC + newtime - start; + break; + } + else + { + status_mesg (fmt_msg, enter_str); + wgetch (win[STA].p); + } } else - return (timestr); + return 0; } + + mem_free (timestr); + return 1; } +/* Request the user to enter a new end time or duration. */ static void update_start_time (long *start, long *dur) { long newtime; unsigned hr, mn; int valid_date; - char *timestr; char *msg_wrong_time = _("Invalid time: start time must be before end time!"); char *msg_enter = _("Press [Enter] to continue"); do { - timestr = day_edit_time (*start); - (void)sscanf (timestr, "%u:%u", &hr, &mn); - mem_free (timestr); + day_edit_time (*start, &hr, &mn); newtime = update_time_in_date (*start, hr, mn); if (newtime < *start + *dur) { @@ -606,7 +664,7 @@ update_start_time (long *start, long *dur) else { status_mesg (msg_wrong_time, msg_enter); - (void)wgetch (win[STA].p); + wgetch (win[STA].p); valid_date = 0; } } @@ -616,15 +674,10 @@ update_start_time (long *start, long *dur) static void update_duration (long *start, long *dur) { - long newtime; - unsigned hr, mn; - char *timestr; + unsigned newdur; - timestr = day_edit_time (*start + *dur); - (void)sscanf (timestr, "%u:%u", &hr, &mn); - mem_free (timestr); - newtime = update_time_in_date (*start, hr, mn); - *dur = (newtime > *start) ? newtime - *start : DAYINSEC + newtime - *start; + day_edit_duration (*start, *dur, &newdur); + *dur = newdur; } static void @@ -638,7 +691,7 @@ static void update_rept (struct rpt **rpt, const long start, struct conf *conf) { const int SINGLECHAR = 2; - int ch, cancel, newfreq, date_entered; + int ch, newfreq, date_entered; long newuntil; char outstr[BUFSIZ]; char *typstr, *freqstr, *timstr; @@ -656,17 +709,16 @@ update_rept (struct rpt **rpt, const long start, struct conf *conf) { status_mesg (msg_rpt_type, msg_rpt_ans); typstr = mem_calloc (SINGLECHAR, sizeof (char)); - (void)snprintf (typstr, SINGLECHAR, "%c", recur_def2char ((*rpt)->type)); - cancel = updatestring (win[STA].p, &typstr, 0, 1); - if (cancel) + snprintf (typstr, SINGLECHAR, "%c", recur_def2char ((*rpt)->type)); + if (updatestring (win[STA].p, &typstr, 0, 1) == GETSTRING_VALID) { + ch = toupper (*typstr); mem_free (typstr); - return; } else { - ch = toupper (*typstr); mem_free (typstr); + return; } } while ((ch != 'D') && (ch != 'W') && (ch != 'M') && (ch != 'Y')); @@ -675,35 +727,33 @@ update_rept (struct rpt **rpt, const long start, struct conf *conf) { status_mesg (_("Enter the new repetition frequence:"), ""); freqstr = mem_malloc (BUFSIZ); - (void)snprintf (freqstr, BUFSIZ, "%d", (*rpt)->freq); - cancel = updatestring (win[STA].p, &freqstr, 0, 1); - if (cancel) - { - mem_free (freqstr); - return; - } - else + snprintf (freqstr, BUFSIZ, "%d", (*rpt)->freq); + if (updatestring (win[STA].p, &freqstr, 0, 1) == GETSTRING_VALID) { newfreq = atoi (freqstr); mem_free (freqstr); if (newfreq == 0) { status_mesg (msg_wrong_freq, msg_enter); - (void)wgetch (win[STA].p); + wgetch (win[STA].p); } } + else + { + mem_free (freqstr); + return; + } } while (newfreq == 0); do { - (void)snprintf (outstr, BUFSIZ, "Enter the new ending date: [%s] or '0'", - DATEFMT_DESC (conf->input_datefmt)); + snprintf (outstr, BUFSIZ, "Enter the new ending date: [%s] or '0'", + DATEFMT_DESC (conf->input_datefmt)); status_mesg (_(outstr), ""); timstr = date_sec2date_str ((*rpt)->until, DATEFMT (conf->input_datefmt)); - cancel = updatestring (win[STA].p, &timstr, 0, 1); - if (cancel) + if (updatestring (win[STA].p, &timstr, 0, 1) != GETSTRING_VALID) { mem_free (timstr); return; @@ -732,7 +782,7 @@ update_rept (struct rpt **rpt, const long start, struct conf *conf) if (newuntil < start) { status_mesg (msg_wrong_time, msg_enter); - (void)wgetch (win[STA].p); + wgetch (win[STA].p); date_entered = 0; } else @@ -740,10 +790,10 @@ update_rept (struct rpt **rpt, const long start, struct conf *conf) } else { - (void)snprintf (outstr, BUFSIZ, msg_fmts, - DATEFMT_DESC (conf->input_datefmt)); + snprintf (outstr, BUFSIZ, msg_fmts, + DATEFMT_DESC (conf->input_datefmt)); status_mesg (msg_wrong_date, _(outstr)); - (void)wgetch (win[STA].p); + wgetch (win[STA].p); date_entered = 0; } } @@ -926,7 +976,7 @@ day_erase_item (long date, int item_number, enum eraseflg flag) } else { - return (0); + return 0; } if (p->type == RECUR_EVNT) { @@ -941,7 +991,7 @@ day_erase_item (long date, int item_number, enum eraseflg flag) if (flag == ERASE_FORCE_ONLY_NOTE) return 0; else - return (p->type); + return p->type; } /* Cut an item so it can be pasted somewhere else later. */ @@ -1033,7 +1083,7 @@ day_item_nb (long date, int day_num, int type) j = LLIST_TS_NEXT (j); } - return (nb_item[type - 1]); + return nb_item[type - 1]; } /* Attach a note to an appointment or event. */ @@ -1045,25 +1095,12 @@ day_edit_note (char *editor) struct apoint *a; struct recur_event *re; struct event *e; - char fullname[BUFSIZ]; - char *filename; long date; int item_num; item_num = apoint_hilt (); p = day_get_item (item_num); - if (p->note == NULL) - { - if ((filename = new_tempfile (path_notes, NOTESIZ)) == NULL) - return; - else - p->note = filename; - } - (void)snprintf (fullname, BUFSIZ, "%s%s", path_notes, p->note); - wins_launch_external (fullname, editor); - - if (io_file_is_empty (fullname) > 0) - erase_note (&p->note, ERASE_FORCE); + edit_note (&p->note, editor); date = calendar_get_slctd_day_sec (); switch (p->type) @@ -1091,12 +1128,61 @@ day_edit_note (char *editor) void day_view_note (char *pager) { + struct day_item *p = day_get_item (apoint_hilt ()); + view_note (p->note, pager); +} + +/* Pipe an appointment or event to an external program. */ +void +day_pipe_item (struct conf *conf) +{ + char cmd[BUFSIZ] = ""; + int pout; + int pid; + FILE *fpout; + int item_num; + long date; struct day_item *p; - char fullname[BUFSIZ]; + struct recur_apoint *ra; + struct apoint *a; + struct recur_event *re; + struct event *e; - p = day_get_item (apoint_hilt ()); - if (p->note == NULL) + status_mesg (_("Pipe item to external command:"), ""); + if (getstring (win[STA].p, cmd, BUFSIZ, 0, 1) != GETSTRING_VALID) return; - (void)snprintf (fullname, BUFSIZ, "%s%s", path_notes, p->note); - wins_launch_external (fullname, pager); + + wins_prepare_external (); + if ((pid = shell_exec (NULL, &pout, cmd))) + { + fpout = fdopen (pout, "w"); + + item_num = apoint_hilt (); + p = day_get_item (item_num); + date = calendar_get_slctd_day_sec (); + switch (p->type) + { + case RECUR_EVNT: + re = recur_get_event (date, day_item_nb (date, item_num, RECUR_EVNT)); + recur_event_write (re, fpout); + break; + case EVNT: + e = event_get (date, day_item_nb (date, item_num, EVNT)); + event_write (e, fpout); + break; + case RECUR_APPT: + ra = recur_get_apoint (date, day_item_nb (date, item_num, RECUR_APPT)); + recur_apoint_write (ra, fpout); + break; + case APPT: + a = apoint_get (date, day_item_nb (date, item_num, APPT)); + apoint_write (a, fpout); + break; + } + + fclose (fpout); + child_wait (NULL, &pout, pid); + press_any_key (); + } + wins_unprepare_external (); } |