Exemple #1
0
        public IsotopeDistInfo GetPrecursorIsotopeDistInfo(Adduct adduct, double decoyMassShift)
        {
            var massDistribution = GetPrecursorMassDistribution();
            var mzDistribution   = massDistribution.OffsetAndDivide(
                adduct.AdductCharge * (BioMassCalc.MassProton + decoyMassShift), adduct.AdductCharge);

            return(IsotopeDistInfo.MakeIsotopeDistInfo(mzDistribution, GetPrecursorMass(MassType.MonoisotopicMassH), adduct, Settings.TransitionSettings.FullScan));
        }
 public TransitionDocNode MakeTransitionDocNode(SrmSettings settings, ExplicitMods explicitMods,
                                                IsotopeDistInfo isotopeDist,
                                                Annotations annotations,
                                                TransitionDocNode.TransitionQuantInfo transitionQuantInfo,
                                                ExplicitTransitionValues explicitTransitionValues,
                                                Results <TransitionChromInfo> results)
 {
     return(GetCrosslinkBuilder(settings, explicitMods).MakeTransitionDocNode(this, isotopeDist, annotations, transitionQuantInfo, explicitTransitionValues, results));
 }
        public static bool IsValidIsotopeTransition(Transition transition, IsotopeDistInfo isotopeDist)
        {
            if (isotopeDist == null || !transition.IsPrecursor())
            {
                return(true);
            }
            int i = isotopeDist.MassIndexToPeakIndex(transition.MassIndex);

            return(0 <= i && i < isotopeDist.CountPeaks);
        }
 public override int GetHashCode()
 {
     unchecked
     {
         int result = base.GetHashCode();
         result = (result * 397) ^ Mz.GetHashCode();
         result = (result * 397) ^ (IsotopeDistInfo != null ? IsotopeDistInfo.GetHashCode() : 0);
         result = (result * 397) ^ (LibInfo != null ? LibInfo.GetHashCode() : 0);
         result = (result * 397) ^ (Results != null ? Results.GetHashCode() : 0);
         return(result);
     }
 }
Exemple #5
0
        public IEnumerable <TransitionDocNode> GetComplexTransitions(TransitionGroup transitionGroup,
                                                                     double precursorMz,
                                                                     IsotopeDistInfo isotopeDist,
                                                                     Dictionary <double, LibraryRankedSpectrumInfo.RankedMI> transitionRanks,
                                                                     IEnumerable <TransitionDocNode> simpleTransitions,
                                                                     bool useFilter)
        {
            var allTransitions =
                RemoveUnmeasurable(precursorMz,
                                   RemoveDuplicates(
                                       GetAllComplexTransitions(transitionGroup, isotopeDist, simpleTransitions, useFilter)))
                .OrderBy(tran => tran.ComplexFragmentIon)
                .ToList();

            IList <TransitionDocNode> ms2transitions;
            IList <TransitionDocNode> ms1transitions;

            if (Settings.TransitionSettings.FullScan.IsEnabledMs)
            {
                ms2transitions = allTransitions.Where(tran => !tran.IsMs1).ToList();
                ms1transitions = allTransitions.Where(tran => tran.IsMs1).ToList();
                if (Settings.TransitionSettings.FullScan.IsHighResPrecursor)
                {
                    ms1transitions = ms1transitions.SelectMany(tran =>
                                                               ExpandPrecursorIsotopes(tran, isotopeDist, useFilter)).ToList();
                }
            }
            else
            {
                ms2transitions = allTransitions;
                ms1transitions = new TransitionDocNode[0];
            }

            if (useFilter)
            {
                if (!Settings.TransitionSettings.Filter.PeptideIonTypes.Contains(IonType.precursor))
                {
                    ms1transitions = new TransitionDocNode[0];
                }

                ms2transitions = FilterTransitions(transitionRanks, ms2transitions).ToList();
            }

            return(ms1transitions.Concat(ms2transitions));
        }
Exemple #6
0
        public TransitionDocNode MakeTransitionDocNode(ComplexFragmentIon complexFragmentIon,
                                                       IsotopeDistInfo isotopeDist,
                                                       Annotations annotations,
                                                       TransitionDocNode.TransitionQuantInfo transitionQuantInfo,
                                                       ExplicitTransitionValues explicitTransitionValues,
                                                       Results <TransitionChromInfo> results)
        {
            var neutralFormula = GetNeutralFormula(complexFragmentIon);
            var productMass    = GetFragmentMassFromFormula(Settings, neutralFormula);

            if (complexFragmentIon.Children.Count > 0)
            {
                complexFragmentIon = complexFragmentIon.CloneTransition();
            }

            if (complexFragmentIon.IsMs1 && Settings.TransitionSettings.FullScan.IsHighResPrecursor)
            {
                isotopeDist         = isotopeDist ?? GetPrecursorIsotopeDistInfo(complexFragmentIon.Transition.Adduct, 0);
                productMass         = isotopeDist.GetMassI(complexFragmentIon.Transition.MassIndex, complexFragmentIon.Transition.DecoyMassShift);
                transitionQuantInfo = transitionQuantInfo.ChangeIsotopeDistInfo(new TransitionIsotopeDistInfo(
                                                                                    isotopeDist.GetRankI(complexFragmentIon.Transition.MassIndex), isotopeDist.GetProportionI(complexFragmentIon.Transition.MassIndex)));
            }
            return(new TransitionDocNode(complexFragmentIon, annotations, productMass, transitionQuantInfo, explicitTransitionValues, results));
        }
