【问题标题】:extracting the 2D screen position of a 3D point with three.js [duplicate]用three.js提取3D点的2D屏幕位置[重复]
【发布时间】:2016-03-16 19:46:07
【问题描述】:

我正在尝试弄清楚如何获取 3D 点的 2D 屏幕坐标。

我正在使用 three.js 来生成一些雪花,它们会从屏幕上缓缓落下。我最初将脚本编写为 2d 画布动画并添加了鼠标交互,因此您可以通过鼠标移动来吹雪。它工作得很好,但是当切换到 webgl 时,雪花现在被表示为 3D 点,并且获得鼠标到每个粒子的距离会使远离屏幕中心的粒子由于透视而以不希望的方式表现。

http://www.simplemathguild.com/snowtest.html

【问题讨论】:

    标签: javascript 3d three.js


    【解决方案1】:

    您需要做的是通过 viewProjection 矩阵转换您的 worldPos vec3,然后执行透视除法。这会将其带到 NDC 空间,其中 (-1,-1,x) = 屏幕左下角, (+1,+1,x) = 屏幕右上角。通过您的屏幕宽度和屏幕高度进行调整,您将获得屏幕空间中的坐标。

    在代码中是这样的:

    worldToScreen: function(viewProjectionMatrix, screenWidth, screenHeight){
        var m = viewProjectionMatrix;
        var w = m[3] * this[0] + m[7] * this[1] + m[11] * this[2] + m[15]; // required for perspective divide
        this.transformByMat4(viewProjectionMatrix);
        if (w!==0){ // do perspective divide and NDC -> screen conversion
            var invW = 1.0/w;
            this[0] = (this[0]*invW + 1) / 2 * screenWidth;
            this[1] = (1-this[1]*invW) / 2 * screenHeight; // screen space Y goes from top to bottom
            this[2] *= invW;
        } 
        return this;
    }
    

    顺便说一句,这基本上就是 GPU 在后台渲染内容的工作,减去 NDC 到屏幕坐标的转换。

    查看Vector3的三个方法,很可能是在那里实现的,或者直接使用上面的sn-p代码。

    【讨论】:

    • 我假设你的意思是“这个”作为 Vector3。据我所知 Three.js 没有 transformByMat4 功能。你能澄清一下吗?
    • 如果不清楚,sn-p 是从我自己的库中提取的,而不是从 Three.js 中提取的。当我写答案时,这个问题被标记为 webgl。我相信transformByMat4的对应方法是applyMatrix in Three,this[0], [1], [2]是Three Vector3的.x,.y,.z属性。
    猜你喜欢
    • 2012-07-17
    • 1970-01-01
    • 1970-01-01
    • 2013-11-22
    • 2015-02-09
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-06-08
    相关资源
    最近更新 更多