# File kwartz.rb, line 1583
        def translate_expr(node, code='', level=0)
            case tkn = node.token
            when :string
                value_str = node.left
                code << "'"
                code << value_str.gsub(/'/, "\\\\'")          #"
                code << "'"

            when :variable, :number
                value_str = node.left
                code << value_str

            when :true, :false, :null  #, :empty
                code << encode(tkn)

            when :function
                funcname = node.left
                obj = encode(funcname)
                if !obj
                    translate(node.right, code)
                elsif obj.is_a?(Array)
                    code << obj[0]
                    translate(node.right, code)
                    code << obj[1]
                elsif obj.is_a?(Proc)
                    obj.call(self, node.right, code)
                else
                    translate(node.right, code)
                end
                
            when '[]'
                translate(node.left, code)
                code << encode('[')
                translate(node.right, code)
                code << encode(']')

            when '{}'                                          ## obsolete
                translate(node.left, code)
                code << encode('{')
                translate(node.right, code)
                code << encode('}')

            when '[:]'
                translate(node.left, code)
                code << encode('[:')
                code << node.right
                code << encode(':]')

            when '.'
                translate(node.left, code)
                code << encode('.')
                code << node.right

            when '+', '-', '*', '/', '%', '^', '.+'
                if node.right
                    #translate(node.left, code)
                    #code << encode(tkn)
                    #translate(node.right, code)
                    _translate_child_expr(code, tkn, node.left)
                    code << encode(tkn)
                    _translate_child_expr(code, tkn, node.right)
                else                  ## unary operator '+' or '-'
                    code << encode('(')
                    code << encode(tkn)
                    _translate_child_expr(code, tkn, node.left)
                    code << encode(')')
                end

            when :empty, :notempty
                ## s==empty  => (s==null || s==''),  s!=empty => (s!=null && s!='')
                op1, op2 = '==', '||'
                op1, op2 = '!=', '&&' if tkn == :notempty
                str_node  = ExprNode.new(:string, '', nil)
                null_node = ExprNode.new(:null, nil, nil)
                l_node    = ExprNode.new(op1, node.left, null_node)
                r_node    = ExprNode.new(op1, node.left, str_node)
                node2     = ExprNode.new(op2, l_node, r_node)
                code << encode('(')
                translate_expr(node2, code, level)
                code << encode(')')

            when '==', '!=', '<', '<=', '>', '>='
                #translate(node.left, code)
                #code << encode(tkn)
                #translate(node.right, code)
                _translate_child_expr(code, tkn, node.left)
                code << encode(tkn)
                _translate_child_expr(code, tkn, node.right)

            when '.==', '.!=', '.<', '.<=', '.>', '.>='                        ## obsolete
                #translate(node.left, code)
                #code << encode(tkn)
                #translate(node.right, code)
                _translate_child_expr(code, tkn, node.left)
                code << encode(tkn)
                _translate_child_expr(code, tkn, node.right)

            when '=', '+=', '-=', '*=', '/=', '%=', '^=', '.+='
                translate(node.left, code)
                code << encode(tkn)
                translate(node.right, code)

            when '!'
                #code << encode('(')
                code << encode(tkn)
                _translate_child_expr(code, tkn, node.left)
                #code << encode(')')

            when '?'
                code << encode('(')
                translate(node.condition, code)
                code << encode('?')
                translate(node.left, code)
                code << encode(':')
                translate(node.right, code)
                code << encode(')')

            when ','
                #translate(node.left, code)
                #code << encode(',')
                #translate(node.right, code)
                _translate_child_expr(code, tkn, node.left)
                code << encode(tkn)
                _translate_child_expr(code, tkn, node.right)

            when '&&', '||'
                flag_l = tkn == '||' && node.left.token  == '&&'
                flag_r = tkn == '||' && node.right.token == '&&'
                code << encode('(') if flag_l
                _translate_child_expr(code, tkn, node.left)
                code << encode(')') if flag_l
                code << encode(tkn)
                code << encode('(') if flag_r
                _translate_child_expr(code, tkn, node.right)
                code << encode(')') if flag_r

            else
                Kwartz::assert("node.token=#{node.token.inspect}")
            end

            return code
        end