Exemple #7
0
 private static double GetMassDelta(IsotopeDistInfo isotopeDist, int massIndex)
 {
     return(isotopeDist.GetMassI(massIndex) - isotopeDist.GetMassI(massIndex - 1));
 }
 public static TransitionIsotopeDistInfo GetIsotopeDistInfo(Transition transition, TransitionLosses losses, IsotopeDistInfo isotopeDist)
 {
     if (isotopeDist == null || !transition.IsPrecursor() || losses != null)
     {
         return(null);
     }
     return(new TransitionIsotopeDistInfo(isotopeDist.GetRankI(transition.MassIndex),
                                          isotopeDist.GetProportionI(transition.MassIndex)));
 }
Exemple #9
0
        public IEnumerable <TransitionDocNode> GetPrecursorTransitions(SrmSettings settings,
                                                                       ExplicitMods mods,
                                                                       IPrecursorMassCalc calcFilterPre,
                                                                       IFragmentMassCalc calcPredict,
                                                                       double precursorMz,
                                                                       IsotopeDistInfo isotopeDist,
                                                                       IList <IList <ExplicitLoss> > potentialLosses,
                                                                       IDictionary <double, LibraryRankedSpectrumInfo.RankedMI> transitionRanks,
                                                                       bool libraryFilter,
                                                                       bool useFilter)
        {
            var      tranSettings = settings.TransitionSettings;
            var      fullScan     = tranSettings.FullScan;
            MassType massType     = tranSettings.Prediction.FragmentMassType;
            int      minMz        = tranSettings.Instrument.GetMinMz(precursorMz);
            int      maxMz        = tranSettings.Instrument.MaxMz;
            bool     precursorMS1 = fullScan.IsEnabledMs;

            if (IsCustomIon)
            {
                var ionMz =
                    BioMassCalc.CalculateIonMz(
                        CustomIon.GetMass(settings.TransitionSettings.Prediction.PrecursorMassType),
                        PrecursorCharge);
                if (!useFilter ||
                    !libraryFilter ||
                    IsMatched(transitionRanks,
                              ionMz, IonType.precursor,
                              PrecursorCharge, null))
                {
                    if (precursorMS1 && isotopeDist != null)
                    {
                        foreach (int i in fullScan.SelectMassIndices(isotopeDist, useFilter))
                        {
                            double precursorMS1Mass = isotopeDist.GetMassI(i);
                            ionMz = BioMassCalc.CalculateIonMz(precursorMS1Mass, PrecursorCharge);
                            if (minMz > ionMz || ionMz > maxMz)
                            {
                                continue;
                            }
                            var isotopeDistInfo = new TransitionIsotopeDistInfo(isotopeDist.GetRankI(i), isotopeDist.GetProportionI(i));
                            yield return(CreateTransitionNode(i, precursorMS1Mass, isotopeDistInfo, null, transitionRanks, CustomIon));
                        }
                    }
                    else
                    {
                        var    transition = new Transition(this, PrecursorCharge, null, CustomIon, IonType.precursor);
                        double massH      = CustomIon.GetMass(settings.TransitionSettings.Prediction.PrecursorMassType);
                        yield return(new TransitionDocNode(transition, null, massH, null, null));
                    }
                }
                yield break;
            }

            string sequence            = Peptide.Sequence;
            bool   precursorNoProducts = precursorMS1 && !fullScan.IsEnabledMsMs &&
                                         tranSettings.Filter.IonTypes.Count == 1 && tranSettings.Filter.IonTypes[0] == IonType.precursor;
            double precursorMassPredict = calcPredict.GetPrecursorFragmentMass(sequence);

            foreach (var losses in CalcTransitionLosses(IonType.precursor, 0, massType, potentialLosses))
            {
                double ionMz = SequenceMassCalc.GetMZ(Transition.CalcMass(precursorMassPredict, losses), PrecursorCharge);
                if (losses == null)
                {
                    if (precursorMS1 && isotopeDist != null)
                    {
                        foreach (int i in fullScan.SelectMassIndices(isotopeDist, useFilter))
                        {
                            double precursorMS1Mass = isotopeDist.GetMassI(i, DecoyMassShift);
                            ionMz = SequenceMassCalc.GetMZ(precursorMS1Mass, PrecursorCharge);
                            if (minMz > ionMz || ionMz > maxMz)
                            {
                                continue;
                            }
                            var isotopeDistInfo = new TransitionIsotopeDistInfo(
                                isotopeDist.GetRankI(i), isotopeDist.GetProportionI(i));
                            yield return(CreateTransitionNode(i, precursorMS1Mass, isotopeDistInfo, null, transitionRanks));
                        }
                        continue;
                    }
                }
                // If there was loss, it is possible (though not likely) that the ion m/z value
                // will now fall below the minimum measurable value for the instrument
                else if (minMz > ionMz)
                {
                    continue;
                }

                // If filtering precursors from MS1 scans, then ranking in MS/MS does not apply
                bool precursorIsProduct = !precursorMS1 || losses != null;
                // Skip product ion precursors, if the should not be included
                if (useFilter && precursorIsProduct && precursorNoProducts)
                {
                    continue;
                }
                if (!useFilter || !precursorIsProduct ||
                    !libraryFilter || IsMatched(transitionRanks, ionMz, IonType.precursor,
                                                PrecursorCharge, losses))
                {
                    yield return(CreateTransitionNode(0, precursorMassPredict, null, losses,
                                                      precursorIsProduct ? transitionRanks : null));
                }
            }
        }
