image size with shortcut groups

User 870ab5b546

01-11-2011 01:32:25

I am having trouble with the new MolPrinter method for finding the best size for a MarvinView applet when the structure contains shortcut groups.  See 24DContracted and 24DNoShortcut below; their only difference is that one has a COOH shortcut group.  I have similar problems when I use Ph, Et, or even Me groups.


 


This wasn't a problem when I was using the old MolImageSize class to get the optimum dimensions -- see 24DContractedOldMethod below -- but it is now with MolPrinter.  Here's the method, with the old MolImageSize code commented out:


 


 


    public static int[] getBestAppletSize(String molStruct,
boolean showAtomMapping) {
final String SELF = "ChemUtils.getBestAppletSize: ";
final int OPT_WIDTH = 250; // preferred # pixels in width
final int MAX_SCALE = 40; // largest scale that looks OK
final int MIN_SCALE = 16; // smallest scale that looks OK
int[] dims = new int[] {OPT_WIDTH, OPT_WIDTH};
if (molStruct == null) {
// debugPrint(SELF + "molStruct is null.");
return dims;
}
// final StringBuilder imgParams = new StringBuilder();
try {
final boolean isLewis = molStruct.contains("Lewis ");
/*
imgParams.append("jpeg:mono,wireframe,scale");
imgParams.append(MAX_SCALE);
imgParams.append(isLewis ? ",H_off" : ",H_heteroterm");
if (showAtomMapping) imgParams.append(",amap");
*/
final Molecule mol = MolImporter.importMol(molStruct);
final MolPrinter printer = new MolPrinter(mol);
printer.setRendering(WIREFRAME_RENDERING_S);
printer.setImplicitH(isLewis ? IMPLICITH_ALL_S : IMPLICITH_HETEROTERM_S);
printer.setScale(MAX_SCALE);
final Rectangle boundingRect =
printer.getBoundingRectangle(
mol.getDocument().getAllMolecules());
// final MolImageSize imgSize = mol.getImageSize(imgParams.toString());
/*
debugPrint(SELF + "for ", molStruct, "\nimage "
+ "at scale 40 has width ", boundingRect.width,
" and height ", boundingRect.height);
/**/
// determine appropriate width
if (boundingRect.width < OPT_WIDTH) {
// use width and height at scale 40
dims[0] = boundingRect.width;
dims[1] = boundingRect.height;
} else {
// scale down
final double smallerScale = ((double) (MAX_SCALE * OPT_WIDTH))
/ (double) boundingRect.width;
if (smallerScale > ((double) MIN_SCALE)) {
// use optimum width
dims[0] = OPT_WIDTH;
dims[1] = (boundingRect.height * OPT_WIDTH) / boundingRect.width;
} else {
// use width that gives minimum bond length
dims[0] = (boundingRect.width * MIN_SCALE) / MAX_SCALE;
dims[1] = (boundingRect.height * MIN_SCALE) / MAX_SCALE;
} // if scale
} // if boundingRect.width
/*
debugPrint(SELF + "setting image size to width ",
dims[0], " and height ", dims[1]);
/**/
} catch (MolFormatException e1) {
System.out.println(SELF + "MolFormatException for " + molStruct);
e1.printStackTrace();
} catch (Exception e2) {
System.out.println(SELF + "got the following exception on "
+ molStruct);
e2.printStackTrace();
}
return dims;
} // getBestAppletSize(String, boolean)

 


Is this a bug in MolPrinter, or is there an easy way to fix this problem?

User 870ab5b546

01-11-2011 18:48:53

In an effort to solve this problem, I decided to convert shortcut groups to pseudoatoms.  I proceeded to cause a NullPointerException in MolPrinter.


INFO: ChemUtils.sGroupsToPseudoatoms: starting with:
<?xml version="1.0" ?>
<cml>
<MDocument>
<MChemicalStruct>
<molecule molID="m1">
<atomArray
atomID="a1 a2 a3 a4 a5 a6 a7 a8"
elementType="C C C C C C R N"
sgroupRef="0 0 0 0 0 0 sg1 0"
x2="1.203125 -0.13054434104825674 -0.13054434104825674 1.203125 2.5367943410482567 2.5367943410482567 1.203125 1.203125"
y2="20.88628346150138 20.116266520942343 18.57623263982426 17.80621569926522 18.57623263982426 20.116266520942343 22.42628346150138 16.26621569926522"
/>
<bondArray>
<bond atomRefs2="a1 a2" order="1" />
<bond atomRefs2="a2 a3" order="2" />
<bond atomRefs2="a3 a4" order="1" />
<bond atomRefs2="a4 a5" order="2" />
<bond atomRefs2="a5 a6" order="1" />
<bond atomRefs2="a1 a6" order="2" />
<bond atomRefs2="a1 a7" order="1" />
<bond atomRefs2="a4 a8" order="1" />
</bondArray>
<molecule id="sg1" role="SuperatomSgroup" title="COOH"
leftName="HOOC" molID="m2">
<atomArray
atomID="a9 a10 a11"
elementType="C O O"
attachmentPoint="1 0 0"
sgroupAttachmentPoint="1 0 0"
x2="0.14437496662139893 1.4780540884494346 -1.1893041552066368"
y2="51.413540827433266 52.18354082743327 52.18354082743327"
/>
<bondArray>
<bond atomRefs2="a10 a9" order="1" />
<bond atomRefs2="a9 a11" order="2" />
</bondArray>
</molecule>
</molecule>
</MChemicalStruct>
</MDocument>
</cml>

