Модераторы: Rickert, Alexeis, BorisVorontsov
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Проблема с VBO 
V
    Опции темы
newinfo2005
Дата 18.9.2010, 19:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 42
Регистрация: 12.6.2008
Где: где-то тут

Репутация: нет
Всего: нет



Привет, всем))
Пишу игру с использованием OpenGL.
Проблема возникла с VBO.
Я натянул на расширение это два класса, первой VBO, который инициализирует это расширение, а второй GPUBuffer неопсредственно работающий с буфером, чтобы было проще с ним работать.
Проблема заключается в том, что применяя свой же класс ландшафт рендрендиться отлично и без вылетов, а чтобы отрендрендить какую-нить модель из файла ASE (тоже реализовано этой в отдельном классе ModelASE) , то вылетает на glDrawArray с ошибкой 0xC000005 что обращение идет к 0x0000000 адресу.
Как побороть данный баг?
привожу код ниже:
Код

ModelASE::ModelASE(char *path, bool buf_)
    {
                       ...........                          
        isbuf = buf_;
                                          .............    
                    arr_obj[i].buf_vertex = GPUBuffer();
                    arr_obj[i].buf_normal = GPUBuffer();
                    if (t_sub_obj.num_mat != -1)
                    {
                        arr_obj[i].buf_texcoord = GPUBuffer();
                    }

                    arr_obj[i].buf_vertex.InitBuf(GL_ARRAY_BUFFER_ARB,GL_STATIC_DRAW_ARB);
                    arr_obj[i].buf_normal.InitBuf(GL_ARRAY_BUFFER_ARB,GL_STATIC_DRAW_ARB);
                    if (t_sub_obj.num_mat != -1)
                    {
                        arr_obj[i].buf_texcoord.InitBuf(GL_ARRAY_BUFFER_ARB,GL_STATIC_DRAW_ARB);
                    }

                    arr_obj[i].buf_vertex.ActBuf((GLubyte *)vertex_arr,arr_obj[i].num_face_cl*9*sizeof(GLfloat));
                    arr_obj[i].buf_normal.ActBuf((GLubyte *)normal_arr,arr_obj[i].num_face_cl*9*sizeof(GLfloat));
                    if (t_sub_obj.num_mat != -1) arr_obj[i].buf_texcoord.ActBuf((GLubyte *)tex_arr,arr_obj[i].num_face_cl*6*sizeof(GLfloat));
                    
                    arr_obj[i].buf_vertex.BindBuf(3,GL_FLOAT,0,GL_VERTEX_ARRAY,GL_VERTEX_ARRAY);
                    arr_obj[i].buf_normal.BindBuf(3,GL_FLOAT,0,GL_NORMAL_ARRAY,GL_NORMAL_ARRAY);
                    if (t_sub_obj.num_mat != -1) arr_obj[i].buf_texcoord.BindBuf(2,GL_FLOAT,0,GL_TEXTURE_COORD_ARRAY,GL_TEXTURE_COORD_ARRAY);
                    
                    free(vertex_arr);
                    free(normal_arr);
                    if (t_sub_obj.num_mat != -1) free(tex_arr);
                    DisableAllStateClient();
                }
            }

    }
void ModelASE::Render() //Рендрендинг модели на сцену
{
    sub_obj t_sub_obj;
    mat_obj t_mat_obj;
    glEnable(GL_TEXTURE_2D);
    for(int i = 0; i<arr_obj.size();i+=1)
    {
        glPushMatrix();
        t_sub_obj = arr_obj[i];
                              .....
        if (!t_sub_obj.isbuf)
        {
                                   .....
                  }
        } else
        {
            arr_obj[i].buf_vertex.BindBuf();
            arr_obj[i].buf_normal.BindBuf();
            if (arr_obj[i].num_mat != -1) arr_obj[i].buf_texcoord.BindBuf();
            glColor3f(1.0f,1.0f,1.0f);
            glDrawArrays(GL_TRIANGLES,0,arr_obj[i].num_face_cl*3); // здесь вылетает
            DisableAllStateClient();
            
        }
 .....
    }
}

Код

