ArgPar-C v1.0.0-build
Simple and powerful Argument Parser for C
Loading...
Searching...
No Matches
APC_ArgParser.h File Reference
#include <stdbool.h>
#include "../../../vendor/cvec/inc/cvec/cvec.h"

Go to the source code of this file.

Data Structures

struct  APC_ArgInfo
struct  APC_ArgParser
struct  APC_RGB

Macros

#define __APC_CPP_GUARD_CLOSE   }
#define __APC_CPP_GUARD_OPEN   extern "C" {

Enumerations

enum  APC_RGB_Command {
  APC_RGB_Command_None , APC_RGB_Command_Reset , APC_RGB_Command_Bold , APC_RGB_Command_Italic ,
  APC_RGB_Command_Underline
}

Functions

char * __apc_colorFormat (APC_ArgParser *argpar, const char *msg)
 Format color;.
APC_RGB __apc_rgbToRGBStruct (const char *rgbStr)
 Convert the default RGB format to a valid RGB struct and parse all extended commands.
char * __apc_setRGB (int r, int g, int b)
 Convert RGB to ANSI escape code.
bool apc_add (APC_ArgParser *argpar, APC_ArgInfo info)
 Setup Arg Information to the argpar.
void apc_destroy (APC_ArgParser *argpar)
 Free all allocated data for argument parser.
char * apc_generateHelp (APC_ArgParser *argpar, const char *title, const char *topInfo, const char *lowerInfo)
 Automatically generate help and pass it to the string to return.
bool apc_get (APC_ArgParser *argpar, const char *id)
 Get if there is an argument present.
APC_ArgParser apc_init (int argc, char *argv[])
 Initialize parser with argc and argv from the main() function.
APC_ArgInfo apc_initInfo (void)
 Initialize information for params.

Macro Definition Documentation

◆ __APC_CPP_GUARD_CLOSE

#define __APC_CPP_GUARD_CLOSE   }

Definition at line 10 of file APC_ArgParser.h.

◆ __APC_CPP_GUARD_OPEN

#define __APC_CPP_GUARD_OPEN   extern "C" {

Definition at line 9 of file APC_ArgParser.h.

Enumeration Type Documentation

◆ APC_RGB_Command

Enumerator
APC_RGB_Command_None 
APC_RGB_Command_Reset 
APC_RGB_Command_Bold 
APC_RGB_Command_Italic 
APC_RGB_Command_Underline 

Definition at line 18 of file APC_ArgParser.h.

19{
25};
@ APC_RGB_Command_Underline
@ APC_RGB_Command_Italic
@ APC_RGB_Command_Reset
@ APC_RGB_Command_None
@ APC_RGB_Command_Bold

Function Documentation

◆ __apc_colorFormat()

char * __apc_colorFormat ( APC_ArgParser * argpar,
const char * msg )

Format color;.

  • Remove color commands if color disabled
  • Convert to color ANSI escape code if enabled
    Parameters
    argparArgument to format color and get data from
    msgMessage to format

Definition at line 199 of file APC_ArgParser.c.

