#!/usr/bin/env perl
# /* {{{1 GNU General Public License
# 
# bdf2db for sofea, the Stack Operated Finite Element Analysis program
# Copyright (C) 2003-2005  Al Danial <al.danial@gmail.com>
# 
# This program 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.
# 
# 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, write to the Free Software Foundation,
# Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
#
# Read .bdf file describing a Nastran model then write it to an SQLite database.
#
# 1}}}
use warnings;
use strict;
BEGIN {
    die "The environment variable TOPS_HOME is not defined; will not be\n",
        "able to find the TopsFEA.pm module file\n"
        unless $ENV{TOPS_HOME};
    1;
}
use Getopt::Std;
use vars qw ( $opt_s );
use Data::Dumper::Simple;
use YAML qw( LoadFile );
use Text::Tabs;
getopts('s:');
my $SQLITE = "sqlite3"; # SQLite command line tool

die "$0  <bdf file(s)>

           Creates an SQLite database containing the Nastran bulk
           data.
" unless @ARGV;

# define a default DB schema if none was passed in
$opt_s = "$ENV{TOPS_HOME}/apps/fea/db/bdf.yaml" unless $opt_s;

my $yaml_ref = LoadFile($opt_s);
# print Dumper($yaml_ref); die;

while (my $bdf_file = shift @ARGV) {
    bdf_to_db($bdf_file); 
}

sub bdf_to_db {  # {{{1
    my ($file) = @_;

    open(IN, $file) or die "Cannot open $file $!\n";
    while (<IN>) {
        next if /^\s*$/ or /^\s*\$/;
        my @w = split_bdf_line($_);
        (my $clean = $w[0]) =~ s/\*$//;   # strip off long format * marker
        printf "%8d. %s\n", $., $clean;
    }
    close(IN);

} # 1}}}
sub split_bdf_line { # {{{1
    my $input = shift @_;

    my @field = ();
    chomp($input = expand($input));
    return clean_bdf_fields(split(/,/, $input)) if $input =~ m{,};

    my $i = 1;
    $field[0] = substr( $input, 0, 8 );
    if( $field[0] =~ /^\s*(\*?)\w+(\*?)\s*/ and
        length($1) + length($2) == 1 ) {  # star card -> double wide columns
        my $lenSoFar = 8;
        foreach ( 16, 16, 16, 16, 8 ) {
            last if $lenSoFar > length($input);
            $field[$i] = substr($input, $lenSoFar, $_);
            $lenSoFar += $_;
            ++$i;
        }
    } else {                              # regular width columns
        while ($i*8 < length($input)) {
            $field[$i] = substr($input, $i*8, 8); ++$i;
        }
    }

    return clean_bdf_fields(@field);
} # 1}}}
sub clean_bdf_fields{ # {{{1
    # trim surrounding whitespace, drop null entries from end of array
    my @in = @_;
    for (@in) { s/^\s*//; s/\s*$//; }
    while (!$in[$#in]) { pop @in; }
    return @in;
} # 1}}}
