Bild men ingen text med MAX7456 (typ löst!)

Övriga diskussioner relaterade till komponenter. Exempelvis radiorör, A/D, kontaktdon eller sensorer.
Användarvisningsbild
JonasJ
Inlägg: 653
Blev medlem: 11 september 2007, 16:02:26
Ort: Kinna
Kontakt:

Bild men ingen text med MAX7456 (typ löst!)

Inlägg av JonasJ »

Hej!

Jag har försökt få igång en MAX7456 ett par kvällar nu utan att lyckats hela vägen. Problemet jag har är att när jag inte har (video)kameran ansluten till den visas texten. När jag kopplar in kameran får jag upp bilden från kameran men ingen text. Jag skulle gärna vilja kunna kombinera dessa så att jag får text och bild samtidigt :)

Jag tror jag gått igenom varenda inställning i databladet och har googlat flera olika kodexempel på nätet bland annat den nedan men lyckas helt enkelt inte få texten att visas samtidigt som bilden. Jag har även provat att byta kameran men det var ingen skillnad.

Kod: Markera allt

#include <avr/io.h>
#include <avr/interrupt.h>


#define RESET PC3	//PB0
#define CS PC2	//PB2
#define MOSI PB5	//PB3
#define MISO PB6	//PB4
#define SCK PB7	//PB5


//Define functions
//======================
void ioinit(void);      //Initializes IO
void delay_ms(uint16_t x); //General purpose delay
void delay_us(int x);
void SPI1_write(char address, char byte);
char SPI1_read(char address);

//======================




int main2 (void)
{
	char x;

    ioinit(); //Setup IO pins and defaults
	
	_delay_ms(1000);
	
	//reset
	PORTC &= ~(1<<RESET);
	_delay_ms(1000);
	PORTC |= (1<<RESET);
	_delay_ms(1000);
	
	SPI_write(0,0x48);	//enable display of OSD image + PAL
	_delay_ms(1);
	
	//automatic black level control, have to read, augment and rewrite
	//The data sheet is rather specific about this
	x = SPI1_read(0xEC);	
	_delay_ms(1);
	x &= 0xEF;
	SPI1_write(0x6C,x);
	_delay_ms(1);
	
	SPI1_write(0x04,0);//DMM set to 0
	
	x = 25;
	
	SPI1_write(0x05,0x01);//DMAH
	
	SPI1_write(0x06,x);//DMAL
	SPI1_write(0x07,0x1D);
	
	SPI1_write(0x06,x+1);//DMAL
	SPI1_write(0x07,0x0B);
	
	SPI1_write(0x06,x+2);//DMAL
	SPI1_write(0x07,0x17);
	
	SPI1_write(0x06,x+3);//DMAL
	SPI1_write(0x07,0x1A);
	
	SPI1_write(0x06,x+4);//DMAL
	SPI1_write(0x07,0x16);
	
	SPI1_write(0x06,x+6);//DMAL
	SPI1_write(0x07,0x0F);
	
	
	while(1)
	{
		SPI1_write(0,0x08);	//enable display of OSD image
		_delay_ms(1000);
		SPI1_write(0,0);	//disable display of OSD image
		_delay_ms(1000);
	}
	
	
}

void ioinit (void)
{
	PORTB = 0xFF;
	PORTC = 0xFF;
	DDRB = (1<<MOSI) | (1<<SCK);
	DDRC = (1<<CS) | (1<<RESET);


}

void SPI1_write(char address, char byte)
{
	unsigned char SPICount;                                       // Counter used to clock out the data

	unsigned char SPIData;                                        // Define a data structure for the SPI data
	
	PORTC |= (1<<CS);                                        		// Make sure we start with active-low CS high
	PORTB &= ~(1<<SCK);                                       		// and CK low
	
	SPIData = address;                                            // Preload the data to be sent with Address
	PORTC &= ~(1<<CS);                                           // Set active-low CS low to start the SPI cycle 

	
	for (SPICount = 0; SPICount < 8; SPICount++)                  // Prepare to clock out the Address byte
	{
		if (SPIData & 0x80) PORTB |= (1<<MOSI);           				// Check for a 1 and set the MOSI line appropriately

		else PORTB &= ~(1<<MOSI);
		
		PORTB |= (1<<SCK);                                         // Toggle the clock line
		PORTB &= ~(1<<SCK);
		
		SPIData <<= 1;                                              // Rotate to get the next bit
	}                                                             // and loop back to send the next bit
														
																// Repeat for the Data byte
	SPIData = byte;                                            // Preload the data to be sent with Data
	
	for (SPICount = 0; SPICount < 8; SPICount++)
	{
		if (SPIData & 0x80) PORTB |= (1<<MOSI);

		else PORTB &= ~(1<<MOSI);
		
		PORTB |= (1<<SCK); 
		PORTB &= ~(1<<SCK);
		
		SPIData <<= 1; 
	}           
	
	PORTC |= (1<<CS);
	PORTB &= ~(1<<MOSI);

}


