dstyle.cc
来自「Click is a modular router toolkit. To us」· CC 代码 · 共 2,157 行 · 第 1/4 页
CC
2,157 行
}dcss_set *dcss_set::default_set(const String &media){ static dcss_set *x; if (!x) x = new dcss_set(default_css, media); return x->remedia(media);}/***** * */static dcss_propmatch *port_pmp[num_port_pm];dcss *dcss_set::ccss_list(const String &str) const{ if (str) for (dcss * const *sp = _s.begin() + 2; sp != _s.end(); ++sp) if ((*sp)->type()[0] == str[0]) return *sp; return 0;}void dcss_set::collect_port_styles(crouter *cr, const delt *e, bool isoutput, int port, int processing, Vector<dcss *> &result){ assert(!e->root()); for (dcss *s = ccss_list("port"); s; s = s->_next) if ((s->pflags() & pflag_port) && s->selector().match_port(isoutput, port, processing) && s->strict_match_context(cr, e)) result.push_back(s); for (dcss *s = _s[0]; s; s = s->_next) if ((s->pflags() & pflag_port) && s->selector().match_port(isoutput, port, processing) && s->strict_match_context(cr, e)) result.push_back(s); collect_elt_styles(cr, e, pflag_port | pflag_no_below, result, 0); if (_below) _below->collect_port_styles(cr, e, isoutput, port, processing, result);}ref_ptr<dport_style> dcss_set::port_style(crouter *cr, const delt *e, bool isoutput, int port, int processing){ Vector<dcss *> sv; collect_port_styles(cr, e, isoutput, port, processing, sv); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<dport_style> &style_cache = _ptable[sa.take_string()]; if (!style_cache) { dcss::assign_all(port_pm, port_pmp, num_port_pm, sv.begin(), sv.end()); dport_style *sty = new dport_style; String s = port_pm[0].vstring("port-shape"); sty->shape = (s.equals("triangle", 8) ? dpshape_triangle : dpshape_rectangle); sty->length = port_pm[1].vpixel("port-length"); sty->width = port_pm[2].vpixel("port-width"); port_pm[3].vcolor(sty->color, "port-color"); sty->border_style = port_pm[4].vborder_style("port-border-style"); sty->border_width = port_pm[5].vpixel("port-border-width"); port_pm[6].vcolor(sty->border_color, "port-border-color"); if (sty->border_color[3] == 0 || sty->border_width <= 0) sty->border_style = dborder_none; sty->margin[0] = port_pm[7].vpixel("port-margin-top"); sty->margin[1] = port_pm[8].vpixel("port-margin-right"); sty->margin[2] = port_pm[9].vpixel("port-margin-bottom"); sty->margin[3] = port_pm[10].vpixel("port-margin-left"); sty->edge_padding = port_pm[11].vpixel("port-edge-padding"); s = port_pm[12].vstring("port-display"); if (s.equals("none", 4)) sty->display = dpdisp_none; else if (s.equals("inputs", 6)) sty->display = dpdisp_inputs; else if (s.equals("outputs", 7)) sty->display = dpdisp_outputs; else sty->display = dpdisp_both; sty->text = cp_unquote(port_pm[13].vstring("port-text")); sty->font = cp_unquote(port_pm[14].vstring("port-font")); style_cache = ref_ptr<dport_style>(sty); } return style_cache;}/***** * */static dcss_propmatch *elt_pmp[num_elt_pm];void dcss_set::collect_elt_styles(crouter *cr, const delt *e, int pflag, Vector<dcss *> &result, int *sensitivity) const{ assert(!e->root()); for (dcss *s = ccss_list(e->type_name()); s; s = s->_next) if ((s->pflags() & pflag) && s->selector().match(cr, e, sensitivity) && s->match_context(cr, e, sensitivity)) result.push_back(s); for (dcss *s = _s[0]; s; s = s->_next) if ((s->pflags() & pflag) && s->selector().match(cr, e, sensitivity) && s->match_context(cr, e, sensitivity)) result.push_back(s); //if (e->parent() && !e->parent()->root()) // collect_elt_styles(cr, e->parent(), pflag | pflag_no_below, result, sensitivity); if (_below && !(pflag & pflag_no_below)) _below->collect_elt_styles(cr, e, pflag, result, sensitivity);}static String parse_flow_split(const char *begin, const char *end){ StringAccum sa; bool output = false; for (begin = cp_skip_space(begin, end); begin < end; ++begin) if (*begin == '/') { if (output || !sa.length()) return String(); output = true; sa << '/'; } else if (isalpha((unsigned char) *begin)) sa << *begin; else break; begin = cp_skip_space(begin, end); if (begin != end || !sa.length() || !output || sa.back() == '/') return String(); else return sa.take_string();}ref_ptr<delt_style> dcss_set::elt_style(crouter *cr, const delt *e, int *sensitivity){ if (sensitivity) *sensitivity = 0; Vector<dcss *> sv; collect_elt_styles(cr, e, pflag_elt, sv, sensitivity); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<delt_style> &style_cache = _etable[sa.take_string()]; if (!style_cache) { dcss::assign_all(elt_pm, elt_pmp, num_elt_pm, sv.begin(), sv.end()); delt_style *sty = new delt_style; elt_pm[0].vcolor(sty->color, "color"); elt_pm[1].vcolor(sty->background_color, "background-color"); sty->border_style = elt_pm[2].vborder_style("border-style"); elt_pm[3].vcolor(sty->border_color, "border-color"); if (sty->border_color[3] == 0) sty->border_style = dborder_none; sty->shadow_style = elt_pm[4].vshadow_style("shadow-style"); sty->shadow_width = elt_pm[5].vpixel("shadow-width", cr, e); elt_pm[6].vcolor(sty->shadow_color, "shadow-color"); if (sty->shadow_color[3] == 0 || sty->shadow_width <= 0) sty->shadow_style = dshadow_none; String s = elt_pm[7].vstring("style"); sty->style = (s.equals("queue", 5) ? destyle_queue : destyle_normal); sty->text = cp_unquote(elt_pm[8].vstring("text")); s = elt_pm[9].vstring("display"); sty->display = dedisp_open; if (s.equals("none", 4)) sty->display = dedisp_none; else if (s.equals("closed", 6)) sty->display = dedisp_closed; else if (s.equals("passthrough", 11)) sty->display = dedisp_passthrough; else if (s.equals("expanded", 8)) sty->display = dedisp_expanded; sty->font = elt_pm[10].vstring("font"); sty->decorations = elt_pm[11].vstring("decorations"); sty->queue_stripe_style = elt_pm[12].vborder_style("queue-stripe-style"); sty->queue_stripe_width = elt_pm[13].vpixel("queue-stripe-width", cr, e); elt_pm[14].vcolor(sty->queue_stripe_color, "queue-stripe-color"); s = elt_pm[15].vstring("port-split"); sty->port_split = dpdisp_none; if (s.equals("inputs", 6)) sty->port_split = dpdisp_inputs; else if (s.equals("outputs", 7)) sty->port_split = dpdisp_outputs; else if (s.equals("both", 4)) sty->port_split = dpdisp_both; s = elt_pm[16].vstring("flow-split"); sty->flow_split = parse_flow_split(s.begin(), s.end()); style_cache = ref_ptr<delt_style>(sty); } return style_cache;}static dcss_propmatch *elt_size_pmp[num_elt_size_pm];ref_ptr<delt_size_style> dcss_set::elt_size_style(crouter *cr, const delt *e, int *sensitivity){ if (sensitivity) *sensitivity = 0; Vector<dcss *> sv; collect_elt_styles(cr, e, pflag_elt_size, sv, sensitivity); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<delt_size_style> &style_cache = _estable[sa.take_string()]; if (!style_cache) { dcss::assign_all(elt_size_pm, elt_size_pmp, num_elt_size_pm, sv.begin(), sv.end()); double scale = elt_size_pm[13].vrelative("scale"); if (scale <= 0) scale = 1; delt_size_style *sty = new delt_size_style; sty->scale = scale; sty->border_width = elt_size_pm[0].vpixel("border-width", cr, e); sty->padding[0] = elt_size_pm[1].vpixel("padding-top", cr, e) * scale; sty->padding[1] = elt_size_pm[2].vpixel("padding-right", cr, e) * scale; sty->padding[2] = elt_size_pm[3].vpixel("padding-bottom", cr, e) * scale; sty->padding[3] = elt_size_pm[4].vpixel("padding-left", cr, e) * scale; sty->min_width = elt_size_pm[5].vpixel("min-width", cr, e) * scale; sty->min_height = elt_size_pm[6].vpixel("min-height", cr, e) * scale; sty->min_length = elt_size_pm[15].vpixel("min-length", cr, e) * scale; sty->height_step = elt_size_pm[7].vpixel("height-step", cr, e) * scale; sty->margin[0] = elt_size_pm[8].vpixel("margin-top", cr, e) * scale; sty->margin[1] = elt_size_pm[9].vpixel("margin-right", cr, e) * scale; sty->margin[2] = elt_size_pm[10].vpixel("margin-bottom", cr, e) * scale; sty->margin[3] = elt_size_pm[11].vpixel("margin-left", cr, e) * scale; sty->queue_stripe_spacing = elt_size_pm[12].vpixel("queue-stripe-spacing", cr, e) * scale; String s = elt_size_pm[14].vstring("orientation"); sty->orientation = 0; if (s.find_left("horizontal") >= 0) sty->orientation = 3; if (s.find_left("reverse") >= 0) sty->orientation ^= 2; style_cache = ref_ptr<delt_size_style>(sty); } return style_cache;}/***** * */static int parse_autorefresh(String str, const char *medium, int *period){ int on = -1; double d; while (String x = cp_shift_spacevec(str)) if (x.equals("on", 2) || (medium && x.equals("both", 4))) on = (medium ? 2 : 1); else if (x.equals("off", 3)) on = 0; else if (medium && x.equals(medium, -1)) on = 1; else if (cp_seconds(x, &d) && d >= 0) { if (on < 0) on = (medium ? 2 : 1); *period = (int) (d * 1000); } return (on < 0 ? 0 : on);}static dcss_propmatch *handler_pmp[num_handler_pm];void dcss_set::collect_handler_styles(crouter *cr, const handler_value *hv, const delt *e, Vector<dcss *> &result, bool &generic) const{ for (dcss * const *sp = _s.begin() + 2; sp != _s.end(); ++sp) if ((*sp)->type()[0] == 'h') for (dcss *s = *sp; s; s = s->_next) if (s->selector().match(hv) && s->match_context(cr, e)) { if (!s->selector().generic_handler() || s->has_context()) generic = false; result.push_back(s); } for (dcss *s = _s[0]; s; s = s->_next) if (s->selector().match(hv) && s->match_context(cr, e)) { if (!s->selector().generic_handler() || s->has_context()) generic = false; result.push_back(s); } if (_below) _below->collect_handler_styles(cr, hv, e, result, generic);}ref_ptr<dhandler_style> dcss_set::handler_style(crouter *cr, const delt *e, const handler_value *hv){ Vector<dcss *> sv; bool generic = true; collect_handler_styles(cr, hv, e, sv, generic); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<dhandler_style> &style_cache = _htable[sa.take_string()]; if (!style_cache) { dcss::assign_all(handler_pm, handler_pmp, num_handler_pm, sv.begin(), sv.end()); dhandler_style *sty = new dhandler_style; sty->autorefresh_period = (int) (handler_pm[1].vseconds("autorefresh-period") * 1000); sty->flags_mask = hflag_autorefresh | hflag_refresh | hflag_visible | hflag_collapse; sty->flags = 0; String s = handler_pm[0].vstring("autorefresh"); if (parse_autorefresh(s, 0, &sty->autorefresh_period)) sty->flags |= hflag_autorefresh; if (!s) sty->flags_mask &= ~hflag_autorefresh; s = handler_pm[2].vstring("display"); if (s && !s.equals("none", 4)) sty->flags |= hflag_visible; if (s.equals("collapse", 8)) sty->flags |= hflag_collapse; if (!s) sty->flags_mask &= ~(hflag_visible | hflag_collapse); s = handler_pm[3].vstring("allow-refresh"); if (s.equals("yes", 3) || s.equals("true", 4)) sty->flags |= hflag_refresh; if (!s) sty->flags_mask &= ~hflag_refresh; style_cache = ref_ptr<dhandler_style>(sty); } return style_cache;}/***** * * * */static dcss_propmatch *fullness_pmp[num_fullness_pm];void dcss_set::collect_decor_styles(PermString decor, crouter *cr, const delt *e, Vector<dcss *> &result, bool &generic) const{ for (dcss * const *sp = _s.begin() + 2; sp != _s.end(); ++sp) if ((*sp)->type()[0] == decor[0]) for (dcss *s = *sp; s; s = s->_next) if (s->selector().match_decor(decor) && s->match_context(cr, e)) { if (!s->selector().generic_decor() || s->has_context()) generic = false; result.push_back(s); } for (dcss *s = _s[0]; s; s = s->_next) if (s->selector().match_decor(decor) && s->match_context(cr, e)) { if (!s->selector().generic_decor() || s->has_context()) generic = false; result.push_back(s); } if (_below) _below->collect_decor_styles(decor, cr, e, result, generic);}ref_ptr<dfullness_style> dcss_set::fullness_style(PermString decor, crouter *cr, const delt *e){ Vector<dcss *> sv; bool generic = true; collect_decor_styles(decor, cr, e, sv, generic); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<dfullness_style> &style_cache = _ftable[sa.take_string()]; if (!style_cache) { dcss::assign_all(fullness_pm, fullness_pmp, num_fullness_pm, sv.begin(), sv.end()); dfullness_style *sty = new dfullness_style; sty->length = fullness_pm[0].vstring("length"); sty->capacity = fullness_pm[1].vstring("capacity"); fullness_pm[2].vcolor(sty->color, "color"); sty->autorefresh_period = (int) (fullness_pm[4].vseconds("autorefresh-period") * 1000); String s = fullness_pm[3].vstring("autorefresh"); sty->autorefresh = parse_autorefresh(s, "length", &sty->autorefresh_period); style_cache = ref_ptr<dfullness_style>(sty); } return style_cache;}/***** * * * */static dcss_propmatch *activity_pmp[num_activity_pm];ref_ptr<dactivity_style> dcss_set::activity_style(PermString decor, crouter *cr, const delt *e){ Vector<dcss *> sv; bool generic = true; collect_decor_styles(decor, cr, e, sv, generic); std::sort(sv.begin(), sv.end(), dcsspp_compare); StringAccum sa(sizeof(unsigned) * sv.size()); for (dcss **sp = sv.begin(); sp != sv.end(); ++sp) *reinterpret_cast<unsigned *>(sa.extend(sizeof(unsigned))) = (*sp)->selector_index(); ref_ptr<dactivity_style> &style_cache = _atable[sa.take_string()]; if (!style_cache) { dcss::assign_all(activity_pm, activity_pmp, num_activity_pm, sv.begin(), sv.end()); dactivity_style *sty = new dactivity_style; sty->handler = activity_pm[0].vstring("handler"); sty->autorefresh_period = (int) (activity_pm[3].vseconds("autorefresh-period") * 1000); String s = activity_pm[2].vstring("autorefresh"); sty->autorefresh = parse_autorefresh(s, "", &sty->autorefresh_period); s = activity_pm[4].vstring("type"); if (s.starts_with("rate", 4)) { sty->type = dactivity_rate; s = s.substring(4); sty->rate_period = 1; (void) cp_seconds(cp_shift_spacevec(s), &sty->rate_period); sty->rate_period = std::max(sty->rate_period, 0.01); } else sty->type = dactivity_absolute; sty->max_value = activity_pm[5].vnumeric("max-value"); sty->min_value = activity_pm[6].vnumeric("min-value"); sty->max_value = std::max(sty->min_value, sty->max_value); sty->decay = activity_pm[7].vseconds("decay"); // parse color series Vector<String> vs; s = activity_pm[1].vstring("color"); while (String sx = ccss_pop_commavec(s)) vs.push_back(sx); if (vs.size() == 0) vs.push_back("none"); if (vs.size() == 1) { vs.push_back(vs[0]); vs[0] = "none"; } for (String *vsp = vs.begin(); vsp != vs.end(); ++vsp) { int x = sty->colors.size(); sty->colors.resize(sty->colors.size() + 5); sty->colors[x] = -1; if (*vsp && isdigit((unsigned char) (*vsp)[0])) { if (!cp_relative(cp_shift_spacevec(*vsp), &sty->colors[x]) || sty->colors[x] < 0 || sty->colors[x] > 1) sty->colors[x] = -1; } if (!cp_color(*vsp, &sty->colors[x+1], &sty->colors[x+2], &sty->colors[x+3], &sty->colors[x+4])) memcpy(&sty->colors[x+1], dcss_property::transparent_color, sizeof(double) * 4); } sty->colors[0] = 0.; sty->colors[sty->colors.size() - 5] = 1.; for (int i = 5; i < sty->colors.size(); i += 5) { if (sty->colors[i] < 0) { int n; for (n = 2; sty->colors[i + 5*(n-1)] < 0; ++n) /* nada */; sty->colors[i] = (sty->colors[i-5] * (n - 1) + sty->colors[i + 5*(n-1)]) / n; } else if (sty->colors[i] < sty->colors[i - 5]) sty->colors[i] = sty->colors[i - 5] + 0.001; } //if (sty->type == dactivity_rate) //sty->decay_begin = std::max(sty->decay_begin, 10U); //sty->decay_end = std::max(sty->decay_begin, sty->decay_end); style_cache = ref_ptr<dactivity_style>(sty); } return style_cache;}/***** * * * */double dcss_set::vpixel(PermString name, crouter *cr, const delt *e) const{ Vector<dcss *> sv; collect_elt_styles(cr, e, pflag_elt | pflag_elt_size, sv, 0); std::sort(sv.begin(), sv.end(), dcsspp_compare); dcss_propmatch pm = { name, 0 }, *pmp = ± dcss::assign_all(&pm, &pmp, 1, sv.begin(), sv.end()); return pm.vpixel(name.c_str(), cr, name, e->parent());}String dcss_set::vstring(PermString name, PermString decor, crouter *cr, const delt *e) const{ Vector<dcss *> sv; bool generic = true; collect_decor_styles(decor, cr, e, sv, generic); std::sort(sv.begin(), sv.end(), dcsspp_compare); dcss_propmatch pm = { name, 0 }, *pmp = ± dcss::assign_all(&pm, &pmp, 1, sv.begin(), sv.end()); return pm.vstring(name.c_str());}}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?