예제 #1
0
// Create a Synchronizer object for a PDF file.
// It creates either a SyncTex or PdfSync object
// based on the synchronization file found in the folder containing the PDF file.
int Synchronizer::Create(const WCHAR *pdffilename, PdfEngine *engine, Synchronizer **sync)
{
    if (!sync || !engine)
        return PDFSYNCERR_INVALID_ARGUMENT;

    const WCHAR *fileExt = path::GetExt(pdffilename);
    if (!str::EqI(fileExt, L".pdf"))
        return PDFSYNCERR_INVALID_ARGUMENT;

    ScopedMem<WCHAR> baseName(str::DupN(pdffilename, fileExt - pdffilename));

    // Check if a PDFSYNC file is present
    ScopedMem<WCHAR> syncFile(str::Join(baseName, PDFSYNC_EXTENSION));
    if (file::Exists(syncFile)) {
        *sync = new Pdfsync(syncFile, engine);
        return *sync ? PDFSYNCERR_SUCCESS : PDFSYNCERR_OUTOFMEMORY;
    }

    // check if SYNCTEX or compressed SYNCTEX file is present
    ScopedMem<WCHAR> texGzFile(str::Join(baseName, SYNCTEXGZ_EXTENSION));
    ScopedMem<WCHAR> texFile(str::Join(baseName, SYNCTEX_EXTENSION));

    if (file::Exists(texGzFile) || file::Exists(texFile)) {
        // due to a bug with synctex_parser.c, this must always be
        // the path to the .synctex file (even if a .synctex.gz file is used instead)
        *sync = new SyncTex(texFile, engine);
        return *sync ? PDFSYNCERR_SUCCESS : PDFSYNCERR_OUTOFMEMORY;
    }

    return PDFSYNCERR_SYNCFILE_NOTFOUND;
}
예제 #2
0
bool ModelPackager::copyTextures(const QString& oldDir, const QDir& newDir) {
    QString errors;
    for (auto texture : _textures) {
        QString oldPath = oldDir + "/" + texture;
        QString newPath = newDir.path() + "/" + texture;

        // Make sure path exists
        if (texture.contains("/")) {
            QString dirPath = newDir.relativeFilePath(QFileInfo(newPath).path());
            newDir.mkpath(dirPath);
        }
        
        QFile texFile(oldPath);
        if (texFile.exists() && texFile.open(QIODevice::ReadOnly)) {
            // Check if texture needs to be recoded
            QFileInfo fileInfo(oldPath);
            QString extension = fileInfo.suffix().toLower();
            bool isJpeg = (extension == "jpg");
            bool mustRecode = !(isJpeg || extension == "png");
            QImage image = QImage::fromData(texFile.readAll());

            // Recode texture if too big
            if (image.width() > MAX_TEXTURE_SIZE || image.height() > MAX_TEXTURE_SIZE) {
                image = image.scaled(MAX_TEXTURE_SIZE, MAX_TEXTURE_SIZE, Qt::KeepAspectRatio);
                mustRecode = true;
            }
            
            // Copy texture
            if (mustRecode) {
                QFile newTexFile(newPath);
                newTexFile.open(QIODevice::WriteOnly);
                image.save(&newTexFile, isJpeg ? "JPG" : "PNG");
            } else {
                texFile.copy(newPath);
            }
        } else {
            errors += QString("\n%1").arg(oldPath);
        }
    }
    
    if (!errors.isEmpty()) {
        OffscreenUi::asyncWarning(nullptr, "ModelPackager::copyTextures()",
                             "Missing textures:" + errors);
        qCDebug(interfaceapp) << "ModelPackager::copyTextures():" << errors;
        return false;
    }
    
    return true;
}
예제 #3
0
 osg::Node* traverseAIScene( const std::string& filename, const struct aiScene* aiScene, const struct aiNode* aiNode,
                             TextureMap& textures, const osgDB::Options* options ) const
 {
     osg::Geode* geode = new osg::Geode;
     for ( unsigned int n=0; n<aiNode->mNumMeshes; ++n )
     {
         // Create geometry basic properties
         const struct aiMesh* mesh = aiScene->mMeshes[ aiNode->mMeshes[n] ];
         osg::Geometry* geom = new osg::Geometry;
         geode->addDrawable( geom );
         
         osg::Vec3Array* va = new osg::Vec3Array(mesh->mNumVertices);
         osg::Vec3Array* na = (mesh->mNormals ? new osg::Vec3Array(mesh->mNumVertices) : NULL);
         osg::Vec4Array* ca = (mesh->mColors[0] ? new osg::Vec4Array(mesh->mNumVertices) : NULL);
         for ( unsigned int i=0; i<mesh->mNumVertices; ++i )
         {
             const aiVector3D& v = mesh->mVertices[i];
             (*va)[i].set( v.x, v.y, v.z );
             if ( na )
             {
                 const aiVector3D& n = mesh->mNormals[i];
                 (*na)[i].set( n.x, n.y, n.z );
             }
             if ( ca )
             {
                 const aiColor4D& c = mesh->mColors[0][i];
                 (*ca)[i].set( c.r, c.g, c.b, c.a );
             }
         }
         
         geom->setVertexArray( va );
         if ( na )
         {
             geom->setNormalArray( na );
             geom->setNormalBinding( osg::Geometry::BIND_PER_VERTEX );
         }
         if ( ca )
         {
             geom->setColorArray( ca );
             geom->setColorBinding( osg::Geometry::BIND_PER_VERTEX );
         }
         
         // Create geometry texture coordinates
         unsigned int unit = 0;
         const aiVector3D* aiTexCoords = mesh->mTextureCoords[unit];
         while ( aiTexCoords!=NULL )
         {
             switch ( mesh->mNumUVComponents[unit] )
             {
             case 1:
                 {
                     osg::FloatArray* ta = new osg::FloatArray(mesh->mNumVertices);
                     for ( unsigned int i=0; i<mesh->mNumVertices; ++i )
                         (*ta)[i] = aiTexCoords[i].x;
                     geom->setTexCoordArray( unit, ta );
                 }
                 break;
             case 2:
                 {
                     osg::Vec2Array* ta = new osg::Vec2Array(mesh->mNumVertices);
                     for ( unsigned int i=0; i<mesh->mNumVertices; ++i )
                     {
                         const aiVector3D& t = aiTexCoords[i];
                         (*ta)[i].set( t.x, t.y );
                     }
                     geom->setTexCoordArray( unit, ta );
                 }
                 break;
             case 3:
                 {
                     osg::Vec3Array* ta = new osg::Vec3Array(mesh->mNumVertices);
                     for ( unsigned int i=0; i<mesh->mNumVertices; ++i )
                     {
                         const aiVector3D& t = aiTexCoords[i];
                         (*ta)[i].set( t.x, t.y, t.z );
                     }
                     geom->setTexCoordArray( unit, ta );
                 }
                 break;
             }
             aiTexCoords = mesh->mTextureCoords[++unit];
         }
         
         // Create geometry primitives
         osg::ref_ptr<osg::DrawElementsUInt> de[5];
         de[1] = new osg::DrawElementsUInt(GL_POINTS);
         de[2] = new osg::DrawElementsUInt(GL_LINES);
         de[3] = new osg::DrawElementsUInt(GL_TRIANGLES);
         de[4] = new osg::DrawElementsUInt(GL_QUADS);
         de[0] = new osg::DrawElementsUInt(GL_POLYGON);
         
         osg::DrawElementsUInt* current = NULL;
         for ( unsigned int f=0; f<mesh->mNumFaces; ++f )
         {
             const struct aiFace& face = mesh->mFaces[f];
             if ( face.mNumIndices>4 ) current = de[0].get();
             else current = de[face.mNumIndices].get();
             
             for ( unsigned i=0; i<face.mNumIndices; ++i )
                 current->push_back( face.mIndices[i] );
         }
         
         for ( unsigned int i=0; i<5; ++i )
         {
             if ( de[i]->size()>0 )
                 geom->addPrimitiveSet( de[i].get() );
         }
         
         // Create textures
         osg::StateSet* ss = geom->getOrCreateStateSet();
         const aiMaterial* aiMtl = aiScene->mMaterials[mesh->mMaterialIndex];
         aiReturn texFound = AI_SUCCESS;
         aiTextureOp envOp = aiTextureOp_Multiply;
         aiTextureMapMode wrapMode[3] = {aiTextureMapMode_Clamp};
         unsigned int texIndex = 0;
         aiString path;
         
         while ( texFound==AI_SUCCESS )
         {
             texFound = aiMtl->GetTexture(
                 aiTextureType_DIFFUSE, texIndex++, &path, NULL, &unit, NULL, &envOp, &(wrapMode[0]) );
             if ( unit>0 ) unit--;  // The output UV seems to start at 1?
             if ( texFound!=AI_SUCCESS ) break;
             
             std::string texFile(path.data);
             if ( !osgDB::isAbsolutePath(texFile) ) texFile = getFullPath( filename, texFile );
             
             TextureMap::iterator itr = textures.find(texFile);
             if ( itr==textures.end() )
             {
                 osg::ref_ptr<osg::Texture2D> tex2D = new osg::Texture2D;
                 tex2D->setWrap( osg::Texture::WRAP_S, getWrapMode(wrapMode[0]) );
                 tex2D->setWrap( osg::Texture::WRAP_T, getWrapMode(wrapMode[1]) );
                 tex2D->setWrap( osg::Texture::WRAP_R, getWrapMode(wrapMode[2]) );
                 tex2D->setFilter( osg::Texture::MIN_FILTER, osg::Texture::LINEAR_MIPMAP_LINEAR );
                 tex2D->setFilter( osg::Texture::MAG_FILTER, osg::Texture::LINEAR );
                 tex2D->setImage( osgDB::readImageFile(texFile, options) );
                 textures[texFile] = tex2D;
             }
             
             ss->setTextureAttributeAndModes( unit, textures[texFile].get() );
             if ( unit>0 ) ss->setTextureAttributeAndModes( unit, new osg::TexEnv(getEnvMode(envOp)) );
         }
         
         // Create materials
         createMaterialData( ss, aiMtl );
     }
     
     aiMatrix4x4 m = aiNode->mTransformation;
     m.Transpose();
     
     // Create the node and continue looking for children
     osg::ref_ptr<osg::MatrixTransform> mt;
     mt = new osg::MatrixTransform;
     mt->setMatrix( osg::Matrixf((float*)&m) );
     for ( unsigned int n=0; n<aiNode->mNumChildren; ++n )
     {
         osg::Node* child = traverseAIScene( filename, aiScene, aiNode->mChildren[n], textures, options );
         if ( child ) mt->addChild( child );
     }
     mt->addChild( geode );
     return mt.release();
 }
