/*
* Dominic Jonak (dom@cmu.edu)
* Autogen v1.8 (06/16/2010)
*
* Description: Website creation program, merges a content (source.txt)
* and layout (layout.html) file. Assumes very strict
* structure for both.
*
* Feel free to use the code, just don't remove this comment.
*
* Disclaimer: It's not finished so don't complain if it's not
* perfect. Don't expect any support either.
*/
#define _GNU_SOURCE
#include
#include
#include
#include
const int stripComments=1;/* whether comments should be stripped out or kept */
int numSections=0;
char **sectionNames=NULL;
char **sectionTexts=NULL;
void addSectionName(const char *s){
numSections++;
sectionNames = (char **)realloc(sectionNames,
numSections * sizeof(char *));
sectionNames[numSections-1] = strdup(s);
}
int numCategories=0;
char **categoryNames=NULL;
char **capCategoryNames=NULL;
void addCategoryName(const char *s){
numCategories++;
categoryNames = (char **)realloc(categoryNames,
numCategories * sizeof(char *));
categoryNames[numCategories-1] = strdup(s);
}
void makeCapCategoryNames(){
int i;
capCategoryNames = (char **)malloc(numCategories * sizeof(char *));
for(i=0;i", buf))break;
addSectionName(buf);
}
/* if the first section is the count, remove it */
if(numSections>1 && numSections-1 == atoi(sectionNames[0])){
sectionNames = sectionNames+1;
numSections--;
}
printf("Read %d sections:\n", numSections);
for(i=0;i0 && isspace(addedText[addedlen-1]))addedlen--;
ret = (char *)realloc(oldText, oldlen + addedlen + 2);
/* add a newline between concats */
/*if(oldlen)ret[oldlen++]='\n';*/
memcpy(ret+oldlen, addedText, addedlen);
ret[oldlen+addedlen]='\0';
return ret;
}
char *readLayoutSection(FILE *f){
char buf[1024];
char commentBuf[sizeof(buf)];
char *ret=NULL;
while(1){
if(!fgets(buf, sizeof(buf), f)){
if(feof(f))break;
fprintf(stderr, "Error reading layout section\n");
exit(-1);
}
/* check if this line is a comment */
if(1 == sscanf(buf, "", commentBuf)){
/* check if this comment signals the end of the current section */
if(-1 != getSectionIndex(commentBuf))break;
/* this is an internal comment, optionally strip it out */
if(stripComments)continue;
}
ret = myconcat(ret, buf);
}
return ret;
}
void readLayoutSections(FILE *f){
int i;
sectionTexts = (char **)malloc((numSections+1) * sizeof(char *));
for(i=0;i1 && numCategories-1 == atoi(categoryNames[0])){
categoryNames = categoryNames+1;
numCategories--;
}
makeCapCategoryNames();
printf("Read %d categories:\n", numCategories);
for(i=0;i=numColorSteps) i = numColorSteps;
fprintf(f, "%c", c);
}
void writeTitle(FILE *f, const char *title){
/* put this in to get a gradient effect */
#if 0
int len = strlen(title);
int k;
for(k=0;k0;k--)
buildFont(f, k, title[len-k]);
fprintf(f, "\n");
#else
fprintf(f, "%s\n", title);
#endif
printf("%s\n", title);
}
void writeCategories(FILE *f){
int i;
char linkHTML[256];
for(i=0;i%s
\n", capCategoryNames[i]);
}
}
void writeLink(FILE *f, char *link){
char linkname[256], linkURL[256];
if(2 != sscanf(link, "%s %s", linkURL, linkname)){
fprintf(stderr, "Error creating link from \"%s\"\n", link);
exit(-1);
}
/* support for multi-word link texts */
strcpy(linkname, strstr(link+strlen(linkURL), linkname));
fprintf(f, "%s\n", linkURL, linkname);
}
char *extractSectionName(char *data, char **rest){
int i=0;
*rest = NULL;
if(!data || '&' != data[0])return NULL;
data++;/* skip the '&' */
while(1){
/* advance to the end of the first token */
if( (data[i]) && !isspace(data[i]) ){
i++;
continue;
}
/* make sure it ends with a ';' */
if(';' != data[i-1])return NULL;
/* pull out and data after the token and save it in rest */
*rest = &data[i];
while( **rest && isspace(**rest) )(*rest)++;
while(**rest && isspace((*rest)[strlen(*rest)-1]))(*rest)[strlen(*rest)-1]='\0';
data[i-1] = '\0';
/* make sure it's a valid section */
if(strcasecmp("end", data) && -1 == getSectionIndex(data)){
data[i-1] = ';';
return NULL;
}
break;
}
return data;
}
void readPageSource(FILE *f){
char linebuf[1024];
char *sectionbuf;
char *restOfLine=NULL;
FILE *output=NULL;
char lastSection[sizeof(linebuf)];
int firstLineInSection=1;
lastSection[0]='\0';
if(!currentHTML){
fprintf(stderr, "Have no html file to write too...\n");
exit(-1);
}
output = fopen(currentHTML, "w");
if(!output){
fprintf(stderr, "Unable to write to \"%s\"\n", currentHTML);
exit(-1);
}
printf("%20s: ", currentHTML);
while(1){ /* read each line */
if(!fgets(linebuf, sizeof(linebuf), f)){
fprintf(stderr, "Error bad source for %s\n", currentHTML);
exit(-1);
}
/*
if(strlen(linebuf)== sizeof(linebuf)-1){
fprintf(stderr, "Buffer too small for %s\n", currentHTML);
exit(-1);
}
*/
if(linebuf[strlen(linebuf)-1] == '\n')
linebuf[strlen(linebuf)-1] = '\0';
if((sectionbuf = extractSectionName(linebuf, &restOfLine))){
/*fprintf(output, "\n", sectionbuf);*/
firstLineInSection=1;
if(!strcasecmp("end", sectionbuf)){
/* reached end */
/*printf("%s: Reached end\n", currentHTML);*/
fprintf(output, "%s\n", sectionTexts[numSections]);
break;
}else{
if(!strcasecmp(sectionbuf, "right"))
writeCategories(output);
else if(!strcasecmp(sectionbuf, "bottom") &&
strcasecmp(lastSection, "right")){
/*fprintf(output, "\n", "right");*/
fprintf(output, "%s\n", sectionTexts[getSectionIndex("right")]);
writeCategories(output);
}
/* insert the specified section */
/*printf("%s: Inserting section %s\n", currentHTML, sectionbuf);*/
/*fprintf(output, "\n", sectionbuf);*/
fprintf(output, "%s", sectionTexts[getSectionIndex(sectionbuf)]);
if(restOfLine)
fprintf(output, "%s", restOfLine);
strcpy(lastSection, sectionbuf);
}
}else{
/* not a comment, write this */
/*printf("%s/%s: Writing source \"%s\"\n", currentHTML, lastSection, linebuf);*/
if(!strcasecmp(lastSection, "bottom"))
writeLink(output, linebuf);
else if(!strcasecmp(lastSection, "top"))
writeTitle(output, linebuf);
else{
/* remove leading whitespace */
char *s = linebuf;
while(*s && isspace(*s))s++;
/* add a newline if appropriate */
if(firstLineInSection)
firstLineInSection=0;
else
fprintf(output, "\n");
fprintf(output, "%s", s);
}
}
} /* done reading each line of the source of this page */
fclose(output);
free(currentHTML);
currentHTML=NULL;
/* determine next file */
if(1 == fscanf(f, "%s", linebuf)){
if(!strstr(linebuf, ".htm")){
fprintf(stderr, "Error, writing to strange file \"%s\"\n", linebuf);
exit(-1);
}
currentHTML = strdup(linebuf);
}
}
void processSource(const char *file){
FILE *f = fopen(file, "r");
if(!f){
fprintf(stderr, "Error, unable to open source file \"%s\"\n", file);
exit(-1);
}
readSourceHeader(f);
while(!feof(f))
readPageSource(f);
fclose(f);
}
int main(){
readLayout("layout.html");
processSource("source.txt");
return 0;
}