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

import 'dart:convert';
import 'dart:io';

import 'package:gen_keycodes/android_code_gen.dart';
import 'package:gen_keycodes/base_code_gen.dart';
import 'package:gen_keycodes/gtk_code_gen.dart';
import 'package:gen_keycodes/ios_code_gen.dart';
import 'package:gen_keycodes/logical_key_data.dart';
import 'package:gen_keycodes/macos_code_gen.dart';
import 'package:gen_keycodes/physical_key_data.dart';
import 'package:gen_keycodes/utils.dart';
import 'package:gen_keycodes/web_code_gen.dart';
import 'package:gen_keycodes/windows_code_gen.dart';
import 'package:path/path.dart' as path;
import 'package:test/test.dart' hide TypeMatcher, isInstanceOf;

String readDataFile(String fileName) {
  return File(path.join(dataRoot, fileName)).readAsStringSync();
}

final PhysicalKeyData physicalData = PhysicalKeyData.fromJson(
    json.decode(readDataFile('physical_key_data.g.json')) as Map<String, dynamic>);
final LogicalKeyData logicalData = LogicalKeyData.fromJson(
    json.decode(readDataFile('logical_key_data.g.json')) as Map<String, dynamic>);
final Map<String, bool> keyGoals = parseMapOfBool(
    readDataFile('layout_goals.json'));

void main() {
  setUp(() {
    testDataRoot = path.canonicalize(path.join(Directory.current.absolute.path, 'data'));
  });

  tearDown((){
    testDataRoot = null;
  });

  void checkCommonOutput(String output) {
    expect(output, contains(RegExp('Copyright 201[34]')));
    expect(output, contains('DO NOT EDIT'));
    expect(output, contains(RegExp(r'\b[kK]eyA\b')));
    expect(output, contains(RegExp(r'\b[Dd]igit1\b')));
    expect(output, contains(RegExp(r'\b[Ff]1\b')));
    expect(output, contains(RegExp(r'\b[Nn]umpad1\b')));
    expect(output, contains(RegExp(r'\b[Ss]hiftLeft\b')));
  }

  test('Generate Keycodes for Android', () {
    const String platform = 'android';
    final PlatformCodeGenerator codeGenerator = AndroidCodeGenerator(
      physicalData,
      logicalData,
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('KeyboardMap.java'));
    expect(output, contains('class KeyboardMap'));
    expect(output, contains('scanCodeToPhysical'));
    expect(output, contains('keyCodeToLogical'));
    checkCommonOutput(output);
  });
  test('Generate Keycodes for macOS', () {
    const String platform = 'macos';
    final PlatformCodeGenerator codeGenerator = MacOSCodeGenerator(
      physicalData,
      logicalData,
      keyGoals,
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('KeyCodeMap.g.mm'));
    expect(output, contains('kValueMask'));
    expect(output, contains('keyCodeToPhysicalKey'));
    expect(output, contains('keyCodeToLogicalKey'));
    expect(output, contains('keyCodeToModifierFlag'));
    expect(output, contains('modifierFlagToKeyCode'));
    expect(output, contains('kCapsLockPhysicalKey'));
    expect(output, contains('kCapsLockLogicalKey'));
    checkCommonOutput(output);
  });
  test('Generate Keycodes for iOS', () {
    const String platform = 'ios';
    final PlatformCodeGenerator codeGenerator = IOSCodeGenerator(
      physicalData,
      logicalData,
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('KeyCodeMap.g.mm'));
    expect(output, contains('kValueMask'));
    expect(output, contains('keyCodeToPhysicalKey'));
    expect(output, contains('keyCodeToLogicalKey'));
    expect(output, contains('keyCodeToModifierFlag'));
    expect(output, contains('modifierFlagToKeyCode'));
    expect(output, contains('functionKeyCodes'));
    expect(output, contains('kCapsLockPhysicalKey'));
    expect(output, contains('kCapsLockLogicalKey'));
    checkCommonOutput(output);
  });
  test('Generate Keycodes for Windows', () {
    const String platform = 'windows';
    final PlatformCodeGenerator codeGenerator = WindowsCodeGenerator(
      physicalData,
      logicalData,
      readDataFile(path.join(dataRoot, 'windows_scancode_logical_map.json')),
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('flutter_key_map.g.cc'));
    expect(output, contains('KeyboardKeyEmbedderHandler::windowsToPhysicalMap_'));
    expect(output, contains('KeyboardKeyEmbedderHandler::windowsToLogicalMap_'));
    expect(output, contains('KeyboardKeyEmbedderHandler::scanCodeToLogicalMap_'));
    checkCommonOutput(output);
  });
  test('Generate Keycodes for Linux', () {
    const String platform = 'gtk';
    final PlatformCodeGenerator codeGenerator = GtkCodeGenerator(
      physicalData,
      logicalData,
      readDataFile(path.join(dataRoot, 'gtk_modifier_bit_mapping.json')),
      readDataFile(path.join(dataRoot, 'gtk_lock_bit_mapping.json')),
      keyGoals,
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('key_mapping.g.cc'));
    expect(output, contains('initialize_modifier_bit_to_checked_keys'));
    expect(output, contains('initialize_lock_bit_to_checked_keys'));
    checkCommonOutput(output);
  });
  test('Generate Keycodes for Web', () {
    const String platform = 'web';
    final PlatformCodeGenerator codeGenerator = WebCodeGenerator(
      physicalData,
      logicalData,
      readDataFile(path.join(dataRoot, 'web_logical_location_mapping.json')),
    );
    final String output = codeGenerator.generate();

    expect(codeGenerator.outputPath(platform), endsWith('key_map.g.dart'));
    expect(output, contains('kWebToLogicalKey'));
    expect(output, contains('kWebToPhysicalKey'));
    expect(output, contains('kWebLogicalLocationMap'));
    checkCommonOutput(output);
  });
  test('LogicalKeyData', () async {
    final List<LogicalKeyEntry> entries = logicalData.entries.toList();

    // Regression tests for https://github.com/flutter/flutter/pull/87098

    expect(
      entries.indexWhere((LogicalKeyEntry entry) => entry.name == 'ShiftLeft'),
      isNot(-1));
    expect(
      entries.indexWhere((LogicalKeyEntry entry) => entry.webNames.contains('ShiftLeft')),
      -1);
    // 'Shift' maps to both 'ShiftLeft' and 'ShiftRight', and should be resolved
    // by other ways.
    expect(
      entries.indexWhere((LogicalKeyEntry entry) => entry.webNames.contains('Shift')),
      -1);
    // Printable keys must not be added with Web key of their names.
    expect(
      entries.indexWhere((LogicalKeyEntry entry) => entry.webNames.contains('Slash')),
      -1);
  });
}
