Skip to content

Commit fc23dcb

Browse files
committed
Merge remote-tracking branch 'ibrahim/camera_fixes'
2 parents fbf34a2 + 43baef4 commit fc23dcb

File tree

7 files changed

+472
-243
lines changed

7 files changed

+472
-243
lines changed

libraries/Himax_HM01B0/himax.cpp

+222-93
Original file line numberDiff line numberDiff line change
@@ -50,6 +50,7 @@ memory mounted on GAPUINO board.
5050

5151
/* Includes ------------------------------------------------------------------*/
5252
#include "himax.h"
53+
#include "camera.h"
5354

5455
/** @addtogroup BSP
5556
* @{
@@ -77,93 +78,122 @@ memory mounted on GAPUINO board.
7778
/** @defgroup GAPUINO_HIMAX_Private_Variables I2C Private Variables
7879
* @{
7980
*/
81+
#define HIMAX_LINE_LEN_PCK_QVGA 0x178
82+
#define HIMAX_FRAME_LENGTH_QVGA 0x104
83+
84+
#define HIMAX_LINE_LEN_PCK_QQVGA 0x178
85+
#define HIMAX_FRAME_LENGTH_QQVGA 0x084
86+
8087
static regval_list_t himax_default_regs[] = {
81-
{BLC_TGT, 0x08}, // BLC target :8 at 8 bit mode
82-
{BLC2_TGT, 0x08}, // BLI target :8 at 8 bit mode
83-
{0x3044, 0x0A}, // Increase CDS time for settling
84-
{0x3045, 0x00}, // Make symetric for cds_tg and rst_tg
85-
{0x3047, 0x0A}, // Increase CDS time for settling
86-
{0x3050, 0xC0}, // Make negative offset up to 4x
87-
{0x3051, 0x42},
88-
{0x3052, 0x50},
89-
{0x3053, 0x00},
90-
{0x3054, 0x03}, // tuning sf sig clamping as lowest
91-
{0x3055, 0xF7}, // tuning dsun
92-
{0x3056, 0xF8}, // increase adc nonoverlap clk
93-
{0x3057, 0x29}, // increase adc pwr for missing code
94-
{0x3058, 0x1F}, // turn on dsun
95-
{0x3059, 0x1E},
96-
{0x3064, 0x00},
97-
{0x3065, 0x04}, // pad pull 0
98-
99-
{BLC_CFG, 0x43}, // BLC_on, IIR
100-
101-
{0x1001, 0x43}, // BLC dithering en
102-
{0x1002, 0x43}, // blc_darkpixel_thd
103-
{0x0350, 0x00}, // Dgain Control
104-
{BLI_EN, 0x01}, // BLI enable
105-
{0x1003, 0x00}, // BLI Target [Def: 0x20]
106-
107-
{DPC_CTRL, 0x01}, // DPC option 0: DPC off 1 : mono 3 : bayer1 5 : bayer2
108-
{0x1009, 0xA0}, // cluster hot pixel th
109-
{0x100A, 0x60}, // cluster cold pixel th
110-
{SINGLE_THR_HOT, 0x90}, // single hot pixel th
111-
{SINGLE_THR_COLD, 0x40}, // single cold pixel th
112-
{0x1012, 0x00}, // Sync. shift disable
113-
{0x2000, 0x07},
114-
{0x2003, 0x00},
115-
{0x2004, 0x1C},
116-
{0x2007, 0x00},
117-
{0x2008, 0x58},
118-
{0x200B, 0x00},
119-
{0x200C, 0x7A},
120-
{0x200F, 0x00},
121-
{0x2010, 0xB8},
122-
{0x2013, 0x00},
123-
{0x2014, 0x58},
124-
{0x2017, 0x00},
125-
{0x2018, 0x9B},
126-
127-
{AE_CTRL, 0x01}, //Automatic Exposure
128-
{AE_TARGET_MEAN, 0x3C}, //AE target mean [Def: 0x3C]
129-
{AE_MIN_MEAN, 0x0A}, //AE min target mean [Def: 0x0A]
130-
131-
{INTEGRATION_H, 0x01}, //Integration H [Def: 0x01]
132-
{INTEGRATION_L, 0x08}, //Integration L [Def: 0x08]
133-
{ANALOG_GAIN, 0x00}, //Analog Global Gain [Def: 0x00]
134-
{DAMPING_FACTOR, 0x20}, //Damping Factor [Def: 0x20]
135-
{DIGITAL_GAIN_H, 0x01}, //Digital Gain High [Def: 0x01]
136-
{DIGITAL_GAIN_L, 0x00}, //Digital Gain Low [Def: 0x00]
137-
138-
{CONVERGE_IN_TH, 0x03}, //Converge in threshold [Def: 0x03]
139-
{CONVERGE_OUT_TH, 0x05}, //Converge out threshold [Def: 0x05]
140-
{MAX_INTG_H, 0x01}, //Maximum INTG High Byte [Def: 0x01]
141-
{MAX_INTG_L, 0x54}, //Maximum INTG Low Byte [Def: 0x54]
142-
{MAX_AGAIN_FULL, 0x03}, //Maximum Analog gain in full frame mode [Def: 0x03]
143-
{MAX_AGAIN_BIN2, 0x04}, //Maximum Analog gain in bin2 mode [Def: 0x04]
144-
145-
{0x210B, 0xC0},
146-
{0x210E, 0x00}, //Flicker Control
147-
{0x210F, 0x00},
148-
{0x2110, 0x3C},
149-
{0x2111, 0x00},
150-
{0x2112, 0x32},
151-
152-
{0x2150, 0x30},
153-
{0x0340, 0x02},
154-
{0x0341, 0x16},
155-
{0x0342, 0x01},
156-
{0x0343, 0x78},
157-
{0x3010, 0x01}, // 324 x 244 pixel
158-
{0x0383, 0x01},
159-
{0x0387, 0x01},
160-
{0x0390, 0x03},
161-
{0x3011, 0x70},
162-
{0x3059, 0x02},
163-
{0x3060, 0x00},
164-
//{0x0601, 0x01},
165-
{IMG_ORIENTATION, 0x00},
166-
{0x0104, 0x01}
88+
{BLC_TGT, 0x08}, // BLC target :8 at 8 bit mode
89+
{BLC2_TGT, 0x08}, // BLI target :8 at 8 bit mode
90+
{0x3044, 0x0A}, // Increase CDS time for settling
91+
{0x3045, 0x00}, // Make symetric for cds_tg and rst_tg
92+
{0x3047, 0x0A}, // Increase CDS time for settling
93+
{0x3050, 0xC0}, // Make negative offset up to 4x
94+
{0x3051, 0x42},
95+
{0x3052, 0x50},
96+
{0x3053, 0x00},
97+
{0x3054, 0x03}, // tuning sf sig clamping as lowest
98+
{0x3055, 0xF7}, // tuning dsun
99+
{0x3056, 0xF8}, // increase adc nonoverlap clk
100+
{0x3057, 0x29}, // increase adc pwr for missing code
101+
{0x3058, 0x1F}, // turn on dsun
102+
{0x3059, 0x1E},
103+
{0x3064, 0x00},
104+
{0x3065, 0x04}, // pad pull 0
105+
106+
{BLC_CFG, 0x43}, // BLC_on, IIR
107+
108+
{0x1001, 0x43}, // BLC dithering en
109+
{0x1002, 0x43}, // blc_darkpixel_thd
110+
{0x0350, 0x7F}, // Dgain Control
111+
{BLI_EN, 0x01}, // BLI enable
112+
{0x1003, 0x00}, // BLI Target [Def: 0x20]
113+
114+
{DPC_CTRL, 0x01}, // DPC option 0: DPC off 1 : mono 3 : bayer1 5 : bayer2
115+
{0x1009, 0xA0}, // cluster hot pixel th
116+
{0x100A, 0x60}, // cluster cold pixel th
117+
{SINGLE_THR_HOT, 0x90}, // single hot pixel th
118+
{SINGLE_THR_COLD, 0x40}, // single cold pixel th
119+
{0x1012, 0x00}, // Sync. shift disable
120+
{0x2000, 0x07},
121+
{0x2003, 0x00},
122+
{0x2004, 0x1C},
123+
{0x2007, 0x00},
124+
{0x2008, 0x58},
125+
{0x200B, 0x00},
126+
{0x200C, 0x7A},
127+
{0x200F, 0x00},
128+
{0x2010, 0xB8},
129+
{0x2013, 0x00},
130+
{0x2014, 0x58},
131+
{0x2017, 0x00},
132+
{0x2018, 0x9B},
133+
134+
{AE_CTRL, 0x01}, //Automatic Exposure
135+
{AE_TARGET_MEAN, 0x3C}, //AE target mean [Def: 0x3C]
136+
{AE_MIN_MEAN, 0x0A}, //AE min target mean [Def: 0x0A]
137+
{CONVERGE_IN_TH, 0x03}, //Converge in threshold [Def: 0x03]
138+
{CONVERGE_OUT_TH, 0x05}, //Converge out threshold [Def: 0x05]
139+
{MAX_INTG_H, (HIMAX_FRAME_LENGTH_QVGA-2)>>8}, //Maximum INTG High Byte [Def: 0x01]
140+
{MAX_INTG_L, (HIMAX_FRAME_LENGTH_QVGA-2)&0xFF}, //Maximum INTG Low Byte [Def: 0x54]
141+
{MAX_AGAIN_FULL, 0x03}, //Maximum Analog gain in full frame mode [Def: 0x03]
142+
{MAX_AGAIN_BIN2, 0x04}, //Maximum Analog gain in bin2 mode [Def: 0x04]
143+
{MAX_DGAIN, 0xC0},
144+
145+
{INTEGRATION_H, 0x01}, //Integration H [Def: 0x01]
146+
{INTEGRATION_L, 0x08}, //Integration L [Def: 0x08]
147+
{ANALOG_GAIN, 0x00}, //Analog Global Gain [Def: 0x00]
148+
{DAMPING_FACTOR, 0x20}, //Damping Factor [Def: 0x20]
149+
{DIGITAL_GAIN_H, 0x01}, //Digital Gain High [Def: 0x01]
150+
{DIGITAL_GAIN_L, 0x00}, //Digital Gain Low [Def: 0x00]
151+
152+
{FS_CTRL, 0x00}, //Flicker Control
153+
154+
{FS_60HZ_H, 0x00},
155+
{FS_60HZ_L, 0x3C},
156+
{FS_50HZ_H, 0x00},
157+
{FS_50HZ_L, 0x32},
158+
159+
{MD_CTRL, 0x30},
160+
{FRAME_LEN_LINES_H, HIMAX_FRAME_LENGTH_QVGA>>8},
161+
{FRAME_LEN_LINES_L, HIMAX_FRAME_LENGTH_QVGA&0xFF},
162+
{LINE_LEN_PCK_H, HIMAX_LINE_LEN_PCK_QVGA>>8},
163+
{LINE_LEN_PCK_L, HIMAX_LINE_LEN_PCK_QVGA&0xFF},
164+
{QVGA_WIN_EN, 0x01}, // Enable QVGA window readout
165+
{0x0383, 0x01},
166+
{0x0387, 0x01},
167+
{0x0390, 0x00},
168+
{0x3011, 0x70},
169+
{0x3059, 0x02},
170+
{OSC_CLK_DIV, 0x0B},
171+
{IMG_ORIENTATION, 0x00}, // change the orientation
172+
{0x0104, 0x01},
173+
};
174+
175+
static regval_list_t himax_qvga_regs[] = {
176+
{0x0383, 0x01},
177+
{0x0387, 0x01},
178+
{0x0390, 0x00},
179+
{MAX_INTG_H, (HIMAX_FRAME_LENGTH_QVGA-2)>>8},
180+
{MAX_INTG_L, (HIMAX_FRAME_LENGTH_QVGA-2)&0xFF},
181+
{FRAME_LEN_LINES_H, (HIMAX_FRAME_LENGTH_QVGA>>8)},
182+
{FRAME_LEN_LINES_L, (HIMAX_FRAME_LENGTH_QVGA&0xFF)},
183+
{LINE_LEN_PCK_H, (HIMAX_LINE_LEN_PCK_QVGA>>8)},
184+
{LINE_LEN_PCK_L, (HIMAX_LINE_LEN_PCK_QVGA&0xFF)},
185+
};
186+
187+
static regval_list_t himax_qqvga_regs[] = {
188+
{0x0383, 0x03},
189+
{0x0387, 0x03},
190+
{0x0390, 0x03},
191+
{MAX_INTG_H, (HIMAX_FRAME_LENGTH_QQVGA-2)>>8},
192+
{MAX_INTG_L, (HIMAX_FRAME_LENGTH_QQVGA-2)&0xFF},
193+
{FRAME_LEN_LINES_H, (HIMAX_FRAME_LENGTH_QQVGA>>8)},
194+
{FRAME_LEN_LINES_L, (HIMAX_FRAME_LENGTH_QQVGA&0xFF)},
195+
{LINE_LEN_PCK_H, (HIMAX_LINE_LEN_PCK_QQVGA>>8)},
196+
{LINE_LEN_PCK_L, (HIMAX_LINE_LEN_PCK_QQVGA&0xFF)},
167197
};
168198

