📄 agg_rasterizer_scanline_aa.h
字号:
if(cur_cell->x > last_x) { alpha = calculate_alpha(m_iterator.cover << (poly_base_shift + 1)); if(alpha) { sl.add_span(last_x, cur_cell->x - last_x, alpha); } } } if(sl.num_spans()) { sl.finalize(m_iterator.last_y); break; } } return true; } //-------------------------------------------------------------------- bool hit_test(int tx, int ty); //-------------------------------------------------------------------- void add_xy(const double* x, const double* y, unsigned n) { if(n > 2) { move_to_d(*x++, *y++); --n; do { line_to_d(*x++, *y++); } while(--n); } } //------------------------------------------------------------------- template<class VertexSource> void add_path(VertexSource& vs, unsigned id=0) { double x; double y; unsigned cmd; vs.rewind(id); while(!is_stop(cmd = vs.vertex(&x, &y))) { add_vertex(x, y, cmd); } } private: //-------------------------------------------------------------------- // Disable copying rasterizer_scanline_aa(const rasterizer_scanline_aa<XScale, AA_Shift>&); const rasterizer_scanline_aa<XScale, AA_Shift>& operator = (const rasterizer_scanline_aa<XScale, AA_Shift>&); //-------------------------------------------------------------------- void move_to_no_clip(int x, int y); void line_to_no_clip(int x, int y); void close_polygon_no_clip(); void clip_segment(int x, int y); private: outline_aa m_outline; int m_gamma[aa_num]; filling_rule_e m_filling_rule; int m_clipped_start_x; int m_clipped_start_y; int m_start_x; int m_start_y; int m_prev_x; int m_prev_y; unsigned m_prev_flags; unsigned m_status; rect m_clip_box; bool m_clipping; iterator m_iterator; }; //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::reset() { m_outline.reset(); m_status = status_initial; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::filling_rule(filling_rule_e filling_rule) { m_filling_rule = filling_rule; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::clip_box(double x1, double y1, double x2, double y2) { reset(); m_clip_box = rect(poly_coord(x1), poly_coord(y1), poly_coord(x2), poly_coord(y2)); m_clip_box.normalize(); m_clipping = true; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::reset_clipping() { reset(); m_clipping = false; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::move_to_no_clip(int x, int y) { if(m_status == status_line_to) { close_polygon_no_clip(); } m_outline.move_to(x * XScale, y); m_clipped_start_x = x; m_clipped_start_y = y; m_status = status_line_to; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::line_to_no_clip(int x, int y) { if(m_status != status_initial) { m_outline.line_to(x * XScale, y); m_status = status_line_to; } } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::close_polygon_no_clip() { if(m_status == status_line_to) { m_outline.line_to(m_clipped_start_x * XScale, m_clipped_start_y); m_status = status_closed; } } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::clip_segment(int x, int y) { unsigned flags = clipping_flags(x, y, m_clip_box); if(m_prev_flags == flags) { if(flags == 0) { if(m_status == status_initial) { move_to_no_clip(x, y); } else { line_to_no_clip(x, y); } } } else { int cx[4]; int cy[4]; unsigned n = clip_liang_barsky(m_prev_x, m_prev_y, x, y, m_clip_box, cx, cy); const int* px = cx; const int* py = cy; while(n--) { if(m_status == status_initial) { move_to_no_clip(*px++, *py++); } else { line_to_no_clip(*px++, *py++); } } } m_prev_flags = flags; m_prev_x = x; m_prev_y = y; } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::add_vertex(double x, double y, unsigned cmd) { if(is_close(cmd)) { close_polygon(); } else { if(is_move_to(cmd)) { move_to(poly_coord(x), poly_coord(y)); } else { if(is_vertex(cmd)) { line_to(poly_coord(x), poly_coord(y)); } } } } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::move_to(int x, int y) { if(m_clipping) { if(m_outline.sorted()) { reset(); } if(m_status == status_line_to) { close_polygon(); } m_prev_x = m_start_x = x; m_prev_y = m_start_y = y; m_status = status_initial; m_prev_flags = clipping_flags(x, y, m_clip_box); if(m_prev_flags == 0) { move_to_no_clip(x, y); } } else { move_to_no_clip(x, y); } } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::line_to(int x, int y) { if(m_clipping) { clip_segment(x, y); } else { line_to_no_clip(x, y); } } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::close_polygon() { if(m_clipping) { clip_segment(m_start_x, m_start_y); } close_polygon_no_clip(); } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::move_to_d(double x, double y) { move_to(poly_coord(x), poly_coord(y)); } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> void rasterizer_scanline_aa<XScale, AA_Shift>::line_to_d(double x, double y) { line_to(poly_coord(x), poly_coord(y)); } //------------------------------------------------------------------------ template<unsigned XScale, unsigned AA_Shift> bool rasterizer_scanline_aa<XScale, AA_Shift>::hit_test(int tx, int ty) { close_polygon(); const cell_aa* const* cells = m_outline.cells(); if(m_outline.num_cells() == 0) return false; int cover = 0; const cell_aa* cur_cell = *cells++; for(;;) { int alpha; int coord = cur_cell->packed_coord; int x = cur_cell->x; int y = cur_cell->y; if(y > ty) return false; int area = cur_cell->area; cover += cur_cell->cover; while((cur_cell = *cells++) != 0) { if(cur_cell->packed_coord != coord) break; area += cur_cell->area; cover += cur_cell->cover; } if(area) { alpha = calculate_alpha((cover << (poly_base_shift + 1)) - area); if(alpha) { if(tx == x && ty == y) return true; } x++; } if(!cur_cell) break; if(cur_cell->x > x) { alpha = calculate_alpha(cover << (poly_base_shift + 1)); if(alpha) { if(ty == y && tx >= x && tx <= cur_cell->x) return true; } } } return false; }}#endif
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -