// Copyright (c) 2013, the Dart project authors.  Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.

part of '../visitor.dart';

/// Visitor that produces a formatted string representation of the CSS tree.
class CssPrinter extends Visitor {
  StringBuffer _buff = StringBuffer();
  bool _prettyPrint = true;
  bool _isInKeyframes = false;
  int _indent = 0;
  bool _startOfLine = true;

  /// Walk the [tree] Stylesheet. [pretty] if true emits line breaks, extra
  /// spaces, friendly property values, etc., if false emits compacted output.
  @override
  void visitTree(StyleSheet tree, {bool pretty = false}) {
    _prettyPrint = pretty;
    _buff = StringBuffer();
    _indent = 0;
    _startOfLine = true;

    visitStyleSheet(tree);
  }

  /// Appends [str] to the output buffer.
  void emit(String str) {
    if (_prettyPrint) {
      if (_startOfLine) {
        _startOfLine = false;
        _buff.write(' ' * _indent);
      }
      _buff.write(str);
    } else {
      _buff.write(str);
    }
  }

  void _emitLBrace() {
    _indent += 2;
    _buff.write('{');

    if (_prettyPrint) {
      _buff.writeln();
      _startOfLine = true;
    }
  }

  void _emitRBrace() {
    _indent -= 2;

    if (_prettyPrint) {
      if (!_startOfLine) _buff.write('\n');
      _buff.write('${' ' * _indent}}\n');
      _startOfLine = true;
    } else {
      _buff.write('}');
    }
  }

  void _emitSemicolon({bool forceLf = false}) {
    if (_prettyPrint) {
      _buff.write(';\n');
      _startOfLine = true;
    } else {
      _buff.write(';');
      if (forceLf) _buff.write('\n');
    }
  }

  void _emitLf({bool force = false}) {
    if (_prettyPrint) {
      _buff.write('\n');
      _startOfLine = true;
    } else if (force) {
      _buff.write('\n');
    }
  }

  /// Returns the output buffer.
  @override
  String toString() => _buff.toString().trim();

  String get _sp => _prettyPrint ? ' ' : '';

  // TODO(terry): When adding obfuscation we'll need isOptimized (compact w/
  //              obfuscation) and have isTesting (compact no obfuscation) and
  //              isCompact would be !prettyPrint.  We'll need another boolean
  //              flag for obfuscation.
  bool get _isTesting => !_prettyPrint;

  @override
  void visitCalcTerm(CalcTerm node) {
    emit('${node.text}(');
    node.expr.visit(this);
    emit(')');
  }

  @override
  void visitCssComment(CssComment node) {
    emit('/* ${node.comment} */');
  }

  @override
  void visitCommentDefinition(CommentDefinition node) {
    emit('<!-- ${node.comment} -->');
  }

  @override
  void visitMediaExpression(MediaExpression node) {
    emit(node.andOperator ? ' AND ' : ' ');
    emit('(${node.mediaFeature}');
    if (node.exprs.expressions.isNotEmpty) {
      emit(':');
      visitExpressions(node.exprs);
    }
    emit(')');
  }

  @override
  void visitMediaQuery(MediaQuery node) {
    var unary = node.hasUnary ? ' ${node.unary}' : '';
    var mediaType = node.hasMediaType ? ' ${node.mediaType}' : '';
    emit('$unary$mediaType');
    for (var expression in node.expressions) {
      visitMediaExpression(expression);
    }
  }

  void emitMediaQueries(List<MediaQuery> queries) {
    var queriesLen = queries.length;
    for (var i = 0; i < queriesLen; i++) {
      var query = queries[i];
      if (i > 0) emit(',');
      visitMediaQuery(query);
    }
  }

  @override
  void visitDocumentDirective(DocumentDirective node) {
    emit('@-moz-document ');
    if (node.functions.isNotEmpty) {
      node.functions.first.visit(this);
      for (var function in node.functions.skip(1)) {
        emit(',$_sp');
        function.visit(this);
      }
    }
    emit(_sp);
    _emitLBrace();
    for (var ruleSet in node.groupRuleBody) {
      ruleSet.visit(this);
    }
    _emitRBrace();
  }

  @override
  void visitSupportsDirective(SupportsDirective node) {
    emit('@supports ');
    node.condition?.visit(this);
    emit(_sp);
    _emitLBrace();
    for (var rule in node.groupRuleBody) {
      rule.visit(this);
    }
    _emitRBrace();
  }

  @override
  void visitSupportsConditionInParens(SupportsConditionInParens node) {
    emit('(');
    node.condition?.visit(this);
    emit(')');
  }

  @override
  void visitSupportsNegation(SupportsNegation node) {
    emit('not$_sp');
    node.condition.visit(this);
  }

