Inline code spans
This commit is contained in:
26
src/include/inlines.h
Normal file
26
src/include/inlines.h
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
/*
|
||||||
|
ncdg - A program to help generate natechoe.dev
|
||||||
|
Copyright (C) 2022 Nate Choe (natechoe9@gmail.com)
|
||||||
|
|
||||||
|
This program is free software: you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU General Public License as published by
|
||||||
|
the Free Software Foundation, either version 3 of the License, or
|
||||||
|
(at your option) any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU General Public License
|
||||||
|
along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
#ifndef HAVE_INLINES
|
||||||
|
#define HAVE_INLINES
|
||||||
|
|
||||||
|
#include <stdio.h>
|
||||||
|
|
||||||
|
void writeline(char *data, FILE *out);
|
||||||
|
void writedata(char *data, size_t len, FILE *out);
|
||||||
|
|
||||||
|
#endif
|
||||||
87
src/inlines.c
Normal file
87
src/inlines.c
Normal file
@@ -0,0 +1,87 @@
|
|||||||
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <inlines.h>
|
||||||
|
|
||||||
|
static const char *punctuation = "!\"#$%&'()*+,-./:;<=>?@[\\]^_`{|}~";
|
||||||
|
struct escape {
|
||||||
|
char c;
|
||||||
|
char *code;
|
||||||
|
};
|
||||||
|
struct escape escapes[] = {
|
||||||
|
{'<', "<"},
|
||||||
|
{'>', ">"},
|
||||||
|
{'&', "&"},
|
||||||
|
};
|
||||||
|
|
||||||
|
static int writecodespan(char *data, int i, size_t len, FILE *out);
|
||||||
|
static void writeescaped(char *data, size_t len, FILE *out);
|
||||||
|
static void writechescape(char c, FILE *out);
|
||||||
|
|
||||||
|
void writeline(char *data, FILE *out) {
|
||||||
|
writedata(data, strlen(data), out);
|
||||||
|
}
|
||||||
|
|
||||||
|
void writedata(char *data, size_t len, FILE *out) {
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < len; ++i) {
|
||||||
|
int newi;
|
||||||
|
if ((newi = writecodespan(data, i, len, out)) >= 0)
|
||||||
|
goto special;
|
||||||
|
if (data[i] == '\\') {
|
||||||
|
if (strchr(punctuation, data[i + 1]) == NULL)
|
||||||
|
writechescape('\\', out);
|
||||||
|
++i;
|
||||||
|
}
|
||||||
|
writechescape(data[i], out);
|
||||||
|
continue;
|
||||||
|
special:
|
||||||
|
i = newi - 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static int writecodespan(char *data, int i, size_t len, FILE *out) {
|
||||||
|
int ticklen;
|
||||||
|
int start, end;
|
||||||
|
|
||||||
|
if (data[i] != '`')
|
||||||
|
return -1;
|
||||||
|
for (ticklen = 0; data[i + ticklen] == '`'; ++ticklen) ;
|
||||||
|
|
||||||
|
start = i + ticklen;
|
||||||
|
for (end = start; end < len; ++end) {
|
||||||
|
int thislen;
|
||||||
|
if (data[end] != '`')
|
||||||
|
continue;
|
||||||
|
for (thislen = 0; data[end + thislen] == '`'; ++thislen);
|
||||||
|
if (ticklen == thislen)
|
||||||
|
break;
|
||||||
|
end += thislen - 1;
|
||||||
|
}
|
||||||
|
if (end >= len) {
|
||||||
|
for (i = 0; i < ticklen; ++i)
|
||||||
|
fputc('`', out);
|
||||||
|
return start + ticklen;
|
||||||
|
}
|
||||||
|
|
||||||
|
fputs("<code>", out);
|
||||||
|
writeescaped(data + start, end - start, out);
|
||||||
|
fputs("</code>", out);
|
||||||
|
return end + ticklen;
|
||||||
|
}
|
||||||
|
|
||||||
|
static void writeescaped(char *data, size_t len, FILE *out) {
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < len; ++i)
|
||||||
|
writechescape(data[i], out);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void writechescape(char c, FILE *out) {
|
||||||
|
int i;
|
||||||
|
for (i = 0; i < sizeof escapes / sizeof *escapes; ++i) {
|
||||||
|
if (escapes[i].c == c) {
|
||||||
|
fputs(escapes[i].code, out);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
fputc(c, out);
|
||||||
|
}
|
||||||
@@ -23,6 +23,7 @@
|
|||||||
#include <io.h>
|
#include <io.h>
|
||||||
#include <util.h>
|
#include <util.h>
|
||||||
#include <mdutil.h>
|
#include <mdutil.h>
|
||||||
|
#include <inlines.h>
|
||||||
#include <template.h>
|
#include <template.h>
|
||||||
|
|
||||||
struct parsestate {
|
struct parsestate {
|
||||||
@@ -80,12 +81,10 @@ static int parseline(char *line, struct parsestate *currstate, FILE *out) {
|
|||||||
type.data.intensity >=
|
type.data.intensity >=
|
||||||
currstate->intensity) {
|
currstate->intensity) {
|
||||||
currstate->prev.type = EMPTY;
|
currstate->prev.type = EMPTY;
|
||||||
fputs("</code>", out);
|
fputs("</code></pre>", out);
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
if (!currstate->isfirst)
|
fprintf(out, "%s\n", line);
|
||||||
fputs("<br>", out);
|
|
||||||
fputs(line, out);
|
|
||||||
currstate->isfirst = 0;
|
currstate->isfirst = 0;
|
||||||
return 0;
|
return 0;
|
||||||
case HTMLCONCRETE:
|
case HTMLCONCRETE:
|
||||||
@@ -124,7 +123,7 @@ static int parseline(char *line, struct parsestate *currstate, FILE *out) {
|
|||||||
return 1;
|
return 1;
|
||||||
currstate->prev.type = EMPTY;
|
currstate->prev.type = EMPTY;
|
||||||
fputs("<h1>", out);
|
fputs("<h1>", out);
|
||||||
fwrite(currstate->para->data, 1, currstate->para->len, out);
|
writedata(currstate->para->data, currstate->para->len, out);
|
||||||
fputs("</h1>", out);
|
fputs("</h1>", out);
|
||||||
resetstring(currstate->para);
|
resetstring(currstate->para);
|
||||||
break;
|
break;
|
||||||
@@ -133,7 +132,7 @@ static int parseline(char *line, struct parsestate *currstate, FILE *out) {
|
|||||||
goto hr;
|
goto hr;
|
||||||
currstate->prev.type = EMPTY;
|
currstate->prev.type = EMPTY;
|
||||||
fputs("<h2>", out);
|
fputs("<h2>", out);
|
||||||
fwrite(currstate->para->data, 1, currstate->para->len, out);
|
writedata(currstate->para->data, currstate->para->len, out);
|
||||||
fputs("</h2>", out);
|
fputs("</h2>", out);
|
||||||
resetstring(currstate->para);
|
resetstring(currstate->para);
|
||||||
break;
|
break;
|
||||||
@@ -169,7 +168,7 @@ static int parseline(char *line, struct parsestate *currstate, FILE *out) {
|
|||||||
* as to not include the wrong tags.
|
* as to not include the wrong tags.
|
||||||
* */
|
* */
|
||||||
case FENCECODE:
|
case FENCECODE:
|
||||||
fputs("<code class='block'>", out);
|
fputs("<pre><code>", out);
|
||||||
currstate->prev.type = FENCECODE;
|
currstate->prev.type = FENCECODE;
|
||||||
currstate->isfirst = 1;
|
currstate->isfirst = 1;
|
||||||
currstate->intensity = type.data.intensity;
|
currstate->intensity = type.data.intensity;
|
||||||
@@ -186,10 +185,9 @@ static int parseline(char *line, struct parsestate *currstate, FILE *out) {
|
|||||||
break;
|
break;
|
||||||
case HEADER:
|
case HEADER:
|
||||||
endpara(currstate, out);
|
endpara(currstate, out);
|
||||||
fprintf(out, "<h%d>%s</h%d>",
|
fprintf(out, "<h%d>", type.data.intensity);
|
||||||
type.data.intensity,
|
writeline(realcontent(line, &type), out);
|
||||||
realcontent(line, &type),
|
fprintf(out, "</h%d>", type.data.intensity);
|
||||||
type.data.intensity);
|
|
||||||
currstate->prev.type = EMPTY;
|
currstate->prev.type = EMPTY;
|
||||||
break;
|
break;
|
||||||
case HTMLCONCRETE:
|
case HTMLCONCRETE:
|
||||||
@@ -225,7 +223,7 @@ static int endpara(struct parsestate *state, FILE *out) {
|
|||||||
return 0;
|
return 0;
|
||||||
case PLAIN:
|
case PLAIN:
|
||||||
fputs("<p>", out);
|
fputs("<p>", out);
|
||||||
fwrite(state->para->data, 1, state->para->len, out);
|
writedata(state->para->data, state->para->len, out);
|
||||||
fputs("</p>", out);
|
fputs("</p>", out);
|
||||||
resetstring(state->para);
|
resetstring(state->para);
|
||||||
return 0;
|
return 0;
|
||||||
|
|||||||
Reference in New Issue
Block a user