source: nanovis/trunk/PointSetRenderer.cpp @ 4901

Last change on this file since 4901 was 4167, checked in by ldelgass, 10 years ago

Texture environment is not part of texture object stored state, so don't set
environment mode before loading textures, should be done at render time.

  • Property svn:eol-style set to native
File size: 4.2 KB
Line 
1/* -*- mode: c++; c-basic-offset: 4; indent-tabs-mode: nil -*- */
2/*
3 * Copyright (c) 2004-2013  HUBzero Foundation, LLC
4 *
5 */
6#include <GL/glew.h>
7
8#include <Image.h>
9#include <ImageLoaderFactory.h>
10#include <ImageLoader.h>
11#include <util/FilePath.h>
12
13#include "PointSetRenderer.h"
14#include "PCASplit.h"
15
16using namespace nv;
17using namespace nv::util;
18using namespace vrmath;
19using namespace PCA;
20
21#define USE_TEXTURE
22//#define USE_SHADER
23#define POINT_SIZE 5
24
25PointSetRenderer::PointSetRenderer()
26{
27    _shader = new PointShader();
28    std::string path = FilePath::getInstance()->getPath("particle2.bmp");
29    if (path.empty()) {
30        ERROR("Particle image not found");
31        return;
32    }
33
34    ImageLoader *loader = ImageLoaderFactory::getInstance()->createLoader("bmp");
35    Image *image = loader->load(path.c_str(), Image::IMG_RGBA);
36    unsigned char *bytes = (unsigned char *)image->getImageBuffer();
37    if (bytes) {
38        for (unsigned int y = 0; y < image->getHeight(); ++y) {
39            for (unsigned int x = 0; x < image->getWidth(); ++x, bytes += 4) {
40                bytes[3] = (bytes[0] == 0) ? 0 : 255;
41            }
42        }
43    }
44
45    if (image) {
46        _pointTexture = new Texture2D(image->getWidth(), image->getHeight(),
47                                      GL_UNSIGNED_BYTE, GL_LINEAR,   
48                                      4, image->getImageBuffer());
49    } else {
50        ERROR("Failed to load particle image");
51    }
52
53    delete loader;
54    delete image;
55    _bucketSort = new BucketSort(1024);
56}
57
58PointSetRenderer::~PointSetRenderer()
59{
60}
61
62void PointSetRenderer::renderPoints(Point *points, int length)
63{
64    Point *p = points;
65    for (int i = 0; i < length; ++i, ++p) {
66        glColor4f(p->color.r, p->color.g, p->color.b, p->color.a);
67        glVertex3f(p->position.x, p->position.y, p->position.z);
68    }
69}
70
71void PointSetRenderer::renderCluster(ClusterList** bucket, int size, int level)
72{
73    float quadratic[] = { 1.0f, 0.0f, 0.01f };
74
75    glEnable(GL_POINT_SPRITE_ARB);
76    glPointParameterfvARB(GL_POINT_DISTANCE_ATTENUATION_ARB, quadratic);
77    glPointParameterfARB(GL_POINT_FADE_THRESHOLD_SIZE_ARB, 60.0f);
78    glPointParameterfARB(GL_POINT_SIZE_MIN_ARB, 1.0f);
79    glPointParameterfARB(GL_POINT_SIZE_MAX_ARB, 100);
80#ifdef USE_TEXTURE
81    glTexEnvi(GL_POINT_SPRITE_ARB, GL_COORD_REPLACE_ARB, GL_TRUE);
82#endif
83
84    bool setSize = false;
85    glBegin(GL_POINTS);
86
87    ClusterList *p;
88    for (int i = size - 1; i >= 0; --i) {
89        p = bucket[i];
90        if (p) {
91            if (!setSize) {
92#ifdef USE_SHADER
93                _shader->setScale(p->data->points[0].size);
94#endif
95                setSize = true;
96            }
97        }
98
99        while (p) {
100            renderPoints(p->data->points, p->data->numOfPoints);
101
102            p = p->next;
103        }
104    }
105
106    glEnd();
107
108    glDisable(GL_POINT_SPRITE_ARB);
109    glPointSize(1);
110}
111
112void PointSetRenderer::render(ClusterAccel *cluster, const Matrix4x4d& mat,
113                              int sortLevel, const Vector3f& scale, const Vector3f& origin)
114{
115    _bucketSort->init();
116    _bucketSort->sort(cluster, mat, sortLevel);
117
118    glDisable(GL_TEXTURE_2D);
119
120#ifdef USE_TEXTURE
121    _pointTexture->activate();
122    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
123#endif
124
125    glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
126    //glBlendFunc(GL_SRC_ALPHA, GL_ONE);
127    glEnable(GL_BLEND);
128
129    glDisable(GL_LIGHTING);
130    glEnable(GL_COLOR_MATERIAL);
131
132    glEnable(GL_VERTEX_PROGRAM_POINT_SIZE);
133    glPushMatrix();
134    float s = 1.0f / scale.x;
135    Vector3f shift(origin.x + scale.x * 0.5, origin.x + scale.x * 0.5, origin.x + scale.x * 0.5);
136    glScalef(s, scale.y / scale.x * s, scale.z / scale.x * s);
137
138    //glTranslatef(-shift.x, -shift.y, -shift.z);
139
140#ifdef USE_SHADER
141    _shader->bind();
142#else
143    glPointSize(POINT_SIZE);
144#endif
145    renderCluster(_bucketSort->getBucket(), _bucketSort->getSize(), 4);
146#ifdef USE_SHADER
147    _shader->unbind();
148#else
149    glPointSize(1.0f);
150#endif
151
152    glPopMatrix();
153
154    glDisable(GL_COLOR_MATERIAL);
155    glEnable(GL_LIGHTING);
156    glDisable(GL_VERTEX_PROGRAM_POINT_SIZE);
157    glDisable(GL_BLEND);
158
159#ifdef USE_TEXTURE
160    glTexEnvi(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE);
161    _pointTexture->deactivate();
162#endif
163}
Note: See TracBrowser for help on using the repository browser.