From ee2ed4c4695e3e051925d3c213732165fcbc4e05 Mon Sep 17 00:00:00 2001 From: Anuken Date: Fri, 15 Jul 2022 10:35:51 -0400 Subject: [PATCH] Better color picker --- core/assets-raw/sprites/ui/alpha-bg-line.png | Bin 0 -> 1331 bytes core/assets-raw/sprites/ui/slider-back.9.png | Bin 197 -> 2418 bytes .../src/mindustry/ui/dialogs/ColorPicker.java | 156 ++++++++++++++++-- gradle.properties | 2 +- 4 files changed, 141 insertions(+), 17 deletions(-) create mode 100644 core/assets-raw/sprites/ui/alpha-bg-line.png diff --git a/core/assets-raw/sprites/ui/alpha-bg-line.png b/core/assets-raw/sprites/ui/alpha-bg-line.png new file mode 100644 index 0000000000000000000000000000000000000000..02becdcf15d341425465a6016adb307c6dd87c61 GIT binary patch literal 1331 zcmeAS@N?(olHy`uVBq!ia0y~yU}#`qU=ZM7V_;yo7g659z`%5`DkP#LD6w3jpeR2r zGbdG{q_QAYA+;hije()!*4?RzlkO^T9N%BvCFkhC(w}T{?hBi3-G8b0Z+q|N-Jbh$ z`LRwZ6^9=SIiL5xSFSnidNJ7}Yo7Nx!EmjW1xJrOE}eQc*k^V8^<>WT`kx&7S=&4e zPJPWNeI0({>taQ#xTgodbNx1R+5WKf!Z&6`2-`5*$x58o; zzOlZW7<;&ePoK$o+O9(r4dy!ug})DHG0LCTb@9SvjV}u}s|Zcg$WQh-ar*gP&Yts} zRi2-c#qOogxA(NWzE<&l(aiEbgP%{CURv+G^Y7=)jduh;zCKj<_iOPtTet6q=U%_g zI&~uBp6J#|zWl}kHWP{>*Qc5sUOVG<7VFvMUfvVcIUgOeLpmmY6x0Y@?$vzG)GUj` z@Z-t0i90vy%b_lI5|EN^U&ms9>zMp}F7BmVO}j3=`Efw1|MZcC zU&5j{S#W<5dAzk%BjP^W1f?HgEY3_!hROT^%QDWmwb)oOgu0xY^n-yh=xLvVWoHWC zv2&Nr?-@qzS~I7ztI&+G#p~F;B7s#6QztE|)3MB2u_`0z>Y8P8TQbg03cfaH^V7-` zp~BwFrky>rHlp<7lUFy--tE4A$hCki>*Ud{=|Ndf10Jq86xLeT`s9IgU&)J!{MLUo z+;cVNPn)&v&YDW?wPo)v75aR+v$k4)?>rH|IU?y+U(YO`TQ_Yp-<4YvCbsq2C1a5;hTZuXN!v`d5%~JcHCBJXnJ;1$7<=3$#+u3xRZl5 zls)F=I4$?&;kfL%ra7-H|H;3u=z#y)d4JT45*Pgzf5LR3_Q^NytlEFiZz+|%Jv8&O z#*Ny&A>X7v*moB<1@3u!Q`hpz-Y3R$|6daL)c(KX2WPs)TNStN(jEo|#^y|C=KxP< zXIM&SV5pc=JJHtTu!GFe_~4~VSNX~W3Qq*g)#>Q6$P(=eP`tvm)@nw~FIHcvNh0Fz z2e&?Wa6IYi!K0Dk?BR|Ae;5i&ih@ce3jLoh5_P1a;7)(}ce(QS3=0DjXI(Yr%h;8> zY%-_e>}XNv^&E;#bu5AtW~QF;4C31N__ZA4zI#V2r~Th)?>>Llb_oH2&h(jyw~k03 zxjcK@!OHm-r@S_K)%e+@U1IH&-?^^h&#|2^HXSftoTg^$FQY2fExV?~KzpXtN0CCG zt0kwzH_5G@v)v+ls#Nyf$@>lFTo0eN)2~>YpK_^1ll#es5x}dPT?t}f0yK6&d%=s|s5a)v5M+@!T8ZPKvSYv(e`^Lv6{tXX| z3zlyGdzH=LvuD-bwMY9JPM8%G-n}-(_CXQ5M2%5OaM@A?--Q7T_s+kVU3B1p?uFgY zzFxa^{3Y{*h3kUM4;)l9h+6Wdbbk5wl5gMM&kU=#zg$+79xiz#lYxPOEy>&6g+Yr! zg~3$%=(3{>3=EtF9+AZi4BWyX%*Zfnjsyb(1AB?5uPggAc78r)fm?kat}rk#xO=)d zhGg7(dubytg8~op!2@11&74!!B$}8w-&LJH+rKKRaKUc>XA@^W{D1F1&ptH9hdn6PaK@>%fP_E;OXk;vd$@?2>>=zZW90i literal 0 HcmV?d00001 diff --git a/core/assets-raw/sprites/ui/slider-back.9.png b/core/assets-raw/sprites/ui/slider-back.9.png index 71762a216384c9f8d41ed1f374acc675ea8138a7..013c6cc7bdc27d80826e13861cb50026f3219751 100644 GIT binary patch delta 2408 zcmX@g_(^Djay{F(s*s41pu}>8f};Gi%$!t(lFEWqh1817GzNx>TWcetCmq({`EywEEiJrge9(w;xX1-2XJ?c3OgnrOn-^%b%^SbK6;Cx+AIn#-|9s!p#MDtTt`$ zyMEmF$&r8$o8&z9?Yn6F`|4jGyXR}$ zsvi{vPyFy{@xfEUJ9j_)Y`bB1edUpUHr{3R(&xU(Enwn}ryD&J`fPbs|4-F%bp_VvxTxWsMC!)#`1?+z84 zTa+Zgk@;uOn}pV+v#uJEJ0}-wJe#dw_HbEicrHuP<`t*J=H68O-`#yr@_dYm+gy?Q zo1ST<-P(65-Nf$9ICa)K%Td7E>~4x+&0e#gXJZr227Fy%mf0tfVD|KqtKe_Z=)9M2 z0{lPhSu#O2H=2C`#|@_RHO)+F3hX%>+-6>l`XHeg(DwX|jkrdF>yCq--_EhBJv|{T zoqJ{7E*+T)vE;lafk#Y5+UMppMcm_l%8Sf!N!v%JQaD= zQ?s1U`W;nR_ogH{XS)}=G}M=_X+QI=h?5g_RK2$tg3Xnn4e#- z^S4s==Tj=4SY-7lPFZ7n_K#uRlqF}g!{vAJY*aSQx79gSKg*hF`L$`;tL-8+Mc0}J zY|og}Q?_xfxVc-QY+cFPy}K{6Z_0dD^R8KW&Z}pxyhbm)lK`dA!6QSkqwp!(CnMssS;l!gMQd_&S4(0I2iErK7cBkIxO;Cp4 z>Ko^-1U5|$Q%Wn_Kc&T5wENSGwWje4O0GxdtzIKAahr#k@2VvEMc#EfznWHZ&yH%Z z4LZrWY~z+!dW-m9m$uwnK7&vERPym@T3#2P-pFw)f4gt%tYFPsYr`^X?!S|kkv)97 zeQ|Qd?}8GZeEGh<%RlAdM7>`YH`B#VkS`$kHqbzR8L5j?vg|Hag9PS)8R z``Dh``8i_~>k?*%)6q|)4>l^gGq}#TRyY-7v9Ue#Z!2rA#+sigIhv-+4@L*&a(+Kl zHNWT*_d&yLJCB(DGX4MU#EssR9slR}e}9>h_bz_kmzaWol1cqdC+7XrS(9N{Kii#8 zJb&KFJC7&zP1<=}RaUjQ-`mRT*}cgqT)F8bQ_k4x{Z~-Pmz7lpDVhCr{f;G@BmZ@I zTg`sDpW{Swqi6c&Kcdr1%udHgzRa1n|IsIX=1(!x_CK0r7h5-P=Mw+v^V9WSUVi$V zf7;^taBlt6=Qq9P>)D@=xwQQBdB#ol+&;ga?mMx~^vr@QLXRaPoDOlO%ef`3X*>Jk zQMdo%ROy0633+R0MHL#q>GkJRx6b?AUlmzjTH(&qR&+LYm%gIcYGpQHUV9mVr_{2K9fGU}n&zYBo-U8}+6d_2(h zY6IWgDKoo0OHA4~mhO+Jf1UcTxkJ+7%2IXfTv5IHH#Xa9^1e6Uy|)V~!909>_+p{e zePm*1MkTNN^F>chW#)EIyI$}`E?@8S&A87x_y74EIVJKTC^Fz~`OY~C8z=SMQL)s7#LeJot*ZRXRnnDxqwr|LLaRs-(ZVZQA`6{Xh(?tf?EJz#%S1&} zudgZl;KBZ*tD3tvuj5*Hm7+m ztKCzWcW(>tx!*?w!={8jDt;6=SzBaV#`8Ocj~BQIX* zSl+RC)w1Ay6Fx>f-E%ZjJ3R99yg#i6=j_{brgWBby+?we_XGteM^V)&iOO!P{kmF3 z-X6F9!5+KcMXxnR)u2dc0Tb`0*X;kB@86C3d6H9KQ-Xb0yv*}t363{Ry|W(I$Xok8 zX8B;x9A0%gekHT<{3X|;qP}o&CosKfJs5?cP7z%WvMZdwUj5?@(W_&cMLHmgMd3 z!l1>V!eAr>7WMMFrTh=dI%XHD@F=ajJod8^`^!Czan{9v=OB hOCQJE8~RoZ{LKpQi#k3xF)%PNc)I$ztaD0e0st8tjNSkM delta 170 zcmew)bd+&|ayOEZ?Ln2z=USBA9#DK@;V(7Cd;X7tQA-4od zlG7|}%1$&D^L%p@{`-;RhNIBpRlAlSwpWroTvNla;QK$}Ni(%~FZ;>xC?ZOsV1^dM zoyUG#udSOZIJ1)P^WJ2m_LVZrie{Wj)PgZqDg69Wt6X*Up8xArRl6Tv+-AOQt$t9k X!uzwk`Ia* cons = c -> {}; Color current = new Color(); + float h, s, v, a; + TextField hexField; + Slider hSlider, sSlider, vSlider, aSlider; public ColorPicker(){ super("@pickcolor"); @@ -23,6 +31,17 @@ public class ColorPicker extends BaseDialog{ this.cons = consumer; show(); + if(hueTex == null){ + hueTex = Pixmaps.hueTexture(128, 1); + hueTex.setFilter(TextureFilter.linear); + } + + float[] values = color.toHsv(new float[3]); + h = values[0]; + s = values[1]; + v = values[2]; + a = color.a; + cont.clear(); cont.pane(t -> { t.table(Tex.pane, i -> { @@ -32,25 +51,113 @@ public class ColorPicker extends BaseDialog{ }}).size(200f); }).colspan(2).padBottom(5); - float w = 150f; - t.row(); - t.defaults().padBottom(4); - t.add("R").color(Pal.remove); - t.slider(0f, 1f, 0.01f, current.r, current::r).width(w); - t.row(); - t.add("G").color(Color.lime); - t.slider(0f, 1f, 0.01f, current.g, current::g).width(w); - t.row(); - t.add("B").color(Color.royal); - t.slider(0f, 1f, 0.01f, current.b, current::b).width(w); - t.row(); + t.defaults().padBottom(6).width(400f).height(44f); + + t.stack(new Image(new TextureRegion(hueTex)), hSlider = new Slider(0f, 360f, 0.3f, false){{ + setValue(h); + moved(value -> { + h = value; + updateColor(); + }); + }}).row(); + + t.stack(new Element(){ + @Override + public void draw(){ + float first = Tmp.c1.set(current).saturation(0f).a(parentAlpha).toFloatBits(); + float second = Tmp.c1.set(current).saturation(1f).a(parentAlpha).toFloatBits(); + + Fill.quad( + x, y, first, + x + width, y, second, + x + width, y + height, second, + x, y + height, first + ); + } + }, sSlider = new Slider(0f, 1f, 0.001f, false){{ + setValue(s); + moved(value -> { + s = value; + updateColor(); + }); + }}).row(); + + t.stack(new Element(){ + @Override + public void draw(){ + float first = Tmp.c1.set(current).value(0f).a(parentAlpha).toFloatBits(); + float second = Tmp.c1.fromHsv(h, s, 1f).a(parentAlpha).toFloatBits(); + + Fill.quad( + x, y, first, + x + width, y, second, + x + width, y + height, second, + x, y + height, first + ); + } + }, vSlider = new Slider(0f, 1f, 0.001f, false){{ + setValue(v); + + moved(value -> { + v = value; + updateColor(); + }); + }}).row(); + if(alpha){ - t.add("A"); - t.slider(0f, 1f, 0.01f, current.a, current::a).width(w); - t.row(); + t.stack(new Image(Tex.alphaBgLine), new Element(){ + @Override + public void draw(){ + float first = Tmp.c1.set(current).a(0f).toFloatBits(); + float second = Tmp.c1.set(current).a(parentAlpha).toFloatBits(); + + Fill.quad( + x, y, first, + x + width, y, second, + x + width, y + height, second, + x, y + height, first + ); + } + }, aSlider = new Slider(0f, 1f, 0.001f, false){{ + setValue(a); + + moved(value -> { + a = value; + updateColor(); + }); + }}).row(); } + + hexField = t.field(current.toString(), value -> { + try{ + current.set(Color.valueOf(value).a(a)); + current.toHsv(values); + h = values[0]; + s = values[1]; + v = values[2]; + a = current.a; + + hSlider.setValue(h); + sSlider.setValue(s); + vSlider.setValue(v); + if(aSlider != null){ + aSlider.setValue(a); + } + + updateColor(false); + }catch(Exception ignored){ + } + }).size(130f, 40f).valid(text -> { + //garbage performance but who cares this runs only every key type anyway + try{ + Color.valueOf(text); + return true; + }catch(Exception e){ + return false; + } + }).get(); }); buttons.clear(); @@ -60,4 +167,21 @@ public class ColorPicker extends BaseDialog{ hide(); }); } + + void updateColor(){ + updateColor(true); + } + + void updateColor(boolean updateField){ + current.fromHsv(h, s, v); + current.a = a; + + if(hexField != null && updateField){ + String val = current.toString(); + if(current.a >= 0.9999f){ + val = val.substring(0, 6); + } + hexField.setText(val); + } + } } diff --git a/gradle.properties b/gradle.properties index 77ed3793fc..b3da1e740d 100644 --- a/gradle.properties +++ b/gradle.properties @@ -25,4 +25,4 @@ org.gradle.caching=true #used for slow jitpack builds; TODO see if this actually works org.gradle.internal.http.socketTimeout=100000 org.gradle.internal.http.connectionTimeout=100000 -archash=b1b88883e2 +archash=47925a7b91