Logo Search packages:      
Sourcecode: adun.app version File versions  Download package

privateStructure.m

/* Copyright 2003  Alexander V. Diemand

    This file is part of MolTalk.

    MolTalk is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.

    MolTalk is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with MolTalk; if not, write to the Free Software
    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA 
 */

/* vim: set filetype=objc: */


#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "privateStructure.oh"
#include "Chain.oh"
#include "privateChain.oh"
#include "ChainFactory.oh"
#include "Residue.oh"
#include "Atom.oh"
#include "Stream.oh"
#include "String.oh"


static NSString *mkTextDate (NSCalendarDate *caldate);



@implementation Structure (Private)


-(void)writePDBHeaderTo:(Stream *)strout  //@nodoc
{
      char buffer;
      int i,counter;
      char end_of_line = { 10, 0 };
      NSRange range;

      /* HEADER */
      NSString *t_date = mkTextDate (date);
      snprintf(buffer,51,"HEADER    %s                                         ",[header cString]);
      snprintf(buffer+50,10,"%s          ",[t_date cString]);
      snprintf(buffer+59,11,"   %s      ",[pdbcode cString]);
      buffer='\0';
      [strout writeCString: buffer];
      [strout writeCString: end_of_line];

      /* TITLE */
      i = [title length];
      if (i <= 60)
      {
            [strout writeString: @"TITLE     "];
            [strout writeString: title];
            i = 60-i;
            buffer='\0';
            for (; i>=0; i--)
            {
                  sprintf(buffer+i," ");
            }
            [strout writeCString: buffer];
            [strout writeCString: end_of_line];
      } else {
            counter = 2;
            range.location = 0;
            range.length = 60;
            [strout writeString: @"TITLE     "];
            [strout writeString: [title substringWithRange: range]];
            [strout writeCString: end_of_line];
            i -= 60;
            range.location += 60;
            while (i > 0)
            {
                  [strout writeString: @"TITLE   "];
                  if (i<60)
                  {
                        range.length = i;
                  }
                  snprintf(buffer,63,"% 2d %s                                                               ",counter,[[title substringWithRange:range]cString]);
                  buffer='\0';
                  [strout writeCString: buffer];
                  i -= range.length;
                  [strout writeCString: end_of_line];
            }
      }


      /* COMPND */

      /* SOURCE */

      /* EXPDTA */

      /* REMARK 2: resolution */

      /* REMARK 4: acceptance of PDB file format V 2.2/1996 */
      [strout writeString: @"REMARK   4                                                            "];
      [strout writeCString: end_of_line];
      [strout writeString: [NSString stringWithFormat:@"REMARK   4 %@ COMPLIES WITH FORMAT V. 2.2, 16-DEC-1996              ",[self pdbcode]]];
      
      [strout writeCString: end_of_line];

      
      /* write MODRES entries for all modified residues */
      Chain *chain;
      Residue *residue;
      NSEnumerator *e_res;
      NSEnumerator *e_chain = [self allChains];
      while ((chain = [e_chain nextObject]))
      {
            e_res = [chain allResidues];
            while ((residue = [e_res nextObject]))
            {
                  if ([residue isModified])
                  {
                        char tbuffer;
                        memset(buffer,32,80);
                        buffer='\0';
                        buffer='\n';
                        buffer='M';buffer='O';buffer='D';buffer='R';buffer='E';buffer='S';
                        buffer = [chain code]; /* chain identifier */
                        [pdbcode getCString: tbuffer maxLength: 4];
                        /* pdb code */
                        buffer=tbuffer;buffer=tbuffer;buffer=tbuffer;buffer=tbuffer;
                        /* residue name */
                        [[residue name] getCString: tbuffer maxLength: 3];
                        buffer=tbuffer;buffer=tbuffer;buffer=tbuffer;
                        /* residue number */
                        snprintf(tbuffer, 10, "% 4u    ", [[residue number] intValue]);
                        for (i=0;i<4;i++)
                        {
                              buffer=tbuffer;
                        }
                        buffer=[residue subcode];
                        /* residue modname */
                        [[residue modname] getCString: tbuffer maxLength: 3];
                        buffer=tbuffer;buffer=tbuffer;buffer=tbuffer;
                        /* modification description */
                        [[residue moddescription] getCString: tbuffer maxLength: 41];
                        for (i=0; (i<[[residue moddescription]length] && i<41); i++)
                        {
                              buffer=tbuffer;
                        }
                        [strout writeCString: buffer];
                  }
            }
      }
}


