AntennaRange.cfg: Added isAntenna to the part prefab for all parts with ModuleLimitedDataTransmitters.
AntennaRange.cfg: Added isAntenna to the part prefab for all parts with ModuleLimitedDataTransmitters.

AntennaRelay.cs: Added a timer to prevent antennas from re-searching their nearest relay multiple times in a single transmission attempt.

Extensions.cs: Remove IsAntenna stuff because we want that to work without persistence data. Doesn't work yet.

ModuleLimitedDataTransmitter.cs:
* Changed DataRate to return a very tiny number if the antenna cannot transmit.
* Changed the transmission message to indictor if it is using a relay or not.
* Removed IsAntenna in favor of using the prefab... hopefully.

file:a/ARTools.cs -> file:b/ARTools.cs
--- a/ARTools.cs
+++ b/ARTools.cs
@@ -22,7 +22,7 @@
 	public static class Tools
 	{
 		private static ScreenMessage debugmsg = new ScreenMessage("", 2f, ScreenMessageStyle.UPPER_RIGHT);
-
+		// Function that posts messages to the screen and the log when DEBUG is defined.
 		[System.Diagnostics.Conditional("DEBUG")]
 		public static void PostDebugMessage(string Msg)
 		{

--- a/AntennaRange.cfg
+++ b/AntennaRange.cfg
@@ -1,50 +1,55 @@
-//

-// AntennaRange © 2013 toadicus

-// 

-// This work is licensed under the Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License. To view a

-// copy of this license, visit http://creativecommons.org/licenses/by-nc-sa/3.0/

-//

-// This software uses the ModuleManager library © 2013 ialdabaoth, used under a Creative Commons Attribution-ShareAlike

-// 3.0 Uported License.

-//

-// Specifications:

-// nominalRange:	The distance from Kerbin at which the antenna will perform exactly as prescribed by packetResourceCost

-// 					and packetSize.

-// maxPowerFactor:	The multiplier on packetResourceCost that defines the maximum power output of the antenna.  When the

-//					power cost exceeds packetResourceCost * maxPowerFactor, transmission will fail.

-// maxDataFactor:	The multipler on packetSize that defines the maximum data bandwidth of the antenna.

-// 

-

-@PART[longAntenna]

-{

-	@MODULE[ModuleDataTransmitter]

-	{

-		@name = ModuleLimitedDataTransmitter

-		nominalRange = 1500000

-		maxPowerFactor = 8

-		maxDataFactor = 4

-	}

-}

-

-@PART[mediumDishAntenna]

-{

-	@MODULE[ModuleDataTransmitter]

-	{

-		@name = ModuleLimitedDataTransmitter

-		nominalRange = 30000000

-		maxPowerFactor = 8

-		maxDataFactor = 4

-	}

-}

-

-@PART[commDish]

-{

-	@MODULE[ModuleDataTransmitter]

-	{

-		@name = ModuleLimitedDataTransmitter

-		nominalRange = 80000000000

-		maxPowerFactor = 8

-		maxDataFactor = 4

-	}

-}

+//
+// AntennaRange © 2013 toadicus
+// 
+// This work is licensed under the Creative Commons Attribution-NonCommercial-ShareAlike 3.0 Unported License. To view a
+// copy of this license, visit http://creativecommons.org/licenses/by-nc-sa/3.0/
+//
+// This software uses the ModuleManager library © 2013 ialdabaoth, used under a Creative Commons Attribution-ShareAlike
+// 3.0 Uported License.
+//
+// Specifications:
+// nominalRange:	The distance from Kerbin at which the antenna will perform exactly as prescribed by packetResourceCost
+// 					and packetSize.
+// maxPowerFactor:	The multiplier on packetResourceCost that defines the maximum power output of the antenna.  When the
+//					power cost exceeds packetResourceCost * maxPowerFactor, transmission will fail.
+// maxDataFactor:	The multipler on packetSize that defines the maximum data bandwidth of the antenna.
+// 
 
+@PART[longAntenna]
+{
+	@MODULE[ModuleDataTransmitter]
+	{
+		@name = ModuleLimitedDataTransmitter
+		nominalRange = 1500000
+		maxPowerFactor = 8
+		maxDataFactor = 4
+	}
+}
+
+@PART[mediumDishAntenna]
+{
+	@MODULE[ModuleDataTransmitter]
+	{
+		@name = ModuleLimitedDataTransmitter
+		nominalRange = 30000000
+		maxPowerFactor = 8
+		maxDataFactor = 4
+	}
+}
+
+@PART[commDish]
+{
+	@MODULE[ModuleDataTransmitter]
+	{
+		@name = ModuleLimitedDataTransmitter
+		nominalRange = 80000000000
+		maxPowerFactor = 8
+		maxDataFactor = 4
+	}
+}
+
+@PART[*]:HAS[MODULE[ModuleLimitedDataTransmitter]]:Final
+{
+	isAntenna = True
+}
+

--- a/AntennaRelay.cs
+++ b/AntennaRelay.cs
@@ -25,6 +25,9 @@
 	{
 		// We don't have a Bard, so we'll hide Kerbin here.
 		protected CelestialBody Kerbin;
+
+		protected System.Diagnostics.Stopwatch searchTimer;
+		protected long millisecondsBetweenSearches;
 
 		/// <summary>
 		/// Gets the parent Vessel.
@@ -113,6 +116,19 @@
 		/// <returns>The nearest relay or null, if no relays in range.</returns>
 		public IAntennaRelay FindNearestRelay()
 		{
+			if (this.searchTimer.IsRunning && this.searchTimer.ElapsedMilliseconds < this.millisecondsBetweenSearches)
+			{
+				return this.nearestRelay;
+			}
+
+			if (this.searchTimer.IsRunning)
+			{
+				this.searchTimer.Stop();
+				this.searchTimer.Reset();
+			}
+
+			this.searchTimer.Start();
+
 			// Set this relay as checked, so that we don't check it again.
 			this.relayChecked = true;
 
@@ -194,9 +210,8 @@
 		public override string ToString()
 		{
 			return string.Format(
-				"Antenna relay on vessel {0} (range to relay: {1}m)",
-				vessel,
-				Tools.MuMech_ToSI(transmitDistance)
+				"Antenna relay on vessel {0}.",
+				vessel
 			);
 		}
 
@@ -207,6 +222,9 @@
 		public AntennaRelay(Vessel v)
 		{
 			this.vessel = v;
+
+			this.searchTimer = new System.Diagnostics.Stopwatch();
+			this.millisecondsBetweenSearches = 5000;
 
 			// HACK: This might not be safe in all circumstances, but since AntennaRelays are not built until Start,
 			// we hope it is safe enough.

--- a/Extensions.cs
+++ b/Extensions.cs
@@ -117,13 +117,12 @@
 				// Loop through the ProtoPartModuleSnapshots in this Vessel
 				foreach (ProtoPartSnapshot pps in vessel.protoVessel.protoPartSnapshots)
 				{
-					ProtoPartModuleSnapshot ppms = pps.modules.FirstOrDefault(p => p.IsAntenna());
-					// If they are antennas...
-					if (ppms != null)
-					{
-						// ...add a new ProtoAntennaRelay wrapper to the list.
-						Transmitters.Add(new ProtoAntennaRelay(ppms, pps, vessel));
-					}
+					Transmitters.AddRange(
+						PartLoader.getPartInfoByName(pps.partName)
+						.partPrefab
+						.Modules
+						.OfType<IAntennaRelay>()
+					);
 				}
 			}
 
@@ -137,21 +136,6 @@
 			// Return the list of IAntennaRelays
 			return Transmitters;
 		}
-
-		// Returns true if this PartModule contains a True IsAntenna field, false otherwise.
-		public static bool IsAntenna (this PartModule module)
-		{
-			return module.Fields.GetValue<bool> ("IsAntenna");
-		}
-
-		// Returns true if this ProtoPartModuleSnapshot contains a persistent True IsAntenna field, false otherwise
-		public static bool IsAntenna(this ProtoPartModuleSnapshot protomodule)
-		{
-			bool result;
-
-			return Boolean.TryParse (protomodule.moduleValues.GetValue ("IsAntenna") ?? "False", out result)
-				? result : false;
-		}
 	}
 }
 

--- a/ModuleLimitedDataTransmitter.cs
+++ b/ModuleLimitedDataTransmitter.cs
@@ -41,10 +41,6 @@
 	 * */
 	public class ModuleLimitedDataTransmitter : ModuleDataTransmitter, IScienceDataTransmitter, IAntennaRelay
 	{
-		// Call this an antenna so that you don't have to.
-		[KSPField(isPersistant = true)]
-		protected bool IsAntenna;
-
 		// Stores the packetResourceCost as defined in the .cfg file.
 		protected float _basepacketResourceCost;
 
@@ -76,10 +72,6 @@
 		// The multipler on packetSize that defines the maximum data bandwidth of the antenna.
 		[KSPField(isPersistant = false)]
 		public float maxDataFactor;
-
-		// This field exists to get saved to the persistence file so that relays can be found on unloaded Vessels.
-		[KSPField(isPersistant = true)]
-		protected float ARmaxTransmitDistance;
 
 		/*
 		 * Properties
@@ -107,7 +99,7 @@
 		{
 			get
 			{
-				return this.ARmaxTransmitDistance;
+				return Mathf.Sqrt (this.maxPowerFactor) * this.nominalRange;
 			}
 		}
 
@@ -144,7 +136,15 @@
 			get
 			{
 				this.PreTransmit_SetPacketSize();
-				return this.packetSize;
+
+				if (this.CanTransmit())
+				{
+					return this.packetSize;
+				}
+				else
+				{
+					return float.Epsilon;
+				}
 			}
 		}
 
@@ -212,9 +212,6 @@
 		{
 			this.Fields.Load(node);
 			base.Fields.Load(node);
-
-			this.ARmaxTransmitDistance = Mathf.Sqrt (this.maxPowerFactor) * this.nominalRange;
-			this.IsAntenna = true;
 
 			base.OnLoad (node);
 
@@ -243,7 +240,7 @@
 		{
 			string ErrorText = string.Format (
 				"Unable to transmit: out of range!  Maximum range = {0}m; Current range = {1}m.",
-				Tools.MuMech_ToSI((double)this.ARmaxTransmitDistance, 2),
+				Tools.MuMech_ToSI((double)this.maxTransmitDistance, 2),
 				Tools.MuMech_ToSI((double)this.transmitDistance, 2)
 				);
 
@@ -289,7 +286,7 @@
 		{
 			string text = base.GetInfo();
 			text += "Nominal Range: " + Tools.MuMech_ToSI((double)this.nominalRange, 2) + "m\n";
-			text += "Maximum Range: " + Tools.MuMech_ToSI((double)this.ARmaxTransmitDistance, 2) + "m\n";
+			text += "Maximum Range: " + Tools.MuMech_ToSI((double)this.maxTransmitDistance, 2) + "m\n";
 			return text;
 		}
 
@@ -334,18 +331,20 @@
 
 			if (this.CanTransmit())
 			{
-				this.ErrorMsg.message = "Beginning transmission ";
+				string message;
+
+				message = "Beginning transmission ";
 
 				if (this.relay.nearestRelay == null)
 				{
-					this.ErrorMsg.message += "directly to Kerbin.";
+					message += "directly to Kerbin.";
 				}
 				else
 				{
-					this.ErrorMsg.message += "via relay " + this.relay.nearestRelay;
-				}
-
-				ScreenMessages.PostScreenMessage(this.ErrorMsg);
+					message += "via relay " + this.relay.nearestRelay;
+				}
+
+				ScreenMessages.PostScreenMessage(message, 4f, ScreenMessageStyle.UPPER_LEFT);
 
 				base.StartTransmission();
 			}
@@ -382,7 +381,7 @@
 				base.packetSize,
 				this._basepacketResourceCost,
 				base.packetResourceCost,
-				this.ARmaxTransmitDistance,
+				this.maxTransmitDistance,
 				this.transmitDistance,
 				this.nominalRange,
 				this.CanTransmit(),

--- a/ProtoAntennaRelay.cs
+++ b/ProtoAntennaRelay.cs
@@ -26,7 +26,10 @@
 	 * */
 	public class ProtoAntennaRelay : AntennaRelay, IAntennaRelay
 	{
+		// Stores the proto module.
 		protected ProtoPartModuleSnapshot protoModule;
+
+		// Stores the proto part, which seems silly because all we need is the name.
 		protected Part partPrefab;
 
 		/// <summary>