Ok, I created a c program that displays a colour status bar. The program take two or three arguments.
First argument is the number of columns to use for the display.
Second argument is the file to watch. It should only contain the percentage to be displayed…
The third, and optional argument is the time delay between updating, in seconds. The default is 60.
Some things need to be said…
First, this is a text based status bar. The number of columns can be increased to a ridiculous amount. The idea is that you can change the xterm display font the larger or smaller, and the number of columns to get the proper fit for what you want.
Here it is:
#include <errno.h>
#include <libgen.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <termios.h>
#include <unistd.h>
// Declare defines.
#define BUFFER_SIZE 10
#define CLEAR_SCREEN puts("\e[2J\e[?25l")
#define COLOUR_BLUE "\x1b[48;5;19m"
#define COLOUR_GREEN "\x1b[48;5;34m"
#define COLOUR_GREY "\x1b[48;5;236m"
#define COLOUR_RED "\x1b[48;5;160m"
#define COLOUR_YELLOW "\x1b[48;5;184m"
#define PROGRAM_NAME_SIZE 50
#define RESET "\e[0m"
// Declare global variables.
char program_name[PROGRAM_NAME_SIZE + 1] = {0};
// Declare function prototypes.
void display_colour_bar (int columns, char *file, int seconds);
int main (int argc, char *argv[])
{
// Declare variables.
FILE *fp = NULL;
// Get program name for error reporting.
strcpy(program_name, basename(argv[0]));
// Check arguments. Must be at least 2 arguments with an optional 3rd.
if(argc != 3 && argc != 4)
{
fprintf(stderr, "Usage: %s NUMBER_OF_COLUMNS FILE_TO_WATCH [SECONDS_BETWEEN_UPDATE]\n", program_name);
exit(EXIT_FAILURE);
}
// #1) Must be greater than 0.
if(atoi(argv[1]) < 1)
{
fprintf(stderr, "Usage: %s " COLOUR_RED "NUMBER_OF_COLUMNS" RESET " FILE_TO_WATCH [SECONDS_BETWEEN_UPDATE]\n", program_name);
exit(EXIT_FAILURE);
}
// #2) Must be positive, including 0, but not exceeding 100.
// #2) File to monitor. Must be a readable file.
// if((argv[2][0] != '0' && atoi(argv[2]) < 1) || atoi(argv[2]) > 100)
if((fp = fopen(argv[2], "rb")) == NULL)
{
// fprintf(stderr, "Usage: %s NUMBER_OF_COLUMNS " COLOUR_RED "PERCENT_INTEGER" RESET "[SECONDS_BETWEEN_UPDATE]\n", program_name);
fprintf(stderr, "Usage: %s NUMBER_OF_COLUMNS " COLOUR_RED "FILE_TO_WATCH" RESET "[SECONDS_BETWEEN_UPDATE]\n", program_name);
exit(EXIT_FAILURE);
}
// Check past, close the file for now.
fclose (fp);
// #3) (Optional) Time delay between updating, in seconds. Must be greater than 0.
if(argc == 4 && atoi(argv[3]) < 1)
{
fprintf(stderr, "Usage: %s NUMBER_OF_COLUMNS FILE_TO_WATCH " COLOUR_RED "[SECONDS_BETWEEN_UPDATE]" RESET "\n", program_name);
exit(EXIT_FAILURE);
}
// Run process.
// display_colour_bar(atoi(argv[1]), atoi(argv[2]), argc == 4 ? atoi(argv[3]) : 60);
display_colour_bar(atoi(argv[1]), argv[2], argc == 4 ? atoi(argv[3]) : 60);
// Exit cleanly.
exit(EXIT_SUCCESS);
}
void display_colour_bar (int columns, char *file, int seconds)
{
// Declare variables.
char buffer[BUFFER_SIZE + 1] = {0};
FILE *fp = NULL;
struct termios settings = {0};
int x = {0};
// Clear screen and make cursor invisible.
CLEAR_SCREEN;
// Get terminal attributes.
tcgetattr(STDIN_FILENO, &settings);
// Set terminal to not echo. This is needed to stop typing from showing up on xterm window.
settings.c_lflag &= ~(ECHO);
tcsetattr(STDIN_FILENO, TCSANOW, &settings);
// Loop forever.
for(;;)
{
// Open the file for reading.
if((fp = fopen(file, "rb")) == NULL)
{
fprintf(stderr, "%s: %s error: fopen failed (%s) (%s)\n", program_name, __func__, strerror(errno), file);
exit(EXIT_FAILURE);
}
// Get data.
fgets(buffer, BUFFER_SIZE, fp);
// Close the file.
fclose(fp);
// Reset cursor and clear the line.
printf("\e[1;0f\e[K");
// Set foreground colour.
switch(atoi(buffer))
{
case 0 ... 15:
printf(COLOUR_RED);
break;
case 16 ... 49:
printf(COLOUR_YELLOW);
break;
case 50 ... 84:
printf(COLOUR_GREEN);
break;
default:
printf(COLOUR_BLUE);
}
// Start displaying the status bar.
for(x = 0; x < (columns * atoi(buffer)) / 100; x++)
printf(" ");
// Set background colour.
printf(COLOUR_GREY);
// Finish the status bar.
for(; x < columns; x++)
printf(" ");
// Reset the colours.
printf(RESET);
// Flush out to screen.
fflush(stdout);
// Wait for next iteration.
sleep(seconds);
}
}
Save it as colour_status_bar.c
and compile with:
gcc -o colour_status_bar colour_status_bar.c
There will most likely be an update to this, like customizable colours from the command line. If others are interested, let me know and I will post any updates.