#!/usr/bin/python
# Generate crossmodal bag-of-words (XBOW) for DAIC
# Put the scripts into a subfolder of the DAIC package, e.g., DAIC/scripts/
# Output: csv files with features generated by openXBOW

import os
import fnmatch
from read_csv import load_features
from write_csv import save_features

# Folders with feature files
folder_lld_features = ['../lld-features/']

# Output
folder_xbow = ['../xbow/']

# OpenXBOW options for each LLD type
window_size = 4.0  # used for AVEC
hop_size = 0.1  # hop size of the labels

openxbow_options = [
    '-attributes nt1[39] -writeName -writeTimeStamp -t ' + str(window_size) +
    ' ' + str(hop_size)
]

openxbow_options_codebook = ['-size 100 -a 1 -log -standardizeInput']

# Temporary files
train_concat = ['TrainDevel_audio_mfcc.csv']

codebooks = ['Codebook_audio_mfcc.txt']

temporary_folder = 'work/'  # To store codebook files and temporary files

# Window size
jar_openxbow = 'openXBOW.jar'  # https://github.com/openXBOW/openXBOW

# Get all files
files_codebook = fnmatch.filter(os.listdir(folder_lld_features[0]),
                                '31*mfcc.csv')  # filenames end with mfcc.csv

all_files = fnmatch.filter(os.listdir(folder_lld_features[0]), '*mfcc.csv')
files_codebook.sort()
all_files.sort()

# Create folder, remove existing files
if not os.path.exists(temporary_folder):
    os.mkdir(temporary_folder)
for fn in train_concat:
    if os.path.exists(temporary_folder + fn):
        os.remove(temporary_folder + fn)
for fn in codebooks:
    if os.path.exists(temporary_folder + fn) and len(
            files_codebook) > 0:  # otherwise, use existing codebook file
        os.remove(temporary_folder + fn)

#
for m in range(0, len(folder_lld_features)):
    folder_in = folder_lld_features[m]
    folder_out = folder_xbow[m]
    xbow_options = openxbow_options[m]
    xbow_codebook = openxbow_options_codebook[m]
    training_files = temporary_folder + train_concat[m]
    codebook = temporary_folder + codebooks[m]

    if not os.path.exists(folder_xbow[m]):
        os.mkdir(folder_xbow[m])

    # Create codebooks
    if len(files_codebook) > 0:
        print('Concatenating feature files for codebook ...')
        for fn in files_codebook:
            features = load_features(folder_in + fn)
            save_features(training_files, features, append=True, instname=fn)

        print('Generating codebook file ' + codebook)
        os.system('java -d64 -Xmx8g -jar ' + jar_openxbow + ' -B ' + codebook +
                  ' -i ' + training_files + ' ' + xbow_options + ' ' +
                  xbow_codebook)

    # Generate XBOW files for train/devel/test and audio/video
    print('Generating BoAW and BoVW feature files for all files ...')
    for fn in all_files:
        print('Generating BoAW and BoVW for file ' + fn + ' ...')
        os.system('java -d64 -Xmx8g -jar ' + jar_openxbow + ' -b ' + codebook +
                  ' -i ' + folder_in + fn + ' -o ' + folder_out + fn + ' ' +
                  xbow_options)