200{
201 CSTR result = cstr_init();
202 cstr_set(&result, msg);
203
204 if (!argpar->enableColor)
205 {
206 // Remove occurrences that have:
207 // `${` until the next `}`
208 int pos = 0;
209
210 while (1)
211 {
212 const int start = cstr_findFrom(&result, "${", pos);
213
214 if (start == CSTR_NPOS)
215 break;
216
217 const int end = cstr_findFrom(&result, "}", start + 2);
218
219 if (end == CSTR_NPOS)
220 break;
221
222 int len = (end - start) + 1;
223
224 cstr_erase(&result, start, len);
225
226 pos = start;
227 }
228 }
229
230 else
231 {
232 // Replace occurrences that have:
233 // `${` until the next `}`
234 // With the corresponding color syntax;
235 // ${r,g,b}
236
237 int pos = 0;
238
239 CSTR substr = cstr_init();
240
241 while (1)
242 {
243 const int start = cstr_findFrom(&result, "${", pos);
244
245 if (start == CSTR_NPOS)
246 break;
247
248 const int end = cstr_findFrom(&result, "}", start + 2);
249
250 if (end == CSTR_NPOS)
251 break;
252
253 int len = (end - start) + 1;
254
255 cstr_set(&substr, result.data);
256 cstr_substr(&substr, start, len);
257
258 // Set the RGB to the struct and then format it to string to
259 // output it in an ANSI color format
260 const APC_RGB rgb = __apc_rgbToRGBStruct(substr.data);
261
262 char *rgbStr = NULL;
263
265 rgbStr = APC_STYLE_RESET;
266
268 rgbStr = APC_STYLE_BOLD;
269
271 rgbStr = APC_STYLE_ITALIC;
272
274 rgbStr = APC_STYLE_UNDERLINE;
275
276 else rgbStr = __apc_setRGB(rgb.r, rgb.g, rgb.b);
277
278 // 1. Remove `${r,g,b}` with its params
279 // 2. And Insert ANSI string at same position where it's supposed to be
280 cstr_erase(&result, start, len);
281 cstr_insert(&result, rgbStr, start);
282
283 // Move position forward past inserted ANSI sequence
284 pos = start + strlen(rgbStr);
285
286 // If external action is made
287 // DO NOT free, or else, it'll crash
288 if (!rgb.__externalAction) { APC_FREE(rgbStr); }
289 }
290
291 cstr_destroy(&substr);
292 }
293
294 char *ret = CSTR_sys_strdup(result.data);
295
296 cstr_destroy(&result);
297
298 return ret;
299}
APC_RGB __apc_rgbToRGBStruct(const char *rgbStr)
Convert the default RGB format to a valid RGB struct and parse all extended commands.
char * __apc_setRGB(int r, int g, int b)
Convert RGB to ANSI escape code.
#define APC_STYLE_ITALIC
Definition APC_config.h:16
#define APC_STYLE_BOLD
Definition APC_config.h:15
#define APC_STYLE_RESET
Definition APC_config.h:14
#define APC_STYLE_UNDERLINE
Definition APC_config.h:17
#define APC_FREE(x)
unsigned int g
unsigned int b
enum APC_RGB_Command __externalAction
unsigned int r

References __apc_rgbToRGBStruct(), __apc_setRGB(), APC_RGB::__externalAction, APC_FREE, APC_RGB_Command_Bold, APC_RGB_Command_Italic, APC_RGB_Command_Reset, APC_RGB_Command_Underline, APC_STYLE_BOLD, APC_STYLE_ITALIC, APC_STYLE_RESET, APC_STYLE_UNDERLINE, APC_RGB::b, APC_ArgParser::enableColor, APC_RGB::g, and APC_RGB::r.

Referenced by apc_generateHelp().

◆ __apc_rgbToRGBStruct()

APC_RGB __apc_rgbToRGBStruct ( const char * rgbStr)

Convert the default RGB format to a valid RGB struct and parse all extended commands.

  • ${r,g,b}
  • ${R}
  • ${BOLD}
    Returns
    New APC_RGB with RGB data and extended data type (italic, bold, reset, ...)

Definition at line 132 of file APC_ArgParser.c.