Exemple #10
0
        public IEnumerable <TransitionDocNode> GetTransitions(SrmSettings settings,
                                                              TransitionGroupDocNode groupDocNode,
                                                              ExplicitMods mods,
                                                              double precursorMz,
                                                              IsotopeDistInfo isotopeDist,
                                                              SpectrumHeaderInfo libInfo,
                                                              IDictionary <double, LibraryRankedSpectrumInfo.RankedMI> transitionRanks,
                                                              bool useFilter)
        {
            Assume.IsTrue(ReferenceEquals(groupDocNode.TransitionGroup, this));
            // Get necessary mass calculators and masses
            var calcFilterPre = settings.GetPrecursorCalc(IsotopeLabelType.light, mods);
            var calcFilter    = settings.GetFragmentCalc(IsotopeLabelType.light, mods);
            var calcPredict   = settings.GetFragmentCalc(LabelType, mods);

            string sequence = Peptide.Sequence;

            // Save the true precursor m/z for TranstionSettings.Accept() now that all isotope types are
            // checked.  This is more correct than just using the light precursor m/z for precursor window
            // exclusion.
            double precursorMzAccept = precursorMz;

            if (!ReferenceEquals(calcFilter, calcPredict))
            {
                // Get the normal precursor m/z for filtering, so that light and heavy ion picks will match.
                precursorMz = IsCustomIon ?
                              BioMassCalc.CalculateIonMz(calcFilterPre.GetPrecursorMass(groupDocNode.CustomIon), groupDocNode.TransitionGroup.PrecursorCharge) :
                              SequenceMassCalc.GetMZ(calcFilterPre.GetPrecursorMass(sequence), groupDocNode.TransitionGroup.PrecursorCharge);
            }
            if (!IsAvoidMismatchedIsotopeTransitions)
            {
                precursorMzAccept = precursorMz;
            }

            var      tranSettings      = settings.TransitionSettings;
            var      filter            = tranSettings.Filter;
            var      charges           = filter.ProductCharges;
            var      startFinder       = filter.FragmentRangeFirst;
            var      endFinder         = filter.FragmentRangeLast;
            double   precursorMzWindow = filter.PrecursorMzWindow;
            var      types             = filter.IonTypes;
            MassType massType          = tranSettings.Prediction.FragmentMassType;
            int      minMz             = tranSettings.Instrument.GetMinMz(precursorMzAccept);
            int      maxMz             = tranSettings.Instrument.MaxMz;

            var pepMods         = settings.PeptideSettings.Modifications;
            var potentialLosses = CalcPotentialLosses(sequence, pepMods, mods, massType);

            // A start m/z will need to be calculated if the start fragment
            // finder uses m/z and their are losses to consider.  If the filter
            // is set to only consider fragments with m/z greater than the
            // precursor, the code below needs to also prevent loss fragments
            // from being under that m/z.
            double startMz = 0;

            // Get library settings
            var pick = tranSettings.Libraries.Pick;

            if (!useFilter)
            {
                pick = TransitionLibraryPick.all;
                var listAll = Transition.ALL_CHARGES.ToList();
                listAll.AddRange(charges.Where(c => !Transition.ALL_CHARGES.Contains(c)));
                listAll.Sort();
                charges = listAll.ToArray();
                types   = Transition.ALL_TYPES;
            }
            // If there are no libraries or no library information, then
            // picking cannot use library information
            else if (!settings.PeptideSettings.Libraries.HasLibraries || libInfo == null)
            {
                pick = TransitionLibraryPick.none;
            }

            // If filtering without library picking
            if (potentialLosses != null)
            {
                if (pick == TransitionLibraryPick.none)
                {
                    // Only include loss combinations where all losses are included always
                    potentialLosses = potentialLosses.Where(losses =>
                                                            losses.All(loss => loss.TransitionLoss.Loss.Inclusion == LossInclusion.Always)).ToArray();
                }
                else if (useFilter)
                {
                    // Exclude all losses which should never be included by default
                    potentialLosses = potentialLosses.Where(losses =>
                                                            losses.All(loss => loss.TransitionLoss.Loss.Inclusion != LossInclusion.Never)).ToArray();
                }
                if (!potentialLosses.Any())
                {
                    potentialLosses = null;
                }
            }

            // Return precursor ions
            if (!useFilter || types.Contains(IonType.precursor))
            {
                bool libraryFilter = (pick == TransitionLibraryPick.all || pick == TransitionLibraryPick.filter);
                foreach (var nodeTran in GetPrecursorTransitions(settings, mods, calcFilterPre, calcPredict,
                                                                 precursorMz, isotopeDist, potentialLosses, transitionRanks, libraryFilter, useFilter))
                {
                    if (minMz <= nodeTran.Mz && nodeTran.Mz <= maxMz)
                    {
                        yield return(nodeTran);
                    }
                }
            }

            // Return special ions from settings, if this is a peptide
            if (!IsCustomIon)
            {
                // This is a peptide, but it may have custom transitions (reporter ions), check those
                foreach (var measuredIon in tranSettings.Filter.MeasuredIons.Where(m => m.IsCustom))
                {
                    if (useFilter && measuredIon.IsOptional)
                    {
                        continue;
                    }
                    var    tran     = new Transition(this, measuredIon.Charge, null, measuredIon.CustomIon);
                    double mass     = settings.GetFragmentMass(IsotopeLabelType.light, null, tran, null);
                    var    nodeTran = new TransitionDocNode(tran, null, mass, null, null);
                    if (minMz <= nodeTran.Mz && nodeTran.Mz <= maxMz)
                    {
                        yield return(nodeTran);
                    }
                }
            }

            // For small molecules we can't generate new nodes, so just mz filter those we have
            foreach (var nodeTran in groupDocNode.Transitions.Where(tran => tran.Transition.IsNonPrecursorNonReporterCustomIon()))
            {
                if (minMz <= nodeTran.Mz && nodeTran.Mz <= maxMz)
                {
                    yield return(nodeTran);
                }
            }

            if (sequence == null) // Completely custom
            {
                yield break;
            }

            // If picking relies on library information
            if (useFilter && pick != TransitionLibraryPick.none)
            {
                // If it is not yet loaded, or nothing got ranked, return an empty enumeration
                if (!settings.PeptideSettings.Libraries.IsLoaded ||
                    (transitionRanks != null && transitionRanks.Count == 0))
                {
                    yield break;
                }
            }

            double[,] massesPredict = calcPredict.GetFragmentIonMasses(sequence);
            int len = massesPredict.GetLength(1);

            if (len == 0)
            {
                yield break;
            }

            double[,] massesFilter = massesPredict;
            if (!ReferenceEquals(calcFilter, calcPredict))
            {
                // Get the normal m/z values for filtering, so that light and heavy
                // ion picks will match.
                massesFilter = calcFilter.GetFragmentIonMasses(sequence);
            }

            // Get types other than this to make sure matches are possible for all types
            var listOtherTypes = new List <Tuple <TransitionGroupDocNode, IFragmentMassCalc> >();

            foreach (var labelType in settings.PeptideSettings.Modifications.GetModificationTypes())
            {
                if (Equals(labelType, LabelType))
                {
                    continue;
                }
                var calc = settings.GetFragmentCalc(labelType, mods);
                if (calc == null)
                {
                    continue;
                }
                var tranGroupOther = new TransitionGroup(Peptide, PrecursorCharge, labelType, false, DecoyMassShift);
                var nodeGroupOther = new TransitionGroupDocNode(tranGroupOther, Annotations.EMPTY, settings, mods,
                                                                libInfo, ExplicitTransitionGroupValues.EMPTY, null, new TransitionDocNode[0], false);

                listOtherTypes.Add(new Tuple <TransitionGroupDocNode, IFragmentMassCalc>(nodeGroupOther, calc));
            }

            // Loop over potential product ions picking transitions
            foreach (IonType type in types)
            {
                // Precursor type is handled above.
                if (type == IonType.precursor)
                {
                    continue;
                }

                foreach (int charge in charges)
                {
                    // Precursor charge can never be lower than product ion charge.
                    if (Math.Abs(PrecursorCharge) < Math.Abs(charge))
                    {
                        continue;
                    }

                    int start = 0, end = 0;
                    if (pick != TransitionLibraryPick.all)
                    {
                        start = startFinder.FindStartFragment(massesFilter, type, charge,
                                                              precursorMz, precursorMzWindow, out startMz);
                        end = endFinder.FindEndFragment(type, start, len);
                        if (Transition.IsCTerminal(type))
                        {
                            Helpers.Swap(ref start, ref end);
                        }
                    }

                    for (int i = 0; i < len; i++)
                    {
                        // Get the predicted m/z that would be used in the transition
                        double massH = massesPredict[(int)type, i];
                        foreach (var losses in CalcTransitionLosses(type, i, massType, potentialLosses))
                        {
                            double ionMz = SequenceMassCalc.GetMZ(Transition.CalcMass(massH, losses), charge);

                            // Make sure the fragment m/z value falls within the valid instrument range.
                            // CONSIDER: This means that a heavy transition might excede the instrument
                            //           range where a light one is accepted, leading to a disparity
                            //           between heavy and light transtions picked.
                            if (minMz > ionMz || ionMz > maxMz)
                            {
                                continue;
                            }

                            TransitionDocNode nodeTranReturn = null;
                            bool accept = true;
                            if (pick == TransitionLibraryPick.all || pick == TransitionLibraryPick.all_plus)
                            {
                                if (!useFilter)
                                {
                                    nodeTranReturn = CreateTransitionNode(type, i, charge, massH, losses, transitionRanks);
                                    accept         = false;
                                }
                                else
                                {
                                    if (IsMatched(transitionRanks, ionMz, type, charge, losses))
                                    {
                                        nodeTranReturn = CreateTransitionNode(type, i, charge, massH, losses, transitionRanks);
                                        accept         = false;
                                    }
                                    // If allowing library or filter, check the filter to decide whether to accept
                                    else if (pick == TransitionLibraryPick.all_plus &&
                                             tranSettings.Accept(sequence, precursorMzAccept, type, i, ionMz, start, end, startMz))
                                    {
                                        nodeTranReturn = CreateTransitionNode(type, i, charge, massH, losses, transitionRanks);
                                    }
                                }
                            }
                            else if (tranSettings.Accept(sequence, precursorMzAccept, type, i, ionMz, start, end, startMz))
                            {
                                if (pick == TransitionLibraryPick.none)
                                {
                                    nodeTranReturn = CreateTransitionNode(type, i, charge, massH, losses, transitionRanks);
                                }
                                else
                                {
                                    if (IsMatched(transitionRanks, ionMz, type, charge, losses))
                                    {
                                        nodeTranReturn = CreateTransitionNode(type, i, charge, massH, losses, transitionRanks);
                                    }
                                }
                            }
                            if (nodeTranReturn != null)
                            {
                                if (IsAvoidMismatchedIsotopeTransitions &&
                                    !OtherLabelTypesAllowed(settings, minMz, maxMz, start, end, startMz, accept,
                                                            groupDocNode, nodeTranReturn, listOtherTypes))
                                {
                                    continue;
                                }
                                Assume.IsTrue(minMz <= nodeTranReturn.Mz && nodeTranReturn.Mz <= maxMz);
                                yield return(nodeTranReturn);
                            }
                        }
                    }
                }
            }
        }