ChemUtils.sGroupsToPseudoatoms: returning:
<?xml version="1.0" ?>
<cml>
<MDocument>
<MChemicalStruct>
<molecule molID="m1">
<atomArray
atomID="a1 a2 a3 a4 a5 a6 a7 a8"
elementType="C C C C C C C N"
mrvPseudo="0 0 0 0 0 0 COOH 0"
x2="1.203125 -0.13054434104825674 -0.13054434104825674 1.203125 2.5367943410482567 2.5367943410482567 1.203125 1.203125"
y2="20.88628346150138 20.116266520942343 18.57623263982426 17.80621569926522 18.57623263982426 20.116266520942343 22.42628346150138 16.26621569926522"
/>
<bondArray>
<bond atomRefs2="a1 a2" order="1" />
<bond atomRefs2="a2 a3" order="2" />
<bond atomRefs2="a3 a4" order="1" />
<bond atomRefs2="a4 a5" order="2" />
<bond atomRefs2="a5 a6" order="1" />
<bond atomRefs2="a1 a6" order="2" />
<bond atomRefs2="a1 a7" order="1" />
<bond atomRefs2="a4 a8" order="1" />
</bondArray>
</molecule>
</MChemicalStruct>
</MDocument>
</cml>

ChemUtils.getBestAppletSize: got the following exception on:
<?xml version="1.0" ?>
<MDocument>
<MChemicalStruct>
<molecule molID="m1">
<atomArray
atomID="a1 a2 a3 a4 a5 a6 a7 a8"
elementType="C C C C C C R N"
sgroupRef="0 0 0 0 0 0 sg1 0"
x2="1.203125 -0.13054434104825674 -0.13054434104825674 1.203125 2.5367943410482567 2.5367943410482567 1.203125 1.203125"
y2="20.88628346150138 20.116266520942343 18.57623263982426 17.80621569926522 18.57623263982426 20.116266520942343 22.42628346150138 16.26621569926522"
/>
<bondArray>
<bond atomRefs2="a1 a2" order="1" />
<bond atomRefs2="a2 a3" order="2" />
<bond atomRefs2="a3 a4" order="1" />
<bond atomRefs2="a4 a5" order="2" />
<bond atomRefs2="a5 a6" order="1" />
<bond atomRefs2="a1 a6" order="2" />
<bond atomRefs2="a1 a7" order="1" />
<bond atomRefs2="a4 a8" order="1" />
</bondArray>
<molecule id="sg1" role="SuperatomSgroup" title="COOH"
leftName="HOOC" molID="m2">
<atomArray
atomID="a9 a10 a11"
elementType="C O O"
attachmentPoint="1 0 0"
x2="0.14437496662139893 1.4780540884494346 -1.1893041552066368"
y2="51.413540827433266 52.18354082743327 52.18354082743327"
/>
<bondArray>
<bond atomRefs2="a10 a9" order="1" />
<bond atomRefs2="a9 a11" order="2" />
</bondArray>
</molecule>
</molecule>
</MChemicalStruct>
</MDocument>

java.lang.NullPointerException
at chemaxon.struc.Molecule.setGUIContracted(Molecule.java:2611)
at chemaxon.struc.Molecule.setGUIContracted(Molecule.java:2593)
at chemaxon.marvin.MolPrinter.initMol(MolPrinter.java:913)
at chemaxon.marvin.MolPrinter.<init>(MolPrinter.java:108)
at chemaxon.marvin.MolPrinter.<init>(MolPrinter.java:93)
at com.epoch.chem.ChemUtils.getBestAppletSize(ChemUtils.java:253)
at org.apache.jsp.authortool.questionsList_jsp._jspService(questionsList_jsp.java:1079)


The relevant code:


            final Molecule mol = MolImporter.importMol(molStruct);
