UNPKG

vue-cesium

Version:
1 lines 6.38 kB
{"version":3,"file":"calculateSpeed.frag.mjs","sources":["../../../../../../../packages/components/overlays/wind/glsl/calculateSpeed.frag.ts"],"sourcesContent":["/*\n * @Author: zouyaoji@https://github.com/zouyaoji\n * @Date: 2021-10-28 09:25:03\n * @LastEditTime: 2023-03-10 13:37:38\n * @LastEditors: zouyaoji 370681295@qq.com\n * @Description:\n * @FilePath: \\vue-cesium@next\\packages\\components\\overlays\\wind\\glsl\\calculateSpeed.frag.ts\n */\nexport default `\n\nprecision highp float;\n\n// the size of UV textures: width = lon, height = lat*lev\nuniform sampler2D U; // eastward wind\nuniform sampler2D V; // northward wind\nuniform sampler2D currentParticlesPosition; // (lon, lat, lev)\n\nuniform vec3 dimension; // (lon, lat, lev)\nuniform vec3 minimum; // minimum of each dimension\nuniform vec3 maximum; // maximum of each dimension\nuniform vec3 interval; // interval of each dimension\n\n// used to calculate the wind norm\nuniform vec2 uSpeedRange; // (min, max);\nuniform vec2 vSpeedRange;\nuniform float pixelSize;\nuniform float speedFactor;\n\nin vec2 v_textureCoordinates;\n\nvec2 mapPositionToNormalizedIndex2D(vec3 lonLatLev) {\n // ensure the range of longitude and latitude\n lonLatLev.x = mod(lonLatLev.x, 360.0);\n lonLatLev.y = clamp(lonLatLev.y, -90.0, 90.0);\n\n vec3 index3D = vec3(0.0);\n index3D.x = (lonLatLev.x - minimum.x) / interval.x;\n index3D.y = (lonLatLev.y - minimum.y) / interval.y;\n index3D.z = (lonLatLev.z - minimum.z) / interval.z;\n\n // the st texture coordinate corresponding to (col, row) index\n // example\n // data array is [0, 1, 2, 3, 4, 5], width = 3, height = 2\n // the content of texture will be\n // t 1.0\n // | 3 4 5\n // |\n // | 0 1 2\n // 0.0------1.0 s\n\n vec2 index2D = vec2(index3D.x, index3D.z * dimension.y + index3D.y);\n vec2 normalizedIndex2D = vec2(index2D.x / dimension.x, index2D.y / (dimension.y * dimension.z));\n return normalizedIndex2D;\n}\n\nfloat getWindComponent(sampler2D componentTexture, vec3 lonLatLev) {\n vec2 normalizedIndex2D = mapPositionToNormalizedIndex2D(lonLatLev);\n float result = texture(componentTexture, normalizedIndex2D).r;\n return result;\n}\n\nfloat interpolateTexture(sampler2D componentTexture, vec3 lonLatLev) {\n float lon = lonLatLev.x;\n float lat = lonLatLev.y;\n float lev = lonLatLev.z;\n\n float lon0 = floor(lon / interval.x) * interval.x;\n float lon1 = lon0 + 1.0 * interval.x;\n float lat0 = floor(lat / interval.y) * interval.y;\n float lat1 = lat0 + 1.0 * interval.y;\n\n float lon0_lat0 = getWindComponent(componentTexture, vec3(lon0, lat0, lev));\n float lon1_lat0 = getWindComponent(componentTexture, vec3(lon1, lat0, lev));\n float lon0_lat1 = getWindComponent(componentTexture, vec3(lon0, lat1, lev));\n float lon1_lat1 = getWindComponent(componentTexture, vec3(lon1, lat1, lev));\n\n float lon_lat0 = mix(lon0_lat0, lon1_lat0, lon - lon0);\n float lon_lat1 = mix(lon0_lat1, lon1_lat1, lon - lon0);\n float lon_lat = mix(lon_lat0, lon_lat1, lat - lat0);\n return lon_lat;\n}\n\nvec3 linearInterpolation(vec3 lonLatLev) {\n // https://en.wikipedia.org/wiki/Bilinear_interpolation\n float u = interpolateTexture(U, lonLatLev);\n float v = interpolateTexture(V, lonLatLev);\n float w = 0.0;\n return vec3(u, v, w);\n}\n\nvec2 lengthOfLonLat(vec3 lonLatLev) {\n // unit conversion: meters -> longitude latitude degrees\n // see https://en.wikipedia.org/wiki/Geographic_coordinate_system#Length_of_a_degree for detail\n\n // Calculate the length of a degree of latitude and longitude in meters\n float latitude = radians(lonLatLev.y);\n\n float term1 = 111132.92;\n float term2 = 559.82 * cos(2.0 * latitude);\n float term3 = 1.175 * cos(4.0 * latitude);\n float term4 = 0.0023 * cos(6.0 * latitude);\n float latLength = term1 - term2 + term3 - term4;\n\n float term5 = 111412.84 * cos(latitude);\n float term6 = 93.5 * cos(3.0 * latitude);\n float term7 = 0.118 * cos(5.0 * latitude);\n float longLength = term5 - term6 + term7;\n\n return vec2(longLength, latLength);\n}\n\nvec3 convertSpeedUnitToLonLat(vec3 lonLatLev, vec3 speed) {\n vec2 lonLatLength = lengthOfLonLat(lonLatLev);\n float u = speed.x / lonLatLength.x;\n float v = speed.y / lonLatLength.y;\n float w = 0.0;\n vec3 windVectorInLonLatLev = vec3(u, v, w);\n\n return windVectorInLonLatLev;\n}\n\nvec3 calculateSpeedByRungeKutta2(vec3 lonLatLev) {\n // see https://en.wikipedia.org/wiki/Runge%E2%80%93Kutta_methods#Second-order_methods_with_two_stages for detail\n const float h = 0.5;\n float speedScaleFactor = speedFactor * pixelSize;\n\n vec3 y_n = lonLatLev;\n vec3 f_n = linearInterpolation(lonLatLev);\n vec3 midpoint = y_n + 0.5 * h * convertSpeedUnitToLonLat(y_n, f_n) * speedScaleFactor;\n vec3 speed = h * linearInterpolation(midpoint) * speedScaleFactor;\n\n return speed;\n}\n\nfloat calculateWindNorm(vec3 speed) {\n vec3 percent = vec3(0.0);\n percent.x = (speed.x - uSpeedRange.x) / (uSpeedRange.y - uSpeedRange.x);\n percent.y = (speed.y - vSpeedRange.x) / (vSpeedRange.y - vSpeedRange.x);\n float norm = length(percent);\n\n return norm;\n}\n\nvoid main() {\n // texture coordinate must be normalized\n vec3 lonLatLev = texture(currentParticlesPosition, v_textureCoordinates).rgb;\n float speedScaleFactor = speedFactor * pixelSize;\n vec3 speed = calculateSpeedByRungeKutta2(lonLatLev);\n vec3 speedInLonLat = convertSpeedUnitToLonLat(lonLatLev, speed);\n\n vec4 particleSpeed = vec4(speedInLonLat, calculateWindNorm(speed / speedScaleFactor));\n out_FragColor = particleSpeed;\n}\n`\n"],"names":[],"mappings":";AAQA,yBAAe,CAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAAA;;;;"}