Kregano Posted February 17, 2017 Share Posted February 17, 2017 I created an AOE suppression ability about a year ago, and it worked fine, patch related hiccups not withstanding. However, now it's not functioning with one particular mod gun, and I'm not exactly sure why. Bug behavior:-Confirmed by multiple people - soldier with Spart's Salvaged Cannon (Standalone Version) will get out of cover when this ability is used, but the firing animation does not happen, none of the targets are suppressed, and ammo is consumed.-Possibly related - soldier with Spart's Salvaged Cannon (Standalone Version) is in range of two targetable enemies. Ability is used, but only one target is suppressed, while the other is not. Animation plays. Code for the Cone of Fire ability: class X2Ability_ConeOfFireStuff extends X2Ability_GrenadierAbilitySet config(GameData_SoldierSkills) dependson (XComGameStateContext_Ability); static function array<X2DataTemplate> CreateTemplates() { local array<X2DataTemplate> Templates; Templates.AddItem(ConeOfFire()); return Templates; } static function X2AbilityTemplate ConeOfFire() { local X2AbilityTemplate Template; local X2AbilityCost_ActionPoints ActionPointCost; local X2AbilityCost_Ammo AmmoCost; local X2AbilityCooldown Cooldown; local X2Effect_ReserveActionPoints ReserveActionPointsEffect; local X2AbilityMultiTarget_Cone ConeMultiTarget; local X2Condition_UnitProperty UnitPropertyCondition; local X2Effect_Suppression SuppressionEffect; `CREATE_X2ABILITY_TEMPLATE(Template, 'ConeOfFire'); Template.IconImage = "img:///UILibrary_ConeOfFire.UIPerk_coneoffire"; ActionPointCost = new class'X2AbilityCost_ActionPoints'; ActionPointCost.bConsumeAllPoints = true; // this will guarantee the unit has at least 1 action point ActionPointCost.bFreeCost = true; // ReserveActionPoints effect will take all action points away Template.AbilityCosts.AddItem(ActionPointCost); AmmoCost = new class'X2AbilityCost_Ammo'; AmmoCost.iAmmo = 2; Template.AbilityCosts.AddItem(AmmoCost); Cooldown = new class'X2AbilityCooldown'; Cooldown.iNumTurns = 1; Template.AbilityCooldown = Cooldown; Template.AbilityShooterConditions.AddItem(default.LivingShooterProperty); Template.AddShooterEffectExclusions(); ReserveActionPointsEffect = new class'X2Effect_ReserveActionPoints'; ReserveActionPointsEffect.ReserveType = 'Suppression'; Template.AddShooterEffect(ReserveActionPointsEffect); Template.AbilityToHitCalc = default.DeadEye; Template.AbilityTargetConditions.AddItem(default.LivingHostileUnitDisallowMindControlProperty); Template.AbilityTargetConditions.AddItem(default.GameplayVisibilityCondition); Template.AbilityTriggers.AddItem(default.PlayerInputTrigger); Template.AbilityTargetStyle = new class'X2AbilityTarget_Cursor'; ConeMultiTarget = new class'X2AbilityMultiTarget_Cone'; ConeMultiTarget.bUseWeaponRadius = true; ConeMultiTarget.ConeEndDiameter = 12 * class'XComWorldData'.const.WORLD_StepSize; ConeMultiTarget.bUseWeaponRangeForLength = true; Template.AbilityMultiTargetStyle = ConeMultiTarget; UnitPropertyCondition = new class'X2Condition_UnitProperty'; UnitPropertyCondition.ExcludeDead = true; UnitPropertyCondition.ExcludeFriendlyToSource = true; Template.AbilityShooterConditions.AddItem(UnitPropertyCondition); Template.AbilityTargetConditions.AddItem(UnitPropertyCondition); SuppressionEffect = new class'X2Effect_Suppression'; SuppressionEffect.BuildPersistentEffect(1, false, true, false, eGameRule_PlayerTurnBegin); SuppressionEffect.bRemoveWhenTargetDies = true; SuppressionEffect.bRemoveWhenSourceDamaged = true; SuppressionEffect.bBringRemoveVisualizationForward = true; SuppressionEffect.SetDisplayInfo(ePerkBuff_Penalty, Template.LocFriendlyName, class'X2Ability_GrenadierAbilitySet'.default.SuppressionTargetEffectDesc, Template.IconImage); SuppressionEffect.SetSourceDisplayInfo(ePerkBuff_Bonus, Template.LocFriendlyName, class'X2Ability_GrenadierAbilitySet'.default.SuppressionSourceEffectDesc, Template.IconImage); Template.AddMultiTargetEffect(SuppressionEffect); Template.AddTargetEffect(class'X2Ability_GrenadierAbilitySet'.static.HoloTargetEffect()); Template.bAllowAmmoEffects = true; Template.ShotHUDPriority = class'UIUtilities_Tactical'.const.CLASS_LIEUTENANT_PRIORITY; Template.AbilitySourceName = 'eAbilitySource_Perk'; Template.eAbilityIconBehaviorHUD = eAbilityIconBehavior_AlwaysShow; Template.bDisplayInUITooltip = false; Template.AdditionalAbilities.AddItem('SuppressionShot'); Template.bIsASuppressionEffect = true; Template.AbilityConfirmSound = "TacticalUI_ActivateAbility"; Template.AssociatedPassives.AddItem('HoloTargeting'); Template.CinescriptCameraType = "StandardSuppression"; Template.BuildNewGameStateFn = TypicalAbility_BuildGameState; Template.BuildVisualizationFn = ConeOfFireBuildVisualization; Template.BuildAppliedVisualizationSyncFn = class'X2Ability_GrenadierAbilitySet'.static.SuppressionBuildVisualizationSync; Template.TargetingMethod = class'X2TargetingMethod_Cone'; Template.bCrossClassEligible = true; return Template; } Code for the visualization (possibly where the error is, although this works on every other mod weapon I use with this skill): simulated function ConeOfFireBuildVisualization(XComGameState VisualizeGameState, out array<VisualizationTrack> OutVisualizationTracks) { local XComGameStateHistory History; local XComGameStateContext_Ability Context; local StateObjectReference InteractingUnitRef; local VisualizationTrack EmptyTrack; local VisualizationTrack BuildTrack; local int i; local XComGameState_Ability Ability; local X2Action_PlaySoundAndFlyOver SoundAndFlyOver; local XComUnitPawn UnitPawn; local XComWeapon Weapon; History = `XCOMHISTORY; Context = XComGameStateContext_Ability(VisualizeGameState.GetContext()); InteractingUnitRef = Context.InputContext.SourceObject; //Configure the visualization track for the shooter //**************************************************************************************** BuildTrack = EmptyTrack; BuildTrack.StateObject_OldState = History.GetGameStateForObjectID(InteractingUnitRef.ObjectID, eReturnType_Reference, VisualizeGameState.HistoryIndex - 1); BuildTrack.StateObject_NewState = VisualizeGameState.GetGameStateForObjectID(InteractingUnitRef.ObjectID); BuildTrack.TrackActor = History.GetVisualizer(InteractingUnitRef.ObjectID); // Check the actor's pawn and weapon, see if they can play the suppression effect UnitPawn = XGUnit(BuildTrack.TrackActor).GetPawn(); Weapon = XComWeapon(UnitPawn.Weapon); if (Weapon != None && !UnitPawn.GetAnimTreeController().CanPlayAnimation(Weapon.WeaponSuppressionFireAnimSequenceName) && !UnitPawn.GetAnimTreeController().CanPlayAnimation(class'XComWeapon'.default.WeaponSuppressionFireAnimSequenceName)) { // The unit can't play their weapon's suppression effect. Replace it with the normal fire effect so at least they'll look like they're shooting Weapon.WeaponSuppressionFireAnimSequenceName = Weapon.WeaponFireAnimSequenceName; } class'X2Action_ExitCover'.static.AddToVisualizationTrack(BuildTrack, Context); class'X2Action_StartSuppression'.static.AddToVisualizationTrack(BuildTrack, Context); OutVisualizationTracks.AddItem(BuildTrack); //**************************************************************************************** //Configure the visualization track for the targets for (i = 0; i < Context.InputContext.MultiTargets.Length; i++) { // Fake it out by assigning the first multi-target as the primary target if (Context.InputContext.PrimaryTarget.ObjectID == 0) Context.InputContext.PrimaryTarget = Context.InputContext.MultiTargets[i]; InteractingUnitRef = Context.InputContext.MultiTargets[i]; Ability = XComGameState_Ability(History.GetGameStateForObjectID(Context.InputContext.AbilityRef.ObjectID, eReturnType_Reference, VisualizeGameState.HistoryIndex - 1)); BuildTrack = EmptyTrack; BuildTrack.StateObject_OldState = History.GetGameStateForObjectID(InteractingUnitRef.ObjectID, eReturnType_Reference, VisualizeGameState.HistoryIndex - 1); BuildTrack.StateObject_NewState = VisualizeGameState.GetGameStateForObjectID(InteractingUnitRef.ObjectID); BuildTrack.TrackActor = History.GetVisualizer(InteractingUnitRef.ObjectID); SoundAndFlyOver = X2Action_PlaySoundAndFlyOver(class'X2Action_PlaySoundAndFlyOver'.static.AddToVisualizationTrack(BuildTrack, Context)); SoundAndFlyOver.SetSoundAndFlyOverParameters(None, Ability.GetMyTemplate().LocFlyOverText, '', eColor_Bad); if (XComGameState_Unit(BuildTrack.StateObject_OldState).ReserveActionPoints.Length != 0 && XComGameState_Unit(BuildTrack.StateObject_NewState).ReserveActionPoints.Length == 0) { SoundAndFlyOver = X2Action_PlaySoundAndFlyOver(class'X2Action_PlaySoundAndFlyOver'.static.AddToVisualizationTrack(BuildTrack, Context)); SoundAndFlyOver.SetSoundAndFlyOverParameters(none, class'XLocalizedData'.default.OverwatchRemovedMsg, '', eColor_Bad); } OutVisualizationTracks.AddItem(BuildTrack); } } Code for Spart's Salvaged Cannon (Standalone): class X2Item_SpartsSalvSA_Weapon extends X2Item config(SpartsSalvSA); var config bool HIDE_PREVIOUS_TIERS_SALV; // Variables from config - GameData_WeaponData.ini // ***** Damage arrays for attack actions ***** var config WeaponDamageValue ADVCONVLMG_SA_CONVENTIONAL_BASEDAMAGE; var config WeaponDamageValue ADVCONVLMG_SA_MAGNETIC_BASEDAMAGE; var config WeaponDamageValue ADVCONVLMG_SA_BEAM_BASEDAMAGE; // ***** Core properties and variables for weapons ***** var config int ADVCONVLMG_SA_CONVENTIONAL_AIM; var config int ADVCONVLMG_SA_CONVENTIONAL_CRITCHANCE; var config int ADVCONVLMG_SA_CONVENTIONAL_ICLIPSIZE; var config int ADVCONVLMG_SA_CONVENTIONAL_ISOUNDRANGE; var config int ADVCONVLMG_SA_CONVENTIONAL_IENVIRONMENTDAMAGE; var config int ADVCONVLMG_SA_CONVENTIONAL_UPGRADESLOTS; var config int ADVCONVLMG_SA_MAGNETIC_AIM; var config int ADVCONVLMG_SA_MAGNETIC_CRITCHANCE; var config int ADVCONVLMG_SA_MAGNETIC_ICLIPSIZE; var config int ADVCONVLMG_SA_MAGNETIC_ISOUNDRANGE; var config int ADVCONVLMG_SA_MAGNETIC_IENVIRONMENTDAMAGE; var config int ADVCONVLMG_SA_MAGNETIC_UPGRADESLOTS; var config int ADVCONVLMG_SA_BEAM_AIM; var config int ADVCONVLMG_SA_BEAM_CRITCHANCE; var config int ADVCONVLMG_SA_BEAM_ICLIPSIZE; var config int ADVCONVLMG_SA_BEAM_ISOUNDRANGE; var config int ADVCONVLMG_SA_BEAM_IENVIRONMENTDAMAGE; var config int ADVCONVLMG_SA_BEAM_UPGRADESLOTS; // ***** Range Modifier Tables ***** var config array<int> ADVCONVLMG_SA_CONVENTIONAL_RANGE; var config array<int> ADVCONVLMG_SA_MAGNETIC_RANGE; var config array<int> ADVCONVLMG_SA_BEAM_RANGE; //Template classes are searched for by the game when it starts. Any derived classes have their CreateTemplates function called //on the class default object. The game expects CreateTemplates to return a list of templates that it will add to the manager //reponsible for those types of templates. Later, these templates will be automatically picked up by the game mechanics and systems. static function array<X2DataTemplate> CreateTemplates() { local array<X2DataTemplate> ModWeapons; local X2ItemTemplateManager ItemTemplateManager; ModWeapons.AddItem(CreateTemplate_AdvCannon_SA_Conventional()); ModWeapons.AddItem(CreateTemplate_AdvCannon_SA_Magnetic()); ModWeapons.AddItem(CreateTemplate_AdvCannon_SA_Beam()); [-snip weapon attachments-] return ModWeapons; } static function X2DataTemplate CreateTemplate_AdvCannon_SA_Conventional() { local X2WeaponTemplate Template; `CREATE_X2TEMPLATE(class'X2WeaponTemplate', Template, 'AdvCannon_SA_CV'); Template.WeaponPanelImage = "_ConventionalRifle"; Template.ItemCat = 'weapon'; Template.WeaponCat = 'cannon'; Template.WeaponTech = 'conventional'; Template.strImage = "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Base"; Template.EquipSound = "Conventional_Weapon_Equip"; Template.Tier = 0; Template.Abilities.AddItem('ADVCONVLMG_SA_CV_StatBonus'); Template.SetUIStatMarkup(class'XLocalizedData'.default.MobilityLabel, eStat_Mobility, class'X2Ability_SpartsSalvSA'.default.ADVCONVLMG_SA_CV_MOBILITY_BONUS); Template.RangeAccuracy = default.ADVCONVLMG_SA_CONVENTIONAL_RANGE; Template.BaseDamage = default.ADVCONVLMG_SA_CONVENTIONAL_BASEDAMAGE; Template.Aim = default.ADVCONVLMG_SA_CONVENTIONAL_AIM; Template.CritChance = default.ADVCONVLMG_SA_CONVENTIONAL_CRITCHANCE; Template.iClipSize = default.ADVCONVLMG_SA_CONVENTIONAL_ICLIPSIZE; Template.iSoundRange = default.ADVCONVLMG_SA_CONVENTIONAL_ISOUNDRANGE; Template.iEnvironmentDamage = default.ADVCONVLMG_SA_CONVENTIONAL_IENVIRONMENTDAMAGE; Template.NumUpgradeSlots = default.ADVCONVLMG_SA_CONVENTIONAL_UPGRADESLOTS; Template.bIsLargeWeapon = true; Template.InventorySlot = eInvSlot_PrimaryWeapon; Template.Abilities.AddItem('StandardShot'); Template.Abilities.AddItem('Overwatch'); Template.Abilities.AddItem('OverwatchShot'); Template.Abilities.AddItem('Reload'); Template.Abilities.AddItem('HotLoadAmmo'); // This all the resources; sounds, animations, models, physics, the works. Template.GameArchetype = "SalvCannonSA.GameData.WP_AdvCannon_CV"; Template.UIArmoryCameraPointTag = 'UIPawnLocation_WeaponUpgrade_Cannon'; Template.AddDefaultAttachment('Mag', "ConvCannon.Meshes.SM_ConvCannon_MagA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_MagA"); Template.AddDefaultAttachment('Reargrip', "ConvCannon.Meshes.SM_ConvCannon_ReargripA"/*REARGRIP INCLUDED IN TRIGGER IMAGE*/); Template.AddDefaultAttachment('Stock', "ConvCannon.Meshes.SM_ConvCannon_StockA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_StockA"); Template.AddDefaultAttachment('StockSupport', "ConvCannon.Meshes.SM_ConvCannon_StockA_Support"); Template.AddDefaultAttachment('Suppressor', "ConvCannon.Meshes.SM_ConvCannon_SuppressorA"); Template.AddDefaultAttachment('Trigger', "ConvCannon.Meshes.SM_ConvCannon_TriggerA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_TriggerA"); Template.AddDefaultAttachment('Light', "ConvAttachments.Meshes.SM_ConvFlashLight", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Flashlight"); Template.iPhysicsImpulse = 5; if (class'X2Item_SpartsSalvSA_Schematics'.default.ADVCANNON_SA_CONVENTIONAL_ENABLE_ONSTART == true) { Template.StartingItem = true; } else { Template.CreatorTemplateName = 'AdvCannon_SA_CV_Schematic'; // The schematic which creates this item } Template.CanBeBuilt = false; Template.bInfiniteItem = true; Template.DamageTypeTemplateName = 'Projectile_Conventional'; if (default.HIDE_PREVIOUS_TIERS_SALV == true) { Template.HideIfPurchased = 'AdvCannon_SA_MG'; } return Template; } static function X2DataTemplate CreateTemplate_AdvCannon_SA_Magnetic() { local X2WeaponTemplate Template; `CREATE_X2TEMPLATE(class'X2WeaponTemplate', Template, 'AdvCannon_SA_MG'); Template.WeaponPanelImage = "_ConventionalRifle"; Template.ItemCat = 'weapon'; Template.WeaponCat = 'cannon'; Template.WeaponTech = 'magnetic'; Template.strImage = "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Base"; Template.EquipSound = "Magnetic_Weapon_Equip"; Template.Tier = 3; Template.Abilities.AddItem('ADVCONVLMG_SA_MG_StatBonus'); Template.SetUIStatMarkup(class'XLocalizedData'.default.MobilityLabel, eStat_Mobility, class'X2Ability_SpartsSalvSA'.default.ADVCONVLMG_SA_MG_MOBILITY_BONUS); Template.RangeAccuracy = default.ADVCONVLMG_SA_MAGNETIC_RANGE; Template.BaseDamage = default.ADVCONVLMG_SA_MAGNETIC_BASEDAMAGE; Template.Aim = default.ADVCONVLMG_SA_MAGNETIC_AIM; Template.CritChance = default.ADVCONVLMG_SA_MAGNETIC_CRITCHANCE; Template.iClipSize = default.ADVCONVLMG_SA_MAGNETIC_ICLIPSIZE; Template.iSoundRange = default.ADVCONVLMG_SA_MAGNETIC_ISOUNDRANGE; Template.iEnvironmentDamage = default.ADVCONVLMG_SA_MAGNETIC_IENVIRONMENTDAMAGE; Template.NumUpgradeSlots = default.ADVCONVLMG_SA_MAGNETIC_UPGRADESLOTS; Template.bIsLargeWeapon = true; Template.InventorySlot = eInvSlot_PrimaryWeapon; Template.Abilities.AddItem('StandardShot'); Template.Abilities.AddItem('Overwatch'); Template.Abilities.AddItem('OverwatchShot'); Template.Abilities.AddItem('Reload'); Template.Abilities.AddItem('HotLoadAmmo'); // This all the resources; sounds, animations, models, physics, the works. Template.GameArchetype = "SalvCannonSA.GameData.WP_AdvCannon_CV"; Template.UIArmoryCameraPointTag = 'UIPawnLocation_WeaponUpgrade_Cannon'; Template.AddDefaultAttachment('Mag', "ConvCannon.Meshes.SM_ConvCannon_MagA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_MagA"); Template.AddDefaultAttachment('Reargrip', "ConvCannon.Meshes.SM_ConvCannon_ReargripA"/*REARGRIP INCLUDED IN TRIGGER IMAGE*/); Template.AddDefaultAttachment('Stock', "ConvCannon.Meshes.SM_ConvCannon_StockA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_StockA"); Template.AddDefaultAttachment('StockSupport', "ConvCannon.Meshes.SM_ConvCannon_StockA_Support"); Template.AddDefaultAttachment('Suppressor', "ConvCannon.Meshes.SM_ConvCannon_SuppressorA"); Template.AddDefaultAttachment('Trigger', "ConvCannon.Meshes.SM_ConvCannon_TriggerA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_TriggerA"); Template.AddDefaultAttachment('Light', "ConvAttachments.Meshes.SM_ConvFlashLight", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Flashlight"); Template.iPhysicsImpulse = 5; Template.CreatorTemplateName = 'AdvCannon_SA_MG_Schematic'; // The schematic which creates this item Template.BaseItem = 'AdvCannon_SA_CV'; // Which item this will be upgraded from Template.CanBeBuilt = false; Template.bInfiniteItem = true; Template.DamageTypeTemplateName = 'Projectile_MagXCom'; if (default.HIDE_PREVIOUS_TIERS_SALV == true) { Template.HideIfPurchased = 'AdvCannon_SA_BM'; } return Template; } static function X2DataTemplate CreateTemplate_AdvCannon_SA_Beam() { local X2WeaponTemplate Template; `CREATE_X2TEMPLATE(class'X2WeaponTemplate', Template, 'AdvCannon_SA_BM'); Template.WeaponPanelImage = "_ConventionalRifle"; Template.ItemCat = 'weapon'; Template.WeaponCat = 'cannon'; Template.WeaponTech = 'beam'; Template.strImage = "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Base"; Template.EquipSound = "Beam_Weapon_Equip"; Template.Tier = 5; Template.Abilities.AddItem('ADVCONVLMG_SA_BM_StatBonus'); Template.SetUIStatMarkup(class'XLocalizedData'.default.MobilityLabel, eStat_Mobility, class'X2Ability_SpartsSalvSA'.default.ADVCONVLMG_SA_BM_MOBILITY_BONUS); Template.RangeAccuracy = default.ADVCONVLMG_SA_BEAM_RANGE; Template.BaseDamage = default.ADVCONVLMG_SA_BEAM_BASEDAMAGE; Template.Aim = default.ADVCONVLMG_SA_BEAM_AIM; Template.CritChance = default.ADVCONVLMG_SA_BEAM_CRITCHANCE; Template.iClipSize = default.ADVCONVLMG_SA_BEAM_ICLIPSIZE; Template.iSoundRange = default.ADVCONVLMG_SA_BEAM_ISOUNDRANGE; Template.iEnvironmentDamage = default.ADVCONVLMG_SA_BEAM_IENVIRONMENTDAMAGE; Template.NumUpgradeSlots = default.ADVCONVLMG_SA_BEAM_UPGRADESLOTS; Template.bIsLargeWeapon = true; Template.InventorySlot = eInvSlot_PrimaryWeapon; Template.Abilities.AddItem('StandardShot'); Template.Abilities.AddItem('Overwatch'); Template.Abilities.AddItem('OverwatchShot'); Template.Abilities.AddItem('Reload'); Template.Abilities.AddItem('HotLoadAmmo'); // This all the resources; sounds, animations, models, physics, the works. Template.GameArchetype = "SalvCannonSA.GameData.WP_AdvCannon_CV"; Template.UIArmoryCameraPointTag = 'UIPawnLocation_WeaponUpgrade_Cannon'; Template.AddDefaultAttachment('Mag', "ConvCannon.Meshes.SM_ConvCannon_MagA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_MagA"); Template.AddDefaultAttachment('Reargrip', "ConvCannon.Meshes.SM_ConvCannon_ReargripA"/*REARGRIP INCLUDED IN TRIGGER IMAGE*/); Template.AddDefaultAttachment('Stock', "ConvCannon.Meshes.SM_ConvCannon_StockA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_StockA"); Template.AddDefaultAttachment('StockSupport', "ConvCannon.Meshes.SM_ConvCannon_StockA_Support"); Template.AddDefaultAttachment('Suppressor', "ConvCannon.Meshes.SM_ConvCannon_SuppressorA"); Template.AddDefaultAttachment('Trigger', "ConvCannon.Meshes.SM_ConvCannon_TriggerA", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_TriggerA"); Template.AddDefaultAttachment('Light', "ConvAttachments.Meshes.SM_ConvFlashLight", , "img:///UILibrary_SpartsSalvSA.ConvAdvCannon_Flashlight"); Template.iPhysicsImpulse = 5; Template.CreatorTemplateName = 'AdvCannon_SA_BM_Schematic'; // The schematic which creates this item Template.BaseItem = 'AdvCannon_SA_MG'; // Which item this will be upgraded from Template.CanBeBuilt = false; Template.bInfiniteItem = true; Template.DamageTypeTemplateName = 'Projectile_BeamXCom'; return Template; } It's entirely possible that there's some sort of problem with my Cone of Fire mod not being able to pull the weapon's range, but I have no idea how to fix this, because the gun seems to use its own custom range profiles. Link to comment Share on other sites More sharing options...
Recommended Posts