  @override
  void visitSupportsConjunction(SupportsConjunction node) {
    if (node.conditions.isNotEmpty) {
      node.conditions.first.visit(this);
      for (var condition in node.conditions.skip(1)) {
        emit('${_sp}and$_sp');
        condition.visit(this);
      }
    }
  }

  @override
  void visitSupportsDisjunction(SupportsDisjunction node) {
    if (node.conditions.isNotEmpty) {
      node.conditions.first.visit(this);
      for (var condition in node.conditions.skip(1)) {
        emit('${_sp}or$_sp');
        condition.visit(this);
      }
    }
  }

  @override
  void visitViewportDirective(ViewportDirective node) {
    emit('@${node.name}$_sp');
    _emitLBrace();
    node.declarations.visit(this);
    _emitRBrace();
  }

  @override
  void visitMediaDirective(MediaDirective node) {
    emit('@media');
    emitMediaQueries(node.mediaQueries.cast<MediaQuery>());
    emit(_sp);
    _emitLBrace();
    for (var ruleset in node.rules) {
      ruleset.visit(this);
    }
    _emitRBrace();
  }

  @override
  void visitHostDirective(HostDirective node) {
    emit('@host$_sp');
    _emitLBrace();
    for (var ruleset in node.rules) {
      ruleset.visit(this);
    }
    _emitRBrace();
  }

  ///  @page : pseudoPage {
  ///    decls
  ///  }
  @override
  void visitPageDirective(PageDirective node) {
    emit('@page');
    if (node.hasIdent || node.hasPseudoPage) {
      if (node.hasIdent) emit(' ');
      emit(node._ident!);
      emit(node.hasPseudoPage ? ':${node._pseudoPage}' : '');
    }

    var declsMargin = node._declsMargin;
    var declsMarginLength = declsMargin.length;
    emit(_sp);
    _emitLBrace();
    for (var i = 0; i < declsMarginLength; i++) {
      declsMargin[i].visit(this);
    }
    _emitRBrace();
  }

  /// @charset "charset encoding"
  @override
  void visitCharsetDirective(CharsetDirective node) {
    emit('@charset "${node.charEncoding}"');
    _emitSemicolon(forceLf: true);
  }

  @override
  void visitImportDirective(ImportDirective node) {
    bool isStartingQuote(String ch) => ch.isNotEmpty && '\'"'.contains(ch[0]);

    if (_isTesting) {
      // Emit assuming url() was parsed; most suite tests use url function.
      emit('@import url(${node.import})');
    } else if (isStartingQuote(node.import)) {
      emit('@import ${node.import}');
    } else {
      // url(...) isn't needed only a URI can follow an @import directive; emit
      // url as a string.
      emit('@import "${node.import}"');
    }
    emitMediaQueries(node.mediaQueries);
    _emitSemicolon(forceLf: true);
  }

  @override
  void visitKeyFrameDirective(KeyFrameDirective node) {
    emit('${node.keyFrameName} ');
    node.name?.visit(this);
    emit(_sp);
    _emitLBrace();
    _isInKeyframes = true;
    for (final block in node._blocks) {
      block.visit(this);
    }
    _isInKeyframes = false;
    _emitRBrace();
  }

  @override
  void visitFontFaceDirective(FontFaceDirective node) {
    emit('@font-face');
    emit(_sp);
    _emitLBrace();
    node._declarations.visit(this);
    _emitRBrace();
  }

  @override
  void visitKeyFrameBlock(KeyFrameBlock node) {
    node._blockSelectors.visit(this);
    emit(_sp);
    _emitLBrace();
    node._declarations.visit(this);
    _emitRBrace();
  }

  @override
  void visitStyletDirective(StyletDirective node) {
    emit('/* @stylet export as ${node.dartClassName} */');
    _emitLf(force: true);
  }

  @override
  void visitNamespaceDirective(NamespaceDirective node) {
    bool isStartingQuote(String ch) => ch.isNotEmpty && '\'"'.contains(ch[0]);

    var uri = node._uri ?? '';
    if (isStartingQuote(uri)) {
      emit('@namespace ${node.prefix}"$uri"');
    } else {
      if (_isTesting) {
        // Emit exactly was we parsed.
        emit('@namespace ${node.prefix}url($uri)');
      } else {
        // url(...) isn't needed only a URI can follow a:
        //    @namespace prefix directive.
        emit('@namespace ${node.prefix}$uri');
      }
    }
    _emitSemicolon(forceLf: true);
  }

  @override
  void visitVarDefinitionDirective(VarDefinitionDirective node) {
    visitVarDefinition(node.def);
    _emitSemicolon();
  }

  @override
  void visitMixinRulesetDirective(MixinRulesetDirective node) {
    emit('@mixin ${node.name} ');
    _emitLBrace();
    for (var ruleset in node.rulesets) {
      ruleset.visit(this);
    }
    _emitRBrace();
  }

