当前位置:网站首页>Unity 颜色板|调色板|无级变色功能
Unity 颜色板|调色板|无级变色功能
2022-07-06 16:05:00 【Fuuyg】
效果
Unity 通过UGUI实现无级变色的调色板功能,非常的简单好用。
项目git地址
https://github.com/zrzhang76/UnityColorBoard
代码(写这个完全是因为CSDN嫌我字数少,建议直接看项目)
颜色板部分
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.EventSystems;
using UnityEngine.UI;
namespace CSharp.UI.ColorBoard
{
public class ColorBoard : MonoBehaviour, IPointerClickHandler, IDragHandler
{
//显示颜色的Texture
Texture2D tex2d;
//RawImage组件
RawImage ri;
//像素宽度高度256(默认值)
int TexPixelLength = 256;
int TexPixelHeight = 256;
//公共组件
public Slider sliderCRGB;
public ColorHue colorHue;
//颜色数组
UnityEngine.Color[,] arrayColor;
//自身的Transform
RectTransform rt;
//颜色聚焦点的圆圈
public RectTransform circleRect;
public delegate void ColorChangeDelegate(Color color);
public event ColorChangeDelegate OnColorChanged;
private void Awake()
{
ri = GetComponent<RawImage>();
rt = GetComponent<RectTransform>();
circleRect = transform.Find("img_cursor").GetComponent<RectTransform>();
TexPixelLength = (int)rt.sizeDelta.x;
TexPixelHeight = (int)rt.sizeDelta.y;
//初始化颜色数组
arrayColor = new UnityEngine.Color[TexPixelLength, TexPixelHeight];
//创建一个固定长宽的Texture
tex2d = new Texture2D(TexPixelLength, TexPixelHeight, TextureFormat.RGB24, true);
//组件赋值图片
ri.texture = tex2d;
ri.texture.wrapMode = TextureWrapMode.Clamp;
//初始化设置板子的颜色为红色
SetColorPanel(UnityEngine.Color.red);
sliderCRGB.onValueChanged.AddListener(OnCRGBValueChanged);
}
//颜色放生变化的监听
void OnCRGBValueChanged(float value)
{
UnityEngine.Color endColor=colorHue.GetColorBySliderValue(value);
SetColorPanel(endColor);
var color = GetColorByPosition(circleRect.anchoredPosition);
OnColorChanged?.Invoke(color);
}
//设置板子的颜色
public void SetColorPanel(UnityEngine.Color endColor)
{
UnityEngine.Color[] CalcArray = CalcArrayColor(endColor);
//给颜色板子填入颜色,并且应用
tex2d.SetPixels(CalcArray);
tex2d.Apply();
}
//通过一个最终颜色值,计算板子上所有像素点应该的颜色,并返回一个数组
UnityEngine.Color[] CalcArrayColor(UnityEngine.Color endColor)
{
//计算最终值和白色的差值在水平方向的平均值,用于计算水平每个像素点的色值
UnityEngine.Color value = (endColor - UnityEngine.Color.white) / (TexPixelLength - 1);
for (int i = 0; i < TexPixelLength; i++)
{
arrayColor[i, TexPixelHeight - 1] = UnityEngine.Color.white + value * i;
}
// 同理,垂直方向
for (int i = 0; i < TexPixelLength; i++)
{
value = (arrayColor[i, TexPixelHeight - 1] - UnityEngine.Color.black) / (TexPixelHeight - 1);
for (int j = 0; j < TexPixelHeight; j++)
{
arrayColor[i, j] = UnityEngine.Color.black + value * j;
}
}
//返回一个数组,保存了所有颜色色值
List<UnityEngine.Color> listColor = new List<UnityEngine.Color>();
for (int i = 0; i < TexPixelHeight; i++)
{
for (int j = 0; j < TexPixelLength; j++)
{
listColor.Add(arrayColor[j, i]);
}
}
return listColor.ToArray();
}
/// <summary>
/// 获取颜色by坐标,坐标是Texture上面的二维坐标
/// </summary>
/// <param name="pos"></param>
/// <returns></returns>
public UnityEngine.Color GetColorByPosition(Vector2 pos)
{
Texture2D tempTex2d = (Texture2D)ri.texture;
UnityEngine.Color getColor = tempTex2d.GetPixel((int)pos.x, (int)pos.y);
return getColor;
}
public Vector2 GetClampPosition(Vector2 touchPos)
{
Vector2 vector2 = new Vector2(touchPos.x, touchPos.y);
vector2.x = Mathf.Clamp(vector2.x, 0.001f, rt.sizeDelta.x);
vector2.y = Mathf.Clamp(vector2.y, 0.001f, rt.sizeDelta.y);
return vector2;
}
//点击事件
public void OnPointerClick(PointerEventData eventData)
{
Vector3 wordPos;
//将UGUI的坐标转为世界坐标
if (RectTransformUtility.ScreenPointToWorldPointInRectangle(rt, eventData.position, eventData.pressEventCamera, out wordPos))
circleRect.position = wordPos;
circleRect.anchoredPosition = GetClampPosition(circleRect.anchoredPosition);
var color = GetColorByPosition(circleRect.anchoredPosition);
OnColorChanged?.Invoke(color);
}
//拖拽事件
public void OnDrag(PointerEventData eventData)
{
Vector3 wordPos;
//将UGUI的坐标转为世界坐标
if (RectTransformUtility.ScreenPointToWorldPointInRectangle(rt, eventData.position, eventData.pressEventCamera, out wordPos))
circleRect.position = wordPos;
circleRect.anchoredPosition = GetClampPosition(circleRect.anchoredPosition);
var color = GetColorByPosition(circleRect.anchoredPosition);
OnColorChanged?.Invoke(color);
}
}
}
色相条部分
using System.Collections.Generic;
using UnityEngine;
using UnityEngine.UI;
public class ColorHue : MonoBehaviour
{
//绘制颜色的Texture
Texture2D tex2d;
//图片展示组件
RawImage ri;
//长宽
int TexPixelWdith = 952;
int TexPixelHeight = 16;
//颜色的数组
UnityEngine.Color[,] arrayColor;
private void Awake()
{
ri = gameObject.GetComponent<RawImage>();
//初始化颜色和Texture
arrayColor = new UnityEngine.Color[TexPixelWdith, TexPixelHeight];
tex2d = new Texture2D(TexPixelWdith, TexPixelHeight, TextureFormat.RGB24,true);
//计算颜色
UnityEngine.Color[] calcArray = CalcArrayColor();
//展示出来
tex2d.SetPixels(calcArray);
tex2d.Apply();
ri.texture = tex2d;
ri.texture.wrapMode = TextureWrapMode.Clamp;
}
//计算色相条上面需要展示的颜色数组
UnityEngine.Color[] CalcArrayColor()
{
//计算水平像素的等分增量
int addValue = (TexPixelWdith - 1) / 3;
//
for (int i = 0; i < TexPixelHeight; i++)
{
arrayColor[0, i] = UnityEngine.Color.red;
arrayColor[addValue, i] = UnityEngine.Color.green;
arrayColor[addValue+addValue, i] = UnityEngine.Color.blue;
arrayColor[TexPixelHeight - 1, i] = UnityEngine.Color.red;
}
UnityEngine.Color value = (UnityEngine.Color.green - UnityEngine.Color.red)/addValue;
for (int i = 0; i < TexPixelHeight; i++)
{
for (int j = 0; j < addValue; j++)
{
arrayColor[j, i] = UnityEngine.Color.red + value * j;
}
}
value = (UnityEngine.Color.blue - UnityEngine.Color.green)/ addValue;
for (int i = 0; i < TexPixelHeight; i++)
{
for (int j = addValue; j < addValue*2; j++)
{
arrayColor[j, i] = UnityEngine.Color.green + value * (j-addValue);
}
}
value = (UnityEngine.Color.red - UnityEngine.Color.blue) / ((TexPixelWdith - 1)-addValue-addValue);
for (int i = 0; i < TexPixelHeight; i++)
{
for (int j = addValue*2; j < TexPixelWdith - 1; j++)
{
arrayColor[j, i] = UnityEngine.Color.blue + value * (j- addValue * 2);
}
}
List<UnityEngine.Color> listColor = new List<UnityEngine.Color>();
for (int i = 0; i < TexPixelHeight; i++)
{
for (int j = 0; j < TexPixelWdith; j++)
{
listColor.Add(arrayColor[j, i]);
}
}
return listColor.ToArray();
}
/// <summary>
/// 获取颜色 根据高度
/// </summary>
/// <param name="value"></param>
/// <returns></returns>
public Color GetColorBySliderValue(float value)
{
float clampValue = Mathf.Clamp(value, 0.001f, 0.999f);
Color getColor=tex2d.GetPixel((int)((TexPixelWdith-1)*clampValue),0);
return getColor;
}
}
制作不易,给个赞呗~~
边栏推荐
- Coscon'22 community convening order is coming! Open the world, invite all communities to embrace open source and open a new world~
- Spark Tuning (II): UDF reduces joins and judgments
- How does crmeb mall system help marketing?
- Should the jar package of MySQL CDC be placed in different places in the Flink running mode?
- 【212】php发送post请求有哪三种方法
- How can Oracle CDC deserialize with jsondebeziumdeserializationschema
- With the help of this treasure artifact, I became the whole stack
- (LeetCode)两数之和
- AI金榜题名时,MLPerf榜单的份量究竟有多重?
- How much does the mlperf list weigh when AI is named?
猜你喜欢