예제 #4
0
	bool MD2Loader::load( const std::string& fileName )
	{
		size_t pos = fileName.find_last_of("/");
		_fileBase = fileName.substr(0, pos+1);
		_fileName = fileName.substr(pos + 1, fileName.size() - 1);

		_md2File = new MD2File;
		std::ifstream f(fileName.c_str(), std::ios_base::binary);

		//
		if (!f.good())
		{
			return false;
		}

		//
		f.seekg(std::ios_base::beg);
		f.read((char*)&_md2File->_header, sizeof(_md2File->_header));

		//
		if (_md2File->_header.ident != 844121161 || _md2File->_header.version != 8)
		{
			return false;
		}

		if (_md2File->_header.num_skins > 0)
		{
			/* Memory allocations */
			_md2File->_data.skins = new skin[_md2File->_header.num_skins];

			/* Read model data */
			f.seekg(_md2File->_header.offset_skins, std::ios_base::beg);
			f.read((char*)_md2File->_data.skins, sizeof(skin) * _md2File->_header.num_skins);
		}

		if (_md2File->_header.num_st > 0)
		{
			_md2File->_data.texcoords = new texCoord[_md2File->_header.num_st];

			f.seekg(_md2File->_header.offset_st, std::ios_base::beg);
			f.read((char*)_md2File->_data.texcoords, sizeof(texCoord) * _md2File->_header.num_st);
		}

		if (_md2File->_header.num_tris > 0)
		{
			_md2File->_data.triangles = new triangle[_md2File->_header.num_tris];

			f.seekg(_md2File->_header.offset_tris, std::ios_base::beg);
			f.read((char*)_md2File->_data.triangles, sizeof(triangle) * _md2File->_header.num_tris);
		}
		
		if (_md2File->_header.num_frames > 0)
		{
			_md2File->_data.frames = new frame[_md2File->_header.num_frames];

			f.seekg(_md2File->_header.offset_frames, std::ios_base::beg);

			//
			for (int i = 0; i < _md2File->_header.num_frames; ++i)
			{
				_md2File->_data.frames[i].vs = new vertex[_md2File->_header.num_vertices];

				//
				f.read((char*)&_md2File->_data.frames[i].scale, sizeof(vec3));
				f.read((char*)&_md2File->_data.frames[i].translate, sizeof(vec3));
				f.read(_md2File->_data.frames[i].name, 16);
				f.read((char*)_md2File->_data.frames[i].vs, sizeof(vertex) * _md2File->_header.num_vertices);
			}		
		}

		//
		if (_md2File->_header.num_glcmds > 0)
		{
			_md2File->_data.glcmds = new int[_md2File->_header.num_glcmds];

			f.seekg(_md2File->_header.offset_glcmds, std::ios_base::beg);
			f.read((char*)_md2File->_data.glcmds, sizeof(int) * _md2File->_header.num_glcmds);
		}

		//
		f.close();

		//
		std::string texFile(fileName.substr(0, fileName.size() - 3));
		if (_md2File->_data.skins)
		{
			texFile = _fileBase + _md2File->_data.skins->name;
			_tex = TextureFactory::getInstancePtr()->createTextureFromFile(texFile);
			if (_tex)
			{
				_texName = _md2File->_data.skins->name;
				return true;
			}
			//texFile = _fileBase + _md2File->_data.skins->name;
			texFile = texFile.substr(0, texFile.size() - 3);
		}
		
		//
		for (int i = 0; i < _Possible_Extend.size(); ++i)
		{
			if (Buddha::FileSystem::getInstancePtr()->isFileExist(texFile + _Possible_Extend[i]))
			{
				_tex = TextureFactory::getInstancePtr()->createTextureFromFile(texFile + _Possible_Extend[i]);
				if (_tex)
				{
					size_t pos = texFile.find_last_of('//');
					if (pos != std::string::npos)
					{
						_texName = texFile.substr(pos + 1, texFile.size() - 1) + _Possible_Extend[i];
					}
					return true;
				}
			}
		}

		//
		return false;
	}
