From 01e2426b496f0eff10dbb9582f99b0cc7ca74bdf Mon Sep 17 00:00:00 2001 From: James Bursa Date: Tue, 7 Oct 2003 21:41:55 +0000 Subject: [project @ 2003-10-07 21:41:55 by bursa] Implementing a new CSS property overview. svn path=/import/netsurf/; revision=349 --- Docs/developer | 70 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) (limited to 'Docs/developer') diff --git a/Docs/developer b/Docs/developer index 8acaca65a..83cd61812 100644 --- a/Docs/developer +++ b/Docs/developer @@ -97,4 +97,74 @@ http://netsurf.strcprstskrzkrk.co.uk/developer/ - libpng (PNG support) http://www.libpng.org/pub/png/libpng.html - zlib http://www.gzip.org/zlib/ +\section addcss Implementing a new CSS property + +In this section I go through adding a CSS property to NetSurf, using the +'white-space' property as an example. -- James Bursa + +1. Read and understand the description of the property in the CSS specification + (I have worked from CSS 2, but now 2.1 is probably better). + +These changes are required in the css directory: + +2. Add the property to css_enums. This file is used to generate css_enum.h + and css_enum.c: + \code css_white_space inherit normal nowrap pre \endcode + (I'm not doing pre-wrap and pre-line for now.) + +3. Add fields to struct ::css_style to represent the property: + \code css_white_space white_space; \endcode + +4. Add a parser function for the property to ruleset.c. Declare a new + function: + \code static void parse_white_space(struct css_style * const s, const struct css_node * const v); \endcode + and add it to ::property_table: + \code { "white-space", parse_white_space }, \endcode + This will cause the function to be called when the parser comes to a rule + giving a value for white-space. The function is passed a linked list of + struct ::css_node, each of which corresponds to a token in the CSS source, + and must update s to correspond to that rule. For white-space, the + implementation is simply: +\code +void parse_white_space(struct css_style * const s, const struct css_node * const v) +{ + css_white_space z; + if (v->type != CSS_NODE_IDENT || v->next != 0) + return; + z = css_white_space_parse(v->data); + if (z != CSS_WHITE_SPACE_UNKNOWN) + s->white_space = z; +} +\endcode + First we check that the value consists of exactly one identifier, as + described in the specification. If it is not, we ignore it, since it may be + some future CSS. The css_white_space_parse() function is generated in + css_enum.c, and converts a string giving a value to a constant. If the + conversion succeeds, the style s is updated. + +5. Add defaults for the style to ::css_base_style, ::css_empty_style, and + ::css_blank_style in css.c. The value in css_base_style should be the one + given as 'Initial' in the spec, and the value in css_empty_style should be + inherit. If 'Inherited' is yes in the spec, the value in css_blank_style + should be inherit, otherwise it should be the one given as 'Initial'. Thus + for white-space, which has "Initial: normal, Inherited: yes" in the spec, we + use CSS_WHITE_SPACE_NORMAL in css_base_style and CSS_WHITE_SPACE_INHERIT in + the other two. + +6. Edit css_cascade() and css_merge() in css.c to handle the property. In + both cases for white-space this looks like: + \code + if (apply->white_space != CSS_WHITE_SPACE_INHERIT) + style->white_space = apply->white_space; + \endcode + Add the property to css_dump_style() (not essential). + +Now the box, layout and / or redraw code needs to be changed to use the new +style property. This varies much more depending on the property. + +For white-space, convert_xml_to_box() was changed to split text at newlines if +white-space was pre, and to replace spaces with hard spaces for nowrap. +Additionally, calculate_inline_container_widths() was changed to give the +appropriate minimum width for pre and nowrap. + */ -- cgit v1.2.3