kleine simulation mit zwei 4ecken, kollisions abfrage noch fehlerhaft, bitte um hilfe!



  • hab ikhg z mirr dochg ghedacht^^ :p



  • ne, mal ehrlich, schreib des ganze doch ma in eine normale klasse, und mach das erstma nicht mit komischen rechtecken 👎 , sondern mit kreisen 👍 , dann hast du nur eine einzige kollisionsabfrage, da kann viel weniger schiefgehen 👍 , bau da noch impulserhaltungssatz rein, und dann kan man des ganze schon zu einem einfachen pool-spielchen weiterentwickeln, wärst wahrscheinlich schon fertig damit, hätteste gleich mit klassen und methoden angefangen, in dem quellcode blickt doch kein mensch durch, wenn du dir des in einer woche anguggst, verstehste auch nix mehr 😃
    ist echt viel einfacher, für den programmierer, sowie fürn leser



  • grrrr.... ich bin doch erst seit ner knappen woche mit WinApi vertraut gg.. und impulserhaltungssatz ... oO da muss ich sicher noch die math.h includen oO...



  • vieleicht noch etwas... wie kann man bei zwei bewegenden ellipsen eine kollision ermitteln?, könnte hier jemmand nen beispiel bringen?



  • Den Variablentyp nicht anzugeben ist meiner Meinung nach, schlechter Stil, aber is nat. deine Sache 😉



  • Das hat er schon geändert. (Hat er gesagt.)

    Die Probleme liegen IMHO am Spaghetti-Code.

    Greetz, Swordfish



  • Swordfish schrieb:

    Das hat er schon geändert. (Hat er gesagt.)

    Hab ja auch nit gesagt, und auch nicht darauf abgezielt, dass das sein Problem lößt ...
    es sah nur scheiße aus 😃



  • CodeFinder schrieb:

    Hab ja auch nit gesagt, und auch nicht darauf abgezielt, dass das sein Problem lößt ...
    es sah nur scheiße aus 😃

    ACK

    Greetz, Swordfish



  • ist der quelltext besser fuer den adel?

    //---------------------------------------------------------------------------
    
    #include <windows.h>
    #include <conio.h>
    
    LRESULT CALLBACK WinProc( HWND, UINT, WPARAM, LPARAM );
    const char szAppName[] = "MainWnd";
    void move_obj( int &ObjPosX1, int &ObjPosY1, int &ObjPosX2, int &ObjPosY2 );
    
    int WINAPI WinMain( HINSTANCE hInstance, HINSTANCE hPrevInstance,
                        LPSTR lpCmdLine, int nCmdShow )
    {
    
        HWND hWnd;
        MSG messages;
        WNDCLASS wc;
    
        wc.cbClsExtra = NULL;
        wc.cbWndExtra = NULL;
        wc.lpszMenuName = NULL;
        wc.lpszClassName = szAppName;
        wc.hInstance = hInstance;
        wc.lpfnWndProc = WinProc;
        wc.hIcon = LoadIcon( NULL, IDI_APPLICATION );
        wc.hCursor = LoadCursor( NULL, IDC_ARROW );
        wc.hbrBackground = ( HBRUSH ) GetStockObject( LTGRAY_BRUSH );
        wc.style = CS_VREDRAW | CS_HREDRAW;
    
        if( !( RegisterClass( &wc ) ) )
        return 0;
    
        hWnd = CreateWindow( szAppName,
                             "Rectangle move, move, move ...",
                             WS_OVERLAPPED | WS_SYSMENU,
                             CW_USEDEFAULT, CW_USEDEFAULT,
                             750, 500,
                             NULL,
                             NULL,
                             hInstance,
                             NULL );
    
        ShowWindow( hWnd, SW_SHOW );
        UpdateWindow( hWnd );
    
        while( GetMessage( &messages, NULL, NULL, NULL ) ) {
    
            TranslateMessage( &messages );
            DispatchMessage( &messages );
        }
        return messages.wParam;
    }
    
    LRESULT CALLBACK WinProc( HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam ) {
    
        static int Speed = 50;
    
        static int ObjPosX1 = 0;
        static int ObjPosY1 = 140;
    
        static int ObjPosX2 = 210;
        static int ObjPosY2 = 100;
    
        move_obj( ObjPosX1, ObjPosY1, ObjPosX2, ObjPosY2 );
    
        switch( message ) {
    
            case WM_LBUTTONDOWN: {
    
                if( wParam ) {
    
                    Speed -= 10;
    
                    if( Speed < 1 ) {
    
                        Speed = 1;
                    }
                }
                return 0;
            }
    
            case WM_RBUTTONDOWN: {
    
                if( wParam ) {
    
                    Speed += 10;
    
                    if( Speed > 50 ) {
    
                        Speed = 50;
                    }
                }
                return 0;
            }
    
            case WM_PAINT: {
    
                PAINTSTRUCT ps;
                HDC hDc;
    
                hDc = BeginPaint( hWnd, &ps ); {
    
                    Rectangle( hDc, ObjPosX1 + 50,ObjPosY1 + 50,ObjPosX1 + 150,ObjPosY1 + 150 );
                    Rectangle( hDc, ObjPosX2 + 50,ObjPosY2 + 50,ObjPosX2 + 150,ObjPosY2 + 150 );
                    Sleep( Speed );
                    InvalidateRect( hWnd, NULL, TRUE );
    
                }
                EndPaint( hWnd, &ps );
                return 0;
            }
    
            case WM_DESTROY: {
    
                PostQuitMessage( 0 );
                return 0;
            }
        }
        return DefWindowProc( hWnd, message, wParam, lParam );
    }
    
    void move_obj( int &ObjPosX1, int &ObjPosY1, int &ObjPosX2, int &ObjPosY2) {
    
        static int ObjX1 = 1;
        static int ObjY1 = -1;
    
        static int ObjX2 = -1;
        static int ObjY2 = -1;
    
    //--- Kollision von Object1 ----------------------------------------------------
    
                if( ( ObjX1 == 1 ) && ( ObjPosX1 < 595 ) ) {    // Linksbewegung + return
    
                    ++ObjPosX1;
                }
                else if( ObjPosX1 == 595 ) {
    
                    ObjX1 = -1;
                    --ObjPosX1;
                }
    
                if( ( ObjY1 == 1 ) && ( ObjPosY1 < 320 ) ) {     // Abwärtsbewegung + return
    
                    ++ObjPosY1;
                }
                else if( ObjPosY1 == 320 ) {
    
                    ObjY1 = -1;
                    --ObjPosY1;
                }
    
                if( ( ObjX1 == -1 ) && ( ObjPosX1 > -50 ) ) {    // Rechtsbewegung + return
    
                    --ObjPosX1;
                }
                else if( ObjPosX1 == -50 ) {
    
                    ObjX1 = 1;
                    ++ObjPosX1;
                }
    
                if( ( ObjY1 == -1 ) && ( ObjPosY1 > -50 ) ) {     // Aufwärtsbewegung + return
    
                    --ObjPosY1;
                }
                else if( ObjPosY1 == -50 ) {
    
                    ObjY1 = 1;
                    ++ObjPosY1;
                }
    
    //--- Kollision von Object2 ----------------------------------------------------
    
                if( ( ObjX2 == 1 ) && ( ObjPosX2 < 595 ) ) {    // Linksbewegung + return
    
                    ++ObjPosX2;
                }
                else if( ObjPosX2 == 595 ) {
    
                    ObjX2 = -1;
                    --ObjPosX2;
                }
    
                if( ( ObjY2 == 1 ) && ( ObjPosY2 < 320 ) ) {     // Abwärtsbewegung + return
    
                    ++ObjPosY2;
                }
                else if( ObjPosY2 == 320 ) {
    
                    ObjY2 = -1;
                    --ObjPosY2;
                }
    
                if( ( ObjX2 == -1 ) && ( ObjPosX2 > -50 ) ) {    // Rechtsbewegung + return
    
                    --ObjPosX2;
                }
                else if( ObjPosX2 == -50 ) {
    
                    ObjX2 = 1;
                    ++ObjPosX2;
                }
    
                if( ( ObjY2 == -1 ) && ( ObjPosY2 > -50 ) ) {     // Aufwärtsbewegung + return
    
                    --ObjPosY2;
                }
                else if( ObjPosY2 == -50 ) {
    
                    ObjY2 = 1;
                    ++ObjPosY2;
                }
    
    //--- Kollision von Object1 mit Object2 ----------------------------------------
    
        if( (( ObjPosX1 + 150 ) == ( ObjPosX2 + 50 )) &&
            (( ObjPosY1 + 50 <= ObjPosY2 + 150 ) &&
             ( ObjPosY1 + 150 >= ObjPosY2 + 50 )) ) {  // Obj1 trift auf linke seite
                                                       // von obj2
                ObjX1 = -1;
                ObjX2 = 1;
        }
    
        if( (( ObjPosX2 + 150 ) == ( ObjPosX1 + 50 )) &&
            (( ObjPosY2 + 50 <= ObjPosY1 + 150 ) &&
             ( ObjPosY2 + 150 >= ObjPosY1 + 50 )) ) {  // Obj1 trift auf rechte seite
                                                       // von obj2
                ObjX1 = 1;
                ObjX2 = -1;
        }
    
        if( (( ObjPosY1 + 150 ) == ( ObjPosY2 + 50 )) &&
            (( ObjPosX1 + 50 <= ObjPosX2 + 150 ) &&
             ( ObjPosX1 + 150 >= ObjPosX2 + 50 )) ) {  // Obj1 trift auf obere seite
                                                       // von obj2
                ObjY1 = -1;
                ObjY2 = 1;
        }
    
        if( (( ObjPosY2 + 150 ) == ( ObjPosY1 + 50 )) &&
            (( ObjPosX2 + 50 <= ObjPosX1 + 150 ) &&
             ( ObjPosX2 + 150 >= ObjPosX1 + 50 )) ) {  // Obj2 trift auf obere seite
                                                       // von obj1
                ObjY1 = 1;
                ObjY2 = -1;
        }
    
    }
    


  • Swordfish schrieb:

    ACK

    Greetz, Swordfish

    ACK ?



  • jetzt wird man hier auch noch ignorriert.....



  • @CodeFinder:

    ➡ ACK

    T0bi schrieb:

    ist der quelltext besser fuer den adel?

    Ich hab' zwar keine Ahnung, wen du hier mit "Adel" mainst, aber:
    nein, ich seh' immer noch keine Implementierung in Klassen, wie zB:

    #include <vector>
    #include <string>
    #include <ctime>
    
    using namespace std;
    
    #define UNICODE
    #define _UNICODE
    
    #include <windows.h>
    
    const unsigned int timer_id = 100;
    const int num_sprites = 10;
    
    class point {
    
        private:
    
            int _x;
            int _y;
    
        public:
    
            const int &x;
            const int &y;
    
            point( ) : x( _x ), y( _y ) { };
            point( int px, int py ) : _x( px ), _y( py ), x( _x ), y( _y ) { };
            point( const point &other ) : _x( other._x ), _y( other._y ), x( _x ), y( _y ) { };
            ~point( ) { };
    
            point& operator=( const point &other )
            {
                _x = other.x;
                _y = other.y;
                return *this;
            }
    
            void set_x( int px ) { _x = px; };
            void set_y( int py ) { _y = py; };
            void set( int px, int py ) { _x = px; _y = py; };
    
            static point random( int min_x, int min_y, int max_x, int max_y )
            {
                return point( static_cast< int >( min_x + ( ( max_x + 1.0 ) * rand( ) / RAND_MAX ) ),
                              static_cast< int >( min_y + ( ( max_y + 1.0 ) * rand( ) / RAND_MAX ) )
                );
            }
    };
    
    class sprite {
    
        public:
            typedef enum direction_t { NONE, UP_RIGHT, UP_LEFT, DOWN_RIGHT, DOWN_LEFT };
    
        private:
    
            point          _pos;
            point          _max;
            unsigned short _dimension;
            direction_t    _direction;
    
        public:
    
            sprite( ) : _pos( point( 0, 0 ) ), _max( point( 0, 0 ) ), _dimension( 0 ), _direction( NONE ) { };
            sprite( const point& ppos, const point &pmax, unsigned short pdimension, direction_t pdirection ) :
                _dimension( pdimension ), _pos( ppos ), _max( pmax ), _direction( pdirection ) { };
    
            sprite( const sprite &other )
            {
                _pos = other._pos;
                _max = other._max;
                _dimension = other._dimension;
                _direction = other._direction;
            }
    
            void move( )
            {
                switch( _direction ) {
    
                    case UP_RIGHT:
    
                        if( ( ( _pos.y - 1 - _dimension / 2 ) == 0 ) && ( ( _pos.x + 1 + _dimension / 2 ) >= _max.x ) ) {
    
                            _direction = DOWN_LEFT;
    
                        } else if( ( _pos.y - 1 - _dimension / 2 ) == 0 ) {
    
                            _direction = DOWN_RIGHT;
    
                        } else if( ( _pos.x + 1 + _dimension / 2 ) >= _max.x ) {
    
                            _direction = UP_LEFT;
                        }
    
                        _pos.set( _pos.x + 1, _pos.y - 1 );
                        break;
    
                    case UP_LEFT:
    
                        if( ( ( _pos.y - 1 - _dimension / 2 ) == 0 ) && ( ( _pos.x - 1 - _dimension / 2 ) == 0 ) ) {
    
                            _direction = DOWN_RIGHT;
    
                        } else if( ( _pos.y - 1 - _dimension / 2 ) == 0 ) {
    
                            _direction = DOWN_LEFT;
    
                        } else if( ( _pos.x - 1 - _dimension / 2 ) == 0 ) {
    
                            _direction = UP_RIGHT;
    
                        }
    
                        _pos.set( _pos.x - 1, _pos.y - 1 );
                        break;
    
                    case DOWN_RIGHT:
    
                        if( ( ( _pos.y + 1 + _dimension / 2 ) == _max.y ) && ( ( _pos.x + 1 + _dimension / 2 ) >= _max.x ) ) {
    
                            _direction = UP_LEFT;
    
                        } else if( ( _pos.y + 1 + _dimension / 2 ) >= _max.y ) {
    
                            _direction = UP_RIGHT;
    
                        } else if( ( _pos.x + 1 + _dimension / 2 ) >= _max.x ) {
    
                            _direction = DOWN_LEFT;
                        }
    
                        _pos.set( _pos.x + 1, _pos.y + 1 );
                        break;
    
                    case DOWN_LEFT:
    
                        if( ( ( _pos.y + 1 + _dimension / 2 ) >= _max.y ) && ( ( _pos.x - 1 - _dimension / 2 ) == 0 ) ) {
    
                            _direction = UP_RIGHT;
    
                        } else if( ( _pos.y + 1 + _dimension / 2 ) >= _max.y ) {
    
                            _direction = UP_LEFT;
    
                        } else if( ( _pos.x - 1 - _dimension / 2 ) == 0 ) {
    
                            _direction = DOWN_RIGHT;
                        }
    
                        _pos.set( _pos.x - 1, _pos.y + 1 );
                        break;
                }
            }
    
            void draw( HDC *dc )
            {
                Rectangle( *dc, _pos.x - _dimension / 2, _pos.y - _dimension / 2, _pos.x + _dimension / 2, _pos.y + _dimension / 2 );
            }
    
            static direction_t random_direction( )
            {			
                switch( static_cast< int >( 4.0 * rand( ) / RAND_MAX ) ) {
    
                    case 0:
                        return UP_RIGHT;
    
                    case 1:
                        return UP_LEFT;
    
                    case 2:
                        return DOWN_RIGHT;
    
                    case 3:
                        return DOWN_LEFT;
                }
    
                return NONE;
            }
    
            void set_max( point &pmax )
            {
                _max = pmax;
            }
    
    };
    
    basic_string< wchar_t > get_errmsg( unsigned long error );
    
    long __stdcall main_window_proc( HWND window, unsigned int message, unsigned int first, long second );
    
    int __stdcall WinMain( HINSTANCE instance, HINSTANCE prev_instance, char *command_line, int show_state )
    {
        wchar_t main_window_class_name[ ] = L"jd_class";
        wchar_t main_window_title[ ] = L"jd";
    
        WNDCLASS wc;
    
        memset( &wc, 0, sizeof( WNDCLASS ) );
    
        wc.hbrBackground = reinterpret_cast< HBRUSH >( GetStockObject( WHITE_BRUSH ) );
        wc.hCursor       = LoadCursor( 0, IDC_ARROW );
        wc.hIcon         = LoadIcon( 0, IDI_APPLICATION );
        wc.hInstance     = instance;
        wc.lpfnWndProc   = main_window_proc;
        wc.lpszClassName = main_window_class_name;
        wc.style         = CS_HREDRAW | CS_VREDRAW;
    
        if( !RegisterClass( &wc ) ) {
    
            MessageBox( 0, get_errmsg( GetLastError( ) ).c_str( ), L"Error:", MB_OK );
            return 0;
        }
    
        HWND main_window = CreateWindow( main_window_class_name,
                                         main_window_title,
                                         WS_OVERLAPPEDWINDOW,
                                         CW_USEDEFAULT,
                                         CW_USEDEFAULT,
                                         200,
                                         200,
                                         0,
                                         0,
                                         instance,
                                         0
        );
    
        if( !main_window ) {
    
            MessageBox( 0, get_errmsg( GetLastError( ) ).c_str( ), L"Error:", MB_OK );
            return 0;
        }
    
        UpdateWindow( main_window );
        ShowWindow( main_window, show_state );
    
        MSG msg;
    
        while( GetMessage( &msg, main_window, 0, 0 ) ) {
    
            TranslateMessage( &msg );
            DispatchMessage( &msg );
        } 
    
        return static_cast< int >( msg.wParam );
    }
    
    basic_string< wchar_t > get_errmsg( unsigned long error )
    {
        void *buffer;
        FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER | FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS,
                       0,
                       error,
                       MAKELANGID( LANG_NEUTRAL, SUBLANG_DEFAULT ),
                       reinterpret_cast< wchar_t* >( &buffer ),
                       0,
                       0
        );
    
        basic_string< wchar_t > errmsg = reinterpret_cast< wchar_t* >( buffer );
        LocalFree( buffer );
        return errmsg;
    };
    
    long __stdcall main_window_proc( HWND window, unsigned int message, unsigned int first, long second )
    {
        static vector< sprite > sprites;
        RECT rect;
    
        switch( message ) {
    
            case WM_CREATE:
    
                srand( static_cast< unsigned int >( time( 0 ) ) );
    
                GetClientRect( window, &rect );
    
                for( int i = 0; i < num_sprites; ++i ) {
    
                    sprites.push_back( sprite( point::random( 5, 5, rect.right - 5, rect.bottom - 5 ),
                                               point( rect.right, rect.bottom ),
                                               10,
                                               sprite::random_direction( ) )
                    );
                }
    
                SetTimer( window, timer_id, 1, 0 );
                return 0;
    
            case WM_SIZING:
    
                GetClientRect( window, &rect );
    
                for( int i = 0; i < num_sprites; ++i ) {
    
                    sprites[ i ].set_max( point( rect.right, rect.bottom ) );
                }
    
                return 0;
    
            case WM_TIMER:
    
                for( int i = 0; i < num_sprites; ++i ) {
    
                    sprites[ i ].move( );
                }
    
                InvalidateRect( window, 0, true );
                return 0;
    
            case WM_PAINT:
    
                HDC dc;
                PAINTSTRUCT ps;
    
                dc = BeginPaint( window, &ps );
    
                for( i = 0; i < num_sprites; ++i ) {
    
                    sprites[ i ].draw( &dc );
                }
    
                EndPaint( window, &ps );
                return 0;
    
            case WM_DESTROY:
            case WM_CLOSE:
    
                PostQuitMessage( 0 );
                return 0;
        }
    
        return static_cast< long >( DefWindowProc( window, message, first, second ) );
    }
    

    @all: hab' das nur 'mal hingekritzelt also nicht haun... 😉

    Greetz, Swordfish



  • omfg, leute, das ist doch wahnsinn :p Tobi & Swordfish, tut mal der menschheit einen gefallen, und schreibt doch ma nur die codeteile hin, auf die es grad ankommt, glaub kaum dass die probleme mit der kollisionsabfrage an einem falschen icon für die fensterklasse liegen 😃 mit tut das mousewheel schon weh wegen dem ganzen herumscrollen! 😮



  • @tobi: wegen der kollision zweier ellipsen such ma im spieleprogrammierer- oder mathe-forum, da gibts des irgendwo bestimmt 👍
    des mit dem pool-spielchen oder impulserhaltungssatz war übrigens einfach nur giftiger sarkasmus 😃 , sollte nur verdeutlichen, wieviel zeit du wegen dem komischen codeaufbau verlierst
    aber zwei kugeln collidieren zu lassen ist wirklich einfacher als desselbe mit rechtecken zu tun, ein kreuzprodukt, zwei punktprodukte, fertig ist die sache, ohne irgendwelcher endlosen if-verzweigungsdschungeln :p



  • @Swordfish:
    Also du magst keine Makros, aber solche akribischen Abkürzen...wie wärs einfach mit Jo oder ja .... 😃 ...irg wie amüsant^^


Anmelden zum Antworten