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

📄 stylesheet.c

📁 一个很有名的浏览器
💻 C
字号:
/* CSS stylesheet handling *//* $Id: stylesheet.c,v 1.45.6.4 2005/04/05 21:08:41 jonas Exp $ */#ifdef HAVE_CONFIG_H#include "config.h"#endif#include <stdlib.h>#include <string.h>#include "elinks.h"#include "document/css/property.h"#include "document/css/stylesheet.h"#include "util/error.h"#include "util/lists.h"#include "util/memory.h"#include "util/string.h"/* You can find some mysterious functions commented out here. I planned to use * them for various smart things (well they all report to * merge_css_stylesheets()), but it turns out it makes no sense to merge * stylesheets now (and maybe it won't in the future neither...). But maybe you * will find them useful at some time, so... Dunno. --pasky */struct css_selector *find_css_selector(struct list_head *sels, enum css_selector_type type,                  enum css_selector_relation rel,                  unsigned char *name, int namelen){	struct css_selector *selector;	assert(sels && name);	foreach (selector, *sels) {		if (type != selector->type || rel != selector->relation)			continue;		if (strlcasecmp(name, namelen, selector->name, -1))			continue;		return selector;	}	return NULL;}struct css_selector *init_css_selector(struct list_head *sels, enum css_selector_type type,                  unsigned char *name, int namelen){	struct css_selector *selector;	selector = mem_calloc(1, sizeof(*selector));	if (!selector) return NULL;	selector->relation = CSR_ROOT; /* Default */	init_list(selector->leaves);	selector->type = type;	init_list(selector->properties);	if (name) {		if (namelen < 0)			namelen = strlen(name);		selector->name = memacpy(name, namelen);		if (!selector->name) {			mem_free(selector);			return NULL;		}		set_mem_comment(selector, name, namelen);	}	if (sels) {		add_to_list(*sels, selector);	}	return selector;}struct css_selector *get_css_selector(struct list_head *sels, enum css_selector_type type,                 enum css_selector_relation rel,                 unsigned char *name, int namelen){	struct css_selector *selector = NULL;	if (sels && name && namelen) {		selector = find_css_selector(sels, type, rel, name, namelen);		if (selector)			return selector;	}	selector = init_css_selector(sels, type, name, namelen);	if (selector) {		selector->relation = rel;		return selector;	}	return NULL;}static struct css_selector *copy_css_selector(struct css_stylesheet *css, struct css_selector *orig){	struct css_selector *copy;	assert(css && orig);	copy = init_css_selector(&css->selectors, orig->type,	                         orig->name, strlen(orig->name));	if (!copy)		return NULL;	return copy;}static voidadd_selector_property(struct css_selector *selector, struct css_property *prop){	struct css_property *newprop = mem_alloc(sizeof(*newprop));	if (newprop) {		copy_struct(newprop, prop);		add_to_list(selector->properties, newprop);	}}voidadd_selector_properties(struct css_selector *selector,                        struct list_head *properties){	struct css_property *prop;	foreach (prop, *properties) {		add_selector_property(selector, prop);	}}static struct css_selector *clone_css_selector(struct css_stylesheet *css, struct css_selector *orig){	struct css_selector *copy;	assert(css && orig);	copy = copy_css_selector(css, orig);	if (!copy)		return NULL;	add_selector_properties(copy, &orig->properties);	return copy;}voidmerge_css_selectors(struct css_selector *sel1, struct css_selector *sel2){	struct css_property *prop;	foreach (prop, sel2->properties) {		struct css_property *origprop;		foreach (origprop, sel1->properties)			if (origprop->type == prop->type) {				del_from_list(origprop);				mem_free(origprop);				break;			}		/* Not there yet, let's add it. */		add_selector_property(sel1, prop);	}}voiddone_css_selector(struct css_selector *selector){	while (selector->leaves.next != &selector->leaves) {		done_css_selector(selector->leaves.next);	}	if (selector->next) del_from_list(selector);	free_list(selector->properties);	mem_free_if(selector->name);	mem_free(selector);}#ifdef DEBUG_CSSvoiddump_css_selector_tree_iter(struct list_head *sels, int level){	struct css_selector *sel;	foreach (sel, *sels) {		struct css_property *prop;		fprintf(stderr, "%*s +- [%s] type %d rel %d props",		        level * 4, " ",		        sel->name, sel->type, sel->relation);		foreach (prop, sel->properties) {			fprintf(stderr, " [%d]", prop->type);		}		fprintf(stderr, "\n");		dump_css_selector_tree_iter(&sel->leaves, level + 1);	}}voiddump_css_selector_tree(struct list_head *sels){	dump_css_selector_tree_iter(sels, 0);}#endifstruct css_stylesheet *init_css_stylesheet(css_stylesheet_importer importer){	struct css_stylesheet *css;	css = mem_calloc(1, sizeof(*css));	if (!css)		return NULL;	css->import = importer;	init_list(css->selectors);	return css;}voidmirror_css_stylesheet(struct css_stylesheet *css1, struct css_stylesheet *css2){	struct css_selector *selector;	foreach (selector, css1->selectors) {		clone_css_selector(css2, selector);	}}#if 0struct css_stylesheet *clone_css_stylesheet(struct css_stylesheet *orig){	struct css_stylesheet *copy;	struct css_selector *selector;	copy = init_css_stylesheet(orig->import);	if (!copy)		return NULL;	mirror_css_stylesheet(orig, copy);	return copy;}voidmerge_css_stylesheets(struct css_stylesheet *css1,		      struct css_stylesheet *css2){	struct css_selector *selector;	assert(css1 && css2);	/* This is 100% evil. And gonna be a huge bottleneck. Essentially	 * O(N^2) where we could be much smarter (ie. sort it once and then	 * always be O(N)). */	foreach (selector, css2->selectors) {		struct css_selector *origsel;		origsel = find_css_selector(&css1->selectors, selector->name,					    strlen(selector->name));		if (!origsel) {			clone_css_selector(css1, selector);		} else {			merge_css_selectors(origsel, selector);		}	}}#endifvoiddone_css_stylesheet(struct css_stylesheet *css){	while (!list_empty(css->selectors)) {		done_css_selector(css->selectors.next);	}}

⌨️ 快捷键说明

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