133{
134 APC_RGB rgb = {0};
136
137 // Reset terminal styles
138 // Such as color, bolds, italics, etc
139 if (strcmp(rgbStr, "${R}") == 0)
140 {
142
143 rgb.r = 0;
144 rgb.g = 0;
145 rgb.b = 0;
146
147 return rgb;
148 }
149
150 else if (strcmp(rgbStr, "${BOLD}") == 0)
151 {
153
154 rgb.r = 0;
155 rgb.g = 0;
156 rgb.b = 0;
157
158 return rgb;
159 }
160
161 else if (strcmp(rgbStr, "${ITALIC}") == 0)
162 {
164
165 rgb.r = 0;
166 rgb.g = 0;
167 rgb.b = 0;
168
169 return rgb;
170 }
171
172 else if (strcmp(rgbStr, "${UNDERLINE}") == 0)
173 {
175
176 rgb.r = 0;
177 rgb.g = 0;
178 rgb.b = 0;
179
180 return rgb;
181 }
182
183 if (!rgbStr)
184 return rgb;
185
186 int r, g, b;
187
188 // Get format: ${r,g,b}
189 if (sscanf(rgbStr, "${%d,%d,%d}", &r, &g, &b) == 3)
190 {
191 if (r >= 0 && r <= 255) rgb.r = (unsigned char)r;
192 if (g >= 0 && g <= 255) rgb.g = (unsigned char)g;
193 if (b >= 0 && b <= 255) rgb.b = (unsigned char)b;
194 }
195
196 return rgb;
197}

References APC_RGB::__externalAction, APC_RGB_Command_Bold, APC_RGB_Command_Italic, APC_RGB_Command_None, APC_RGB_Command_Reset, APC_RGB_Command_Underline, APC_RGB::b, APC_RGB::g, and APC_RGB::r.

Referenced by __apc_colorFormat().

◆ __apc_setRGB()

char * __apc_setRGB ( int r,
int g,
int b )

Convert RGB to ANSI escape code.

Parameters
rRed color
gGreen color
bBlue color
Returns
Constructed ANSI escape code

Definition at line 101 of file APC_ArgParser.c.

102{
103 if (r < 0 || r > 255) return NULL;
104 if (g < 0 || g > 255) return NULL;
105 if (b < 0 || b > 255) return NULL;
106
107 CSTR formatted = cstr_init();
108
109 char tmp[16];
110
111 cstr_set(&formatted, "\033[38;2;");
112
113 snprintf(tmp, sizeof(tmp), "%u", r);
114 cstr_add(&formatted, tmp);
115 cstr_add(&formatted, ";");
116
117 snprintf(tmp, sizeof(tmp), "%u", g);
118 cstr_add(&formatted, tmp);
119 cstr_add(&formatted, ";");
120
121 snprintf(tmp, sizeof(tmp), "%u", b);
122 cstr_add(&formatted, tmp);
123 cstr_add(&formatted, "m");
124
125 char *ret = CSTR_sys_strdup(formatted.data);
126
127 cstr_destroy(&formatted);
128
129 return ret;
130}

Referenced by __apc_colorFormat().

◆ apc_add()

bool apc_add ( APC_ArgParser * argpar,
APC_ArgInfo info )

Setup Arg Information to the argpar.

Parameters
argparArgument Parser to modify information from
infoCreate information about the param
Returns
false if fail, true if success

Definition at line 48 of file APC_ArgParser.c.

49{
50 // Make addition checks
51 if (info.id[0] == '\0' ||
52 info.param[0] == '\0')
53 return false;
54
55 // If passed, push it:
56 cvec_push(&argpar->args, APC_ArgInfo, info);
57
58 return true;
59}

References APC_ArgParser::args, APC_ArgInfo::id, and APC_ArgInfo::param.

Referenced by main().

◆ apc_destroy()

void apc_destroy ( APC_ArgParser * argpar)

Free all allocated data for argument parser.

Parameters
argparArgument parser to free from memory

Definition at line 33 of file APC_ArgParser.c.

34{
35 for (size_t i = 0 ; i < argpar->args.size ; i++)
36 {
37 APC_ArgInfo *info = cvec_get(&argpar->args, i);
38
39 if (!info) continue;
40
41 // Destroy
42 cvec_destroy(&info->aliases);
43 }
44
45 cvec_destroy(&argpar->args);
46}

References APC_ArgInfo::aliases, and APC_ArgParser::args.

Referenced by main().

◆ apc_generateHelp()

char * apc_generateHelp ( APC_ArgParser * argpar,
const char * title,
const char * topInfo,
const char * lowerInfo )

Automatically generate help and pass it to the string to return.

Parameters
argparArgument parser to generate help from
titleTitle of the help
topInfoTop information (eg: Little intro of the tool)
lowerInfoLower information (eg: License, ...)
Returns
Generated help with escape characters for colors (if enabled)

Definition at line 301 of file APC_ArgParser.c.

305{
306 CSTR docs = cstr_init();
307 cstr_set(&docs, "");
308
309 CSTR tmpContent = cstr_init();
310 cstr_set(&tmpContent, "");
311
312 char *result = NULL;
313
314 // Title
315 cstr_clear(&tmpContent);
316 cstr_add(&tmpContent, APC_STYLECOLOR_TITLE "${BOLD}");
317 cstr_add(&tmpContent, title ? title : "");
318 cstr_add(&tmpContent, "${R}\n");
319
320 result = __apc_colorFormat(argpar, tmpContent.data);
321
322 if (result)
323 {
324 cstr_add(&docs, result);
325 APC_FREE(result);
326 }
327
328 // Top info
329 cstr_clear(&tmpContent);
330 cstr_add(&tmpContent, "${ITALIC}");
331 cstr_add(&tmpContent, topInfo ? topInfo : "");
332 cstr_add(&tmpContent, "${R}\n");
333
334 result = __apc_colorFormat(argpar, tmpContent.data);
335
336 if (result)
337 {
338 cstr_add(&docs, result);
339 APC_FREE(result);
340 }
341
342 // MAIN INFO
343
344 for (size_t i = 0 ; i < argpar->args.size ; i++)
345 {
346 const APC_ArgInfo *info = cvec_get(&argpar->args, i);
347
348 cstr_clear(&tmpContent);
349
350 // Example:
351 // help [ --help|-h|-? ]; Show this help
352 // Structure:
353 // {ID} [ {param1}|{param2}|{alias1}|{alias2}|{...} ]; {Description}
354 cstr_add(&tmpContent, info->id);
355
356 // Open optional
357 if (!info->required)
358 {
359 char *parsedColor = __apc_colorFormat(argpar, APC_STYLECOLOR_OPTIONAL);
360
361 cstr_add(&tmpContent, parsedColor);
362 cstr_add(&tmpContent, " [ ");
363
364 APC_FREE(parsedColor);
365 }
366
367 cstr_add(&tmpContent, info->param);
368
369 if (strlen(info->sparam) > 0)
370 {
371 cstr_add(&tmpContent, "|");
372 cstr_add(&tmpContent, info->sparam);
373 }
374
375 for (size_t i = 0 ; i < info->aliases.size ; i++)
376 {
377 const char **aliasName = cvec_get(&info->aliases, i);
378
379 if (!aliasName && !*aliasName)
380 continue;
381
382 cstr_add(&tmpContent, "|");
383 cstr_add(&tmpContent, *aliasName);
384 }
385
386 // Close optional
387 if (!info->required)
388 {
389 char *parsedColor = __apc_colorFormat(argpar, "${R}");
390
391 cstr_add(&tmpContent, " ]");
392 cstr_add(&tmpContent, parsedColor);
393
394 APC_FREE(parsedColor);
395 }
396
397 cstr_add(&tmpContent, "; ");
398 cstr_add(&tmpContent, info->help);
399 cstr_add(&tmpContent, "\n");
400
401 cstr_add(&docs, tmpContent.data);
402 }
403
404 //
405
406 // Lower info
407 cstr_clear(&tmpContent);
408 cstr_add(&tmpContent, "${ITALIC}");
409 cstr_add(&tmpContent, lowerInfo ? lowerInfo : "");
410 cstr_add(&tmpContent, "${R}");
411
412 result = __apc_colorFormat(argpar, tmpContent.data);
413
414 if (result)
415 {
416 cstr_add(&docs, result);
417 APC_FREE(result);
418 }
419
420 char *data = CSTR_sys_strdup(docs.data);
421
422 cstr_destroy(&docs);
423 cstr_destroy(&tmpContent);
424
425 return data;
426}
char * __apc_colorFormat(APC_ArgParser *argpar, const char *msg)
Format color;.
#define APC_STYLECOLOR_TITLE
Definition APC_config.h:20
#define APC_STYLECOLOR_OPTIONAL
Definition APC_config.h:21