-(void)writePDBConectTo:(Stream*)strout   //@nodoc
{

      Chain *chain;
      NSEnumerator *e_chain = [chains objectEnumerator];
      while ((chain = [e_chain nextObject]))
      {
            NSEnumerator *e_res = [chain allResidues];
            Residue *residue;
            while ((residue = [e_res nextObject]))
            {
                  [self writePDBConectResidue: residue to: strout];
            }
            e_res = [chain allHeterogens];
            while ((residue = [e_res nextObject]))
            {
                  [self writePDBConectResidue: residue to: strout];
            }
      }
}


-(void)writePDBConectResidue:(Residue*)residue to:(Stream*)strout //@nodoc
{
      NSEnumerator *e_atm = [residue allAtoms];
      Atom *atom;
      while ((atom = [e_atm nextObject]))
      {
            unsigned int i=0;
            NSEnumerator *e_atm2 = [atom allBondedAtoms];
            Atom *atom2;
            char buffer;
            while ( (atom2 = [e_atm2 nextObject]) 
                  && !([[atom name] isEqualToString:@"N"] && [[atom2 name] isEqualToString:@"C"])
                  && ([[atom number] compare: [atom2 number]] == NSOrderedDescending) )
                  /* we don't write covalent bonds N-C betweenn residues
                   * we don't write bonds twice (atom bonds to atom2, and
                   * atom2 bonds to atom)  */
            {
                  if (i==0)
                  {
                        memset(buffer,32,82);
                        buffer='\0';
                        buffer='\n';
                        sprintf(buffer,"CONECT% 5u",[[atom number] intValue]);
                        buffer=' ';
                  }
                  snprintf(buffer+(i*5)+11,6,"% 5u",[[atom2 number] intValue]);
                  i++;
                  buffer=' ';
                  if (i>=4)
                  {
                        i=0;
                        [strout writeCString: buffer];
                  }
            }
            if (i>0)
            {
                  [strout writeCString: buffer];
            }
      }
}


-(void)writePDBChain:(Chain*)chain to:(Stream *)strout fromSerial:(unsigned int*)serial   //@nodoc
{
      Residue *residue;
      NSEnumerator *e_res = [chain allResidues];
      Residue *lastres = nil;
      while ((residue = [e_res nextObject]))
      {
            if ([residue isModified])
            {
                  [self writePDBHeterogen: residue inChain: chain to: strout fromSerial: serial];
            } else {
                  [self writePDBResidue: residue inChain: chain to: strout fromSerial: serial];
            }
            lastres=residue;
      } /* all residues */
      
      /* write out TER */
      if (lastres != nil)
      { /* only if there is an amino acid in this chain */
            char buffer;
            char tbuffer;
            memset(buffer,32,80);
            buffer='\0';
            buffer='\n';
            buffer='T';buffer='E';buffer='R';
            buffer = [chain code]; /* chain identifier */
            [[lastres name] getCString: tbuffer maxLength: 3]; /* residue name */
            buffer = tbuffer; buffer = tbuffer; buffer = tbuffer;
            snprintf(tbuffer, 10, "% 4u    ", [[lastres number] intValue]); /* residue number */
            buffer=tbuffer; buffer=tbuffer; buffer=tbuffer; buffer=tbuffer;
            snprintf(buffer+6,6,"% 5u",*serial); buffer=' '; *serial = *serial + 1;
            [strout writeCString: buffer];
      }
      
      e_res = [chain allHeterogens];
      while ((residue = [e_res nextObject]))
      {
            [self writePDBHeterogen: residue inChain: chain to: strout fromSerial: serial];
      } /* all heterogens */
      
      e_res = [chain allSolvent];
      while ((residue = [e_res nextObject]))
      {
            [self writePDBHeterogen: residue inChain: chain to: strout fromSerial: serial];
      } /* all solvent */
      
}


