-
Notifications
You must be signed in to change notification settings - Fork 9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Several small improvements #3
base: master
Are you sure you want to change the base?
Changes from 1 commit
05c4587
0a01bcd
ac42708
a889235
0f526c7
423977f
c0f3877
b2a950e
f290689
22f3acf
5252078
1213f9e
18d809e
b239de6
8746d6a
83d9275
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -316,27 +316,48 @@ int main(int argc, char *argv[]) | |
uint16_t *channel = out_buf[channel_ordering[bayer_order][i]]; | ||
int mid_value_avg = 0; | ||
int count = 0; | ||
//Average out the centre 64 pixels. | ||
for (x=(single_channel_width>>1)-4; x<=(single_channel_width>>1)+4; x++) | ||
{ | ||
for (y=(single_channel_height>>1)-4; y<=(single_channel_height>>1)+4; y++) | ||
{ | ||
mid_value_avg += channel[x + y*single_channel_width]; | ||
count++; | ||
} | ||
} | ||
uint16_t middle_val = (mid_value_avg / count) << 5; | ||
|
||
uint16_t *line; | ||
const char *channel_comments[4] = { | ||
"R", | ||
"Gr", | ||
"Gb", | ||
"B" | ||
}; | ||
printf("Middle_val is %d\n", middle_val); | ||
}; | ||
|
||
// Search highest value | ||
float max_val = 0; | ||
for (y=0; y<grid_height; y++) | ||
{ | ||
int y_start = y*32; | ||
int y_stop = y_start + 32 <= single_channel_height ? y_start + 32 : single_channel_height; | ||
for (x=0; x<grid_width; x++) | ||
{ | ||
int x_start = x*32; | ||
int x_stop = x_start + 32 <= single_channel_width ? x_start + 32 : single_channel_width; | ||
|
||
float block_val = 0; | ||
uint16_t block_px = 0; | ||
|
||
for(int y_px = y_start; y_px < y_stop; y_px++){ | ||
line = &channel[y_px*(single_channel_width)]; | ||
for(int x_px = x_start; x_px < x_stop; x_px++){ | ||
block_val += line[x_px]; | ||
block_px++; | ||
} | ||
} | ||
|
||
block_val /= block_px; | ||
if(block_val > max_val){ | ||
max_val = block_val; | ||
} | ||
} | ||
} | ||
|
||
max_val *= 32; | ||
printf("Max_val is %.0f\n", max_val); | ||
fprintf(header, "//%s - Ch %d\n", channel_comments[i], channel_ordering[bayer_order][i]); | ||
uint16_t *line; | ||
|
||
// Calculate gain for each block | ||
for (y=0; y<grid_height; y++) | ||
{ | ||
int y_start = y*32; | ||
|
@@ -356,11 +377,11 @@ int main(int argc, char *argv[]) | |
block_px++; | ||
} | ||
} | ||
int gain = (middle_val*block_px) / block_sum; | ||
int gain = (max_val*block_px) / block_sum + 0.5; | ||
if (gain > 255) | ||
gain = 255; //Clip as uint8_t | ||
else if (gain < 32) | ||
gain = 32; //Clip at x1.0 | ||
gain = 32; //Clip at x1.0, should never happen | ||
fprintf(header, "%d, ", gain ); | ||
fprintf(table, "%d %d %d %d\n", x * 32 + 16, y * 32 + 16, gain, i ); | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This feels wrong. Enlarging the average to 5x5, or even up as far as 9x9 would be reasonable, but otherwise you're ignoring a large amount of the detail. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I do not know which algorithm is used for the interpolation. I don't see a problem with this approach. From my point of view and for my applications the results are better. There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I've been thinking again. If you look at lens shading across the width (alternatively across the height), the brightness will be a function similar to figure a. The average value changes only slightly with the width of the viewed area. However, the brightness signal from the sensor is subject to noise (figure b). A wider area improves the average value. Only in case of peaks smaller areas are better (figure c). In this case, however, the peak would have to lie exactly in a calculation area. Or am I misunderstanding something? There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Integrated a parameter for the cell size. |
||
uint8_t gain_bin = gain; | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Without a better description I can't say for certain what this is meant to be doing, but it's very ugly to run the same loop twice, once to find this max_val, and then again to compute the cell gains.
Allocate arrays for block_val and block_px (if it's really necessary) and compute once. Calculating the gains then becomes an iteration over those arrays instead of the whole image.
(Sorry, embedded programming always makes you think of more efficient code).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Running the loop twice is of course not a high-performance solution. But it runs very fast on my Raspberry Pi 3B ;-)
Quick and dirty - I will fix it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Double calculation loop removed