Compare commits
11 Commits
914ce0d7ad
...
main
Author | SHA1 | Date | |
---|---|---|---|
7fb5978b34 | |||
790e60d23f | |||
b2fcc087af | |||
9d151c4dad | |||
b24d97213e | |||
97af579397
|
|||
57e8c4a499 | |||
d779e6f3a0 | |||
02b305cc8b | |||
6b7a1c459b | |||
96a18b8cdb |
4
.gitignore
vendored
4
.gitignore
vendored
@@ -1 +1,5 @@
|
|||||||
bbs
|
bbs
|
||||||
|
build/
|
||||||
|
|
||||||
|
# Machine generated files:
|
||||||
|
src/version.c
|
||||||
|
17
Makefile
17
Makefile
@@ -3,7 +3,10 @@
|
|||||||
# Makefile for Amber's BBS Interface
|
# Makefile for Amber's BBS Interface
|
||||||
# Buildsys by Gale Faraday
|
# Buildsys by Gale Faraday
|
||||||
|
|
||||||
.PHONY: all clean run
|
# `generate` must be called before `all` to build version information and other
|
||||||
|
# machine generated files.
|
||||||
|
|
||||||
|
.PHONY: all clean run generate
|
||||||
.SUFFIXES:
|
.SUFFIXES:
|
||||||
|
|
||||||
.DEFAULT_GOAL := all
|
.DEFAULT_GOAL := all
|
||||||
@@ -11,14 +14,15 @@
|
|||||||
TARGET := $(shell basename $(CURDIR))
|
TARGET := $(shell basename $(CURDIR))
|
||||||
SOURCES := src/
|
SOURCES := src/
|
||||||
BUILD := build/
|
BUILD := build/
|
||||||
|
GENABLES := $(SOURCES)version.c
|
||||||
OBJS := $(patsubst $(SOURCES)%.c,$(BUILD)%.o,$(wildcard $(SOURCES)*.c))
|
OBJS := $(patsubst $(SOURCES)%.c,$(BUILD)%.o,$(wildcard $(SOURCES)*.c))
|
||||||
EXECUTABLE := $(TARGET)
|
EXECUTABLE := $(TARGET)
|
||||||
|
|
||||||
|
|
||||||
CC := gcc
|
CC := gcc
|
||||||
LD := gcc
|
LD := gcc
|
||||||
CFLAGS := -std=c99 -pedantic -Wall -Wextra -O2 -ggdb
|
CFLAGS := -std=c99 -pedantic -Wall -Wextra -Wno-unused-parameter -O2 -ggdb
|
||||||
LDFLAGS := $(CFLAGS) -lncursesw
|
LDFLAGS := $(CFLAGS) -lncurses
|
||||||
|
|
||||||
all: $(EXECUTABLE)
|
all: $(EXECUTABLE)
|
||||||
|
|
||||||
@@ -27,7 +31,12 @@ run: $(EXECUTABLE)
|
|||||||
|
|
||||||
.IGNORE: clean
|
.IGNORE: clean
|
||||||
clean:
|
clean:
|
||||||
@rm -rvf $(BUILD) $(EXECUTABLE)
|
@rm -rvf $(BUILD) $(EXECUTABLE) $(GENABLES)
|
||||||
|
|
||||||
|
generate: $(GENABLES)
|
||||||
|
|
||||||
|
$(GENABLES): genver.sh
|
||||||
|
./genver.sh
|
||||||
|
|
||||||
$(EXECUTABLE): $(OBJS)
|
$(EXECUTABLE): $(OBJS)
|
||||||
$(LD) $(LDFLAGS) -o $@ $^
|
$(LD) $(LDFLAGS) -o $@ $^
|
||||||
|
@@ -4,13 +4,11 @@ This is a simple bbs program written in c. The way it is meant to work is that a
|
|||||||
|
|
||||||
## Building
|
## Building
|
||||||
|
|
||||||
The only dependency is `ncurses`. The makefile asks for `-lncursesw` but unicode is not yet used, so `-lncurses` should be fine. `ncurses` is almost guaranteed preinstalled on your system.
|
`bbs` depends only upon `ncurses`.
|
||||||
|
|
||||||
The program is standardized on c99. It should run fine on c89, but there will be warnings. You'll have to edit the makefile to request c89 from `gcc`.
|
Run `make generate` to generate `version.c`, then `make` to build. Build files will be in `build/` and the executable `bbs` will be in the root of the repo.
|
||||||
|
|
||||||
To build, run `make`. It will drop an executable named `bbs` in the current folder.
|
`make run` will build and run the program, and `make clean` will clean up the `build/` directory.
|
||||||
|
|
||||||
The makefile has the additional command `make run`, which just launches the program after compilation.
|
|
||||||
|
|
||||||
## License
|
## License
|
||||||
|
|
||||||
|
21
genver.sh
Executable file
21
genver.sh
Executable file
@@ -0,0 +1,21 @@
|
|||||||
|
#!/usr/bin/env bash
|
||||||
|
|
||||||
|
# Script to generate version information file
|
||||||
|
|
||||||
|
# Current git hash
|
||||||
|
HASH="$(git describe --always --dirty)"
|
||||||
|
|
||||||
|
# Current git tag
|
||||||
|
TAG="$(git describe --always --dirty --tags)"
|
||||||
|
|
||||||
|
# Output filename
|
||||||
|
OUTFILE='src/version.c'
|
||||||
|
|
||||||
|
sed -e "s/<HASH>/$HASH/g" -e "s/<TAG>/$TAG/g" <<EOF > "$OUTFILE"
|
||||||
|
/* Build version information. This file generated by genver.sh */
|
||||||
|
|
||||||
|
const char GIT_HASH[] = "<HASH>";
|
||||||
|
const char GIT_TAG[] = "<TAG>";
|
||||||
|
const char CC_VERSION[] = __VERSION__;
|
||||||
|
const char BUILD_DATE[] = __DATE__;
|
||||||
|
EOF
|
@@ -3,21 +3,47 @@
|
|||||||
#include <curses.h>
|
#include <curses.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
#include <locale.h>
|
#include <locale.h>
|
||||||
|
|
||||||
#include "globals.h"
|
#include "globals.h"
|
||||||
#include "screens.h"
|
#include "screens.h"
|
||||||
|
|
||||||
const unsigned int GETCH_TIMEOUT = 10; /* in ms */
|
|
||||||
const char* LOCALE = "en_US.UTF-8"; /* enable unicode support, set to "ANSI_X3.4-1968" for ascii */
|
|
||||||
|
|
||||||
char error_message[MAX_ERROR_MESSAGE_SIZE];
|
char error_message[MAX_ERROR_MESSAGE_SIZE];
|
||||||
|
|
||||||
|
unsigned int terminal_width;
|
||||||
|
unsigned int terminal_height;
|
||||||
|
unsigned int old_terminal_width = 0;
|
||||||
|
unsigned int old_terminal_height = 0;
|
||||||
|
|
||||||
|
enum Status status = STATUS_NEED_REFRESH; /* refresh screens[active_screen].window on first loop */
|
||||||
|
char input = ' ';
|
||||||
|
|
||||||
|
unsigned int screen_before_error = HOME;
|
||||||
|
enum ActiveScreen active_screen = HOME;
|
||||||
|
|
||||||
static void draw_screen (struct Screen *screen, char *input) {
|
static void draw_screen (struct Screen *screen, char *input) {
|
||||||
screen->draw_screen(screen, input);
|
screen->draw_screen(screen, input);
|
||||||
box(screen->win, 0, 0);
|
wattron(screen->win, A_STANDOUT);
|
||||||
/* wattron(screen->win, A_STANDOUT); */
|
|
||||||
mvwprintw(screen->win, 0, 1, " %s ", screen->name);
|
mvwprintw(screen->win, 0, 1, " %s ", screen->name);
|
||||||
/* wattroff(screen->win, A_STANDOUT); */
|
wattroff(screen->win, A_STANDOUT);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void resize_active_screen() {
|
||||||
|
wclear(screens[active_screen].win);
|
||||||
|
wresize(screens[active_screen].win, terminal_height, terminal_width);
|
||||||
|
mvwin(screens[active_screen].win, 0, 0);
|
||||||
|
wrefresh(screens[active_screen].win);
|
||||||
|
old_terminal_width = terminal_width;
|
||||||
|
old_terminal_height = terminal_height;
|
||||||
|
|
||||||
|
if (terminal_width < 80 || terminal_height < 24) {
|
||||||
|
if (active_screen != ERROR) {
|
||||||
|
strcpy(error_message, "This program expects at least 80 rows by 24 columns.");
|
||||||
|
screen_before_error = active_screen;
|
||||||
|
};
|
||||||
|
active_screen = ERROR;
|
||||||
|
} else if (active_screen != screen_before_error) {
|
||||||
|
active_screen = screen_before_error;
|
||||||
|
};
|
||||||
|
status = STATUS_NEED_REFRESH;
|
||||||
}
|
}
|
||||||
|
|
||||||
int main() {
|
int main() {
|
||||||
@@ -25,24 +51,15 @@ int main() {
|
|||||||
initscr(); /* start ncurses */
|
initscr(); /* start ncurses */
|
||||||
noecho(); /* hide keyboard input */
|
noecho(); /* hide keyboard input */
|
||||||
curs_set(0); /* disable cursor */
|
curs_set(0); /* disable cursor */
|
||||||
|
keypad(stdscr, TRUE); /* enable extra keys */
|
||||||
timeout(GETCH_TIMEOUT); /* set timeout for getch() */
|
timeout(GETCH_TIMEOUT); /* set timeout for getch() */
|
||||||
setlocale(LC_CTYPE, LOCALE); /* set locale, UTF8 support is enabled here */
|
setlocale(LC_CTYPE, ""); /* set locale to current locale */
|
||||||
|
|
||||||
unsigned int terminal_width;
|
|
||||||
unsigned int terminal_height;
|
|
||||||
unsigned int old_terminal_width = 0;
|
|
||||||
unsigned int old_terminal_height = 0;
|
|
||||||
|
|
||||||
enum Status status = STATUS_NEED_REFRESH; /* refresh screens[active_screen].window on first loop */
|
|
||||||
char input = ' ';
|
|
||||||
|
|
||||||
strcpy(error_message, "");
|
strcpy(error_message, "");
|
||||||
|
|
||||||
getmaxyx(stdscr, terminal_height, terminal_width);
|
getmaxyx(stdscr, terminal_height, terminal_width);
|
||||||
|
|
||||||
unsigned int screen_before_error = HOME;
|
|
||||||
|
|
||||||
enum ActiveScreen active_screen = HOME;
|
|
||||||
|
|
||||||
/* could be it's own init func within the screen's file. */
|
/* could be it's own init func within the screen's file. */
|
||||||
screens[HOME].win = newwin(terminal_height, terminal_width, 0, 0);
|
screens[HOME].win = newwin(terminal_height, terminal_width, 0, 0);
|
||||||
@@ -58,27 +75,10 @@ int main() {
|
|||||||
status = STATUS_NEED_REFRESH;
|
status = STATUS_NEED_REFRESH;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
getmaxyx(stdscr, terminal_height, terminal_width);
|
getmaxyx(stdscr, terminal_height, terminal_width);
|
||||||
|
|
||||||
/* resize active screen's window */
|
|
||||||
if (old_terminal_width != terminal_width || old_terminal_height != terminal_height) {
|
if (old_terminal_width != terminal_width || old_terminal_height != terminal_height) {
|
||||||
wclear(screens[active_screen].win);
|
resize_active_screen();
|
||||||
wresize(screens[active_screen].win, terminal_height, terminal_width);
|
|
||||||
mvwin(screens[active_screen].win, 0, 0);
|
|
||||||
wrefresh(screens[active_screen].win);
|
|
||||||
old_terminal_width = terminal_width;
|
|
||||||
old_terminal_height = terminal_height;
|
|
||||||
|
|
||||||
if (terminal_width < 80 || terminal_height < 24) {
|
|
||||||
if (active_screen != ERROR) {
|
|
||||||
strcpy(error_message, "This program expects at least 80 rows by 24 columns.");
|
|
||||||
screen_before_error = active_screen;
|
|
||||||
};
|
|
||||||
active_screen = ERROR;
|
|
||||||
} else if (active_screen != screen_before_error) {
|
|
||||||
active_screen = screen_before_error;
|
|
||||||
};
|
|
||||||
status = STATUS_NEED_REFRESH;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
/* refresh active screen's window */
|
/* refresh active screen's window */
|
||||||
@@ -91,7 +91,8 @@ int main() {
|
|||||||
};
|
};
|
||||||
|
|
||||||
/* clean up */
|
/* clean up */
|
||||||
delwin(screens[active_screen].win); /* TODO: delete all windows in screens[] */
|
delwin(screens[0].win); /* could be in a destructor function in the screen's file */
|
||||||
|
delwin(screens[1].win);
|
||||||
nocbreak();
|
nocbreak();
|
||||||
endwin(); /* ends curses mode */
|
endwin(); /* ends curses mode */
|
||||||
curs_set(1);
|
curs_set(1);
|
@@ -3,6 +3,8 @@
|
|||||||
#include <curses.h>
|
#include <curses.h>
|
||||||
#include "screens.h"
|
#include "screens.h"
|
||||||
|
|
||||||
void draw_error(struct Screen *screen, __attribute__((unused)) char *input) {
|
/* char *input is unused */
|
||||||
|
void draw_error(struct Screen *screen, char *input) {
|
||||||
|
box(screen->win, 0, 0);
|
||||||
mvwprintw(screen->win, 1, 2, "%s", error_message);
|
mvwprintw(screen->win, 1, 2, "%s", error_message);
|
||||||
}
|
}
|
@@ -1,5 +1,6 @@
|
|||||||
/* SPDX-License-Identifier: MIT */
|
/* SPDX-License-Identifier: MIT */
|
||||||
|
|
||||||
|
#define GETCH_TIMEOUT 10 /* in ms */
|
||||||
#define MAX_SCREEN_NAME_SIZE 20 /* size of the screen name array */
|
#define MAX_SCREEN_NAME_SIZE 20 /* size of the screen name array */
|
||||||
#define MAX_ERROR_MESSAGE_SIZE 60 /* size of error_message array */
|
#define MAX_ERROR_MESSAGE_SIZE 60 /* size of error_message array */
|
||||||
|
|
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
#include <curses.h>
|
#include <curses.h>
|
||||||
#include "screens.h"
|
#include "screens.h"
|
||||||
|
#include "version.h"
|
||||||
|
|
||||||
void draw_home(struct Screen *screen, char *input) {
|
void draw_home(struct Screen *screen, char *input) {
|
||||||
static char* banner = ""
|
static char* banner = ""
|
||||||
@@ -13,8 +14,13 @@ void draw_home(struct Screen *screen, char *input) {
|
|||||||
" \\__,_|_| |_| |_|_.__/ \\___|_| |___/ .__/|_|\\__,_|\\___\\___(_)_| |_|\\___|\\__|\n"
|
" \\__,_|_| |_| |_|_.__/ \\___|_| |___/ .__/|_|\\__,_|\\___\\___(_)_| |_|\\___|\\__|\n"
|
||||||
" | | \n"
|
" | | \n"
|
||||||
" |_| \n";
|
" |_| \n";
|
||||||
|
|
||||||
mvwprintw(screen->win, 1, 2, "Thank you for visiting:");
|
mvwprintw(screen->win, 1, 2, "Thank you for visiting:");
|
||||||
mvwprintw(screen->win, 2, 1, "%s", banner);
|
mvwprintw(screen->win, 2, 1, "%s", banner);
|
||||||
mvwprintw(screen->win, 10, 1, "Your current input is: %s", input);
|
mvwprintw(screen->win, 10, 1, "Your current input is: %s", input);
|
||||||
|
wclrtoeol(screen->win); /* clear rest of line to prevent longer inputs from sticking around */
|
||||||
|
mvwprintw(screen->win, 11, 1, "Git hash: %s", GIT_HASH);
|
||||||
|
mvwprintw(screen->win, 12, 1, "Git tag: %s", GIT_TAG);
|
||||||
|
mvwprintw(screen->win, 13, 1, "CC version: %s", CC_VERSION);
|
||||||
|
mvwprintw(screen->win, 14, 1, "Build date: %s", BUILD_DATE);
|
||||||
|
box(screen->win, 0, 0);
|
||||||
}
|
}
|
6
src/version.h
Normal file
6
src/version.h
Normal file
@@ -0,0 +1,6 @@
|
|||||||
|
/* Header for version information constants */
|
||||||
|
|
||||||
|
extern const char GIT_HASH[];
|
||||||
|
extern const char GIT_TAG[];
|
||||||
|
extern const char CC_VERSION[];
|
||||||
|
extern const char BUILD_DATE[];
|
Reference in New Issue
Block a user