Ejemplo n.º 1
0
        public static TimeSpan Finish(string taskname)
        {
            TimeSpan final = TimeSpan.Zero;

            if (s_DictionaryStarts.TryRemove(taskname, out TimeSpan objStartTimeSpan))
            {
                final = s_Time.Elapsed - objStartTimeSpan;

#if DEBUG
                string strLogEntry = string.Format(GlobalSettings.InvariantCultureInfo, "Task \"{0}\" finished in {1}",
                                                   taskname, final);
                //Log.Trace(strLogEntry);

                Debug.WriteLine(strLogEntry);
#endif

                s_DictionaryStatistics.AddOrUpdate(taskname, x => new Tuple <TimeSpan, int>(final, 1),
                                                   (x, y) => new Tuple <TimeSpan, int>(
                                                       y.Item1 + final, y.Item2 + 1));
            }
            else
            {
                Debug.WriteLine("Non started task \"" + taskname + "\" finished");
            }
            return(final);
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Generates a character cache, which prevents us from repeatedly loading XmlNodes or caching a full character.
        /// </summary>
        /// <param name="strFile"></param>
        private TreeNode CacheCharacters(string strFile)
        {
            if (!File.Exists(strFile))
            {
                Program.MainForm.ShowMessageBox(
                    this,
                    string.Format(GlobalSettings.CultureInfo,
                                  LanguageManager.GetString("Message_File_Cannot_Be_Accessed"), strFile));
                return(null);
            }

            using (ThreadSafeList <XPathNavigator> lstCharacterXmlStatblocks = new ThreadSafeList <XPathNavigator>(3))
            {
                try
                {
                    using (ZipArchive zipArchive
                               = ZipFile.Open(strFile, ZipArchiveMode.Read, Encoding.GetEncoding(850)))
                    {
                        Parallel.ForEach(zipArchive.Entries, entry =>
                        {
                            string strEntryFullName = entry.FullName;
                            if (strEntryFullName.EndsWith(".xml", StringComparison.OrdinalIgnoreCase) &&
                                strEntryFullName.StartsWith("statblocks_xml", StringComparison.Ordinal))
                            {
                                // If we run into any problems loading the character cache, fail out early.
                                try
                                {
                                    XPathDocument xmlSourceDoc;
                                    using (StreamReader sr = new StreamReader(entry.Open(), true))
                                        using (XmlReader objXmlReader
                                                   = XmlReader.Create(sr, GlobalSettings.SafeXmlReaderSettings))
                                            xmlSourceDoc = new XPathDocument(objXmlReader);
                                    XPathNavigator objToAdd = xmlSourceDoc.CreateNavigator();
                                    // ReSharper disable once AccessToDisposedClosure
                                    lstCharacterXmlStatblocks.Add(objToAdd);
                                }
                                // If we run into any problems loading the character cache, fail out early.
                                catch (IOException)
                                {
                                    Utils.BreakIfDebug();
                                }
                                catch (XmlException)
                                {
                                    Utils.BreakIfDebug();
                                }
                            }
                            else if (strEntryFullName.StartsWith("images", StringComparison.Ordinal) &&
                                     strEntryFullName.Contains('.'))
                            {
                                string strKey = Path.GetFileName(strEntryFullName);
                                using (Bitmap bmpMugshot = new Bitmap(entry.Open(), true))
                                {
                                    Bitmap bmpNewMugshot = bmpMugshot.PixelFormat == PixelFormat.Format32bppPArgb
                                        ? bmpMugshot.Clone() as Bitmap // Clone makes sure file handle is closed
                                        : bmpMugshot.ConvertPixelFormat(PixelFormat.Format32bppPArgb);
                                    while (!_dicImages.TryAdd(strKey, bmpNewMugshot))
                                    {
                                        if (_dicImages.TryRemove(strKey, out Bitmap bmpOldMugshot))
                                        {
                                            bmpOldMugshot?.Dispose();
                                        }
                                    }
                                }
                            }
                        });
                    }
                }
                catch (IOException)
                {
                    Program.MainForm.ShowMessageBox(
                        this,
                        string.Format(GlobalSettings.CultureInfo,
                                      LanguageManager.GetString("Message_File_Cannot_Be_Accessed"), strFile));
                    return(null);
                }
                catch (NotSupportedException)
                {
                    Program.MainForm.ShowMessageBox(
                        this,
                        string.Format(GlobalSettings.CultureInfo,
                                      LanguageManager.GetString("Message_File_Cannot_Be_Accessed"), strFile));
                    return(null);
                }
                catch (UnauthorizedAccessException)
                {
                    Program.MainForm.ShowMessageBox(
                        this, LanguageManager.GetString("Message_Insufficient_Permissions_Warning"));
                    return(null);
                }

                string strFileText
                    = strFile.CheapReplace(Utils.GetStartupPath, () => '<' + Application.ProductName + '>');
                TreeNode nodRootNode = new TreeNode
                {
                    Text        = strFileText,
                    ToolTipText = strFileText
                };

                XPathNavigator xmlMetatypesDocument = XmlManager.LoadXPath("metatypes.xml");
                foreach (XPathNavigator xmlCharacterDocument in lstCharacterXmlStatblocks)
                {
                    XPathNavigator xmlBaseCharacterNode
                        = xmlCharacterDocument.SelectSingleNode("/document/public/character");
                    if (xmlBaseCharacterNode != null)
                    {
                        HeroLabCharacterCache objCache = new HeroLabCharacterCache
                        {
                            PlayerName = xmlBaseCharacterNode.SelectSingleNode("@playername")?.Value ?? string.Empty
                        };
                        string strNameString = xmlBaseCharacterNode.SelectSingleNode("@name")?.Value ?? string.Empty;
                        objCache.CharacterId = strNameString;
                        if (!string.IsNullOrEmpty(strNameString))
                        {
                            int intAsIndex = strNameString.IndexOf(" as ", StringComparison.Ordinal);
                            if (intAsIndex != -1)
                            {
                                objCache.CharacterName = strNameString.Substring(0, intAsIndex);
                                objCache.CharacterAlias
                                    = strNameString.Substring(intAsIndex).TrimStart(" as ").Trim('\'');
                            }
                            else
                            {
                                objCache.CharacterName = strNameString;
                            }
                        }

                        string strRaceString = xmlBaseCharacterNode.SelectSingleNode("race/@name")?.Value;
                        if (strRaceString == "Metasapient")
                        {
                            strRaceString = "A.I.";
                        }
                        if (!string.IsNullOrEmpty(strRaceString))
                        {
                            foreach (XPathNavigator xmlMetatype in xmlMetatypesDocument.Select(
                                         "/chummer/metatypes/metatype"))
                            {
                                string strMetatypeName = xmlMetatype.SelectSingleNode("name")?.Value ?? string.Empty;
                                if (strMetatypeName == strRaceString)
                                {
                                    objCache.Metatype    = strMetatypeName;
                                    objCache.Metavariant = "None";
                                    break;
                                }

                                foreach (XPathNavigator xmlMetavariant in
                                         xmlMetatype.SelectAndCacheExpression("metavariants/metavariant"))
                                {
                                    string strMetavariantName
                                        = xmlMetavariant.SelectSingleNode("name")?.Value ?? string.Empty;
                                    if (strMetavariantName == strRaceString)
                                    {
                                        objCache.Metatype    = strMetatypeName;
                                        objCache.Metavariant = strMetavariantName;
                                        break;
                                    }
                                }
                            }
                        }

                        objCache.Description = xmlBaseCharacterNode.SelectSingleNode("personal/description")?.Value;
                        objCache.Karma       = xmlBaseCharacterNode.SelectSingleNode("karma/@total")?.Value ?? "0";
                        objCache.Essence     = xmlBaseCharacterNode
                                               .SelectSingleNode("attributes/attribute[@name = \"Essence\"]/@text")?.Value;
                        objCache.BuildMethod
                            = xmlBaseCharacterNode.SelectSingleNode("creation/bp/@total")?.Value == "25"
                                ? nameof(CharacterBuildMethod.Priority)
                                : nameof(CharacterBuildMethod.Karma);

                        objCache.Created = objCache.Karma != "0";
                        if (!objCache.Created)
                        {
                            XPathNodeIterator xmlJournalEntries = xmlBaseCharacterNode.SelectAndCacheExpression("journals/journal");
                            if (xmlJournalEntries?.Count > 1)
                            {
                                objCache.Created = true;
                            }
                            else if (xmlJournalEntries?.Count == 1 &&
                                     xmlJournalEntries.Current?.SelectSingleNode("@name")?.Value != "Title")
                            {
                                objCache.Created = true;
                            }
                        }

                        string strImageString = xmlBaseCharacterNode.SelectSingleNode("images/image/@filename")?.Value;
                        if (!string.IsNullOrEmpty(strImageString) &&
                            _dicImages.TryGetValue(strImageString, out Bitmap objTemp))
                        {
                            objCache.Mugshot = objTemp;
                        }

                        objCache.FilePath = strFile;
                        TreeNode objNode = new TreeNode
                        {
                            Text        = CalculatedName(objCache),
                            ToolTipText = strFile.CheapReplace(Utils.GetStartupPath,
                                                               () => '<' + Application.ProductName + '>')
                        };
                        nodRootNode.Nodes.Add(objNode);

                        _lstCharacterCache.Add(objCache);
                        objNode.Tag = _lstCharacterCache.IndexOf(objCache);
                    }
                }

                nodRootNode.Expand();
                return(nodRootNode);
            }
        }
Ejemplo n.º 3
0
        private static void LoadCustomCharacterSettings()
        {
            // Don't attempt to load custom character settings if we're still loading all settings
            if (Interlocked.CompareExchange(ref _intDicLoadedCharacterSettingsLoadedStatus, 1, 2) <= 1)
            {
                return;
            }
            try
            {
                using (LockingDictionary <string, CharacterSettings> dicNewLoadedCharacterSettings = new LockingDictionary <string, CharacterSettings>())
                {
                    string strSettingsPath = Path.Combine(Utils.GetStartupPath, "settings");
                    if (Directory.Exists(strSettingsPath))
                    {
                        Parallel.ForEach(Directory.EnumerateFiles(strSettingsPath, "*.xml"), strSettingsFilePath =>
                        {
                            string strSettingName = Path.GetFileName(strSettingsFilePath);
                            CharacterSettings objNewCharacterSettings = new CharacterSettings();
                            if (!objNewCharacterSettings.Load(strSettingName, false) ||
                                (objNewCharacterSettings.BuildMethodIsLifeModule &&
                                 !GlobalSettings.LifeModuleEnabled)
                                // ReSharper disable once AccessToDisposedClosure
                                || !dicNewLoadedCharacterSettings.TryAdd(objNewCharacterSettings.DictionaryKey,
                                                                         objNewCharacterSettings))
                            {
                                objNewCharacterSettings.Dispose();
                            }
                        });
                    }

                    using (new FetchSafelyFromPool <HashSet <string> >(Utils.StringHashSetPool, out HashSet <string> setRemovedSettingsKeys))
                    {
                        foreach (CharacterSettings objExistingSettings in s_DicLoadedCharacterSettings.Values.ToList())
                        {
                            if (objExistingSettings.BuiltInOption)
                            {
                                continue;
                            }
                            if (!dicNewLoadedCharacterSettings.TryRemove(objExistingSettings.DictionaryKey,
                                                                         out CharacterSettings objNewSettings))
                            {
                                setRemovedSettingsKeys.Add(objExistingSettings.DictionaryKey);
                            }
                            else
                            {
                                objExistingSettings.CopyValues(objNewSettings);
                                objNewSettings.Dispose();
                            }
                        }

                        foreach (CharacterSettings objNewSettings in dicNewLoadedCharacterSettings.Values)
                        {
                            if (!s_DicLoadedCharacterSettings.TryAdd(objNewSettings.DictionaryKey, objNewSettings))
                            {
                                objNewSettings.Dispose();
                            }
                        }

                        foreach (string strSettingToRemove in setRemovedSettingsKeys)
                        {
                            CharacterSettings objSettingsToDelete = s_DicLoadedCharacterSettings[strSettingToRemove];
                            try
                            {
                                Lazy <string> strBestMatchNewSettingsKey = new Lazy <string>(() =>
                                {
                                    int intBestScore = int.MinValue;
                                    string strReturn = string.Empty;
                                    foreach (CharacterSettings objExistingSettings in s_DicLoadedCharacterSettings.Values)
                                    {
                                        if (setRemovedSettingsKeys.Contains(objExistingSettings.DictionaryKey))
                                        {
                                            continue;
                                        }
                                        // ReSharper disable once AccessToDisposedClosure
                                        int intLoopScore = CalculateCharacterSettingsMatchScore(objSettingsToDelete, objExistingSettings);
                                        if (intLoopScore > intBestScore)
                                        {
                                            intBestScore = intLoopScore;
                                            strReturn    = objExistingSettings.DictionaryKey;
                                        }
                                    }
                                    return(strReturn);
                                });
                                foreach (Character objCharacter in Program.OpenCharacters)
                                {
                                    if (objCharacter.SettingsKey == objSettingsToDelete.DictionaryKey)
                                    {
                                        objCharacter.SettingsKey = strBestMatchNewSettingsKey.Value;
                                    }
                                }
                            }
                            finally
                            {
                                s_DicLoadedCharacterSettings.Remove(objSettingsToDelete.DictionaryKey);
                                objSettingsToDelete.Dispose();
                            }
                        }
                    }
                }
            }
            finally
            {
                Interlocked.Increment(ref _intDicLoadedCharacterSettingsLoadedStatus);
            }
        }