protected virtual void Dispose(bool disposing)
        {
            if (_disposed)
            {
                return;
            }

            if (disposing)
            {
                Name = string.Empty;
                Parts?.Clear();

                UnderlyingPackage.Close();

                try
                {
                    File.Delete(_tempFileName);
                }
                catch (IOException ex)
                {
                    Debug.Fail(ex.Message);
                }
            }

            _disposed = true;
        }
        public OfficePart CreateCustomPart(XmlPart partType)
        {
            string relativePath;
            string relType;

            switch (partType)
            {
            case XmlPart.RibbonX12:
                relativePath = "/customUI/customUI.xml";
                relType      = CustomUiPartRelType;
                break;

            case XmlPart.RibbonX14:
                relativePath = "/customUI/customUI14.xml";
                relType      = CustomUi14PartRelType;
                break;

            case XmlPart.Qat12:
                relativePath = "/customUI/qat.xml";
                relType      = QatPartRelType;
                break;

            default:
                throw new ArgumentException($"Unexpected {nameof(partType)}: {partType}");
            }

            var customUiUri  = new Uri(relativePath, UriKind.Relative);
            var relationship = UnderlyingPackage.CreateRelationship(customUiUri, TargetMode.Internal, relType);

            OfficePart part;

            if (!UnderlyingPackage.PartExists(customUiUri))
            {
                part = new OfficePart(UnderlyingPackage.CreatePart(customUiUri, "application/xml"), partType, relationship.Id);
            }
            else
            {
                part = new OfficePart(UnderlyingPackage.GetPart(customUiUri), partType, relationship.Id);
            }

            if (Parts == null)
            {
                Parts = new List <OfficePart>();
            }

            Parts.Add(part);
            IsDirty = true;

            return(part);
        }
        public void RemoveCustomPart(XmlPart partType)
        {
            if (Parts == null)
            {
                return;
            }

            for (var i = Parts.Count - 1; i >= 0; i--)
            {
                if (Parts[i].PartType != partType)
                {
                    continue;
                }

                var part = Parts[i];
                part.Remove();

                Parts.RemoveAt(i);

                UnderlyingPackage.Flush();
                IsDirty = true;
            }
        }
        public void Save(string?customFileName = null, bool preserveAttributes = true)
        {
            if (string.IsNullOrEmpty(customFileName))
            {
                customFileName = Name;
            }

            if (!IsDirty && customFileName == Name)
            {
                return;
            }

            UnderlyingPackage.Flush();
            UnderlyingPackage.Close();

            var info = new FileInfo(customFileName);

            if (info.Exists)
            {
                File.SetAttributes(customFileName, FileAttributes.Normal);
            }

            try
            {
                File.Copy(_tempFileName, customFileName, true /*overwrite*/);
                if (info.Exists && preserveAttributes)
                {
                    File.SetAttributes(customFileName, info.Attributes);
                }
            }
            finally
            {
                Init();
            }

            IsDirty = false;
        }