import jalview.io.AlignFile;
import jalview.io.FileParse;
import jalview.schemes.ResidueProperties;
+import jalview.util.Comparison;
import jalview.util.MessageManager;
import java.io.IOException;
+import java.util.ArrayList;
import java.util.Hashtable;
+import java.util.List;
import java.util.Map;
import javajs.awt.Dimension;
import org.jmol.api.JmolStatusListener;
import org.jmol.api.JmolViewer;
import org.jmol.c.CBK;
+import org.jmol.c.STR;
import org.jmol.modelset.Group;
import org.jmol.modelset.Model;
import org.jmol.modelset.ModelSet;
import org.jmol.modelsetbio.BioModel;
import org.jmol.modelsetbio.BioPolymer;
+import org.jmol.modelsetbio.Monomer;
import org.jmol.viewer.Viewer;
/**
{
viewer = (Viewer) JmolViewer.allocateViewer(null, null, null, null,
null, "-x -o -n", this);
+ // ensure the 'new' (DSSP) not 'old' (Ramachandran) SS method is used
+ viewer.setBooleanProperty("defaultStructureDSSP", true);
} catch (ClassCastException x)
{
throw new Error(MessageManager.formatMessage(
}
}
- /*
- * (non-Javadoc)
+ /**
+ * Convert Jmol's secondary structure code to Jalview's, and stored it in the
+ * secondary structure arrays at the given sequence position
*
- * @see jalview.io.AlignFile#parse()
+ * @param proteinStructureSubType
+ * @param pos
+ * @param secstr
+ * @param secstrcode
*/
- @Override
- public void parse() throws IOException
+ protected void setSecondaryStructure(STR proteinStructureSubType,
+ int pos, char[] secstr, char[] secstrcode)
{
- Viewer jmd = getJmolData();
- jmd.openReader(getDataName(), getDataName(), getReader());
- waitForScript(jmd);
-
- if (jmd.ms.mc > 0)
+ switch (proteinStructureSubType)
{
- ModelSet ms = jmd.ms;
- // Jmol 14.2 added third argument doReport = false
- ms.calculateStructures(null, true, false, false, true);
- // System.out.println("Structs\n"+structs);
- Group group = null;
- int modelIndex = -1;
- for (Model model : ms.am)
+ case HELIX310:
+ if (secstr[pos] == 0)
{
- modelIndex++;
- for (BioPolymer bp : ((BioModel) model).bioPolymers)
- {
- int lastChainId = 0; // int value of character e.g. 65 for A
- String lastChainIdAlpha = "";
-
- int[] groups = bp.getLeadAtomIndices();
- char seq[] = new char[groups.length], secstr[] = new char[groups.length], secstrcode[] = new char[groups.length];
- int groupc = 0, len = 0, firstrnum = 1, lastrnum = 0;
-
- do
- {
- if (groupc >= groups.length
- || ms.at[groups[groupc]].group.chain.chainID != lastChainId)
- {
- /*
- * on change of chain (or at end), construct the sequence and
- * secondary structure annotation for the last chain
- */
- if (len > 0)
- {
- boolean isNa = bp.isNucleic();
- // normalise sequence from Jmol to jalview
- int[] cinds = isNa ? ResidueProperties.nucleotideIndex
- : ResidueProperties.aaIndex;
- int nonGap = isNa ? ResidueProperties.maxNucleotideIndex
- : ResidueProperties.maxProteinIndex;
- char ngc = 'X';
- char newseq[] = new char[len];
- Annotation asecstr[] = new Annotation[len + firstrnum - 1];
- for (int p = 0; p < len; p++)
- {
- newseq[p] = cinds[seq[p]] == nonGap ? ngc : seq[p];
- if (secstr[p] >= 'A' && secstr[p] <= 'z')
- {
- try
- {
- asecstr[p] = new Annotation("" + secstr[p], null,
- secstrcode[p], Float.NaN);
- } catch (ArrayIndexOutOfBoundsException e)
- {
- // skip - patch for JAL-1836
- }
- }
- }
- String modelTitle = (String) ms
- .getInfo(modelIndex, "title");
- SequenceI sq = new Sequence("" + getDataName() + "|"
- + modelTitle + "|" + lastChainIdAlpha, newseq,
- firstrnum, lastrnum);
- PDBEntry pdbe = new PDBEntry();
- pdbe.setFile(getDataName());
- pdbe.setId(getDataName());
- pdbe.setProperty(new Hashtable());
- // pdbe.getProperty().put("CHAIN", "" + _lastChainId);
- pdbe.setChainCode(lastChainIdAlpha);
- sq.addPDBId(pdbe);
- // JAL-1533
- // Need to put the number of models for this polymer somewhere
- // for Chimera/others to grab
- // pdbe.getProperty().put("PDBMODELS", biopoly.)
- seqs.add(sq);
- if (!isNa)
- {
- String mt = modelTitle == null ? getDataName()
- : modelTitle;
- if (lastChainId >= ' ')
- {
- mt += lastChainIdAlpha;
- }
- AlignmentAnnotation ann = new AlignmentAnnotation(
- "Secondary Structure", "Secondary Structure for "
- + mt, asecstr);
- ann.belowAlignment = true;
- ann.visible = true;
- ann.autoCalculated = false;
- ann.setCalcId(getClass().getName());
- sq.addAlignmentAnnotation(ann);
- ann.adjustForAlignment();
- ann.validateRangeAndDisplay();
- annotations.add(ann);
- }
- }
- len = 0;
- firstrnum = 1;
- lastrnum = 0;
- }
- if (groupc < groups.length)
- {
- group = ms.at[groups[groupc]].group;
- if (len == 0)
- {
- firstrnum = group.getResno();
- lastChainId = group.chain.chainID;
- lastChainIdAlpha = group.chain.getIDStr();
- }
- else
- {
- lastrnum = group.getResno();
- }
- seq[len] = group.getGroup1();
-
- /*
- * JAL-1828 replace a modified amino acid with its standard
- * equivalent (e.g. MSE with MET->M) to maximise sequence matching
- */
- String threeLetterCode = group.getGroup3();
- String canonical = ResidueProperties
- .getCanonicalAminoAcid(threeLetterCode);
- if (canonical != null
- && !canonical.equalsIgnoreCase(threeLetterCode))
- {
- seq[len] = ResidueProperties
- .getSingleCharacterCode(canonical);
- }
- switch (group.getProteinStructureSubType())
- {
- case HELIX310:
- if (secstr[len] == 0)
- {
- secstr[len] = '3';
- }
- case HELIXALPHA:
- if (secstr[len] == 0)
- {
- secstr[len] = 'H';
- }
- case HELIXPI:
- if (secstr[len] == 0)
- {
- secstr[len] = 'P';
- }
- case HELIX:
- if (secstr[len] == 0)
- {
- secstr[len] = 'H';
- }
- secstrcode[len] = 'H';
- break;
- case SHEET:
- secstr[len] = 'E';
- secstrcode[len] = 'E';
- break;
- default:
- secstr[len] = 0;
- secstrcode[len] = 0;
- }
- len++;
- }
- } while (groupc++ < groups.length);
- }
+ secstr[pos] = '3';
}
-
- /*
- * lastScriptTermination = -9465; String dsspOut =
- * jmd.evalString("calculate STRUCTURE"); if (dsspOut.equals("pending")) {
- * while (lastScriptTermination == -9465) { try { Thread.sleep(50); }
- * catch (Exception x) { } ; } } System.out.println(lastConsoleEcho);
- */
+ case HELIXALPHA:
+ if (secstr[pos] == 0)
+ {
+ secstr[pos] = 'H';
+ }
+ case HELIXPI:
+ if (secstr[pos] == 0)
+ {
+ secstr[pos] = 'P';
+ }
+ case HELIX:
+ if (secstr[pos] == 0)
+ {
+ secstr[pos] = 'H';
+ }
+ secstrcode[pos] = 'H';
+ break;
+ case SHEET:
+ secstr[pos] = 'E';
+ secstrcode[pos] = 'E';
+ break;
+ default:
+ secstr[pos] = 0;
+ secstrcode[pos] = 0;
}
}
- /*
- * (non-Javadoc)
+ /**
+ * Convert any non-standard peptide codes to their standard code table
+ * equivalent. (Initial version only does Selenomethionine MSE->MET.)
*
- * @see jalview.io.AlignFile#print()
+ * @param threeLetterCode
+ * @param seq
+ * @param pos
+ */
+ protected void replaceNonCanonicalResidue(String threeLetterCode,
+ char[] seq, int pos)
+ {
+ String canonical = ResidueProperties
+ .getCanonicalAminoAcid(threeLetterCode);
+ if (canonical != null && !canonical.equalsIgnoreCase(threeLetterCode))
+ {
+ seq[pos] = ResidueProperties.getSingleCharacterCode(canonical);
+ }
+ }
+
+ /**
+ * Not implemented - returns null
*/
@Override
public String print()
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented
+ */
@Override
public void setCallbackFunction(String callbackType,
String callbackFunction)
{
- // TODO Auto-generated method stub
-
}
- /*
- * @Override public void notifyCallback(EnumCallback type, Object[] data) {
- * try { switch (type) { case ERROR: case SCRIPT:
- * notifyScriptTermination((String) data[2], ((Integer) data[3]).intValue());
- * break; case MESSAGE: sendConsoleMessage((data == null) ? ((String) null) :
- * (String) data[1]); break; case LOADSTRUCT: notifyFileLoaded((String)
- * data[1], (String) data[2], (String) data[3], (String) data[4], ((Integer)
- * data[5]).intValue());
- *
- * break; default: // System.err.println("Unhandled callback " + type + " " //
- * + data[1].toString()); break; } } catch (Exception e) {
- * System.err.println("Squashed Jmol callback handler error:");
- * e.printStackTrace(); } }
- */
- public void notifyCallback(CBK type, Object[] data)
+ @Override
+ public void notifyCallback(CBK cbType, Object[] data)
{
String strInfo = (data == null || data[1] == null ? null : data[1]
.toString());
- switch (type)
+ switch (cbType)
{
case ECHO:
sendConsoleEcho(strInfo);
}
}
+ /**
+ * Not implemented - returns null
+ */
@Override
public String eval(String strEval)
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented - returns null
+ */
@Override
public float[][] functionXY(String functionName, int x, int y)
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented - returns null
+ */
@Override
public float[][][] functionXYZ(String functionName, int nx, int ny, int nz)
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented - returns null
+ */
@Override
- public String createImage(String fileName, String type,
+ public String createImage(String fileName, String imageType,
Object text_or_bytes, int quality)
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented - returns null
+ */
@Override
public Map<String, Object> getRegistryInfo()
{
- // TODO Auto-generated method stub
return null;
}
+ /**
+ * Not implemented
+ */
@Override
public void showUrl(String url)
{
- // TODO Auto-generated method stub
-
}
+ /**
+ * Not implemented - returns null
+ */
@Override
public Dimension resizeInnerPanel(String data)
{
return null;
}
+ /**
+ * Calls the Jmol library to parse the PDB file, and then inspects the
+ * resulting object model to generate Jalview-style sequences, with secondary
+ * structure annotation added where available (i.e. where it has been computed
+ * by Jmol using DSSP).
+ *
+ * @see jalview.io.AlignFile#parse()
+ */
+ @Override
+ public void parse() throws IOException
+ {
+ Viewer jmolModel = getJmolData();
+ jmolModel.openReader(getDataName(), getDataName(), getReader());
+ waitForScript(jmolModel);
+
+ /*
+ * Convert one or more Jmol Model objects to Jalview objects.
+ */
+ if (jmolModel.ms.mc > 0)
+ {
+ parseBiopolymers(jmolModel.ms);
+ }
+ }
+
+ /**
+ * Process the Jmol BioPolymer array and generate a Jalview sequence for each
+ * chain found (including any secondary structure annotation from DSSP)
+ *
+ * @param ms
+ * @throws IOException
+ */
+ public void parseBiopolymers(ModelSet ms) throws IOException
+ {
+ int modelIndex = -1;
+ for (Model model : ms.am)
+ {
+ modelIndex++;
+ String modelTitle = (String) ms.getInfo(modelIndex, "title");
+
+ /*
+ * as chains can span BioPolymers, we first make a flattened list,
+ * and then work out the lengths of chains present
+ */
+ List<Monomer> monomers = getMonomers(ms, (BioModel) model);
+ List<Integer> chainLengths = getChainLengths(monomers);
+
+ /*
+ * now chop up the Monomer list to make Jalview Sequences
+ */
+ int from = 0;
+ for (int length : chainLengths)
+ {
+ buildSequenceFromChain(monomers.subList(from, from + length), modelTitle);
+ from += length;
+ }
+ }
+ }
+
+ /**
+ * Helper method to construct a sequence for one chain and add it to the seqs
+ * list
+ *
+ * @param monomers
+ * a list of all monomers in the chain
+ * @param modelTitle
+ */
+ protected void buildSequenceFromChain(List<Monomer> monomers, String modelTitle)
+ {
+ final int length = monomers.size();
+
+ /*
+ * arrays to hold sequence and secondary structure
+ */
+ char[] seq = new char[length];
+ char[] secstr = new char[length];
+ char[] secstrcode = new char[length];
+
+ /*
+ * populate the sequence and secondary structure arrays
+ */
+ extractJmolChainData(monomers, seq, secstr, secstrcode);
+
+ /*
+ * grab chain code and start position from first residue;
+ */
+ String chainId = monomers.get(0).chain.getIDStr();
+ int firstResNum = monomers.get(0).getResno();
+ if (firstResNum < 1)
+ {
+ // Jalview doesn't like residue < 1, so force this to 1
+ System.err.println("Converting chain " + chainId + " first RESNUM ("
+ + firstResNum + ") to 1");
+ firstResNum = 1;
+ }
+
+ /*
+ * convert any non-gap unknown residues to 'X'
+ */
+ convertNonGapCharacters(seq);
+
+ /*
+ * construct and add the Jalview sequence
+ */
+ SequenceI sq = new Sequence("" + getDataName() + "|" + modelTitle + "|"
+ + chainId, seq, firstResNum, firstResNum + length - 1);
+ seqs.add(sq);
+
+ /*
+ * add secondary structure predictions (if any)
+ */
+ addSecondaryStructureAnnotation(modelTitle, sq, secstr, secstrcode,
+ chainId, firstResNum);
+
+ /*
+ * record the PDB id for the sequence
+ */
+ addPdbid(sq, chainId);
+ }
+
+ /**
+ * Scans the list of (Jmol) Monomer objects, and adds the residue for each to
+ * the sequence array, and any converted secondary structure prediction to the
+ * secondary structure arrays
+ *
+ * @param monomers
+ * @param seq
+ * @param secstr
+ * @param secstrcode
+ */
+ protected void extractJmolChainData(List<Monomer> monomers, char[] seq,
+ char[] secstr, char[] secstrcode)
+ {
+ int pos = 0;
+ for (Monomer monomer : monomers)
+ {
+ seq[pos] = monomer.getGroup1();
+
+ /*
+ * JAL-1828 replace a modified amino acid with its standard
+ * equivalent (e.g. MSE with MET->M) to maximise sequence matching
+ */
+ replaceNonCanonicalResidue(monomer.getGroup3(), seq, pos);
+
+ /*
+ * if Jmol has derived a secondary structure prediction for
+ * this position, convert it to Jalview equivalent and save it
+ */
+ setSecondaryStructure(monomer.getProteinStructureSubType(), pos,
+ secstr, secstrcode);
+ pos++;
+ }
+ }
+
+ /**
+ * Helper method that adds an AlignmentAnnotation for secondary structure to
+ * the sequence, provided at least one secondary structure prediction has been
+ * made
+ *
+ * @param modelTitle
+ * @param seq
+ * @param secstr
+ * @param secstrcode
+ * @param chainId
+ * @param firstResNum
+ * @return
+ */
+ protected void addSecondaryStructureAnnotation(String modelTitle,
+ SequenceI sq, char[] secstr, char[] secstrcode,
+ String chainId, int firstResNum)
+ {
+ char[] seq = sq.getSequence();
+ boolean ssFound = false;
+ Annotation asecstr[] = new Annotation[seq.length + firstResNum - 1];
+ for (int p = 0; p < seq.length; p++)
+ {
+ if (secstr[p] >= 'A' && secstr[p] <= 'z')
+ {
+ asecstr[p] = new Annotation(String.valueOf(secstr[p]), null,
+ secstrcode[p], Float.NaN);
+ ssFound = true;
+ }
+ }
+
+ if (ssFound)
+ {
+ String mt = modelTitle == null ? getDataName() : modelTitle;
+ mt += chainId;
+ AlignmentAnnotation ann = new AlignmentAnnotation(
+ "Secondary Structure", "Secondary Structure for " + mt,
+ asecstr);
+ ann.belowAlignment = true;
+ ann.visible = true;
+ ann.autoCalculated = false;
+ ann.setCalcId(getClass().getName());
+ ann.adjustForAlignment();
+ ann.validateRangeAndDisplay();
+ annotations.add(ann);
+ sq.addAlignmentAnnotation(ann);
+ }
+ }
+
+ /**
+ * Replace any non-gap miscellaneous characters with 'X'
+ *
+ * @param seq
+ * @return
+ */
+ protected void convertNonGapCharacters(char[] seq)
+ {
+ boolean isNa = Comparison.areNucleotide(new char[][] { seq });
+ int[] cinds = isNa ? ResidueProperties.nucleotideIndex
+ : ResidueProperties.aaIndex;
+ int nonGap = isNa ? ResidueProperties.maxNucleotideIndex
+ : ResidueProperties.maxProteinIndex;
+
+ for (int p = 0; p < seq.length; p++)
+ {
+ if (cinds[seq[p]] == nonGap)
+ {
+ seq[p] = 'X';
+ }
+ }
+ }
+
+ /**
+ * @param sq
+ * @param chainId
+ */
+ protected void addPdbid(SequenceI sq, String chainId)
+ {
+ PDBEntry pdbe = new PDBEntry();
+ pdbe.setFile(getDataName());
+ pdbe.setId(getDataName());
+ pdbe.setProperty(new Hashtable());
+ // pdbe.getProperty().put("CHAIN", "" + _lastChainId);
+ pdbe.setChainCode(chainId);
+ sq.addPDBId(pdbe);
+ }
+
+ /**
+ * Scans the list of Monomers (residue models), inspecting the chain id for
+ * each, and returns an array whose length is the number of chains, and values
+ * the length of each chain
+ *
+ * @param monomers
+ * @return
+ */
+ protected List<Integer> getChainLengths(List<Monomer> monomers)
+ {
+ List<Integer> chainLengths = new ArrayList<Integer>();
+ int lastChainId = -1;
+ int length = 0;
+
+ for (Monomer monomer : monomers)
+ {
+ int chainId = monomer.chain.chainID;
+ if (chainId != lastChainId && length > 0)
+ {
+ /*
+ * change of chain - record the length of the last one
+ */
+ chainLengths.add(length);
+ length = 0;
+ }
+ lastChainId = chainId;
+ length++;
+ }
+ if (length > 0)
+ {
+ /*
+ * record the length of the final chain
+ */
+ chainLengths.add(length);
+ }
+
+ return chainLengths;
+ }
+
+ /**
+ * Returns a flattened list of Monomer (residue) in order, across all
+ * BioPolymers in the model. This simplifies assembling chains which span
+ * BioPolymers. The result does not include any alternate residues reported
+ * for the same sequence position (RESNUM value).
+ *
+ * @param ms
+ * @param model
+ * @return
+ */
+ protected List<Monomer> getMonomers(ModelSet ms, BioModel model)
+ {
+ List<Monomer> result = new ArrayList<Monomer>();
+ String lastSeqCode = "";
+
+ for (BioPolymer bp : model.bioPolymers) {
+ for (int groupLeadAtoms : bp.getLeadAtomIndices())
+ {
+ Group group = ms.at[groupLeadAtoms].group;
+ if (group instanceof Monomer)
+ {
+ /*
+ * ignore alternate residue at same position
+ * example: 1ejg has residues A:LEU, B:ILE, C:ILE at RESNUM=25
+ */
+ String seqcodeString = group.getSeqcodeString();
+ if (!lastSeqCode.equals(seqcodeString))
+ {
+ result.add((Monomer) group);
+ }
+ else
+ {
+ System.out.println("skipping");
+ }
+ lastSeqCode = seqcodeString;
+ }
+ }
+ }
+ return result;
+ }
+
}
*/
public class PDBFileWithJmolTest
{
+ /*
+ * 1GAQ has been reduced to alpha carbons only
+ * 1QCF is the full PDB file including headers, HETATM etc
+ */
String[] testFile = new String[] { "./examples/1GAQ.txt",
"./test/jalview/ext/jmol/1QCF.pdb" }; // ,
- // "./examples/DNMT1_MOUSE.pdb"
- // };
+ //@formatter:off
+ // a modified and very cut-down extract of 4UJ4
+ String pdbWithChainBreak =
+ "HEADER TRANSPORT PROTEIN 08-APR-15 4UJ4\n" +
+ // chain B has missing residues; these should all go in the same sequence:
+ "ATOM 1909 CA VAL B 358 21.329 -19.739 -67.740 1.00201.05 C\n" +
+ "ATOM 1916 CA GLY B 359 21.694 -23.563 -67.661 1.00198.09 C\n" +
+ "ATOM 1920 CA LYS B 367 32.471 -12.135 -77.100 1.00257.97 C\n" +
+ "ATOM 1925 CA ALA B 368 31.032 -9.324 -74.946 1.00276.01 C\n" +
+ // switch to chain C; should be a separate sequence
+ "ATOM 1930 CA SER C 369 32.589 -7.517 -71.978 1.00265.44 C\n" +
+ "ATOM 1936 CA ALA C 370 31.650 -6.849 -68.346 1.00249.48 C\n";
+ //@formatter:on
+
+ //@formatter:off
+ // a very cut-down extract of 1ejg
+ String pdbWithAltLoc =
+ "HEADER TRANSPORT PROTEIN 08-APR-15 1EJG\n" +
+ "ATOM 448 CA ALA A 24 6.619 16.195 1.970 1.00 1.65 C\n" +
+ "ATOM 458 CA ALEU A 25 3.048 14.822 1.781 0.57 1.48 C\n" +
+ // alternative residue 25 entries (with ILE instead of LEU) should be ignored:
+ "ATOM 478 CA BILE A 25 3.048 14.822 1.781 0.21 1.48 C\n" +
+ // including the next altloc causes the unit test to fail but it works with the full file
+ // not sure why!
+ // "ATOM 479 CA CILE A 25 3.048 14.822 1.781 0.22 1.48 C\n" +
+ "ATOM 512 CA CYS A 26 4.137 11.461 3.154 1.00 1.52 C\n";
+ //@formatter:on
@BeforeMethod(alwaysRun = true)
public void setUp()
"Secondary structure not associated for sequence "
+ sq.getName(), sq.getAnnotation()[0].sequenceRef == sq);
}
+
+ /**
+ * Test parsing a chain with missing residues
+ *
+ * @throws Exception
+ */
+ @Test(groups = { "Functional" })
+ public void testParse_missingResidues() throws Exception
+ {
+ PDBfile mctest = new PDBfile(false, false, false, pdbWithChainBreak,
+ AppletFormatAdapter.PASTE);
+ PDBFileWithJmol jtest = new PDBFileWithJmol(pdbWithChainBreak,
+ jalview.io.AppletFormatAdapter.PASTE);
+ Vector<SequenceI> seqs = jtest.getSeqs();
+ Vector<SequenceI> mcseqs = mctest.getSeqs();
+
+ assertEquals("Failed to find 2 sequences\n", 2, seqs.size());
+ assertEquals("Failed to find 2 sequences\n", 2, mcseqs.size());
+ assertEquals("VGKA", seqs.get(0).getSequenceAsString());
+ assertEquals("VGKA", mcseqs.get(0).getSequenceAsString());
+ assertEquals("SA", seqs.get(1).getSequenceAsString());
+ assertEquals("SA", mcseqs.get(1).getSequenceAsString());
+ }
+
+ /**
+ * Test parsing a chain with 'altloc' residues
+ *
+ * @throws Exception
+ */
+ @Test(groups = { "Functional" })
+ public void testParse_alternativeResidues() throws Exception
+ {
+ PDBfile mctest = new PDBfile(false, false, false, pdbWithAltLoc,
+ AppletFormatAdapter.PASTE);
+ PDBFileWithJmol jtest = new PDBFileWithJmol(pdbWithAltLoc,
+ jalview.io.AppletFormatAdapter.PASTE);
+ Vector<SequenceI> seqs = jtest.getSeqs();
+ Vector<SequenceI> mcseqs = mctest.getSeqs();
+
+ assertEquals("Failed to find 1 sequence\n", 1, seqs.size());
+ assertEquals("Failed to find 1 sequence\n", 1, mcseqs.size());
+ assertEquals("ALC", seqs.get(0).getSequenceAsString());
+ assertEquals("ALC", mcseqs.get(0).getSequenceAsString());
+ }
}