void DiMotionSerializer::ImportMotion( DiDataStreamPtr& stream, DiMotion* pDest ) { char sign[4]; stream->Read(sign,4); if (sign[0] == 'D' && sign[1] == 'i' && sign[2] == 'M' && sign[3] == 'o') { uint16 version; stream->Read(&version,sizeof(uint16)); if (version >= MOTION_SERIAL_VERSION_NUM) { DI_ERROR("Invalid version number!"); return; } DiMotionSerializerImpl* impl = GetImplemention((DiMotionSerialVersion)version); if (impl) { impl->ImportMotion(stream,pDest); } DI_DELETE impl; return; } DI_ERROR("Invalid head format!"); return; }
void DiMeshSerializer::ImportMesh( DiDataStreamPtr& stream, DiMesh* pDest ) { DI_SERIAL_LOG("Loading mesh : %s", stream->GetName().c_str()); char sign[4]; stream->Read(sign,4); if (CheckHead(sign)) { uint16 version; stream->Read(&version,sizeof(uint16)); DI_SERIAL_LOG("Mesh version: %d", version); if (version >= MODEL_SERIAL_VERSION_NUM) { DI_ERROR("Unknow mesh version."); return; } DiMeshSerializerImpl* impl = GetImplemention((DiMeshSerialVersion)version); if (impl) { impl->ImportMesh(stream,pDest); } DI_DELETE impl; return; } DI_ERROR("Invalid mesh file head."); return; }
DiTransUnitPtr DiCullNode::DetachObject( unsigned short index ) { DiTransUnitPtr ret; if (index < mObjectsByName.size()) { ObjectMap::iterator i = mObjectsByName.begin(); while (index--)++i; ret = i->second; mObjectsByName.erase(i); if (ret->GetParentNode() == this) { ret->NotifyAttached((DiCullNode*)0); } NeedUpdate(); return ret; } else { DI_ERROR("Cannot detach object, invalid index"); return NULL; } }
void DiMeshSerializerImpl::ReadSubMesh( DiDataStreamPtr& stream, DiMesh* pMesh ) { DI_SERIAL_LOG("Reading submesh.."); DiSubMesh* sm = pMesh->CreateSubMesh(); unsigned short streamID = 0; DiString material = ReadString(stream); sm->SetMaterialName(material); DI_SERIAL_LOG("Liking material: %s", material.c_str()); unsigned int indexCount = 0; ReadInts(stream, &indexCount, 1); DI_SERIAL_LOG("Indeices count: %d", indexCount); bool idx32bit; ReadBools(stream, &idx32bit, 1); DI_SERIAL_LOG("Index size: %d", idx32bit?32:16); uint16 primitive; ReadShorts(stream,&primitive,1); sm->SetPrimitiveType((DiPrimitiveType)primitive); DI_SERIAL_LOG("Primitive type: %d", primitive); if (indexCount > 0) { void* indexdata = sm->CreateIndexData(indexCount,idx32bit?TRUE:FALSE); int size = indexCount * (sm->GetIndexSize() / 8); stream->Read(indexdata, size); DI_SERIAL_LOG("%d bytes readed", size); } streamID = ReadChunk(stream); if (streamID != DI_GEOMETRY) { DI_ERROR("Bad stream ID"); return; } ReadGeometry(stream, sm); if (!stream->Eof()) { streamID = ReadChunk(stream); if (streamID == DI_MESH_WEIGHTS) { ReadSubMeshBoneWeights(stream,sm); } else { if (!stream->Eof()) stream->Skip(-MSTREAM_OVERHEAD_SIZE); } } }
void DiInstanceBatch::SetInstancesPerBatch( size_t instancesPerBatch ) { if( !mInstancedModels.empty() ) { DI_ERROR("SetInstancesPerBatch Error: empty instanced model"); } mInstancesPerBatch = instancesPerBatch; }
void DiD3D9ErrorCheck::CheckError(HRESULT hr) { if (hr != S_OK) { DiString desc = "Direct3D API Error:\n"; desc += GetResultString(hr); DI_ERROR(desc.c_str()); } }
void DiInstanceManager::SetInstancesPerBatch( size_t instancesPerBatch ) { if( !mInstanceBatches.empty() ) { DI_ERROR("Error: SetInstancesPerBatch(), instance batch empty"); return; } mInstancesPerBatch = instancesPerBatch; }
void DiInstanceManager::SetMaxLookupTableInstances( size_t maxLookupTableInstances ) { if( !mInstanceBatches.empty() ) { DI_ERROR("Error: SetInstancesPerBatch(), instance batch empty"); return; } mMaxLookupTableInstances = maxLookupTableInstances; }
DiTransUnitPtr DiCullNode::GetAttachedObject( const DiString& name ) { ObjectMap::iterator i = mObjectsByName.find(name); if (i == mObjectsByName.end()) { DI_ERROR("Cannot find the attachment object by name : %s",name.c_str()); } return i->second; }
DiInstanceBatchPtr DiInstanceManager::BuildNewBatch(const DiString& materialName, bool firstTime) { DiSubMesh::IndexMap &idxMap = mMeshReference->GetSubMesh(mSubMeshIdx)->GetBlendIndexToBoneIndexMap(); //idxMap = idxMap.empty() ? mMeshReference->sharedBlendIndexToBoneIndexMap : idxMap; DiMaterialPtr mat = DiAssetManager::GetInstance().GetAsset<DiMaterial>( materialName ); InstanceBatchVec &materialInstanceBatch = mInstanceBatches[materialName]; DiInstanceBatchPtr batch; DiString name; name.Format("%s_InstanceBatch_%d",mName.c_str(),mIdCount++); switch( mInstancingTechnique ) { case INSTANCE_SHADER_BASED: batch = make_shared<DiInstanceBatchShader>( this, mMeshReference, mMotionReference, mat, mInstancesPerBatch, &idxMap, name ); break; case INSTANCE_HARDWARE_BASED: batch = make_shared<DiInstanceBatchHardware>(this, mMeshReference, mat, mInstancesPerBatch, name ); break; default: DI_ERROR("Unsupported instanced technique."); break; } if( !firstTime ) { batch->BuildFrom( mMeshReference->GetSubMesh(mSubMeshIdx) ); } else { const size_t maxInstPerBatch = batch->CalculateMaxNumInstances( mMeshReference-> GetSubMesh(mSubMeshIdx) ); mInstancesPerBatch = DiMath::Min( maxInstPerBatch, mInstancesPerBatch ); batch->SetInstancesPerBatch( mInstancesPerBatch ); batch->Build( mMeshReference->GetSubMesh(mSubMeshIdx) ); } //const BatchSettings &batchSettings = mBatchSettings[materialName]; //batch->SetCastShadows( batchSettings.setting[CAST_SHADOWS] ); DiCullNode *sceneNode = mSceneManager->GetRootNode()->CreateChild(); sceneNode->AttachObject( batch ); materialInstanceBatch.push_back( batch ); return batch; }
DiNodeClip* DiAnimation::CreateNodeClip( uint32 handle ) { if (HasNodeClip(handle)) { DI_ERROR("The node clip which handle is has already existed%", handle); return NULL; } DiNodeClip* ret = DI_NEW DiNodeClip(this, handle); mNodeClips[handle] = ret; return ret; }
DiNodeClip* DiAnimation::GetNodeClip( uint32 handle ) const { NodeClips::const_iterator i = mNodeClips.find(handle); if (i == mNodeClips.end()) { DI_ERROR("Cannot find the node clips which handle is %d",handle); return NULL; } return i->second; }
DiNodeClip* DiAnimation::CreateAttachClip( DiString strAttachName ) { if (HasAttachClip(strAttachName)) { DI_ERROR("The asttach clip named %s has already existed", strAttachName.c_str()); return NULL; } DiNodeClip* ret = DI_NEW DiNodeClip(this, strAttachName.ToHash()); mAttachClips[strAttachName] = ret; return ret; }
bool DiInstancedModel::ShareTransformWith( DiInstancedModel *slave ) { if( !this->mBatchOwner->HasSkeleton() || !this->mBatchOwner->SupportsSkeletalAnimation() ) { return false; } if( this->mSharedTransformModel ) { DI_ERROR("已经共享了其他的实例模型"); return false; } if( this->mBatchOwner->GetSkeleton() != slave->mBatchOwner->GetSkeleton() ) { DI_ERROR("骨骼无法匹配"); return false; } slave->UnlinkTransform(); slave->DestroySkeletonInstance(); slave->mSkeletonInstance = this->mSkeletonInstance; slave->mClipSet = this->mClipSet; slave->mBoneMatrices = this->mBoneMatrices; if (mBatchOwner->UseBoneWorldMatrices()) { slave->mBoneWorldMatrices = this->mBoneWorldMatrices; } slave->mSharedTransformModel = this; this->mSharingPartners.push_back( slave ); slave->mBatchOwner->MarkTransformSharingDirty(); return true; }
DiTimer::DiTimer() { LARGE_INTEGER frequent; if (QueryPerformanceFrequency(&frequent)) { mTicksPerSec = frequent.QuadPart; Start(); } else { DI_ERROR("Unable to use high performace timer!"); } }
void DiCullNode::AttachObject(DiTransUnitPtr obj) { if (obj->IsAttached()) { DI_ERROR("The object has been attached"); } obj->NotifyAttached(this); DI_ASSERT(!mObjectsByName.contains(obj->GetName())); mObjectsByName.insert(ObjectMap::value_type(obj->GetName(), obj)); NeedUpdate(); }
DiTransUnitPtr DiCullNode::GetAttachedObject( unsigned short index ) { if (index < mObjectsByName.size()) { ObjectMap::iterator i = mObjectsByName.begin(); while (index--)++i; return i->second; } else { DI_ERROR("Cannot find the attachment object by id : %d",index); return NULL; } }
bool DiD3D9WindowTarget::SwapBuffer() { bool resized = CheckSizeChanged(); HRESULT hr = Present(); if (D3DERR_DEVICELOST == hr || resized) return false; else { if (FAILED(hr)) { DI_ERROR("Swaping buffer failed!"); } return true; } }
DiTransUnitPtr DiCullNode::DetachObject( const DiString& name ) { ObjectMap::iterator it = mObjectsByName.find(name); if (it == mObjectsByName.end()) { DI_ERROR("Cannot find the object : %s", name.c_str()); } DiTransUnitPtr ret = it->second; mObjectsByName.erase(it); if (ret->GetParentNode() == this) { ret->NotifyAttached((DiCullNode*)0); } NeedUpdate(); return ret; }
bool DiWin32EGLWindow::_Create(uint32& width, uint32& height, const DiString& title, bool fullscreen) { bool ok = false; DI_ASSERT(!mWndHandle); registerWindowClass((HINSTANCE)::GetModuleHandle(0)); RECT winRect; winRect.left = 0; winRect.top = 0; winRect.right = width; winRect.bottom = height; DWORD dwstyle = (fullscreen ? gFullscreenStyle : gWindowStyle); uint32 offset = fullscreen ? 0 : 50; ::AdjustWindowRect(&winRect, dwstyle, 0); mWndHandle = ::CreateWindowA(gWindowClass, title.c_str(), dwstyle, offset, offset, winRect.right - winRect.left, winRect.bottom - winRect.top, 0, 0, 0, 0); DI_ASSERT(mWndHandle); mWindow = (NativeWindowType)mWndHandle; if (mWndHandle) { ok = true; ShowWindow((HWND)mWndHandle, SW_SHOWNORMAL); ::SetFocus((HWND)mWndHandle); SetWindowLongPtr((HWND)mWndHandle, GWLP_USERDATA, PtrToLong(this)); mHDC = ::GetDC((HWND)mWndHandle); } RAWINPUTDEVICE rawInputDevice; rawInputDevice.usUsagePage = 1; rawInputDevice.usUsage = 6; rawInputDevice.dwFlags = 0; rawInputDevice.hwndTarget = NULL; BOOL status = RegisterRawInputDevices(&rawInputDevice, 1, sizeof(rawInputDevice)); if (status != TRUE) { DI_ERROR("RegisterRawInputDevices failed: %d", GetLastError()); } mNativeDisplay = GetDC(mWindow); mEglDisplay = eglGetDisplay(mNativeDisplay); // fallback for some emulations if (mEglDisplay == EGL_NO_DISPLAY) { mEglDisplay = eglGetDisplay(EGL_DEFAULT_DISPLAY); } eglInitialize(mEglDisplay, NULL, NULL); eglBindAPI(EGL_OPENGL_ES_API); mGLSupport->SetGLDisplay(mEglDisplay); mEglSurface = CreateSurfaceFromWindow(mEglDisplay, mWindow); return ok; }