protected override void SetAdditionalSimParams(IPropertyWrapper simMaterial) { base.SetAdditionalSimParams(simMaterial); simMaterial.SetFloat(sp_Damping, Settings._damping); simMaterial.SetFloat(sp_Gravity, OceanRenderer.Instance.Gravity * Settings._gravityMultiplier); float laplacianKernelAngle = _rotateLaplacian ? Mathf.PI * 2f * Random.value : 0f; simMaterial.SetVector(sp_LaplacianAxisX, new Vector2(Mathf.Cos(laplacianKernelAngle), Mathf.Sin(laplacianKernelAngle))); // assign sea floor depth - to slot 1 current frame data. minor bug here - this depth will actually be from the previous frame, // because the depth is scheduled to render just before the animated waves, and this sim happens before animated waves. if (OceanRenderer.Instance._lodDataSeaDepths) { OceanRenderer.Instance._lodDataSeaDepths.BindResultData(simMaterial); } else { LodDataMgrSeaFloorDepth.BindNull(simMaterial); } if (OceanRenderer.Instance._lodDataFlow) { OceanRenderer.Instance._lodDataFlow.BindResultData(simMaterial); } else { LodDataMgrFlow.BindNull(simMaterial); } }
protected override void SetAdditionalSimParams(IPropertyWrapper simMaterial) { base.SetAdditionalSimParams(simMaterial); simMaterial.SetFloat(sp_Damping, Settings._damping); simMaterial.SetFloat(sp_Gravity, OceanRenderer.Instance.Gravity * Settings._gravityMultiplier); simMaterial.SetFloat(sp_CourantNumber, Settings._courantNumber); // assign sea floor depth - to slot 1 current frame data. minor bug here - this depth will actually be from the previous frame, // because the depth is scheduled to render just before the animated waves, and this sim happens before animated waves. LodDataMgrSeaFloorDepth.Bind(simMaterial); LodDataMgrFlow.Bind(simMaterial); }
protected override void SetAdditionalSimParams(IPropertyWrapper simMaterial) { base.SetAdditionalSimParams(simMaterial); simMaterial.SetFloat(sp_FoamFadeRate, Settings._foamFadeRate); simMaterial.SetFloat(sp_WaveFoamStrength, Settings._waveFoamStrength); simMaterial.SetFloat(sp_WaveFoamCoverage, Settings._waveFoamCoverage); simMaterial.SetFloat(sp_ShorelineFoamMaxDepth, Settings._shorelineFoamMaxDepth); simMaterial.SetFloat(sp_ShorelineFoamStrength, Settings._shorelineFoamStrength); // assign animated waves - to slot 1 current frame data LodDataMgrAnimWaves.Bind(simMaterial); // assign sea floor depth - to slot 1 current frame data LodDataMgrSeaFloorDepth.Bind(simMaterial); // assign flow - to slot 1 current frame data LodDataMgrFlow.Bind(simMaterial); }
protected virtual void BindData(int shapeSlot, IPropertyWrapper properties, Texture applyData, bool blendOut, ref LodTransform.RenderData renderData) { if (applyData) { properties.SetTexture(_paramsLodDataSampler[shapeSlot], applyData); } properties.SetVector(_paramsPosScale[shapeSlot], new Vector3(renderData._posSnapped.x, renderData._posSnapped.z, transform.lossyScale.x)); properties.SetFloat(_paramsLodIdx[shapeSlot], LodTransform.LodIndex); properties.SetVector(_paramsOceanParams[shapeSlot], new Vector4(renderData._texelWidth, renderData._textureRes, 1f, 1f / renderData._textureRes)); }
public void ApplyMaterialParams(int shapeSlot, IPropertyWrapper properties, bool applyWaveHeights, bool blendOut) { if (applyWaveHeights) { properties.SetTexture("_WD_Sampler_" + shapeSlot.ToString(), cam.targetTexture); } if (_rtOceanDepth != null) { properties.SetTexture("_WD_OceanDepth_Sampler_" + shapeSlot.ToString(), _rtOceanDepth); } // need to blend out shape if this is the largest lod, and the ocean might get scaled down later (so the largest lod will disappear) bool needToBlendOutShape = _lodIndex == _lodCount - 1 && OceanRenderer.Instance.ScaleCouldDecrease && blendOut; float shapeWeight = needToBlendOutShape ? OceanRenderer.Instance.ViewerAltitudeLevelAlpha : 1f; properties.SetVector("_WD_Params_" + shapeSlot.ToString(), new Vector3(_renderData._texelWidth, _renderData._textureRes, shapeWeight)); properties.SetVector("_WD_Pos_" + shapeSlot.ToString(), new Vector2(_renderData._posSnapped.x, _renderData._posSnapped.z)); properties.SetFloat("_WD_LodIdx_" + shapeSlot.ToString(), _lodIndex); }
public void ApplyMaterialParams(int shapeSlot, IPropertyWrapper properties, bool applyWaveHeights, bool blendOut) { if (applyWaveHeights) { properties.SetTexture(_paramsDisplacementsSampler[shapeSlot], cam.targetTexture); } if (_rtOceanDepth != null) { properties.SetTexture(_paramsOceanDepthSampler[shapeSlot], _rtOceanDepth); } // need to blend out shape if this is the largest lod, and the ocean might get scaled down later (so the largest lod will disappear) bool needToBlendOutShape = _lodIndex == _lodCount - 1 && OceanRenderer.Instance.ScaleCouldDecrease && blendOut; float shapeWeight = needToBlendOutShape ? OceanRenderer.Instance.ViewerAltitudeLevelAlpha : 1f; properties.SetVector(_paramsOceanParams[shapeSlot], new Vector4(_renderData._texelWidth, _renderData._textureRes, shapeWeight, 1f / _renderData._textureRes)); properties.SetVector(_paramsPosScale[shapeSlot], new Vector3(_renderData._posSnapped.x, _renderData._posSnapped.z, transform.lossyScale.x)); properties.SetFloat(_paramsLodIdx[shapeSlot], _lodIndex); }
public void BindCopySettings(IPropertyWrapper target) { target.SetFloat(sp_HorizDisplace, Settings._horizDisplace); target.SetFloat(sp_DisplaceClamp, Settings._displaceClamp); }
/// <summary> /// Computes Gerstner params for a set of waves, for the given lod idx. Writes shader data to the given property. /// Returns number of wave components rendered in this batch. /// </summary> int UpdateBatch(int lodIdx, int firstComponent, int lastComponentNonInc, IPropertyWrapper property) { int numComponents = lastComponentNonInc - firstComponent; int numInBatch = 0; int dropped = 0; float twopi = 2f * Mathf.PI; float one_over_2pi = 1f / twopi; float minWavelengthThisBatch = OceanRenderer.Instance._lods[lodIdx].MaxWavelength() / 2f; float maxWavelengthCurrentlyRendering = OceanRenderer.Instance._lods[OceanRenderer.Instance.CurrentLodCount - 1].MaxWavelength(); float viewerAltitudeLevelAlpha = OceanRenderer.Instance.ViewerAltitudeLevelAlpha; // register any nonzero components for (int i = 0; i < numComponents; i++) { float wl = _wavelengths[firstComponent + i]; // compute amp - contains logic for shifting wave components between last two lods.. float amp = _amplitudes[firstComponent + i]; bool renderingIntoLastTwoLods = minWavelengthThisBatch * 4.01f > maxWavelengthCurrentlyRendering; // no special weighting needed for any lods except the last 2 if (renderingIntoLastTwoLods) { bool renderingIntoLastLod = minWavelengthThisBatch * 2.01f > maxWavelengthCurrentlyRendering; if (renderingIntoLastLod) { // example: fade out the last lod as viewer drops in altitude, so there is no pop when the lod chain shifts in scale amp *= viewerAltitudeLevelAlpha; } else { // rendering to second-to-last lod. nothing required unless we are dealing with large wavelengths, which we want to transition into // this second-to-last lod when the viewer drops in altitude, ready for a seamless transition when the lod chain shifts in scale amp *= (wl < 2f * minWavelengthThisBatch) ? 1f : 1f - viewerAltitudeLevelAlpha; } } if (amp >= 0.001f) { if (numInBatch < BATCH_SIZE) { int vi = numInBatch / 4; int ei = numInBatch - vi * 4; UpdateBatchScratchData._twoPiOverWavelengthsBatch[vi][ei] = 2f * Mathf.PI / wl; UpdateBatchScratchData._ampsBatch[vi][ei] = amp; float chopScale = _spectrum._chopScales[(firstComponent + i) / _componentsPerOctave]; UpdateBatchScratchData._chopAmpsBatch[vi][ei] = -chopScale * _spectrum._chop * amp; float angle = Mathf.Deg2Rad * (OceanRenderer.Instance._windDirectionAngle + _angleDegs[firstComponent + i]); UpdateBatchScratchData._waveDirXBatch[vi][ei] = Mathf.Cos(angle); UpdateBatchScratchData._waveDirZBatch[vi][ei] = Mathf.Sin(angle); // It used to be this, but I'm pushing all the stuff that doesn't depend on position into the phase. //half4 angle = k * (C * _CrestTime + x) + _Phases[vi]; float gravityScale = _spectrum._gravityScales[(firstComponent + i) / _componentsPerOctave]; float gravity = OceanRenderer.Instance.Gravity * _spectrum._gravityScale; float C = Mathf.Sqrt(wl * gravity * gravityScale * one_over_2pi); float k = twopi / wl; // Repeat every 2pi to keep angle bounded - helps precision on 16bit platforms UpdateBatchScratchData._phasesBatch[vi][ei] = Mathf.Repeat(_phases[firstComponent + i] + k * C * OceanRenderer.Instance.CurrentTime, Mathf.PI * 2f); numInBatch++; } else { dropped++; } } } if (dropped > 0) { Debug.LogWarning(string.Format("Gerstner LOD{0}: Batch limit reached, dropped {1} wavelengths. To support bigger batch sizes, see the comment around the BATCH_SIZE declaration.", lodIdx, dropped), this); numComponents = BATCH_SIZE; } if (numInBatch == 0) { // no waves to draw - abort return(numInBatch); } // if we did not fill the batch, put a terminator signal after the last position if (numInBatch < BATCH_SIZE) { int vi_last = numInBatch / 4; int ei_last = numInBatch - vi_last * 4; for (int vi = vi_last; vi < BATCH_SIZE / 4; vi++) { for (int ei = ei_last; ei < 4; ei++) { UpdateBatchScratchData._twoPiOverWavelengthsBatch[vi][ei] = 1f; // wary of NaNs UpdateBatchScratchData._ampsBatch[vi][ei] = 0f; UpdateBatchScratchData._waveDirXBatch[vi][ei] = 0f; UpdateBatchScratchData._waveDirZBatch[vi][ei] = 0f; UpdateBatchScratchData._phasesBatch[vi][ei] = 0f; UpdateBatchScratchData._chopAmpsBatch[vi][ei] = 0f; } ei_last = 0; } } // apply the data to the shape property property.SetVectorArray(sp_TwoPiOverWavelengths, UpdateBatchScratchData._twoPiOverWavelengthsBatch); property.SetVectorArray(sp_Amplitudes, UpdateBatchScratchData._ampsBatch); property.SetVectorArray(sp_WaveDirX, UpdateBatchScratchData._waveDirXBatch); property.SetVectorArray(sp_WaveDirZ, UpdateBatchScratchData._waveDirZBatch); property.SetVectorArray(sp_Phases, UpdateBatchScratchData._phasesBatch); property.SetVectorArray(sp_ChopAmps, UpdateBatchScratchData._chopAmpsBatch); property.SetFloat(sp_NumInBatch, numInBatch); property.SetFloat(sp_AttenuationInShallows, OceanRenderer.Instance._simSettingsAnimatedWaves.AttenuationInShallows); int numVecs = (numInBatch + 3) / 4; property.SetInt(sp_NumWaveVecs, numVecs); OceanRenderer.Instance._lodDataAnimWaves.BindResultData(lodIdx, 0, property); if (OceanRenderer.Instance._lodDataSeaDepths) { OceanRenderer.Instance._lodDataSeaDepths.BindResultData(lodIdx, 0, property, false); } return(numInBatch); }