Maison >développement back-end >C++ >Comment puis-je gérer en toute sécurité les objets OpenGL dans les classes C RAII ?

Comment puis-je gérer en toute sécurité les objets OpenGL dans les classes C RAII ?

Susan Sarandon
Susan Sarandonoriginal
2024-11-25 10:52:11495parcourir

How Can I Safely Manage OpenGL Objects within C   RAII Classes?

Objets OpenGL dans les classes C RAII : pièges et solutions

Dans les classes C RAII, les membres sont automatiquement libérés lorsque l'objet sort de la portée pour assurer la désallocation des ressources. Cependant, lorsque vous traitez des objets OpenGL dans de telles classes, des conséquences inattendues peuvent survenir.

Considérez le code suivant :

class BufferObject
{
private:
  GLuint buff_;

public:
  BufferObject() { glGenBuffers(1, &buff_); }
  ~BufferObject() { glDeleteBuffers(1, &buff_); }
  // Other members
};

Cette classe gère un objet tampon OpenGL, qui doit être supprimé dans le destructeur. Cependant, des erreurs inattendues se produisent lors de la tentative de copie ou de déplacement-construction de ces objets.

Le problème provient du manque de copie explicite ou de déplacement de constructeurs/opérateurs d'affectation. Le constructeur de copie généré par le compilateur copie simplement les variables membres, ce qui conduit à deux objets partageant le même objet tampon OpenGL. Lorsqu'un objet est détruit, l'autre devient invalide, ce qui entraîne des erreurs.

De même, la fonction InitBuffer :

BufferObject InitBuffer()
{
  BufferObject buff;
  // Do stuff with `buff`
  return buff;
}

échoue également car le buff est détruit après avoir été copié dans la valeur de retour.

Pour résoudre ces pièges, des types de déplacement uniquement doivent être utilisés. En C , cela signifie supprimer le constructeur de copie et l'opérateur d'affectation de copie, tout en fournissant des équivalents de déplacement qui transfèrent la propriété :

class BufferObject
{
private:
  GLuint buff_;

public:
  BufferObject() { glGenBuffers(1, &buff_); }
  BufferObject(const BufferObject&) = delete; // no copy constructor
  BufferObject& operator=(const BufferObject&) = delete; // no copy assignment

  BufferObject(BufferObject&& other) : buff_(other.buff_) { other.buff_ = 0; }
  BufferObject& operator=(BufferObject&& other)
  {
    if(this != &other)
    {
      Release(); // release current resource
      buff_ = other.buff_;
      other.buff_ = 0;
    }
    return *this;
  }
  ~BufferObject() { Release(); }
  void Release() { if(buff_) glDeleteBuffers(1, &buff_); }
  // Other members
};

Avec ces modifications, la copie et le déplacement des instances BufferObject deviennent sécurisés et les ressources OpenGL sont gérées correctement dans le modèle RAII.

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn