new site generation foundation in place, now need the meta parser and include directives

master
Allen Webster 2017-07-15 16:15:03 -04:00
parent ff0a1f3bc3
commit 64c19f4f12
5 changed files with 185 additions and 148 deletions

View File

@ -18,15 +18,8 @@ struct Enriched_Text{
internal Enriched_Text
load_enriched_text(char *directory, char *filename){
Enriched_Text result = {0};
char space[256];
String fname = make_fixed_width_string(space);
append(&fname, directory);
append(&fname, "/");
append(&fname, filename);
terminate_with_null(&fname);
result.source = file_dump(fname.str);
char *fname = fm_str(directory, "/", filename);
result.source = file_dump(fname);
return(result);
}
@ -35,6 +28,7 @@ load_enriched_text(char *directory, char *filename){
enum{
Doc_Root,
Doc_Section,
Doc_Error,
Doc_Todo,
Doc_Include,
Doc_DocList,
@ -51,8 +45,6 @@ enum{
Doc_Video,
Doc_BeginParagraph,
Doc_EndParagraph,
Doc_BeginSection,
Doc_EndSection,
Doc_BeginList,
Doc_EndList,
Doc_BeginItem,
@ -86,7 +78,7 @@ struct Document_Item{
Document_Item *last_child;
String name;
String id;
i32 show_title;
b32 show_title;
} section;
struct{
@ -254,36 +246,6 @@ add_image_instantiation(Basic_List *list, i32 w, i32 h){
instantiation->h = h;
}
internal void
set_section_name(Document_Item *item, char *name, i32 show_title){
i32 name_len = str_size(name);
item->section.name = make_string_cap(fm_push_array(char, name_len+1), 0, name_len+1);
fm_align();
append(&item->section.name, name);
item->section.show_title = show_title;
}
internal void
set_section_id(Document_Item *item, char *id){
i32 id_len = str_size(id);
item->section.id = make_string_cap(fm_push_array(char, id_len+1), 0, id_len+1);
fm_align();
append(&item->section.id, id);
}
internal void
begin_document_description(Abstract_Item *doc, char *title, i32 show_title){
*doc = null_abstract_item;
doc->item_type = ItemType_Document;
doc->root_item = fm_push_array(Document_Item, 1);
*doc->root_item = null_document_item;
doc->section_stack[doc->section_top] = doc->root_item;
doc->root_item->type = Doc_Root;
set_section_name(doc->root_item, title, show_title);
}
internal Abstract_Item*
add_generic_file(Document_System *system, char *source_file, char *extension, char *name){
Abstract_Item *item = create_item(&system->file_list, name);
@ -320,8 +282,38 @@ add_image_description(Document_System *system, char *source_file, char *extensio
return(item);
}
internal void
set_section_name(Document_Item *item, char *name, b32 show_title){
i32 name_len = str_size(name);
item->section.name = str_alloc(name_len + 1);
fm_align();
append(&item->section.name, name);
item->section.show_title = show_title;
}
internal void
set_section_id(Document_Item *item, char *id){
i32 id_len = str_size(id);
item->section.id = str_alloc(id_len + 1);
fm_align();
append(&item->section.id, id);
}
internal void
begin_document_description(Abstract_Item *doc, char *title, b32 show_title){
*doc = null_abstract_item;
doc->item_type = ItemType_Document;
doc->root_item = fm_push_array(Document_Item, 1);
*doc->root_item = null_document_item;
doc->section_stack[doc->section_top] = doc->root_item;
doc->root_item->type = Doc_Root;
set_section_name(doc->root_item, title, show_title);
}
internal Abstract_Item*
begin_document_description(Document_System *system, char *title, char *name, i32 show_title){
begin_document_description(Document_System *system, char *title, char *name, b32 show_title){
Abstract_Item *item = create_item(&system->doc_list, name);
if (item){
begin_document_description(item, title, show_title);
@ -359,7 +351,7 @@ begin_section(Abstract_Item *item, char *title, char *id){
section->type = Doc_Section;
set_section_name(section, title, 1);
set_section_name(section, title, true);
if (id != 0){
set_section_id(section, id);
}
@ -373,6 +365,29 @@ end_section(Abstract_Item *doc){
--doc->section_top;
}
internal void
add_error(Abstract_Item *doc, String text){
Assert(doc->section_top + 1 < ArrayCount(doc->section_stack));
Document_Item *parent = doc->section_stack[doc->section_top];
Document_Item *item = fm_push_array(Document_Item, 1);
*item = null_document_item;
item->type = Doc_Error;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
}
internal void
report_error_missing_body(Abstract_Item *doc, String command_body){
char space[512];
String error_string = make_fixed_width_string(space);
append(&error_string, "missing body for ");
append(&error_string, command_body);
add_error(doc, error_string);
}
internal void
add_todo(Abstract_Item *doc){
Assert(doc->section_top + 1 < ArrayCount(doc->section_stack));
@ -455,6 +470,7 @@ add_plain_old_text(Abstract_Item *doc, String text){
*item = null_document_item;
item->type = Doc_PlainOldText;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
@ -491,6 +507,7 @@ add_begin_style(Abstract_Item *doc, String text){
*item = null_document_item;
item->type = Doc_BeginStyle;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
@ -515,6 +532,7 @@ add_document_link(Abstract_Item *doc, String text){
*item = null_document_item;
item->type = Doc_DocumentLink;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
@ -528,6 +546,7 @@ add_begin_link(Abstract_Item *doc, String text){
*item = null_document_item;
item->type = Doc_BeginLink;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
@ -552,9 +571,11 @@ add_image(Abstract_Item *doc, String text, String extra_text){
*item = null_document_item;
item->type = Doc_Image;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
if (extra_text.size > 0){
item->string.string2 = str_alloc(extra_text.size);
fm_align();
copy(&item->string.string2, extra_text);
}
@ -569,6 +590,7 @@ add_video(Abstract_Item *doc, String text){
*item = null_document_item;
item->type = Doc_Video;
item->string.string = str_alloc(text.size);
fm_align();
copy(&item->string.string, text);
append_child(parent, item);
@ -596,30 +618,6 @@ add_end_paragraph(Abstract_Item *doc){
append_child(parent, item);
}
internal void
add_begin_section(Abstract_Item *doc, String text){
Assert(doc->section_top + 1 < ArrayCount(doc->section_stack));
Document_Item *parent = doc->section_stack[doc->section_top];
Document_Item *item = fm_push_array(Document_Item, 1);
*item = null_document_item;
item->type = Doc_BeginSection;
item->string.string = str_alloc(text.size);
copy(&item->string.string, text);
append_child(parent, item);
}
internal void
add_end_section(Abstract_Item *doc){
Assert(doc->section_top + 1 < ArrayCount(doc->section_stack));
Document_Item *parent = doc->section_stack[doc->section_top];
Document_Item *item = fm_push_array(Document_Item, 1);
*item = null_document_item;
item->type = Doc_EndSection;
append_child(parent, item);
}
internal void
add_begin_list(Abstract_Item *doc){
Assert(doc->section_top + 1 < ArrayCount(doc->section_stack));
@ -682,6 +680,8 @@ enum Command_Types{
Cmd_Section,
Cmd_EndSection,
Cmd_Version,
Cmd_TableOfContents,
Cmd_Todo,
// never below this
Cmd_COUNT,
};
@ -708,6 +708,8 @@ get_enriched_commands(){
enriched_commands_global_array[Cmd_Section] = make_lit_string("SECTION");
enriched_commands_global_array[Cmd_EndSection] = make_lit_string("END_SECTION");
enriched_commands_global_array[Cmd_Version] = make_lit_string("VERSION");
enriched_commands_global_array[Cmd_TableOfContents] = make_lit_string("TABLE_OF_CONTENTS");
enriched_commands_global_array[Cmd_Todo] = make_lit_string("TODO");
}
return(enriched_commands_global_array);
}
@ -765,12 +767,14 @@ extract_command_body(String l, i32 *i_in_out, String *body_text_out){
internal Abstract_Item*
make_document_from_text(Document_System *doc_system, char *title, char *name, Enriched_Text *text){
String source = text->source;
Abstract_Item *doc = begin_document_description(doc_system, title, name, 0);
Abstract_Item *doc = begin_document_description(doc_system, title, name, false);
for (String line = get_first_double_line(source);
line.str;
line = get_next_double_line(source, line)){
String l = skip_chop_whitespace(line);
if (l.size == 0) continue;
add_begin_paragraph(doc);
i32 start = 0, i = 0;
@ -819,7 +823,7 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_begin_style(doc, body_text);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
@ -837,7 +841,7 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_document_link(doc, body_text);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
@ -869,7 +873,7 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_begin_link(doc, body_text);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
@ -888,7 +892,7 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_image(doc, body_text, size_parameter);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
@ -900,7 +904,7 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_video(doc, body_text);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
@ -911,16 +915,25 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
if (has_body){
String extra_text = {0};
extract_command_body(l, &i, &extra_text);
add_begin_section(doc, body_text);
String title = str_alloc(body_text.size + 1);
copy(&title, body_text);
terminate_with_null(&title);
String id = str_alloc(extra_text.size + 1);
copy(&id, extra_text);
terminate_with_null(&id);
begin_section(doc, title.str, id.str);
}
else{
// TODO(allen):
report_error_missing_body(doc, command_string);
}
}break;
case Cmd_EndSection:
{
add_end_section(doc);
end_section(doc);
}break;
case Cmd_Version:
@ -928,14 +941,34 @@ make_document_from_text(Document_System *doc_system, char *title, char *name, En
add_version(doc);
}break;
case Cmd_TableOfContents:
{
add_table_of_contents(doc);
}break;
case Cmd_Todo:
{
add_todo(doc);
}break;
default:
{
// TODO(allen):
char space[512];
String error = make_fixed_width_string(space);
append(&error, "unrecognized command ");
append(&error, command_string);
add_error(doc, error);
}break;
}
start = i;
}
}
if (start != i){
add_plain_old_text(doc, substr(l, start, i - start));
}
add_end_paragraph(doc);
}
@ -1029,14 +1062,24 @@ append_section_number(String *out, Section_Counter *section_counter){
append_section_number_reduced(out, section_counter, 0);
}
#define ERROR_HTML_START "<span style='color:#F00'>! generator error: "
#define ERROR_HTML_END " !</span>"
internal void
output_error(String *out, String error){
append(out, ERROR_HTML_START);
append(out, error);
append(out, ERROR_HTML_END);
fprintf(stdout, "error: %.*s\n", error.size, error.str);
}
internal void
report_error_html_missing_body(String *out, String command_name){
#define STR_START "<span style='color:#F00'>! Doc generator error: missing body for "
#define STR_SLOW " !</span>"
append(out, STR_START);
append(out, command_name);
append(out, STR_SLOW);
fprintf(stdout, "error: missing body for %.*s\n", command_name.size, command_name.str);
char space[512];
String str = make_fixed_width_string(space);
append(&str, "missing body for ");
append(&str, command_name);
output_error(out, str);
}
internal void
@ -1074,11 +1117,10 @@ html_render_section_header(String *out, String section_name, String section_id,
#define HTML_WIDTH 800
internal void
output_plain_old_text(String *out, char *text, u32 length){
String l = make_string(text, length);
output_plain_old_text(String *out, String l){
u32 start = 0;
u32 i = 0;
for (; i < length; ++i){
for (; i < (u32)l.size; ++i){
char ch = l.str[i];
switch (ch){
case '<':
@ -1102,13 +1144,13 @@ output_plain_old_text(String *out, char *text, u32 length){
}
internal void
output_begin_style(String *out, char *name, u32 length){
String l = make_string(name, length);
output_begin_style(String *out, String l){
if (match(l, "code")){
append(out, "<span style='"HTML_CODE_STYLE"'>");
}
else{
fprintf(stdout, "error: unrecognized style\n");
append(out, "<span>");
}
}
@ -1118,8 +1160,7 @@ output_end_style(String *out){
}
internal void
output_document_link(String *out, char *name, u32 length){
String l = make_string(name, length);
output_document_link(String *out, String l){
append(out, "<a href='#");
append(out, l);
append(out, "_doc'>");
@ -1128,8 +1169,7 @@ output_document_link(String *out, char *name, u32 length){
}
internal void
output_begin_link(Document_System *doc_system, String *out, char *name, u32 length){
String l = make_string(name, length);
output_begin_link(Document_System *doc_system, String *out, String l){
append(out, "<a ");
if (l.str[0] == '!'){
append(out, "target='_blank' ");
@ -1162,10 +1202,7 @@ output_end_link(String *out){
}
internal void
output_image(Document_System *doc_system, String *out, char *name, u32 length, char *name2, u32 length2){
String l = make_string(name, length);
String l2 = make_string(name2, length2);
output_image(Document_System *doc_system, String *out, String l, String l2){
i32 pixel_height = 10;
i32 pixel_width = HTML_WIDTH;
@ -1206,9 +1243,7 @@ output_image(Document_System *doc_system, String *out, char *name, u32 length, c
}
internal void
output_video(String *out, char *name, u32 length){
String l = make_string(name, length);
output_video(String *out, String l){
if (match_part_sc(l, "youtube:")){
i32 pixel_width = HTML_WIDTH;
i32 pixel_height = (i32)(pixel_width * 0.5625f);
@ -1219,13 +1254,16 @@ output_video(String *out, char *name, u32 length){
append_int_to_str(out, pixel_width);
append(out, "' height='");
append_int_to_str(out, pixel_height);
append(out, "' src='");
append(out, "' src='https://www.youtube.com/embed/");
append(out, youtube_str);
append(out, "' allowfullscreen> </iframe>");
}
else{
append(out, "<span style='color:#F00'>! Doc generator error: unrecognized video type !</span>");
fprintf(stdout, "error: unrecognized video type %.*s\n", l.size, l.str);
char space[512];
String str = make_fixed_width_string(space);
append(&str, "unrecognized video type ");
append(&str, l);
output_error(out, str);
}
}
@ -1240,9 +1278,8 @@ output_end_paragraph(String *out){
}
internal void
output_begin_section(String *out, Section_Counter *section_counter, char *name, u32 length){
String l = make_string(name, length);
html_render_section_header(out, l, null_string, section_counter);
output_begin_section(String *out, Section_Counter *section_counter, String l, String l2){
html_render_section_header(out, l, l2, section_counter);
++section_counter->nest_level;
section_counter->list_item_counter = 0;
}
@ -1254,8 +1291,7 @@ output_end_section(String *out, Section_Counter *section_counter){
++section_counter->counter[section_counter->nest_level];
}
else{
append(out, "<span style='color:#F00'>! Doc generator error: unmatched section end !</span>");
fprintf(stdout, "error: unmatched section end\n");
output_error(out, make_lit_string("unmatched section end"));
}
}
@ -1302,7 +1338,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
for (; i < l.size; ++i){
char ch = l.str[i];
if (ch == '\\'){
output_plain_old_text(out, l.str + start, i - start);
output_plain_old_text(out, substr(l, start, i - start));
i32 command_start = i + 1;
i32 command_end = command_start;
@ -1338,7 +1374,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
String body_text = {0};
b32 has_body = extract_command_body(l, &i, &body_text);
if (has_body){
output_begin_style(out, body_text.str, body_text.size);
output_begin_style(out, body_text);
}
else{
report_error_html_missing_body(out, command_string);
@ -1356,7 +1392,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
String body_text = {0};
b32 has_body = extract_command_body(l, &i, &body_text);
if (has_body){
output_document_link(out, body_text.str, body_text.size);
output_document_link(out, body_text);
}
else{
report_error_html_missing_body(out, command_string);
@ -1388,7 +1424,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
String body_text = {0};
b32 has_body = extract_command_body(l, &i, &body_text);
if (has_body){
output_begin_link(doc_system, out, body_text.str, body_text.size);
output_begin_link(doc_system, out, body_text);
}
else{
report_error_html_missing_body(out, command_string);
@ -1407,7 +1443,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
if (has_body){
String size_parameter = {0};
extract_command_body(l, &i, &size_parameter);
output_image(doc_system, out, body_text.str, body_text.size, size_parameter.str, size_parameter.size);
output_image(doc_system, out, body_text, size_parameter);
}
else{
report_error_html_missing_body(out, command_string);
@ -1419,7 +1455,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
String body_text = {0};
b32 has_body = extract_command_body(l, &i, &body_text);
if (has_body){
output_video(out, body_text.str, body_text.size);
output_video(out, body_text);
}
else{
report_error_html_missing_body(out, command_string);
@ -1433,7 +1469,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
if (has_body){
String extra_text = {0};
extract_command_body(l, &i, &extra_text);
output_begin_section(out, section_counter, body_text.str, body_text.size);
output_begin_section(out, section_counter, body_text, extra_text);
}
else{
report_error_html_missing_body(out, command_string);
@ -1450,10 +1486,19 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
append(out, VERSION);
}break;
case Cmd_TableOfContents:
{
String str = make_lit_string("Cmd_TableOfContents does not work in this system");
output_error(out, str);
}break;
default:
{
append(out, "<span style='color:#F00'>! Doc generator error: unrecognized command !</span>");
fprintf(stdout, "error: unrecognized command %.*s\n", command_string.size, command_string.str);
char space[512];
String str = make_fixed_width_string(space);
append(&str, "unrecognized command ");
append(&str, command_string);
output_error(out, str);
}break;
}
@ -1462,7 +1507,7 @@ write_enriched_text_html(String *out, Enriched_Text *text, Document_System *doc_
}
if (start != i){
output_plain_old_text(out, l.str + start, i - start);
output_plain_old_text(out, substr(l, start, i - start));
}
output_end_paragraph(out);
@ -2162,6 +2207,13 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
}
}break;
case Doc_Error:
{
if (head){
output_error(out, item->string.string);
}
}break;
case Doc_Todo:
{
if (head){
@ -2272,7 +2324,7 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
case Doc_PlainOldText:
{
if (head){
output_plain_old_text(out, item->string.string.str, item->string.string.size);
output_plain_old_text(out, item->string.string);
}
}break;
@ -2286,7 +2338,7 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
case Doc_BeginStyle:
{
if (head){
output_begin_style(out, item->string.string.str, item->string.string.size);
output_begin_style(out, item->string.string);
}
}break;
@ -2300,14 +2352,14 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
case Doc_DocumentLink:
{
if (head){
output_document_link(out, item->string.string.str, item->string.string.size);
output_document_link(out, item->string.string);
}
}break;
case Doc_BeginLink:
{
if (head){
output_begin_link(doc_system, out, item->string.string.str, item->string.string.size);
output_begin_link(doc_system, out, item->string.string);
}
}break;
@ -2321,14 +2373,14 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
case Doc_Image:
{
if (head){
output_image(doc_system, out, item->string.string.str, item->string.string.size, item->string.string2.str, item->string.string2.size);
output_image(doc_system, out, item->string.string, item->string.string2);
}
}break;
case Doc_Video:
{
if (head){
output_video(out, item->string.string.str, item->string.string.size);
output_video(out, item->string.string);
}
}break;
@ -2346,21 +2398,6 @@ doc_item_html(String *out, Document_System *doc_system, Used_Links *used_links,
}
}break;
// HACK(allen): There is also a Doc_Section type item where the section is actually a parent to the children and begin/end are handled by the one item. That should be the only type.
case Doc_BeginSection:
{
if (head){
output_begin_section(out, section_counter, item->string.string.str, item->string.string.size);
}
}break;
case Doc_EndSection:
{
if (head){
output_end_section(out, section_counter);
}
}break;
case Doc_BeginList:
{
if (head){

View File

@ -109,7 +109,7 @@ generate_4coder_docs(Document_System *doc_system, char *code_directory, char *sr
*lexer_introduction = load_enriched_text(src_directory, "lexer_introduction.txt");
// NOTE(allen): Put together the abstract document
Abstract_Item *doc = begin_document_description(doc_system, "4coder API Docs", "custom_docs", 1);
Abstract_Item *doc = begin_document_description(doc_system, "4coder API Docs", "custom_docs", true);
add_table_of_contents(doc);

View File

@ -38,7 +38,7 @@
\END_SECTION
\END_SECTION
\SECTION{String Library}
\SECTION{String Library}{string_library}
\SECTION{String Library Intro}
\TODO
\END_SECTION
@ -52,7 +52,7 @@
\END_SECTION
\END_SECTION
\SECTION{Lexer Library}
\SECTION{Lexer Library}{lexer_library}
\SECTION{Lexer Intro}
\INCLUDE{lexer_introduction.txt}
\END_SECTION

View File

@ -5,19 +5,19 @@
Getting started with 4coder and navigating your files:
\VIDEO{youtube:https://www.youtube.com/embed/h5cbOcnSrcc}
\VIDEO{youtube:h5cbOcnSrcc}
Setting up and navigating your project with 4coder:
\VIDEO{youtube:https://www.youtube.com/embed/glPEpaT6GH0}
\VIDEO{youtube:glPEpaT6GH0}
Extending your project with a project.4coder file:
\VIDEO{youtube:https://www.youtube.com/embed/iZLtS3IoatE}
\VIDEO{youtube:iZLtS3IoatE}
Using customizable keywords in the 4coder custom API:
\VIDEO{youtube:https://www.youtube.com/watch?v=qoEvc4uC9Uw}
\VIDEO{youtube:qoEvc4uC9Uw}
More tutorials coming soon.

View File

@ -1,5 +1,5 @@
1
0
101
102