obraz kolorow -> skala szarosci (wielostopniowa)

0

Chce napisac program zamieniajacy obraz kolorowy (w RGB) w n-stopniowa skale szarosci (n jest podawane przez uzytkownika). Jesli n = 2 to ma byc to tylko czern i biel, jesli n = 3 to czern, biel i jeden odcien posredni, itd. Drugie dosc istotne zalozenie jest takie, by uzyskany obraz byl jak najlepszej jakosci (oczywiscie jesli jest wiele metod). Jaka metode najlepiej zastosowac?

Z gory dzieki.

0

Najlepiej wylicz średnią z R,G i B i zamień je na otrzymana wartość. Jeśli ci potrzeba możesz też łatwo zaookrąglić tą wartość. Na przykład jeśli n=16 to program dzieli 256 na 16 i zamienia średnią na najbliższą wartość...progi wynoszą wtedy 0, 0x10, 0x20, 0x30, etc. Więc jeśli wyjdzie przyladowo średnia 0x27 to zamieni wartość R,G i B na 0x30

0

hehe wdepnales wlasnie w ten sam syf w ktorym siedze od jakiegos czasu :D
to tak, teoretycznie jest to dosc proste :)

masz obraz rgb zamieniasz go na rgb w skali szarosci (srednia arytmetyczna w kazdy kanal, lub wartosci liczone ze wzoru ktory bardziej odpowiada charakterystyce ludzkiego oka), nastepnie musisz zaimplementowac kwantyzacje kolorów, na 256 mozliwych do uzyskania barwach mozesz zastosowac prosty algorytm na najwieksza ilosc powtorzen lub popularnosciowy. jak juz to przemieli twoj obraz to otrzymujesz n wartosci z najbardziej znaczacymi kolorami.

Jezeli chcesz miec cos takiego ze przy 2 barwach masz tylko czern i biel to zrob sobie generacje palety, na podstawie dzielenia
"pasma" na 2..256 sektorow. w ktorym kazdy to jakies nasycenie schodzące ku bieli. wtedy nie potrzebna ci kwantyzacja a kolor w tabeli dla kazdego piksela mozesz obliczyc poprzez obliczenie odleglosci eukulidesowej w przestrzeni RGB do kazdego z n kolorow z tabeli.

0

na razie proboje konwertowac do 256-stopniowej skali i nie bardzo mi to wychodzi, tzn z takiego obrazka: http://img20.imageshack.us/my.php?image=0614if.jpg dostaje taki: http://img20.imageshack.us/my.php?image=fout5po.png i nie wiem co jest nie tak.

Procedura konwersji wyglada tak:

	char bgr[3];	// piksel odczytany w BGR
	char grayBgr[3];
	char gray;		// piksel w skali szarosci
	int pnt = 0;
	DWORD rBytes;

	for( int i=1; i<=bmpSize/3; i++) {
			memcpy(bgr,bmp+pnt,3);		// odczytaj piksel w BGR
			//gray = (bgr[2]*77 + bgr[1]*150 + bgr[0]*29) / 256;	// konwertuj do skali szarosci
			//gray = 0.3*bgr[2] + 0.59*bgr[1] + 0.1*bgr[0];
			gray = (bgr[0]+bgr[1]+bgr[2])/3;
			grayBgr[0] = gray;	grayBgr[1] = gray;	grayBgr[2] = gray;
			memcpy(bmp+pnt,grayBgr,3); // nadpisz stary piksel
			pnt += 3;		// nastepny piksel
	}
	// utworz plik wyjsciowy
	HANDLE fout = CreateFile("C:\\fout.bmp",GENERIC_WRITE,0,0,CREATE_ALWAYS,0,0);
	// zapisz naglowek
	WriteFile(fout,header,54,&rBytes,0);
	// zapisz bitmape wynikowa
	WriteFile(fout,bmp,bmpSize,&rBytes,0);
	delete[] bmp;
	CloseHandle(fout);

bmpSize to rozmiar bitmapy, bmp to bitmapa zczytana z pliku .bmp. Plik wyjsciowy ma ten sam naglowek co wejsciowy. A BGR dlatego bo w plikach .BMP RGB zapisane jest odwrotnie. Efekt jest taki sam dla obu sposobow obliczania szarosci. Jakis pomysl?

jezeli chcesz miec cos takiego ze przy 2 barwach masz tylko czern i biel to zrob sobie generacje palety, na podstawie dzielenia
"pasma" na 2..256 sektorow. w ktorym kazdy to jakies nasycenie schodzące ku bieli. wtedy nie potrzebna ci kwantyzacja a kolor w tabeli dla kazdego piksela mozesz obliczyc poprzez obliczenie odleglosci eukulidesowej w przestrzeni RGB do kazdego z n kolorow z tabeli.

no wlasnie tak chce to zrobic, moze dla uproszczenia bede konwertowal tak: obraz kolorowy-> 256 skala szarosci-> n-stopniowa.

0

na moje oko to masz chyba przekroczenie zakresu
sproboj tak:

short gray;
unsigned char bgr[3], grayBgr[3];

i teraz w petli:
gray = (bgr[0]+bgr[1]+bgr[2])/3;
jezeli dalej bedzie sie szmacic to:

gray = ((short)bgr[0]+(short)bgr[1]+(short)bgr[2])/3;

0
cepa napisał(a)

na moje oko to masz chyba przekroczenie zakresu
sproboj tak:

short gray;
unsigned char bgr[3], grayBgr[3];

i teraz w petli:
gray = (bgr[0]+bgr[1]+bgr[2])/3;
jezeli dalej bedzie sie szmacic to:

gray = ((short)bgr[0]+(short)bgr[1]+(short)bgr[2])/3;

pomoglo, dzieki wielkie.

1 użytkowników online, w tym zalogowanych: 0, gości: 1