Exemple #11
0
            public static TransitionQuantInfo GetTransitionQuantInfo(Transition transition, TransitionLosses losses, IsotopeDistInfo isotopeDist, TypedMass massH, IDictionary <double, LibraryRankedSpectrumInfo.RankedMI> ranks)
            {
                var transitionIsotopeDistInfo = GetIsotopeDistInfo(transition, losses, isotopeDist);

                return(GetLibTransitionQuantInfo(transition, losses, massH, ranks).ChangeIsotopeDistInfo(transitionIsotopeDistInfo));
            }
Exemple #12
0
 public TransitionDocNode MakeTransitionDocNode(ComplexFragmentIon complexFragmentIon, IsotopeDistInfo isotopeDist = null)
 {
     return(MakeTransitionDocNode(complexFragmentIon, isotopeDist, Annotations.EMPTY,
                                  TransitionDocNode.TransitionQuantInfo.DEFAULT, ExplicitTransitionValues.EMPTY, null));
 }
Exemple #13
0
        public IEnumerable <TransitionDocNode> ExpandPrecursorIsotopes(TransitionDocNode transitionNode, IsotopeDistInfo isotopeDist, bool useFilter)
        {
            var fullScan = Settings.TransitionSettings.FullScan;

            foreach (int massIndex in fullScan.SelectMassIndices(isotopeDist, useFilter))
            {
                var complexFragmentIon = transitionNode.ComplexFragmentIon.ChangeMassIndex(massIndex);
                yield return(MakeTransitionDocNode(complexFragmentIon, isotopeDist));
            }
        }