  @override
  void visitMixinDeclarationDirective(MixinDeclarationDirective node) {
    emit('@mixin ${node.name}$_sp');
    _emitLBrace();
    visitDeclarationGroup(node.declarations);
    _emitRBrace();
  }

  /// Added optional newLine for handling @include at top-level vs/ inside of
  /// a declaration group.
  @override
  void visitIncludeDirective(IncludeDirective node, [bool topLevel = true]) {
    if (topLevel) _emitLf();
    emit('@include ${node.name}');
    _emitSemicolon(forceLf: true);
  }

  @override
  void visitContentDirective(ContentDirective node) {
    // TODO(terry): TBD
  }

  @override
  void visitRuleSet(RuleSet node) {
    node.selectorGroup?.visit(this);
    emit(_sp);
    _emitLBrace();
    node.declarationGroup.visit(this);
    _emitRBrace();
  }

  @override
  void visitDeclarationGroup(DeclarationGroup node) {
    var declarations = node.declarations;
    var declarationsLength = declarations.length;
    for (var i = 0; i < declarationsLength; i++) {
      declarations[i].visit(this);
      // Don't emit the last semicolon in compact mode.
      if (_prettyPrint || i < declarationsLength - 1) {
        _emitSemicolon();
      }
    }
  }

  @override
  void visitMarginGroup(MarginGroup node) {
    var marginSymName =
        TokenKind.idToValue(TokenKind.MARGIN_DIRECTIVES, node.margin_sym);

    emit('@$marginSymName$_sp');
    _emitLBrace();
    visitDeclarationGroup(node);
    _emitRBrace();
  }

  @override
  void visitDeclaration(Declaration node) {
    emit('${node.property}:$_sp');
    node.expression?.visit(this);
    if (node.important) {
      emit('$_sp!important');
    }
  }

  @override
  void visitVarDefinition(VarDefinition node) {
    emit('var-${node.definedName}: ');
    node.expression?.visit(this);
  }

  @override
  void visitIncludeMixinAtDeclaration(IncludeMixinAtDeclaration node) {
    // Don't emit a new line we're inside of a declaration group.
    visitIncludeDirective(node.include, false);
  }

  @override
  void visitExtendDeclaration(ExtendDeclaration node) {
    emit('@extend ');
    for (var selector in node.selectors) {
      selector.visit(this);
    }
  }

  @override
  void visitSelectorGroup(SelectorGroup node) {
    var selectors = node.selectors;
    var selectorsLength = selectors.length;
    for (var i = 0; i < selectorsLength; i++) {
      if (i > 0) emit(',$_sp');
      selectors[i].visit(this);
    }
  }

  @override
  void visitSimpleSelectorSequence(SimpleSelectorSequence node) {
    emit(node._combinatorToString);
    node.simpleSelector.visit(this);
  }

  @override
  void visitSimpleSelector(SimpleSelector node) {
    emit(node.name);
  }

  @override
  void visitNamespaceSelector(NamespaceSelector node) {
    emit(node.toString());
  }

  @override
  void visitElementSelector(ElementSelector node) {
    emit(node.toString());
  }

  @override
  void visitAttributeSelector(AttributeSelector node) {
    emit(node.toString());
  }

  @override
  void visitIdSelector(IdSelector node) {
    emit(node.toString());
  }

  @override
  void visitClassSelector(ClassSelector node) {
    emit(node.toString());
  }

  @override
  void visitPseudoClassSelector(PseudoClassSelector node) {
    emit(node.toString());
  }

  @override
  void visitPseudoElementSelector(PseudoElementSelector node) {
    emit(node.toString());
  }

  @override
  void visitPseudoClassFunctionSelector(PseudoClassFunctionSelector node) {
    emit(':${node.name}(');
    node.argument.visit(this);
    emit(')');
  }

  @override
  void visitPseudoElementFunctionSelector(PseudoElementFunctionSelector node) {
    emit('::${node.name}(');
    node.expression.visit(this);
    emit(')');
  }

  @override
  void visitNegationSelector(NegationSelector node) {
    emit(':not(');
    node.negationArg?.visit(this);
    emit(')');
  }

  @override
  void visitSelectorExpression(SelectorExpression node) {
    var expressions = node.expressions;
    var expressionsLength = expressions.length;
    for (var i = 0; i < expressionsLength; i++) {
      // Add space seperator between terms without an operator.
      var expression = expressions[i];
      expression.visit(this);
    }
  }

  @override
  void visitUnicodeRangeTerm(UnicodeRangeTerm node) {
    if (node.hasSecond) {
      emit('U+${node.first}-${node.second}');
    } else {
      emit('U+${node.first}');
    }
  }

  @override
  void visitLiteralTerm(LiteralTerm node) {
    emit(node.text);
  }

