Example #1
0
MFString MFString::SubStr(int offset, int count) const
{
	if(!pData)
		return *this;

	// limit within the strings range
	int maxChars = (int)pData->bytes - offset;
	if(count < 0 || count > maxChars)
		count = maxChars;

	// bail if we don't need to do anything
	if(count == (int)pData->bytes)
		return *this;

	// allocate a new string
	MFString t;
    t.Reserve(count + 1);
	t.pData->bytes = count;

	// copy sub string
	MFString_CopyN(t.pData->pMemory, pData->pMemory + offset, count);
	t.pData->pMemory[count] = 0;

	return t;
}
Example #2
0
void ParseID3(MFAudioStream *pStream, MFID3 *pID3, int dataSize)
{
	unsigned char *pData = pID3->pID3Data;

	while(pData - pID3->pID3Data <= dataSize)
	{
		if(pID3->major == 2)
		{
			// for the moment, to be safe...
//			MFDebug_Assert(false, "Make this work!!");
			return;

			//int size = (int)pData[5] | ((int)pData[4] << 7) | ((int)pData[3] << 14);
			//pData += 6 + size;
		}
		if(pID3->major > 2)
		{
			ID3Chunk *pChunkHeader = (ID3Chunk*)pData;
			int size = GetSynchSafeInt(pData + 4);

			if(*pData == 'T')
			{
				//uint8 encoding = pData[10];
				const char *pString = (const char*)pData + 11;

				switch(pChunkHeader->id)
				{
					case MFMAKEFOURCC('T', 'I', 'T', '2'):
						MFString_CopyN(pStream->streamInfo.songName, pString, MFMin(size-1, (int)sizeof(pStream->streamInfo.songName)-1));
						break;
					case MFMAKEFOURCC('T', 'A', 'L', 'B'):
						MFString_CopyN(pStream->streamInfo.albumName, pString, MFMin(size-1, (int)sizeof(pStream->streamInfo.albumName)-1));
						break;
					case MFMAKEFOURCC('T', 'P', 'E', '1'):
					case MFMAKEFOURCC('T', 'P', 'E', '2'):
						MFString_CopyN(pStream->streamInfo.artistName, pString, MFMin(size-1, (int)sizeof(pStream->streamInfo.artistName)-1));
						break;
					case MFMAKEFOURCC('T', 'C', 'O', 'N'):
						MFString_CopyN(pStream->streamInfo.genre, pString, MFMin(size-1, (int)sizeof(pStream->streamInfo.genre)-1));
						break;
				}
			}

			pData += 10 + size;
		}
	}
}
Example #3
0
MFString& MFString::Replace(int offset, int range, MFString string)
{
	if(!pData)
	{
		pData = string.pData;
		if(pData)
			++pData->refCount;
		return *this;
	}

	// limit within the strings range
	offset = MFMin(offset, (int)pData->bytes);
	int maxChars = (int)pData->bytes - offset;
	if(range > maxChars)
		range = maxChars;

	// bail if we don't need to do anything
	int strLen = string.NumBytes();
	if(range == 0 && strLen == 0)
		return *this;

	int reposition = strLen - range;
	int newSize = (int)pData->bytes + reposition;

	// reserve memory for the new string
	Reserve(newSize);

	// move tail into place
	if(reposition)
	{
		int tailOffset = offset + range;
		char *pSrc = pData->pMemory + tailOffset;
		char *pDest = pSrc + reposition;

		if(pDest < pSrc)
		{
			while(*pSrc)
				*pDest++ = *pSrc++;
			*pDest = 0;
		}
		else
		{
			int len = (int)pData->bytes - tailOffset;
			while(len >= 0)
			{
				pDest[len] = pSrc[len];
				--len;
			}
		}
	}

	// insert string
	if(strLen)
		MFString_CopyN(pData->pMemory + offset, string.pData->pMemory, strLen);

	pData->bytes = newSize;

	return *this;
}
Example #4
0
MF_API MFTexture* MFTexture_CreateRenderTarget(const char *pName, int width, int height, MFTextureFormat targetFormat)
{
	MFTexture *pTexture = MFTexture_FindTexture(pName);

	if(!pTexture)
	{
		pTexture = &gTextureBank.Create(pName);

		if(targetFormat & TexFmt_SelectNicest)
		{
			targetFormat = TexFmt_A8R8G8B8;
		}

		pTexture->pTemplateData = (MFTextureTemplateData*)MFHeap_AllocAndZero(sizeof(MFTextureTemplateData) + sizeof(MFTextureSurfaceLevel));
		pTexture->pTemplateData->pSurfaces = (MFTextureSurfaceLevel*)&pTexture->pTemplateData[1];
		pTexture->pTemplateData->magicNumber = MFMAKEFOURCC('F','T','E','X');
		pTexture->pTemplateData->imageFormat = targetFormat;
		pTexture->pTemplateData->mipLevels = 1;
		pTexture->pTemplateData->flags = TEX_RenderTarget;

		pTexture->pTemplateData->pSurfaces->width = width;
		pTexture->pTemplateData->pSurfaces->height = height;
		pTexture->pTemplateData->pSurfaces->bitsPerPixel = MFTexture_GetBitsPerPixel(pTexture->pTemplateData->imageFormat);
		pTexture->pTemplateData->pSurfaces->xBlocks = width;
		pTexture->pTemplateData->pSurfaces->yBlocks = height;
		pTexture->pTemplateData->pSurfaces->bitsPerBlock = pTexture->pTemplateData->pSurfaces->bitsPerPixel;
		pTexture->pTemplateData->pSurfaces->pImageData = NULL;
		pTexture->pTemplateData->pSurfaces->bufferLength = 0;
		pTexture->pTemplateData->pSurfaces->pPaletteEntries = NULL;
		pTexture->pTemplateData->pSurfaces->paletteBufferLength = 0;

		pTexture->refCount = 1;
		MFString_CopyN(pTexture->name, pName, sizeof(pTexture->name) - 1);
		pTexture->name[sizeof(pTexture->name) - 1] = 0;

		D3DFORMAT platformFormat = (D3DFORMAT)MFTexture_GetPlatformFormatID(targetFormat, MFDD_D3D9);
		HRESULT hr = pd3dDevice->CreateTexture(width, height, 1, D3DUSAGE_RENDERTARGET, platformFormat, D3DPOOL_DEFAULT, (IDirect3DTexture9**)&pTexture->pInternalData, NULL);

		if(hr != D3D_OK)
		{
			MFHeap_Free(pTexture->pTemplateData);
			gTextureBank.DestroyItem(*pTexture);
			pTexture = NULL;
		}
	}
	else
	{
		pTexture->refCount++;
	}

	return pTexture;
}
Example #5
0
MF_API const char * MFStrN(const char *pSource, size_t n)
{
	char *pBuffer = &gStringBuffer[gStringOffset];

	MFString_CopyN(pBuffer, pSource, (int)n);
	pBuffer[n] = 0;

	gStringOffset += (uint32)n+1;

	if(gStringOffset >= sizeof(gStringBuffer) - 1024) gStringOffset = 0;

	return pBuffer;
}
Example #6
0
MFString::MFString(const char *pString, size_t maxChars)
{
	if(!pString)
	{
		pData = NULL;
	}
	else
	{
		pData = MFStringData_Alloc();
		pData->bytes = MFString_LengthN(pString, (int)maxChars);

		pData->pMemory = (char*)stringHeap.Alloc(pData->bytes + 1, &pData->allocated);

		MFString_CopyN(pData->pMemory, pString, (int)pData->bytes);
		pData->pMemory[pData->bytes] = 0;
	}
}
Example #7
0
void MFSound_InitModulePlatformSpecific(int *pSoundDataSize, int *pVoiceDataSize)
{
	MFCALLSTACK;

	gDevices.Init(sizeof(AudioDevice), 8, 8);

	ALCint minor, major;
	alcGetIntegerv(NULL, ALC_MAJOR_VERSION, 1, &major);
	alcGetIntegerv(NULL, ALC_MINOR_VERSION, 1, &minor);
	gAPIVersion = major*100 + minor;

	bool bCanEnumerate, bHasCapture;
	if(gAPIVersion >= 101)
	{
		bCanEnumerate = true;
		bHasCapture = true;
	}
	else
	{
		bCanEnumerate = alcIsExtensionPresent(NULL, "ALC_ENUMERATE_ALL_EXT") == AL_TRUE;
		bHasCapture = alcIsExtensionPresent(NULL, "ALC_EXT_CAPTURE") == AL_TRUE;
	}

	if(bCanEnumerate)
	{
		const char *pDevices = alcGetString(NULL, ALC_ALL_DEVICES_SPECIFIER);
		const char *pDefault = alcGetString(NULL, ALC_DEFAULT_DEVICE_SPECIFIER);
		while(pDevices && *pDevices)
		{
			bool bIsDefault = !MFString_Compare(pDevices, pDefault);
			MFDebug_Log(2, MFStr("OpenAL: found output device '%s'%s", pDevices, bIsDefault ? " (default)" : ""));

			MFDevice *pDevice = MFDevice_AllocDevice(MFDT_AudioRender, &DestroyDevice);
			pDevice->pInternal = gDevices.AllocAndZero();
			pDevice->state = MFDevState_Ready;

			AudioDevice &device = *(AudioDevice*)pDevice->pInternal;
			MFString_CopyN(pDevice->strings[MFDS_ID], pDevices, sizeof(pDevice->strings[MFDS_ID])-1);
			pDevice->strings[MFDS_ID][sizeof(pDevice->strings[MFDS_ID])-1] = 0;
			device.pDevice = NULL;

			if(bIsDefault)
					MFDevice_SetDefaultDevice(MFDT_AudioRender, MFDDT_All, pDevice);

			pDevices += MFString_Length(pDevices) + 1;
		}

		if(!MFDevice_GetDefaultDevice(MFDT_AudioRender, MFDDT_Default))
		{
			MFDebug_Warn(2, "OpenAL: No default output device?");

			// HACK: set it to the first one...
			MFDevice *pDevice = MFDevice_GetDeviceByIndex(MFDT_AudioRender, 0);
			MFDevice_SetDefaultDevice(MFDT_AudioRender, MFDDT_All, pDevice);
		}

		if(bHasCapture)
		{
			pDevices = alcGetString(NULL, ALC_CAPTURE_DEVICE_SPECIFIER);
			pDefault = alcGetString(NULL, ALC_CAPTURE_DEFAULT_DEVICE_SPECIFIER);
			while(pDevices && *pDevices)
			{
				bool bIsDefault = !MFString_Compare(pDevices, pDefault);
				MFDebug_Log(2, MFStr("OpenAL: found capture device '%s'%s", pDevices, bIsDefault ? " (default)" : ""));

				MFDevice *pDevice = MFDevice_AllocDevice(MFDT_AudioCapture, &DestroyDevice);
				pDevice->pInternal = gDevices.AllocAndZero();
				pDevice->state = MFDevState_Ready;

				AudioDevice &device = *(AudioDevice*)pDevice->pInternal;
				MFString_CopyN(pDevice->strings[MFDS_ID], pDevices, sizeof(pDevice->strings[MFDS_ID])-1);
				pDevice->strings[MFDS_ID][sizeof(pDevice->strings[MFDS_ID])-1] = 0;
				device.pDevice = NULL;

				if(bIsDefault)
					MFDevice_SetDefaultDevice(MFDT_AudioCapture, MFDDT_All, pDevice);

				pDevices += MFString_Length(pDevices) + 1;
			}

			if(!MFDevice_GetDefaultDevice(MFDT_AudioCapture, MFDDT_Default))
				MFDebug_Warn(2, "OpenAL: No default capture device?");
		}
	}

	// create a context
	Context *pContext = CreateContext(MFDevice_GetDefaultDevice(MFDT_AudioRender, MFDDT_Default));
	MakeCurrent(pContext);

	// we need to return the size of the internal structures so the platform independant
	// code can make the correct allocations..
	*pSoundDataSize = sizeof(MFSoundDataInternal);
	*pVoiceDataSize = sizeof(MFVoiceDataInternal);
}
Example #8
0
void CreateVorbisStream(MFAudioStream *pStream, const char *pFilename)
{
	MFCALLSTACK;

	MFVorbisStream *pVS = (MFVorbisStream*)MFHeap_Alloc(sizeof(MFVorbisStream));
	pStream->pStreamData = pVS;

	// open vorbis file
	MFFile* hFile = MFFileSystem_Open(pFilename);
	if(!hFile)
		return;

	// attempt to cache the vorbis stream
	MFOpenDataCachedFile cachedOpen;
	cachedOpen.cbSize = sizeof(MFOpenDataCachedFile);
	cachedOpen.openFlags = MFOF_Read | MFOF_Binary | MFOF_Cached_CleanupBaseFile;
	cachedOpen.maxCacheSize = 256*1024; // 256k cache for vorbis stream should be heaps!!
	cachedOpen.pBaseFile = hFile;

	MFFile *pCachedFile = MFFile_Open(MFFileSystem_GetInternalFileSystemHandle(MFFSH_CachedFileSystem), &cachedOpen);
	if(pCachedFile)
		hFile = pCachedFile;

	// setup vorbis read callbacks
	ov_callbacks callbacks;
	callbacks.read_func = MFFile_StdRead;
	callbacks.seek_func = MFSound_VorbisSeek;
	callbacks.close_func = MFFile_StdClose;
	callbacks.tell_func = MFFile_StdTell;

	// open vorbis file
	if(ov_test_callbacks(hFile, &pVS->vorbisFile, NULL, 0, callbacks))
	{
		MFDebug_Assert(false, "Not a vorbis file.");
		MFHeap_Free(pVS);
		return;
	}

	ov_test_open(&pVS->vorbisFile);

	// get vorbis file info
	pVS->pInfo = ov_info(&pVS->vorbisFile, -1);

#if defined(VORBIS_TREMOR)
//	pStream->trackLength = (float)ov_pcm_total(&pVS->vorbisFile, -1) / (float)pVS->pInfo->rate;
	pStream->trackLength = 1000.0f;
#else
	pStream->trackLength = (float)ov_time_total(&pVS->vorbisFile, -1);
#endif

	// fill out the stream info
	pStream->streamInfo.sampleRate = pVS->pInfo->rate;
	pStream->streamInfo.channels = pVS->pInfo->channels;
	pStream->streamInfo.bitsPerSample = 16;
	pStream->streamInfo.bufferLength = pVS->pInfo->rate;

	// read the vorbis comment data
	pVS->pComment = ov_comment(&pVS->vorbisFile, -1);
	if(pVS->pComment)
	{
		const char *pTitle = vorbis_comment_query(pVS->pComment, "TITLE", 0);
		const char *pArtist = vorbis_comment_query(pVS->pComment, "ALBUM", 0);
		const char *pAlbum = vorbis_comment_query(pVS->pComment, "ARTIST", 0);
		const char *pGenre = vorbis_comment_query(pVS->pComment, "GENRE", 0);

		if(pTitle)
			MFString_CopyN(pStream->streamInfo.songName, pTitle, sizeof(pStream->streamInfo.songName)-1);
		if(pArtist)
			MFString_CopyN(pStream->streamInfo.artistName, pArtist, sizeof(pStream->streamInfo.artistName)-1);
		if(pAlbum)
			MFString_CopyN(pStream->streamInfo.albumName, pAlbum, sizeof(pStream->streamInfo.albumName)-1);
		if(pGenre)
			MFString_CopyN(pStream->streamInfo.genre, pGenre, sizeof(pStream->streamInfo.genre)-1);
	}
}
Example #9
0
int* ParseMaterialList(const char *pText, F3DSubObject &sub, int numFaces)
{
	int *pMatFaces = NULL;

	const char *pMatList = FindSectionInScope(pText, "MeshMaterialList");

	if(pMatList)
	{
		SkipToken(pMatList, "MeshMaterialList");
		SkipToken(pMatList, "{");

		int numMats = GetInt(pMatList, &pMatList);
		MFDebug_Assert(numMats < 16, "Exceeded maximum 16 materials per subobject...");
		int numMatFaces = GetInt(pMatList, &pMatList);
		MFDebug_Assert(numMatFaces == numFaces, "Number of material faces does not match number of mesh faces");

		pMatFaces = (int*)MFHeap_Alloc(sizeof(int)*numMatFaces);
		GetIntArray(pMatList, pMatFaces, numMatFaces, &pMatList);

		// process materials...
		const char *pToken = GetNextToken(pMatList, &pMatList);
//		MFDebug_Assert(!MFString_Compare(pToken, ";"), "Value is not terminated with a semicolon.\n");

		if(!MFString_Compare(pToken, ";"))
			pToken = GetNextToken(pMatList, &pMatList);

		while(MFString_Compare(pToken, "}"))
		{
			if(!MFString_Compare(pToken, "Material"))
			{
				const char *pMatName = GetNextToken(pMatList, &pToken);

				if(MFString_Compare(pMatName, "{"))
					pMatList = pToken;
				else
					pMatName = "Unknown Material";

				int matID = pModel->GetMaterialChunk()->GetMaterialIndexByName(pMatName);

				F3DMaterialSubobject &matSub = sub.matSubobjects.push();

				if(matID != -1)
				{
					matSub.materialIndex = matID;
					SkipSection(pMatList);
				}
				else
				{
					matSub.materialIndex = pModel->GetMaterialChunk()->materials.size();
					F3DMaterial &mat = pModel->GetMaterialChunk()->materials.push();
					MFString_CopyN(mat.name, pMatName, 64);

					SkipToken(pMatList, "{");

					mat.diffuse.x = GetFloat(pMatList, &pMatList);
					mat.diffuse.y = GetFloat(pMatList, &pMatList);
					mat.diffuse.z = GetFloat(pMatList, &pMatList);
					mat.diffuse.w = GetFloat(pMatList, &pMatList);
					SkipToken(pMatList, ";");

					mat.specularLevel = GetFloat(pMatList, &pMatList);

					mat.specular.x = GetFloat(pMatList, &pMatList);
					mat.specular.y = GetFloat(pMatList, &pMatList);
					mat.specular.z = GetFloat(pMatList, &pMatList);
					mat.diffuse.w = 0.0f;
					SkipToken(pMatList, ";");

					mat.emissive.x = GetFloat(pMatList, &pMatList);
					mat.emissive.y = GetFloat(pMatList, &pMatList);
					mat.emissive.z = GetFloat(pMatList, &pMatList);
					mat.emissive.w = 0.0f;
					SkipToken(pMatList, ";");

					// any textures...
					pToken = GetNextToken(pMatList, &pMatList);

					while(MFString_Compare(pToken, "}"))
					{
						if(!MFString_Compare(pToken, "TextureFilename"))
						{
							SkipToken(pMatList, "{");
							MFString_Copy(mat.maps[0], GetString(pMatList, &pMatList));
							SkipToken(pMatList, "}");
						}
						else
						{
							MFDebug_Warn(4, MFStr("Unknown token '%s'\n", pToken));
						}

						pToken = GetNextToken(pMatList, &pMatList);
					}
				}
			}
			else if(!MFString_Compare(pToken, "{"))
			{
				// read material name
				const char *pMatName = GetNextToken(pMatList, &pMatList);

				int matID = pModel->GetMaterialChunk()->GetMaterialIndexByName(pMatName);

				F3DMaterialSubobject &matSub = sub.matSubobjects.push();

				if(matID != -1)
				{
					matSub.materialIndex = matID;
				}
				else
				{
					matSub.materialIndex = pModel->GetMaterialChunk()->materials.size();
					F3DMaterial &mat = pModel->GetMaterialChunk()->materials.push();
					MFString_CopyN(mat.name, pMatName, 64);
				}

				pToken = GetNextToken(pMatList, &pMatList);
				MFDebug_Assert(!MFString_Compare(pToken, "}"), "Scope not closed.\n");
			}
			else
			{
				MFDebug_Warn(4, MFStr("Unknown token '%s'\n", pToken));
			}

			pToken = GetNextToken(pMatList, &pMatList);
		}
	}

	return pMatFaces;
}