Show realistic lighting and shadows for a given time of day.
Use case
You can use realistic lighting to evaluate the shadow impact of buildings and utility infrastructure on the surrounding community. This could be useful for civil engineers and urban planners, or for events management assessing the impact of building shadows during an outdoor event.
How to use the sample
Select one of the three lighting options to show that lighting effect on the SceneView
. Select a time of day from the slider (based on a 24hr clock), and a date from the date picker, to show the lighting for that time of day in the SceneView
.
How it works
- Create a
Scene
and display it in a composableSceneView
. - Create a
ZonedDateTime
to define the day and time of day. - Set the sun time to the scene view using zoned date time and a time offset in milliseconds.
- Set the sun lighting of the scene view to a
LightingMode
ofNoLight
,Light
, orLightAndShadows
.
Relevant API
- Scene
- SceneView
- SceneView.SunLighting
Additional information
This sample uses the GeoView-Compose Toolkit module to be able to implement a composable SceneView.
Tags
3D, lighting, realism, realistic, rendering, sceneview-compose, shadows, sun, time, toolkit
Sample Code
/* Copyright 2025 Esri * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. * */ package com.esri.arcgismaps.sample.showrealisticlightandshadows.components import android.app.Application import androidx.compose.runtime.MutableState import androidx.compose.runtime.mutableStateOf import androidx.compose.ui.graphics.Color import androidx.lifecycle.AndroidViewModel import com.arcgismaps.geometry.Point import com.arcgismaps.geometry.SpatialReference import com.arcgismaps.mapping.ArcGISScene import com.arcgismaps.mapping.ArcGISTiledElevationSource import com.arcgismaps.mapping.BasemapStyle import com.arcgismaps.mapping.Surface import com.arcgismaps.mapping.Viewpoint import com.arcgismaps.mapping.layers.ArcGISSceneLayer import com.arcgismaps.mapping.view.AtmosphereEffect import com.arcgismaps.mapping.view.Camera import com.arcgismaps.mapping.view.LightingMode import com.arcgismaps.mapping.view.SpaceEffect import com.esri.arcgismaps.sample.sampleslib.components.MessageDialogViewModel class ShowRealisticLightAndShadowsViewModel(application: Application) : AndroidViewModel(application) { val arcGISScene = ArcGISScene(BasemapStyle.ArcGISTopographic).apply { // Add a base surface with elevation source baseSurface = Surface().apply { // Create an elevation source from Terrain3D REST service elevationSources.add( ArcGISTiledElevationSource( "https://elevation3d.arcgis.com/arcgis/rest/services/WorldElevation3D/Terrain3D/ImageServer" ) ) } // Create a scene layer from buildings REST service operationalLayers.add( ArcGISSceneLayer( "https://tiles.arcgis.com/tiles/P3ePLMYs2RVChkJx/arcgis/rest/services/DevA_BuildingShells/SceneServer" ) ) // Create a point to center on val point = Point( x = -122.69033, y = 45.54605, z = 500.0, spatialReference = SpatialReference.wgs84() ) initialViewpoint = Viewpoint( center = point, scale = 17000.0, camera = Camera( locationPoint = point, heading = 162.58544, pitch = 72.0, roll = 0.0 ) ) } // Create a LightingOptionsState with default values that will be used by the scene view val lightingOptionsState = LightingOptionsState( mutableStateOf(LightingMode.LightAndShadows), mutableStateOf(Color(red = 220, green = 220, blue = 220, alpha = 255)), mutableStateOf(AtmosphereEffect.HorizonOnly), mutableStateOf(SpaceEffect.Stars) ) // Create a message dialog view model for handling error messages val messageDialogVM = MessageDialogViewModel() } /** * Represents various lighting options used by the composable scene view. */ data class LightingOptionsState( val sunLighting: MutableState<LightingMode>, val ambientLightColor: MutableState<Color>, val atmosphereEffect: MutableState<AtmosphereEffect>, val spaceEffect: MutableState<SpaceEffect> )