Exemple #14
0
        public IEnumerable <TransitionDocNode> GetAllComplexTransitions(
            TransitionGroup transitionGroup,
            IsotopeDistInfo isotopeDist,
            IEnumerable <TransitionDocNode> simpleTransitions,
            bool useFilter)
        {
            var startingFragmentIons = new List <ComplexFragmentIon>();
            var productAdducts       = Settings.TransitionSettings.Filter.PeptideProductCharges.ToHashSet();
            var precursorLosses      = new HashSet <TransitionLosses>();

            foreach (var simpleTransition in simpleTransitions)
            {
                var startingFragmentIon = simpleTransition.ComplexFragmentIon
                                          .ChangeCrosslinkStructure(ExplicitMods.Crosslinks);
                startingFragmentIons.Add(startingFragmentIon);
                if (startingFragmentIon.IsIonTypePrecursor)
                {
                    precursorLosses.Add(startingFragmentIon.TransitionLosses);
                }
            }

            bool excludePrecursors = false;
            IEnumerable <Adduct> allProductAdducts;

            if (useFilter)
            {
                allProductAdducts = Settings.TransitionSettings.Filter.PeptideProductCharges;
                excludePrecursors = !Settings.TransitionSettings.Filter.PeptideIonTypes.Contains(IonType.precursor);
            }
            else
            {
                allProductAdducts = Settings.TransitionSettings.Filter.PeptideProductCharges
                                    .Concat(Transition.DEFAULT_PEPTIDE_CHARGES);
            }

            allProductAdducts = allProductAdducts.Append(transitionGroup.PrecursorAdduct);

            // Add ions representing the precursor waiting to be joined with a crosslinked peptide
            foreach (var productAdduct in allProductAdducts.Distinct())
            {
                foreach (var transitionLosses in precursorLosses)
                {
                    if (productAdduct.IsValidProductAdduct(transitionGroup.PrecursorAdduct, null))
                    {
                        var precursorTransition = new Transition(transitionGroup, IonType.precursor,
                                                                 Peptide.Sequence.Length - 1, 0, productAdduct);

                        startingFragmentIons.Add(new ComplexFragmentIon(precursorTransition, transitionLosses, ExplicitMods.Crosslinks, true));
                        startingFragmentIons.Add(new ComplexFragmentIon(precursorTransition, transitionLosses, ExplicitMods.Crosslinks));
                    }
                }
            }

            foreach (var complexFragmentIon in LinkedPeptide.PermuteComplexFragmentIons(ExplicitMods, Settings,
                                                                                        Settings.PeptideSettings.Modifications.MaxNeutralLosses, useFilter, startingFragmentIons.Distinct()).Distinct())
            {
                bool isPrecursor = complexFragmentIon.IsIonTypePrecursor;
                if (isPrecursor)
                {
                    if (excludePrecursors)
                    {
                        continue;
                    }
                    var expectedCharge = transitionGroup.PrecursorAdduct.AdductCharge;
                    if (complexFragmentIon.TransitionLosses != null)
                    {
                        if (complexFragmentIon.Transition.MassIndex != 0)
                        {
                            continue;
                        }
                        expectedCharge -= complexFragmentIon.TransitionLosses.TotalCharge;
                    }

                    if (expectedCharge != complexFragmentIon.Transition.Adduct.AdductCharge)
                    {
                        continue;
                    }
                }
                else
                {
                    if (complexFragmentIon.Transition.MassIndex != 0)
                    {
                        continue;
                    }
                    if (useFilter)
                    {
                        if (!productAdducts.Contains(complexFragmentIon.Transition.Adduct))
                        {
                            continue;
                        }
                    }
                }

                if (!complexFragmentIon.Transition.Adduct.IsValidProductAdduct(transitionGroup.PrecursorAdduct,
                                                                               complexFragmentIon.TransitionLosses))
                {
                    continue;
                }

                var complexTransitionDocNode = MakeTransitionDocNode(complexFragmentIon, isotopeDist);
                yield return(complexTransitionDocNode);
            }
        }
