/*
 * Copyright information removed for SIGGRAPH anonymous review process.
 * This file is licensed under the GNU General Public License.
 */

#include "image.h"
#include <stdio.h>

namespace OGF {

    typedef unsigned char  byte ;
    typedef unsigned short word ;
    typedef unsigned long  dword ;

#ifdef MACHINE_IS_BIG_ENDIAN

    static inline void write_byte(FILE* f, byte b) {
        fwrite(&b, 1, 1, f) ;
    }

    static inline void write_word(FILE* f, word w) {
        fwrite(&w, 2, 1, f) ;
    }

    static inline void write_dword(FILE* f, word dw) {
        fwrite(&dw, 4, 1, f) ;
    }

#else

    static inline void write_byte(FILE* f, byte b) {
        fwrite(&b, 1, 1, f) ;
    }

    static inline void write_word(FILE* f, word w) {
        byte* b = (byte*)&w ;
        write_byte(f,b[1]) ;
        write_byte(f,b[0]) ;
    }

    static inline void write_dword(FILE* f, word dw) {
        byte* b = (byte*)&dw ;
        write_byte(f,b[3]) ;
        write_byte(f,b[2]) ;
        write_byte(f,b[1]) ;
        write_byte(f,b[0]) ;
    }

#endif
    

    void Image::save_as_rgb(const std::string& file_name) {
        FILE* f = fopen(file_name.c_str(), "wb") ;
        if(f == NULL) {
            return ;
        }

        int nb_channels = bytes_per_pixel_ ;

        // Write the RGB header

        write_word(f, word(474)) ;                // RGB magic
        write_byte(f, byte(0)) ;                  // Non-compressed
        write_byte(f, byte(1)) ;                  // 1 byte per pixel channel
        write_word(f, word(3)) ;                  // 2D image with 4 channels
        write_word(f, word(width())) ;             // width
        write_word(f, word(height())) ;            // height
        write_word(f, word(nb_channels)) ; // number of channels
        write_dword(f, dword(0)) ;                // min pixel value 
        write_dword(f, dword(255)) ;              // max pixel value
        write_dword(f, dword(0)) ;                // dummy

        char image_name[80] ;
        sprintf(image_name, "Generated by ARDECO rasterizer") ;
        fwrite(image_name, 1, 80, f) ;
        write_dword(f, dword(0)) ;               // colormap ID

        for(int i=0; i<404; i++) {                   // dummy
            write_byte(f, dword(0)) ;             // (padding to make the header  
        }                                                       //  size equal to 512 bytes)
        
        // Write the RGB data
        int nb_pixels = width_ * height_ ;
        for(int channel = 0; channel <nb_channels; channel++) {
            byte* ptr = base_mem_ + channel ;
            for(int i=0; i<nb_pixels; i++) {
                write_byte(f, *ptr) ;
                ptr += bytes_per_pixel_ ;
            }
        }

        fclose(f) ;
    }

}
