Exemple #1
0
 private void handleLocationEvent(LocationEvent @event)
 {
     systemName = @event.system;
     systemX    = @event.x;
     systemY    = @event.y;
     systemZ    = @event.z;
 }
        private void LocationCallback(LocationEvent obj)
        {
            SetValue(() => CurrentSystemName, obj.StarSystem);
            SetValue(() => CurrentSystemAddress, obj.SystemAddress);

            AddNavigationPoint(obj.Timestamp, obj.StarSystem, NavigationPointType.Current, null);
        }
        protected LocationEvent getLocationEventObject(MySql.Data.MySqlClient.MySqlDataReader reader)
        {
            DateTime      dt  = Database.fromUnix(Convert.ToInt64(reader["locTime"].ToString()));
            LocationEvent evt = new LocationEvent(int.Parse(reader["userID"].ToString()), dt, double.Parse(reader["lat"].ToString()), double.Parse(reader["lng"].ToString()));

            return(evt);
        }
Exemple #4
0
 private static void OnLocation(Message msg)
 {
     LocationEvent?.Invoke(new SystemMsgEventArgs()
     {
         msg = msg
     });
 }
Exemple #5
0
 public void AddOnLocationChangeListener(UnityAction <Location> listener)
 {
     if (onLocationChange == null)
     {
         onLocationChange = new LocationEvent();
     }
     onLocationChange.AddListener(listener);
 }
Exemple #6
0
 internal LocationEvent InvokeEvent(LocationEvent arg)
 {
     if (_api.ValidateEvent(arg))
     {
         Location?.Invoke(_api, arg);
     }
     return(arg);
 }
Exemple #7
0
 private bool eventLocation(LocationEvent theEvent)
 {
     updateCurrentSystem(theEvent.system);
     // Always update the current system with the current co-ordinates, just in case things have changed
     CurrentStarSystem.x = theEvent.x;
     CurrentStarSystem.y = theEvent.y;
     CurrentStarSystem.z = theEvent.z;
     return(true);
 }
Exemple #8
0
 private void handleLocationEvent(LocationEvent @event)
 {
     if (@event.timestamp > updateDat)
     {
         targetSystem = @event.systemname;
         updateDat    = @event.timestamp;
         writeRecord();
     }
 }
Exemple #9
0
 private void handleLocationEvent(LocationEvent @event)
 {
     // Set all of the information available from the event
     systemName    = @event.system;
     systemAddress = @event.systemAddress;
     systemX       = @event.x;
     systemY       = @event.y;
     systemZ       = @event.z;
     stationName   = @event.station;
     marketId      = @event.marketId;
 }
Exemple #10
0
        }); // 0=lose, 1=win

        #endregion

        #region Methods

        // Unity methods
        void Awake()
        {
#if FULLLOG
            MoreDebug.Log("singleton, nokeep.");
#endif
            // singleton
            exists = false;
            if (only == null)
            {
                // DontDestroyOnLoad (gameObject);
                only = this;
#if FULLLOG
                MoreDebug.Log("Singleton created. qqq");
#endif
            }
            else if (only != this)
            {
                MoreDebug.LogError("More than one level manager found.");
                Destroy(gameObject);
#if FULLLOG
                MoreDebug.Log("Duplicate singleton destroyed.");
#endif
            }
            exists = true;

            // local init

            // Check for a pregame manager
            if (PregameManager.only != null)   // Created but maybe not awake yet
            {
                Game = PregameManager.only;
            }
            // Check for a campaign manager
            if ((CampaignManager.count > 0) && (CampaignManager.campaign != null))
            {
                Campaign = CampaignManager.campaign;
            }
            // Create events
            if (OnBeginLevel == null)
            {
                OnBeginLevel = new UnityEvent();
            }
            if (OnEndLevel == null)
            {
                OnEndLevel = new UnityEvent();
            }
            if (OnGetLocation == null)
            {
                OnGetLocation = new LocationEvent();
            }

            // done with Awake()
        }