typedef void (APIENTRY * PFNGLBINDBUFFERARBPROC) (GLenum target, GLuint buffer);
typedef void (APIENTRY * PFNGLDELETEBUFFERSARBPROC) (GLsizei n, const GLuint *buffers);
typedef void (APIENTRY * PFNGLGENBUFFERSARBPROC) (GLsizei n, GLuint *buffers);
typedef void (APIENTRY * PFNGLBUFFERDATAARBPROC) (GLenum target, int size, const GLvoid *data, GLenum usage);

class VBO
{
public:
    PFNGLGENBUFFERSARBPROC glGenBuffersARB; // VBO Name Generation Procedure
    PFNGLBINDBUFFERARBPROC glBindBufferARB; // VBO Bind Procedure
    PFNGLBUFFERDATAARBPROC glBufferDataARB; // VBO Data Loading Procedure
    PFNGLDELETEBUFFERSARBPROC glDeleteBuffersARB;  
    bool isdelete;
    VBO();
    bool InitVBO();
    bool IsExtensionSupported(char* szTargetExtension );
    void DeleteVBO();
    ~VBO();
};
class GPUBuffer
{
private:
  GLuint id;
  GLenum target;
  GLenum usage;
  VBO vbo;
  GLint size;
  GLint size_p;
  GLenum type;
  GLint stride;
  GLenum typebuf;
  GLenum typeclient;
public:
    bool Error;
    bool isdelete;
    GPUBuffer();
    void InitBuf(GLenum target_,GLenum usage_);
    void ActBuf(GLubyte *data,GLuint size_);
    void ActBuf(GLubyte *data,GLuint size_,GLenum target_,GLenum usage_);
    void BindBuf();
    void BindBuf(GLint size_,GLenum type_,GLint stride_,GLenum typebuf_,GLenum typeclient_);
    
