/// <summary> /// 描画時に呼び出される3D処理 /// </summary> /// <param name="immediateContext"></param> /// <param name="totalTime">アプリケーションが開始してからの経過時間 (秒単位) です。</param> /// <param name="elapsedTime">最後のフレームからの経過時間 (秒単位) です。</param> /// <param name="oldPriority">1つ前のプライオリティ</param> /// <param name="priority">プライオリティ</param> /// <param name="cbd"></param> /// <param name="callNum">レンダーが呼ばれた回数 0~</param> /// <param name="passCount">エフェクトパス 0~</param> /// <returns></returns> internal abstract int CallDraw3D( DeviceContext immediateContext, double totalTime, float elapsedTime, MCDrawCommandPriority oldPriority, MCDrawCommandPriority priority, MCCallBatchDrawing cbd, int callNum, int passCount );
/// <summary> /// 描画コマンドを解読し、描画処理を開始する /// </summary> /// <param name="device">レンダリングに使われる D3D11Device デバイス</param> /// <param name="immediateContext">描画対象</param> /// <param name="totalTime">アプリケーションが開始してからの経過時間 (秒単位) です。</param> /// <param name="elapsedTime">最後のフレームからの経過時間 (秒単位) です。</param> /// <returns>通常、エラーが発生しなかった場合は 0 を返す。</returns> public int AllDrawing(SharpDX.Direct3D11.Device device, DeviceContext immediateContext, double totalTime, float elapsedTime) { int hr = 0; MCCallBatchDrawing callBathDraw; int i, j, nowCnt; int targetMax, targetCnt, translucence; int passCnt; float fZ; int maxPassNum; int cameraSameCheckFlg; MCDrawingEffect de; IMCEffect effect; if (m_drawingEffectGroup == null) { goto GOTO_END; } // エフェクトグループの更新 m_drawingEffectGroup.OnUpdate(totalTime, elapsedTime); // 描画処理を開始したことを知らせるフラグを立てる StartAllDrawing(); m_oldDCRegNum = m_DCRegNum; // 実行された描画コマンドのリセット m_DCommandRunNum = 0; //============================= // 描画コマンドをソートする //============================= Sorting(); //#################################################### //# 登録されている対象とするMCDrawingEffectで派生された //# クラスの数だけ繰り返す //#################################################### nowCnt = 0; foreach (var nowNDEI in m_drawingEffectGroup.GetNoDrawEffectIndexPtr()) { targetMax = 0; translucence = 0; // MCDrawingEffectポインタ de = nowNDEI.Value; // callBathDraw = de; Debug.Assert(callBathDraw != null); effect = callBathDraw.GetEffect(); Debug.Assert(effect != null); // 前回のカメラの視錘台の値をそのまま使うかチェックフラグ取得 cameraSameCheckFlg = de.GetCameraSameCheckFlg(); if (de.IsSimpleProcess && de.RegistrationCount == 0) { //==============================// // 単体でもエフェクト処理をする // //==============================// for (i = 0; i < de.CallRenderCount; ++i) { //############### //# レンダー開始 hr = de.OnRenderStart(device, immediateContext, totalTime, elapsedTime, i); { if (hr != 0) { de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } effect.GetPass(out maxPassNum); for (passCnt = 0; passCnt < maxPassNum; ++passCnt) { effect.SetPass(passCnt); if (de.OnRenderBetweenBefore(device, immediateContext, totalTime, elapsedTime, i, 0) != 0) { hr = -1; de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } if (de.OnRenderBetweenAfter(device, immediateContext, totalTime, elapsedTime, i, 0) != 0) { hr = -1; de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } } } de.OnRenderEnd(device, immediateContext, i); //# レンダー終了 //############### } } else if (de.RegistrationCount > 0) { //==============================// // 描画コマンドが存在した // //==============================// for (i = 0; i < de.CallRenderCount; ++i) { //############### //# レンダー開始 hr = de.OnRenderStart(device, immediateContext, totalTime, elapsedTime, i); { if (hr != 0) { de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } //========================= // 視錘台の衝突判定チェック //========================= if ((cameraSameCheckFlg & 0x00000001) == 0) { targetMax = 0; translucence = 0; for (j = 0; j < de.RegistrationCount; ++j) { MCDrawBase tmpDC = m_aDrawCommand[nowCnt + j]; //----------------------------------------------------------- // 視錘台と描画対象の衝突チェック // 場合によっては、ここで対象オブジェクトを半透明化しても良い //----------------------------------------------------------- if ( tmpDC.CameraCollison( de.GetCurrentCamera(), out fZ) ) { //--------------------------------------- // 視錘台内にオブジェクトがあったので登録 //--------------------------------------- // カメラ位置からのZ値をセット tmpDC.SetZValueFromCamera(fZ); // そしてターゲット登録 if (!tmpDC.DrawCommandPriority.D3Translucent) { // 不透明 m_aDrawComandTarget[targetMax++] = tmpDC; } else { // 半透明 m_aDCTmp00[translucence++] = tmpDC; } ++m_DCommandRunNum; } } if (translucence > 0) { //-------------------------- // 半透明オブジェクトソート //-------------------------- TranslucenceSorting(translucence, ref m_aDCTmp00); targetMax += translucence; for (int cnt = 0; cnt < translucence; ++cnt) { m_aDrawComandTarget[targetMax + cnt] = m_aDCTmp00[cnt]; } ResetDCTmp00(translucence); } else { } } cameraSameCheckFlg >>= 1; //===================== // エフェクト //===================== MCDrawCommandPriority priorityTmp, priorityOld = new MCDrawCommandPriority(); int targetOffset = 0; //BYTE bNowD3Type; targetCnt = 0; do { // MCDrawCommandPriorityのパラメータを元にテクニックの変更 de.OnCheckChangeTechnique(m_aDrawComandTarget[targetCnt]); effect.GetPass(out maxPassNum); for (passCnt = 0; passCnt < maxPassNum; ++passCnt) { effect.SetPass(passCnt); if (de.OnRenderBetweenBefore(device, immediateContext, totalTime, elapsedTime, i, passCnt) != 0) { hr = -1; de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } // 最初の一回は前回の物が存在しないため // 初期化 priorityOld.Init(); for (targetCnt = targetOffset; targetCnt < targetMax; ++targetCnt) { //-------------------------- // 描画ターゲットの呼び出し //-------------------------- priorityTmp = m_aDrawComandTarget[targetCnt].DrawCommandPriority; if (priorityTmp.D3) { //------------- // 3D属性である //------------- if (de.IsCurrentPassCallDraw2D3D) { hr = m_aDrawComandTarget[targetCnt].CallDraw3D( immediateContext, totalTime, elapsedTime, priorityOld, priorityTmp, callBathDraw, i, passCnt ); } if ((targetCnt + 1) < targetMax) { if (priorityTmp.D3TypeFlags != m_aDrawComandTarget[targetCnt + 1].DrawCommandPriority.D3TypeFlags || priorityTmp.Technique != m_aDrawComandTarget[targetCnt + 1].DrawCommandPriority.Technique) { // タイプが変わった(例:通常からボーンに変わったとか) if (passCnt == (maxPassNum - 1)) { // タイプが変わった所から開始するための処理 targetOffset = ++targetCnt; } break; } } } else { // ISprite if (de.IsCurrentPassCallDraw2D3D) { de.SetSpriteTypeNo((int)priorityTmp.D2RenderType); hr = m_aDrawComandTarget[targetCnt].CallDrawingSprite( totalTime, elapsedTime, de.GetSpriteRenderType(), callBathDraw ); } if ((targetCnt + 1) < targetMax) { if (priorityTmp.D2RenderType != m_aDrawComandTarget[targetCnt + 1].DrawCommandPriority.D2RenderType || priorityTmp.Technique != m_aDrawComandTarget[targetCnt + 1].DrawCommandPriority.Technique) { // スプライト処理タイプが変わった または // テクニックが変わった if (passCnt == (maxPassNum - 1)) { // タイプが変わった所から開始するための処理 targetOffset = ++targetCnt; } break; } } //------------- } // MCDrawCommandPriorityの保存 priorityOld = m_aDrawComandTarget[targetCnt].DrawCommandPriority; } if (hr != 0) { de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } if (de.OnRenderBetweenAfter(device, immediateContext, totalTime, elapsedTime, i, passCnt) != 0) { hr = -1; de.OnRenderEnd(device, immediateContext, i); Debug.Assert(false); goto GOTO_END; } } } while (targetCnt < targetMax); } de.OnRenderEnd(device, immediateContext, i); //# レンダー終了 //############### } // m_paDCRegの位置を移動させるために加算 nowCnt += de.RegistrationCount; } else { //==============================// // 単体の場合処理しない // //==============================// } } GOTO_END: //===================================== // リセットする //===================================== AllDrawingReset(); // 描画処理を終了したことを知らせるフラグを立てる EndAllDrawing(); return(hr); }