summaryrefslogtreecommitdiffstats
path: root/lexer/theme-lexer.l
blob: a540c22912aec3b741f2965eba73559c187f5454 (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
%option noyywrap nounput
%option bison-locations

%{
#include <stdio.h>


#include "lexer/theme-parser.h"

%}
%{

#define YY_USER_ACTION {\
    yylloc->last_column+= yyleng;\
}
#define YY_LLOC_START {\
    yylloc->first_line = yylloc->last_line; yylloc->first_column = yylloc->last_column;\
}
%}
WHITESPACE [ \t]
WORD       [_\-a-zA-Z0-9]+
STRING     [ \t_\-a-zA-Z0-9]+
HEX        [0-9a-fA-F]
NUMBER     [0-9]
%%

%{
YY_LLOC_START
%}

"//"            {
    int c;
    while ((c = input()) != EOF){
        if (c == '\n') {
            yylloc->last_column = 1;
            yylloc->last_line ++;
            break;
        }
        yylloc->last_column++;
    }
    YY_LLOC_START
}
"/*"            {
    int c = 0, p;
    int nesting_depth = 1;
    while (nesting_depth) {
        p = c;
        c = input();
        switch (c) {
        case '*': yylloc->last_column++; if (p == '/') { c = 0; nesting_depth++; } break;
        case '/': yylloc->last_column++; if (p == '*') { c = 0; nesting_depth--; } break;
        case '\n':  {
            yylloc->last_column = 1;
            yylloc->last_line ++;
            break;
        }
        case EOF: nesting_depth = 0; break;
        default:
            yylloc->last_column++;
        ;
        }
    }
    YY_LLOC_START
}

"\{"                { return BOPEN;}
"\}"                { return BCLOSE;}
":"                 { return PSEP; }
";"                 { return PCLOSE;}
"."                 { return NSEP; }
"#"                 { return NAME_PREFIX;}
(true|false)        { yylval->bval= g_strcmp0(yytext, "true") == 0; return T_BOOLEAN;}
{NUMBER}+           { yylval->ival = (int)g_ascii_strtoll(yytext, NULL, 10); return T_INT;}
{NUMBER}+\.{NUMBER}+   { yylval->fval = g_ascii_strtod(yytext, NULL); return T_DOUBLE;}
@{WORD}             { yylval->sval = g_strdup(yytext); return CLASS_NAME; }
{WORD}              { yylval->sval = g_strdup(yytext); return N_STRING;}
{WHITESPACE}	; // ignore all whitespace
\"{STRING}\"        { yytext[yyleng-1] = '\0'; yylval->sval = g_strdup(&yytext[1]); return T_STRING;}

#{HEX}{8}       {
    union {  unsigned int val; struct { unsigned char b,g,r,a;};} val;
    val.val = (unsigned int)strtoull ( &yytext[1], NULL, 16);
    yylval->colorval.alpha = val.a/255.0;
    yylval->colorval.red   = val.r/255.0;
    yylval->colorval.green = val.g/255.0;
    yylval->colorval.blue  = val.b/255.0;
    return T_COLOR;
}
#{HEX}{6}       {
    union {  unsigned int val; struct { unsigned char b,g,r,a;};} val;
    val.val = (unsigned int)g_ascii_strtoull ( &yytext[1], NULL, 16);
    yylval->colorval.alpha = 1.0;
    yylval->colorval.red   = val.r/255.0;
    yylval->colorval.green = val.g/255.0;
    yylval->colorval.blue  = val.b/255.0;
    return T_COLOR;
}
rgba\({NUMBER}{1,3},{NUMBER}{1,3},{NUMBER}{1,3},[01](\.{NUMBER}+)?\) {
    char *endptr = &yytext[5];
    yylval->colorval.red = g_ascii_strtoull ( endptr, &endptr, 10);
    yylval->colorval.green= g_ascii_strtoull ( endptr+1, &endptr, 10);
    yylval->colorval.blue= g_ascii_strtoull ( endptr+1, &endptr, 10);
    yylval->colorval.alpha= g_ascii_strtod ( endptr+1, NULL);
    return T_COLOR;
}
rgb\({NUMBER}{1,3},{NUMBER}{1,3},{NUMBER}{1,3}\) {
    char *endptr = &yytext[4];
    yylval->colorval.red   = g_ascii_strtoull ( endptr, &endptr, 10);
    yylval->colorval.green = g_ascii_strtoull ( endptr+1, &endptr, 10);
    yylval->colorval.blue  = g_ascii_strtoull ( endptr+1, &endptr, 10);
    yylval->colorval.alpha = 1.0;
    return T_COLOR;
}
(\r\n|\n) {
        yylloc->last_column = 1;
        yylloc->last_line ++;
};

<*><<EOF>>  {
    yyterminate();
}
%%