    GLuint GetId();
    GLenum GetTarget();
    GLenum GetUsage();
    GLint GetSize();
    GLenum GetType();
    GLint GetStride();
    GLenum GetTypebuf();
    GLenum GetTypeClient();
    void SetTarget(GLenum _target);
    void SetUsage(GLenum _usage);
    void SetSize(GLint _size);
    void SetType(GLenum _type);
    void SetStride(GLint _stride);
    void SetTypebuf(GLenum _typebuf);
    void DeleteGPUBuffer();
    void SetTypeClient(GLenum typeclient_);
    ~GPUBuffer();
};

    VBO::VBO()
    {
        glGenBuffersARB = NULL; // VBO Name Generation Procedure
        glBindBufferARB = NULL; // VBO Bind Procedure
        glBufferDataARB = NULL; // VBO Data Loading Procedure
        glDeleteBuffersARB = NULL;  
        isdelete = false;
    }
    bool VBO::InitVBO()
    {
//        if(IsExtensionSupported( "GL_ARB_vertex_buffer_object" ))
          {
            glGenBuffersARB = (PFNGLGENBUFFERSARBPROC) wglGetProcAddress("glGenBuffersARB");
            glBindBufferARB = (PFNGLBINDBUFFERARBPROC) wglGetProcAddress("glBindBufferARB");
            glBufferDataARB = (PFNGLBUFFERDATAARBPROC) wglGetProcAddress("glBufferDataARB");
            glDeleteBuffersARB = (PFNGLDELETEBUFFERSARBPROC) wglGetProcAddress("glDeleteBuffersARB");
            return true;
          }
        return false;
    }
    bool VBO::IsExtensionSupported(char* szTargetExtension )
    {
        const unsigned char *pszExtensions = NULL;
        const unsigned char *pszStart;
        unsigned char *pszWhere, *pszTerminator;
        // Имя расширения не должно содержать пробелы
        pszWhere = (unsigned char *) strchr( szTargetExtension, ' ' );
        if( pszWhere || *szTargetExtension == '\0' )
          return false;
        // Получить строку расширения

        pszExtensions = (unsigned char *)glGetString(GL_VERSION);
        // Поиск в строке расширений
        pszStart = pszExtensions;
        for(;;)
        {
            pszWhere = (unsigned char *) strstr( (const char *) pszStart, szTargetExtension );
            if( !pszWhere )
                break;
            pszTerminator = pszWhere + strlen( szTargetExtension );
            if( pszWhere == pszStart || *( pszWhere - 1 ) == ' ' )
                if( *pszTerminator == ' ' || *pszTerminator == '\0' )
                    return true;
            pszStart = pszTerminator;
        }
        return false;
    }
    void VBO::DeleteVBO()
    {

    }
    VBO::~VBO()
    {
        if(isdelete) DeleteVBO();
    }

    GPUBuffer::GPUBuffer()
    {
        Error = false;
        isdelete = false;
        vbo = VBO();
        if (vbo.InitVBO()) return;
        Error = true;
    }
    void GPUBuffer::InitBuf(GLenum target_,GLenum usage_)
    {
        target = target_;
        usage = usage_;
        vbo.glGenBuffersARB(1,&id);
    }
    void GPUBuffer::ActBuf(GLubyte *data,GLuint size_)
    {
        ActBuf(data,size_,target,usage);
    }
    void GPUBuffer::ActBuf(GLubyte *data,GLuint size_,GLenum target_,GLenum usage_)
    {
            size = size_;
            target = target_;
            usage = usage_;
            vbo.glBindBufferARB(target,id);
            vbo.glBufferDataARB(target,size,data,usage_);
    }
    void GPUBuffer::BindBuf()
    {
        BindBuf(size_p,type,stride,typebuf,typeclient);
    }
    void GPUBuffer::BindBuf(GLint size_,GLenum type_,GLint stride_,GLenum typebuf_,GLenum typeclient_)
    {
        size_p = size_;
        type = type_;
        stride = stride_;
        typebuf = typebuf_;
        typeclient = typeclient_;
        glEnableClientState(typeclient_);
        vbo.glBindBufferARB(target,id);
        switch(typeclient_)
        {
        case GL_VERTEX_ARRAY:
            glVertexPointer(size_p,type,stride,NULL);
            break;
        case GL_TEXTURE_COORD_ARRAY:
            glTexCoordPointer(size_p,type,stride,NULL);
            break;
        case GL_NORMAL_ARRAY:
            glNormalPointer(type,stride,NULL);
            break;
        case GL_COLOR_ARRAY:
            glColorPointer(size_p,type,stride,NULL);
            break;
        }
    }
    void GPUBuffer::SetTypeClient(GLenum typeclient_)
    {
        typeclient = typeclient_;
    }
    GLenum GPUBuffer::GetTypeClient()
    {
        return typeclient;
    }
    GLuint GPUBuffer::GetId()
    {
        return id;
    }
    GLenum GPUBuffer::GetTarget()
    {
        return target;
    }
    GLenum GPUBuffer::GetUsage()
    {
        return usage;
    }
    GLint GPUBuffer::GetSize()
    {
        return size;
    }
    GLenum GPUBuffer::GetType()
    {
        return type;
    }
    GLint GPUBuffer::GetStride()
    {
        return stride;
    }
    GLenum GPUBuffer::GetTypebuf()
    {
        return typebuf;
    }

    void GPUBuffer::SetTarget(GLenum _target)
    {
        target = _target;
    }
    void GPUBuffer::SetUsage(GLenum _usage)
    {
        usage = _usage;
    }
    void GPUBuffer::SetSize(GLint _size)
    {
        size = _size;
    }
    void GPUBuffer::SetType(GLenum _type)
    {
        type = _type;
    }
    void GPUBuffer::SetStride(GLint _stride)
    {
        stride = _stride;
    }
    void GPUBuffer::SetTypebuf(GLenum _typebuf)
    {
        typebuf = _typebuf;
    }
    void GPUBuffer::DeleteGPUBuffer()
    {
        vbo.glDeleteBuffersARB(1,&id);
    }
    GPUBuffer::~GPUBuffer()
    {
        if (isdelete) DeleteGPUBuffer();
    }
void DisableAllStateClient()
{
    glDisableClientState( GL_VERTEX_ARRAY ); // запрет вершинных массивов
    glDisableClientState( GL_TEXTURE_COORD_ARRAY );
    glDisableClientState( GL_NORMAL_ARRAY );
    glDisableClientState( GL_COLOR_ARRAY );        
}

PM MAIL ICQ   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Вы можете найти полезным что...
Alexeis
Rickert
  • Английская документация по DirectX лежит где-то здесь.
  • Английская документация по OpenGL лежит где-то там.
  • Гейм-дев у нас обсуждают где-то тут

Ждём вас! С уважением, Alexeis, Rickert.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Мультимедия, OpenGL/DirectX | Следующая тема »


 




[ Время генерации скрипта: 0.0790 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.