Index: tools/atlas/AtlasUI/ActorEditor/ActorEditor.cpp
===================================================================
--- tools/atlas/AtlasUI/ActorEditor/ActorEditor.cpp	(revision 7796)
+++ tools/atlas/AtlasUI/ActorEditor/ActorEditor.cpp	(working copy)
@@ -73,6 +73,9 @@
 	m_CastShadows = new wxCheckBox(propertiesPanel, wxID_ANY, _("Cast shadow"));
 	propertiesSizer->Add(m_CastShadows, wxSizerFlags().Border(wxALL, 5));
 
+	m_ReceiveShadows = new wxCheckBox(propertiesPanel, wxID_ANY, _("Receive shadow"));
+	propertiesSizer->Add(m_ReceiveShadows, wxSizerFlags().Border(wxALL, 5));
+
 	m_Float = new wxCheckBox(propertiesPanel, wxID_ANY, _("Float on water"));
 	propertiesSizer->Add(m_Float, wxSizerFlags().Border(wxALL, 5));
 
@@ -107,6 +110,7 @@
 	m_ActorEditorListCtrl->ThawData(actor);
 
 	m_CastShadows->SetValue(actor["castshadow"].defined());
+	m_ReceiveShadows->SetValue(actor["receiveshadow"].defined());
 	m_Float->SetValue(actor["float"].defined());
 	m_Material->SetValue((wxString)actor["material"]);
 }
@@ -118,6 +122,9 @@
 	if (m_CastShadows->IsChecked())
 		actor.set("castshadow", L"");
 
+	if (m_ReceiveShadows->IsChecked())
+		actor.set("receiveshadow", L"");
+		
 	if (m_Float->IsChecked())
 		actor.set("float", L"");
 
@@ -173,6 +180,9 @@
 
 		if (wxString(in["Object"]["Properties"]["@castshadows"]) == _T("1"))
 			actor.add("castshadow", L"");
+			
+		if (wxString(in["Object"]["Properties"]["@receiveshadows"]) == _T("1"))
+			actor.add("receiveshadow", L"");
 
 		// Things to strip leading strings (for converting filenames, since the
 		// new format doesn't store the entire path)
@@ -247,6 +257,7 @@
 		AtObj actor;
 
 		if (in["actor"]["castshadow"].defined()) actor.add("castshadow", in["actor"]["castshadow"]);
+		if (in["actor"]["receiveshadow"].defined()) actor.add("receiveshadow", in["actor"]["receiveshadow"]);
 		if (in["actor"]["material"].defined()) actor.add("material", in["actor"]["material"]);
 
 		for (AtIter grpit = in["actor"]["group"]; grpit.defined(); ++grpit)
@@ -317,6 +328,7 @@
 	m_ActorEditorListCtrl->ImportData(actor);
 
 	m_CastShadows->SetValue(actor["castshadow"].defined());
+	m_ReceiveShadows->SetValue(actor["receiveshadow"].defined());
 	m_Float->SetValue(actor["float"].defined());
 	m_Material->SetValue((wxString)actor["material"]);
 }
@@ -330,6 +342,9 @@
 
 	if (m_CastShadows->IsChecked())
 		actor.set("castshadow", L"");
+		
+	if (m_ReceiveShadows->IsChecked())
+		actor.set("receiveshadow", L"");
 
 	if (m_Float->IsChecked())
 		actor.set("float", L"");
Index: tools/atlas/AtlasUI/ActorEditor/ActorEditor.h
===================================================================
--- tools/atlas/AtlasUI/ActorEditor/ActorEditor.h	(revision 7796)
+++ tools/atlas/AtlasUI/ActorEditor/ActorEditor.h	(working copy)
@@ -48,6 +48,7 @@
 	ActorEditorListCtrl* m_ActorEditorListCtrl;
 
 	wxCheckBox* m_CastShadows;
+	wxCheckBox* m_ReceiveShadows;
 	wxCheckBox* m_Float;
 	wxComboBox* m_Material;
 