Cloud native (32) | kubernetes introduction to platform storage system

借助这个宝藏神器,我成为全栈了

PDF批量拆分、合并、书签提取、书签写入小工具

How to implement Lua entry of API gateway

The problem of ASP reading Oracle Database

Ajout, suppression et modification d'un tableau json par JS

Today, I met a senior test developer from Tencent and saw the ceiling of the foundation

Gpt-3 is a peer review online when it has been submitted for its own research

leetcode:236. 二叉树的最近公共祖先

The worse the AI performance, the higher the bonus? Doctor of New York University offered a reward for the task of making the big model perform poorly
随机推荐
[system analyst's road] Chapter 7 double disk system design (service-oriented development method)
这个『根据 op 值判断操作类型来自己组装 sql』是指在哪里实现?是指单纯用 Flink Tabl
Microsoft win11 is still "unsatisfactory". Multi user feedback will cause frequent MSI crashes
Entropy information entropy cross entropy
Daily question brushing record (XV)
Eureka Client启动后就关闭 Unregistering application xxx with eureka with status DOWN
One minute to learn how to install the system, win7 XP, win10 and win11 become very simple
Gradle知识概括
Modules that can be used by both the electron main process and the rendering process
Master binary tree in one article
Nftscan Developer Platform launches Pro API commercial services
leetcode:236. 二叉树的最近公共祖先
Restoration analysis of protobuf protocol of bullet screen in station B
为了交通安全,可以做些什么?
Graphite document: four countermeasures to solve the problem of enterprise document information security
leetcode:236. The nearest common ancestor of binary tree
每人每年最高500万经费!选人不选项目,专注基础科研,科学家主导腾讯出资的「新基石」启动申报...
Where does this "judge the operation type according to the op value and assemble SQL by yourself" mean? It means simply using Flink tab
JS addition, deletion, modification and query of JSON array
PDF批量拆分、合并、书签提取、书签写入小工具