示例#1
0
        /// <summary>
        /// Hide the repeated atoms and bonds of a multiple group. We hide al atoms that
        /// belong to the group unless they are defined in the parent atom list. Any
        /// bond to those atoms that is not a crossing bond or one connecting atoms in
        /// the parent list is hidden.
        /// </summary>
        /// <param name="container">molecule</param>
        /// <param name="sgroup">multiple group display shortcut</param>
        private static void HideMultipleParts(IAtomContainer container, Sgroup sgroup)
        {
            var crossing    = sgroup.Bonds;
            var atoms       = sgroup.Atoms;
            var parentAtoms = (ICollection <IAtom>)sgroup.GetValue(SgroupKey.CtabParentAtomList);

            foreach (var bond in container.Bonds)
            {
                if (parentAtoms.Contains(bond.Begin) && parentAtoms.Contains(bond.End))
                {
                    continue;
                }
                if (atoms.Contains(bond.Begin) || atoms.Contains(bond.End))
                {
                    StandardGenerator.Hide(bond);
                }
            }
            foreach (var atom in atoms)
            {
                if (!parentAtoms.Contains(atom))
                {
                    StandardGenerator.Hide(atom);
                }
            }
            foreach (var bond in crossing)
            {
                StandardGenerator.Unhide(bond);
            }
        }
示例#2
0
        /// <summary>
        /// If the molecule has display shortcuts (abbreviations or multiple group sgroups) certain parts
        /// of the structure are hidden from display. This method marks the parts to hide and in the case
        /// of abbreviations, remaps atom symbols. Apart from additional property flags, the molecule
        /// is unchanged by this method.
        /// </summary>
        /// <param name="container">molecule input</param>
        /// <param name="symbolRemap">a map that will hold symbol remapping</param>
        public static void PrepareDisplayShortcuts(IAtomContainer container, IDictionary <IAtom, string> symbolRemap)
        {
            var sgroups = container.GetCtabSgroups();

            if (sgroups == null || !sgroups.Any())
            {
                return;
            }

            // select abbreviations that should be contracted
            foreach (var sgroup in sgroups)
            {
                if (sgroup.Type == SgroupType.CtabAbbreviation)
                {
                    bool?expansion = (bool?)sgroup.GetValue(SgroupKey.CtabExpansion);
                    // abbreviation is displayed as expanded
                    if (expansion ?? false)
                    {
                        continue;
                    }
                    // no or empty label, skip it
                    if (string.IsNullOrEmpty(sgroup.Subscript))
                    {
                        continue;
                    }

                    // only contract if the atoms are either partially or fully highlighted
                    if (CheckAbbreviationHighlight(container, sgroup))
                    {
                        ContractAbbreviation(container, symbolRemap, sgroup);
                    }
                }
                else if (sgroup.Type == SgroupType.CtabMultipleGroup)
                {
                    HideMultipleParts(container, sgroup);
                }
                else if (sgroup.Type == SgroupType.ExtMulticenter)
                {
                    var atoms = sgroup.Atoms;
                    // should only be one bond
                    foreach (var bond in sgroup.Bonds)
                    {
                        var beg = bond.Begin;
                        var end = bond.End;
                        if (atoms.Contains(beg))
                        {
                            StandardGenerator.HideFully(beg);
                        }
                        else
                        {
                            StandardGenerator.HideFully(end);
                        }
                    }
                }
            }
        }
        private IRenderingElement GenerateAbbreviationSgroup(IAtomContainer mol, Sgroup sgroup)
        {
            string label = sgroup.Subscript;

            // already handled by symbol remapping
            if (sgroup.Bonds.Count > 0 || string.IsNullOrEmpty(label))
            {
                return(new ElementGroup());
            }
            if (!CheckAbbreviationHighlight(mol, sgroup))
            {
                return(new ElementGroup());
            }
            // we're showing a label where there were no atoms before, we put it in the
            // middle of all of those which were hidden
            var sgroupAtoms = sgroup.Atoms;

            Debug.Assert(sgroupAtoms.Any());

            var highlight = sgroupAtoms.First().GetProperty <Color>(StandardGenerator.HighlightColorKey);
            var style     = parameters.GetHighlighting();
            var glowWidth = parameters.GetOuterGlowWidth();

            Vector2 labelCoords = GeometryUtil.Get2DCenter(sgroupAtoms);

            ElementGroup labelgroup = new ElementGroup();

            foreach (var outline in atomGenerator.GenerateAbbreviatedSymbol(label, HydrogenPosition.Right)
                     .Resize(1 / scale, 1 / -scale)
                     .GetOutlines())
            {
                if (highlight != null && style == HighlightStyle.Colored)
                {
                    labelgroup.Add(GeneralPath.ShapeOf(outline, highlight));
                }
                else
                {
                    labelgroup.Add(GeneralPath.ShapeOf(outline, foreground));
                }
            }

            if (highlight != null && style == HighlightStyle.OuterGlow)
            {
                ElementGroup group = new ElementGroup
                {
                    // outer glow needs to be being the label
                    StandardGenerator.OuterGlow(labelgroup, highlight, glowWidth, stroke),
                    labelgroup
                };
                return(group);
            }
            else
            {
                return(MarkedElement.MarkupAtom(labelgroup, null));
            }
        }
