// Copyright 2016 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <stdio.h>
#include <string.h>

#define MAX_WIDTH 40
#define MAX(a, b) ((a > b) ? a : b)
#define MIN(a, b) ((a < b) ? a : b)

// Returns the length of the longst line of the message.
static int LongestLineLength(int argc, char** argv) {
  int max_len = 0;
  int cur_line = 0;

  for (int i = 0; i < argc; i++) {
    int word_len = strlen(argv[i]) + 1;

    // If the word itself is too long to fit in a line, then
    // we return the maximum width.
    if (word_len >= MAX_WIDTH)
      return MAX_WIDTH;

    if (cur_line + word_len >= MAX_WIDTH) {
      cur_line = word_len;
    } else {
      cur_line += word_len;
    }

    max_len = MAX(cur_line, max_len);
  }

  return max_len;
}

static void PrintPaddedBreak(int pad) {
  for (int i = 0; i < pad; i++) {
    printf(" ");
  }
  printf(" |\n");
}

// Prints the message
static void PrintMessage(int argc, char** argv, int longest) {
  int cur_line_len = 0;

  for (int i = 0; i < argc; i++) {
    int word_len = strlen(argv[i]) + 1;

    if (cur_line_len == 0)
      printf("| ");

    // If it all fits in the line, then print the word and move on.
    if (cur_line_len + word_len <= MAX_WIDTH) {
      printf("%s ", argv[i]);

      if (cur_line_len + word_len == MAX_WIDTH) {
        PrintPaddedBreak(longest - cur_line_len - word_len);
        cur_line_len = 0;
        continue;
      }

      cur_line_len += word_len;

      if (i == argc - 1)
        PrintPaddedBreak(longest - cur_line_len);

      continue;
    }

    // Create a line break if the current line is nonempty.
    if (cur_line_len > 0) {
      PrintPaddedBreak(longest - cur_line_len);
      printf("| ");
    }

    // If the word itself is too long, then we need to break it apart.
    // Otherwise, we print the current word and move on.
    if (word_len > MAX_WIDTH) {
      char* str = argv[i];
      int processed = 0;
      for (int j = 0; j <= word_len / MAX_WIDTH; j++) {
        int len = MIN(MAX_WIDTH, strlen(str));
        printf("%.*s", len, str);
        PrintPaddedBreak(longest - len);
        str += len;
        processed += len;
        if (processed >= word_len - 1) break;
        printf("| ");
      }

      cur_line_len = 0;
    } else {
      printf("%s ", argv[i]);
      cur_line_len = word_len;
      if (word_len == MAX_WIDTH || i == argc - 1) {
        PrintPaddedBreak(longest - cur_line_len);
      }
    }
  }
}

int main(int argc, char** argv) {
  if (argc == 1) {
    printf("Usage: cowsay [message]\n");
    return 1;
  }

  // No wordwrap because I'm too lazy.
  int bubble_width = LongestLineLength(argc - 1, argv + 1) + 1;

  printf(" _");
  for (int i = 0; i < bubble_width; i++)
    printf("_");
  printf(" \n");

  PrintMessage(argc - 1, argv + 1, bubble_width - 1);

  printf(" -");
  for (int i = 0; i < bubble_width; i++)
    printf("-");
  printf(" \n");

  printf("     \\  ^__^\n");
  printf("      \\ (oo)\\_____\n");
  printf("        (__)\\     )\\/\\\n");
  printf("           ||----w |\n");
  printf("           ||     ||\n");

  return 0;
}