char SPI1_read(char address)
{
	unsigned char SPICount;                                       // Counter used to clock out the data
  
	char SPIData; 
	char temp;
	
	PORTC |= (1<<CS);                                        		// Make sure we start with active-low CS high
	PORTB &= ~(1<<SCK);                                       		// and CK low
	
	SPIData = address;                                            // Preload the data to be sent with Address
	PORTC &= ~(1<<CS);                                           // Set active-low CS low to start the SPI cycle 

	
	for (SPICount = 0; SPICount < 8; SPICount++)                  // Prepare to clock out the Address byte
	{
		if (SPIData & 0x80) PORTB |= (1<<MOSI);           				// Check for a 1 and set the MOSI line appropriately

		else PORTB &= ~(1<<MOSI);
		
		PORTB |= (1<<SCK);                                         // Toggle the clock line
		PORTB &= ~(1<<SCK);
		
		SPIData <<= 1;                                              // Rotate to get the next bit
	}                                                             // and loop back to send the next bit
	

	PORTB &= ~(1<<MOSI);                                         // Reset the MOSI data line
	
	SPIData = 0;
	
	for (SPICount = 0; SPICount < 8; SPICount++)                  // Prepare to clock in the data to be read
	{
		SPIData <<=1;                                               // Rotate the data
		PORTB |= (1<<SCK);                                         // Raise the clock to clock the data out of the MAX7456
		
		temp = PINB;
		if (temp & (1<<MISO)) SPIData |= 1;                       // Read the data bit
		
		PORTB &= ~(1<<SCK);                                       // Drop the clock ready for the next bit
	}                                                             // and loop back
	PORTC |= (1<<CS);                                                 // Raise CS
					  
	return SPIData;                              // Finally return the read data


}
Jag hoppas att någon här känner igen felet och kan tipsa mig vad det kan vara. Har jag trots mina försök missat en inställning eller kan jag ha pajat kretsen?

Edit: MAX7456 sitter på ett breakoutkort från Sparkfun...
Du har inte behörighet att öppna de filer som bifogats till detta inlägg.
Senast redigerad av JonasJ 3 november 2013, 13:59:53, redigerad totalt 1 gång.
B1n4ry
EF Sponsor
Inlägg: 1327
Blev medlem: 30 november 2005, 20:02:50
Ort: Borås
Kontakt:

Re: Bild men ingen text med MAX7456

Inlägg av B1n4ry »

Är det kanske så att du måste skicka in extern sync för att kunna föra overlay på befintlig videosignal?
Jag tolkar tabellen längs ner på sid 11 i databladet lite så.
Med internal sync står det OSD only. Men med extern sync Vin+OSD
Auto väljer nog bara mellan dessa två lägen om jag gissar rätt...

//B1N4RY
Användarvisningsbild
JonasJ
Inlägg: 653
Blev medlem: 11 september 2007, 16:02:26
Ort: Kinna
Kontakt:

Re: Bild men ingen text med MAX7456

Inlägg av JonasJ »

Tack för idéen! Tyvärr var det ingen skillnad. Oavsett hur jag satte bitarna får jag inget overlay på skärm. Men du fick mig att leta vidare och min teori nu är att den byte jag läser från kretsen alltid blir 255. Det konstiga är att alla andra funktioner verkar fungera (visa/gömma displayen, visa/gömma video) och för att aktivera en del av dessa funktioner måste jag först läsa data vilket tyder på att antingen har det slumpat sig så bra (eller kanske dåligt i detta sammanhanget) att det fungerar trots att jag alltid läser 255 eller så är det något annat skumt fel. Jag har beställt en logikanalysator så jag kan se vad som faktiskt skickas över bussen.
Användarvisningsbild
JonasJ
Inlägg: 653
Blev medlem: 11 september 2007, 16:02:26
Ort: Kinna
Kontakt:

Re: Bild men ingen text med MAX7456

Inlägg av JonasJ »

Nu har jag kommit på felet efter att ha inhandlat en logikanalysator från Saleae. För att ändra en bit på en viss adress läser jag först upp hela byten, därefter ändrar jag den aktuella biten och skriver tillbaka hela byten. Problemet är att när jag läser byten får jag bara upp 0x00. Så om jag har ändrat en bit tidigare kommer jag att skriva över den när jag ändrar den andra biten. Om jag istället för att påverka enskilda bitar skriver hela byten samtidigt så att jag aldrig behöver läsa något från kretsen fungerar det.
2013-11-03 13.41.29.jpg
Så här ser det ut när jag läser upp en byte från MAX7456:
saleae.png
Först skriver jag address-byten. I detta fall vill jag läsa från address 0x80. Sedan skickar jag iväg en dummy byte för att skapa klockcyklarna som behövs för att MAX7456:en ska lägga ut datan. Som syns i bilden svarar den men tolkas av logikanalystorn och av AVR som värde 0x00. Jag har även försökt sätta CHPA=1 (att AVR ska läsa signalen vid sista flanken av klocksignalen) men tyvärr fungerar inte det heller (den läser fortfarande värdet som 0x00). Eftersom jag egentligen inte behöver kunna läsa data och inte riktigt har några idéer kvar ger jag upp för tillfället.

För övrigt är jag mäkta imponerad av Saleaes logikanalysator och tillhörande mjukvara. Jag har tidigare kört en logikanalysator för isådär 12000 kr men den kommer inte i närheten av Saleaes. (jo, jag förstår att prestandan på den för 12000 kr är bättre än Saleaes men för mina behov räcker den gott och väl till!). Rekommenderas starkt!

Det jag håller på att bygga är för övrigt en handkontroller för ROV:n med 2 st joystickar och en skärm med touchfunktion.
Du har inte behörighet att öppna de filer som bifogats till detta inlägg.
Skriv svar