| 94 | |
| 95 | //-------------------------------------------------------------------- |
| 96 | template<class Img> void blur_x(Img& img, unsigned radius) |
| 97 | { |
| 98 | if(radius < 1) return; |
| 99 | |
| 100 | unsigned x, y, xp, i; |
| 101 | unsigned stack_ptr; |
| 102 | unsigned stack_start; |
| 103 | |
| 104 | color_type pix; |
| 105 | color_type* stack_pix; |
| 106 | calculator_type sum; |
| 107 | calculator_type sum_in; |
| 108 | calculator_type sum_out; |
| 109 | |
| 110 | unsigned w = img.width(); |
| 111 | unsigned h = img.height(); |
| 112 | unsigned wm = w - 1; |
| 113 | unsigned div = radius * 2 + 1; |
| 114 | |
| 115 | unsigned div_sum = (radius + 1) * (radius + 1); |
| 116 | unsigned mul_sum = 0; |
| 117 | unsigned shr_sum = 0; |
| 118 | unsigned max_val = color_type::base_mask; |
| 119 | |
| 120 | if(max_val <= 255 && radius < 255) |
| 121 | { |
| 122 | mul_sum = stack_blur_tables<int>::g_stack_blur8_mul[radius]; |
| 123 | shr_sum = stack_blur_tables<int>::g_stack_blur8_shr[radius]; |
| 124 | } |
| 125 | |
| 126 | m_buf.allocate(w, 128); |
| 127 | m_stack.allocate(div, 32); |
| 128 | |
| 129 | for(y = 0; y < h; y++) |
| 130 | { |
| 131 | sum.clear(); |
| 132 | sum_in.clear(); |
| 133 | sum_out.clear(); |
| 134 | |
| 135 | pix = img.pixel(0, y); |
| 136 | for(i = 0; i <= radius; i++) |
| 137 | { |
| 138 | m_stack[i] = pix; |
| 139 | sum.add(pix, i + 1); |
| 140 | sum_out.add(pix); |
| 141 | } |
| 142 | for(i = 1; i <= radius; i++) |
| 143 | { |
| 144 | pix = img.pixel((i > wm) ? wm : i, y); |
| 145 | m_stack[i + radius] = pix; |
| 146 | sum.add(pix, radius + 1 - i); |
| 147 | sum_in.add(pix); |
| 148 | } |
| 149 | |
| 150 | stack_ptr = radius; |
| 151 | for(x = 0; x < w; x++) |
| 152 | { |
| 153 | if(mul_sum) sum.calc_pix(m_buf[x], mul_sum, shr_sum); |