Index: graphics/Model.cpp
===================================================================
--- graphics/Model.cpp	(revision 7796)
+++ graphics/Model.cpp	(working copy)
@@ -379,6 +379,10 @@
 	m_Flags &= ~MODELFLAG_CASTSHADOWS;
 	if (source->m_Flags & MODELFLAG_CASTSHADOWS)
 		m_Flags |= MODELFLAG_CASTSHADOWS;
+		
+	m_Flags &= ~MODELFLAG_RECEIVESHADOWS;
+	if (source->m_Flags & MODELFLAG_RECEIVESHADOWS)
+		m_Flags |= MODELFLAG_RECEIVESHADOWS;
 
 	m_ObjectBounds.SetEmpty();
 	InvalidateBounds();
Index: graphics/Model.h
===================================================================
--- graphics/Model.h	(revision 7796)
+++ graphics/Model.h	(working copy)
@@ -37,7 +37,8 @@
 class CSkeletonAnimManager;
 
 #define MODELFLAG_CASTSHADOWS		(1<<0)
-#define MODELFLAG_NOLOOPANIMATION	(1<<1)
+#define MODELFLAG_RECEIVESHADOWS	(1<<1)
+#define MODELFLAG_NOLOOPANIMATION	(1<<2)
 
 ///////////////////////////////////////////////////////////////////////////////
 // CModel: basically, a mesh object - holds the texturing and skinning 
Index: graphics/ObjectBase.h
===================================================================
--- graphics/ObjectBase.h	(revision 7796)
+++ graphics/ObjectBase.h	(working copy)
@@ -120,6 +120,8 @@
 		bool m_AutoFlatten;
 		// cast shadows from this object
 		bool m_CastShadows;
+		// this object receives shadows
+		bool m_ReceiveShadows;
 		// float on top of water
 		bool m_FloatOnWater;
 	} m_Properties;
Index: graphics/ObjectBase.cpp
===================================================================
--- graphics/ObjectBase.cpp	(revision 7796)
+++ graphics/ObjectBase.cpp	(working copy)
@@ -35,7 +35,8 @@
 CObjectBase::CObjectBase(CObjectManager& objectManager)
 : m_ObjectManager(objectManager)
 {
-	m_Properties.m_CastShadows = true;
+	m_Properties.m_CastShadows = false;
+	m_Properties.m_ReceiveShadows = false;
 	m_Properties.m_AutoFlatten = false;
 	m_Properties.m_FloatOnWater = false;
 }
@@ -51,6 +52,7 @@
 	#define AT(x) int at_##x = XeroFile.GetAttributeID(#x)
 	EL(actor);
 	EL(castshadow);
+	EL(receiveshadow);
 	EL(float);
 	EL(material);
 	EL(group);
@@ -213,8 +215,12 @@
 		}
 		else if (child_name == el_castshadow)
 		{
-			m_Properties.m_CastShadows = true; // TODO: this is the default, so it's a bit useless
+			m_Properties.m_CastShadows = true;
 		}
+		else if (child_name == el_receiveshadow)
+		{
+			m_Properties.m_ReceiveShadows = true;
+		}
 		else if (child_name == el_float)
 		{
 			m_Properties.m_FloatOnWater = true;
Index: graphics/ObjectEntry.cpp
===================================================================
--- graphics/ObjectEntry.cpp	(revision 7796)
+++ graphics/ObjectEntry.cpp	(working copy)
@@ -199,6 +199,10 @@
 	{
 		m_Model->SetFlags(m_Model->GetFlags()|MODELFLAG_CASTSHADOWS);
 	}
+	if (m_Base->m_Properties.m_ReceiveShadows)
+	{
+		m_Model->SetFlags(m_Model->GetFlags()|MODELFLAG_RECEIVESHADOWS);
+	}
 
 	// replace any units using old model to now use new model; also reprop models, if necessary
 	// FIXME, RC - ugh, doesn't recurse correctly through props
