2 * Copyright notice from original mutt:
3 * Copyright (C) ????-2004 Justin Hibbits <jrh29@po.cwru.edu>
4 * Copyright (C) 2004 Thomer M. Gil <mutt@thomer.com>
6 * Parts were written/modified by:
7 * Rocco Rutte <pdmef@cs.tu-berlin.de>
8 * Nico Golde <nico@ngolde.de>
10 * This file is part of mutt-ng, see http://www.muttng.org/.
11 * It's licensed under the GNU General Public License,
12 * please see the file GPL in the top level source directory.
15 #include <lib-ui/lib-ui.h>
16 #include <lib-ui/menu.h>
25 static int CurBuffy = 0;
27 /* computes first entry to be shown */
28 static int calc_boundaries(void)
30 if (CurBuffy < 0 || CurBuffy >= Incoming.len)
33 if (option(OPTSIDEBARNEWMAILONLY)) {
36 for (int i = 0; i < CurBuffy; i++) {
37 n += Incoming.arr[i]->new > 0;
44 for (int i = CurBuffy - 1; i >= 0; i--) {
45 if (Incoming.arr[i]->new > 0 && --n <= 0) {
52 return CurBuffy - (CurBuffy % (LINES - 3));
56 static void shortened_hierarchy(char *dst, char *hbox, int maxlen)
58 int dots = 0, last_dot = 0, len = m_strlen(hbox);
60 if (m_strisempty(SidebarBoundary)) {
61 memcpy(dst, hbox, MIN(len, maxlen));
65 for (int i = 0; i < len; ++i) {
66 if (strchr(SidebarBoundary, hbox[i])) {
73 memcpy(dst, hbox, MIN(len, maxlen));
78 for (int i = 1, j = 1; i < len && j < maxlen - 1; ++i) {
79 if (!strchr(SidebarBoundary, hbox[i]))
82 if (len - i <= maxlen - j) {
83 memcpy(dst, hbox + i, len - i);
88 memcpy(dst, hbox + i, maxlen - j);
93 dst[j++] = hbox[i + 1];
98 sidebar_number_format(char* dest, ssize_t destlen,
99 char op, const char* src, const char* fmt,
100 const char* ifstr, const char* elstr,
101 anytype data, format_flag flags)
104 BUFFY* b = Incoming.arr[data.i];
105 int opt = flags & M_FORMAT_OPTIONAL;
106 int c = Context && !m_strcmp(Context->path, b->path);
112 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
113 snprintf (dest, destlen, tmp, c ? Context->deleted : 0);
114 } else if ((c && Context->deleted == 0) || !c)
119 case 'f': /* for compatibility */
121 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
122 snprintf (dest, destlen, tmp, c ? Context->flagged : b->msg_flagged);
123 } else if ((c && Context->flagged == 0) || (!c && b->msg_flagged == 0))
127 case 'c': /* for compatibility */
130 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
131 snprintf (dest, destlen, tmp, c ? Context->msgcount : b->msgcount);
132 } else if ((c && Context->msgcount == 0) || (!c && b->msgcount == 0))
135 /* total shown, i.e. not hidden by limit */
138 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
139 snprintf (dest, destlen, tmp, c ? Context->vcount : 0);
140 } else if ((c && Context->vcount == 0) || !c)
146 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
147 snprintf (dest, destlen, tmp, c ? Context->new : b->new);
148 } else if ((c && Context->new == 0) || (!c && b->new == 0))
154 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
155 snprintf (dest, destlen, tmp, c ? Context->unread : b->msg_unread);
156 } else if ((c && Context->unread == 0) || (!c && b->msg_unread == 0))
162 snprintf (tmp, sizeof (tmp), "%%%sd", fmt);
163 snprintf (dest, destlen, tmp, c ? Context->tagged : 0);
164 } else if ((c && Context->tagged == 0) || !c)
169 if (flags & M_FORMAT_OPTIONAL)
170 m_strformat(dest, destlen, 0, opt ? ifstr : elstr,
171 sidebar_number_format, data, flags);
177 * 0 item was not printed ('cause of $sidebar_newmail_only)
180 static int make_sidebar_entry(WINDOW *sw, char *sbox, int idx, ssize_t len)
183 char no[STRING], entry[STRING];
184 int l_m = m_strlen(Maildir);
186 if (option(OPTSIDEBARNEWMAILONLY) && sbox && Context && Context->path
187 && m_strcmp(Context->path, sbox) && Incoming.arr[idx]->new == 0
191 m_strformat(no, sizeof(no), len, SidebarNumberFormat,
192 sidebar_number_format, idx, 0);
193 lencnt = m_strlen(no);
195 if (l_m > 0 && m_strncmp(sbox, Maildir, l_m) == 0 && m_strlen(sbox) > l_m)
198 if (Maildir[strlen(Maildir) - 1] != '/') {
202 sbox = basename(sbox);
205 snprintf(entry, sizeof(entry), "%*s", (int)len, no);
206 if (option(OPTSHORTENHIERARCHY) && m_strlen(sbox) > len - lencnt - 1) {
207 shortened_hierarchy(entry, sbox, len - lencnt - 1);
209 memcpy(entry, sbox, MIN(len - lencnt - 1, m_strlen(sbox)));
211 waddnstr(sw, entry, len);
216 /* returns folder name of currently
217 * selected folder for <sidebar-open>
219 const char *sidebar_get_current(void)
221 if (0 <= CurBuffy && CurBuffy < Incoming.len)
222 return Incoming.arr[CurBuffy]->path;
226 /* internally sets item to buf */
227 void sidebar_set_current(const char* buf)
229 int i = buffy_lookup(buf);
235 /* fix counters for a context
236 * FIXME since ctx must not be of our business, move it elsewhere
238 void sidebar_set_buffystats(CONTEXT *curContext)
243 if (!curContext || (i = buffy_lookup(curContext->path)) < 0)
245 tmp = Incoming.arr[i];
246 tmp->new = curContext->new;
247 tmp->msg_unread = curContext->unread;
248 tmp->msgcount = curContext->msgcount;
249 tmp->msg_flagged = curContext->flagged;
252 int sidebar_draw(void)
254 static short prev_show_value = -1;
258 /* initialize first time */
259 if (prev_show_value != option(OPTMBOXPANE)) {
260 if ((prev_show_value = option(OPTMBOXPANE))) {
261 /* after toggle: force recounting of all mail */
266 sw = ui_layout_sidebar_w();
271 SETCOLOR(sw, MT_COLOR_SIDEBAR);
272 mvwhline(sw, 0, 0, ACS_HLINE, x - 1);
273 mvwaddch(sw, 0, x - 1, ACS_TTEE);
276 for (int i = calc_boundaries(); i < Incoming.len && line < y - 1; i++) {
277 BUFFY *tmp = Incoming.arr[i];
280 SETCOLOR(sw, MT_COLOR_INDICATOR);
281 else if (tmp->new > 0)
282 SETCOLOR(sw, MT_COLOR_NEW);
283 else if (tmp->msg_flagged > 0)
284 SETCOLOR(sw, MT_COLOR_FLAGGED);
286 SETCOLOR(sw, MT_COLOR_NORMAL);
288 if (make_sidebar_entry(sw, tmp->path, i, x - 1)) {
289 SETCOLOR(sw, MT_COLOR_SIDEBAR);
290 waddch(sw, ACS_VLINE);
295 while (line < y - 1) {
296 SETCOLOR(sw, MT_COLOR_NORMAL);
297 whline(sw, ' ', x - 1);
298 SETCOLOR(sw, MT_COLOR_SIDEBAR);
299 mvwaddch(sw, line++, x - 1, ACS_VLINE);
302 SETCOLOR(sw, MT_COLOR_SIDEBAR);
303 mvwhline(sw, y - 1, 0, ACS_HLINE, x - 1);
304 mvwaddch(sw, y - 1, x - 1, ACS_BTEE);
308 void sidebar_scroll(int op)
314 case OP_SIDEBAR_NEXT:
315 if (!option(OPTSIDEBARNEWMAILONLY)) {
316 CurBuffy = (CurBuffy + 1) % Incoming.len;
320 case OP_SIDEBAR_NEXT_NEW:
321 for (int i = 1; i < Incoming.len; i++) {
322 if (Incoming.arr[(CurBuffy + i) % Incoming.len]->new > 0) {
323 CurBuffy = (CurBuffy + i) % Incoming.len;
329 case OP_SIDEBAR_PREV:
330 if (!option(OPTSIDEBARNEWMAILONLY)) {
332 CurBuffy = Incoming.len;
338 case OP_SIDEBAR_PREV_NEW:
339 for (int i = Incoming.len - 1; i > 0; i--) {
340 if (Incoming.arr[(CurBuffy + i) % Incoming.len]->new > 0) {
341 CurBuffy = (CurBuffy + i) % Incoming.len;
347 case OP_SIDEBAR_SCROLL_UP:
348 CurBuffy -= LINES - 3;
352 case OP_SIDEBAR_SCROLL_DOWN:
353 CurBuffy += LINES - 3;
354 if (CurBuffy >= Incoming.len)
355 CurBuffy = Incoming.len - 1;