示例#4
0
        /// <summary>
        /// Hide the atoms and bonds of a contracted abbreviation. If the abbreviations is attached
        /// we remap the attachment symbol to display the name. If there are no attachments the symbol
        /// we be added later ({@see #generateSgroups}).
        /// </summary>
        /// <param name="container">molecule</param>
        /// <param name="sgroup">abbreviation group display shortcut</param>
        private static void ContractAbbreviation(IAtomContainer container, IDictionary <IAtom, string> symbolRemap, Sgroup sgroup)
        {
            var crossing = sgroup.Bonds;
            var atoms    = sgroup.Atoms;

            // only do 0,1 attachments for now
            if (crossing.Count > 1)
            {
                return;
            }

            foreach (var atom in atoms)
            {
                StandardGenerator.Hide(atom);
            }
            foreach (var bond in container.Bonds)
            {
                if (atoms.Contains(bond.Begin) ||
                    atoms.Contains(bond.End))
                {
                    StandardGenerator.Hide(bond);
                }
            }
            foreach (var bond in crossing)
            {
                StandardGenerator.Unhide(bond);
                var a1 = bond.Begin;
                var a2 = bond.End;
                StandardGenerator.Unhide(a1);
                if (atoms.Contains(a1))
                {
                    symbolRemap[a1] = sgroup.Subscript;
                }
                StandardGenerator.Unhide(a2);
                if (atoms.Contains(a2))
                {
                    symbolRemap[a2] = sgroup.Subscript;
                }
            }
        }
示例#5
0
        private IRenderingElement GenerateAbbreviationSgroup(IAtomContainer mol, Sgroup sgroup)
        {
            string label = sgroup.Subscript;

            // already handled by symbol remapping
            if (sgroup.Bonds.Count > 0 || string.IsNullOrEmpty(label))
            {
                return(new ElementGroup());
            }
            if (!CheckAbbreviationHighlight(mol, sgroup))
            {
                return(new ElementGroup());
            }
            // we're showing a label where there were no atoms before, we put it in the
            // middle of all of those which were hidden
            var sgroupAtoms = sgroup.Atoms;

            Debug.Assert(sgroupAtoms.Any());

            var highlight = sgroupAtoms.First().GetProperty <Color>(StandardGenerator.HighlightColorKey);
            var style     = parameters.GetHighlighting();
            var glowWidth = parameters.GetOuterGlowWidth();

            Vector2 labelLocation;

            if (mol.Atoms.Count == sgroup.Atoms.Count)
            {
                labelLocation = GeometryUtil.Get2DCenter(sgroupAtoms);
            }
            else
            {
                // contraction of part of a fragment, e.g. SALT
                // here we work out the point we want to place the contract relative
                // to the SGroup Atoms
                labelLocation = new Vector2();
                var sgrpCenter = GeometryUtil.Get2DCenter(sgroupAtoms);
                var molCenter  = GeometryUtil.Get2DCenter(mol);
                var minMax     = GeometryUtil.GetMinMax(sgroupAtoms);
                var xDiff      = sgrpCenter.X - molCenter.X;
                var yDiff      = sgrpCenter.Y - molCenter.Y;
                if (xDiff > 0.1)
                {
                    labelLocation.X = minMax[0]; // min x
                    label           = INTERPUNCT + label;
                }
                else if (xDiff < -0.1)
                {
                    labelLocation.X = minMax[2]; // max x
                    label           = label + INTERPUNCT;
                }
                else
                {
                    labelLocation.X = sgrpCenter.X;
                    label           = INTERPUNCT + label;
                }
                if (yDiff > 0.1)
                {
                    labelLocation.Y = minMax[1]; // min y
                }
                else if (yDiff < -0.1)
                {
                    labelLocation.Y = minMax[3]; // max y
                }
                else
                {
                    labelLocation.Y = sgrpCenter.Y;
                }
            }

            var labelgroup = new ElementGroup();

            foreach (var outline in atomGenerator.GenerateAbbreviatedSymbol(label, HydrogenPosition.Right)
                     .Center(labelLocation.X, labelLocation.Y)
                     .Resize(1 / scale, 1 / -scale)
                     .GetOutlines())
            {
                if (highlight != null && style == HighlightStyle.Colored)
                {
                    labelgroup.Add(GeneralPath.ShapeOf(outline, highlight));
                }
                else
                {
                    labelgroup.Add(GeneralPath.ShapeOf(outline, foreground));
                }
            }

            if (highlight != null && style == HighlightStyle.OuterGlow)
            {
                var group = new ElementGroup
                {
                    // outer glow needs to be being the label
                    StandardGenerator.OuterGlow(labelgroup, highlight, glowWidth, stroke),
                    labelgroup
                };
                return(group);
            }
            else
            {
                return(MarkedElement.MarkupAtom(labelgroup, null));
            }
        }
示例#6
0
 private TextOutline MakeText(string subscriptSuffix, Vector2 b1p2, Vector2 b1pvec, double labelScale)
 {
     return(StandardGenerator.GenerateAnnotation(b1p2, subscriptSuffix, VecmathUtil.Negate(b1pvec), 1, labelScale, font, emSize, null).Resize(1 / scale, 1 / scale));
 }