Exemple #15
0
 public TransitionDocNode MakeTransitionDocNode(SrmSettings settings, ExplicitMods explicitMods, IsotopeDistInfo isotopeDist)
 {
     return(MakeTransitionDocNode(settings, explicitMods, isotopeDist, Annotations.EMPTY, TransitionDocNode.TransitionQuantInfo.DEFAULT, ExplicitTransitionValues.EMPTY, null));
 }
Exemple #16
0
        public static TransitionDocNode FromTransitionProto(AnnotationScrubber scrubber, SrmSettings settings,
                                                            TransitionGroup group, ExplicitMods mods, IsotopeDistInfo isotopeDist, ExplicitTransitionValues pre422ExplicitTransitionValues,
                                                            SkylineDocumentProto.Types.Transition transitionProto)
        {
            var         stringPool  = scrubber.StringPool;
            IonType     ionType     = DataValues.FromIonType(transitionProto.FragmentType);
            MeasuredIon measuredIon = null;

            if (transitionProto.MeasuredIonName != null)
            {
                measuredIon = settings.TransitionSettings.Filter.MeasuredIons.SingleOrDefault(
                    i => i.Name.Equals(transitionProto.MeasuredIonName.Value));
                if (measuredIon == null)
                {
                    throw new InvalidDataException(string.Format(Resources.TransitionInfo_ReadXmlAttributes_The_reporter_ion__0__was_not_found_in_the_transition_filter_settings_, transitionProto.MeasuredIonName));
                }
                ionType = IonType.custom;
            }
            bool           isCustom    = Transition.IsCustom(ionType, group);
            bool           isPrecursor = Transition.IsPrecursor(ionType);
            CustomMolecule customIon   = null;

            if (isCustom)
            {
                if (measuredIon != null)
                {
                    customIon = measuredIon.SettingsCustomIon;
                }
                else if (isPrecursor)
                {
                    customIon = group.CustomMolecule;
                }
                else
                {
                    var formula      = DataValues.FromOptional(transitionProto.Formula);
                    var moleculeID   = MoleculeAccessionNumbers.FromString(DataValues.FromOptional(transitionProto.MoleculeId)); // Tab separated list of InChiKey, CAS etc
                    var monoMassH    = DataValues.FromOptional(transitionProto.MonoMassH);
                    var averageMassH = DataValues.FromOptional(transitionProto.AverageMassH);
                    var monoMass     = DataValues.FromOptional(transitionProto.MonoMass) ?? monoMassH;
                    var averageMass  = DataValues.FromOptional(transitionProto.AverageMass) ?? averageMassH;
                    customIon = new CustomMolecule(formula,
                                                   new TypedMass(monoMass.Value, monoMassH.HasValue ? MassType.MonoisotopicMassH : MassType.Monoisotopic),
                                                   new TypedMass(averageMass.Value, averageMassH.HasValue ? MassType.AverageMassH : MassType.Average),
                                                   DataValues.FromOptional(transitionProto.CustomIonName), moleculeID);
                }
            }
            Transition transition;
            var        adductString = DataValues.FromOptional(transitionProto.Adduct);
            var        adduct       = string.IsNullOrEmpty(adductString)
                ? Adduct.FromChargeProtonated(transitionProto.Charge)
                : Adduct.FromStringAssumeChargeOnly(adductString);

            if (isCustom)
            {
                transition = new Transition(group, isPrecursor ? group.PrecursorAdduct :adduct, transitionProto.MassIndex, customIon, ionType);
            }
            else if (isPrecursor)
            {
                transition = new Transition(group, ionType, group.Peptide.Length - 1, transitionProto.MassIndex,
                                            group.PrecursorAdduct, DataValues.FromOptional(transitionProto.DecoyMassShift));
            }
            else
            {
                int offset = Transition.OrdinalToOffset(ionType, transitionProto.FragmentOrdinal,
                                                        group.Peptide.Length);
                transition = new Transition(group, ionType, offset, transitionProto.MassIndex, adduct, DataValues.FromOptional(transitionProto.DecoyMassShift));
            }
            var losses          = TransitionLosses.FromLossProtos(settings, transitionProto.Losses);
            var mass            = settings.GetFragmentMass(group, mods, transition, isotopeDist);
            var isotopeDistInfo = GetIsotopeDistInfo(transition, losses, isotopeDist);

            if (group.DecoyMassShift.HasValue && transitionProto.DecoyMassShift == null)
            {
                throw new InvalidDataException(Resources.SrmDocument_ReadTransitionXml_All_transitions_of_decoy_precursors_must_have_a_decoy_mass_shift);
            }

            TransitionLibInfo libInfo = null;

            if (transitionProto.LibInfo != null)
            {
                libInfo = new TransitionLibInfo(transitionProto.LibInfo.Rank, transitionProto.LibInfo.Intensity);
            }
            var annotations = scrubber.ScrubAnnotations(Annotations.FromProtoAnnotations(transitionProto.Annotations), AnnotationDef.AnnotationTarget.transition);
            var results     = TransitionChromInfo.FromProtoTransitionResults(scrubber, settings, transitionProto.Results);
            var explicitTransitionValues = pre422ExplicitTransitionValues ?? ExplicitTransitionValues.Create(
                DataValues.FromOptional(transitionProto.ExplicitCollisionEnergy),
                DataValues.FromOptional(transitionProto.ExplicitIonMobilityHighEnergyOffset),
                DataValues.FromOptional(transitionProto.ExplicitSLens),
                DataValues.FromOptional(transitionProto.ExplicitConeVoltage),
                DataValues.FromOptional(transitionProto.ExplicitDeclusteringPotential));

            return(new TransitionDocNode(transition, annotations, losses, mass, new TransitionQuantInfo(isotopeDistInfo, libInfo, !transitionProto.NotQuantitative), explicitTransitionValues, results));
        }
