/*
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License version 3 as published by
the Free Software Foundation.
This program 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 this program. If not, see <http://www.gnu.org/licenses/>.
*/
package org.cirqwizard.layers;
import org.cirqwizard.excellon.ExcellonParser;
import org.cirqwizard.geom.Point;
import org.cirqwizard.gerber.GerberParser;
import org.cirqwizard.pp.PPParser;
import org.cirqwizard.settings.ImportSettings;
import org.cirqwizard.settings.SettingsFactory;
import java.io.File;
import java.io.FileReader;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.stream.Collectors;
public class Board
{
public enum LayerType
{
TOP, BOTTOM, DRILLING, MILLING, SOLDER_PASTE, PLACEMENT
}
private HashMap<LayerType, Layer> layers = new HashMap<>();
private int width;
private int height;
public Layer getLayer(LayerType type)
{
return layers.get(type);
}
public void setLayer(LayerType type, Layer layer)
{
layers.put(type, layer);
}
public int getWidth()
{
return width;
}
public int getHeight()
{
return height;
}
public void loadLayers(String filename) throws IOException
{
if (new File(filename + ".cmp").exists())
setLayer(LayerType.TOP, new Layer(new GerberParser(new FileReader(filename + ".cmp")).parse()));
if (new File(filename + ".sol").exists())
setLayer(LayerType.BOTTOM, new Layer(new GerberParser(new FileReader(filename + ".sol")).parse()));
ImportSettings importSettings = SettingsFactory.getImportSettings();
if (new File(filename + ".drd").exists())
setLayer(LayerType.DRILLING, new Layer(new ExcellonParser(importSettings.getExcellonIntegerPlaces().getValue(),
importSettings.getExcellonDecimalPlaces().getValue(),
importSettings.getExcellonUnits().getValue().getMultiplier(),
new FileReader(filename + ".drd")).parse()));
if (new File(filename + ".ncl").exists())
setLayer(LayerType.MILLING, new Layer(new GerberParser(new FileReader(filename + ".ncl")).parse()));
if (new File(filename + ".crc").exists())
setLayer(LayerType.SOLDER_PASTE, new Layer(new GerberParser(new FileReader(filename + ".crc")).parse()));
if (new File(filename + ".mnt").exists())
{
setLayer(LayerType.PLACEMENT, new Layer(new PPParser(new FileReader(filename + ".mnt"),
importSettings.getCentroidFileFormat().getValue().getRegex(),
importSettings.getCentroidUnits().getValue().getMultiplier()).parse()));
}
List<LayerType> toRemove = layers.keySet().stream().filter(k -> layers.get(k).getElements().isEmpty()).collect(Collectors.toList());
toRemove.stream().forEach(k -> layers.remove(k));
if (hasLayers())
moveToOrigin();
}
public void moveToOrigin()
{
int minX = layers.values().stream().mapToInt(layer -> layer.getMinPoint().getX()).min().getAsInt();
int minY = layers.values().stream().mapToInt(layer -> layer.getMinPoint().getY()).min().getAsInt();
Point min = new Point(-minX, -minY);
layers.values().stream().forEach(layer -> layer.move(min));
updateDimensions();
}
private void updateDimensions()
{
width = layers.values().stream().mapToInt(layer -> layer.getMaxPoint().getX()).max().getAsInt();
height = layers.values().stream().mapToInt(layer -> layer.getMaxPoint().getY()).max().getAsInt();
}
public void rotate(boolean clockwise)
{
layers.values().stream().forEach(l -> l.rotate(clockwise));
moveToOrigin();
}
public boolean hasLayers()
{
return !layers.isEmpty();
}
}