sGroupsToPseudoatoms(mol);
final MolPrinter printer = new MolPrinter(mol);

    public static void sGroupsToPseudoatoms(Molecule mol) {
final String SELF = "ChemUtils.sGroupsToPseudoatoms: ";
debugPrintMRV(SELF + "starting with:\n", mol);
final Sgroup[] sgroups = mol.getSgroupArray();
for (Sgroup sgroupRaw : sgroups) {
final SuperatomSgroup sgroup = (SuperatomSgroup) sgroupRaw;
final SgroupAtom superatom = sgroup.getSuperAtom();
final String symb = superatom.getSymbol();
final int mapNum = superatom.getAtomMap();
final MolAtom attachPt = sgroup.findAttachAtom();
final MolAtom[] sgAtoms = sgroup.getAtomArray();
final int numSgAtoms = sgAtoms.length;
for (int sgAtomNum = numSgAtoms - 1; sgAtomNum >= 0; sgAtomNum--) {
final MolAtom sgAtom = sgAtoms[sgAtomNum];
// In the following line, we really mean pointer equality.
if (sgAtom == attachPt) {
sgAtom.setAtno(MolAtom.PSEUDO);
sgAtom.setAliasstr(symb);
if (mapNum > 0) {
sgAtom.setAtomMap(mapNum);
debugPrint(SELF + "shortcut group ",
symb, " has map number ", mapNum);
} else {
debugPrint(SELF + "shortcut group ",
symb, " is unmapped.");
}
} else { // sgroup atom is not attachment point
mol.removeAtom(sgAtom);
} // if sgroup atom is not attachment point
} // for each atom in sgroup
} // for each shortcut group
mol.ungroupSgroups();
debugPrintMRV(SELF + "returning:\n", mol);
} // sGroupsToPseudoatoms(Molecule)

ChemAxon 5433b8e56b

04-11-2011 12:10:10

Hi Bob,


sorry for the late reply, i have forwarded the issue with setGUIContracted issue from MolPrinter to the core team, they are examining the problem, as soon as i have the answer from them i will forward it to you.


We are also examining the image metrics issue, we will notify you about the results, as soon as possible.


Regards,
Istvan

ChemAxon 25dcd765a3

05-11-2011 18:31:49

We have fixed the setGUIContracted issue.


The fix is will be included in 5.8 release.


Thank you for the report.

User 870ab5b546

08-11-2011 02:27:28

Can you suggest a workaround for the problem in the meantime?

ChemAxon 25dcd765a3

08-11-2011 15:14:21

Hi Bob,


Please try this workaround:


sGroupsToPseudoatoms(mol);
MDocument doc;
if (mol.getDocument()==null){
    doc = new MDocument(mol);
} else {
    doc = mol.getDocument();
}
sGroupsToPseudoatoms((Molecule)doc.getMainMoleculeGraph());

So try to do the pseudo atom conversion for the mainMolecule of the document also.


Let me know if it does not work.

User 870ab5b546

08-11-2011 15:41:08

 



Thanks, that helps a lot, though it would be best to fix the original problem so I don't have to replace all the shortcut groups with pseudoatoms (twice, no less).



 

ChemAxon 25dcd765a3

09-11-2011 08:41:13










bobgr wrote:

Thanks, that helps a lot, though it would be best to fix the original problem so I don't have to replace all the shortcut groups with pseudoatoms (twice, no less).





We (core team) have solved the issue which is connected to this double conversion. So you don't need the workaround after 5.8.


Istvan (Marvin team) can tell more about the image metrics issue and the fix (as far as I understand that is the original issue).

ChemAxon 5433b8e56b

23-11-2011 11:48:15

Hi Bob,


we tried to find the cause and push the fix into 5.8, but we do not have enough time to do it. We will keen on to include the fix for bounding rectangle calculation in the next release.


Regards,
Istvan

User 870ab5b546

23-11-2011 14:41:11

Thanks for the update.  The workaround works, so I can be patient.

User 870ab5b546

14-08-2012 01:33:06

Since the fix was apparently in 5.8ff, and we're now up to 5.10, I removed the workaround to see what would happen.  I can remove the two calls to sGroupsToPseudoatoms(), but I need to preserve the printer.setScale() command.

ChemAxon 5433b8e56b

24-09-2012 23:10:19

Hi Bob,


Sorry for the late catch up on this, as I understood you have the workaround and it worked ok, and we did not had the time to check the issue thoroughly inside the printer until now.


As we found the size is calculated well in this case, and in the cases we have tested beyond your example structure. We have put effort on the fine tuning of size calculation, after your report, and with 5.10 and 5.11 it is working for me with MolPrinter just as before with the getImageSize method.


The need to set the scale which for the size is calculated is natural, just as it was required before to set the scale part of the parameter of the getImageSize method. It is not really clear for me that is it a complaint about the required setScale call, or just a statement? If you have any suggestion about how to make it more comfortable for use please do not hasitate to write it for us.


Regards,
Istvan

User 870ab5b546

27-09-2012 15:40:38

It was not a complaint, just a statement for the record.