  @override
  void visitHexColorTerm(HexColorTerm node) {
    String? mappedName;
    if (_isTesting && (node.value is! BAD_HEX_VALUE)) {
      mappedName = TokenKind.hexToColorName(node.value);
    }
    mappedName ??= '#${node.text}';

    emit(mappedName);
  }

  @override
  void visitNumberTerm(NumberTerm node) {
    visitLiteralTerm(node);
  }

  @override
  void visitUnitTerm(UnitTerm node) {
    emit(node.toString());
  }

  @override
  void visitLengthTerm(LengthTerm node) {
    emit(node.toString());
  }

  @override
  void visitPercentageTerm(PercentageTerm node) {
    emit('${node.text}%');
  }

  @override
  void visitEmTerm(EmTerm node) {
    emit('${node.text}em');
  }

  @override
  void visitExTerm(ExTerm node) {
    emit('${node.text}ex');
  }

  @override
  void visitAngleTerm(AngleTerm node) {
    emit(node.toString());
  }

  @override
  void visitTimeTerm(TimeTerm node) {
    emit(node.toString());
  }

  @override
  void visitFreqTerm(FreqTerm node) {
    emit(node.toString());
  }

  @override
  void visitFractionTerm(FractionTerm node) {
    emit('${node.text}fr');
  }

  @override
  void visitUriTerm(UriTerm node) {
    emit('url("${node.text}")');
  }

  @override
  void visitResolutionTerm(ResolutionTerm node) {
    emit(node.toString());
  }

  @override
  void visitViewportTerm(ViewportTerm node) {
    emit(node.toString());
  }

  @override
  void visitLineHeightTerm(LineHeightTerm node) {
    emit(node.toString());
  }

  @override
  void visitFunctionTerm(FunctionTerm node) {
    // TODO(terry): Optimize rgb to a hexcolor.
    emit('${node.text}(');
    node._params.visit(this);
    emit(')');
  }

  @override
  void visitGroupTerm(GroupTerm node) {
    emit('(');
    var terms = node._terms;
    var termsLength = terms.length;
    for (var i = 0; i < termsLength; i++) {
      if (i > 0) emit(_sp);
      terms[i].visit(this);
    }
    emit(')');
  }

  @override
  void visitItemTerm(ItemTerm node) {
    emit('[${node.text}]');
  }

  @override
  void visitIE8Term(IE8Term node) {
    visitLiteralTerm(node);
  }

  @override
  void visitOperatorSlash(OperatorSlash node) {
    emit('/');
  }

  @override
  void visitOperatorComma(OperatorComma node) {
    emit(',');
  }

  @override
  void visitOperatorPlus(OperatorPlus node) {
    emit('+');
  }

  @override
  void visitOperatorMinus(OperatorMinus node) {
    emit('-');
  }

  @override
  void visitVarUsage(VarUsage node) {
    emit('var(${node.name}');
    if (node.defaultValues.isNotEmpty) {
      emit(',');
      for (var defaultValue in node.defaultValues) {
        emit(' ');
        defaultValue.visit(this);
      }
    }
    emit(')');
  }

  @override
  void visitExpressions(Expressions node) {
    var expressions = node.expressions;
    var expressionsLength = expressions.length;

    for (var i = 0; i < expressionsLength; i++) {
      // Add space seperator between terms without an operator.
      // TODO(terry): Should have a BinaryExpression to solve this problem.
      var expression = expressions[i];
      if (i > 0 &&
          !(expression is OperatorComma || expression is OperatorSlash)) {
        // If the previous expression is an operator, use `_sp` so the space is
        // collapsed when emitted in compact mode. If the previous expression
        // isn't an operator, the space is significant to delimit the two
        // expressions and can't be collapsed.
        var previous = expressions[i - 1];
        if (previous is OperatorComma || previous is OperatorSlash) {
          emit(_sp);
        } else if (previous is PercentageTerm &&
            expression is PercentageTerm &&
            _isInKeyframes) {
          emit(',');
          emit(_sp);
        } else {
          emit(' ');
        }
      }
      expression.visit(this);
    }
  }

  @override
  void visitBinaryExpression(BinaryExpression node) {
    // TODO(terry): TBD
    throw UnimplementedError('visitBinaryExpression');
  }

  @override
  void visitUnaryExpression(UnaryExpression node) {
    // TODO(terry): TBD
    throw UnimplementedError('visitUnaryExpression');
  }

  @override
  void visitIdentifier(Identifier node) {
    emit(node.name);
  }

  @override
  void visitWildcard(Wildcard node) {
    emit('*');
  }

  @override
  void visitDartStyleExpression(DartStyleExpression node) {
    // TODO(terry): TBD
    throw UnimplementedError('visitDartStyleExpression');
  }
}
