// Copyright 2010-2014, Google Inc.
// All rights reserved.
//
// Redistribution and use in source and binary forms, with or without
// modification, are permitted provided that the following conditions are
// met:
//
//     * Redistributions of source code must retain the above copyright
// notice, this list of conditions and the following disclaimer.
//     * Redistributions in binary form must reproduce the above
// copyright notice, this list of conditions and the following disclaimer
// in the documentation and/or other materials provided with the
// distribution.
//     * Neither the name of Google Inc. nor the names of its
// contributors may be used to endorse or promote products derived from
// this software without specific prior written permission.
//
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

// Handwriting module using zinnia.

#include "handwriting/zinnia_handwriting.h"

#include "base/file_util.h"
#include "base/logging.h"
#include "base/mac_util.h"
#include "base/mmap.h"
#include "base/system_util.h"

namespace mozc {
namespace handwriting {
namespace {
const uint32 kBoxSize = 200;
}  // namespace

// static
string ZinniaHandwriting::GetModelFileName() {
#ifdef OS_MACOSX
  // TODO(komatsu): Fix the file name to "handwriting-ja.model" like the
  // Windows implementation regardless which data file is actually
  // used.  See also gui.gyp:hand_writing_mac.
  const char kModelFile[] = "handwriting-light-ja.model";
  return FileUtil::JoinPath(MacUtil::GetResourcesDirectory(), kModelFile);
#elif defined(USE_LIBZINNIA)
  // On Linux, use the model for tegaki-zinnia.
#if defined(MOZC_ZINNIA_MODEL_FILE)
  const char kModelFile[] = MOZC_ZINNIA_MODEL_FILE;
#else
  const char kModelFile[] =
      "/usr/share/tegaki/models/zinnia/handwriting-ja.model";
#endif  // MOZC_ZINNIA_MODEL_FILE
  return kModelFile;
#else
  const char kModelFile[] = "handwriting-ja.model";
  return FileUtil::JoinPath(SystemUtil::GetServerDirectory(), kModelFile);
#endif  // OS_MACOSX
}

ZinniaHandwriting::ZinniaHandwriting(StringPiece model_file)
    : recognizer_(zinnia::Recognizer::create()),
      character_(zinnia::Character::create()),
      mmap_(new Mmap),
      zinnia_model_error_(false) {
  DCHECK(recognizer_.get());
  DCHECK(character_.get());

  if (!mmap_->Open(model_file.as_string().c_str())) {
    LOG(ERROR) << "Cannot open model file:" << model_file;
    zinnia_model_error_ = true;
    return;
  }
  if (!recognizer_->open(mmap_->begin(), mmap_->size())) {
    LOG(ERROR) << "Model file is broken:" << model_file;
    zinnia_model_error_ = true;
    return;
  }
}

ZinniaHandwriting::~ZinniaHandwriting() {}

HandwritingStatus ZinniaHandwriting::Recognize(
    const Strokes &strokes, vector<string> *candidates) const {
  if (zinnia_model_error_) {
    return HANDWRITING_ERROR;
  }

  character_->clear();
  character_->set_width(kBoxSize);
  character_->set_height(kBoxSize);
  for (size_t i = 0; i < strokes.size(); ++i) {
    for (size_t j = 0; j < strokes[i].size(); ++j) {
      character_->add(i,
                      static_cast<int>(kBoxSize * strokes[i][j].first),
                      static_cast<int>(kBoxSize * strokes[i][j].second));
    }
  }

  const int kMaxResultSize = 100;
  scoped_ptr<zinnia::Result> result(recognizer_->classify(*character_,
                                                          kMaxResultSize));
  if (result.get() == NULL) {
    return HANDWRITING_ERROR;
  }

  candidates->clear();
  for (size_t i = 0; i < result->size(); ++i) {
    candidates->push_back(result->value(i));
  }
  return HANDWRITING_NO_ERROR;
}

HandwritingStatus ZinniaHandwriting::Commit(const Strokes &strokes,
                                            const string &result) {
  // Do nothing so far.
  return HANDWRITING_NO_ERROR;
}

}  // namespace handwriting
}  // namespace mozc
