зеркало из https://github.com/mozilla/gecko-dev.git
415 строки
11 KiB
C
415 строки
11 KiB
C
/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
|
*
|
|
* The contents of this file are subject to the Netscape Public License
|
|
* Version 1.0 (the "NPL"); you may not use this file except in
|
|
* compliance with the NPL. You may obtain a copy of the NPL at
|
|
* http://www.mozilla.org/NPL/
|
|
*
|
|
* Software distributed under the NPL is distributed on an "AS IS" basis,
|
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the NPL
|
|
* for the specific language governing rights and limitations under the
|
|
* NPL.
|
|
*
|
|
* The Initial Developer of this code under the NPL is Netscape
|
|
* Communications Corporation. Portions created by Netscape are
|
|
* Copyright (C) 1998 Netscape Communications Corporation. All Rights
|
|
* Reserved.
|
|
*/
|
|
|
|
#ifdef DOM
|
|
|
|
#include "xp.h"
|
|
#include "pa_parse.h"
|
|
#include "layout.h"
|
|
#include "laylayer.h"
|
|
#include "laystyle.h"
|
|
#include "libmocha.h"
|
|
#include "stystruc.h"
|
|
#include "stystack.h"
|
|
#include "layers.h"
|
|
|
|
|
|
/* Initial attempt at DOM by letting JS set style of SPAN contents */
|
|
void lo_SetColor( LO_Element *ele, LO_Color *color, lo_DocState *state,
|
|
Bool background);
|
|
static void lo_SetFontFamily( MWContext *context, LO_Element *ele, char *family);
|
|
static void lo_SetFontWeight( MWContext *context, LO_Element *ele, char *weight);
|
|
static void lo_SetFontSlant( MWContext *context, LO_Element *ele, char *weight);
|
|
static void lo_SetFontSize( MWContext *context, LO_Element *ele, int32 size);
|
|
|
|
/* Public functions */
|
|
JSObject *
|
|
LO_GetMochaObjectOfParentSpan( LO_Element *ele)
|
|
{
|
|
LO_SpanStruct *span;
|
|
lo_NameList *name_rec;
|
|
JSObject *obj = NULL;
|
|
|
|
if (LO_IsWithinSpan( ele ))
|
|
{
|
|
/* Go back in the layout element list until we find a SPAN element */
|
|
span = lo_FindParentSpan(ele);
|
|
if ( span != NULL )
|
|
{
|
|
name_rec = (lo_NameList *) span->name_rec;
|
|
if (name_rec != NULL)
|
|
obj = name_rec->mocha_object;
|
|
}
|
|
}
|
|
|
|
return obj;
|
|
}
|
|
|
|
/* Set the color of all layout elements contained within the span */
|
|
void LO_SetSpanColor(MWContext* context, void *span, LO_Color *color)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
#if 0
|
|
lo_SetColor(ele, color, FALSE);
|
|
#endif
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Set the background color of all layout elements contained within the span */
|
|
void LO_SetSpanBackground(MWContext* context, void *span, LO_Color *color)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
#if 0
|
|
lo_SetColor(ele, color, TRUE);
|
|
#endif
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Set the font family (Arial, Helvetica, Times) of all the layout
|
|
elements contained within the span */
|
|
void
|
|
LO_SetSpanFontFamily(MWContext* context, void *span, char *family)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
lo_SetFontFamily(context, ele, family);
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Set the font weight (medium, bold, heavy, etc.) of all the layout
|
|
elements contained within the span */
|
|
void
|
|
LO_SetSpanFontWeight(MWContext* context, void *span, char *weight)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
lo_SetFontWeight(context, ele, weight);
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Set the font size (in points) of all the layout elements contained
|
|
within the span */
|
|
void
|
|
LO_SetSpanFontSize(MWContext* context, void *span, int32 size)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
lo_SetFontSize(context, ele, size);
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Set the font slant (in points) of all the layout elements contained
|
|
within the span */
|
|
void
|
|
LO_SetSpanFontSlant(MWContext* context, void *span, char *slant)
|
|
{
|
|
lo_NameList *name_rec = (lo_NameList *)span;
|
|
LO_SpanStruct *parent_span = lo_FindParentSpan(name_rec->element);
|
|
LO_Element *ele;
|
|
|
|
ele = parent_span->lo_any.next;
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
{
|
|
lo_SetFontSlant(context, ele, slant);
|
|
ele = ele->lo_any.next;
|
|
}
|
|
}
|
|
|
|
/* Functions internal to layout */
|
|
LO_SpanStruct *
|
|
lo_FindParentSpan( LO_Element *ele )
|
|
{
|
|
while (ele != NULL && ele->lo_any.type != LO_SPAN)
|
|
ele = ele->lo_any.prev;
|
|
|
|
return (LO_SpanStruct *) ele;
|
|
}
|
|
|
|
#define GET_UNSHARED_TEXT_ATTR(new, old) \
|
|
PR_BEGIN_MACRO \
|
|
if ((old)->refcnt != 1) { \
|
|
(new) = lo_NewCopyTextAttr(state, (old)); \
|
|
(old)->refcnt--; \
|
|
} else { \
|
|
(new) = (old); \
|
|
} \
|
|
PR_END_MACRO
|
|
|
|
void lo_SetColor( LO_Element *ele, LO_Color *color, lo_DocState *state,
|
|
Bool background)
|
|
{
|
|
LO_TextAttr *new_attr;
|
|
switch (ele->lo_any.type)
|
|
{
|
|
case LO_TEXTBLOCK:
|
|
GET_UNSHARED_TEXT_ATTR(new_attr, ele->lo_textBlock.text_attr);
|
|
ele->lo_textBlock.text_attr = new_attr;
|
|
break;
|
|
case LO_TEXT:
|
|
GET_UNSHARED_TEXT_ATTR(new_attr, ele->lo_text.text_attr);
|
|
ele->lo_text.text_attr = new_attr;
|
|
break;
|
|
case LO_BULLET:
|
|
GET_UNSHARED_TEXT_ATTR(new_attr, ele->lo_bullet.text_attr);
|
|
ele->lo_bullet.text_attr = new_attr;
|
|
break;
|
|
default:
|
|
return;
|
|
}
|
|
if (background)
|
|
{
|
|
new_attr->bg = *color;
|
|
new_attr->no_background = FALSE;
|
|
}
|
|
else
|
|
{
|
|
new_attr->fg = *color;
|
|
}
|
|
}
|
|
|
|
/* Functions internal to this file */
|
|
static void
|
|
lo_SetFontFamily( MWContext *context,
|
|
LO_Element *ele,
|
|
char *new_face)
|
|
{
|
|
LO_TextAttr *text_attr;
|
|
|
|
/* if the point size is different, tell the FE to release it's data,
|
|
set the point_size to the new value, and then have the FE
|
|
recompute it's information. */
|
|
switch (ele->lo_any.type)
|
|
{
|
|
case LO_TEXTBLOCK:
|
|
text_attr = ele->lo_textBlock.text_attr;
|
|
break;
|
|
case LO_TEXT:
|
|
text_attr = ele->lo_text.text_attr;
|
|
break;
|
|
case LO_BULLET:
|
|
text_attr = ele->lo_bullet.text_attr;
|
|
break;
|
|
default:
|
|
/* we don't mess with any other type of element */
|
|
return;
|
|
}
|
|
|
|
if (ele->lo_any.type == LO_TEXT)
|
|
{
|
|
LO_TextInfo text_info;
|
|
LO_TextStruct tmp_text;
|
|
memset (&tmp_text, 0, sizeof (tmp_text));
|
|
|
|
FE_ReleaseTextAttrFeData(context, text_attr);
|
|
|
|
/* XP_FREE(text_attr->font_face); */
|
|
text_attr->font_face = strdup(new_face);
|
|
|
|
tmp_text = ele->lo_text;
|
|
|
|
FE_GetTextInfo(context, &tmp_text, &text_info);
|
|
}
|
|
else if (ele->lo_any.type == LO_TEXTBLOCK)
|
|
{
|
|
/* XP_FREE(text_attr->font_face); */
|
|
text_attr->font_face = strdup(new_face);
|
|
}
|
|
}
|
|
|
|
static void
|
|
lo_SetFontWeight( MWContext *context,
|
|
LO_Element *ele,
|
|
char *weight)
|
|
{
|
|
LO_TextAttr *text_attr;
|
|
int new_weight = atoi(weight);
|
|
|
|
/* if the point size is different, tell the FE to release it's data,
|
|
set the point_size to the new value, and then have the FE
|
|
recompute it's information. */
|
|
switch (ele->lo_any.type)
|
|
{
|
|
case LO_TEXTBLOCK:
|
|
text_attr = ele->lo_textBlock.text_attr;
|
|
break;
|
|
case LO_TEXT:
|
|
text_attr = ele->lo_text.text_attr;
|
|
break;
|
|
case LO_BULLET:
|
|
text_attr = ele->lo_bullet.text_attr;
|
|
break;
|
|
default:
|
|
/* we don't mess with any other type of element */
|
|
return;
|
|
}
|
|
|
|
if (ele->lo_any.type == LO_TEXT)
|
|
{
|
|
LO_TextInfo text_info;
|
|
LO_TextStruct tmp_text;
|
|
memset (&tmp_text, 0, sizeof (tmp_text));
|
|
|
|
FE_ReleaseTextAttrFeData(context, text_attr);
|
|
|
|
text_attr->font_weight = new_weight;
|
|
if(text_attr->font_weight > 900)
|
|
text_attr->font_weight = 900;
|
|
|
|
tmp_text = ele->lo_text;
|
|
|
|
FE_GetTextInfo(context, &tmp_text, &text_info);
|
|
}
|
|
else if (ele->lo_any.type == LO_TEXTBLOCK)
|
|
{
|
|
text_attr->font_weight = new_weight;
|
|
if (text_attr->font_weight > 900)
|
|
text_attr->font_weight = 900;
|
|
}
|
|
|
|
}
|
|
|
|
static void
|
|
lo_SetFontSlant( MWContext *context,
|
|
LO_Element *ele,
|
|
char *slant)
|
|
{
|
|
LO_TextAttr *text_attr;
|
|
int flag;
|
|
|
|
/* if the point size is different, tell the FE to release it's data,
|
|
set the point_size to the new value, and then have the FE
|
|
recompute it's information. */
|
|
switch (ele->lo_any.type)
|
|
{
|
|
case LO_TEXTBLOCK:
|
|
text_attr = ele->lo_textBlock.text_attr;
|
|
break;
|
|
case LO_TEXT:
|
|
text_attr = ele->lo_text.text_attr;
|
|
break;
|
|
case LO_BULLET:
|
|
text_attr = ele->lo_bullet.text_attr;
|
|
break;
|
|
default:
|
|
/* we don't mess with any other type of element */
|
|
return;
|
|
}
|
|
|
|
if (!strcmp(slant, "italic"))
|
|
flag = LO_FONT_ITALIC;
|
|
else if (!strcmp(slant, "fixed"))
|
|
flag = LO_FONT_FIXED;
|
|
|
|
if (ele->lo_any.type == LO_TEXTBLOCK
|
|
&& !text_attr->fontmask & flag)
|
|
{
|
|
LO_TextInfo text_info;
|
|
LO_TextStruct tmp_text;
|
|
memset (&tmp_text, 0, sizeof (tmp_text));
|
|
|
|
FE_ReleaseTextAttrFeData(context, text_attr);
|
|
|
|
text_attr->fontmask |= flag;
|
|
|
|
tmp_text = ele->lo_text;
|
|
|
|
FE_GetTextInfo(context, &tmp_text, &text_info);
|
|
}
|
|
}
|
|
|
|
static void
|
|
lo_SetFontSize( MWContext *context,
|
|
LO_Element *ele,
|
|
int32 new_size)
|
|
{
|
|
LO_TextAttr *text_attr;
|
|
|
|
/* if the point size is different, tell the FE to release it's data,
|
|
set the point_size to the new value, and then have the FE
|
|
recompute it's information. */
|
|
switch (ele->lo_any.type)
|
|
{
|
|
case LO_TEXTBLOCK:
|
|
text_attr = ele->lo_textBlock.text_attr;
|
|
break;
|
|
case LO_TEXT:
|
|
text_attr = ele->lo_text.text_attr;
|
|
break;
|
|
case LO_BULLET:
|
|
text_attr = ele->lo_bullet.text_attr;
|
|
break;
|
|
default:
|
|
/* we don't mess with any other type of element */
|
|
return;
|
|
}
|
|
|
|
if (ele->lo_any.type == LO_TEXT)
|
|
{
|
|
LO_TextInfo text_info;
|
|
LO_TextStruct tmp_text;
|
|
memset (&tmp_text, 0, sizeof (tmp_text));
|
|
|
|
FE_ReleaseTextAttrFeData(context, text_attr);
|
|
|
|
text_attr->point_size = new_size;
|
|
|
|
tmp_text = ele->lo_text;
|
|
|
|
FE_GetTextInfo(context, &tmp_text, &text_info);
|
|
}
|
|
else if (ele->lo_any.type == LO_TEXTBLOCK)
|
|
{
|
|
text_attr->point_size = new_size;
|
|
}
|
|
|
|
}
|
|
|
|
#endif
|