예제 #5
0
bool TestRenderer::LoadTexture(const std::wstring& filename, ID3D11ShaderResourceView** srv)
{
    FileHandle texFile(CreateFile(filename.c_str(), GENERIC_READ,
        FILE_SHARE_READ, nullptr, OPEN_EXISTING, FILE_ATTRIBUTE_NORMAL, nullptr));
    if (!texFile.IsValid())
    {
        LogError(L"Failed to open texture.");
        return false;
    }

    DWORD bytesRead{};
    uint32_t fileSize = GetFileSize(texFile.Get(), nullptr);

    TextureHeader texHeader{};
    if (!ReadFile(texFile.Get(), &texHeader, sizeof(texHeader), &bytesRead, nullptr))
    {
        LogError(L"Failed to read texture.");
        return false;
    }

    if (texHeader.Signature != TextureHeader::ExpectedSignature)
    {
        LogError(L"Invalid texture file.");
        return false;
    }

    uint32_t pixelDataSize = fileSize - sizeof(TextureHeader);
    std::unique_ptr<uint8_t[]> pixelData(new uint8_t[pixelDataSize]);
    if (!ReadFile(texFile.Get(), pixelData.get(), pixelDataSize, &bytesRead, nullptr))
    {
        LogError(L"Failed to read texture data.");
        return false;
    }

    D3D11_TEXTURE2D_DESC td{};
    td.ArraySize = texHeader.ArrayCount;
    td.Format = texHeader.Format;
#if USE_SRGB
    if (td.Format == DXGI_FORMAT_R8G8B8A8_UNORM)
    {
        td.Format = DXGI_FORMAT_R8G8B8A8_UNORM_SRGB;
    }
    else if (td.Format == DXGI_FORMAT_B8G8R8A8_UNORM)
    {
        td.Format = DXGI_FORMAT_B8G8R8A8_UNORM_SRGB;
    }
#endif
    td.Width = texHeader.Width;
    td.Height = texHeader.Height;
    td.MipLevels = texHeader.MipLevels;
    td.BindFlags = D3D11_BIND_SHADER_RESOURCE;
    td.SampleDesc.Count = 1;
    td.Usage = D3D11_USAGE_DEFAULT;

    D3D11_SUBRESOURCE_DATA init[20] {};
    uint32_t bpp = (uint32_t)BitsPerPixel(td.Format) / 8;

    ComPtr<ID3D11Texture2D> texture;
    HRESULT hr = S_OK;

    // Only try to use mips if width & height are the same size
    if (td.Width == td.Height && td.MipLevels > 1)
    {
        uint32_t width = td.Width;
        uint32_t height = td.Height;
        uint8_t* pPixels = pixelData.get();

        for (int m = 0; m < (int)td.MipLevels; ++m)
        {
            init[m].pSysMem = pPixels;
            init[m].SysMemPitch = width * bpp;
            init[m].SysMemSlicePitch = width * height * bpp;

            width = max(width >> 1, 1);
            height = max(height >> 1, 1);
            pPixels += init[m].SysMemSlicePitch;
        }

        hr = Device->CreateTexture2D(&td, init, &texture);
    }