summary | shortlog | log | commit | commitdiff | tree
raw | patch | inline | side by side (parent: fd85fef)
raw | patch | inline | side by side (parent: fd85fef)
author | Jonas Fonseca <fonseca@diku.dk> | |
Thu, 27 Apr 2006 09:21:05 +0000 (11:21 +0200) | ||
committer | Jonas Fonseca <fonseca@antimatter.localdomain> | |
Thu, 27 Apr 2006 09:21:05 +0000 (11:21 +0200) |
tig.c | patch | blob | history |
index 4e261a12b14aa07028cd033b136888dc937e7574..a0cbfe936c11fb3c29d7a5f00ebea5b179668e35 100644 (file)
--- a/tig.c
+++ b/tig.c
#define NDEBUG
#endif
+#include <assert.h>
+#include <ctype.h>
+#include <signal.h>
#include <stdarg.h>
-#include <stdlib.h>
#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
-#include <signal.h>
-#include <assert.h>
#include <curses.h>
#include <form.h>
#define REQ_DIFF (REQ_OFFSET + 0)
#define REQ_LOG (REQ_OFFSET + 1)
#define REQ_MAIN (REQ_OFFSET + 2)
+#define REQ_VIEWS (REQ_OFFSET + 3)
#define REQ_QUIT (REQ_OFFSET + 11)
#define REQ_VERSION (REQ_OFFSET + 12)
char *cmd;
char *id;
+
/* Rendering */
- int (*render)(struct view *, unsigned int);
+ int (*read)(struct view *, char *);
+ int (*draw)(struct view *, unsigned int);
+ size_t objsize; /* Size of objects in the line index */
+
WINDOW *win;
int height, width;
/* Buffering */
unsigned long lines; /* Total number of lines */
- char **line; /* Line index */
+ void **line; /* Line index */
/* Loading */
FILE *pipe;
};
-static int default_renderer(struct view *view, unsigned int lineno);
+struct commit {
+ char id[41];
+ char title[75];
+};
+
+static int pager_draw(struct view *view, unsigned int lineno);
+static int pager_read(struct view *view, char *line);
+
+static int main_draw(struct view *view, unsigned int lineno);
+static int main_read(struct view *view, char *line);
#define DIFF_CMD \
"git log --stat -n1 %s ; echo; " \
static WINDOW *status_win;
#define SIZEOF_ID 1024
+#define SIZEOF_VIEWS (REQ_VIEWS - REQ_OFFSET)
char head_id[SIZEOF_ID] = "HEAD";
char commit_id[SIZEOF_ID] = "HEAD";
static unsigned int current_view;
static unsigned int nloading;
+static struct view views[];
+static struct view *display[];
+
static struct view views[] = {
- { "diff", DIFF_CMD, commit_id, default_renderer },
- { "log", LOG_CMD, head_id, default_renderer },
- { "main", MAIN_CMD, head_id, default_renderer },
+ { "diff", DIFF_CMD, commit_id, pager_read, pager_draw, sizeof(char) },
+ { "log", LOG_CMD, head_id, pager_read, pager_draw, sizeof(struct commit) },
+ { "main", MAIN_CMD, head_id, main_read, main_draw },
};
static struct view *display[ARRAY_SIZE(views)];
+
#define foreach_view(view, i) \
for (i = 0; i < sizeof(display) && (view = display[i]); i++)
wmove(view->win, 0, 0);
for (lineno = 0; lineno < view->height; lineno++) {
- if (!view->render(view, lineno))
+ if (!view->draw(view, lineno))
break;
}
assert(lines);
{
- int from = lines > 0 ? view->height - lines : 0;
- int to = from + (lines > 0 ? lines : -lines);
+ int line = lines > 0 ? view->height - lines : 0;
+ int end = line + (lines > 0 ? lines : -lines);
wscrl(view->win, lines);
- for (; from < to; from++) {
- if (!view->render(view, from))
+ for (; line < end; line++) {
+ if (!view->draw(view, line))
break;
}
}
/* Move current line into the view. */
if (view->lineno < view->offset) {
view->lineno = view->offset;
- view->render(view, 0);
+ view->draw(view, 0);
} else if (view->lineno >= view->offset + view->height) {
view->lineno = view->offset + view->height - 1;
- view->render(view, view->lineno - view->offset);
+ view->draw(view, view->lineno - view->offset);
}
assert(view->offset <= view->lineno && view->lineno <= view->lines);
}
view->lineno += steps;
- view->render(view, view->lineno - steps - view->offset);
+ view->draw(view, view->lineno - steps - view->offset);
if (view->lineno < view->offset ||
view->lineno >= view->offset + view->height) {
return;
}
- view->render(view, view->lineno - view->offset);
+ view->draw(view, view->lineno - view->offset);
redrawwin(view->win);
wrefresh(view->win);
{
char buffer[BUFSIZ];
char *line;
- char **tmp;
+ void **tmp;
int redraw;
int lines = view->height;
return TRUE;
/* Only redraw after the first reading session. */
- redraw = !view->line;
+ /* FIXME: ... and possibly more. */
+ redraw = view->height > view->lines;
tmp = realloc(view->line, sizeof(*view->line) * (view->lines + lines));
if (!tmp)
if (linelen)
line[linelen - 1] = 0;
- view->line[view->lines] = strdup(line);
- if (!view->line[view->lines])
+ if (!view->read(view, line))
goto alloc_error;
- view->lines++;
if (lines-- == 1)
break;
};
static int
-default_renderer(struct view *view, unsigned int lineno)
+pager_draw(struct view *view, unsigned int lineno)
{
char *line;
int linelen;
return TRUE;
}
+static int
+pager_read(struct view *view, char *line)
+{
+ view->line[view->lines] = strdup(line);
+ if (!view->line[view->lines])
+ return FALSE;
+
+ view->lines++;
+ return TRUE;
+}
+
+static int
+main_draw(struct view *view, unsigned int lineno)
+{
+ struct commit *commit;
+ int attr = A_NORMAL;
+
+ if (view->offset + lineno >= view->lines)
+ return FALSE;
+
+ commit = view->line[view->offset + lineno];
+ if (!commit) return FALSE;
+
+ attr = attrs[0].attr;
+
+ if (view->offset + lineno == view->lineno) {
+ strncpy(commit_id, commit->id, SIZEOF_ID);
+ attr = COLOR_PAIR(COLOR_CURSOR) | A_BOLD;
+ }
+
+ mvwaddch(view->win, lineno, 0, ACS_LTEE);
+ wattrset(view->win, attr);
+ mvwaddstr(view->win, lineno, 2, commit->title);
+ wattrset(view->win, A_NORMAL);
+
+ return TRUE;
+}
+
+static int
+main_read(struct view *view, char *line)
+{
+ int linelen = strlen(line);
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(attrs); i++) {
+ if (linelen < attrs[i].linelen
+ || strncmp(attrs[i].line, line, attrs[i].linelen))
+ continue;
+ break;
+ }
+
+ if (i == 0) {
+ struct commit *commit;
+
+ commit = calloc(1, sizeof(struct commit));
+ if (!commit)
+ return FALSE;
+
+ view->line[view->lines++] = commit;
+
+ strncpy(commit->id, line + 7, 41);
+
+ } else {
+ struct commit *commit = view->line[view->lines - 1];
+
+ if (!commit->title[0] &&
+ linelen > 5 &&
+ !strncmp(line, " ", 4) &&
+ !isspace(line[5]))
+ strncpy(commit->title, line + 4, sizeof(commit->title));
+ }
+
+ return TRUE;
+}
+
+
/*
* Main
*/