package org.seqcode.viz.metaprofile;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import javax.imageio.ImageIO;
import org.seqcode.data.io.FASTALoader;
import org.seqcode.data.io.RegionFileUtilities;
import org.seqcode.genome.Genome;
import org.seqcode.genome.Species;
import org.seqcode.genome.location.StrandedRegion;
import org.seqcode.genome.sequence.SequenceGenerator;
import org.seqcode.gseutils.ArgParser;
import org.seqcode.gseutils.Args;
import org.seqcode.gseutils.NotFoundException;
import org.seqcode.gseutils.Pair;
public class SequenceAlignmentFigure {
private static Color AColor = Color.RED;
private static Color CColor = Color.BLUE;
private static Color GColor = Color.ORANGE;
private static Color TColor = Color.GREEN;
private static Color GapColor = Color.WHITE;
private static Color NColor = Color.GRAY;
public SequenceAlignmentFigure(){}
public static void setColors(Color a, Color c, Color g, Color t){
AColor = a;
CColor = c;
GColor = g;
TColor = t;
}
/**
* Visualize sequences as color pixels
* @param seqs, raw sequences or FASTA sequences
* @param width, width of each base, in pixel
* @param height, height of each base, in pixel
* @param f, output file
*/
public static void visualizeSequences(List<String> seqs, int width, int height, File f){
if (seqs.size()==0)
return;
int pixheight = 0;
int maxLen = 0;
for (String s:seqs){
if (s.length()!=0 && s.charAt(0)!='>') { // ignore header line of FASTA file
pixheight += height;
if (maxLen < s.length())
maxLen = s.length();
}
}
int pixwidth = maxLen*width;
System.setProperty("java.awt.headless", "true");
BufferedImage im = new BufferedImage(pixwidth, pixheight,BufferedImage.TYPE_INT_ARGB);
Graphics g = im.getGraphics();
Graphics2D g2 = (Graphics2D)g;
g2.setColor(Color.WHITE);
g2.fillRect(0,0,pixwidth, pixheight);
int count = 0;
for (String s:seqs){
if (s.charAt(0)=='>') // ignore header line of FASTA file
continue;
char[] letters = s.toCharArray();
for (int j=0;j<letters.length;j++){
switch(letters[j]){
case 'A':
case 'a':
g.setColor(AColor);
break;
case 'C':
case 'c':
g.setColor(CColor);
break;
case 'G':
case 'g':
g.setColor(GColor);
break;
case 'T':
case 't':
g.setColor(TColor);
break;
case '-':
g.setColor(GapColor);
break;
default:
g.setColor(NColor);
}
g.fillRect(j*width, count*height, width, height);
}
count++;
}
try {
ImageIO.write(im,"png",f);
} catch (IOException ex) {
ex.printStackTrace();
}
}
public static void main(String[] args) {
ArgParser ap = new ArgParser(args);
Color AColor = Color.RED;
Color CColor = Color.BLUE;
Color GColor = Color.ORANGE;
Color TColor = Color.GREEN;
try {
String outFile = ap.hasKey("out") ? ap.getKeyValue("out") : "out.png";
String seqOutFile = ap.hasKey("seqout") ? ap.getKeyValue("seqout") : null;
int win = ap.hasKey("win") ? new Integer(ap.getKeyValue("win")).intValue():-1;
List<String> seqs = null;
//color options
if(ap.hasKey("wscolor")){
CColor = new Color(128,100,128);
GColor = new Color(128,100,128);
AColor = Color.YELLOW;
TColor = Color.YELLOW;
}
if(ap.hasKey("species") && ap.hasKey("gen") && (ap.hasKey("peaks") || ap.hasKey("bed"))){
Pair<Species, Genome> pair = Args.parseGenome(args);
Genome currgen = pair.cdr();
String genomeSequencePath = ap.hasKey("gen") ? ap.getKeyValue("gen") : null;
SequenceGenerator seqgen = new SequenceGenerator(currgen);
if(genomeSequencePath != null){
seqgen.useCache(true);
seqgen.useLocalFiles(true);
seqgen.setGenomePath(genomeSequencePath);
}
List<StrandedRegion> regions = null;
if(ap.hasKey("peaks")){
String peaksFile = ap.getKeyValue("peaks");
regions = RegionFileUtilities.loadStrandedRegionsFromMotifFile(currgen, peaksFile, win);
}else if(ap.hasKey("bed")){
String bedFile = ap.getKeyValue("bed");
regions = RegionFileUtilities.loadStrandedRegionsFromBEDFile(currgen, bedFile, win);
}
seqs = RegionFileUtilities.getSequencesForStrandedRegions(regions, seqgen);
}else if(ap.hasKey("seq")){
String seqsFile = ap.getKeyValue("seq");
FASTALoader loader = new FASTALoader();
File f = new File(seqsFile);
seqs = new ArrayList<String>();
Iterator<Pair<String, String>> it = loader.execute(f);
while(it.hasNext()){
Pair<String, String> p = it.next();
String name = p.car();
String seq = p.cdr();
seqs.add(seq);
}
}else{
SequenceAlignmentFigure.printHelp();
}
if(seqs !=null){
SequenceAlignmentFigure fig = new SequenceAlignmentFigure();
fig.setColors(AColor, CColor, GColor, TColor);
fig.visualizeSequences(seqs, 3, 1, new File(outFile));
if(seqOutFile != null){
FileWriter fout = new FileWriter(seqOutFile);
for(String s: seqs){
fout.write(String.format("%s\n", s));
}
fout.close();
}
}
} catch (NotFoundException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
public static void printHelp(){
System.err.println("Usage:\n " +
"SequenceAlignmentFigure \n" +
" Required: \n" +
" --species <species;version> AND --gen <sequence directory>\n AND" +
" (--peaks <file containing stranded coordinates> OR --bed <bed file>)\n\tOR\n" +
" --seq <FASTA file>\n" +
" Optional:\n" +
" --win <window of sequence around peaks> \n"+
" --out <output filename>\n" +
" --seqout <sequence output filename>\n" +
" --wscolor [color bases according to Weak & Strong]" +
"");
return;
}
}