Exemple #11
0
        public void TestLocationAllegiance()
        {
            string       line   = @"{ ""timestamp"":""2018-12-09T18:39:32Z"", ""event"":""Location"", ""Docked"":false, ""StarSystem"":""Col 285 Sector SP-K b23-7"", ""SystemAddress"":16065459463649, ""StarPos"":[112.31250,13.46875,153.06250], ""SystemAllegiance"":"""", ""SystemEconomy"":""$economy_None;"", ""SystemEconomy_Localised"":""None"", ""SystemSecondEconomy"":""$economy_None;"", ""SystemSecondEconomy_Localised"":""None"", ""SystemGovernment"":""$government_None;"", ""SystemGovernment_Localised"":""None"", ""SystemSecurity"":""$GAlAXY_MAP_INFO_state_anarchy;"", ""SystemSecurity_Localised"":""Anarchy"", ""Population"":0, ""Body"":""Col 285 Sector SP-K b23-7 A"", ""BodyID"":1, ""BodyType"":""Star"" }";
            List <Event> events = JournalMonitor.ParseJournalEntry(line);

            Assert.AreEqual(1, events.Count);
            LocationEvent @event = (LocationEvent)events[0];

            Assert.IsNotNull(@event.raw);
            Assert.AreEqual("None", @event.Allegiance?.invariantName);
            Assert.AreEqual("$faction_None", @event.Allegiance?.edname);
        }
 private void LocationCallback(LocationEvent obj)
 {
     if (obj.Docked)
     {
         SetValue(() => DockingState, DockingStates.Docked);
         SetValue(() => CurrentStationname, obj.StationName);
         SetValue(() => CurrentStationMarketId, obj.MarketID);
     }
     else
     {
         SetValue(() => DockingState, DockingStates.Undocked);
         SetValue(() => CurrentStationname, "");
         SetValue(() => CurrentStationMarketId, 0);
     }
 }
Exemple #13
0
        public void TestLocationEventHandler()
        {
            string       line   = "{ \"timestamp\":\"2018-12-27T08:05:23Z\", \"event\":\"Location\", \"Docked\":true, \"MarketID\":3230448384, \"StationName\":\"Cleve Hub\", \"StationType\":\"Orbis\", \"StarSystem\":\"Eravate\", \"SystemAddress\":5856221467362, \"StarPos\":[-42.43750,-3.15625,59.65625], \"SystemAllegiance\":\"Federation\", \"SystemEconomy\":\"$economy_Agri;\", \"SystemEconomy_Localised\":\"Agriculture\", \"SystemSecondEconomy\":\"$economy_Industrial;\", \"SystemSecondEconomy_Localised\":\"Industrial\", \"SystemGovernment\":\"$government_Corporate;\", \"SystemGovernment_Localised\":\"Corporate\", \"SystemSecurity\":\"$SYSTEM_SECURITY_high;\", \"SystemSecurity_Localised\":\"High Security\", \"Population\":740380179, \"Body\":\"Cleve Hub\", \"BodyID\":48, \"BodyType\":\"Station\", \"Powers\":[ \"Zachary Hudson\" ], \"PowerplayState\":\"Exploited\", \"Factions\":[ { \"Name\":\"Eravate School of Commerce\", \"FactionState\":\"None\", \"Government\":\"Cooperative\", \"Influence\":0.086913, \"Allegiance\":\"Independent\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":91.840103 }, { \"Name\":\"Pilots Federation Local Branch\", \"FactionState\":\"None\", \"Government\":\"Democracy\", \"Influence\":0.000000, \"Allegiance\":\"PilotsFederation\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":42.790199 }, { \"Name\":\"Independent Eravate Free\", \"FactionState\":\"None\", \"Government\":\"Democracy\", \"Influence\":0.123876, \"Allegiance\":\"Independent\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":100.000000 }, { \"Name\":\"Eravate Network\", \"FactionState\":\"None\", \"Government\":\"Corporate\", \"Influence\":0.036963, \"Allegiance\":\"Federation\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":100.000000 }, { \"Name\":\"Traditional Eravate Autocracy\", \"FactionState\":\"None\", \"Government\":\"Dictatorship\", \"Influence\":0.064935, \"Allegiance\":\"Independent\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":100.000000 }, { \"Name\":\"Eravate Life Services\", \"FactionState\":\"None\", \"Government\":\"Corporate\", \"Influence\":0.095904, \"Allegiance\":\"Independent\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":100.000000 }, { \"Name\":\"Official Eravate Flag\", \"FactionState\":\"None\", \"Government\":\"Dictatorship\", \"Influence\":0.179820, \"Allegiance\":\"Independent\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"MyReputation\":100.000000 }, { \"Name\":\"Adle's Armada\", \"FactionState\":\"None\", \"Government\":\"Corporate\", \"Influence\":0.411588, \"Allegiance\":\"Federation\", \"Happiness\":\"$Faction_HappinessBand2;\", \"Happiness_Localised\":\"Happy\", \"SquadronFaction\":true, \"HappiestSystem\":true, \"HomeSystem\":true, \"MyReputation\":100.000000, \"PendingStates\":[ { \"State\":\"Boom\", \"Trend\":0 } ] } ], \"SystemFaction\":{ \"Name\":\"Adle's Armada\", \"FactionState\":\"None\" } }";
            List <Event> events = JournalMonitor.ParseJournalEntry(line);

            Assert.AreEqual(1, events.Count);
            LocationEvent @event = (LocationEvent)events[0];

            Assert.IsNotNull(@event);
            Assert.IsInstanceOfType(@event, typeof(LocationEvent));

            PrivateObject privateObject = new PrivateObject(Eddi.EDDI.Instance);
            var           result        = (bool)privateObject.Invoke("eventLocation", new object[] { @event });

            Assert.IsTrue(result);
        }
Exemple #14
0
        private bool eventLocation(LocationEvent theEvent)
        {
            updateCurrentSystem(theEvent.system);
            // Always update the current system with the current co-ordinates, just in case things have changed
            CurrentStarSystem.x = theEvent.x;
            CurrentStarSystem.y = theEvent.y;
            CurrentStarSystem.z = theEvent.z;

            if (theEvent.docked == true)
            {
                // In this case body === station

                if (CurrentStation != null && CurrentStation.name == theEvent.body)
                {
                    // We are already at this station; nothing to do
                    Logging.Debug("Already at station " + theEvent.body);
                    return(false);
                }
                // Update the station
                Logging.Debug("Now at station " + theEvent.body);
                Station station = CurrentStarSystem.stations.Find(s => s.name == theEvent.body);
                if (station == null)
                {
                    // This station is unknown to us, might not be in EDDB or we might not have connectivity.  Use a placeholder
                    station            = new Station();
                    station.name       = theEvent.body;
                    station.systemname = theEvent.system;
                }

                // Information from the event might be more current than that from EDDB so use it in preference
                station.state      = theEvent.factionstate;
                station.faction    = theEvent.faction;
                station.government = theEvent.government;
                station.allegiance = theEvent.allegiance;

                CurrentStation = station;

                // Now call refreshProfile() to obtain the outfitting and commodity information
                refreshProfile();
            }

            return(true);
        }
        private async void TravelOnLocationAsync(object sender, LocationEvent e)
        {
            var request = StartRequest();

            if (e.Factions != null && e.Factions.Length > 0)
            {
                foreach (var faction in e.Factions)
                {
                    request.AddCommand(new SetCommanderReputationMinorFaction(faction.Name, faction.MyReputation));
                }
            }

            request.AddCommand(new SetCommanderTravelLocation(e.StarSystem)
            {
                Station = e.StationName, MarketId = e.MarketId
            });

            await request.SendAsync()
            .ConfigureAwait(false);
        }
Exemple #16
0
        /// <summary>
        /// 事件模型
        /// </summary>
        /// <param name="xml"></param>
        /// <returns></returns>
        private EventBase GetEventModel(XmlUtils xml)
        {
            string    eventType = xml.GetValue("/xml/Event").ToLower();
            EventBase message   = null;

            switch (eventType)
            {
            case "unsubscribe":
                message = new UnsubscribeEvent();
                break;

            case "subscribe":
                message = new SubscribeEvent();
                break;

            case "scan":
                message = new ScanEvent();
                break;

            case "location":
                message = new LocationEvent();
                break;

            case "click":
                message = new ClickEvent();
                break;

            case "view":
                message = new ViewEvent();
                break;

            default:
                return(null);
            }

            return(message);
        }
Exemple #17
0
        private string prepareEventData(Event theEvent)
        {
            // Prep transient game state info (metadata) per https://www.edsm.net/en/api-journal-v1.
            // Unpackage the event, add transient game state info as applicable, then repackage and send the event
            IDictionary <string, object> eventObject = Deserializtion.DeserializeData(theEvent.raw);
            string eventType = JsonParsing.getString(eventObject, "event");

            if (ignoredEvents.Contains(eventType) || theEvent.raw == null)
            {
                return(null);
            }

            // Add metadata from events
            switch (eventType)
            {
            case "LoadGame":
            {
                eventObject.Add("_systemAddress", null);
                eventObject.Add("_systemName", null);
                eventObject.Add("_systemCoordinates", null);
                eventObject.Add("_marketId", null);
                eventObject.Add("_stationName", null);
                break;
            }

            case "SetUserShipName":
            {
                ShipRenamedEvent shipRenamedEvent = (ShipRenamedEvent)theEvent;
                eventObject.Add("_shipId", shipRenamedEvent.shipid);
                break;
            }

            case "ShipyardBuy":
            {
                eventObject.Add("_shipId", null);
                break;
            }

            case "ShipyardSwap":
            {
                ShipSwappedEvent shipSwappedEvent = (ShipSwappedEvent)theEvent;
                eventObject.Add("_shipId", shipSwappedEvent.shipid);
                break;
            }

            case "Loadout":
            {
                ShipLoadoutEvent shipLoadoutEvent = (ShipLoadoutEvent)theEvent;
                eventObject.Add("_shipId", shipLoadoutEvent.shipid);
                break;
            }

            case "Undocked":
            {
                eventObject.Add("_marketId", null);
                eventObject.Add("_stationName", null);
                break;
            }

            case "Location":
            {
                LocationEvent locationEvent = (LocationEvent)theEvent;
                eventObject.Add("_systemAddress", null);         // We don't collect this info yet
                eventObject.Add("_systemName", locationEvent.system);
                List <decimal?> _systemCoordinates = new List <decimal?>
                {
                    locationEvent.x,
                    locationEvent.y,
                    locationEvent.z
                };
                eventObject.Add("_systemCoordinates", _systemCoordinates);
                eventObject.Add("_marketId", null);         // We don't collect this info yet
                eventObject.Add("_stationName", locationEvent.station);
                break;
            }

            case "FSDJump":
            {
                JumpedEvent jumpedEvent = (JumpedEvent)theEvent;
                eventObject.Add("_systemAddress", null);         // We don't collect this info yet
                eventObject.Add("_systemName", jumpedEvent.system);
                List <decimal?> _systemCoordinates = new List <decimal?>
                {
                    jumpedEvent.x,
                    jumpedEvent.y,
                    jumpedEvent.z
                };
                eventObject.Add("_systemCoordinates", _systemCoordinates);
                break;
            }

            case "Docked":
            {
                DockedEvent dockedEvent = (DockedEvent)theEvent;
                eventObject.Add("_systemAddress", null);         // We don't collect this info yet
                eventObject.Add("_systemName", dockedEvent.system);
                eventObject.Add("_systemCoordinates", null);
                eventObject.Add("_marketId", null);         // We don't collect this info yet
                eventObject.Add("_stationName", dockedEvent.station);
                break;
            }
            }

            // Supplement with metadata from the tracked game state, as applicable
            if (EDDI.Instance.CurrentStarSystem != null)
            {
                if (!eventObject.ContainsKey("_systemAddress") && !eventObject.ContainsKey("SystemAddress"))
                {
                    eventObject.Add("_systemAddress", null); // We don't collect this info yet
                }
                if (!eventObject.ContainsKey("_systemName") && !eventObject.ContainsKey("SystemName"))
                {
                    eventObject.Add("_systemName", EDDI.Instance.CurrentStarSystem.name);
                }
                if (!eventObject.ContainsKey("_systemCoordinates") && !eventObject.ContainsKey("StarPos"))
                {
                    List <decimal?> _coordinates = new List <decimal?>
                    {
                        EDDI.Instance.CurrentStarSystem.x,
                        EDDI.Instance.CurrentStarSystem.y,
                        EDDI.Instance.CurrentStarSystem.z
                    };
                    eventObject.Add("_systemCoordinates", _coordinates);
                }
            }
            if (EDDI.Instance.CurrentStation != null)
            {
                if (!eventObject.ContainsKey("_marketId") && !eventObject.ContainsKey("MarketID"))
                {
                    eventObject.Add("_marketId", null); // We don't collect this info yet
                }
                if (!eventObject.ContainsKey("_stationName") && !eventObject.ContainsKey("StationName"))
                {
                    eventObject.Add("_stationName", EDDI.Instance.CurrentStation.name);
                }
            }
            if (EDDI.Instance.CurrentShip != null && !eventObject.ContainsKey("ShipId") && !eventObject.ContainsKey("_shipId"))
            {
                eventObject.Add("_shipId", EDDI.Instance.CurrentShip.LocalId);
            }

            return(JsonConvert.SerializeObject(eventObject).Normalize());
        }
Exemple #18
0
        /// <summary>
        /// 初始化微信消息处理事件
        /// </summary>
        private void InitEventsHandle()
        {
            #region 普通消息
            //文本消息
            handlerList.Add(MessageType.Text, ReceiveEventType.None, (data) =>
            {
                ReceiveTextMessage?.Invoke(data.ConvertBodyTo <TextMessage>(), Replier.Create(data));
            });

            //图片消息
            handlerList.Add(MessageType.Image, ReceiveEventType.None, (data) =>
            {
                ReceiveImageMessage?.Invoke(data.ConvertBodyTo <ImageMessage>(), Replier.Create(data));
            });

            //语音消息
            handlerList.Add(MessageType.Voice, ReceiveEventType.None, (data) =>
            {
                ReceiveVoiceMessage?.Invoke(data.ConvertBodyTo <VoiceMessage>(), Replier.Create(data));
            });

            //视频消息
            handlerList.Add(MessageType.Video, ReceiveEventType.None, (data) =>
            {
                ReceiveVideoMessage?.Invoke(data.ConvertBodyTo <VideoMessage>(), Replier.Create(data));
            });

            //小视频消息
            handlerList.Add(MessageType.ShortVideo, ReceiveEventType.None, (data) =>
            {
                ReceiveShortVideoMessage?.Invoke(data.ConvertBodyTo <ShortVideoMessage>(), Replier.Create(data));
            });

            //地理位置消息
            handlerList.Add(MessageType.Location, ReceiveEventType.None, (data) =>
            {
                ReceiveLocationMessage?.Invoke(data.ConvertBodyTo <LocationMessage>(), Replier.Create(data));
            });

            //链接消息
            handlerList.Add(MessageType.Link, ReceiveEventType.None, (data) =>
            {
                ReceiveLinkMessage?.Invoke(data.ConvertBodyTo <LinkMessage>(), Replier.Create(data));
            });
            #endregion

            #region 事件消息
            //关注事件
            handlerList.Add(MessageType.Event, ReceiveEventType.Subscribe, (data) =>
            {
                var _event = data.ConvertBodyTo <ScanEventArgs>();
                if (string.IsNullOrEmpty(_event.EventKey))
                {
                    SubscribeEvent?.Invoke(_event, Replier.Create(data));
                }
                else
                {
                    _event.EventKey = _event.EventKey.Substring("qrscene_".Length);
                    ScanEvent?.Invoke(_event, Replier.Create(data));
                }
            });

            //取消关注事件
            handlerList.Add(MessageType.Event, ReceiveEventType.UnSubscribe, (data) =>
            {
                PassReply(data);
                UnSubscribeEvent?.Invoke(data.ConvertBodyTo <EventArgsBase>());
            });

            //扫描带参数二维码事件
            handlerList.Add(MessageType.Event, ReceiveEventType.Scan, (data) =>
            {
                ScanEvent?.Invoke(data.ConvertBodyTo <ScanEventArgs>(), Replier.Create(data));
            });

            //上报地理位置事件
            handlerList.Add(MessageType.Event, ReceiveEventType.Location, (data) =>
            {
                PassReply(data);
                LocationEvent?.Invoke(data.ConvertBodyTo <LocationEventArgs>());
            });

            //点击菜单拉取消息事件
            handlerList.Add(MessageType.Event, ReceiveEventType.Click, (data) =>
            {
                MenuClickEvent?.Invoke(data.ConvertBodyTo <WithKeyEventArgs>(), Replier.Create(data));
            });

            //点击菜单跳转链接事件
            handlerList.Add(MessageType.Event, ReceiveEventType.View, (data) =>
            {
                PassReply(data);
                ViewEvent?.Invoke(data.ConvertBodyTo <WithKeyEventArgs>());
            });

            //群发任务完成事件
            handlerList.Add(MessageType.Event, ReceiveEventType.MessageEndJobFinish, (data) =>
            {
                PassReply(data);
                MessageEndJobFinishEvent?.Invoke(data.ConvertBodyTo <MessageEndJobFinishEventArgs>());
            });

            //模板消息发送完成事件
            handlerList.Add(MessageType.Event, ReceiveEventType.TemplateSendJobFinish, (data) =>
            {
                PassReply(data);
                TemplateSendJobFinishEvent?.Invoke(data.ConvertBodyTo <TemplateSendJobFinishEventArgs>());
            });

            //买单事件推送
            handlerList.Add(MessageType.Event, ReceiveEventType.user_pay_from_pay_cell, (data) =>
            {
                PassReply(data);
                UserPayFromPayCellEvent?.Invoke(data.ConvertBodyTo <UserPayFromPayCellEventArgs>(), Replier.Create(data));
            });

            //卡券审核事件
            handlerList.Add(MessageType.Event, ReceiveEventType.card_pass_check, (data) =>
            {
                PassReply(data);
                CardPassCheckEvent?.Invoke(data.ConvertBodyTo <CardPassCheckEventArgs>(), Replier.Create(data));
            });

            //卡券领取事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_get_card, (data) =>
            {
                PassReply(data);
                UserGetCardEvent?.Invoke(data.ConvertBodyTo <UserGetCardEventArgs>(), Replier.Create(data));
            });

            //卡券转赠事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_gifting_card, (data) =>
            {
                PassReply(data);
                UserGiftingCardEvent?.Invoke(data.ConvertBodyTo <UserGiftingCardEventArgs>(), Replier.Create(data));
            });

            //卡券删除事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_del_card, (data) =>
            {
                PassReply(data);
                UserDelCardEvent?.Invoke(data.ConvertBodyTo <UserDelCardEventArgs>(), Replier.Create(data));
            });

            //卡券核销事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_consume_card, (data) =>
            {
                PassReply(data);
                UserConsumeCardEvent?.Invoke(data.ConvertBodyTo <UserConsumeCardEventArgs>(), Replier.Create(data));
            });

            //进入会员卡事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_view_card, (data) =>
            {
                PassReply(data);
                UserViewCardEvent?.Invoke(data.ConvertBodyTo <UserViewCardEventArgs>(), Replier.Create(data));
            });

            //从卡券进入公众号会话事件
            handlerList.Add(MessageType.Event, ReceiveEventType.user_enter_session_from_card, (data) =>
            {
                PassReply(data);
                UserEnterSessionFromCardEvent?.Invoke(data.ConvertBodyTo <UserEnterSessionFromCardEventArgs>(), Replier.Create(data));
            });

            //会员卡内容更新事件
            handlerList.Add(MessageType.Event, ReceiveEventType.update_member_card, (data) =>
            {
                PassReply(data);
                UpdateMemberCardEvent?.Invoke(data.ConvertBodyTo <UpdateMemberCardEventArgs>(), Replier.Create(data));
            });

            //会员卡激活事件推送
            handlerList.Add(MessageType.Event, ReceiveEventType.submit_membercard_user_info, (data) =>
            {
                PassReply(data);
                SubmitMemberCardUserInfoEvent?.Invoke(data.ConvertBodyTo <SubmitMemberCardUserInfoEventArgs>(), Replier.Create(data));
            });

            //库存报警事件
            handlerList.Add(MessageType.Event, ReceiveEventType.card_sku_remind, (data) =>
            {
                PassReply(data);
                CardSkuRemindEvent?.Invoke(data.ConvertBodyTo <CardSkuRemindEventArgs>(), Replier.Create(data));
            });

            //券点流水详情事件
            handlerList.Add(MessageType.Event, ReceiveEventType.card_pay_order, (data) =>
            {
                PassReply(data);
                CardPayOrderEvent?.Invoke(data.ConvertBodyTo <CardPayOrderEventArgs>(), Replier.Create(data));
            });

            #endregion
        }
 public void Load(LocationEvent fun)
 {
     this.onEvent = fun;
     this.StartCoroutine(LoadGps());
 }
Exemple #20
0
        public void TestJournalLocationEvent()
        {
            string line = @"{
	""timestamp"": ""2018-08-12T02: 52: 13Z"",
	""event"": ""Location"",
	""Docked"": true,
	""MarketID"": 3223343616,
	""StationName"": ""RayGateway"",
	""StationType"": ""Coriolis"",
	""StarSystem"": ""Diaguandri"",
	""SystemAddress"": 670417429889,
	""StarPos"": [-41.06250,
	-62.15625,
	-103.25000],
	""SystemAllegiance"": ""Independent"",
	""SystemEconomy"": ""$economy_HighTech;"",
	""SystemEconomy_Localised"": ""HighTech"",
	""SystemSecondEconomy"": ""$economy_Refinery;"",
	""SystemSecondEconomy_Localised"": ""Refinery"",
	""SystemGovernment"": ""$government_Democracy;"",
	""SystemGovernment_Localised"": ""Democracy"",
	""SystemSecurity"": ""$SYSTEM_SECURITY_medium;"",
	""SystemSecurity_Localised"": ""MediumSecurity"",
	""Population"": 10303479,
	""Body"": ""RayGateway"",
	""BodyID"": 32,
	""BodyType"": ""Station"",
	""Factions"": [{
		""Name"": ""DiaguandriInterstellar"",
		""FactionState"": ""None"",
		""Government"": ""Corporate"",
		""Influence"": 0.090000,
		""Allegiance"": ""Independent"",
		""RecoveringStates"": [{
			""State"": ""Boom"",
			""Trend"": 0
		}]
	},
	{
		""Name"": ""People'sMET20Liberals"",
		""FactionState"": ""Boom"",
		""Government"": ""Democracy"",
		""Influence"": 0.206000,
		""Allegiance"": ""Federation""
	},
	{
		""Name"": ""PilotsFederationLocalBranch"",
		""FactionState"": ""None"",
		""Government"": ""Democracy"",
		""Influence"": 0.000000,
		""Allegiance"": ""PilotsFederation""
	},
	{
		""Name"": ""NaturalDiaguandriRegulatoryState"",
		""FactionState"": ""Boom"",
		""Government"": ""Dictatorship"",
		""Influence"": 0.072000,
		""Allegiance"": ""Independent""
	},
	{
		""Name"": ""CartelofDiaguandri"",
		""FactionState"": ""Bust"",
		""Government"": ""Anarchy"",
		""Influence"": 0.121000,
		""Allegiance"": ""Independent"",
		""PendingStates"": [{
			""State"": ""Boom"",
			""Trend"": 1
		},
		{
			""State"": ""CivilUnrest"",
			""Trend"": -1
		}]
	},
	{
		""Name"": ""RevolutionaryPartyofDiaguandri"",
		""FactionState"": ""Boom"",
		""Government"": ""Democracy"",
		""Influence"": 0.181000,
		""Allegiance"": ""Federation"",
		""PendingStates"": [{
			""State"": ""Bust"",
			""Trend"": 0
		}]
	},
	{
		""Name"": ""TheBrotherhoodoftheDarkCircle"",
		""FactionState"": ""Boom"",
		""Government"": ""Corporate"",
		""Influence"": 0.086000,
		""Allegiance"": ""Independent""
	},
	{
		""Name"": ""EXO"",
		""FactionState"": ""None"",
		""Government"": ""Democracy"",
		""Influence"": 0.244000,
		""Allegiance"": ""Independent"",
		""PendingStates"": [{
			""State"": ""Boom"",
			""Trend"": 1
		}]
	}],
	""SystemFaction"": ""EXO""
}";

            List <Event> events = JournalMonitor.ParseJournalEntry(line);

            Assert.IsTrue(events.Count == 1);
            LocationEvent @event = (LocationEvent)events[0];

            Assert.AreEqual("Independent", @event.Allegiance.invariantName);
            Assert.AreEqual("RayGateway", @event.body);
            Assert.AreEqual("Station", @event.bodytype);
            Assert.AreEqual(true, @event.docked);
            Assert.AreEqual("High Tech", @event.economy);
            Assert.AreEqual("Refinery", @event.economy2);
            Assert.AreEqual("EXO", @event.faction);
            Assert.AreEqual("Democracy", @event.government);
            Assert.IsNull(@event.latitude);
            Assert.IsNull(@event.longitude);
            Assert.AreEqual(3223343616, @event.marketId);
            Assert.AreEqual(10303479, @event.population);
            Assert.AreEqual("Medium", @event.security);
            Assert.AreEqual("RayGateway", @event.station);
            Assert.AreEqual("Coriolis", @event.stationtype);
            Assert.AreEqual("Diaguandri", @event.system);
            Assert.AreEqual(670417429889, @event.systemAddress);
            Assert.AreEqual(-41.06250M, @event.x);
            Assert.AreEqual(-62.15625M, @event.y);
            Assert.AreEqual(-103.25000M, @event.z);
        }
        public static Event ParseJournalEntry(string line)
        {
            try
            {
                Match match = JsonRegex.Match(line);
                if (match.Success)
                {
                    IDictionary<string, object> data = Deserializtion.DeserializeData(line);

                    // Every event has a timestamp field
                    DateTime timestamp = DateTime.Now;
                    if (data.ContainsKey("timestamp"))
                    {
                        if (data["timestamp"] is DateTime)
                        {
                            timestamp = ((DateTime)data["timestamp"]).ToUniversalTime();
                        }
                        else
                        {
                            timestamp = DateTime.Parse((string)data["timestamp"]).ToUniversalTime();
                        }
                    }
                    else
                    {
                        Logging.Warn("Event without timestamp; using current time");
                    }

                    // Every event has an event field
                    if (!data.ContainsKey("event"))
                    {
                        Logging.Warn("Event without event field!");
                        return null;
                    }

                    bool handled = false;

                    Event journalEvent = null;
                    string edType = (string)data["event"];
                    switch (edType)
                    {
                        case "Docked":
                            {
                                object val;
                                data.TryGetValue("StarSystem", out val);
                                string systemName = (string)val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                data.TryGetValue("Allegiance", out val);
                                // FD sends "" rather than null; fix that here
                                if (((string)val) == "") { val = null; }
                                Superpower allegiance = Superpower.From((string)val);
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;
                                data.TryGetValue("FactionState", out val);
                                State factionState = State.FromEDName((string)val);
                                data.TryGetValue("Economy", out val);
                                Economy economy = Economy.FromEDName((string)val);
                                data.TryGetValue("Government", out val);
                                Government government = Government.FromEDName((string)val);
                                data.TryGetValue("Security", out val);
                                SecurityLevel securityLevel = SecurityLevel.FromEDName((string)val);
                                journalEvent = new DockedEvent(timestamp, systemName, stationName, allegiance, faction, factionState, economy, government, securityLevel);
                            }
                            handled = true;
                            break;
                        case "Undocked":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                journalEvent = new UndockedEvent(timestamp, stationName);
                            }
                            handled = true;
                            break;
                        case "Touchdown":
                            {
                                object val;
                                data.TryGetValue("Latitude", out val);
                                decimal latitude = (decimal)(double)val;
                                data.TryGetValue("Longitude", out val);
                                decimal longitude = (decimal)(double)val;
                                journalEvent = new TouchdownEvent(timestamp, longitude, latitude);
                            }
                            handled = true;
                            break;
                        case "Liftoff":
                            {
                                object val;
                                data.TryGetValue("Latitude", out val);
                                decimal latitude = (decimal)(double)val;
                                data.TryGetValue("Longitude", out val);
                                decimal longitude = (decimal)(double)val;
                                journalEvent = new LiftoffEvent(timestamp, longitude, latitude);
                            }
                            handled = true;
                            break;
                        case "SupercruiseEntry":
                            {
                                object val;
                                data.TryGetValue("StarSystem", out val);
                                string system = (string)val;
                                journalEvent = new EnteredSupercruiseEvent(timestamp, system);
                            }
                            handled = true;
                            break;
                        case "SupercruiseExit":
                            {
                                object val;
                                data.TryGetValue("StarSystem", out val);
                                string system = (string)val;
                                data.TryGetValue("Body", out val);
                                string body = (string)val;
                                data.TryGetValue("BodyType", out val);
                                string bodyType = (string)val;
                                journalEvent = new EnteredNormalSpaceEvent(timestamp, system, body, bodyType);
                            }
                            handled = true;
                            break;
                        case "FSDJump":
                            {
                                object val;

                                data.TryGetValue("StarSystem", out val);
                                string systemName = (string)val;
                                data.TryGetValue("StarPos", out val);
                                List<object> starPos = (List<object>)val;
                                decimal x = Math.Round((decimal)((double)starPos[0]) * 32) / (decimal)32.0;
                                decimal y = Math.Round((decimal)((double)starPos[1]) * 32) / (decimal)32.0;
                                decimal z = Math.Round((decimal)((double)starPos[2]) * 32) / (decimal)32.0;

                                data.TryGetValue("FuelUsed", out val);
                                decimal fuelUsed = (decimal)(double)val;

                                data.TryGetValue("FuelLevel", out val);
                                decimal fuelRemaining = (decimal)(double)val;

                                data.TryGetValue("Allegiance", out val);
                                // FD sends "" rather than null; fix that here
                                if (((string)val) == "") { val = null; }
                                Superpower allegiance = Superpower.From((string)val);
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;
                                data.TryGetValue("FactionState", out val);
                                State factionState = State.FromEDName((string)val);
                                data.TryGetValue("Economy", out val);
                                Economy economy = Economy.FromEDName((string)val);
                                data.TryGetValue("Government", out val);
                                Government government = Government.FromEDName((string)val);
                                data.TryGetValue("Security", out val);
                                SecurityLevel security = SecurityLevel.FromEDName((string)val);

                                journalEvent = new JumpedEvent(timestamp, systemName, x, y, z, fuelUsed, fuelRemaining, allegiance, faction, factionState, economy, government, security);
                            }
                            handled = true;
                            break;
                        case "Location":
                            {
                                object val;

                                data.TryGetValue("StarSystem", out val);
                                string systemName = (string)val;

                                data.TryGetValue("StarPos", out val);
                                List<object> starPos = (List<object>)val;
                                decimal x = Math.Round((decimal)((double)starPos[0]) * 32) / (decimal)32.0;
                                decimal y = Math.Round((decimal)((double)starPos[1]) * 32) / (decimal)32.0;
                                decimal z = Math.Round((decimal)((double)starPos[2]) * 32) / (decimal)32.0;

                                data.TryGetValue("Body", out val);
                                string body = (string)val;
                                data.TryGetValue("BodyType", out val);
                                string bodyType = (string)val;
                                data.TryGetValue("Docked", out val);
                                bool docked = (bool)val;
                                data.TryGetValue("Allegiance", out val);
                                // FD sends "" rather than null; fix that here
                                if (((string)val) == "") { val = null; }
                                Superpower allegiance = Superpower.From((string)val);
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;
                                data.TryGetValue("FactionState", out val);
                                State factionState = State.FromEDName((string)val);
                                data.TryGetValue("Economy", out val);
                                Economy economy = Economy.FromEDName((string)val);
                                data.TryGetValue("Government", out val);
                                Government government = Government.FromEDName((string)val);
                                data.TryGetValue("Security", out val);
                                SecurityLevel security = SecurityLevel.FromEDName((string)val);


                                journalEvent = new LocationEvent(timestamp, systemName, x, y, z, body, bodyType, docked, allegiance, faction, factionState, economy, government, security);
                            }
                            handled = true;
                            break;
                        case "Bounty":
                            {
                                object val;

                                data.TryGetValue("Target", out val);
                                string target = (string)val;

                                data.TryGetValue("VictimFaction", out val);
                                string victimFaction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(victimFaction);
                                victimFaction = superpowerFaction != null ? superpowerFaction.name : victimFaction;

                                long reward;
                                List<Reward> rewards = new List<Reward>();

                                if (data.ContainsKey("Reward"))
                                {
                                    // Old-style
                                    data.TryGetValue("Reward", out val);
                                    reward = (long)val;
                                    if (reward == 0)
                                    {
                                        // 0-credit reward; ignore
                                        break;
                                    }
                                    data.TryGetValue("Faction", out val);
                                    string factionName = (string)val;
                                    // Might be a superpower...
                                    superpowerFaction = Superpower.From(factionName);
                                    factionName = superpowerFaction != null ? superpowerFaction.name : factionName;
                                    rewards.Add(new Reward(factionName, reward));
                                }
                                else
                                {
                                    data.TryGetValue("TotalReward", out val);
                                    reward = (long)val;

                                    // Obtain list of rewards
                                    data.TryGetValue("Rewards", out val);
                                    List<object> rewardsData = (List<object>)val;
                                    if (rewardsData != null)
                                    {
                                        foreach (Dictionary<string, object> rewardData in rewardsData)
                                        {
                                            rewardData.TryGetValue("Faction", out val);
                                            string factionName = (string)val;
                                            // Might be a superpower...
                                            superpowerFaction = Superpower.From(factionName);
                                            factionName = superpowerFaction != null ? superpowerFaction.name : factionName;

                                            rewardData.TryGetValue("Reward", out val);
                                            long factionReward = (long)val;

                                            rewards.Add(new Reward(factionName, factionReward));
                                        }
                                    }
                                }

                                journalEvent = new BountyAwardedEvent(timestamp, target, victimFaction, reward, rewards);
                            }
                            handled = true;
                            break;
                        case "CapShipBond":
                        case "FactionKillBond":
                            {
                                object val;
                                data.TryGetValue("Faction", out val);
                                string awardingFaction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(awardingFaction);
                                awardingFaction = superpowerFaction != null ? superpowerFaction.name : awardingFaction;
                                data.TryGetValue("Reward", out val);
                                long reward = (long)val;
                                data.TryGetValue("VictimFaction", out val);
                                string victimFaction = (string)val;
                                journalEvent = new BondAwardedEvent(timestamp, awardingFaction, victimFaction, reward);
                            }
                            handled = true;
                            break;
                        case "CommitCrime":
                            {
                                object val;
                                data.TryGetValue("CrimeType", out val);
                                string crimetype = (string)val;
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;
                                data.TryGetValue("Victim", out val);
                                string victim = (string)val;
                                // Might be a fine or a bounty
                                if (data.ContainsKey("Fine"))
                                {
                                    data.TryGetValue("Fine", out val);
                                    long fine = (long)val;
                                    journalEvent = new FineIncurredEvent(timestamp, crimetype, faction, victim, fine);
                                }
                                else
                                {
                                    data.TryGetValue("Bounty", out val);
                                    long bounty = (long)val;
                                    journalEvent = new BountyIncurredEvent(timestamp, crimetype, faction, victim, bounty);
                                }
                            }
                            handled = true;
                            break;
                        case "Promotion":
                            {
                                object val;
                                if (data.ContainsKey("Combat"))
                                {
                                    data.TryGetValue("Combat", out val);
                                    CombatRating rating = CombatRating.FromRank((int)(long)val);
                                    journalEvent = new CombatPromotionEvent(timestamp, rating);
                                    handled = true;
                                }
                                else if (data.ContainsKey("Trade"))
                                {
                                    data.TryGetValue("Trade", out val);
                                    TradeRating rating = TradeRating.FromRank((int)(long)val);
                                    journalEvent = new TradePromotionEvent(timestamp, rating);
                                    handled = true;
                                }
                                else if (data.ContainsKey("Explore"))
                                {
                                    data.TryGetValue("Explore", out val);
                                    ExplorationRating rating = ExplorationRating.FromRank((int)(long)val);
                                    journalEvent = new ExplorationPromotionEvent(timestamp, rating);
                                    handled = true;
                                }
                            }
                            break;
                        case "CollectCargo":
                            {
                                object val;
                                data.TryGetValue("Type", out val);
                                string commodityName = (string)val;
                                Commodity commodity = CommodityDefinitions.FromName(commodityName);
                                if (commodity == null)
                                {
                                    Logging.Error("Failed to map collectcargo type " + commodityName + " to commodity");
                                }
                                data.TryGetValue("Stolen", out val);
                                bool stolen = (bool)val;
                                journalEvent = new CommodityCollectedEvent(timestamp, commodity, stolen);
                                handled = true;
                            }
                            handled = true;
                            break;
                        case "EjectCargo":
                            {
                                object val;
                                data.TryGetValue("Type", out val);
                                string commodityName = (string)val;
                                Commodity commodity = CommodityDefinitions.FromName(commodityName);
                                if (commodity == null)
                                {
                                    Logging.Error("Failed to map ejectcargo type " + commodityName + " to commodity");
                                }
                                string cargo = (string)val;
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                data.TryGetValue("Abandoned", out val);
                                bool abandoned = (bool)val;
                                journalEvent = new CommodityEjectedEvent(timestamp, commodity, amount, abandoned);
                                handled = true;
                            }
                            handled = true;
                            break;
                        case "CockpitBreached":
                            journalEvent = new CockpitBreachedEvent(timestamp);
                            handled = true;
                            break;
                        case "Scan":
                            {
                                object val;
                                // Common items
                                data.TryGetValue("BodyName", out val);
                                string name = (string)val;

                                data.TryGetValue("DistanceFromArrivalLS", out val);
                                decimal distancefromarrival = (decimal)(double)val;

                                data.TryGetValue("Radius", out val);
                                decimal radius = (decimal)(double)val;

                                data.TryGetValue("OrbitalPeriod", out val);
                                decimal? orbitalperiod = (decimal?)(double?)val;

                                data.TryGetValue("RotationPeriod", out val);
                                decimal rotationperiod = (decimal)(double)val;

                                data.TryGetValue("SemiMajorAxis", out val);
                                decimal? semimajoraxis = (decimal?)(double?)val;

                                data.TryGetValue("Eccentricity", out val);
                                decimal? eccentricity = (decimal?)(double?)val;

                                data.TryGetValue("OrbitalInclination", out val);
                                decimal? orbitalinclination = (decimal?)(double?)val;

                                data.TryGetValue("Periapsis", out val);
                                decimal? periapsis = (decimal?)(double?)val;

                                data.TryGetValue("Rings", out val);
                                List<object> ringsData = (List<object>)val;
                                List<Ring> rings = new List<Ring>();
                                if (ringsData != null)
                                {
                                    foreach (Dictionary<string, object> ringData in ringsData)
                                    {
                                        ringData.TryGetValue("Name", out val);
                                        string ringName = (string)val;

                                        ringData.TryGetValue("RingClass", out val);
                                        Composition ringComposition = Composition.FromEDName((string)val);

                                        ringData.TryGetValue("MassMT", out val);
                                        decimal ringMass = (decimal)(double)val;

                                        ringData.TryGetValue("InnerRad", out val);
                                        decimal ringInnerRadius = (decimal)(double)val;

                                        ringData.TryGetValue("OuterRad", out val);
                                        decimal ringOuterRadius = (decimal)(double)val;

                                        rings.Add(new Ring(ringName, ringComposition, ringMass, ringInnerRadius, ringOuterRadius));
                                    }
                                }


                                if (data.ContainsKey("StarType"))
                                {
                                    // Star
                                    data.TryGetValue("StarType", out val);
                                    string starType = (string)val;

                                    data.TryGetValue("StellarMass", out val);
                                    decimal stellarMass = (decimal)(double)val;

                                    data.TryGetValue("AbsoluteMagnitude", out val);
                                    decimal absoluteMagnitude = (decimal)(double)val;

                                    data.TryGetValue("Age_MY", out val);
                                    long age = (long)val * 1000000;

                                    data.TryGetValue("SurfaceTemperature", out val);
                                    decimal temperature = (decimal)(double)val;

                                    journalEvent = new StarScannedEvent(timestamp, name, starType, stellarMass, radius, absoluteMagnitude, age, temperature, distancefromarrival, orbitalperiod, rotationperiod, semimajoraxis, eccentricity, orbitalinclination, periapsis, rings);
                                    handled = true;
                                }
                                else
                                {
                                    // Body
                                    data.TryGetValue("TidalLock", out val);
                                    bool tidallyLocked = (bool)val;

                                    data.TryGetValue("PlanetClass", out val);
                                    string bodyClass = (string)val;

                                    // MKW: Gravity in the Journal is in m/s; must convert it to G
                                    data.TryGetValue("SurfaceGravity", out val);
                                    decimal gravity = Body.ms2g((decimal)(double)val);

                                    data.TryGetValue("SurfaceTemperature", out val);
                                    decimal temperature = (decimal)(double)val;

                                    data.TryGetValue("SurfacePressure", out val);
                                    decimal pressure = (decimal)(double)val;

                                    data.TryGetValue("Landable", out val);
                                    bool landable = (bool)val;

                                    data.TryGetValue("Materials", out val);
                                    IDictionary<string, object> materialsData = (IDictionary<string, object>)val;
                                    List<MaterialPresence> materials = new List<MaterialPresence>();
                                    if (materialsData != null)
                                    {
                                        foreach (KeyValuePair<string, object> kv in materialsData)
                                        {
                                            Material material = Material.FromEDName(kv.Key);
                                            if (material != null)
                                            {
                                                materials.Add(new MaterialPresence(material, (decimal)(double)kv.Value));
                                            }
                                        }
                                    }

                                    data.TryGetValue("TerraformState", out val);
                                    string terraformState = (string)val;

                                    // Atmosphere
                                    data.TryGetValue("Atmosphere", out val);
                                    string atmosphere = (string)val;

                                    // Volcanism
                                    data.TryGetValue("Volcanism", out val);
                                    string volcanism = (string)val;

                                    journalEvent = new BodyScannedEvent(timestamp, name, bodyClass, gravity, temperature, pressure, tidallyLocked, landable, atmosphere, volcanism, distancefromarrival, (decimal)orbitalperiod, rotationperiod, semimajoraxis, eccentricity, orbitalinclination, periapsis, rings, materials, terraformState);
                                    handled = true;
                                }
                            }
                            break;
                        case "ShipyardBuy":
                            {
                                object val;
                                // We don't have a ship ID at this point so use the ship type
                                data.TryGetValue("ShipType", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(null, shipModel);

                                data.TryGetValue("ShipPrice", out val);
                                long price = (long)val;

                                data.TryGetValue("StoreShipID", out val);
                                int? storedShipId = (val == null ? (int?)null : (int)(long)val);
                                data.TryGetValue("StoreOldShip", out val);
                                string storedShipModel = (string)val;
                                Ship storedShip = storedShipId == null ? null : findShip(storedShipId, storedShipModel);

                                data.TryGetValue("SellShipID", out val);
                                int? soldShipId = (val == null ? (int?)null : (int)(long)val);
                                data.TryGetValue("SellOldShip", out val);
                                string soldShipModel = (string)val;
                                Ship soldShip = soldShipId == null ? null : findShip(soldShipId, soldShipModel);

                                data.TryGetValue("SellPrice", out val);
                                long? soldPrice = (long?)val;
                                journalEvent = new ShipPurchasedEvent(timestamp, ship, price, soldShip, soldPrice, storedShip);
                            }
                            handled = true;
                            break;
                        case "ShipyardNew":
                            {
                                object val;
                                data.TryGetValue("NewShipID", out val);
                                int shipId = (int)(long)val;
                                data.TryGetValue("ShipType", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(shipId, shipModel);

                                journalEvent = new ShipDeliveredEvent(timestamp, ship);
                            }
                            handled = true;
                            break;
                        case "ShipyardSell":
                            {
                                object val;
                                data.TryGetValue("SellShipID", out val);
                                int shipId = (int)(long)val;
                                data.TryGetValue("ShipType", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(shipId, shipModel);
                                data.TryGetValue("ShipPrice", out val);
                                long price = (long)val;
                                journalEvent = new ShipSoldEvent(timestamp, ship, price);
                            }
                            handled = true;
                            break;
                        case "ShipyardSwap":
                            {
                                object val;

                                data.TryGetValue("ShipID", out val);
                                int shipId = (int)(long)val;
                                data.TryGetValue("ShipType", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(shipId, shipModel);

                                data.TryGetValue("StoreShipID", out val);
                                int? storedShipId = (val == null ? (int?)null : (int)(long)val);
                                data.TryGetValue("StoreOldShip", out val);
                                string storedShipModel = (string)val;
                                Ship storedShip = storedShipId == null ? null : findShip(storedShipId, storedShipModel);

                                data.TryGetValue("SellShipID", out val);
                                int? soldShipId = (val == null ? (int?)null : (int)(long)val);
                                data.TryGetValue("SellOldShip", out val);
                                string soldShipModel = (string)val;
                                Ship soldShip = soldShipId == null ? null : findShip(soldShipId, soldShipModel);

                                journalEvent = new ShipSwappedEvent(timestamp, ship, soldShip, storedShip);
                            }
                            handled = true;
                            break;
                        case "ShipyardTransfer":
                            {
                                object val;
                                data.TryGetValue("ShipID", out val);
                                int shipId = (int)(long)val;
                                data.TryGetValue("ShipType", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(shipId, shipModel);

                                data.TryGetValue("System", out val);
                                string system = (string)val;

                                data.TryGetValue("Distance", out val);
                                decimal distance = (decimal)(double)val;

                                data.TryGetValue("TransferPrice", out val);
                                long price = (long)val;

                                journalEvent = new ShipTransferInitiatedEvent(timestamp, ship, system, distance, price);

                                handled = true;
                            }
                            break;
                        case "LaunchSRV":
                            {
                                object val;
                                data.TryGetValue("Loadout", out val);
                                string loadout = (string)val;
                                journalEvent = new SRVLaunchedEvent(timestamp, loadout);
                            }
                            handled = true;
                            break;
                        case "DockSRV":
                            journalEvent = new SRVDockedEvent(timestamp);
                            handled = true;
                            break;
                        case "LaunchFighter":
                            {
                                object val;
                                data.TryGetValue("Loadout", out val);
                                string loadout = (string)val;
                                data.TryGetValue("PlayerControlled", out val);
                                bool playerControlled = (bool)val;
                                journalEvent = new FighterLaunchedEvent(timestamp, loadout, playerControlled);
                            }
                            handled = true;
                            break;
                        case "DockFighter":
                            journalEvent = new FighterDockedEvent(timestamp);
                            handled = true;
                            break;
                        case "VehicleSwitch":
                            {
                                object val;
                                data.TryGetValue("To", out val);
                                string to = (string)val;
                                if (to == "Fighter")
                                {
                                    journalEvent = new ControllingFighterEvent(timestamp);
                                    handled = true;
                                }
                                else if (to == "Mothership")
                                {
                                    journalEvent = new ControllingShipEvent(timestamp);
                                    handled = true;
                                }
                            }
                            break;
                        case "Interdicted":
                            {
                                object val;
                                data.TryGetValue("Submitted", out val);
                                bool submitted = (bool)val;
                                data.TryGetValue("Interdictor", out val);
                                string interdictor = (string)val;
                                data.TryGetValue("IsPlayer", out val);
                                bool iscommander = (bool)val;
                                data.TryGetValue("CombatRank", out val);
                                CombatRating rating = (val == null ? null : CombatRating.FromRank((int)(long)val));
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                data.TryGetValue("Power", out val);
                                string power = (string)val;

                                journalEvent = new ShipInterdictedEvent(timestamp, true, submitted, iscommander, interdictor, rating, faction, power);
                                handled = true;
                            }
                            break;
                        case "EscapeInterdiction":
                            {
                                object val;
                                data.TryGetValue("Interdictor", out val);
                                string interdictor = (string)val;
                                data.TryGetValue("IsPlayer", out val);
                                bool iscommander = (bool)val;

                                journalEvent = new ShipInterdictedEvent(timestamp, false, false, iscommander, interdictor, null, null, null);
                                handled = true;
                            }
                            break;
                        case "Interdiction":
                            {
                                object val;
                                data.TryGetValue("Success", out val);
                                bool success = (bool)val;
                                data.TryGetValue("Interdicted", out val);
                                string interdictee = (string)val;
                                data.TryGetValue("IsPlayer", out val);
                                bool iscommander = (bool)val;
                                data.TryGetValue("CombatRank", out val);
                                CombatRating rating = (val == null ? null : CombatRating.FromRank((int)(long)val));
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                data.TryGetValue("Power", out val);
                                string power = (string)val;

                                journalEvent = new ShipInterdictionEvent(timestamp, success, iscommander, interdictee, rating, faction, power);
                                handled = true;
                            }
                            break;
                        case "PVPKill":
                            {
                                object val;
                                data.TryGetValue("Victim", out val);
                                string victim = (string)val;
                                data.TryGetValue("CombatRank", out val);
                                CombatRating rating = (val == null ? null : CombatRating.FromRank((int)(long)val));

                                journalEvent = new KilledEvent(timestamp, victim, rating);
                                handled = true;
                            }
                            break;
                        case "MaterialCollected":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                Material material = Material.FromEDName((string)val);
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                journalEvent = new MaterialCollectedEvent(timestamp, material, amount);
                                handled = true;
                            }
                            break;
                        case "MaterialDiscarded":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                Material material = Material.FromEDName((string)val);
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                journalEvent = new MaterialDiscardedEvent(timestamp, material, amount);
                                handled = true;
                            }
                            break;
                        case "MaterialDiscovered":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                Material material = Material.FromEDName((string)val);
                                journalEvent = new MaterialDiscoveredEvent(timestamp, material);
                                handled = true;
                            }
                            break;
                        case "ScientificResearch":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                Material material = Material.FromEDName((string)val);
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                journalEvent = new MaterialDonatedEvent(timestamp, material, amount);
                                handled = true;
                            }
                            break;
                        case "ReceiveText":
                            {
                                object val;
                                data.TryGetValue("From", out val);
                                string from = (string)val;

                                data.TryGetValue("Channel", out val);
                                string channel = (string)val;

                                if (!(from.StartsWith("$cmdr") || from.StartsWith("&")))
                                {
                                    // For now we log everything that isn't commander speech
                                    Logging.Report("NPC speech", line);
                                }
                                else
                                {
                                    from = from.Replace("$cmdr_decorate:#name=", "Commander ").Replace(";", "").Replace("&", "Commander ");
                                    data.TryGetValue("Message", out val);
                                    string message = (string)val;
                                    journalEvent = new MessageReceivedEvent(timestamp, from, true, channel, message);
                                }
                            }
                            handled = true;
                            break;
                        case "SendText":
                            {
                                object val;
                                data.TryGetValue("To", out val);
                                string to = (string)val;
                                to = to.Replace("$cmdr_decorate:#name=", "Commander ").Replace(";", "").Replace("&", "Commander ");
                                data.TryGetValue("Message", out val);
                                string message = (string)val;
                                journalEvent = new MessageSentEvent(timestamp, to, message);
                            }
                            handled = true;
                            break;
                        case "DockingRequested":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                journalEvent = new DockingRequestedEvent(timestamp, stationName);
                            }
                            handled = true;
                            break;
                        case "DockingGranted":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                data.TryGetValue("LandingPad", out val);
                                int landingPad = (int)(long)val;
                                journalEvent = new DockingGrantedEvent(timestamp, stationName, landingPad);
                            }
                            handled = true;
                            break;
                        case "DockingDenied":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                data.TryGetValue("Reason", out val);
                                string reason = (string)val;
                                journalEvent = new DockingDeniedEvent(timestamp, stationName, reason);
                            }
                            handled = true;
                            break;
                        case "DockingCancelled":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                journalEvent = new DockingCancelledEvent(timestamp, stationName);
                            }
                            handled = true;
                            break;
                        case "DockingTimeout":
                            {
                                object val;
                                data.TryGetValue("StationName", out val);
                                string stationName = (string)val;
                                journalEvent = new DockingTimedOutEvent(timestamp, stationName);
                            }
                            handled = true;
                            break;
                        case "MiningRefined":
                            {
                                object val;
                                data.TryGetValue("Type", out val);
                                string commodityName = (string)val;

                                Commodity commodity = CommodityDefinitions.FromName(commodityName);
                                if (commodity == null)
                                {
                                    Logging.Error("Failed to map commodityrefined type " + commodityName + " to commodity");
                                }
                                journalEvent = new CommodityRefinedEvent(timestamp, commodity);
                            }
                            handled = true;
                            break;
                        case "HeatWarning":
                            journalEvent = new HeatWarningEvent(timestamp);
                            handled = true;
                            break;
                        case "HeatDamage":
                            journalEvent = new HeatDamageEvent(timestamp);
                            handled = true;
                            break;
                        case "HullDamage":
                            {
                                object val;
                                data.TryGetValue("Health", out val);
                                decimal health = sensibleHealth((decimal)(((double)val) * 100));
                                journalEvent = new HullDamagedEvent(timestamp, health);
                            }
                            handled = true;
                            break;
                        case "ShieldState":
                            {
                                object val;
                                data.TryGetValue("ShieldsUp", out val);
                                bool shieldsUp = (bool)val;
                                if (shieldsUp == true)
                                {
                                    journalEvent = new ShieldsUpEvent(timestamp);
                                }
                                else
                                {
                                    journalEvent = new ShieldsDownEvent(timestamp);
                                }
                                handled = true;
                                break;
                            }
                        case "SelfDestruct":
                            journalEvent = new SelfDestructEvent(timestamp);
                            handled = true;
                            break;
                        case "Died":
                            {
                                object val;

                                List<string> names = new List<string>();
                                List<string> ships = new List<string>();
                                List<CombatRating> ratings = new List<CombatRating>();

                                if (data.ContainsKey("KillerName"))
                                {
                                    // Single killer
                                    data.TryGetValue("KillerName", out val);
                                    names.Add((string)val);
                                    data.TryGetValue("KillerShip", out val);
                                    ships.Add((string)val);
                                    data.TryGetValue("KillerRank", out val);
                                    ratings.Add(CombatRating.FromEDName((string)val));
                                }
                                if (data.ContainsKey("killers"))
                                {
                                    // Multiple killers
                                    data.TryGetValue("Killers", out val);
                                    List<object> killers = (List<object>)val;
                                    foreach (IDictionary<string, object> killer in killers)
                                    {
                                        killer.TryGetValue("Name", out val);
                                        names.Add((string)val);
                                        killer.TryGetValue("Ship", out val);
                                        ships.Add((string)val);
                                        killer.TryGetValue("Rank", out val);
                                        ratings.Add(CombatRating.FromEDName((string)val));
                                    }
                                }
                                journalEvent = new DiedEvent(timestamp, names, ships, ratings);
                                handled = true;
                            }
                            break;
                        case "BuyExplorationData":
                            {
                                object val;
                                data.TryGetValue("System", out val);
                                string system = (string)val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;
                                journalEvent = new ExplorationDataPurchasedEvent(timestamp, system, price);
                                handled = true;
                                break;
                            }
                        case "SellExplorationData":
                            {
                                object val;
                                data.TryGetValue("Systems", out val);
                                List<string> systems = ((List<object>)val).Cast<string>().ToList();
                                data.TryGetValue("Discovered", out val);
                                List<string> firsts = ((List<object>)val).Cast<string>().ToList();
                                data.TryGetValue("BaseValue", out val);
                                decimal reward = (long)val;
                                data.TryGetValue("Bonus", out val);
                                decimal bonus = (long)val;
                                journalEvent = new ExplorationDataSoldEvent(timestamp, systems, firsts, reward, bonus);
                                handled = true;
                                break;
                            }
                        case "USSDrop":
                            {
                                object val;
                                data.TryGetValue("USSType", out val);
                                string source = (string)val;
                                data.TryGetValue("USSThreat", out val);
                                int threat = (int)(long)val;
                                journalEvent = new EnteredSignalSourceEvent(timestamp, source, threat);
                            }
                            handled = true;
                            break;
                        case "MarketBuy":
                            {
                                object val;
                                data.TryGetValue("Type", out val);
                                string commodityName = (string)val;
                                Commodity commodity = CommodityDefinitions.FromName(commodityName);
                                if (commodity == null)
                                {
                                    Logging.Error("Failed to map marketbuy type " + commodityName + " to commodity");
                                }
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                data.TryGetValue("BuyPrice", out val);
                                long price = (long)val;
                                journalEvent = new CommodityPurchasedEvent(timestamp, commodity, amount, price);
                                handled = true;
                                break;
                            }
                        case "MarketSell":
                            {
                                object val;
                                data.TryGetValue("Type", out val);
                                string commodityName = (string)val;
                                Commodity commodity = CommodityDefinitions.FromName(commodityName);
                                if (commodity == null)
                                {
                                    Logging.Error("Failed to map marketsell type " + commodityName + " to commodity");
                                }
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                data.TryGetValue("SellPrice", out val);
                                long price = (long)val;
                                data.TryGetValue("AvgPricePaid", out val);
                                long buyPrice = (long)val;
                                // We don't care about buy price, we care about profit per unit
                                long profit = price - buyPrice;
                                data.TryGetValue("IllegalGoods", out val);
                                bool illegal = (val == null ? false : (bool)val);
                                data.TryGetValue("StolenGoods", out val);
                                bool stolen = (val == null ? false : (bool)val);
                                data.TryGetValue("BlackMarket", out val);
                                bool blackmarket = (val == null ? false : (bool)val);
                                journalEvent = new CommoditySoldEvent(timestamp, commodity, amount, price, profit, illegal, stolen, blackmarket);
                                handled = true;
                                break;
                            }
                        case "LoadGame":
                            {
                                object val;
                                data.TryGetValue("Commander", out val);
                                string commander = (string)val;
                                data.TryGetValue("ShipID", out val);
                                int? shipId = (int?)(long?)val;
                                data.TryGetValue("Ship", out val);
                                string shipModel = (string)val;
                                Ship ship = findShip(shipId, shipModel);
                                data.TryGetValue("GameMode", out val);
                                GameMode mode = GameMode.FromEDName((string)val);
                                data.TryGetValue("Group", out val);
                                string group = (string)val;
                                data.TryGetValue("Credits", out val);
                                decimal credits = (long)val;
                                journalEvent = new CommanderContinuedEvent(timestamp, commander, ship, mode, group, credits);
                                handled = true;
                                break;
                            }
                        case "CrewHire":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Might be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;
                                data.TryGetValue("CombatRank", out val);
                                CombatRating rating = CombatRating.FromRank((int)(long)val);
                                journalEvent = new CrewHiredEvent(timestamp, name, faction, price, rating);
                                handled = true;
                                break;
                            }
                        case "CrewFire":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                journalEvent = new CrewFiredEvent(timestamp, name);
                                handled = true;
                                break;
                            }
                        case "CrewAssign":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("Role", out val);
                                string role = (string)val;
                                journalEvent = new CrewAssignedEvent(timestamp, name, role);
                                handled = true;
                                break;
                            }
                        case "BuyAmmo":
                            {
                                object val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;
                                journalEvent = new ShipRestockedEvent(timestamp, price);
                                handled = true;
                                break;
                            }
                        case "BuyDrones":
                            {
                                object val;
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                data.TryGetValue("BuyPrice", out val);
                                long price = (long)val;
                                journalEvent = new LimpetPurchasedEvent(timestamp, amount, price);
                                handled = true;
                                break;
                            }
                        case "SellDrones":
                            {
                                object val;
                                data.TryGetValue("Count", out val);
                                int amount = (int)(long)val;
                                data.TryGetValue("SellPrice", out val);
                                long price = (long)val;
                                journalEvent = new LimpetSoldEvent(timestamp, amount, price);
                                handled = true;
                                break;
                            }
                        case "ClearSavedGame":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                journalEvent = new ClearedSaveEvent(timestamp, name);
                                handled = true;
                                break;
                            }
                        case "NewCommander":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("Package", out val);
                                string package = (string)val;
                                journalEvent = new CommanderStartedEvent(timestamp, name, package);
                                handled = true;
                                break;
                            }
                        case "Progress":
                            {
                                object val;
                                data.TryGetValue("Combat", out val);
                                decimal combat = (long)val;
                                data.TryGetValue("Trade", out val);
                                decimal trade = (long)val;
                                data.TryGetValue("Explore", out val);
                                decimal exploration = (long)val;
                                data.TryGetValue("CQC", out val);
                                decimal cqc = (long)val;
                                data.TryGetValue("Empire", out val);
                                decimal empire = (long)val;
                                data.TryGetValue("Federation", out val);
                                decimal federation = (long)val;

                                journalEvent = new CommanderProgressEvent(timestamp, combat, trade, exploration, cqc, empire, federation);
                                handled = true;
                                break;
                            }
                        case "Rank":
                            {
                                object val;
                                data.TryGetValue("Combat", out val);
                                CombatRating combat = CombatRating.FromRank((int)((long)val));
                                data.TryGetValue("Trade", out val);
                                TradeRating trade = TradeRating.FromRank((int)((long)val));
                                data.TryGetValue("Explore", out val);
                                ExplorationRating exploration = ExplorationRating.FromRank((int)((long)val));
                                data.TryGetValue("CQC", out val);
                                CQCRating cqc = CQCRating.FromRank((int)((long)val));
                                data.TryGetValue("Empire", out val);
                                EmpireRating empire = EmpireRating.FromRank((int)((long)val));
                                data.TryGetValue("Federation", out val);
                                FederationRating federation = FederationRating.FromRank((int)((long)val));

                                journalEvent = new CommanderRatingsEvent(timestamp, combat, trade, exploration, cqc, empire, federation);
                                handled = true;
                                break;
                            }
                        case "Screenshot":
                            {
                                object val;
                                data.TryGetValue("Filename", out val);
                                string filename = (string)val;
                                data.TryGetValue("Width", out val);
                                int width = (int)(long)val;
                                data.TryGetValue("Height", out val);
                                int height = (int)(long)val;
                                data.TryGetValue("System", out val);
                                string system = (string)val;
                                data.TryGetValue("Body", out val);
                                string body = (string)val;

                                journalEvent = new ScreenshotEvent(timestamp, filename, width, height, system, body);
                                handled = true;
                                break;
                            }
                        case "BuyTradeData":
                            {
                                object val;
                                data.TryGetValue("System", out val);
                                string system = (string)val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;

                                journalEvent = new TradeDataPurchasedEvent(timestamp, system, price);
                                handled = true;
                                break;
                            }
                        case "PayFines":
                            {
                                object val;
                                data.TryGetValue("Amount", out val);
                                long amount = (long)val;

                                journalEvent = new FinePaidEvent(timestamp, amount, false);
                                handled = true;
                                break;
                            }
                        case "PayLegacyFines":
                            {
                                object val;
                                data.TryGetValue("Amount", out val);
                                long amount = (long)val;

                                journalEvent = new FinePaidEvent(timestamp, amount, true);
                                handled = true;
                                break;
                            }
                        case "RefuelPartial":
                            {
                                object val;
                                data.TryGetValue("Amount", out val);
                                decimal amount = (decimal)(double)val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;

                                journalEvent = new ShipRefuelledEvent(timestamp, price, amount);
                                handled = true;
                                break;
                            }
                        case "RefuelAll":
                            {
                                object val;
                                data.TryGetValue("Amount", out val);
                                decimal amount = (decimal)(double)val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;

                                journalEvent = new ShipRefuelledEvent(timestamp, price, amount);
                                handled = true;
                                break;
                            }
                        //case "RedeemVoucher":
                        //    {
                        //        object val;
                        //        data.TryGetValue("Amount", out val);
                        //        decimal amount = (decimal)(double)val;
                        //        data.TryGetValue("Cost", out val);
                        //        long price = (long)val;

                        //        journalEvent = new ShipRefuelledEvent(timestamp, price, amount);
                        //        handled = true;
                        //        break;
                        //    }
                        case "CommunityGoalJoin":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("System", out val);
                                string system = (string)val;

                                journalEvent = new MissionAcceptedEvent(timestamp, null, name, system, null, true, null);
                                handled = true;
                                break;
                            }
                        case "CommunityGoalReward":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("System", out val);
                                string system = (string)val;
                                data.TryGetValue("Reward", out val);
                                long reward = (val == null ? 0 : (long)val);

                                journalEvent = new MissionCompletedEvent(timestamp, null, name, system, true, reward, 0);
                                handled = true;
                                break;
                            }
                        case "MissionAccepted":
                            {
                                object val;
                                data.TryGetValue("MissionID", out val);
                                long missionid = (long)val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("Faction", out val);
                                string faction = (string)val;
                                // Could be a superpower...
                                Superpower superpowerFaction = Superpower.From(faction);
                                faction = superpowerFaction != null ? superpowerFaction.name : faction;

                                data.TryGetValue("Expiry", out val);
                                DateTime? expiry = (val == null ? (DateTime?)null : (DateTime)val);

                                journalEvent = new MissionAcceptedEvent(timestamp, missionid, name, null, faction, false, expiry);
                                handled = true;
                                break;
                            }
                        case "MissionCompleted":
                            {
                                object val;
                                data.TryGetValue("MissionID", out val);
                                long missionid = (long)val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                data.TryGetValue("Reward", out val);
                                long reward = (val == null ? 0 : (long)val);
                                data.TryGetValue("Donation", out val);
                                long donation = (val == null ? 0 : (long)val);

                                journalEvent = new MissionCompletedEvent(timestamp, missionid, name, null, false, reward, donation);
                                handled = true;
                                break;
                            }
                        case "MissionAbandoned":
                            {
                                object val;
                                data.TryGetValue("MissionID", out val);
                                long missionid = (long)val;
                                data.TryGetValue("Name", out val);
                                string name = (string)val;
                                journalEvent = new MissionAbandonedEvent(timestamp, missionid, name);
                                handled = true;
                                break;
                            }
                        case "Repair":
                            {
                                object val;
                                data.TryGetValue("Item", out val);
                                string item = (string)val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;
                                journalEvent = new ShipRepairedEvent(timestamp, item, price);
                                handled = true;
                                break;
                            }
                        case "RepairAll":
                            {
                                object val;
                                data.TryGetValue("Cost", out val);
                                long price = (long)val;
                                journalEvent = new ShipRepairedEvent(timestamp, null, price);
                                handled = true;
                                break;
                            }
                        case "RebootRepair":
                            {
                                object val;
                                data.TryGetValue("Modules", out val);
                                List<object> modulesJson = (List<object>)val;

                                List<string> modules = new List<string>();
                                foreach (string module in modulesJson)
                                {
                                    modules.Add(module);
                                }
                                journalEvent = new ShipRebootedEvent(timestamp, modules);
                                handled = true;
                                break;
                            }
                        case "Synthesis":
                            {
                                object val;
                                data.TryGetValue("Name", out val);
                                string synthesis = (string)val;

                                data.TryGetValue("Materials", out val);
                                Dictionary<string, object> materialsData = (Dictionary<string, object>)val;
                                List<MaterialAmount> materials = new List<MaterialAmount>();
                                if (materialsData != null)
                                {
                                    foreach (KeyValuePair<string, object> materialData in materialsData)
                                    {
                                        Material material = Material.FromEDName(materialData.Key);
                                        materials.Add(new MaterialAmount(material, (int)(long)materialData.Value));
                                    }
                                }

                                journalEvent = new SynthesisedEvent(timestamp, synthesis, materials);
                                handled = true;
                                break;
                            }
                    }

                    if (journalEvent != null)
                    {
                        journalEvent.raw = line;
                    }

                    if (handled)
                    {
                        if (journalEvent == null)
                        {
                            Logging.Debug("Handled event");
                        }
                        else
                        {
                            Logging.Debug("Handled event: " + JsonConvert.SerializeObject(journalEvent));
                        }
                    }
                    else
                    {
                        Logging.Debug("Unhandled event: " + line);
                    }
                    return journalEvent;
                }
            }
            catch (Exception ex)
            {
                Logging.Warn("Failed to parse line: " + ex.ToString());
                Logging.Error("Exception whilst parsing line", line);
            }
            return null;
        }
 private string DealWithMsg(LocationEvent locationEvent)
 {
     return("");
 }
Exemple #23
0
        private IObservable <LocationEvent> CreateLocationObservable(LocationOptions options)
        {
            return(Observable.Create <LocationEvent>(async(o) =>
            {
                var lc = new MyLocationCallback((lr) =>
                {
                    foreach (var item in lr.Locations)
                    {
                        double?verticalAccuracy = null;

                        if (Android.OS.Build.VERSION.SdkInt >= Android.OS.BuildVersionCodes.O)
                        {
                            if (item.HasVerticalAccuracy)
                            {
                                verticalAccuracy = item.VerticalAccuracyMeters;
                            }
                        }

                        var location = new Location(item.Latitude, item.Longitude,
                                                    item.HasAccuracy ? item.Accuracy : (double?)null,
                                                    item.HasAltitude ? item.Altitude : (double?)null,
                                                    verticalAccuracy,
                                                    item.HasBearing ? item.Bearing : (double?)null,
                                                    item.HasSpeed ? item.Speed : (double?)null);

                        DateTimeOffset dto;

                        if (Android.OS.Build.VERSION.SdkInt >= Android.OS.BuildVersionCodes.JellyBeanMr1)
                        {
                            var en = item.ElapsedRealtimeNanos;

                            var sn = SystemClock.ElapsedRealtimeNanos();

                            var age = (sn - en) / 1000000;

                            dto = DateTimeOffset.FromUnixTimeMilliseconds(
                                DateTimeOffset.UtcNow.ToUnixTimeMilliseconds() - age);
                        }
                        else
                        {
                            dto = DateTimeOffset.Now;
                        }

                        var locationEvent = new LocationEvent(dto, location);

                        o.OnNext(locationEvent);
                    }
                });


                var request = CreateRequest(options);

                await _fusedLocationProviderClient.RequestLocationUpdatesAsync(request, lc, _context.MainLooper).ConfigureAwait(false);

                Interlocked.Increment(ref NoActiveObservables);

                return Disposable.Create(() =>
                {
                    Interlocked.Decrement(ref NoActiveObservables);

                    _fusedLocationProviderClient.RemoveLocationUpdates(lc);
                });
            }));
        }
        private void AssertEvent(LocationEvent @event)
        {
            Assert.NotNull(@event);
            Assert.Equal(DateTime.Parse("2019-09-08T09:53:44Z"), @event.Timestamp);
            Assert.Equal(EventName, @event.Event);
            Assert.Equal(4479.807617, @event.DistFromStarLs, 6);
            Assert.True(@event.Docked);
            Assert.Equal("Krikalev Hangar", @event.StationName);
            Assert.Equal("Outpost", @event.StationType);
            Assert.Equal(3223662592, @event.MarketId);
            Assert.Equal("Eurybia Blue Mafia", @event.StationFaction.Name);
            Assert.Equal("Expansion", @event.StationFaction.State);
            Assert.Equal("$government_Anarchy;", @event.StationGovernment);
            Assert.Equal("Анархия", @event.StationGovernmentLocalised);
            Assert.Equal(GovernmentType.Anarchy, @event.StationGovernmentType);
            Assert.Equal(17, @event.StationServices.Length);
            Assert.Equal("$economy_Refinery;", @event.StationEconomy);
            Assert.Equal(EconomyType.Refinery, @event.StationEconomyType);
            Assert.Equal("Переработка", @event.StationEconomyLocalised);
            Assert.Equal("$economy_Refinery;", @event.StationEconomies[0].Name);
            Assert.Equal(EconomyType.Refinery, @event.StationEconomies[0].Type);
            Assert.Equal("Переработка", @event.StationEconomies[0].NameLocalised);
            Assert.Equal(1.000000, @event.StationEconomies[0].Proportion, 6);
            Assert.Equal("Njortamool", @event.StarSystem);
            Assert.Equal(5372466973488, @event.SystemAddress);
            Assert.Equal(46.65625, @event.StarPos[0], 5);
            Assert.Equal(-43.34375, @event.StarPos[1], 5);
            Assert.Equal(-43.68750, @event.StarPos[2], 5);
            Assert.Equal(Allegiance.Independent, @event.SystemAllegiance);
            Assert.Equal("$economy_Refinery;", @event.SystemEconomy);
            Assert.Equal(EconomyType.Refinery, @event.SystemEconomyType);
            Assert.Equal("Переработка", @event.SystemEconomyLocalised);
            Assert.Equal("$economy_None;", @event.SystemSecondEconomy);
            Assert.Equal(EconomyType.None, @event.SystemSecondEconomyType);
            Assert.Equal("Нет", @event.SystemSecondEconomyLocalised);
            Assert.Equal("$government_Anarchy;", @event.SystemGovernment);
            Assert.Equal(GovernmentType.Anarchy, @event.SystemGovernmentType);
            Assert.Equal("Анархия", @event.SystemGovernmentLocalised);
            Assert.Equal("$GAlAXY_MAP_INFO_state_anarchy;", @event.SystemSecurity);
            Assert.Equal(SecurityType.Anarchy, @event.SystemSecurityType);
            Assert.Equal("Анархия", @event.SystemSecurityLocalised);
            Assert.Equal(29911, @event.Population);
            Assert.Equal("Krikalev Hangar", @event.Body);
            Assert.Equal(16, @event.BodyId);
            Assert.Equal(BodyType.Station, @event.BodyType);
            Assert.Equal("Eurybia Blue Mafia", @event.SystemFaction.Name);
            Assert.Equal("Expansion", @event.SystemFaction.State);

            Assert.Equal(6, @event.Factions.Length);
            Assert.Equal("Eurybia Blue Mafia", @event.Factions[4].Name);
            Assert.Equal("Expansion", @event.Factions[4].State);
            Assert.Equal("Anarchy", @event.Factions[4].Government);
            Assert.Equal(GovernmentType.Anarchy, @event.Factions[4].GovernmentType);
            Assert.Equal(0.747000, @event.Factions[4].Influence, 6);
            Assert.Equal(Allegiance.Independent, @event.Factions[4].Allegiance);
            Assert.Equal(Happiness.Happy, @event.Factions[4].Happiness);
            Assert.Equal("Счастье", @event.Factions[4].HappinessLocalised);
            Assert.Equal(92.326302, @event.Factions[4].MyReputation, 6);
            Assert.Equal(State.Outbreak, @event.Factions[4].RecoveringStates[0].State);
            Assert.Equal(0, @event.Factions[4].RecoveringStates[0].Trend);
            Assert.Equal(State.Boom, @event.Factions[4].ActiveStates[0].State);
            Assert.Null(@event.Factions[4].ActiveStates[0].Trend);
            Assert.Equal(State.Expansion, @event.Factions[4].ActiveStates[1].State);
            Assert.Null(@event.Factions[4].ActiveStates[1].Trend);
        }
Exemple #25
0
 internal void InvokeLocationEvent(LocationEvent arg)
 {
     LocationEvent?.Invoke(this, arg);
 }
Exemple #26
0
        /// <summary>
        /// 从请求中提取微信消息推送的请求数据
        /// </summary>
        /// <param name="request">推送过来的请求</param>
        /// <returns>消息推送的请求数据</returns>
        public MsgRequest GetMsgRequestData(WeChatEncryptMsg requestEncryptMsg)
        {
            //微信服务器在五秒内收不到响应会断掉连接,并且重新发起请求,总共重试三次
            //消息排重,推荐使用msgid排重;事件类型消息推荐使用FromUserName + CreateTime 排重
            //服务器无法保证在五秒内处理并回复,直接回复success;直接回复空串,微信不再重试
            //开发者在5秒内未回复任何内容,开发者回复了异常数据,微信系统提示“该公众号暂时无法提供服务,请稍后再试”
            if (weChatConfig == null)
            {
                throw new NullReferenceException("请使用构造MessageLinkUp(idOrAppId),或初始化Initialize(idOrAppId)");
            }
            string xmlText;//消息

            if (weChatConfig.EnCrypt)
            {
                //消息是密文,要解密后处理
                xmlText = MessageDecrypt(requestEncryptMsg);
            }
            else
            {
                var          stream = requestEncryptMsg.Body; //具体消息数据在请求流里面
                StreamReader reader = new StreamReader(stream);
                xmlText = reader.ReadToEnd();                 //消息
                reader.Close();
            }
            XmlDocument xmlDoc = new XmlDocument();

            xmlDoc.LoadXml(xmlText);
            XmlNode    rootNode   = xmlDoc.SelectSingleNode("xml");
            MsgRequest msgRequest = null;

            if (rootNode["MsgType"] == null)
            {
                msgRequest = new MsgRequest();
            }
            else
            {
                string msgType = rootNode["MsgType"].InnerText;
                switch (msgType)
                {
                case "text":
                    ContentMsg contentMsg = new ContentMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        contentMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["Content"] != null)
                    {
                        contentMsg.Content = rootNode["Content"].InnerText;
                    }
                    msgRequest = contentMsg;
                    break;

                case "image":
                    PictureMsg pictureMsg = new PictureMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        pictureMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["PicUrl"] != null)
                    {
                        pictureMsg.PicUrl = rootNode["PicUrl"].InnerText;
                    }
                    if (rootNode["MediaId"] != null)
                    {
                        pictureMsg.MediaId = rootNode["MediaId"].InnerText;
                    }
                    msgRequest = pictureMsg;
                    break;

                case "voice":
                    VoiceMsg voiceMsg = new VoiceMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        voiceMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["MediaId"] != null)
                    {
                        voiceMsg.MediaId = rootNode["MediaId"].InnerText;
                    }
                    if (rootNode["Format"] != null)
                    {
                        voiceMsg.Format = rootNode["Format"].InnerText;
                    }
                    if (rootNode["Recognition"] != null)
                    {
                        voiceMsg.Recognition = rootNode["Recognition"].InnerText;
                    }
                    msgRequest = voiceMsg;
                    break;

                case "video":
                    VideoMsg videoMsg = new VideoMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        videoMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["MediaId"] != null)
                    {
                        videoMsg.MediaId = rootNode["MediaId"].InnerText;
                    }
                    if (rootNode["ThumbMediaId"] != null)
                    {
                        videoMsg.ThumbMediaId = rootNode["ThumbMediaId"].InnerText;
                    }
                    msgRequest = videoMsg;
                    break;

                case "shortvideo":
                    ShortVideoMsg shortVideoMsg = new ShortVideoMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        shortVideoMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["MediaId"] != null)
                    {
                        shortVideoMsg.MediaId = rootNode["MediaId"].InnerText;
                    }
                    if (rootNode["ThumbMediaId"] != null)
                    {
                        shortVideoMsg.ThumbMediaId = rootNode["ThumbMediaId"].InnerText;
                    }
                    msgRequest = shortVideoMsg;
                    break;

                case "location":
                    LocationMsg locationMsg = new LocationMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        locationMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["Location_X"] != null)
                    {
                        locationMsg.Location_X = Convert.ToDouble(rootNode["Location_X"].InnerText);
                    }
                    if (rootNode["Location_Y"] != null)
                    {
                        locationMsg.Location_Y = Convert.ToDouble(rootNode["Location_Y"].InnerText);
                    }
                    if (rootNode["Scale"] != null)
                    {
                        locationMsg.Scale = int.Parse(rootNode["Scale"].InnerText);
                    }
                    if (rootNode["Label"] != null)
                    {
                        locationMsg.Label = rootNode["Label"].InnerText;
                    }
                    msgRequest = locationMsg;
                    break;

                case "link":
                    LinkMsg linkMsg = new LinkMsg();
                    if (rootNode["MsgId"] != null)
                    {
                        linkMsg.MsgId = Convert.ToInt64(rootNode["MsgId"].InnerText);
                    }
                    if (rootNode["Title"] != null)
                    {
                        linkMsg.Title = rootNode["Title"].InnerText;
                    }
                    if (rootNode["Description"] != null)
                    {
                        linkMsg.Description = rootNode["Description"].InnerText;
                    }
                    if (rootNode["Url"] != null)
                    {
                        linkMsg.Url = rootNode["Url"].InnerText;
                    }
                    msgRequest = linkMsg;
                    break;

                case "event":
                    if (rootNode["Event"] != null)
                    {
                        string eventStr = rootNode["Event"].InnerText.ToLower();
                        switch (eventStr)
                        {
                        case "subscribe":
                            if (rootNode["EventKey"] != null)
                            {
                                string eventKey = rootNode["EventKey"].InnerText;
                                if (eventKey.StartsWith("qrscene_"))
                                {
                                    ScanSubscribeEvent scanSubscribeEvent = new ScanSubscribeEvent();
                                    scanSubscribeEvent.EventKey = eventKey;
                                    if (rootNode["Ticket"] != null)
                                    {
                                        scanSubscribeEvent.Ticket = rootNode["Ticket"].InnerText;
                                    }
                                    msgRequest = scanSubscribeEvent;
                                }
                            }
                            if (msgRequest == null)
                            {
                                msgRequest = new SubscribeEvent();
                            }
                            break;

                        case "unsubscribe": msgRequest = new UnSubscribeEvent(); break;

                        case "scan":
                            ScanEvent scanEvent = new ScanEvent();
                            if (rootNode["EventKey"] != null)
                            {
                                scanEvent.EventKey = rootNode["EventKey"].InnerText;
                            }
                            if (rootNode["Ticket"] != null)
                            {
                                scanEvent.Ticket = rootNode["Ticket"].InnerText;
                            }
                            msgRequest = scanEvent;
                            break;

                        case "location":
                            LocationEvent locationEvent = new LocationEvent();
                            if (rootNode["Latitude"] != null)
                            {
                                locationEvent.Latitude = double.Parse(rootNode["Latitude"].InnerText);
                            }
                            if (rootNode["Longitude"] != null)
                            {
                                locationEvent.Longitude = double.Parse(rootNode["Longitude"].InnerText);
                            }
                            if (rootNode["Precision"] != null)
                            {
                                locationEvent.Precision = double.Parse(rootNode["Precision"].InnerText);
                            }
                            msgRequest = locationEvent;
                            break;

                        case "click":
                            ClickEvent clickEvent = new ClickEvent();
                            if (rootNode["EventKey"] != null)
                            {
                                clickEvent.EventKey = rootNode["EventKey"].InnerText;
                            }
                            msgRequest = clickEvent;
                            break;

                        case "view":
                            ViewEvent viewEvent = new ViewEvent();
                            if (rootNode["EventKey"] != null)
                            {
                                viewEvent.EventKey = rootNode["EventKey"].InnerText;
                            }
                            msgRequest = viewEvent;
                            break;

                        case "masssendjobfinish":        //批量发送群发消息处理完成的消息通知
                            MassSendJobFinishEvent sendJobFinishEvent = new MassSendJobFinishEvent();
                            if (rootNode["MsgID"] != null)
                            {
                                sendJobFinishEvent.MsgID = int.Parse(rootNode["MsgID"].InnerText);
                            }
                            if (rootNode["Status"] != null)
                            {
                                sendJobFinishEvent.Status = Enum.Parse <MassSendJobStatus>(rootNode["Status"].InnerText);
                            }
                            if (rootNode["TotalCount"] != null)
                            {
                                sendJobFinishEvent.TotalCount = int.Parse(rootNode["TotalCount"].InnerText);
                            }
                            if (rootNode["FilterCount"] != null)
                            {
                                sendJobFinishEvent.FilterCount = int.Parse(rootNode["FilterCount"].InnerText);
                            }
                            if (rootNode["SentCount"] != null)
                            {
                                sendJobFinishEvent.SentCount = int.Parse(rootNode["SentCount"].InnerText);
                            }
                            if (rootNode["ErrorCount"] != null)
                            {
                                sendJobFinishEvent.ErrorCount = int.Parse(rootNode["ErrorCount"].InnerText);
                            }
                            XmlNodeList checkResultList = rootNode["CopyrightCheckResult"]?.ChildNodes;
                            if (checkResultList != null && checkResultList.Count > 0)
                            {
                                XmlNode countNode      = rootNode["CopyrightCheckResult"]["Count"];
                                XmlNode checkStateNode = rootNode["CopyrightCheckResult"]["CheckState"];
                                XmlNode resultListNode = rootNode["CopyrightCheckResult"]["ResultList"];
                                if (countNode != null)
                                {
                                    sendJobFinishEvent.CopyrightCheckCount = int.Parse(countNode.InnerText);
                                }
                                else if (checkStateNode != null)
                                {
                                    sendJobFinishEvent.CheckState = int.Parse(checkStateNode.InnerText);
                                }
                                else if (resultListNode != null)
                                {
                                    sendJobFinishEvent.ResultList = new List <ArticleCheckResult>();
                                    foreach (XmlNode itemNode in resultListNode)
                                    {
                                        sendJobFinishEvent.ResultList.Add(new ArticleCheckResult()
                                        {
                                            ArticleIdx            = int.Parse(itemNode["ArticleIdx"].InnerText),
                                            UserDeclareState      = int.Parse(itemNode["UserDeclareState"].InnerText),
                                            AuditState            = int.Parse(itemNode["AuditState"].InnerText),
                                            OriginalArticleUrl    = itemNode["OriginalArticleUrl"].InnerText,
                                            OriginalArticleType   = int.Parse(itemNode["OriginalArticleType"].InnerText),
                                            CanReprint            = bool.Parse(itemNode["CanReprint"].InnerText),
                                            NeedReplaceContent    = bool.Parse(itemNode["NeedReplaceContent"].InnerText),
                                            NeedShowReprintSource = bool.Parse(itemNode["NeedShowReprintSource"].InnerText),
                                        });
                                    }
                                }
                            }
                            msgRequest = sendJobFinishEvent;
                            break;

                        case "templatesendjobfinish":
                            TemplateSendJobFinishEvent templateSendFinishEvent = new TemplateSendJobFinishEvent();
                            if (rootNode["MsgID"] != null)
                            {
                                templateSendFinishEvent.MsgID = int.Parse(rootNode["MsgID"].InnerText);
                            }
                            if (rootNode["Status"] != null)
                            {
                                templateSendFinishEvent.Status = rootNode["Status"].InnerText;
                            }
                            break;

                        default: msgRequest = new MsgRequest(); break;
                        }
                    }
                    break;

                default: msgRequest = new MsgRequest(); break;
                }
                msgRequest.MsgType = msgType;
            }
            msgRequest.ToUserName   = rootNode["ToUserName"].InnerText;
            msgRequest.FromUserName = rootNode["FromUserName"].InnerText;
            msgRequest.CreateTime   = int.Parse(rootNode["CreateTime"].InnerText);

            return(msgRequest);
        }
        private bool eventLocation(LocationEvent theEvent)
        {
            updateCurrentSystem(theEvent.system);
            // Always update the current system with the current co-ordinates, just in case things have changed
            CurrentStarSystem.x = theEvent.x;
            CurrentStarSystem.y = theEvent.y;
            CurrentStarSystem.z = theEvent.z;

            if (theEvent.docked == true)
            {
                // In this case body === station

                if (CurrentStation != null && CurrentStation.name == theEvent.body)
                {
                    // We are already at this station; nothing to do
                    Logging.Debug("Already at station " + theEvent.body);
                    return false;
                }
                // Update the station
                Logging.Debug("Now at station " + theEvent.body);
                Station station = CurrentStarSystem.stations.Find(s => s.name == theEvent.body);
                if (station == null)
                {
                    // This station is unknown to us, might not be in EDDB or we might not have connectivity.  Use a placeholder
                    station = new Station();
                    station.name = theEvent.body;
                    station.systemname = theEvent.system;
                }

                // Information from the event might be more current than that from EDDB so use it in preference
                station.state = theEvent.factionstate;
                station.faction = theEvent.faction;
                station.government = theEvent.government;
                station.allegiance = theEvent.allegiance;

                CurrentStation = station;

                // Now call refreshProfile() to obtain the outfitting and commodity information
                refreshProfile();
            }

            return true;
        }
Exemple #28
0
 void RaiseLocationEvent()
 {
     LocationEvent?.Invoke(this, new LocationEventArgs(LocationType));
 }
Exemple #29
0
 protected virtual string ProcessLocationEvent(LocationEvent msg)
 {
     return(DefaultProcess(msg));
 }
Exemple #30
0
 internal void InvokeLocationEvent(LocationEvent arg) => LocationEvent?.Invoke(null, arg);