Skip to content
Snippets Groups Projects
Commit 00826735 authored by Jiří Kalvoda's avatar Jiří Kalvoda
Browse files

OSDD Add MQTT module.

parent 3bdd9d53
No related branches found
No related tags found
No related merge requests found
......@@ -3,8 +3,6 @@ ARCHIVE=osdd-$(VERSION).tar.gz
CFLAGS=-g3 -Wall -W -Wno-parentheses -Wstrict-prototypes -Wmissing-prototypes -Wundef -Wredundant-decls -std=gnu99 -Wformat-truncation=0
#-fsanitize=address
all: osdd osdc osd-batt osd-alsa
osdd: osdd.o util.o osdd-set.o
......@@ -13,7 +11,10 @@ osd-batt: osd-batt.o util.o client.o
osd-alsa: osd-alsa.o util.o client.o
# OSDD MODULES
osdd: display.o osdd-file.o
osdd: display.o
osdd: osdd-file.o osdd-to-string.o
osdd: osdd-mqtt.o osdd-to-string.o -lpaho-mqtt3a -lpaho-mqtt3c
osdd: LDLIBS+=$(shell pkg-config --libs xft) -lXext -lX11
#LDLIBS += -fsanitize=address
......@@ -24,7 +25,7 @@ osd-batt: LDLIBS+=-lX11
osd-alsa.o: CFLAGS+=$(shell pkg-config --cflags alsa)
osd-alsa: LDLIBS+=$(shell pkg-config --libs alsa) -lX11
display.o osdd-file.o: CFLAGS+=$(shell pkg-config --cflags xft)
display.o osdd-to-string.o: CFLAGS+=$(shell pkg-config --cflags xft)
clean:
rm -f *~ *.o TAGS core osdd osdc osd-batt osd-alsa
......
......@@ -6,99 +6,14 @@
#include "osdd-file.h"
#include "util.h"
#include <stdio.h>
#include <string.h>
#include <time.h>
#include <getopt.h>
#include <stdlib.h>
#include <X11/Xlib.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <X11/extensions/shape.h>
#include <X11/extensions/render.h>
#include <X11/Xft/Xft.h>
#include "osdd-to-string.h"
#include <stdio.h>
#include <stdlib.h>
#include <stdbool.h>
#include <string.h>
#include <time.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <X11/extensions/shape.h>
#include <X11/extensions/render.h>
#include <X11/Xft/Xft.h>
#include <getopt.h>
#include <stdlib.h>
static void replace_no_text(char * in)
{
for(;*in;in++)
{
if(' '== *in) continue;
if('a'<= *in&& *in<='z') continue;
if('A'<= *in&& *in<='Z') continue;
if('0'<= *in&& *in<='9') continue;
//if(128 <= (unsigned char)*in) continue;
*in='?';
}
}
static
char * expand_backslash(char * in)
{
char * out = xmalloc(strlen(in)+1);
int i=0;
for(;*in;i++,in++)
{
if(in[0]=='\\')
{
switch(in[1])
{
case 'n':
out[i]='\n';
break;
case 't':
out[i]='\t';
break;
case '0':
out[i]='\0';
break;
default:
out[i]='?';
break;
}
if(in[1]) in++;
}
else
out[i]=*in;
}
out[i]=0;
return out;
}
static void
colorToRGB(char * name, int *r, int *g, int *b)
{
Display *d = XOpenDisplay(NULL);
int s = XDefaultScreen(d);
Visual *v = XDefaultVisual(d,s);
Colormap cmap = DefaultColormap(d,s);
XftColor color;
if (XftColorAllocName(d, v, cmap, name, &color))
{
typeof(color.color) c = color.color;
*r = c.red;
*g = c.green;
*b = c.blue;
}
else *r=*g=*b=-1;
XftColorFree(d, v, cmap, &color);
XCloseDisplay(d);
}
// ************************* STATE STRUCT **********
......@@ -106,101 +21,15 @@ struct file_state
{
char * file_name;
char * open_mode;
bool clear;
char * line_separator;
char * msq_separator;
char * time_separator;
//tmp usage:
XftColor fg_color;
enum {
FILE_COLOR_NO,
FILE_COLOR_RGB_DEC,
FILE_COLOR_RGB_HEX,
FILE_COLOR_RGB_HASHTAG_HEX,
FILE_COLOR_TERM_RGB,
FILE_COLOR_ORIGINAL,
} color_mode;
enum {
FILE_TIME_NO,
FILE_TIME_UNIX,
FILE_TIME_ISO,
} time_mode;
bool replace_no_text;
struct osd_to_string_state to_string;
};
// ************************* MAIN FUNCTIONS *******
static
void file_show(struct file_state *state, struct osd_line * lines, int num_lines)
{
VECTOR(char) out = NULL;
switch(state->time_mode)
{
case FILE_TIME_NO:
break;
case FILE_TIME_UNIX:
vprint(&out,"%lld%s",(long long)time(0),state->time_separator);
break;
case FILE_TIME_ISO:
void file_write_to_file(struct file_state *state, VECTOR(char) out)
{
time_t t = time(NULL);
struct tm tm = *localtime(&t);
vprint(&out,"%04d-%02d-%02d %02d:%02d:%02d%s", tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday, tm.tm_hour, tm.tm_min, tm.tm_sec,state->time_separator);
}
break;
}
for(int i=0;i<num_lines;i++)
{
struct osd_line * line = lines+i;
//if(!(line->log & 1)) continue;
if(line->type!=OSD_TYPE_TEXT) continue;
int r,g,b;
VECTOR(char) text=0;
VRESERVE(text,strlen(line->u.text)+1);
char color[30];
color[0]=0;
char * end_color = "";
vprint(&text,"%s",line->u.text);
if(state->replace_no_text) replace_no_text(text);
switch(state->color_mode)
{
case FILE_COLOR_RGB_DEC:
case FILE_COLOR_RGB_HEX:
case FILE_COLOR_RGB_HASHTAG_HEX:
case FILE_COLOR_TERM_RGB:
colorToRGB(line->fg_color,&r,&g,&b);
break;
default:
break;
}
switch(state->color_mode)
{
case FILE_COLOR_RGB_DEC:
sprintf(color,"%d %d %d ",r/256,g/256,b/256);
break;
case FILE_COLOR_RGB_HEX:
sprintf(color,"%02x%02x%02x ",r/256,g/256,b/256);
break;
case FILE_COLOR_RGB_HASHTAG_HEX:
sprintf(color,"#%02x%02x%02x ",r/256,g/256,b/256);
break;
case FILE_COLOR_TERM_RGB:
sprintf(color,"\e[38;2;%d;%d;%dm",r/256,g/256,b/256);
end_color = "\e[0m";
break;
case FILE_COLOR_ORIGINAL:
sprintf(color,"%s ",line->fg_color);
break;
case FILE_COLOR_NO:
break;
}
vprint(&out,"%s%s%s%s", color, text, end_color,state->line_separator);
VFREE(text);
}
vprint(&out,"%s",state->msq_separator);
if(!out) return;
FILE * f = fopen(state->file_name,state->open_mode);
if(f)
{
......@@ -210,11 +39,16 @@ void file_show(struct file_state *state, struct osd_line * lines, int num_lines)
VFREE(out);
}
static
void file_show(struct file_state *state, struct osd_line * lines, int num_lines)
{
file_write_to_file(state,osd_to_string(&state->to_string, lines, num_lines));
}
static
void file_clear(struct file_state *state)
{
if(state->clear)
file_show(state,0,0);
file_write_to_file(state,osd_to_string_end_msg(&state->to_string));
}
// ************************* NEW ******************
......@@ -225,12 +59,7 @@ void file_new_help(FILE * f)
fprintf(f,"\
Module FILE help:\n\
-a, --append \t\tAppend to file (do not overwrite)\n\
-c, --color=<{}>\tSet how to print color of messages {no, rgbDEC, rgbHEX, rgbHEXHASHTAG, term, original}\n\
-l, --line-separator=<s>Separato of each line.\n\
-m, --msq-separator=<s>\tSeparato of each message.\n\
-r, --replace\t\tReplace not alphabet and number in output to '?'\n\
-t, --time=<{}>\t\tSet how to print actual time {no, unix, iso}\n\
-T, --time-separator=<s>Separator of time and message text\n\
" OSDD_TO_STRING_HELP "\
\n\
");
}
......@@ -241,15 +70,10 @@ struct osd_abstract file_new(int argc, char ** argv, Display * nope)
(void)nope;
argc++;argv--;
struct osd_abstract r;
static const char short_opts[] = "+ac:l:m:rt:T:";
static const char short_opts[] = "+a" OSDD_TO_STRING_SHORTOP;
static const struct option long_opts[] = {
{ "append", no_argument, NULL, 'a' },
{ "color", required_argument, NULL, 'c' },
{ "line-separator", required_argument, NULL, 'l' },
{ "msq-separator", required_argument, NULL, 'm' },
{ "replace", no_argument, NULL, 'r' },
{ "time", required_argument, NULL, 't' },
{ "time-separator", required_argument, NULL, 'T' },
OSDD_TO_STRING_LONGOP
{ NULL, 0, NULL, 0 },
};
memset(&r,0,sizeof(r));
......@@ -257,58 +81,18 @@ struct osd_abstract file_new(int argc, char ** argv, Display * nope)
memset(state,0,sizeof(state)[0]);
state->open_mode = "w";
state->line_separator = expand_backslash("\\n");
state->time_separator = expand_backslash("\\n");
state->msq_separator = expand_backslash("");
state->clear=0;
osd_to_string_state_init(&state->to_string);
int opt;
optind = 0;
while ((opt = getopt_long(argc, argv, short_opts, long_opts, NULL)) >= 0)
{
if(!osd_to_string_parse_arg(&state->to_string,opt))
switch (opt)
{
case 'a':
state->open_mode = "a";
break;
case 'c':
if(!strcmp(optarg,"no")) state->color_mode = FILE_COLOR_NO; else
if(!strcmp(optarg,"rgbDEC")) state->color_mode = FILE_COLOR_RGB_DEC; else
if(!strcmp(optarg,"rgbHEX")) state->color_mode = FILE_COLOR_RGB_HEX; else
if(!strcmp(optarg,"rgbHEXHASHTAG")) state->color_mode = FILE_COLOR_RGB_HASHTAG_HEX; else
if(!strcmp(optarg,"term")) state->color_mode = FILE_COLOR_TERM_RGB; else
if(!strcmp(optarg,"original")) state->color_mode = FILE_COLOR_ORIGINAL; else
{
fprintf(stderr,"Color mode %s not exist\n\n",optarg);
file_new_help(stderr);
exit(0);
}
break;
case 'l':
free(state->line_separator);
state->line_separator = expand_backslash(optarg);
break;
case 'm':
free(state->msq_separator);
state->msq_separator = expand_backslash(optarg);
break;
case 'r':
state->replace_no_text = 1;
break;
case 't':
if(!strcmp(optarg,"no")) state->time_mode = FILE_TIME_NO; else
if(!strcmp(optarg,"unix")) state->time_mode = FILE_TIME_UNIX; else
if(!strcmp(optarg,"iso")) state->time_mode = FILE_TIME_ISO; else
{
fprintf(stderr,"Time mode %s not exist\n\n",optarg);
file_new_help(stderr);
exit(0);
}
break;
case 'T':
free(state->time_separator);
state->time_separator = expand_backslash(optarg);
break;
default:
fprintf(stderr,"Option %c not exist\n\n",opt);
file_new_help(stderr);
......
/*
* On-screen Display
*
* (c) 2021 Jiri Kalvoda <jirikalvoda@kam.mff.cuni.cz>
*/
#include "osdd-mqtt.h"
#include "util.h"
#include "osdd-to-string.h"
#include <stdio.h>
#include <string.h>
#include <getopt.h>
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <MQTTClient.h>
// ************************* STATE STRUCT **********
struct mqtt_state
{
char * mqtt_addres;
char * mqtt_user;
char * mqtt_passwd;
char * mqtt_topic;
struct osd_to_string_state to_string;
int pipe_fd;
bool mqtt_retained;
int mqtt_qos;
};
struct mqtt_fork_state
{
int fd;
bool connected;
MQTTClient client;
struct mqtt_state * state;
};
// ************************* FORK *****************
static
void mqtt_fork_connect(struct mqtt_fork_state * fork_state)
{
//fprintf(stderr,"MQTT CONNECT\n");
int rc;
for(int i=0;i<2;i++)
{
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wmissing-field-initializers"
MQTTClient_connectOptions conn_opts = MQTTClient_connectOptions_initializer;
conn_opts.httpProxy = 0;
#pragma GCC diagnostic pop
static char mqtt_con_name[300] = "";
if(!mqtt_con_name[0]) sprintf(mqtt_con_name,"led-include-%d-%d",(1),(2));
MQTTClient_create(&fork_state->client, fork_state->state->mqtt_addres, mqtt_con_name,
MQTTCLIENT_PERSISTENCE_NONE, NULL);
conn_opts.keepAliveInterval = 600;
conn_opts.cleansession = 0;
conn_opts.username = fork_state->state->mqtt_user;
conn_opts.password = fork_state->state->mqtt_passwd;
if ((rc = MQTTClient_connect(fork_state->client , &conn_opts)) == MQTTCLIENT_SUCCESS)
{
//fprintf(stderr,"MQTT CONNECT OK\n");
fork_state->connected = 1;
return;
}
MQTTClient_destroy(&fork_state->client);
fprintf(stderr,"MQTT CONNECT FAILD\n");
}
fork_state->connected = 0;
//printf("Failed to connect MQTT, return code %d\n", rc);
//throw std::runtime_error("MQTT Connect error");
}
int TIMEOUT = 10000;
static
void mqtt_fork_sent(struct mqtt_fork_state * fork_state, char * data)
{
int rc;
for(int i=0;;i++)
{
if(!fork_state->connected) mqtt_fork_connect(fork_state);
if(fork_state->connected)
for(int i=0;i<2;i++)
{
MQTTClient_message pubmsg = MQTTClient_message_initializer;
MQTTClient_deliveryToken token;
pubmsg.payload = (void *)data;
pubmsg.payloadlen = strlen(data);
pubmsg.qos = fork_state->state->mqtt_qos;
pubmsg.retained = fork_state->state->mqtt_retained;
//fprintf(stderr,"RETAINED %d QOS %d\n", pubmsg.retained, pubmsg.qos);
MQTTClient_publishMessage(fork_state->client, fork_state->state->mqtt_topic, &pubmsg, &token);
rc = MQTTClient_waitForCompletion(fork_state->client, token, TIMEOUT);
if(rc == MQTTCLIENT_SUCCESS) return;
}
if(i==1)
return;
MQTTClient_destroy(&fork_state->client);
mqtt_fork_connect(fork_state);
}
}
static
void NONRET mqtt_fork_main(struct mqtt_state * state, int fd)
{
struct mqtt_fork_state fork_state;
fork_state.fd = fd;
fork_state.connected = 0;
fork_state.state = state;
while(1)
{
int size;
read(fd,&size,sizeof(int));
char * in = xmalloc(size);
read(fd,in,size);
//fprintf(stderr,"MQTT |%s|\n",in);
mqtt_fork_sent(&fork_state,in);
}
}
// ************************* MAIN FUNCTIONS *******
static
void mqtt_write_to_mqtt(struct mqtt_state *state, VECTOR(char) out)
{
if(!out) return;
int size = VSIZE(out);
char * buf = xmalloc(size+sizeof(int));
memcpy(buf + sizeof(int), out, size);
*(int *) buf = size;
write(state->pipe_fd,buf,size+sizeof(int));
free(buf);
VFREE(out);
}
static
void mqtt_show(struct mqtt_state *state, struct osd_line * lines, int num_lines)
{
mqtt_write_to_mqtt(state,osd_to_string(&state->to_string, lines, num_lines));
}
static
void mqtt_clear(struct mqtt_state *state)
{
mqtt_write_to_mqtt(state,osd_to_string_end_msg(&state->to_string));
}
// ************************* NEW ******************
static
void mqtt_new_help(FILE * f)
{
fprintf(f,"\
Module MQTT help:\n\
-R, --retained \t\tSending messages will be retained\n\
-q, --qos=<{}> \t\tSet QOS of sending messages. {0,1,2}\n\
" OSDD_TO_STRING_HELP "\
\n\
");
}
static
struct osd_abstract mqtt_new(int argc, char ** argv, Display * nope)
{
(void)nope;
argc++;argv--;
struct osd_abstract r;
static const char short_opts[] = "+Rq:" OSDD_TO_STRING_SHORTOP;
static const struct option long_opts[] = {
{ "retained", no_argument, NULL, 'R' },
{ "qos", required_argument, NULL, 'q' },
OSDD_TO_STRING_LONGOP
{ NULL, 0, NULL, 0 },
};
memset(&r,0,sizeof(r));
struct mqtt_state *state = xmalloc(sizeof(*state));
memset(state,0,sizeof(state)[0]);
state->mqtt_qos = 1;
state->mqtt_retained = 0;
osd_to_string_state_init(&state->to_string);
int opt;
optind = 0;
while ((opt = getopt_long(argc, argv, short_opts, long_opts, NULL)) >= 0)
{
if(!osd_to_string_parse_arg(&state->to_string,opt))
switch (opt)
{
case 'R':
state->mqtt_retained = 1;
break;
case 'q':
state->mqtt_qos = atoi(optarg);
break;
default:
fprintf(stderr,"Option %c not exist\n\n",opt);
mqtt_new_help(stderr);
exit(0);
}
}
int ind = optind;
if(ind + 4 > argc)
{
fprintf(stderr,"Missing positional argument\n\n");
mqtt_new_help(stderr);
exit(0);
}
state->mqtt_addres = argv[ind++];
state->mqtt_user = argv[ind++];
state->mqtt_passwd = argv[ind++];
state->mqtt_topic = argv[ind++];
if(ind != argc)
{
fprintf(stderr,"Too many arguments\n\n");
mqtt_new_help(stderr);
exit(0);
}
r.context = state;
void (*show)(struct mqtt_state*, struct osd_line*, int) = mqtt_show;
r.show = (void (*)(void*, struct osd_line*, int)) show;
void (*clear)(struct mqtt_state*) = mqtt_clear;
r.clear = (void (*)(void*)) clear;
int fd[2];
pipe(fd);
if(fork() == 0)
{
close (fd[1]);
//write (fd[WRITE], phrase, strlen ( phrase) +1);
mqtt_fork_main(state , fd[0]);
}
close(fd[0]);
fcntl(fd[1], F_SETFL, O_NONBLOCK);
state->pipe_fd = fd[1];
return r;
}
// ************************* CREATOR ****************************
struct osd_creator_abstract mqtt_creator_new(void)
{
struct osd_creator_abstract r;
memset(&r, 0, sizeof(r));
r.name = "MQTT";
r.help = mqtt_new_help;
r.new.add_one_osd = mqtt_new;
return r;
}
/*
* On-screen Display
*
* (c) 2020--2021 Jiri Kalvoda <jirikalvoda@kam.mff.cuni.cz>
*/
#include "osdd-set.h"
struct osd_creator_abstract mqtt_creator_new(void);
......@@ -6,5 +6,16 @@ pkill -f not2osd
not2osd &
tmp=$(mktemp)
echo "Xft.render: False" > $tmp
XENVIRONMENT=$tmp ./osdd -D DISPLAY_BY_OUTPUTS default nolog [ -n a%d ] FILE default log loglog [ -a -l' ' -m'\n' -T' ' -tiso -cterm ~/.osdd_log ] FILE default log loglast [ -l'\n' -tunix -T'\n' -crgbHEX -r ~/.osdd_last ] | bash
XENVIRONMENT=$tmp \
./osdd -D \
DISPLAY_BY_OUTPUTS default nolog [ -n a%d ] \
FILE default log loglog [ -a -l' ' -m'\n' -T' ' -tiso -cterm ~/.osdd_log ] \
FILE default log loglast [ -l'\n' -tunix -T'\n' -crgbHEX -r ~/.osdd_last ] \
MQTT default mqtt led [ -e'\0' -E -crgbDEC -tunix -R -q0 \
$(cat ~/.secret/mqtt/rpi0-all.addres) \
$(cat ~/.secret/mqtt/rpi0-led-include.user) \
$(cat ~/.secret/mqtt/rpi0-led-include.passwd) \
osd/arch ] \
| bash
rm $tmp
pkill -f not2osd
/*
* On-screen Display
*
* (c) 2020--2021 Jiri Kalvoda <jirikalvoda@kam.mff.cuni.cz>
*/
#include "osdd-to-string.h"
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <getopt.h>
#include <time.h>
#include <X11/Xlib.h>
#include <X11/Xlib.h>
#include <X11/Xatom.h>
#include <X11/extensions/shape.h>
#include <X11/extensions/render.h>
#include <X11/Xft/Xft.h>
static
char * expand_backslash(char * in)
{
char * out = xmalloc(strlen(in)+1);
int i=0;
for(;*in;i++,in++)
{
if(in[0]=='\\')
{
switch(in[1])
{
case 'n':
out[i]='\n';
break;
case 't':
out[i]='\t';
break;
case '0':
out[i]='\0';
break;
default:
out[i]='?';
break;
}
if(in[1]) in++;
}
else
out[i]=*in;
}
out[i]=0;
return out;
}
static void replace_no_text(char * in)
{
for(;*in;in++)
{
if(' '== *in) continue;
if('a'<= *in&& *in<='z') continue;
if('A'<= *in&& *in<='Z') continue;
if('0'<= *in&& *in<='9') continue;
//if(128 <= (unsigned char)*in) continue;
*in='?';
}
}
static void
colorToRGB(char * name, int *r, int *g, int *b)
{
Display *d = XOpenDisplay(NULL);
int s = XDefaultScreen(d);
Visual *v = XDefaultVisual(d,s);
Colormap cmap = DefaultColormap(d,s);
XftColor color;
if (XftColorAllocName(d, v, cmap, name, &color))
{
typeof(color.color) c = color.color;
*r = c.red;
*g = c.green;
*b = c.blue;
}
else *r=*g=*b=-1;
XftColorFree(d, v, cmap, &color);
XCloseDisplay(d);
}
bool osd_to_string_parse_arg(struct osd_to_string_state *state, char arg)
{
switch(arg)
{
case 'c':
if(!strcmp(optarg,"no")) state->color_mode = FILE_COLOR_NO; else
if(!strcmp(optarg,"rgbDEC")) state->color_mode = FILE_COLOR_RGB_DEC; else
if(!strcmp(optarg,"rgbHEX")) state->color_mode = FILE_COLOR_RGB_HEX; else
if(!strcmp(optarg,"rgbHEXHASHTAG")) state->color_mode = FILE_COLOR_RGB_HASHTAG_HEX; else
if(!strcmp(optarg,"term")) state->color_mode = FILE_COLOR_TERM_RGB; else
if(!strcmp(optarg,"original")) state->color_mode = FILE_COLOR_ORIGINAL; else
{
fprintf(stderr,"Color mode %s not exist\n\n",optarg);
exit(0);
}
break;
case 'l':
free(state->line_separator);
state->line_separator = expand_backslash(optarg);
break;
case 'm':
free(state->msq_separator);
state->msq_separator = expand_backslash(optarg);
break;
case 'r':
state->replace_no_text = 1;
break;
case 't':
if(!strcmp(optarg,"no")) state->time_mode = FILE_TIME_NO; else
if(!strcmp(optarg,"unix")) state->time_mode = FILE_TIME_UNIX; else
if(!strcmp(optarg,"iso")) state->time_mode = FILE_TIME_ISO; else
{
fprintf(stderr,"Time mode %s not exist\n\n",optarg);
exit(0);
}
break;
case 'T':
free(state->time_separator);
state->time_separator = expand_backslash(optarg);
break;
case 'e':
if(state->end_of_mes_by) free(state->end_of_mes_by);
state->end_of_mes_by = expand_backslash(optarg);
break;
case 'E':
state->end_of_mes_time = 1;
break;
default:
return 0;
}
return 1;
}
static
void osd_to_string_time(struct osd_to_string_state *state, VECTOR(char) * out)
{
switch(state->time_mode)
{
case FILE_TIME_NO:
break;
case FILE_TIME_UNIX:
vprint(out,"%lld%s",(long long)time(0),state->time_separator);
break;
case FILE_TIME_ISO:
{
time_t t = time(NULL);
struct tm tm = *localtime(&t);
vprint(out,"%04d-%02d-%02d %02d:%02d:%02d%s", tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday, tm.tm_hour, tm.tm_min, tm.tm_sec,state->time_separator);
}
break;
}
}
VECTOR(char) osd_to_string(struct osd_to_string_state *state, struct osd_line * lines, int num_lines)
{
VECTOR(char) out = NULL;
osd_to_string_time(state, &out);
for(int i=0;i<num_lines;i++)
{
struct osd_line * line = lines+i;
//if(!(line->log & 1)) continue;
if(line->type!=OSD_TYPE_TEXT) continue;
int r,g,b;
VECTOR(char) text=0;
VRESERVE(text,strlen(line->u.text)+1);
char color[30];
color[0]=0;
char * end_color = "";
vprint(&text,"%s",line->u.text);
if(state->replace_no_text) replace_no_text(text);
switch(state->color_mode)
{
case FILE_COLOR_RGB_DEC:
case FILE_COLOR_RGB_HEX:
case FILE_COLOR_RGB_HASHTAG_HEX:
case FILE_COLOR_TERM_RGB:
colorToRGB(line->fg_color,&r,&g,&b);
break;
default:
break;
}
switch(state->color_mode)
{
case FILE_COLOR_RGB_DEC:
sprintf(color,"%d %d %d ",r/256,g/256,b/256);
break;
case FILE_COLOR_RGB_HEX:
sprintf(color,"%02x%02x%02x ",r/256,g/256,b/256);
break;
case FILE_COLOR_RGB_HASHTAG_HEX:
sprintf(color,"#%02x%02x%02x ",r/256,g/256,b/256);
break;
case FILE_COLOR_TERM_RGB:
sprintf(color,"\e[38;2;%d;%d;%dm",r/256,g/256,b/256);
end_color = "\e[0m";
break;
case FILE_COLOR_ORIGINAL:
sprintf(color,"%s ",line->fg_color);
break;
case FILE_COLOR_NO:
break;
}
vprint(&out,"%s%s%s%s", color, text, end_color,state->line_separator);
VFREE(text);
}
vprint(&out,"%s",state->msq_separator);
return out;
}
VECTOR(char) osd_to_string_end_msg(struct osd_to_string_state *state)
{
if(!state->end_of_mes_by) return 0;
VECTOR(char) out=0;
if(state->end_of_mes_time)
osd_to_string_time(state, &out);
vprint(&out,"%s",state->end_of_mes_by);
return out;
}
void osd_to_string_state_init(struct osd_to_string_state * state)
{
state->line_separator = expand_backslash("\\n");
state->time_separator = expand_backslash("\\n");
state->msq_separator = expand_backslash("");
state->end_of_mes_by = 0;
}
/*
* On-screen Display
*
* (c) 2020--2021 Jiri Kalvoda <jirikalvoda@kam.mff.cuni.cz>
*/
#include "osdd-set.h"
#include "util.h"
#define OSDD_TO_STRING_LONGOP \
{ "color", required_argument, NULL, 'c' },\
{ "line-separator", required_argument, NULL, 'l' },\
{ "msq-separator", required_argument, NULL, 'm' },\
{ "replace", no_argument, NULL, 'r' },\
{ "time", required_argument, NULL, 't' },\
{ "time-separator", required_argument, NULL, 'T' },\
{ "end", required_argument, NULL, 'e' },\
#define OSDD_TO_STRING_SHORTOP \
"c:l:m:rt:T:e:E"
#define OSDD_TO_STRING_HELP "\
-c, --color=<{}>\tSet how to print color of messages {no, rgbDEC, rgbHEX, rgbHEXHASHTAG, term, original}\n\
-l, --line-separator=<s>Separato of each line.\n\
-m, --msq-separator=<s>\tSeparato of each message.\n\
-r, --replace\t\tReplace not alphabet and number in output to '?'\n\
-t, --time=<{}>\t\tSet how to print actual time {no, unix, iso}\n\
-T, --time-separator=<s>Separator of time and message text\n\
-E, --end-time\t\tWrite actual time to end messages (format from -t -T)\n\
"
struct osd_to_string_state
{
char * line_separator;
char * msq_separator;
char * time_separator;
enum {
FILE_COLOR_NO,
FILE_COLOR_RGB_DEC,
FILE_COLOR_RGB_HEX,
FILE_COLOR_RGB_HASHTAG_HEX,
FILE_COLOR_TERM_RGB,
FILE_COLOR_ORIGINAL,
} color_mode;
enum {
FILE_TIME_NO,
FILE_TIME_UNIX,
FILE_TIME_ISO,
} time_mode;
bool replace_no_text;
char * end_of_mes_by;
bool end_of_mes_time;
};
VECTOR(char) osd_to_string(struct osd_to_string_state *state, struct osd_line * lines, int num_lines);
VECTOR(char) osd_to_string_end_msg(struct osd_to_string_state *state);
bool osd_to_string_parse_arg(struct osd_to_string_state *state, char arg);
void osd_to_string_state_init(struct osd_to_string_state * state);
......@@ -18,8 +18,10 @@
#define DEBUG
#include "util.h"
#include "osdd-set.h"
#include "display.h"
#include "osdd-file.h"
#include "osdd-mqtt.h"
static struct osd_set osd;
......@@ -431,6 +433,7 @@ main(int argc, char **argv)
VPB(creator,display_creator_new());
VPB(creator,display_by_outputs_creator_new());
VPB(creator,file_creator_new());
VPB(creator,mqtt_creator_new());
setlocale(LC_CTYPE, "");
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment