Nilorea Library
C utilities for networking, threading, graphics
Loading...
Searching...
No Matches
n_gui.c
Go to the documentation of this file.
1
9#include "nilorea/n_common.h"
10#include "nilorea/n_log.h"
11#include "nilorea/n_str.h"
12#include "nilorea/n_gui.h"
13
18
24void n_gui_init_tokenizer(N_GUI_TOKENIZER* tokenizer, const char* input) {
25 tokenizer->input = input;
26 tokenizer->position = 0;
27}
28
35 return tokenizer->input[tokenizer->position++];
36}
37
44 return tokenizer->input[tokenizer->position];
45}
46
53 return tokenizer->input[tokenizer->position] == '\0';
54}
55
62N_GUI_TOKEN n_gui_next_token(N_GUI_TOKENIZER* tokenizer, bool* inside_open_tag) {
63 N_GUI_TOKEN token = {.type = N_GUI_TOKEN_EOF, .value = {0}};
64 char ch;
65
66 // Skip whitespace
67 while (isspace(n_gui_peek_char(tokenizer))) {
68 n_gui_next_char(tokenizer);
69 }
70
71 ch = n_gui_peek_char(tokenizer);
72
73 // Handle end of file
74 if (ch == '\0') {
75 token.type = N_GUI_TOKEN_EOF;
76 return token;
77 }
78
79 // Handle opening tag '<'
80 if (ch == '<') {
81 n_gui_next_char(tokenizer);
82 ch = n_gui_peek_char(tokenizer);
83 if (ch == '/') {
84 n_gui_next_char(tokenizer);
85 *inside_open_tag = false;
87 strncpy(token.value, "/", N_GUI_MAX_TOKEN_SIZE - 1);
88 } else {
89 *inside_open_tag = true;
91 strncpy(token.value, "<", N_GUI_MAX_TOKEN_SIZE - 1);
92 }
93 return token;
94 }
95
96 // Handle closing tag '>'
97 if (ch == '>') {
98 n_gui_next_char(tokenizer);
99 *inside_open_tag = false;
101 strncpy(token.value, ">", N_GUI_MAX_TOKEN_SIZE - 1);
102 return token;
103 }
104
105 // Handle attribute values
106 if (ch == '=') {
107 n_gui_next_char(tokenizer); // consume '='
109 ch = n_gui_peek_char(tokenizer);
110 if (ch == '"' || ch == '\'') {
111 char quote = n_gui_next_char(tokenizer);
112 int pos = 0;
113 while (n_gui_peek_char(tokenizer) != quote && !n_gui_is_eof(tokenizer)) {
114 if (pos < N_GUI_MAX_TOKEN_SIZE - 1) {
115 token.value[pos++] = n_gui_next_char(tokenizer);
116 }
117 }
118 n_gui_next_char(tokenizer); // consume closing quote
119 token.value[pos] = '\0';
120 }
121 return token;
122 }
123
124 // Handle tag names and attribute names
125 if (*inside_open_tag && (isalpha(ch) || ch == '-')) {
126 int pos = 0;
127 while (isalnum(n_gui_peek_char(tokenizer)) || n_gui_peek_char(tokenizer) == '-' || n_gui_peek_char(tokenizer) == '_') {
128 if (pos < N_GUI_MAX_TOKEN_SIZE - 1) {
129 token.value[pos++] = n_gui_next_char(tokenizer);
130 }
131 }
132 token.value[pos] = '\0';
133
134 // Check if the next character is '=' to identify as attribute name
135 if (n_gui_peek_char(tokenizer) == '=') {
137 } else {
139 }
140 return token;
141 }
142
143 // Handle text content
144 if (ch != '<' && ch != '>') {
145 if (!*inside_open_tag) { // Only capture text when not inside a tag
146 int pos = 0;
147 while (ch != '<' && ch != '>' && !n_gui_is_eof(tokenizer)) {
148 if (pos < N_GUI_MAX_TOKEN_SIZE - 1) {
149 token.value[pos++] = n_gui_next_char(tokenizer);
150 }
151 ch = n_gui_peek_char(tokenizer);
152 }
153 token.value[pos] = '\0';
154 token.type = N_GUI_TOKEN_TEXT;
155
156 // Handle text content if there is a valid length
157 if (pos > 0) {
158 return token;
159 }
160 }
161 }
162 // Default case for unknown or unsupported characters
163 n_gui_next_char(tokenizer); // consume character
164 return n_gui_next_token(tokenizer, inside_open_tag);
165}
166
172 switch (token.type) {
174 printf("N_GUI_TOKEN_TAG_OPEN: %s\n", token.value);
175 break;
177 printf("N_GUI_TOKEN_TAG_CLOSE: %s\n", token.value);
178 break;
180 printf("N_GUI_TOKEN_TAG_NAME: %s\n", token.value);
181 break;
183 printf("N_GUI_TOKEN_ATTR_NAME: %s\n", token.value);
184 break;
186 printf("N_GUI_TOKEN_ATTR_VALUE: %s\n", token.value);
187 break;
188 case N_GUI_TOKEN_TEXT:
189 printf("N_GUI_TOKEN_TEXT: %s\n", token.value);
190 break;
191 case N_GUI_TOKEN_EOF:
192 printf("N_GUI_TOKEN_EOF\n");
193 break;
194 }
195}
196
203N_GUI_DIALOG* n_gui_load_dialog(char* html, char* css) {
204 __n_assert(html, return NULL);
205 N_STR* nstr_html = file_to_nstr(html);
206 __n_assert(nstr_html, return NULL);
207
208 // no assert for css, html can have no style X-D
209 // __n_assert( html , return NULL );
210 N_STR* nstr_css = NULL;
211 if (css) {
212 nstr_css = file_to_nstr(css);
213 }
214
215 N_GUI_DIALOG* gui = NULL;
216 Malloc(gui, N_GUI_DIALOG, 1);
217 __n_assert(gui, free_nstr(&nstr_html); free_nstr(&nstr_css); return NULL);
218
219 N_GUI_TOKENIZER tokenizer;
220 n_gui_init_tokenizer(&tokenizer, _nstr(nstr_html));
221 N_GUI_TOKEN token;
222 bool inside_open_tag = false;
223 while ((token = n_gui_next_token(&tokenizer, &inside_open_tag)).type != N_GUI_TOKEN_EOF) {
224 switch (token.type) {
226 } break;
228 }
230 }
232 }
234 }
235 case N_GUI_TOKEN_TEXT: {
236 }
237 case N_GUI_TOKEN_EOF: {
238 }
239 }
240 }
241
242 free_nstr(&nstr_html);
243 free_nstr(&nstr_css);
244
245 return NULL;
246}
#define Malloc(__ptr, __struct, __size)
Malloc Handler to get errors and set to 0.
Definition n_common.h:185
#define __n_assert(__ptr, __ret)
macro to assert things
Definition n_common.h:256
#define _nstr(__PTR)
N_STR or "NULL" string for logging purposes.
Definition n_common.h:180
#define N_ENUM_DEFINE(MACRO_DEFINITION, enum_name)
Macro to define an N_ENUM.
Definition n_enum.h:144
char value[1024]
token content
Definition n_gui.h:118
size_t type
type of token
Definition n_gui.h:116
size_t position
position in the input text
Definition n_gui.h:126
const char * input
pointer to the input text
Definition n_gui.h:124
__N_GUI_TOKEN
Network codes declaration.
Definition n_gui.h:48
char n_gui_next_char(N_GUI_TOKENIZER *tokenizer)
Get next character from input.
Definition n_gui.c:34
void n_gui_print_token(N_GUI_TOKEN token)
Function to print a token (for debugging purposes)
Definition n_gui.c:171
int n_gui_is_eof(N_GUI_TOKENIZER *tokenizer)
 
Definition n_gui.c:52
char n_gui_peek_char(N_GUI_TOKENIZER *tokenizer)
Peek at next character without advancing the position.
Definition n_gui.c:43
N_GUI_DIALOG * n_gui_load_dialog(char *html, char *css)
Load a html + css file into a N_GUI_DIALOG.
Definition n_gui.c:203
#define N_GUI_MAX_TOKEN_SIZE
maximum size of a single token content
Definition n_gui.h:27
void n_gui_init_tokenizer(N_GUI_TOKENIZER *tokenizer, const char *input)
Initialize tokenizer.
Definition n_gui.c:24
N_GUI_TOKEN n_gui_next_token(N_GUI_TOKENIZER *tokenizer, bool *inside_open_tag)
Read next N_GUI_TOKEN from input.
Definition n_gui.c:62
@ N_GUI_TOKEN_TAG_CLOSE
Definition n_gui.h:48
@ N_GUI_TOKEN_TAG_OPEN
Definition n_gui.h:48
@ N_GUI_TOKEN_TAG_NAME
Definition n_gui.h:48
@ N_GUI_TOKEN_ATTR_NAME
Definition n_gui.h:48
@ N_GUI_TOKEN_EOF
Definition n_gui.h:48
@ N_GUI_TOKEN_ATTR_VALUE
Definition n_gui.h:48
@ N_GUI_TOKEN_TEXT
Definition n_gui.h:48
structure of a N_GUI_DIALOG
Definition n_gui.h:106
structure of a N_GUI_TOKENIZER token
Definition n_gui.h:114
structure of a N_GUI_DIALOG tokenizer
Definition n_gui.h:122
#define free_nstr(__ptr)
free a N_STR structure and set the pointer to NULL
Definition n_str.h:176
N_STR * file_to_nstr(char *filename)
Load a whole file into a N_STR.
Definition n_str.c:260
A box including a string and his lenght.
Definition n_str.h:39
Common headers and low-level functions & define.
N_ENUM_N_GUI_TOKEN
N_GUI context codes.
Definition n_gui.c:15
GUI headers.
Generic log system.
N_STR and string function declaration.