169199
/* SPI transfer command sequence array */
@@ -207,8 +237,12 @@ uint8_t HIMAX_Open(void)
207237

208238
//printf("Model: %x:%x\n", HIMAX_RegRead(MODEL_ID_H), HIMAX_RegRead(MODEL_ID_L));
209239

210-
if (HIMAX_Reset()!=0) return -1;
211-
//HIMAX_Boot();
240+
if (HIMAX_Reset()!=0) {
241+
return -1;
242+
}
243+
244+
HIMAX_Boot();
245+
212246
//For debugging camera Configuration
213247
//HIMAX_PrintReg();
214248
HAL_Delay(200);
@@ -220,9 +254,105 @@ uint8_t HIMAX_Open(void)
220254
* @brief This function selects HIMAX camera mode.
221255
* @retval None
222256
*/
223-
void HIMAX_Mode(uint8_t mode)
257+
int HIMAX_Mode(uint8_t mode)
258+
{
259+
return HIMAX_RegWrite(MODE_SELECT, mode);
260+
}
261+
262+
int HIMAX_SetResolution(uint32_t resolution)
224263
{
225-
HIMAX_RegWrite(MODE_SELECT, mode);
264+
int ret = 0;
265+
uint32_t regs_count = 0;
266+
regval_list_t *regs = NULL;
267+
268+
switch (resolution) {
269+
case CAMERA_R160x120:
270+
regs = himax_qqvga_regs;
271+
regs_count = sizeof(himax_qqvga_regs) / sizeof(regval_list_t);
272+
break;
273+
case CAMERA_R320x240:
274+
regs = himax_qvga_regs;
275+
regs_count = sizeof(himax_qvga_regs) / sizeof(regval_list_t);
276+
break;
277+
default:
278+
return -1;
279+
}
280+
281+
for(uint32_t i = 0; i < regs_count; i++) {
282+
ret |= HIMAX_RegWrite(regs[i].reg_num, regs[i].value);
283+
}
284+
285+
return ret;
286+
}
287+
288+
int HIMAX_SetFramerate(uint32_t framerate)
289+
{
290+
uint8_t osc_div = 0;
291+
// binning is enabled for QQVGA
292+
uint8_t binning = HIMAX_RegRead(BINNING_MODE) & 0x03;
293+
294+
switch (framerate) {
295+
case 15:
296+
osc_div = (binning) ? 0x00 : 0x01;
297+
break;
298+
case 30:
299+
osc_div = (binning) ? 0x01 : 0x02;
300+
break;
301+
case 60:
302+
osc_div = (binning) ? 0x02 : 0x03;
303+
break;
304+
case 120:
305+
// Set to max FPS for QVGA and QQVGA.
306+
osc_div = 0x03;
307+
break;
308+
default:
309+
return -1;
310+
}
311+
312+
return HIMAX_RegWrite(OSC_CLK_DIV, 0x08 | osc_div);
313+
}
314+
315+
int HIMAX_EnableMD(bool enable)
316+
{
317+
int ret = HIMAX_ClearMD();
318+
if (enable) {
319+
ret |= HIMAX_RegWrite(MD_CTRL, 0x03);
320+
} else {
321+
ret |= HIMAX_RegWrite(MD_CTRL, 0x30);
322+
}
323+
return ret;
324+
}
325+
326+
int HIMAX_SetMDThreshold(uint32_t low, uint32_t high)
327+
{
328+
int ret = 0;
329+
ret |= HIMAX_RegWrite(MD_THL, low & 0xff);
330+
ret |= HIMAX_RegWrite(MD_THH, high & 0xff);
331+
return ret;
332+
}
333+
334+
int HIMAX_SetLROI(uint32_t x1, uint32_t y1, uint32_t x2, uint32_t y2)
335+
{
336+
int ret = 0;
337+
ret |= HIMAX_RegWrite(MD_LROI_X_START_H, (x1>>8));
338+
ret |= HIMAX_RegWrite(MD_LROI_X_START_L, (x1&0xff));
339+
ret |= HIMAX_RegWrite(MD_LROI_Y_START_H, (y1>>8));
340+
ret |= HIMAX_RegWrite(MD_LROI_Y_START_L, (y1&0xff));
341+
ret |= HIMAX_RegWrite(MD_LROI_X_END_H, (x2>>8));
342+
ret |= HIMAX_RegWrite(MD_LROI_X_END_L, (x2&0xff));
343+
ret |= HIMAX_RegWrite(MD_LROI_Y_END_H, (y2>>8));
344+
ret |= HIMAX_RegWrite(MD_LROI_Y_END_L, (y2&0xff));
345+
return ret;
346+
}
347+
348+
int HIMAX_PollMD()
349+
{
350+
return HIMAX_RegRead(MD_INTERRUPT);
351+
}
352+
353+
int HIMAX_ClearMD()
354+
{
355+
return HIMAX_RegWrite(I2C_CLEAR, 0x01);
226356
}
227357

228358
/**
@@ -284,13 +414,12 @@ static uint8_t HIMAX_Boot()
284414
uint32_t i;
285415

286416
for(i = 0; i < (sizeof(himax_default_regs) / sizeof(regval_list_t)); i++) {
287-
//printf("%d\n", i);
288417
HIMAX_RegWrite(himax_default_regs[i].reg_num, himax_default_regs[i].value);
289-
//delay(1);
290418
}
291419

292420
HIMAX_RegWrite(PCLK_POLARITY, (0x20 | PCLK_FALLING_EDGE));
293421

422+
HIMAX_RegWrite(MODE_SELECT, HIMAX_Standby);
294423
return 0;
295424
}
296425

@@ -354,4 +483,4 @@ static uint8_t HIMAX_PrintReg()
354483

355484
/**
356485
* @}
357-
*/
486+
*/

0 commit comments

Comments
 (0)