// 發射武器 
	public bool ActiveWeapon( string _WeaponComponentName , 
					   		  NamedObject _TargetUnit , 
							  string _TargetComponentName )
	{
		/*
		Debug.Log( "ActiveWeapon()" + 
				   this.gameObject.name + " " + 
				   _WeaponComponentName + " " + 
				   _TargetUnit.Name + " "+ 
					_TargetComponentName ) ;
		//*/
		SystemLogManager.AddLog( SystemLogManager.SysLogType.FireWeapon , 
			this.gameObject.name + ":" + _WeaponComponentName + ":" + _TargetUnit.Name + ":" + _TargetComponentName ) ;
		
		// get weapon data
		UnitData unitData = this.gameObject.GetComponent<UnitData>() ;
		if( null == unitData )
		{
			Debug.Log( "ActiveWeapon() null == unitData" ) ;
			return false ;
		}
		
		if( false == unitData.componentMap.ContainsKey( _WeaponComponentName ) )
		{
			Debug.Log( "ActiveWeapon() no such component:" + _WeaponComponentName + ".") ;
			return false ;
		}
		UnitComponentData weaponComponent = unitData.componentMap[ _WeaponComponentName ] ;
		
			
		WeaponDataSet weaponSet = null ;
		if( false == this.m_WeaponDataMap.ContainsKey( _WeaponComponentName ) )
		{
			Debug.Log( "false == this.m_WeaponDataMap.ContainsKey( _WeaponComponentName ):" + _WeaponComponentName ) ;
			return false ;
		}
		weaponSet = this.m_WeaponDataMap[ _WeaponComponentName ] ;
		WeaponParam weaponParam = weaponComponent.m_WeaponParam ;
		
		// weapon data
		float weapenDamage = weaponComponent.TotalEffect() ;
		// Debug.Log( "weapenDamage" + weapenDamage ) ;
		float weapenAccuracy = weaponParam.m_Accuracy ;// 0~1
		// Debug.Log( "weapenAccuracy" + weapenAccuracy ) ;
		float weaponMissRage = 1.0f - weapenAccuracy ;
		float sceneMaximumMissDistance = 1.0f ;	
		
		// check able to fire
		if( WeaponFireState.Ready != weaponSet.m_FireState )
		{
			// Debug.Log( "WeaponFireState.Ready != weaponSet.m_FireState"  ) ;
			return false ;
		}
		
		// get Target Unit Object : the unit contains data.
		if( null == _TargetUnit.Obj )
		{
			Debug.Log( "null == weaponSet.TargetUnitObject"  ) ;
			return false ;
		}
		
		// find out hit component name
		UnitDamageSystem unitDamageSys = _TargetUnit.Obj.GetComponent< UnitDamageSystem >() ;
		if( null == unitDamageSys )
		{
			Debug.Log( "ActiveWeapon() : null == unitDamageSys" ) ;			
			return false ;
		}
		
		// 取得被擊中的部件
		string realUnitName = "" ;
		string realComponentObjectName = "" ;
		if( false == unitDamageSys.RetrieveRealTargetComponent( this.gameObject , 
														 		_TargetComponentName ,
																ref realUnitName ,
																ref realComponentObjectName ) )
		{
			Debug.Log( "unitDamageSys.RetrieveRealTargetComponent fail" ) ;
			return false ;
		}
		if( _TargetUnit.Name != realUnitName )
		{
			NamedObject unit = new NamedObject( realUnitName ) ;
			unitDamageSys = unit.Obj.GetComponent< UnitDamageSystem >() ;
			if( null == unitDamageSys )
			{
				Debug.Log( "ActiveWeapon() : null == unitDamageSys realUnitName=" + realUnitName ) ;			
				return false ;
			}
		}
		weaponSet.SetupTarget( realUnitName , realComponentObjectName ) ;
		
		
		// true Hit Component Object , it may the same with target unit object.
		// Debug.Log( "weaponSet.TargetUnitName=" + weaponSet.TargetUnitName ) ;
		// Debug.Log( "weaponSet.TargetComponentObjectName=" + weaponSet.TargetComponentObjectName ) ;
		
		unitDamageSys = weaponSet.TargetUnitObject.GetComponent< UnitDamageSystem >() ;
		if( null == unitDamageSys )
		{
			// Debug.Log( "ActiveWeapon() : null == unitDamageSys" ) ;
			return false ;
		}			
		
		// Debug.Log( "ActiveWeapon() TargetComponentName" + realTargetComponentName ) ;
		
		// create corresponding weapong effect object
		if( null == weaponSet.Effect3DObject )
		{
			Debug.Log( "null == weaponSet.Effect3DObject:" + weaponSet.Effect3DObjectName ) ;
			return false ;
		}
		
		float damageCause = 0.0f ;
		// calculate displacement 
		{
			int randomMax = 100 ;
			int randomValue = Random.Range( 0 , randomMax ) ;
			
			int halfRandomValue = randomMax / 2 ;			
			float randomRatio = (randomMax - randomValue) / (float) randomMax ;
			damageCause = weapenDamage * ( weapenAccuracy + randomRatio * weaponMissRage ) ;
			
			float halfValue = (float)( randomValue - halfRandomValue ) / (float) ( randomMax );
			float randomDisplacement = 0.0f ;
			randomDisplacement = sceneMaximumMissDistance * halfValue ;
			
			float positiveInX = 1.0f;
			if( 1 == Random.Range( 0 , 1 ) )
				positiveInX = -1.0f ;
			
			float positiveInZ = 1.0f;
			if( 1 == Random.Range( 0 , 1 ) )
				positiveInZ = -1.0f ;
			
			weaponSet.m_Displacement = new Vector3( randomDisplacement * positiveInX , 
												  0 , 
												  randomDisplacement * positiveInZ ) ;
			
		}	
		
		weaponSet.m_CauseDamage = damageCause ; 
		
		if( weaponSet.m_WeaponType == WeaponType.Phaser )
		{
			weaponSet.m_FireTotalTime = 2.1f ;// 造成兩次觸發
			weaponSet.m_FireStartTime = Time.time ;
			
			WeaponPhaserEffect phaserEffect = weaponSet.Effect3DObject.GetComponent< WeaponPhaserEffect >() ;
			if( null != phaserEffect )
			{
				phaserEffect.Setup( weaponSet ) ;
			}


			
			// cause damage effect imidiatly
			if( null != unitDamageSys )
			{
				string damageEffectName = unitDamageSys.ActiveDamageEffect( this.gameObject , 
																			weaponSet.TargetComponentObjectName ) ;
				if( 0 != damageEffectName.Length )
				{
					RelativeDamageEffect relativeDamageEffect = new RelativeDamageEffect() ;
					relativeDamageEffect.m_TargetUnit = weaponSet.TargetUnitObject ;
					relativeDamageEffect.m_DamageEffectName = damageEffectName ;
					weaponSet.m_RelativeDamageEffectNames.Add( relativeDamageEffect ) ;
				}
			}
		}
		else if( weaponSet.m_WeaponType == WeaponType.TrakorBeam )
		{
			WeaponTrackorBeamEffect trackorBeamEffect = weaponSet.Effect3DObject.GetComponent< WeaponTrackorBeamEffect >() ;
			if( null != trackorBeamEffect )
			{
				weaponSet.m_CauseDamage = weaponComponent.TotalEffect() ;
				trackorBeamEffect.Setup( weaponSet ) ;
			}

			weaponSet.m_FireTotalTime = 999.0f ;
			weaponSet.m_FireStartTime = Time.time ;
		}
		else if( weaponSet.m_WeaponType == WeaponType.Torpedo )
		{
			weaponSet.Effect3DObject.transform.position = weaponSet.Component3DObject.transform.position ;
			weaponSet.m_TargetDirection = weaponSet.TargetComponentObject.transform.position - weaponSet.Effect3DObject.transform.position ;
			weaponSet.m_TargetDirection.Normalize() ;
			
			WeaponPhotonTorpedoEffect torpedoEffect = weaponSet.Effect3DObject.GetComponent< WeaponPhotonTorpedoEffect >() ;
			if( null != torpedoEffect )
			{
				torpedoEffect.Setup( weaponSet ) ;
			}

			weaponSet.m_FireTotalTime = 10.0f ;
			weaponSet.m_FireStartTime = Time.time ;				
		}
		else if( weaponSet.m_WeaponType == WeaponType.Cannon )
		{
			weaponSet.Effect3DObject.transform.position = weaponSet.Component3DObject.transform.position ;
			weaponSet.m_TargetDirection = weaponSet.TargetComponentObject.transform.position - weaponSet.Effect3DObject.transform.position ;
			weaponSet.m_TargetDirection.Normalize() ;
			
			WeaponCannonEffect cannonEffect = weaponSet.Effect3DObject.GetComponent< WeaponCannonEffect >() ;
			if( null != cannonEffect )
			{
				cannonEffect.Setup( weaponSet ) ;
			}

			weaponSet.m_FireTotalTime = 10.0f ;
			weaponSet.m_FireStartTime = Time.time ;				
		}		
		else 
		{
			Debug.Log( "weaponSet.m_WeaponType=" + weaponSet.m_WeaponType ) ;
		}
		
		
			
		ActiveEffect( weaponSet ) ;

		
		weaponSet.m_FireState = WeaponFireState.FireAnimating ;
		
		// weapn fire, clear the reload energy		
		weaponComponent.m_ReloadEnergy.Clear() ;
		
		return true ;
	}
 public RelativeDamageEffect( RelativeDamageEffect _src )
 {
     m_TargetUnit = _src.m_TargetUnit ;
     m_DamageEffectName = _src.m_DamageEffectName ;
 }