Approximate AO: Diffuse Bounce Hack
[blender.git] / release / scripts / ui / properties_world.py
1 # ##### BEGIN GPL LICENSE BLOCK #####
2 #
3 #  This program is free software; you can redistribute it and/or
4 #  modify it under the terms of the GNU General Public License
5 #  as published by the Free Software Foundation; either version 2
6 #  of the License, or (at your option) any later version.
7 #
8 #  This program is distributed in the hope that it will be useful,
9 #  but WITHOUT ANY WARRANTY; without even the implied warranty of
10 #  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
11 #  GNU General Public License for more details.
12 #
13 #  You should have received a copy of the GNU General Public License
14 #  along with this program; if not, write to the Free Software Foundation,
15 #  Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
16 #
17 # ##### END GPL LICENSE BLOCK #####
18
19 # <pep8 compliant>
20 import bpy
21
22 narrowui = 180
23
24
25 class WorldButtonsPanel(bpy.types.Panel):
26     bl_space_type = 'PROPERTIES'
27     bl_region_type = 'WINDOW'
28     bl_context = "world"
29     # COMPAT_ENGINES must be defined in each subclass, external engines can add themselves here
30
31     def poll(self, context):
32         rd = context.scene.render_data
33         return (context.world) and (not rd.use_game_engine) and (rd.engine in self.COMPAT_ENGINES)
34
35
36 class WORLD_PT_preview(WorldButtonsPanel):
37     bl_label = "Preview"
38     COMPAT_ENGINES = set(['BLENDER_RENDER'])
39
40     def draw(self, context):
41         self.layout.template_preview(context.world)
42
43
44 class WORLD_PT_context_world(WorldButtonsPanel):
45     bl_label = ""
46     bl_show_header = False
47     COMPAT_ENGINES = set(['BLENDER_RENDER'])
48
49     def poll(self, context):
50         rd = context.scene.render_data
51         return (not rd.use_game_engine) and (rd.engine in self.COMPAT_ENGINES)
52
53     def draw(self, context):
54         layout = self.layout
55
56         scene = context.scene
57         world = context.world
58         space = context.space_data
59         wide_ui = context.region.width > narrowui
60
61
62         if wide_ui:
63             split = layout.split(percentage=0.65)
64             if scene:
65                 split.template_ID(scene, "world", new="world.new")
66             elif world:
67                 split.template_ID(space, "pin_id")
68         else:
69             layout.template_ID(scene, "world", new="world.new")
70
71
72 class WORLD_PT_world(WorldButtonsPanel):
73     bl_label = "World"
74     COMPAT_ENGINES = set(['BLENDER_RENDER'])
75
76     def draw(self, context):
77         layout = self.layout
78         wide_ui = context.region.width > narrowui
79         world = context.world
80
81         if wide_ui:
82             row = layout.row()
83             row.prop(world, "paper_sky")
84             row.prop(world, "blend_sky")
85             row.prop(world, "real_sky")
86         else:
87             col = layout.column()
88             col.prop(world, "paper_sky")
89             col.prop(world, "blend_sky")
90             col.prop(world, "real_sky")
91
92         row = layout.row()
93         row.column().prop(world, "horizon_color")
94         col = row.column()
95         col.prop(world, "zenith_color")
96         col.active = world.blend_sky
97         row.column().prop(world, "ambient_color")
98
99
100 class WORLD_PT_mist(WorldButtonsPanel):
101     bl_label = "Mist"
102     COMPAT_ENGINES = set(['BLENDER_RENDER'])
103
104     def draw_header(self, context):
105         world = context.world
106
107         self.layout.prop(world.mist, "enabled", text="")
108
109     def draw(self, context):
110         layout = self.layout
111         wide_ui = context.region.width > narrowui
112         world = context.world
113
114         layout.active = world.mist.enabled
115
116         split = layout.split()
117
118         col = split.column()
119         col.prop(world.mist, "intensity", slider=True)
120         col.prop(world.mist, "start")
121
122         if wide_ui:
123             col = split.column()
124         col.prop(world.mist, "depth")
125         col.prop(world.mist, "height")
126
127         layout.prop(world.mist, "falloff")
128
129
130 class WORLD_PT_stars(WorldButtonsPanel):
131     bl_label = "Stars"
132     COMPAT_ENGINES = set(['BLENDER_RENDER'])
133
134     def draw_header(self, context):
135         world = context.world
136
137         self.layout.prop(world.stars, "enabled", text="")
138
139     def draw(self, context):
140         layout = self.layout
141         wide_ui = context.region.width > narrowui
142         world = context.world
143
144         layout.active = world.stars.enabled
145
146         split = layout.split()
147
148         col = split.column()
149         col.prop(world.stars, "size")
150         col.prop(world.stars, "color_randomization", text="Colors")
151
152         if wide_ui:
153             col = split.column()
154         col.prop(world.stars, "min_distance", text="Min. Dist")
155         col.prop(world.stars, "average_separation", text="Separation")
156
157
158 class WORLD_PT_ambient_occlusion(WorldButtonsPanel):
159     bl_label = "Ambient Occlusion"
160     COMPAT_ENGINES = set(['BLENDER_RENDER'])
161
162     def draw_header(self, context):
163         world = context.world
164
165         self.layout.prop(world.ambient_occlusion, "enabled", text="")
166
167     def draw(self, context):
168         layout = self.layout
169         wide_ui = context.region.width > narrowui
170         ao = context.world.ambient_occlusion
171
172         layout.active = ao.enabled
173
174         layout.prop(ao, "gather_method", expand=True)
175
176         split = layout.split()
177
178         col = split.column()
179         col.label(text="Attenuation:")
180         if ao.gather_method == 'RAYTRACE':
181             col.prop(ao, "distance")
182         col.prop(ao, "falloff")
183         sub = col.row()
184         sub.active = ao.falloff
185         sub.prop(ao, "falloff_strength", text="Strength")
186
187         if ao.gather_method == 'RAYTRACE':
188             if wide_ui:
189                 col = split.column()
190
191             col.label(text="Sampling:")
192             col.prop(ao, "sample_method", text="")
193
194             sub = col.column()
195             sub.prop(ao, "samples")
196
197             if ao.sample_method == 'ADAPTIVE_QMC':
198                 sub.prop(ao, "threshold")
199                 sub.prop(ao, "adapt_to_speed", slider=True)
200             elif ao.sample_method == 'CONSTANT_JITTERED':
201                 sub.prop(ao, "bias")
202
203         if ao.gather_method == 'APPROXIMATE':
204             if wide_ui:
205                 col = split.column()
206
207             col.label(text="Sampling:")
208             col.prop(ao, "passes")
209             col.prop(ao, "error_tolerance", text="Error")
210             col.prop(ao, "pixel_cache")
211             col.prop(ao, "correction")
212
213         col = layout.column()
214         col.label(text="Influence:")
215
216         col.row().prop(ao, "blend_mode", expand=True)
217
218         split = layout.split()
219
220         col = split.column()
221         col.prop(ao, "energy")
222         col.prop(ao, "indirect_energy")
223
224         if wide_ui:
225             col = split.column()
226         col.prop(ao, "color")
227
228 bpy.types.register(WORLD_PT_context_world)
229 bpy.types.register(WORLD_PT_preview)
230 bpy.types.register(WORLD_PT_world)
231 bpy.types.register(WORLD_PT_ambient_occlusion)
232 bpy.types.register(WORLD_PT_mist)
233 bpy.types.register(WORLD_PT_stars)