References __apc_colorFormat(), APC_ArgInfo::aliases, APC_FREE, APC_STYLECOLOR_OPTIONAL, APC_STYLECOLOR_TITLE, APC_ArgParser::args, APC_ArgInfo::help, APC_ArgInfo::id, APC_ArgInfo::param, APC_ArgInfo::required, and APC_ArgInfo::sparam.

Referenced by main().

◆ apc_get()

bool apc_get ( APC_ArgParser * argpar,
const char * id )

Get if there is an argument present.

Parameters
argparGet parameters from argpar
idID to fetch
Returns
false if fail, true if success

Definition at line 61 of file APC_ArgParser.c.

62{
63 if (id[0] == '\0' || !id ||
64 !argpar)
65 return false;
66
67 // Check main CVEC ARGS
68 for (size_t arg = 0 ; arg < argpar->args.size ; arg++)
69 {
70 APC_ArgInfo *info = cvec_get(&argpar->args, arg);
71
72 if (!info) continue;
73
74 if (strcmp(info->id, id) != 0)
75 continue;
76
77 // Check ARGV from apc_init() function
78 for (int argv = 0 ; argv < argpar->argc ; argv++)
79 {
80 if (strcmp(argpar->argv[argv], info->param) == 0 ||
81 strcmp(argpar->argv[argv], info->sparam) == 0)
82 return true;
83
84 // Parse aliases
85 for (size_t a = 0 ; a < info->aliases.size ; a++)
86 {
87 char **alias = cvec_get(&info->aliases, a);
88
89 if (!alias && !*alias)
90 continue;
91
92 if (strcmp(argpar->argv[argv], *alias) == 0)
93 return true;
94 }
95 }
96 }
97
98 return false;
99}

References APC_ArgInfo::aliases, APC_ArgParser::argc, APC_ArgParser::args, APC_ArgParser::argv, APC_ArgInfo::id, APC_ArgInfo::param, and APC_ArgInfo::sparam.

Referenced by main().

◆ apc_init()

APC_ArgParser apc_init ( int argc,
char * argv[] )

Initialize parser with argc and argv from the main() function.

Parameters
argcNumber of arguments
argvArgument values
Returns
Constructed APC_ArgParser with all the recommended data

Definition at line 12 of file APC_ArgParser.c.

13{
14 APC_ArgParser parser = {0};
15
16 parser.argc = argc;
17 parser.argv = argv;
18 parser.args = cvec_init(-1, sizeof(APC_ArgInfo));
19 parser.enableColor = true;
20
21 return parser;
22}

References APC_ArgParser::argc, APC_ArgParser::args, APC_ArgParser::argv, and APC_ArgParser::enableColor.

Referenced by main().

◆ apc_initInfo()

APC_ArgInfo apc_initInfo ( void )

Initialize information for params.

  • Constructed empty aliases
  • required defaults to false
    Returns
    Initialized APC_ArgInfo with default values

Definition at line 24 of file APC_ArgParser.c.

25{
26 APC_ArgInfo info = {0};
27 info.aliases = cvec_init(-1, sizeof(const char*));
28 info.required = false;
29
30 return info;
31}

References APC_ArgInfo::aliases, and APC_ArgInfo::required.

Referenced by main().