-(void)writePDBResidue:(Residue*)residue inChain:(Chain*)chain to:(Stream*)strout fromSerial:(unsigned int*)serial      //@nodoc
{
      NSString *t_str;
      int t_chrg;
      char buffer;
      char tbuffer;
      char tbuffer2;
      memset(buffer,32,80);
      buffer='\0';
      buffer='\n';
      buffer='A';buffer='T';buffer='O';buffer='M';
      buffer = [chain code]; /* chain identifier */
      [[residue name] getCString: tbuffer maxLength: 3]; /* residue name */
      buffer = tbuffer; buffer = tbuffer; buffer = tbuffer;
      snprintf(tbuffer, 10, "% 4u    ", [[residue number] intValue]); /* residue number */
      buffer=tbuffer; buffer=tbuffer; buffer=tbuffer; buffer=tbuffer;
      buffer='1';buffer='.';buffer='0';buffer='0'; /* occupancy */

      NSEnumerator *e_atms = [residue allAtoms];
      Atom *atom;
      while ((atom = [e_atms nextObject]))
      {
            double temperature,x,y,z;
            temperature = [atom temperature];
            x = [atom x];
            y = [atom y];
            z = [atom z];
            [atom setNumber: *serial];
            snprintf(buffer+6,6,"% 5u",*serial); *serial = *serial + 1;
            buffer=' ';
            tbuffer=32; tbuffer=32; tbuffer=32; tbuffer=32;
            [[atom name] getCString: tbuffer maxLength: 4];
            if (tbuffer[1]==0) tbuffer=32;
            if (tbuffer[2]==0) tbuffer=32;
            if (tbuffer[3]==0) tbuffer=32;
            [[atom elementName] getCString: tbuffer2 maxLength: 2];
            /* elementName is prefix? */
            if (tbuffer[0]==tbuffer2[0])
            {
                  if (tbuffer2[1]==0) 
                  {  // length == 1
                        buffer=32; buffer=tbuffer;
                        buffer=tbuffer; buffer=tbuffer;
                  } else {
                     // length == 2
                        buffer=tbuffer; buffer=tbuffer;
                        buffer=tbuffer; buffer=tbuffer;
                  }
            } else {
                  buffer=tbuffer; buffer=tbuffer;
                  buffer=tbuffer; buffer=tbuffer;
            }
            sprintf(buffer+30,"% 8.3f",x);
            sprintf(buffer+38,"% 8.3f",y);
            sprintf(buffer+46,"% 8.3f",z);
            buffer=' ';
            sprintf(buffer+60,"%6.2f",temperature);
            buffer=' ';
            t_str = [atom elementName];
            buffer = ' ';
            buffer = ' ';
            if ([t_str length]==1)
            {
                  buffer = (char)[t_str characterAtIndex:0];
            } else {
                  buffer = (char)[t_str characterAtIndex:0];
                  buffer = (char)[t_str characterAtIndex:1];
            }
            buffer = ' ';
            buffer = ' ';
            t_chrg = [atom charge];
            if (t_chrg != 0)
            {
                  if (t_chrg < 0)
                  {
                        buffer = (char)(0-t_chrg+48);
                        buffer = '-';
                  } else {
                        buffer = (char)(t_chrg+48);
                        buffer = '+';
                  }
            }
            [strout writeCString: buffer];
      }
}


-(void)writePDBHeterogen:(Residue*)residue inChain:(Chain*)chain to:(Stream*)strout fromSerial:(unsigned int*)serial    //@nodoc
{
      NSString *t_str;
      int t_chrg;
      char buffer;
      char tbuffer;
      char tbuffer2;
      memset(buffer,32,82);
      buffer='\0';
      buffer='\n';
      buffer='H';buffer='E';buffer='T';buffer='A';buffer='T';buffer='M';
      buffer = [chain code]; /* chain identifier */
      [[residue name] getCString: tbuffer maxLength: 3]; /* residue name */
      buffer = tbuffer; buffer = tbuffer; buffer = tbuffer;
      snprintf(tbuffer, 10, "% 4u    ", [[residue number] intValue]); /* residue number */
      buffer=tbuffer; buffer=tbuffer; buffer=tbuffer; buffer=tbuffer;
      buffer='1';buffer='.';buffer='0';buffer='0'; /* occupancy */

      NSEnumerator *e_atms = [residue allAtoms];
      Atom *atom;
      while ((atom = [e_atms nextObject]))
      {
            double temperature,x,y,z;
            temperature = [atom temperature];
            x = [atom x];
            y = [atom y];
            z = [atom z];
            [atom setNumber: *serial];
            snprintf(buffer+6,6,"% 5u",*serial); *serial = *serial + 1;
            buffer=' ';
            tbuffer=32; tbuffer=32; tbuffer=32; tbuffer=32;
            [[atom name] getCString: tbuffer maxLength: 4];
            if (tbuffer[1]==0) tbuffer=32;
            if (tbuffer[2]==0) tbuffer=32;
            if (tbuffer[3]==0) tbuffer=32;
            [[atom elementName] getCString: tbuffer2 maxLength: 2];
            /* elementName is prefix? */
            if (tbuffer[0]==tbuffer2[0])
            {
                  if (tbuffer2[1]==0) 
                  {  // length == 1
                        buffer=32; buffer=tbuffer;
                        buffer=tbuffer; buffer=tbuffer;
                  } else {
                     // length == 2
                        buffer=tbuffer; buffer=tbuffer;
                        buffer=tbuffer; buffer=tbuffer;
                  }
            } else {
                  buffer=tbuffer; buffer=tbuffer;
                  buffer=tbuffer; buffer=tbuffer;
            }
            sprintf(buffer+30,"% 8.3f",x);
            sprintf(buffer+38,"% 8.3f",y);
            sprintf(buffer+46,"% 8.3f",z);
            buffer=' ';
            sprintf(buffer+60,"%6.2f",temperature);
            buffer=' ';
            buffer = ' ';
            buffer = ' ';
            t_str = [atom elementName];
            if ([t_str length]==1)
            {
                  buffer = (char)[t_str characterAtIndex:0];
            } else {
                  buffer = (char)[t_str characterAtIndex:0];
                  buffer = (char)[t_str characterAtIndex:1];
            }
            buffer = ' ';
            buffer = ' ';
            t_chrg = [atom charge];
            if (t_chrg != 0)
            {
                  if (t_chrg < 0)
                  {
                        buffer = (char)(0-t_chrg+48);
                        buffer = '-';
                  } else {
                        buffer = (char)(t_chrg+48);
                        buffer = '+';
                  }
            }
            [strout writeCString: buffer];
      }
}


-(Chain*)mkChain:(NSNumber*)p_chain //@nodoc
{
      Chain *chain = [self getChain:p_chain];
      if (chain == nil)
      {
            chain = [ChainFactory newChainWithCode:[p_chain charValue]];
            [chains addObject:chain];
            [chain setStructure:self];
      }
      return chain;
}


-(void)expdata:(int)p_expdata //@nodoc
{
      expdata = p_expdata;
}


-(void)resolution:(float)p_resolution     //@nodoc
{
      resolution = p_resolution;
}


-(void)header:(NSString*)p_header   //@nodoc
{
      RETAIN(p_header);
      if (header)
      {
            RELEASE(header);
      }
      header = p_header;
}


-(void)title:(NSString*)p_title     //@nodoc
{
      RETAIN(p_title);
      if (title)
      {
            RELEASE(title);
      }
      title = p_title;
}


-(void)keywords:(NSString*)p_kw     //@nodoc
{
      if (!p_kw)
      {
            return;
      }
      if (keywords)
      {
            RELEASE(keywords);
      }
      NSMutableArray *t_arr = [NSMutableArray new];
      
      char *t_str = (char*)[p_kw lossyCString];
      int slen = strlen(t_str);
      int lasti=0;
      int i;
      for (i=0; i<slen; i++)
      {
            if (t_str[i]=='\0')
            {
                  break;
            }
            // ',' is the field delimiter
            if (t_str[i]==',')
            {
                  t_str='\0';
                  [t_arr addObject:[[NSString stringWithCString:(t_str+lasti)]clipleft]];
                  lasti = i+1;
            }
      }
      if (i>0 && lasti != i)
      {
            [t_arr addObject:[[NSString stringWithCString:(t_str+lasti)]clipleft]];
      }
      keywords = [NSArray arrayWithArray: t_arr];
      RETAIN(keywords);
}


-(void)date:(NSCalendarDate*)p_date //@nodoc
{
      RETAIN(p_date);
      if (date)
      {
            RELEASE(date);
      }
      date = p_date;
}


-(void)revdate:(NSCalendarDate*)p_date    //@nodoc
{
      RETAIN(p_date);
      if (revdate)
      {
            RELEASE(revdate);
      }
      revdate = p_date;
}


-(void)pdbcode:(NSString*)p_pdbcode //@nodoc
{
      RETAIN(p_pdbcode);
      if (pdbcode)
      {
            RELEASE(pdbcode);
      }
      pdbcode = p_pdbcode;
}


-(void)hetname:(id)name forKey:(NSString*)key   //@nodoc
{
      if (hetnames==nil)
      {
            hetnames = RETAIN([NSMutableDictionary new]);
      }
      [hetnames setObject:name forKey:key];
}


@end



/* convert NSCalendarDate to the format DD-MMM-YY, where MMM is a textual 
 * representation of a month
 */
NSString *mkTextDate (NSCalendarDate *caldate)
{
      NSString *t_m;
      int month=1;
      int year=2000;
      int day=1;

      if (caldate)
      {
            month = [caldate monthOfYear];
            day = [caldate dayOfMonth];
            year = [caldate yearOfCommonEra];
      }
      if (year >= 2000)
      {
            year -= 2000;
      } else {
            year -= 1900;
      }

      switch (month)
      {
      case 1:  t_m = @"JAN"; break;
      case 2:  t_m = @"FEB"; break;
      case 3:  t_m = @"MAR"; break;
      case 4:  t_m = @"APR"; break;
      case 5:  t_m = @"MAI"; break;
      case 6:  t_m = @"JUN"; break;
      case 7:  t_m = @"JUL"; break;
      case 8:  t_m = @"AUG"; break;
      case 9:  t_m = @"SEP"; break;
      case 10:  t_m = @"OCT"; break;
      case 11:  t_m = @"NOV"; break;
      case 12:  t_m = @"DEC"; break;
      default: t_m = @"XXX";
      }

      return [NSString stringWithFormat:@"%02d-%@-%02d",day,t_m,year];
}



Generated by  Doxygen 1.6.0   Back to index