(Unity + 2D) Change UI 按钮位置问题
(Unity + 2D) Change UI Button position issue
最近几天一直在为Unity中的一个问题而头疼。
好的,我不会详细介绍我的游戏,但我做了一个非常简单的例子来说明我的问题。
我有一个 2D 场景这些组件:
场景加载时,我点击此脚本执行的按钮:
Vector3 pos = transform.position;
pos.x -= 10;
transform.position = pos;
我也试过这个代码:
transform.position = Camera.main.WorldToScreenPoint(new Vector3(0, 0, 0));
问题是,当我单击按钮时,对象的 x-pos 设置为 -1536,这与预期不符。图为点击按钮后的场景。注意 Rect Transform 值:
所以我做了一些谷歌搜索,发现了 ScreenToWorldPoint、WorldToScreenPoint 等,但这些转换都没有解决我的问题。
我很确定我在这里遗漏了一些东西,这可能就在我面前,但我就是想不通是什么。
我希望有人能指出我正确的方向。
此致。
试试这些东西,因为我不明白你想做什么
尝试使用 transform.deltaposition
转到 canvas 然后再按屏幕尺寸缩放!您可以使用 transform.position = new Vector3(transform.position.x -10,transform.position.y, transform.positon.z)
如果这不起作用
transform.Translate(new Vector3(transform.deltaposition.x - 10,transform.deltaposition.y, transform.deltaposition.z);
我有一个更好的主意。与其改变按钮的位置,不如改变按钮代表的值?
移动按钮
请记住,按钮是游戏对象,每个游戏对象在其变换中都有一个位置向量。因此,如果您的按钮名为 ButtonA,那么您希望在您的代码中获得对该按钮的引用。
GameObject buttonA = GameObject.Find("ButtonA");
//或者您可以从检查器中分配游戏对象
获得按钮的引用后,即可继续移动它。假设我们想将 ButtonA 向左移动 10 个单位。
Vector3 pos = buttonA.transform.position;
pos.X -= 10f;
buttonA.transform.position = pos;
尝试使用 transform.localposition = new Vector3(0,0,0);
,因为您的按钮是多个游戏对象的子对象。您也可以尝试使用 transform.TransformPoint
,它应该 just convert localpos to worldpos.
问题是您的按钮在另一个对象内。你想改变本地位置。 transform.localPosition -= new Vector3(10, 0, 0)
问题是您使用的是 transform.position
而不是 rectTransform.anchoredPosition
。
虽然确实 UI 元素仍然是 GameObjects
并且确实具有可在脚本中访问的正常 Transform
组件,但您在编辑器中看到的是 RectTransform
建立在上面。这是 UI 元素的特殊检查器 window,它使用锚定定位系统,因此您可以指定边缘如何与其父元素对齐。
当您设置 GameObject
的 transform.position
时,您提供了一个以 3D 场景单位(默认为米)指定的世界 space 位置。这不同于相对于 canvas 或父 UI 元素的局部位置,在参考像素中指定(参考像素大小由 canvas“参考分辨率”字段确定)。
您使用 Camera.WorldToScreenPoint
的一个潜在问题是该函数 returns 一个位置 以像素指定 。然而,如前所述,设置 transform.position
是在 场景单位 中指定的(即默认情况下为米),而不是相对于父 UI 元素。不过,检查器知道它是一个 UI 元素,因此它不会向您显示该值,而是向您显示转换为 UI 的本地坐标的世界位置。
换句话说,当您将位置设置为零时,您将获得主相机视图中恰好超过场景零点的任何像素的索引,并将这些像素数转换为米,然后移动元素在那里。编辑器向您显示 参考像素 中相对于对象的父元素 UI 的位置(不一定是屏幕像素,请检查您的 canvas 设置)。要验证,请尝试稍微倾斜相机并注意显示的值会有所不同。
因此您需要再次使用 rectTransform.anchoredPosition
,并且您还需要确保 canvas 分辨率与您的屏幕分辨率相同(或者计算差异).对象的锚定方式对于 rectTransform
值所指的内容也很重要。
正如@Joseph 清楚解释的那样,您必须为 UI 组件更改 RectTransform
,而不是更改 Transform
.
要实现你想要的,这样做:
RectTransform rectTransform = this.GetComponent<RectTransform>();
Vector2 anchoredPos = rectTransform.anchoredPosition;
anchoredPos.x -= 10;
rectTransform.anchoredPosition = anchoredPos;
请记住,这个 10
不是您的 3D 世界 space 单位(如米或厘米)。
最近几天一直在为Unity中的一个问题而头疼。
好的,我不会详细介绍我的游戏,但我做了一个非常简单的例子来说明我的问题。
我有一个 2D 场景这些组件:
场景加载时,我点击此脚本执行的按钮:
Vector3 pos = transform.position;
pos.x -= 10;
transform.position = pos;
我也试过这个代码:
transform.position = Camera.main.WorldToScreenPoint(new Vector3(0, 0, 0));
问题是,当我单击按钮时,对象的 x-pos 设置为 -1536,这与预期不符。图为点击按钮后的场景。注意 Rect Transform 值:
所以我做了一些谷歌搜索,发现了 ScreenToWorldPoint、WorldToScreenPoint 等,但这些转换都没有解决我的问题。
我很确定我在这里遗漏了一些东西,这可能就在我面前,但我就是想不通是什么。
我希望有人能指出我正确的方向。
此致。
试试这些东西,因为我不明白你想做什么
尝试使用 transform.deltaposition 转到 canvas 然后再按屏幕尺寸缩放!您可以使用 transform.position = new Vector3(transform.position.x -10,transform.position.y, transform.positon.z)
如果这不起作用 transform.Translate(new Vector3(transform.deltaposition.x - 10,transform.deltaposition.y, transform.deltaposition.z);
我有一个更好的主意。与其改变按钮的位置,不如改变按钮代表的值?
移动按钮
请记住,按钮是游戏对象,每个游戏对象在其变换中都有一个位置向量。因此,如果您的按钮名为 ButtonA,那么您希望在您的代码中获得对该按钮的引用。
GameObject buttonA = GameObject.Find("ButtonA");
//或者您可以从检查器中分配游戏对象
获得按钮的引用后,即可继续移动它。假设我们想将 ButtonA 向左移动 10 个单位。
Vector3 pos = buttonA.transform.position;
pos.X -= 10f;
buttonA.transform.position = pos;
尝试使用 transform.localposition = new Vector3(0,0,0);
,因为您的按钮是多个游戏对象的子对象。您也可以尝试使用 transform.TransformPoint
,它应该 just convert localpos to worldpos.
问题是您的按钮在另一个对象内。你想改变本地位置。 transform.localPosition -= new Vector3(10, 0, 0)
问题是您使用的是 transform.position
而不是 rectTransform.anchoredPosition
。
虽然确实 UI 元素仍然是 GameObjects
并且确实具有可在脚本中访问的正常 Transform
组件,但您在编辑器中看到的是 RectTransform
建立在上面。这是 UI 元素的特殊检查器 window,它使用锚定定位系统,因此您可以指定边缘如何与其父元素对齐。
当您设置 GameObject
的 transform.position
时,您提供了一个以 3D 场景单位(默认为米)指定的世界 space 位置。这不同于相对于 canvas 或父 UI 元素的局部位置,在参考像素中指定(参考像素大小由 canvas“参考分辨率”字段确定)。
您使用 Camera.WorldToScreenPoint
的一个潜在问题是该函数 returns 一个位置 以像素指定 。然而,如前所述,设置 transform.position
是在 场景单位 中指定的(即默认情况下为米),而不是相对于父 UI 元素。不过,检查器知道它是一个 UI 元素,因此它不会向您显示该值,而是向您显示转换为 UI 的本地坐标的世界位置。
换句话说,当您将位置设置为零时,您将获得主相机视图中恰好超过场景零点的任何像素的索引,并将这些像素数转换为米,然后移动元素在那里。编辑器向您显示 参考像素 中相对于对象的父元素 UI 的位置(不一定是屏幕像素,请检查您的 canvas 设置)。要验证,请尝试稍微倾斜相机并注意显示的值会有所不同。
因此您需要再次使用 rectTransform.anchoredPosition
,并且您还需要确保 canvas 分辨率与您的屏幕分辨率相同(或者计算差异).对象的锚定方式对于 rectTransform
值所指的内容也很重要。
正如@Joseph 清楚解释的那样,您必须为 UI 组件更改 RectTransform
,而不是更改 Transform
.
要实现你想要的,这样做:
RectTransform rectTransform = this.GetComponent<RectTransform>();
Vector2 anchoredPos = rectTransform.anchoredPosition;
anchoredPos.x -= 10;
rectTransform.anchoredPosition = anchoredPos;
请记住,这个 10
不是您的 3D 世界 space 单位(如米或厘米)。