Exemple #17
0
        public IEnumerable <TransitionDocNode> GetPrecursorTransitions(SrmSettings settings,
                                                                       ExplicitMods mods,
                                                                       IPrecursorMassCalc calcPredictPre,
                                                                       IFragmentMassCalc calcPredict,
                                                                       double precursorMz,
                                                                       IsotopeDistInfo isotopeDist,
                                                                       IList <IList <ExplicitLoss> > potentialLosses,
                                                                       IDictionary <double, LibraryRankedSpectrumInfo.RankedMI> transitionRanks,
                                                                       bool libraryFilter,
                                                                       bool useFilter,
                                                                       bool ensureMassesAreMeasurable)
        {
            var      tranSettings = settings.TransitionSettings;
            var      fullScan     = tranSettings.FullScan;
            int      minMz        = tranSettings.Instrument.GetMinMz(precursorMz);
            int      maxMz        = tranSettings.Instrument.MaxMz;
            bool     precursorMS1 = fullScan.IsEnabledMs;
            MassType massType     = tranSettings.Prediction.FragmentMassType;
            MassType massTypeIon  = precursorMS1 ? tranSettings.Prediction.PrecursorMassType : massType;

            var  sequence            = Peptide.Target;
            var  ionTypes            = IsProteomic ? tranSettings.Filter.PeptideIonTypes : tranSettings.Filter.SmallMoleculeIonTypes;
            bool precursorNoProducts = precursorMS1 && !fullScan.IsEnabledMsMs &&
                                       ionTypes.Count == 1 && ionTypes[0] == IonType.precursor;
            var precursorMassPredict = precursorMS1
                ? calcPredictPre.GetPrecursorMass(sequence)
                : calcPredict.GetPrecursorFragmentMass(sequence);

            foreach (var losses in CalcTransitionLosses(IonType.precursor, 0, massType, potentialLosses))
            {
                Adduct productAdduct;
                if (losses == null)
                {
                    productAdduct = PrecursorAdduct;
                }
                else
                {
                    productAdduct = losses.GetProductAdduct(PrecursorAdduct);
                    if (productAdduct == null)
                    {
                        continue;
                    }
                }

                double ionMz = IsProteomic ?
                               SequenceMassCalc.GetMZ(Transition.CalcMass(precursorMassPredict, losses), PrecursorAdduct) :
                               PrecursorAdduct.MzFromNeutralMass(CustomMolecule.GetMass(massTypeIon), massTypeIon);

                if (losses == null)
                {
                    if (precursorMS1 && isotopeDist != null && ensureMassesAreMeasurable)
                    {
                        foreach (int i in fullScan.SelectMassIndices(isotopeDist, useFilter))
                        {
                            var precursorMS1Mass = isotopeDist.GetMassI(i, DecoyMassShift);
                            ionMz = SequenceMassCalc.GetMZ(precursorMS1Mass, PrecursorAdduct);
                            if (minMz > ionMz || ionMz > maxMz)
                            {
                                continue;
                            }
                            var isotopeDistInfo = new TransitionIsotopeDistInfo(
                                isotopeDist.GetRankI(i), isotopeDist.GetProportionI(i));
                            yield return(CreateTransitionNode(i, precursorMS1Mass, isotopeDistInfo, null, transitionRanks, productAdduct));
                        }
                        continue;
                    }
                }
                // If there was loss, it is possible (though not likely) that the ion m/z value
                // will now fall below the minimum measurable value for the instrument
                else if (ensureMassesAreMeasurable && minMz > ionMz)
                {
                    continue;
                }

                // If filtering precursors from MS1 scans, then ranking in MS/MS does not apply
                bool precursorIsProduct = !precursorMS1 || losses != null;
                // Skip product ion precursors, if the should not be included
                if (useFilter && precursorIsProduct && precursorNoProducts)
                {
                    continue;
                }
                if (!useFilter || !precursorIsProduct ||
                    !libraryFilter || IsMatched(transitionRanks, ionMz, IonType.precursor,
                                                PrecursorAdduct, losses))
                {
                    yield return(CreateTransitionNode(0, precursorMassPredict, null, losses,
                                                      precursorIsProduct ? transitionRanks : null, productAdduct));
                }
            }
        }