- Home /
Divided Huge Texture Shader
I have a huge sphere (you can think a planet) and 21600x10800 texture for it. (That size req because there is a zoom option) Sure i will divide that texture. But how to use? I need a shader for it.
That scene havent much object but i dont want waste performance too. I need a basic diffuse with a little self lightning. I mean if there is no light, it req visible a little instead of black. with light it will be more lighter. (No lightning texture only not black without light)
How to write that shader?
Answer by ScroodgeM · Jul 31, 2012 at 09:25 PM
unity supports maximum of 4096x4096 textures, so you should split it to 18 textures.
and the best way even in performance reason is to make a 3d model of sphere mapped to 18 different materials. then use just a regular shader.
P.S. "No lightning texture only not black without light" is also known as Ambient Light
P.P.S. i could help you to write a shader with 18 textures, but i'm not sure this will be better then 18 materials with simple shaders...
remove grid by changing texture wrap mode from 'repeat' to 'clamp'
shader limits can be avoided, for example ignoring tiling/offset of textures is way to decrease calculations
post your shader - i'll look
never use textures with non-power-of-two size in 3d graphics. use 4096x4096 and it will takes no more then 64$$anonymous$$B per texture, 48$$anonymous$$B without alpha channel
sorry for shader, but i didn't found a way to make more then 16 textures. before that all limits was avoided in my practice 8). this one looks like compiler limit. hope unity4 will support texture arrays.
about memory i said already, 4096x4096 RGBA 32bit texture will take 64$$anonymous$$B (without mipmaps).
and the last. to avoid sharp edges on textures seams, first switch them to clamp ins$$anonymous$$d of repeat, second - make a 1-pixel border same on seamed textures (so top pixel row on bottom texture should be same as bottom pixel row on top texture and so on)
is this error always occurs on 11s loading? try to load different images without any associating with material?
hmm... don't know what can it be... try to add Debug.Log and check log file for point where it crashes. try to first load all 18 images and then assign it....
and open a new question here in UA. most of people who can know a solution will never read these coments 8)
Answer by SuperProgrammer · Aug 01, 2012 at 11:42 AM
If i change it to clamp, only 1 texture normal others getting one color. So i cant choose clamp i think it req divide sphere to objects. Currently one object and 18 material. If i divide it to 18 sphere part. It will get smoothing problem.
Shader:
Shader "Custom/Planet" { Properties { _MainTex11 ("Texture 1 1", 2D) = "white" {} _MainTex12 ("Texture 1 2", 2D) = "white" {} _MainTex13 ("Texture 1 3", 2D) = "white" {} _MainTex21 ("Texture 2 1", 2D) = "white" {} _MainTex22 ("Texture 2 2", 2D) = "white" {} _MainTex23 ("Texture 2 3", 2D) = "white" {} _MainTex31 ("Texture 3 1", 2D) = "white" {} _MainTex32 ("Texture 3 2", 2D) = "white" {} _MainTex33 ("Texture 3 3", 2D) = "white" {} _MainTex41 ("Texture 4 1", 2D) = "white" {} _MainTex42 ("Texture 4 2", 2D) = "white" {} _MainTex43 ("Texture 4 3", 2D) = "white" {} _MainTex51 ("Texture 5 1", 2D) = "white" {} _MainTex52 ("Texture 5 2", 2D) = "white" {} _MainTex53 ("Texture 5 3", 2D) = "white" {} _MainTex61 ("Texture 6 1", 2D) = "white" {} _MainTex62 ("Texture 6 2", 2D) = "white" {} _MainTex63 ("Texture 6 3", 2D) = "white" {} } SubShader { Tags { "RenderType"="Opaque" } LOD 200
CGPROGRAM
#pragma surface surf Lambert
sampler2D _MainTex11;
sampler2D _MainTex12;
sampler2D _MainTex13;
sampler2D _MainTex21;
sampler2D _MainTex22;
sampler2D _MainTex23;
sampler2D _MainTex31;
sampler2D _MainTex32;
sampler2D _MainTex33;
sampler2D _MainTex41;
sampler2D _MainTex42;
sampler2D _MainTex43;
sampler2D _MainTex51;
sampler2D _MainTex52;
sampler2D _MainTex53;
sampler2D _MainTex61;
sampler2D _MainTex62;
sampler2D _MainTex63;
struct Input {
float2 uv_MainTex11;
};
void surf (Input IN, inout SurfaceOutput o) {
if (IN.uv_MainTex11.x >= 5.0/6.0) {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex61, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex62, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex63, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
else if (IN.uv_MainTex11.x >= 4.0/6.0) {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex51, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex52, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex53, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
else if (IN.uv_MainTex11.x >= 3.0/6.0) {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex41, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex42, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex43, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
else if (IN.uv_MainTex11.x >= 2.0/6.0) {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex31, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex32, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex33, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
else if (IN.uv_MainTex11.x >= 1.0/6.0) {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex21, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex22, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex23, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
else {
if (IN.uv_MainTex11.y >= 2.0/3.0) {
o.Albedo = tex2D (_MainTex11, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else if (IN.uv_MainTex11.y >= 1.0/3.0) {
o.Albedo = tex2D (_MainTex12, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
else {
o.Albedo = tex2D (_MainTex13, IN.uv_MainTex11 * float2(6.0, 3.0)).rgb;
}
}
}
ENDCG
}
FallBack "Diffuse"
}
Inspired by this code snippet, I created a surface shader to put four 4096x2048 textures on a sphere. It does only work with texture mode repeat, and along the borders of the textures occurs a dividing line. Any way to get around this? Or is multi-sub material the only way?
Answer by SuperProgrammer · Aug 02, 2012 at 03:25 PM
Final Answer: Using multi-sub material better then shader. Always use power of 2 sized textures for less size. (Bigger size for less size ;)
As i found "Do not download big images dynamically" because no runtime compression. Sure there is a function "Texture2D.Compress" but not enough.
I will load DDS file instead of jpg (DXT1 compressed texture). I will take care of its size with some other methods.
Btw again ScroodgeM thanks for help.
PS did you check you video memory usage? textures in VRA$$anonymous$$ are always stored uncompressed, and texture 4$$anonymous$$x4$$anonymous$$x32bit with mipmaps will take about 85 $$anonymous$$B of VRA$$anonymous$$. 18 textures 85 $$anonymous$$B each means 1.5GB of VRA$$anonymous$$... r u sure you and all users have such size?
Your answer
Follow this Question
Related Questions
Global Rendering with a shader that uses a texture 1 Answer
How can i get mixed texture from one shader and set it for another object with another shader? 0 Answers
Open project from MAC at PC 2 Answers
Change between 2 textures based on a variable 1 Answer
Rendering a G-Buffer for a cubemap 0 Answers