001    /*
002     * Copyright 2010-2015 JetBrains s.r.o.
003     *
004     * Licensed under the Apache License, Version 2.0 (the "License");
005     * you may not use this file except in compliance with the License.
006     * You may obtain a copy of the License at
007     *
008     * http://www.apache.org/licenses/LICENSE-2.0
009     *
010     * Unless required by applicable law or agreed to in writing, software
011     * distributed under the License is distributed on an "AS IS" BASIS,
012     * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013     * See the License for the specific language governing permissions and
014     * limitations under the License.
015     */
016    
017    package org.jetbrains.kotlin.js.translate.operation;
018    
019    import com.google.dart.compiler.backend.js.ast.JsBinaryOperation;
020    import com.google.dart.compiler.backend.js.ast.JsBinaryOperator;
021    import com.google.dart.compiler.backend.js.ast.JsExpression;
022    import org.jetbrains.annotations.NotNull;
023    import org.jetbrains.annotations.Nullable;
024    import org.jetbrains.kotlin.descriptors.CallableDescriptor;
025    import org.jetbrains.kotlin.js.translate.context.TranslationContext;
026    import org.jetbrains.kotlin.js.translate.general.AbstractTranslator;
027    import org.jetbrains.kotlin.lexer.JetToken;
028    import org.jetbrains.kotlin.psi.JetBinaryExpression;
029    import org.jetbrains.kotlin.types.expressions.OperatorConventions;
030    
031    import static org.jetbrains.kotlin.js.translate.utils.BindingUtils.getCallableDescriptorForOperationExpression;
032    import static org.jetbrains.kotlin.js.translate.utils.ErrorReportingUtils.message;
033    import static org.jetbrains.kotlin.js.translate.utils.JsDescriptorUtils.isCompareTo;
034    import static org.jetbrains.kotlin.js.translate.utils.PsiUtils.getOperationToken;
035    
036    public final class CompareToTranslator extends AbstractTranslator {
037    
038        public static boolean isCompareToCall(
039                @NotNull JetToken operationToken,
040                @Nullable CallableDescriptor operationDescriptor
041        ) {
042            if (!OperatorConventions.COMPARISON_OPERATIONS.contains(operationToken) || operationDescriptor == null) return false;
043    
044            return isCompareTo(operationDescriptor);
045        }
046    
047        @NotNull
048        public static JsExpression translate(@NotNull JetBinaryExpression expression,
049                @NotNull TranslationContext context) {
050            return (new CompareToTranslator(expression, context)).translate();
051        }
052    
053        @NotNull
054        private final JetBinaryExpression expression;
055    
056        private CompareToTranslator(
057                @NotNull JetBinaryExpression expression,
058                @NotNull TranslationContext context
059        ) {
060            super(context);
061            this.expression = expression;
062            CallableDescriptor descriptor = getCallableDescriptorForOperationExpression(context.bindingContext(), expression);
063            assert descriptor != null : "CompareTo should always have a descriptor";
064            assert (OperatorConventions.COMPARISON_OPERATIONS.contains(getOperationToken(expression))) :
065                    message(expression, "CompareToTranslator supported only expressions with operation token from COMPARISON_OPERATIONS, " +
066                                        "expression: " + expression.getText());
067        }
068    
069        @NotNull
070        private JsExpression translate() {
071            JsBinaryOperator correspondingOperator = OperatorTable.getBinaryOperator(getOperationToken(expression));
072            JsExpression methodCall = BinaryOperationTranslator.translateAsOverloadedCall(expression, context());
073            return new JsBinaryOperation(correspondingOperator, methodCall, context().program().getNumberLiteral(0));
074        }
075    }