⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 htmlgen.c

📁 用于linux和其他unix下面的
💻 C
📖 第 1 页 / 共 2 页
字号:
/*		HTML Generator**		==============****	This version of the HTML object sends HTML markup to the output stream.**** Bugs:	Line wrapping is not done at all.**		All data handled as PCDATA.**		Should convert old XMP, LISTING and PLAINTEXT to PRE.****	It is not obvious to me right now whether the HEAD should be generated**	from the incomming data or the anchor.	Currently it is from the former**	which is cleanest.*/#include <HTUtils.h>#define BUFFER_SIZE    200	/* Line buffer attempts to make neat breaks */#define MAX_CLEANNESS	20/* Implements:*/#include <HTMLGen.h>#include <HTMLDTD.h>#include <HTStream.h>#include <SGML.h>#include <HTFormat.h>#ifdef USE_COLOR_STYLE#include <LYCharUtils.h>#include <AttrList.h>#include <LYHash.h>#include <LYStyle.h>#endif#include <LYGlobalDefs.h>#include <LYLeaks.h>#define PUTC(c) (*me->targetClass.put_character)(me->target, c)/* #define PUTS(s) (*me->targetClass.put_string)(me->target, s) */#define PUTB(s,l) (*me->targetClass.put_block)(me->target, s, l)#ifdef USE_COLOR_STYLEPUBLIC char class_string[TEMPSTRINGSIZE];static char *Style_className = NULL;static char myHash[128];static int hcode;#endif/*		HTML Object**		-----------*/struct _HTStream {	CONST HTStreamClass *		isa;	HTStream *			target;	HTStreamClass			targetClass;	/* COPY for speed */};struct _HTStructured {	CONST HTStructuredClass *	isa;	HTStream *			target;	HTStreamClass			targetClass;	/* COPY for speed */	char				buffer[BUFFER_SIZE+1]; /* 1for NL */	int				buffer_maxchars;	char *				write_pointer;	char *				line_break [MAX_CLEANNESS+1];	int				cleanness;	BOOL				overflowed;	BOOL				delete_line_break_char[MAX_CLEANNESS+1];	BOOL				preformatted;	BOOL				escape_specials;	BOOL				in_attrval;#ifdef USE_COLOR_STYLE	HText *				text;#endif};/*	Flush Buffer**	------------*/PRIVATE void flush_breaks ARGS1(	HTStructured *,		me){    int i;    for (i=0; i<= MAX_CLEANNESS; i++) {	me->line_break[i] = NULL;    }}PRIVATE void HTMLGen_flush ARGS1(	HTStructured *,		me){    (*me->targetClass.put_block)(me->target,				 me->buffer,				 me->write_pointer - me->buffer);    me->write_pointer = me->buffer;    flush_breaks(me);    me->cleanness = 0;    me->delete_line_break_char[0] = NO;}#ifdef USE_COLOR_STYLE/* *  We need to flush our buffer each time before we effect a color style *  change, this also relies on the subsequent stage not doing any *  buffering - this is currently true, in cases where it matters the *  target stream should be the HTPlain converter. *  The flushing currently prevents reasonable line breaking in lines *  with tags.  Since color styles help visual scanning of displayed *  source lines, and long lines are wrapped in GridText anyway, this *  is probably acceptable (or even A Good Thing - more to see in one *  screenful). *  The pointer to the HText structure is initialized here before *  we effect the first style change.  Getting it from the global *  HTMainText variable isn't very clean, since it relies on the fact *  that HText_new() has already been called for the current stream *  stack's document by the time we start processing the first element; *  we rely on HTMLGenerator's callers (HTMLParsedPresent in particular) *  to guarantee this when it matters.  Normally the target stream will *  have been setup by HTPlainPresent, which does what we need in this *  respect.  (A check whether we have the right output stream could be *  done by checking that targetClass.name is "PlainPresenter" or similar.) * *  All special color style handling is only done if LYPreparsedSource *  is set.  We could always do it for displaying source generated by *  an internal gateway, but this makes the rule more simple for the *  user: color styles are applied to html source only with the *  -preparsed flag. - kw */PRIVATE void do_cstyle_flush ARGS1(	HTStructured *,		me){    if (!me->text && LYPreparsedSource) {	me->text = HTMainText;    }    if (me->text) {	HTMLGen_flush(me);    }}#endif /* COLOR_STYLE *//*	Weighted optional line break****	We keep track of all the breaks for when we chop the line*/PRIVATE void allow_break ARGS3(	HTStructured *, me,	int,		new_cleanness,	BOOL,		dlbc){    if (dlbc && me->write_pointer == me->buffer) dlbc = NO;    me->line_break[new_cleanness] =			 dlbc ? me->write_pointer - 1 /* Point to space */			      : me->write_pointer ;   /* point to gap */    me->delete_line_break_char[new_cleanness] = dlbc;    if (new_cleanness >= me->cleanness &&	(me->overflowed || me->line_break[new_cleanness] > me->buffer))	me->cleanness = new_cleanness;}/*	Character handling**	------------------****	The tricky bits are the line break handling.  This attempts**	to synchrononise line breaks on sentence or phrase ends.  This**	is important if one stores SGML files in a line-oriented code**	repository, so that if a small change is made, line ends don't**	shift in a ripple-through to apparently change a large part of the**	file.  We give extra "cleanness" to spaces appearing directly**	after periods (full stops), [semi]colons and commas.**	   This should make the source files easier to read and modify**	by hand, too, though this is not a primary design consideration. TBL*/PRIVATE void HTMLGen_put_character ARGS2(	HTStructured *,		me,	char,			c){    if (me->escape_specials && UCH(c) < 32) {	if (c == HT_NON_BREAK_SPACE || c == HT_EN_SPACE ||	    c == LY_SOFT_HYPHEN) { /* recursion... */	    HTMLGen_put_character(me, '&');	    HTMLGen_put_character(me, '#');	    HTMLGen_put_character(me, 'x');	    switch(c) {	    case HT_NON_BREAK_SPACE: /* &#xA0; */		HTMLGen_put_character(me, 'A');		HTMLGen_put_character(me, '0');		break;	    case HT_EN_SPACE: /* &#x2002; */		HTMLGen_put_character(me, '2');		HTMLGen_put_character(me, '0');		HTMLGen_put_character(me, '0');		HTMLGen_put_character(me, '2');		break;	    case LY_SOFT_HYPHEN: /* &#xAD; */		HTMLGen_put_character(me, 'A');		HTMLGen_put_character(me, 'D');		break;	    }	    c = ';';	}    }    *me->write_pointer++ = c;    if (c == '\n') {	HTMLGen_flush(me);	return;    }    /* Figure our whether we can break at this point    */    if ((!me->preformatted && (c == ' ' || c == '\t'))) {	int new_cleanness = 3;	if (me->write_pointer > (me->buffer + 1)) {	    char delims[5];	    char * p;	    strcpy(delims, ",;:.");		/* @@ english bias */	    p = strchr(delims, me->write_pointer[-2]);	    if (p) new_cleanness = p - delims + 6;	    if (!me->in_attrval) new_cleanness += 10;	}	allow_break(me, new_cleanness, YES);    }    /*     *	Flush buffer out when full, or whenever the line is over     *	the nominal maximum and we can break at all     */    if (me->write_pointer >= me->buffer + me->buffer_maxchars ||	(me->overflowed && me->cleanness)) {	if (me->cleanness) {	    char line_break_char = me->line_break[me->cleanness][0];	    char * saved = me->line_break[me->cleanness];	    if (me->delete_line_break_char[me->cleanness]) saved++;	    me->line_break[me->cleanness][0] = '\n';	    (*me->targetClass.put_block)(me->target,					 me->buffer,			       me->line_break[me->cleanness] - me->buffer + 1);	    me->line_break[me->cleanness][0] = line_break_char;	    {  /* move next line in */		char * p = saved;		char *q;		for (q = me->buffer; p < me->write_pointer; )		    *q++ = *p++;	    }	    me->cleanness = 0;	    /* Now we have to check whether ther are any perfectly good breaks	    ** which weren't good enough for the last line but may be	    **	good enough for the next	    */	    {		int i;		for(i=0; i <= MAX_CLEANNESS; i++) {		    if (me->line_break[i] != NULL &&			me->line_break[i] > saved) {			me->line_break[i] = me->line_break[i] -						(saved-me->buffer);			me->cleanness = i;		    } else {			me->line_break[i] = NULL;		    }		}	    }	    me->delete_line_break_char[0] = 0;	    me->write_pointer = me->write_pointer - (saved-me->buffer);	    me->overflowed = NO;	} else {	    (*me->targetClass.put_block)(me->target,					 me->buffer,					 me->buffer_maxchars);	    me->write_pointer = me->buffer;	    flush_breaks(me);	    me->overflowed = YES;	}    }}/*	String handling**	---------------*/PRIVATE void HTMLGen_put_string ARGS2(	HTStructured *,		me,	CONST char *,		s){    CONST char * p;    for (p = s; *p; p++)	HTMLGen_put_character(me, *p);}PRIVATE void HTMLGen_write ARGS3(	HTStructured *,		me,	CONST char *,		s,	int,			l){    CONST char * p;    for (p = s; p < (s + l); p++)	HTMLGen_put_character(me, *p);}/*	Start Element**	-------------****	Within the opening tag, there may be spaces**	and the line may be broken at these spaces.*/PRIVATE int HTMLGen_start_element ARGS6(	HTStructured *,		me,	int,			element_number,	CONST BOOL*,		present,	CONST char **,		value,	int,			charset GCC_UNUSED,	char **,		insert GCC_UNUSED){    int i;    BOOL was_preformatted = me->preformatted;    HTTag * tag = &HTML_dtd.tags[element_number];#if defined(USE_COLOR_STYLE)    char *title = NULL;    char *title_tmp = NULL;    if (LYPreparsedSource) {	/*	 *  Same logic as in HTML_start_element, copied from there. - kw	 */	HTSprintf (&Style_className, ";%s", HTML_dtd.tags[element_number].name);	strcpy (myHash, HTML_dtd.tags[element_number].name);	if (class_string[0])	{	    int len = strlen(myHash);	    sprintf (myHash + len, ".%.*s", (int) sizeof(myHash) - len - 2, class_string);	    HTSprintf (&Style_className, ".%s", class_string);	}	class_string[0] = '\0';	strtolower(myHash);	hcode = hash_code(myHash);	strtolower(Style_className);	if (TRACE_STYLE)	{	    fprintf(tfp, "CSSTRIM:%s -> %d", myHash, hcode);	    if (hashStyles[hcode].code!=hcode)	    {		char *rp = strrchr(myHash, '.');		fprintf(tfp, " (undefined) %s\n", myHash);		if (rp)		{		    int hcd;		    *rp = '\0'; /* trim the class */		    hcd = hash_code(myHash);		    fprintf(tfp, "CSS:%s -> %d", myHash, hcd);		    if (hashStyles[hcd].code!=hcd)			fprintf(tfp, " (undefined) %s\n", myHash);		    else			fprintf(tfp, " ca=%d\n", hashStyles[hcd].color);		}	    }	    else		fprintf(tfp, " ca=%d\n", hashStyles[hcode].color);	}	if (displayStyles[element_number + STARTAT].color > -2) /* actually set */	{	    CTRACE2(TRACE_STYLE,		    (tfp, "CSSTRIM: start_element: top <%s>\n",			  HTML_dtd.tags[element_number].name));	    do_cstyle_flush(me);	    HText_characterStyle(me->text, hcode, 1);	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -