Skocz do zawartości

Konwersja danych i pixele


PsichiX

Rekomendowane odpowiedzi

Witam. Mam dwa ważne pytania:

1. Jest jakiś sposób na konwersję typów danych, np. double->int, itp.?

2. W jaki sposób można prowadzić operacje bezpośrednio na pixelach całego ekranu? W SDL jest to możliwe, ale SDL tworzy osobne okno i w nim rysuje, a mi zależy na bezpośrednim dostępie do każdego pixela ekranu.

 

Bardzo proszę o odpowiedź na te dwa pytania, z góry dziękuję. :)

Pozdrawiam.

Odnośnik do komentarza
Udostępnij na innych stronach

Dzięki wam, tylko jakiej (jakich) funkcji użyć do rysowania pixela (bo nie za bardzo znam WinAPI)?

Jeśli ktoś wie jaka jest do tego funkcja/funkcje to bardzo prosiłbym by je podał.

Lub chociaż jakiś tutek lub przykład w którym jest ta funkcja do rysowania pixeli bezpośrednio na ekranie. Będę ogromnie wdzięczny :)

 

Pozdrawiam

Odnośnik do komentarza
Udostępnij na innych stronach

Nie pamiętam za bardzo bo nie używam często Win aPI tylko na stworzenie okna do DirectX i czasem do obsługi klawiatury ale jestem pewien, że było to w początkowych numerach WARP'a i w części o Win API "Megatutorialu". Powinno być w rozdziale o pędzlach.

Odnośnik do komentarza
Udostępnij na innych stronach

Wielkie dzieki will - od tego zalezy czy XenoN bedzie chodzil szybciej :D

W razie gdybys cos znalazl na ten temat to napisz na PW. A gdybys mial gdzies zrodlo swojego programiku do rysowania po ekranie i był tak mily i dal choc wycinek z tym kodem to bede Tobie do konca zycia wdzieczny i zawsze pomoge w gm :)

I jeszcze raz dziękuję =D

Odnośnik do komentarza
Udostępnij na innych stronach

#include <string>

#include <sstream>

#define WIN32_LEAN_AND_MEAN

#include <windows.h>

#include <windowsx.h>

 

 

// dane okna

std::string g_strKlasaOkna = "od0dogk_ColorPicker_Window";

HWND g_hwndOkno = NULL;

 

// uchwyt do kontekstu ekranu

HDC g_hdcEkran = NULL;

 

// pobrany kolor

COLORREF g_clKolor = RGB(255, 255, 255); // początkowo biały

 

 

// --- procedura zdarzeniowa okna ---

 

LRESULT CALLBACK WindowEventProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)

{

switch (uMsg)

{

case WM_LBUTTONDOWN:

// łapiemy myszkę

SetCapture (hWnd);

 

// ustawiamy kursor w kształcie celownika

SetCursor (LoadCursor(NULL, IDC_CROSS));

return 0;

 

case WM_MOUSEMOVE:

// sprawdzamy, czy myszka jest złapana

if (GetCapture() == hWnd)

{

// odczytujemy współrzędne kursora

POINT ptKursor;

ptKursor.x = GET_X_LPARAM(lParam);

ptKursor.y = GET_Y_LPARAM(lParam);

 

// przeliczamy je na koordynaty ekranowe

ClientToScreen (hWnd, &ptKursor);

 

// pobieramy kolor z miejsca, gdzie jest kursor myszy

g_clKolor = GetPixel(g_hdcEkran, ptKursor.x, ptKursor.y);

 

// wymuszamy odświeżenie okna programu, aby pokazać pobrany kolor

InvalidateRect (hWnd, NULL, TRUE);

}

return 0;

 

case WM_LBUTTONUP:

// uwalniamy mysz

ReleaseCapture();

 

// ustawiamy kursor strzałki

SetCursor (LoadCursor(NULL, IDC_ARROW));

return 0;

 

case WM_PAINT:

{

// odrysowanie zawartości okna

{

PAINTSTRUCT ps;

HDC hdcOkno;

 

// zaczynamy

hdcOkno = BeginPaint(hWnd, &ps);

 

// pobieramy obszar klienta okna

RECT rcObszarKlienta;

GetClientRect (hWnd, &rcObszarKlienta);

 

// wypełniamy go pobranym kolorem

// w tym celu najpierw tworzymy odpowiedni pędzel,

// a potem wypełniamy prostokąt obszaru klienta

// potem usuwamy pędzel

HBRUSH hbrPedzel = CreateSolidBrush(g_clKolor);

FillRect (hdcOkno, &rcObszarKlienta, hbrPedzel);

DeleteObject (hbrPedzel);

 

// kończymy rysowanie

EndPaint (hWnd, &ps);

}

 

// pokazanie składowych RGB koloru

{

// pobieramy te składowe i konwertujemy na napis

std::stringstream Strumien;

Strumien << "RGB: " << (int) GetRValue(g_clKolor) << ", "

<< (int) GetGValue(g_clKolor) << ", "

<< (int) GetBValue(g_clKolor);

 

// ustawiamy ten napis jako tytuł okna programu

SetWindowText (hWnd, Strumien.str().c_str());

}

 

return 0;

}

 

case WM_DESTROY:

// zwalniamy kontekst ekranu

ReleaseDC (NULL, g_hdcEkran);

 

// kończymy program

PostQuitMessage (0);

return 0;

}

 

return DefWindowProc(hWnd, uMsg, wParam, lParam);

}

 

 

// --- funkcja WinMain() ---

 

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int nCmdShow)

{

/* rejestrujemy klasę okna */

 

WNDCLASSEX KlasaOkna;

 

// wypełniamy strukturę WNDCLASSEX

ZeroMemory (&KlasaOkna, sizeof(WNDCLASSEX));

KlasaOkna.cbSize = sizeof(WNDCLASSEX);

KlasaOkna.hInstance = hInstance;

KlasaOkna.lpfnWndProc = WindowEventProc;

KlasaOkna.lpszClassName = g_strKlasaOkna.c_str();

KlasaOkna.hCursor = LoadCursor(NULL, IDC_ARROW);

KlasaOkna.hIcon = LoadIcon(NULL, IDI_APPLICATION);

 

// rejestrujemy klasę okna

RegisterClassEx (&KlasaOkna);

 

 

/* tworzymy okno */

 

// tworzymy okno funkcją CreateWindowEx

g_hwndOkno = CreateWindowEx(WS_EX_TOOLWINDOW,

g_strKlasaOkna.c_str(),

NULL,

WS_OVERLAPPED | WS_BORDER | WS_CAPTION | WS_SYSMENU,

0, 0,

125,

80,

NULL,

NULL,

hInstance,

NULL);

 

// pokazujemy nasze okno i je od razu odświeżamy

ShowWindow (g_hwndOkno, nCmdShow);

UpdateWindow (g_hwndOkno);

 

 

/* pobieramy kontekst urządzenia ekranu */

g_hdcEkran = GetDC(NULL);

 

 

/* pętla komunikatów */

 

MSG msgKomunikat;

while (GetMessage(&msgKomunikat, NULL, 0, 0))

{

TranslateMessage (&msgKomunikat);

DispatchMessage (&msgKomunikat);

}

 

// zwracamy kod wyjścia

return static_cast<int>(msgKomunikat.wParam);

}

 

 

 

to dość ciekawy programik i bardzo łatwy ;] a z tym rysowaniem poszukam gdzieś go mam xD

P.S srry za długi post xD

Odnośnik do komentarza
Udostępnij na innych stronach

Dzieki! Gdy XenoN bedzie gotowy to pelna wersja laduje do Ciebie na bank, a jak chcesz by w czyms pomóc to pisz na PW :)

Odnośnik do komentarza
Udostępnij na innych stronach

// Scribble - okienkowy szkicownik

 

#include <string>

#define WIN32_LEAN_AND_MEAN

#include <windows.h>

#include <windowsx.h>

 

 

// nazwa klasy okna

std::string g_strKlasaOkna = "od0dogk_Window";

 

// dane okna

HDC g_hdcOkno; // uchwyt kontekstu urządzenia okna

 

 

// --- procedura zdarzeniowa okna ---

 

LRESULT CALLBACK WindowEventProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)

{

switch (uMsg)

{

case WM_LBUTTONDOWN:

// przejmujemy myszkę

SetCapture (hWnd);

 

// przesuwamy pióro (służące do rysowania po oknie) w punkt kliknięcia

MoveToEx (g_hdcOkno, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam), NULL);

 

// zwracamy zero

return 0;

 

case WM_MOUSEMOVE:

// jeżeli nasze okno posiada myszkę

if (GetCapture() == hWnd)

// rysujemy linie od poprzedniego do aktualnego miejsca kursora myszki

LineTo (g_hdcOkno, GET_X_LPARAM(lParam), GET_Y_LPARAM(lParam));

 

// zwracamy zero

return 0;

 

case WM_LBUTTONUP:

// oddajemy władzę nad myszką do systemu

ReleaseCapture();

return 0;

 

//--------------------------------------------------------------------------------

 

case WM_DESTROY:

// kończymy program

PostQuitMessage (0);

return 0;

}

 

return DefWindowProc(hWnd, uMsg, wParam, lParam);

}

 

 

// --- funkcja WinMain() ---

 

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, LPSTR, int nCmdShow)

{

/* rejestrujemy klasę okna */

 

WNDCLASSEX KlasaOkna;

 

// wypełniamy strukturę WNDCLASSEX

ZeroMemory (&KlasaOkna, sizeof(WNDCLASSEX));

KlasaOkna.cbSize = sizeof(WNDCLASSEX);

KlasaOkna.hInstance = hInstance;

KlasaOkna.lpfnWndProc = WindowEventProc;

KlasaOkna.lpszClassName = g_strKlasaOkna.c_str();

KlasaOkna.hCursor = LoadCursor(NULL, IDC_ARROW);

KlasaOkna.hIcon = LoadIcon(NULL, IDI_APPLICATION);

KlasaOkna.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH); // białe tło

KlasaOkna.style = CS_OWNDC; // własny kontekst urządzenia okna

 

// rejestrujemy klasę okna

RegisterClassEx (&KlasaOkna);

 

 

/* tworzymy okno */

 

// tworzymy okno funkcją CreateWindowEx

HWND hOkno = NULL;

hOkno = CreateWindowEx(NULL, // rozszerzony styl okna

g_strKlasaOkna.c_str(), // klasa okna

"Szkicownik", // tekst na pasku tytułu

WS_OVERLAPPEDWINDOW, // styl okna

CW_USEDEFAULT, // współrzędna pozioma

CW_USEDEFAULT, // współrzędna pionowa

CW_USEDEFAULT, // szerokość

CW_USEDEFAULT, // wysokość

NULL, // uchwyt do okna nadrzędnego

NULL, // uchwyt do menu

hInstance, // uchwyt do instancji aplikacji

NULL); // dodatkowe dane

 

// pobieramy uchwyt do kontekstu urządzenia obszaru klienta okna

g_hdcOkno = GetDC(hOkno);

 

// pokazujemy nasze okno

ShowWindow (hOkno, nCmdShow);

 

 

/* pętla komunikatów */

 

MSG msgKomunikat;

while (GetMessage(&msgKomunikat, NULL, 0, 0))

{

TranslateMessage (&msgKomunikat);

DispatchMessage (&msgKomunikat);

}

 

// zwracamy kod wyjścia

return static_cast<int>(msgKomunikat.wParam);

}

 

 

Tu masz malowanie w oknie ale z tego co pamiętam zmień tylko w GetDC argument na NULL zamiast hOkno.

Wtedy będziesz mógł malować po pulpicie.

Odnośnik do komentarza
Udostępnij na innych stronach

Jeśli chodzi Ci o rysowanie pixel po pixelu to mam rozwiązanie.

 

Kod DLLa (C++, w C::B )

    #define exportdll extern "C" __declspec(dllexport)

    #include <windows.h>

    HDC gmHDC;
    HWND gmHWND;

    exportdll double Init ( double hwnd )
    {
            int t = (int )hwnd;
            HWND gmHWND = (HWND)t;
            gmHDC = GetDC( gmHWND );
            return 1;
    }

    exportdll double DrawPixel ( double x, double y, double color )
    {
            SetPixel( gmHDC, (int)x, (int)y, (COLORREF) color );
            return 1;
    }

 

W GMie coś takiego:

//   Definiujemy funkcje DLLa
     dll = 'winds.dll';
     call = dll_stdcall;
     ex[0] = external_define( dll, 'Init', call, ty_real, 1, ty_real );
     ex[1] = external_define( dll, 'DrawPixel', call, ty_real, 3, ty_real, ty_real, ty_real );

//   Musimy wyłączyć rysowanie GMa
     set_automatic_draw( false );
     screen_redraw();

//   Inicjacja
     external_call( ex[0], window_handle() ); 

//   Rysujemy czerwony pixel w punkcje (10, 10)
     external_call( ex[1], 10, 10, c_red );

Do testowania tu:

http://www.gmclan.org/up152_3_winds.html

Klik, klik.

Odnośnik do komentarza
Udostępnij na innych stronach

Wielkie dzieki Tymon, jeśli chodzi o c++ to jestes moim BOGIEM :D Masz u mnie ogromny respect, jak sie kiedys spotkamy to na bank stawiam Ci piwo (opcjonalnie inny 'soczek' :P ). Jeszcze raz ogromne dzieki Tymonowi (za perfekcyjne odgadniecie mysli0 i Will'owi (za niezbedne naprowadzenie) - a jednak c++ nie jest az tak trudny, wystarczy studiowac przyklady zawansowanych w tym temacie i mozna sie szybko nauczyc :) Wielkie dzieki wam obu - nareszcie ruszy XenoN.GL - szybszy, wydajniejszy i z lepsza grafika.

 

Mam jeszcze tylko male pytanko: czy renderowanie scen metoda raytracingu (w szczegolnosci backward raytracingu) jest oplacalne (chodzi o szybkosc, bo efektow graficznych jestem pewien)?

Odnośnik do komentarza
Udostępnij na innych stronach

Jeśli chcesz dodać odpowiedź, zaloguj się lub zarejestruj nowe konto

Jedynie zarejestrowani użytkownicy mogą komentować zawartość tej strony.

Zarejestruj nowe konto

Załóż nowe konto. To bardzo proste!

Zarejestruj się

Zaloguj się

Posiadasz już konto? Zaloguj się poniżej.

Zaloguj się
  • Ostatnio przeglądający   0 użytkowników

    • Brak zarejestrowanych użytkowników przeglądających tę stronę.
×
×
  • Dodaj nową pozycję...