Пример #1
0
int main(int argc, char** argv)
#endif
{
	tCreationFlags creationFlags;
	creationFlags.sWindowTitle = "Displacement-mapped sphere";

	int32 width = 640;
	int32 height = 480;

	#ifdef __amigaos4__
	if ( argc == 3 )
	{
		width = iClamp( atoi( argv[1] ), 160, 1600 );
		height = iClamp( atoi( argv[2] ), 160, 1280 );		
	}
	#endif
	
	#ifdef WIN32
	creationFlags.hIcon = LoadIcon( GetModuleHandle( 0 ), MAKEINTRESOURCE( IDI_ICON1 ) );
	#endif
	
	creationFlags.iWindowWidth = width;
	creationFlags.iWindowHeight = height;
	creationFlags.bWindowed = true;

	CDisplacedSphere theApp;
	if( !theApp.bInitialize( creationFlags ) )
		return 1;

	return theApp.iRun();
}
Пример #2
0
// Get's the color at a certain value
ofColor ImgTexture::getColor(int inX, int inY)
{
	iClamp(1, mResizedImage.width-1, inX);
	iClamp(1, mResizedImage.height-1, inY);

	return mResizedImage.getColor(inX, inY);;
}
Пример #3
0
int main(int argc, char** argv)
#endif
{
	tCreationFlags creationFlags;
	creationFlags.sWindowTitle = "Raytracer";
	
	int32 iWidth = 320;
	int32 iHeight = 240;

	#ifdef __amigaos4__
	if ( argc == 3 )
	{
		iWidth = iClamp( atoi( argv[1] ), 160, 1600 );
		iHeight = iClamp( atoi( argv[2] ), 160, 1280 );		
	}
	#endif

	#ifdef WIN32
	creationFlags.hIcon = LoadIcon( GetModuleHandle( 0 ), MAKEINTRESOURCE( IDI_ICON1 ) );
	#endif
	
	creationFlags.iWindowWidth = iWidth;
	creationFlags.iWindowHeight = iHeight;
	creationFlags.bWindowed = true;

	CApp theApp;
	if( !theApp.bInitialize( creationFlags ) )
		return 1;

	return theApp.iRun();
}
Пример #4
0
/** Applies a 5x5 filter to monochrome image I (wrapping at the boundaries) */
static uint8 applyFilter(
    const uint8*    I,
    int             x,
    int             y,
    int             w,
    int             h,
    const float     filter[5][5]) {

    debugAssert(isEven(w));
    debugAssert(isEven(h));

    float sum = 0.0f;
    float denom = 0.0f;

    for (int dy = 0; dy < 5; ++dy) {
        int offset = ((y + dy + h - 2) % h) * w;

        for (int dx = 0; dx < 5; ++dx) {
            float f = filter[dy][dx];
            sum += f * I[((x + dx + w - 2) % w) + offset];
            denom += f;
        }
    }

    return (uint8)iClamp(iRound(sum / denom), 0, 255);
}
Пример #5
0
/**
 @param brighten Most Quake II textures are dark; this argument is a factor to make
 them brighter by.  Default = 1.0, normal intensity.  It is safe to call
 load multiple times-- the previously loaded model will be freed correctly.
*/
TextureRef loadBrightTexture(const std::string& filename, double brighten) {

    alwaysAssertM(fileExists(filename), std::string("Can't find \"") + filename + "\"");

    TextureRef texture;

    if (brighten == 1.0) {

        texture = Texture::fromFile(filename, TextureFormat::RGBA8, Texture::CLAMP);

    } else {

        // Brighten the image
        GImage im(filename);

        if (im.channels == 3) {
            for (int i = im.width * im.height - 1; i >= 0; --i) {
                Color3uint8& color = im.pixel3()[i];

                for (int c = 0; c < 3; ++c) {
                    color[c] = iClamp(color[c] * brighten, 0, 255);
                }
            }

            const uint8* array[1];
            array[0] = im.byte();

            texture = Texture::fromMemory(filename, array, TextureFormat::RGB8, im.width, im.height, 1, TextureFormat::RGB8, Texture::CLAMP);
        } else {
            for (int i = im.width * im.height - 1; i >= 0; --i) {
                Color4uint8& color = im.pixel4()[i];

                for (int c = 0; c < 3; ++c) {
                    color[c] = iClamp(color[c] * brighten, 0, 255);
                }
            }

            const uint8* array[1];
            array[0] = im.byte();

            texture = Texture::fromMemory(filename, array, TextureFormat::RGBA8, im.width, im.height, 1, TextureFormat::RGBA8, Texture::CLAMP);
        }
    }

    return texture;
}
Пример #6
0
void TextOutput::setIndentLevel(int i) {
    indentLevel = i;

    // If there were more pops than pushes, don't let that take us below 0 indent.
    // Don't ever indent more than the number of columns.
    indentSpaces = 
        iClamp(option.spacesPerIndent * indentLevel, 
               0, 
               option.numColumns - 1);
}
Пример #7
0
void Texture::Preprocess::modulateImage(ImageFormat::Code fmt, void* _byte, int n) const {
    debugAssertM(
        (fmt == ImageFormat::CODE_RGB8) ||
        (fmt == ImageFormat::CODE_RGBA8) ||
        (fmt == ImageFormat::CODE_R8) ||
        (fmt == ImageFormat::CODE_L8),
        "Texture preprocessing only implemented for 1, 3, 4 8-bit channels.");

    uint8* byte = static_cast<uint8*>(_byte);

    // Make a lookup table
    uint8 adjust[4][256];
    for (int c = 0; c < 4; ++c) {
        for (int i = 0; i < 256; ++i) {
            float s = float(pow((i * modulate[c]) / 255, gammaAdjust) * 255);
            adjust[c][i] = iClamp(iRound(s), 0, 255);
        }
    }

    switch (fmt) {
    case ImageFormat::CODE_RGBA8:
        for (int i = 0; i < n; ++i) {
            for (int c = 0; c < 3; ++c, ++i) {
                byte[i] = adjust[c][byte[i]];
            }
        }

        if (convertToPremultipliedAlpha) {
            for (int i = 0; i < n; i += 4) {
                int a = byte[i + 3];
                for (int c = 0; c < 3; ++c) {
                    byte[i + c] = (int(byte[i + c]) * a) / 255;
                }
            }
        }
        break;

    case ImageFormat::CODE_RGB8:
        for (int i = 0; i < n; ) {
            for (int c = 0; c < 3; ++c, ++i) {
                byte[i] = adjust[c][byte[i]];
            }
        }
        break;

    case ImageFormat::CODE_R8:
    case ImageFormat::CODE_L8:
        for (int i = 0; i < n; ++i) {
            byte[i] = adjust[0][byte[i]];
        }
        break;

    default:;
    }
}
Пример #8
0
void SDLWindow::setDimensions(const Rect2D& dims) {
    #ifdef G3D_WIN32
        int W = screenWidth();
        int H = screenHeight();

        int x = iClamp((int)dims.x0(), 0, W);
        int y = iClamp((int)dims.y0(), 0, H);
        int w = iClamp((int)dims.width(), 1, W);
        int h = iClamp((int)dims.height(), 1, H);

        SetWindowPos(_Win32HWND, NULL, x, y, w, h, SWP_NOZORDER);
        // Do not update settings-- wait for an event to notify us
    #endif

	#ifdef G3D_LINUX
		//TODO: Linux
	#endif 

    // TODO: OS X
}
void PhysicsFrameSplineEditor::setSpline(const PhysicsFrameSpline& s) {
    m_spline = s;

    // Ensure that there is at least one node
    if (m_spline.control.size() == 0) {
        m_spline.control.append(PFrame());
    }

    m_selectedControlPointIndex = iClamp(m_selectedControlPointIndex, 0, m_spline.control.size() - 1);
    
    m_nodeManipulator->setFrame(m_spline.control[m_selectedControlPointIndex]);
}
Пример #10
0
void ToneMap::makeGammaCorrectionTextures() {
    if (RG.notNull() || (profile == NO_TONE)) {
        return;
    }
    
    // The inverse gamma ramp function
    G3D::uint8 ramp[256];
    
    for (int i = 0; i < 256; ++i) {
        // Linear
        //ramp[i] = i;

        // Inverse power
        const double A = 1.9;
        // Brighten the screen image by 1.0 / 0.75 = 1.34, since we darkened the 
        // scene when rendering to avoid saturation.
        ramp[i] = iClamp(iRound((1.0 - pow(1.0 - i/255.0, A)) * 255.0 / 0.75), 0, 255);

        // Log
        // const double A = 10, B = 1; 
        // ramp[i] = iRound(((log(A*i/255.0 + B) - log(B)) /
        //                  (log(A+B) - log(B))) * 255.0);
    }
    
    GImage data(256, 256, 3);
    
    for (int g = 0; g < 256; ++g) {
        for (int r = 0; r < 256; ++r) {
            Color3uint8& p = data.pixel3(r, g);
            p.r = ramp[r];
            p.g = ramp[g];
            p.b = 0;
        }
    }
    
    // MIP-mapping causes bad interpolation for some reason
	RG = Texture::fromGImage("RG Gamma", data, TextureFormat::RGB8, Texture::DIM_2D, Texture::Settings::video());
    
    if (profile != PS20) {
        // On PS20 we can re-use the original RG texture
        data.resize(256, 1, 3);
        for (int b = 0; b < 256; ++b) {
            Color3uint8& p = data.pixel3(b, 0);
            p.r = 0;
            p.g = 0;
            p.b = ramp[b];
        }
    
        B = Texture::fromGImage("B Gamma", data, TextureFormat::RGB8, Texture::DIM_2D, Texture::Settings::video());
    }
}
Пример #11
0
void SDLWindow::setPosition(int x, int y) {
    #ifdef G3D_WIN32
        int W = screenWidth();
        int H = screenHeight();

        x = iClamp(x, 0, W);
        y = iClamp(y, 0, H);

        SetWindowPos(_Win32HWND, NULL, x, y, 0, 0, SWP_NOZORDER | SWP_NOSIZE);
        // Do not update settings-- wait for an event to notify us
    #endif

	#ifdef G3D_LINUX
	    const int W = screenWidth(_X11Display);
        const int H = screenHeight(_X11Display);

        x = iClamp(x, 0, W);
        y = iClamp(y, 0, H);

		XMoveWindow(_X11Display, _X11WMWindow, x, y);
	#endif
    // TODO: OS X
}
Пример #12
0
bool cTileRasterizer::setup(const cVertex &v0,const cVertex &v1,const cVertex &v2)
{
	bool setup_ok=cRasterizer::setup(v0,v1,v2);
	
	// add cTileRasterizer-specific setup code here

	mZMin = mZMax = (uint32)iClamp( int(0xffffff*mVertices[0].mAttributes[ATTRIBUTE_POSITION].z), 0, 0xffffff );

	for (int i = 1; i < 3; i++) {
		// convert float z to 24 bit fixed z
		uint32 z = (uint32)iClamp( int(0xffffff*mVertices[i].mAttributes[ATTRIBUTE_POSITION].z), 0, 0xffffff );
		mZMin = MIN2(mZMin,z);
		mZMax = MAX2(mZMax,z);
	}


	// compute tile coordinates
	mTileCoordsMin.x=(mBBox2DMin.x/mTileWidth);							// floor 
	mTileCoordsMin.y=(mBBox2DMin.y/mTileHeight);						// floor
	mTileCoordsMax.x=((mBBox2DMax.x+mTileWidth-1)/mTileWidth);			// ceil 
	mTileCoordsMax.y=((mBBox2DMax.y+mTileHeight-1)/mTileHeight);		// ceil

	return setup_ok;
}
Пример #13
0
void BinaryOutput::compress(int level) {
    if (m_alreadyWritten > 0) {
        throw "Cannot compress huge files (part of this file has already been written to disk).";
    }
    debugAssertM(! m_committed, "Cannot compress after committing.");
    alwaysAssertM(m_bufferLen < 0xFFFFFFFF, "Compress only works for 32-bit files.");

    // This is the worst-case size, as mandated by zlib
    unsigned long compressedSize = iCeil(m_bufferLen * 1.001) + 12;

    // Save the old buffer and reallocate to the worst-case size
    const uint8* src     = m_buffer;
    const uint32 srcSize = (uint32)m_bufferLen;

    // add space for the 4-byte header
    m_maxBufferLen = compressedSize + 4;
    m_buffer = (uint8*)System::malloc(m_maxBufferLen);
    
    // Write the header containing the old buffer size, which is needed for decompression
    {
        const uint8* convert = (const uint8*)&srcSize;
        if (m_swapBytes) {
            m_buffer[0] = convert[3];
            m_buffer[1] = convert[2];
            m_buffer[2] = convert[1];
            m_buffer[3] = convert[0];
        } else {
            m_buffer[0] = convert[0];
            m_buffer[1] = convert[1];
            m_buffer[2] = convert[2];
            m_buffer[3] = convert[3];
        }
    }

    // Compress and write after the header
    int result = compress2(m_buffer + 4, &compressedSize, src, srcSize, iClamp(level, 0, 9));

    debugAssert(result == Z_OK); (void)result;
    m_bufferLen = compressedSize + 4;
    m_pos = m_bufferLen;

    // Free the old data
    System::free((void*)src);
}
Пример #14
0
result CMuli3DPresentTargetLinuxX11::Present( const float32 *i_pSource, uint32 i_iFloats )
{
	m3ddeviceparameters DeviceParameters = m_pParent->GetDeviceParameters();

	// Copy pixels to the ximage-buffer ---------------------------------------

	fpuTruncate();

	if( m_iPixelBytes == 2 )
	{
		// 16-bit
		uint16 *pDestination = (uint16 *)m_pXImage->data;
		uint32 iPixels = DeviceParameters.iBackbufferWidth * DeviceParameters.iBackbufferHeight;
		while( iPixels-- )
		{
			const int32 iR = iClamp( ftol( i_pSource[0] * m_i16bitMaxVal[0] ), 0, m_i16bitMaxVal[0] );
			const int32 iG = iClamp( ftol( i_pSource[1] * m_i16bitMaxVal[1] ), 0, m_i16bitMaxVal[1] );
			const int32 iB = iClamp( ftol( i_pSource[2] * m_i16bitMaxVal[2] ), 0, m_i16bitMaxVal[2] );
			i_pSource += i_iFloats;

			*pDestination++ = ( iR << m_i16bitShift[0] ) | ( iG << m_i16bitShift[1] ) | ( iB << m_i16bitShift[2] );
		}
	}
	else
	{
		// 24- or 32-bit
		uint8 *pDestination = (uint8 *)m_pXImage->data;
		uint32 iPixels = DeviceParameters.iBackbufferWidth * DeviceParameters.iBackbufferHeight;
		while( iPixels-- )
		{
			pDestination[0] = iClamp( ftol( i_pSource[2] * 255.0f ), 0, 255 ); // b
			pDestination[1] = iClamp( ftol( i_pSource[1] * 255.0f ), 0, 255 ); // g
			pDestination[2] = iClamp( ftol( i_pSource[0] * 255.0f ), 0, 255 ); // r

			i_pSource += i_iFloats;
			pDestination += m_iPixelBytes;
		}
	}

	fpuReset();

	// Present to window/screen
	XPutImage( m_pDisplay, DeviceParameters.hDeviceWindow, m_WindowGC, m_pXImage, 0, 0,
		0, 0, DeviceParameters.iBackbufferWidth, DeviceParameters.iBackbufferHeight );

	return s_ok;
}
Пример #15
0
void MD2Model::Part::load(const std::string& filename, float resize) {

    resize *= 0.55f;

    // If models are being reloaded it is dangerous to trust the interpolation cache.
    interpolatedModel = NULL;

    alwaysAssertM(FileSystem::exists(filename), std::string("Can't find \"") + filename + "\"");

    setNormalTable();

    // Clear out
    reset();

    BinaryInput b(filename, G3D_LITTLE_ENDIAN);

    MD2ModelHeader header;

    header.deserialize(b);
    debugAssert(header.version == 8);
    debugAssert(header.numVertices <= 4096);

    keyFrame.resize(header.numFrames);
    Array<Vector3> frameMin;
    frameMin.resize(header.numFrames); 
    Array<Vector3> frameMax;
    frameMax.resize(header.numFrames);
    Array<double>  frameRad;
    frameRad.resize(header.numFrames);

    texCoordScale.x = 1.0f / header.skinWidth;
    texCoordScale.y = 1.0f / header.skinHeight;

    Vector3 min  = Vector3::inf();
    Vector3 max  = -Vector3::inf();
    double  rad  = 0;

    if (header.numVertices < 3) {
        Log::common()->printf("\n*****************\nWarning: \"%s\" is corrupted and is not being loaded.\n", filename.c_str());
        return;
    }

    loadTextureFilenames(b, header.numSkins, header.offsetSkins);

    for (int f = 0; f < keyFrame.size(); ++f) {
        MD2Frame md2Frame;

        b.setPosition(header.offsetFrames + f * header.frameSize);
        md2Frame.deserialize(b);

        // Read the vertices for the frame
        keyFrame[f].vertexArray.resize(header.numVertices);
        keyFrame[f].normalArray.resize(header.numVertices);

        // Per-pose bounds
        Vector3 min_1  = Vector3::inf();
        Vector3 max_1  = -Vector3::inf();
        double  rad_1  = 0;

        // Quake's axes are permuted and scaled
        double scale[3]   = {-.07, .07, -.07};
        int    permute[3] = {2, 0, 1};
        int v, i;
        for (v = 0; v < header.numVertices; ++v) {

            Vector3& vertex = keyFrame[f].vertexArray[v];
            for (i = 0; i < 3; ++i) {
                vertex[permute[i]] = (b.readUInt8() * md2Frame.scale[i] + md2Frame.translate[i]) * float(scale[permute[i]]);
            }

            vertex *= resize;

            uint8 normalIndex = b.readUInt8();
            debugAssertM(normalIndex < 162, "Illegal canonical normal index in file");
            keyFrame[f].normalArray[v] = iClamp(normalIndex, 0, 161);

            min_1 = min_1.min(vertex);
            max_1 = max_1.max(vertex);

            if (vertex.squaredMagnitude() > rad_1) {
                rad_1 = vertex.squaredMagnitude();
            }
        }

        frameMin[f] = min_1;
        frameMax[f] = max_1;
        frameRad[f] = sqrt(rad_1);

        min = min.min(min_1);
        max = max.max(max_1);

        if (rad_1 > rad) {
            rad = rad_1;
        }
    }

    // Compute per-animation bounds based on frame bounds
    for (int a = 0; a < JUMP; ++a) {
        const int first = animationTable[a].first;
        const int last  = animationTable[a].last;

        if ((first < header.numFrames) && (last < header.numFrames)) {
            Vector3 min = frameMin[first];
            Vector3 max = frameMax[first];
            double rad  = frameRad[first];

            for (int i = first + 1; i <= last; ++i) {
                min = min.min(frameMin[i]);
                max = max.max(frameMax[i]);
                rad = G3D::max(rad, frameRad[i]);
            }

            animationBoundingBox[a]    = AABox(min, max);

            // Sometimes the sphere bounding the box is tighter than the one we calculated.
            const float boxRadSq = (max-min).squaredMagnitude() * 0.25f;

            if (boxRadSq >= square(rad)) {
                animationBoundingSphere[a] = Sphere(Vector3::zero(), (float)rad);
            } else {
                animationBoundingSphere[a] = Sphere((max + min) * 0.5f, sqrt(boxRadSq));
            }

        } else {
            // This animation is not supported by this model
            animationBoundingBox[a]    = AABox(Vector3::zero(), Vector3::zero());
            animationBoundingSphere[a] = Sphere(Vector3::zero(), 0);
        }
    }

    animationBoundingBox[JUMP] = animationBoundingBox[JUMP_DOWN];
    animationBoundingSphere[JUMP] = animationBoundingSphere[JUMP_DOWN];

    boundingBox    = AABox(min, max);
    boundingSphere = Sphere(Vector3::zero(), (float)sqrt(rad));

    // Load the texture coords
    Array<Vector2int16> fileTexCoords;
    fileTexCoords.resize(header.numTexCoords);
    b.setPosition(header.offsetTexCoords);
    for (int t = 0; t < fileTexCoords.size(); ++t) {
        fileTexCoords[t].x = b.readUInt16();
        fileTexCoords[t].y = b.readUInt16();
    }

    // The indices for the texture coords (which don't match the
    // vertex indices originally).
    indexArray.resize(header.numTriangles * 3);
    Array<Vector2int16> index_texCoordArray;
    index_texCoordArray.resize(indexArray.size());

    // Read the triangles, reversing them to get triangle list order
    b.setPosition(header.offsetTriangles);
    for (int t = header.numTriangles - 1; t >= 0; --t) {

        for (int i = 2; i >= 0; --i) {
            indexArray[t * 3 + i] = b.readUInt16();
        }

        for (int i = 2; i >= 0; --i) {
            index_texCoordArray[t * 3 + i] = fileTexCoords[b.readUInt16()];
        }
    }

    computeTexCoords(index_texCoordArray);

    // Read the primitives
    {
        primitiveArray.clear();
        b.setPosition(header.offsetGlCommands);
        
        int n = b.readInt32();

        while (n != 0) {
            Primitive& primitive = primitiveArray.next();

            if (n > 0) {
                primitive.type = PrimitiveType::TRIANGLE_STRIP;
            } else {
                primitive.type = PrimitiveType::TRIANGLE_FAN;
                n = -n;
            }

            primitive.pvertexArray.resize(n);

            Array<Primitive::PVertex>&  pvertex = primitive.pvertexArray;

            for (int i = 0; i < pvertex.size(); ++i) {
                pvertex[i].texCoord.x = b.readFloat32();
                pvertex[i].texCoord.y = b.readFloat32();
                pvertex[i].index      = b.readInt32();
            }

            n = b.readInt32();
        }
    }


    MeshAlg::computeAdjacency(keyFrame[0].vertexArray, indexArray, faceArray, edgeArray, vertexArray);
    weldedFaceArray = faceArray;
    weldedEdgeArray = edgeArray;
    weldedVertexArray = vertexArray;
    MeshAlg::weldAdjacency(keyFrame[0].vertexArray, weldedFaceArray, weldedEdgeArray, weldedVertexArray);

    numBoundaryEdges = MeshAlg::countBoundaryEdges(edgeArray);
    numWeldedBoundaryEdges = MeshAlg::countBoundaryEdges(weldedEdgeArray);

    shared_ptr<VertexBuffer> indexBuffer = 
        VertexBuffer::create(indexArray.size() * sizeof(int), VertexBuffer::WRITE_ONCE);
    indexVAR = IndexStream(indexArray, indexBuffer);
}
Пример #16
0
void GuiDropDownList::setList(const Array<GuiText>& c) {
    m_listValue = c;
    *m_indexValue = iClamp(*m_indexValue, 0, m_listValue.size() - 1);
    m_menu.reset();
}
Пример #17
0
Vector2int16 Vector2int16::clamp(const Vector2int16& lo, const Vector2int16& hi) {
    return Vector2int16(iClamp(x, lo.x, hi.x), iClamp(y, lo.y, hi.y));
}
Пример #18
0
Vector4int8::Vector4int8(const Vector3& source, int8 w) : w(w) {
    x = iClamp(iRound(source.x), -128, 127);
    y = iClamp(iRound(source.y), -128, 127);
    z = iClamp(iRound(source.z), -128, 127);
}
Пример #19
0
Color1uint8::Color1uint8(const class Color1& c) : value(iClamp(iFloor(c.value * 256), 0, 255)) {
}
Пример #20
0
/** Converts a bug count into a quality rating*/
const char* quality(int bugCount) {
    static const char* q[] = {"A+", "A-", "B+", "B-", "C+", "C-", "D+", "D-", "F"};
    return q[iClamp(bugCount, 0, 8)];
}
Пример #21
0
void  App::onGraphics (RenderDevice *rd, Array< SurfaceRef > &posed3D, Array< Surface2DRef > &posed2D) {
    rd->setColorClearValue(Color3::white());
    rd->clear();

    doFunStuff();

    rd->push2D();

        int w = rd->width();
        int h = rd->height();

        ///////////////////////////////////////
        // Left panel
#       define LABEL(str) p.y += titleFont->draw2D(rd, str, p - Vector2((float)w * 0.0075f, 0), s * 2, Color3::white() * 0.4f).y
#       define PRINT(str) p.y += reportFont->draw2D(rd, str, p, s, Color3::black()).y

        int x0 = int(w * 0.015f);
        // Cursor position
        Vector2 p(x0, h * 0.02f);

        // Font size
        float s = w * 0.013;

        LABEL("Shaders");
        PRINT(std::string("Combiners: ") + combineShader);
        PRINT(std::string("Assembly:   ") + asmShader);
        PRINT(std::string("GLSL:         ") + glslShader);

        p.y += s * 2;
        LABEL("Extensions");
        PRINT(std::string("FSAA:                           ") + ((GLCaps::supports("WGL_ARB_multisample") || GLCaps::supports("GL_ARB_multisample")) ? "Yes" : "No"));
        PRINT(std::string("Two-sided Stencil:        ") + ((GLCaps::supports_two_sided_stencil() ? "Yes" : "No")));
        PRINT(std::string("Stencil Wrap:               ") + (GLCaps::supports("GL_EXT_stencil_wrap") ? "Yes" : "No"));
        PRINT(std::string("Texture Compression: ") + (GLCaps::supports("GL_EXT_texture_compression_s3tc") ? "Yes" : "No"));
        PRINT(std::string("Shadow Maps:             ") + (GLCaps::supports("GL_ARB_shadow") ? "Yes" : "No"));
        PRINT(std::string("Frame Buffer Object:   ") + (GLCaps::supports("GL_EXT_framebuffer_object") ? "Yes" : "No"));
        PRINT(std::string("Vertex Arrays:              ") + (GLCaps::supports_GL_ARB_vertex_buffer_object() ? "Yes" : "No"));
        
            
        ///////////////////////////////////////
        // Right Panel
        x0 = int(w * 0.6f);
        // Cursor position
        p = Vector2(x0, h * 0.02f);

        // Graphics Card
        LABEL("Graphics Card");
        rd->setTexture(0, cardLogo);
        Draw::rect2D(Rect2D::xywh(p.x - s * 6, p.y, s * 5, s * 5), rd);
        rd->setTexture(0, NULL);

        PRINT(GLCaps::vendor().c_str());
        PRINT(GLCaps::renderer().c_str());
        PRINT(format("Driver Version %s", GLCaps::driverVersion().c_str()));

#       ifdef G3D_WIN32        
            PRINT(format("%d MB Video RAM", DXCaps::videoMemorySize() / (1024 * 1024)));
            {
                uint32 ver = DXCaps::version();
                PRINT(format("DirectX %d.%d", ver/100, ver%100));
            }
#       endif

        p.y += s * 2;

        // Processor
        LABEL("Processor");
        rd->setTexture(0, chipLogo);
        Draw::rect2D(Rect2D::xywh(p.x - s * 6, p.y, s * 5, s * 5), rd);
        rd->setTexture(0, NULL);

        PRINT(System::cpuVendor().c_str());
        PRINT(System::cpuArchitecture().c_str());

        Array<std::string> features;
        if (System::has3DNow()) {
            features.append("3DNow");
        }
        if (System::hasMMX()) {
            features.append("MMX");
        }
        if (System::hasSSE()) {
            features.append("SSE");
        }
        if (System::hasSSE2()) {
            features.append("SSE2");
        }
        if (chipSpeed != "") {
            PRINT(chipSpeed + " " + stringJoin(features, '/'));
        } else {
            PRINT(stringJoin(features, '/'));
        }

        p.y += s * 2;

        // Operating System
        LABEL("OS");
        rd->setTexture(0, osLogo);
        Draw::rect2D(Rect2D::xywh(p.x - s * 6, p.y - s * 2, s * 5, s * 5), rd);
        rd->setTexture(0, NULL);


        if (beginsWith(System::operatingSystem(), "Windows 5.0")) {
            PRINT("Windows 2000");
        } else if (beginsWith(System::operatingSystem(), "Windows 5.1")) {
            PRINT("Windows XP");
        }
        PRINT(System::operatingSystem().c_str());

        p.y += s * 3;

        x0 = int(w - s * 10);
        titleFont->draw2D(rd, "Features", p - Vector2(w * 0.0075f, 0), s * 2, Color3::white() * 0.4f);
        p.y += reportFont->draw2D(rd, format("f%d", featureRating), Vector2(x0, p.y), s*2, Color3::red() * 0.5).y;
        drawBar(rd, featureRating, p);

        // Designed to put NV40 at 50
        performanceRating = log(rd->stats().frameRate) * 15.0f;

        p.y += s * 4;
        performanceButton =
            Rect2D::xywh(p,
                         titleFont->draw2D(rd, "Speed", p - Vector2(w * 0.0075f, 0), s * 2, Color3::white() * 0.4f));

        {
            float spd = iRound(performanceRating * 10) / 10.0f;
            p.y += reportFont->draw2D(rd, format("%5.1f", spd), Vector2(x0 - s*2, p.y), s*2, Color3::red() * 0.5).y;
        }
        drawBar(rd, (int)min(performanceRating, 100.0f), p);

        p.y += s * 4;
        titleFont->draw2D(rd, "Quality", p - Vector2(w * 0.0075f, 0), s * 2, Color3::white() * 0.4f);
        p.y += reportFont->draw2D(rd, quality(bugCount), Vector2(x0, p.y), s*2, Color3::red() * 0.5f).y;
        drawBar(rd, iClamp(100 - bugCount * 10, 0, 100), p);

#       undef PRINT


        p.y = h - 50;
#       define PRINT(str) p.y += reportFont->draw2D(rd, str, p, 8, Color3::black()).y;

        PRINT("These ratings are based on the performance of G3D apps.");
        PRINT("They may not be representative of overall 3D performance.");
        PRINT("Speed is based on both processor and graphics card. Upgrading");
        PRINT("your graphics driver may improve Quality and Features.");
#       undef  PRINT
#       undef LABEL

        switch (popup) {
        case NONE:
            break;

        case PERFORMANCE:
            {
                //  Draw the popup box
                Rect2D box = drawPopup("Performance Details");
                p.x = box.x0() + 10;
                p.y = box.y0() + 30;

                Vector2 spacing(box.width() / 6.5, 0);

                std::string str;

                float factor = 3 * vertexPerformance.numTris / 1e6;

#               define PRINT(cap, val)   \
                    reportFont->draw2D(rd, cap, p, s, Color3::black());\
                    reportFont->draw2D(rd, (vertexPerformance.val[0] > 0) ? \
                        format("%5.1f", vertexPerformance.val[0]) : \
                        std::string("X"), p + spacing * 3, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT);\
                    reportFont->draw2D(rd, (vertexPerformance.val[0] > 0) ? \
                        format("%5.1f", factor * vertexPerformance.val[0]) : \
                        std::string("X"), p + spacing * 4, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT);\
                    reportFont->draw2D(rd, (vertexPerformance.val[1] > 0) ? \
                        format("%5.1f", vertexPerformance.val[1]) : \
                        std::string("X"), p + spacing * 5, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT);\
                    p.y += reportFont->draw2D(rd, (vertexPerformance.val[1] > 0) ? \
                        format("%5.1f", factor * vertexPerformance.val[1]) : \
                        std::string("X"), p + spacing * 6, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT).y;

                reportFont->draw2D(rd, "Incoherent", p + spacing * 3.5, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT);
                p.y += reportFont->draw2D(rd, "Coherent", p + spacing * 5.5, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT).y;

                reportFont->draw2D(rd, "FPS*", p + spacing * 3, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT);
                reportFont->draw2D(rd, "MVerts/s", p + spacing * 4, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT);
                reportFont->draw2D(rd, "FPS*", p + spacing * 5, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT).y;
                p.y += reportFont->draw2D(rd, "MVerts/s", p + spacing * 6, s, Color3::black(), Color4::clear(), GFont::XALIGN_RIGHT).y;
                
                PRINT("glBegin/glEnd", beginEndFPS);
                PRINT("glDrawElements", drawElementsRAMFPS); 
                PRINT("  + VBO", drawElementsVBOFPS);
                PRINT("  + uint16", drawElementsVBO16FPS);
                PRINT("  + gl interleave", drawElementsVBOIFPS);
                PRINT("  + manual interleave", drawElementsVBOIMFPS);
                PRINT("  (without shading)", drawElementsVBOPeakFPS);

                reportFont->draw2D(rd, "glDrawArrays", p, s, Color3::black());
                reportFont->draw2D(rd, (vertexPerformance.drawArraysVBOPeakFPS > 0) ? \
                    format("%5.1f", vertexPerformance.drawArraysVBOPeakFPS) : \
                    std::string("X"), p + spacing * 5, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT);\
                p.y += reportFont->draw2D(rd, (vertexPerformance.drawArraysVBOPeakFPS > 0) ? \
                    format("%5.1f", factor * vertexPerformance.drawArraysVBOPeakFPS) : \
                    std::string("X"), p + spacing * 6, s, Color3::red() * 0.5, Color4::clear(), GFont::XALIGN_RIGHT).y;

#               undef PRINT

                p.y += s;
                p.y += reportFont->draw2D(rd, format("* FPS at %d k polys/frame.", 
                    iRound(vertexPerformance.numTris / 1000.0)), p + Vector2(20, 0), s, Color3::black()).y;
            }
        }

    rd->pop2D();
}
Пример #22
0
result CMuli3DPresentTargetAmigaOS4::Present( const float32 *i_pSource, uint32 i_iFloats )
{
	m3ddeviceparameters DeviceParameters = m_pParent->GetDeviceParameters();

	// Copy pixels to the image-buffer ---------------------------------------

	// Doesn't currently do anything...
	fpuTruncate();

	// Picasso96 RenderInfo for locking the bitmap
	struct RenderInfo ri;

	// Lock bitmap for drawing
	ULONG lock = IP96->p96LockBitMap( m_pBitMap, (UBYTE*)&ri, sizeof(struct RenderInfo) );

	if ( lock )
	{
		// Pointer to allocated buffer
		uint8 *pDestination = (uint8 *)ri.Memory;
	
		// Help pointer to a row in bitmap
		uint8 *_pDestination;
	
		for ( uint32 y = 0; y < DeviceParameters.iBackbufferHeight; y++ )
		{
			// Next row
			_pDestination = pDestination + y * ri.BytesPerRow; 

			for ( uint32 x = 0; x < DeviceParameters.iBackbufferWidth; x++ )
			{
		 		//*_pDestination++ = iClamp( (int32)( *i_pSource++ * 255.0f ), 0, 255 ); // r
				//*_pDestination++ = iClamp( (int32)( *i_pSource++ * 255.0f ), 0, 255 ); // g
				//*_pDestination++ = iClamp( (int32)( *i_pSource++ * 255.0f ), 0, 255 ); // b

				// Set r, g and b bytes in our buffer
		 		_pDestination[0] = iClamp( ftol( i_pSource[0] * 255.0f ), 0, 255 ); // r
				_pDestination[1] = iClamp( ftol( i_pSource[1] * 255.0f ), 0, 255 ); // g
				_pDestination[2] = iClamp( ftol( i_pSource[2] * 255.0f ), 0, 255 ); // b

		 		//*_pDestination++ = (iClamp( ftol( i_pSource[0] * 255.0f ), 0, 255 ) << 16) |
				//	(iClamp( ftol( i_pSource[1] * 255.0f ), 0, 255 ) << 8) |
				//	iClamp( ftol( i_pSource[2] * 255.0f ), 0, 255 );

				i_pSource += i_iFloats;
				_pDestination += 3;
			}
		}

		IP96->p96UnlockBitMap( m_pBitMap, lock );

		// Blit bitmap to window
		IGraphics->BltBitMapRastPort( m_pBitMap, 0, 0, DeviceParameters.hDeviceWindow->RPort, DeviceParameters.hDeviceWindow->BorderLeft, DeviceParameters.hDeviceWindow->BorderTop, DeviceParameters.iBackbufferWidth, DeviceParameters.iBackbufferHeight, 0xC0);
	
		IGraphics->WaitTOF();
	} // lock

	// Doesn't currently do anything...
	fpuReset();

	return s_ok;
}
Пример #23
0
result CMuli3DPresentTargetWin32::Present( const float32 *i_pSource, uint32 i_iFloats )
{
	m3ddeviceparameters DeviceParameters = m_pParent->GetDeviceParameters();

	// Check for lost DirectDraw surfaces -------------------------------------
	if( m_bDDSurfaceLost )
	{
		m_pDirectDrawSurfaces[0]->Restore();
		if( DeviceParameters.bWindowed )
			m_pDirectDrawSurfaces[1]->Restore();
		m_bDDSurfaceLost = false;
	}

    // Lock backbuffer-surface-------------------------------------------------
	DDSURFACEDESC2 descSurface;
    descSurface.dwSize = sizeof( DDSURFACEDESC2 );
    if( FAILED( m_pDirectDrawSurfaces[1]->Lock( 0, &descSurface, DDLOCK_WAIT|DDLOCK_NOSYSLOCK|DDLOCK_WRITEONLY, 0 ) ) )
	{
		FUNC_FAILING( "CMuli3DPresentTargetWin32::Present: couldn't lock secondary surface.\n" );
		return e_unknown;
	}

	const uint32 iDestBytes = descSurface.ddpfPixelFormat.dwRGBBitCount / 8;

    // Copy pixels to the backbuffer-surface ----------------------------------
	const uint32 iDestRowJump = descSurface.lPitch - iDestBytes * DeviceParameters.iBackbufferWidth;
	uint8 *pDestination = (uint8 *)descSurface.lpSurface;

	fpuTruncate();

	if( iDestBytes == 2 )
	{
		// 16-bit
		uint32 iHeight = DeviceParameters.iBackbufferHeight;
		while( iHeight-- )
		{
			uint32 iWidth = DeviceParameters.iBackbufferWidth;
			while( iWidth-- )
			{
				const int32 iR = iClamp( ftol( i_pSource[0] * m_i16bitMaxVal[0] ), 0, m_i16bitMaxVal[0] );
				const int32 iG = iClamp( ftol( i_pSource[1] * m_i16bitMaxVal[1] ), 0, m_i16bitMaxVal[1] );
				const int32 iB = iClamp( ftol( i_pSource[2] * m_i16bitMaxVal[2] ), 0, m_i16bitMaxVal[2] );
				i_pSource += i_iFloats;

				*((uint16 *)pDestination) = ( iR << m_i16bitShift[0] ) | ( iG << m_i16bitShift[1] ) | ( iB << m_i16bitShift[2] );
				pDestination += 2;
			}
			pDestination += iDestRowJump;
		}
	}
	else
	{
		// 24- or 32-bit
		uint32 iHeight = DeviceParameters.iBackbufferHeight;
		while( iHeight-- )
		{
			uint32 iWidth = DeviceParameters.iBackbufferWidth;
			while( iWidth-- )
			{
				pDestination[0] = iClamp( ftol( i_pSource[2] * 255.0f ), 0, 255 ); // b
				pDestination[1] = iClamp( ftol( i_pSource[1] * 255.0f ), 0, 255 ); // g
				pDestination[2] = iClamp( ftol( i_pSource[0] * 255.0f ), 0, 255 ); // r

				i_pSource += i_iFloats;
				pDestination += iDestBytes;
			}
			pDestination += iDestRowJump;
		}
	}

	fpuReset();

    // Unlock backbuffer-surface and surface
    m_pDirectDrawSurfaces[1]->Unlock( 0 );

	// Present the image to the screen ----------------------------------------
	if( DeviceParameters.bWindowed )
	{
		POINT pntTopLeft = { 0, 0 };
        ClientToScreen( DeviceParameters.hDeviceWindow, &pntTopLeft );

		RECT rctDestination;
        GetClientRect( DeviceParameters.hDeviceWindow, &rctDestination );
		OffsetRect( &rctDestination, pntTopLeft.x, pntTopLeft.y );

		RECT rctSource;
		SetRect( &rctSource, 0, 0, DeviceParameters.iBackbufferWidth, DeviceParameters.iBackbufferHeight );

        // Blt secondary to primary surface
        if( FAILED( m_pDirectDrawSurfaces[0]->Blt( &rctDestination, m_pDirectDrawSurfaces[1], &rctSource, DDBLT_WAIT, 0 ) ) )
		{
			m_bDDSurfaceLost = true;
			FUNC_FAILING( "CMuli3DPresentTargetWin32::Present: primary surfaces have been lost!\n" );
			return e_unknown;
		}
	}
	else
	{
		if( FAILED( m_pDirectDrawSurfaces[0]->Flip( 0, DDFLIP_WAIT ) ) )
		{
			m_bDDSurfaceLost = true;
			FUNC_FAILING( "CMuli3DPresentTargetWin32::Present: surfaces have been lost!\n" );
			return e_unknown;
		}
	}

	return s_ok;
}
Пример #24
0
Vector4int8::Vector4int8(const Vector4& source) {
    x = iClamp(iRound(source.x), -128, 127);
    y = iClamp(iRound(source.y), -128, 127);
    z = iClamp(iRound(source.z), -128, 127);
    w = iClamp(iRound(source.w), -128, 127);
}
void PhysicsFrameSplineEditor::setSelectedControlPointIndex(int i) {
    m_selectedControlPointIndex = iClamp(i, 0, m_spline.control.size() - 1);
    // Move the manipulator to the new control point
    m_nodeManipulator->setFrame(m_spline.control[m_selectedControlPointIndex]);
}
Пример #26
0
void Welder::toGridCoords(Vector3 v, int& x, int& y, int& z) const {
    v = (v - offset) * scale;
    x = iClamp(iFloor(v.x * GRID_RES), 0, GRID_RES - 1);
    y = iClamp(iFloor(v.y * GRID_RES), 0, GRID_RES - 1);
    z = iClamp(iFloor(v.z * GRID_RES), 0, GRID_RES - 1);
}
Пример #27
0
Vector2int32 Vector2int32::clamp(const Vector2int32& lo, const Vector2int32& hi) {
    return Vector2int32(iClamp(x, lo.x, hi.x), iClamp(y, lo.y, hi.y));
}
Пример #28
0
SDLWindow::SDLWindow(const GWindow::Settings& settings) {

#if defined(G3D_OSX)
	NSApplicationWrapper wrapper;

	// Hack to get our window/process to the front...
	ProcessSerialNumber psn = { 0, kCurrentProcess};    
	TransformProcessType (&psn, kProcessTransformToForegroundApplication);
	SetFrontProcess (&psn);

	_pool = new NSAutoreleasePoolWrapper();
#endif

	if (SDL_Init(SDL_INIT_NOPARACHUTE | SDL_INIT_VIDEO | 
                 SDL_INIT_JOYSTICK) < 0 ) {

        fprintf(stderr, "Unable to initialize SDL: %s\n", SDL_GetError());
		debugPrintf("Unable to initialize SDL: %s\n", SDL_GetError());
        Log::common()->printf("Unable to initialize SDL: %s\n", SDL_GetError());
		exit(1);
	}

    // Set default icon if available
    if (settings.defaultIconFilename != "nodefault") {

        try {

            GImage defaultIcon;
            defaultIcon.load(settings.defaultIconFilename);

            setIcon(defaultIcon);
        } catch (const GImage::Error& e) {
            // Throw away default icon
            fprintf(stderr, "GWindow's default icon failed to load: %s (%s)", e.filename.c_str(), e.reason.c_str());
		    debugPrintf("GWindow's default icon failed to load: %s (%s)", e.filename.c_str(), e.reason.c_str());
            Log::common()->printf("GWindow's default icon failed to load: %s (%s)", e.filename.c_str(), e.reason.c_str());            
        }
    }

    if (! settings.fullScreen) {
        // This doesn't really work very well due to SDL bugs so we fix up 
        // the position after the window is created.
        if (settings.center) {
            System::setEnv("SDL_VIDEO_CENTERED", "");
        } else {
            System::setEnv("SDL_VIDEO_WINDOW_POS", format("%d,%d", settings.x, settings.y));
        }
    }

    _mouseVisible = true;
    _inputCapture = false;

	// Request various OpenGL parameters
	SDL_GL_SetAttribute(SDL_GL_DEPTH_SIZE,      settings.depthBits);
	SDL_GL_SetAttribute(SDL_GL_DOUBLEBUFFER,    1);
	SDL_GL_SetAttribute(SDL_GL_STENCIL_SIZE,    settings.stencilBits);
	SDL_GL_SetAttribute(SDL_GL_RED_SIZE,        settings.rgbBits);
	SDL_GL_SetAttribute(SDL_GL_GREEN_SIZE,      settings.rgbBits);
	SDL_GL_SetAttribute(SDL_GL_BLUE_SIZE,       settings.rgbBits);
	SDL_GL_SetAttribute(SDL_GL_ALPHA_SIZE,      settings.alphaBits);
	SDL_GL_SetAttribute(SDL_GL_STEREO,          settings.stereo);

    #if SDL_FSAA
        if (settings.fsaaSamples > 1) {
            SDL_GL_SetAttribute(SDL_GL_MULTISAMPLEBUFFERS, 1);
            SDL_GL_SetAttribute(SDL_GL_MULTISAMPLESAMPLES, 
                                settings.fsaaSamples);
        }
    #endif

	// Create a width x height OpenGL screen 
    int flags = 
        SDL_HWSURFACE |
        SDL_OPENGL |
        (settings.fullScreen ? SDL_FULLSCREEN : 0) |
        (settings.resizable ? SDL_RESIZABLE : 0) |
        (settings.framed ? 0 : SDL_NOFRAME);

	if (SDL_SetVideoMode(settings.width, settings.height, 0, flags) == NULL) {
        debugAssert(false);
        Log::common()->printf("Unable to create OpenGL screen: %s\n", 
                              SDL_GetError());
		error("Critical Error", 
              format("Unable to create OpenGL screen: %s\n", 
                     SDL_GetError()).c_str(), true);
		SDL_Quit();
		exit(2);
	}

    // See what video mode we really got
    _settings = settings;
    int depthBits, stencilBits, redBits, greenBits, blueBits, alphaBits;
    glGetIntegerv(GL_DEPTH_BITS, &depthBits);
    glGetIntegerv(GL_STENCIL_BITS, &stencilBits);

    glGetIntegerv(GL_RED_BITS,   &redBits);
    glGetIntegerv(GL_GREEN_BITS, &greenBits);
    glGetIntegerv(GL_BLUE_BITS,  &blueBits);
    glGetIntegerv(GL_ALPHA_BITS, &alphaBits);
    int actualFSAABuffers = 0, actualFSAASamples = 0;

    #if SDL_FSAA
        SDL_GL_GetAttribute(SDL_GL_MULTISAMPLEBUFFERS, &actualFSAABuffers);
        SDL_GL_GetAttribute(SDL_GL_MULTISAMPLESAMPLES, &actualFSAASamples);
    #else
        (void)actualFSAABuffers;
        (void)actualFSAASamples;
    #endif
    _settings.rgbBits     = iMin(iMin(redBits, greenBits), blueBits);
    _settings.alphaBits   = alphaBits;
    _settings.stencilBits = stencilBits;
    _settings.depthBits   = depthBits;
    _settings.fsaaSamples = actualFSAASamples;

    SDL_version ver;
    SDL_VERSION(&ver);
    _version = format("%d,%0d.%0d", ver.major, ver.minor, ver.patch);

    SDL_EnableUNICODE(1);
    setCaption("G3D");

    SDL_SysWMinfo info;
    SDL_VERSION(&info.version);
    SDL_GetWMInfo(&info);

    _glContext = glGetCurrentContext();

    #if defined(G3D_WIN32)
        // Extract SDL HDC/HWND on Win32
        _Win32HWND  = info.window;
        _Win32HDC   = wglGetCurrentDC();
    #elif defined(G3D_LINUX)
        // Extract SDL's internal Display pointer on Linux        
        _X11Display = info.info.x11.display;
        _X11Window  = info.info.x11.window;
        _X11WMWindow  = info.info.x11.wmwindow;

        if (glXGetCurrentDisplay != NULL) {
            G3D::_internal::x11Display = glXGetCurrentDisplay();
        } else {
            G3D::_internal::x11Display = info.info.x11.display;
        }

        if (glXGetCurrentDrawable != NULL) {
            // A Drawable appears to be either a Window or a Pixmap
            G3D::_internal::x11Window  = glXGetCurrentDrawable();
        } else {
            G3D::_internal::x11Window  = info.info.x11.window;
        }
    #endif

    // Adjust window position
    #ifdef G3D_WIN32
        if (! settings.fullScreen) {
            int W = screenWidth();
            int H = screenHeight();
            int x = iClamp(settings.x, 0, W);
            int y = iClamp(settings.y, 0, H);

            if (settings.center) {
                x = (W - settings.width) / 2;
                y = (H - settings.height) / 2;
            }

            SetWindowPos(_Win32HWND, NULL, x, y, 0, 0, SWP_NOZORDER | SWP_NOSIZE);
        }
    #endif

	#ifdef G3D_LINUX
		 if (! settings.fullScreen) {
            int W = screenWidth(_X11Display);
            int H = screenHeight(_X11Display);
            int x = iClamp(settings.x, 0, W);
            int y = iClamp(settings.y, 0, H);

            if (settings.center) {
                x = (W  - settings.width) / 2;
                y = (H - settings.height) / 2;
            }
			XMoveWindow(_X11Display, _X11WMWindow, x, y);
        }
	#endif


	// Check for joysticks
    int j = SDL_NumJoysticks();
    if ((j < 0) || (j > 10)) {
        // If there is no joystick adapter on Win32,
        // SDL returns ridiculous numbers.
        j = 0;
    }

	if (j > 0) {
        SDL_JoystickEventState(SDL_ENABLE);
        // Turn on the joysticks

        joy.resize(j);
        for (int i = 0; i < j; ++i) {
            joy[i] = SDL_JoystickOpen(i);
            debugAssert(joy[i]);
        }
	}

    GLCaps::init();

	// Register this window as the current window
	makeCurrent();

#	if defined(G3D_LINUX)
		// If G3D is using the default assertion hooks, replace them with our own that use
		// SDL functions to release the mouse, since we've been unable to implement
		// a non-SDL way of releasing the mouse using the X11 handle directly.
		if (assertionHook() == _internal::_handleDebugAssert_) {
			setFailureHook(SDL_handleDebugAssert_);
		}

		if (failureHook() == _internal::_handleErrorCheck_) {
			setFailureHook(SDL_handleErrorCheck_);
		}
#	endif
}