donglu9872 2014-04-21 07:15
浏览 228

PHP电子邮件 - 纯文本格式的间距

I'm want to send php mail in plain text and i am NOT allowed to use html but I'm having issues with spacing. The output should look like this:

Item         Qty        Price
Whatever      1          5000USD
Whatever2     2            50USD

 Subtotal                5050USD
 Tax                       50USD

 TOTAL                   5100USD

Which is pretty difficult considering amounts and product names always vary so it ends up looking very messy. Since columns widths are always going to be different i would like to right-align the last column so everything looks aligned and clean. Is there any practical method to do this?

Thank you.

EDIT:

This is my current code:

function render($indent = "", InvoicePayment $payment = null)
{
    $prefix = (!is_null($payment) && !$payment->isFirst()) ? 'second' : 'first';
    $tm_added = is_null($payment) ? $this->tm_added : $payment->dattm;

    $newline = "
";

    $price_width = max(mb_strlen(Am_Currency::render($this->{$prefix . '_total'}, $this->currency)), 8);

    $column_padding = 3;
    $column_title_max = 60;
    $column_title_min = 20;
    $column_qty = 15;
    $column_num = 3;
    $column_amount = $price_width;
    $space = str_repeat(' ', $column_padding);

    $max_length = 0;
    foreach ($this->getItems() as $item) {
        $max_length = max(mb_strlen(___($item->item_title)), $max_length);
    }

    $column_title = max(min($max_length, $column_title_max), $column_title_min);
    $row_width = $column_num + $column_padding +
                 $column_title + $column_padding +
                 $column_qty + $column_padding +
                 $column_amount + $column_padding;

    $column_total = $column_title +
                    $column_qty + $column_padding;
    $total_space = str_repeat(' ', $column_padding + $column_num + $column_padding);

    $border = $indent . str_repeat('-', $row_width) . "$newline";

    $out = $indent . ___("Invoice") . ' #' . $this->public_id . " / " . amDate($tm_added) . "$newline";
    $out .= $border;
    $out .= $indent . sprintf("{$space}%{$column_num}s{$space}%-{$column_title}s{$space}%{$column_qty}s{$space}%{$price_width}s$newline",
            " ", ___('Subscription/Product Title'), ___('Quantity'), ___('Unit Price'));
    $out .= $border;
    $num = 1;
    foreach ($this->getItems() as $item) {
        $title = explode("
", $this->wordWrap(___($item->item_title), $column_title, "
", true));
        $out .= $indent . sprintf("{$space}%{$column_num}s{$space}%-{$column_title}s{$space}%{$column_qty}s{$space}%{$price_width}s$newline",
            $num . '.', $title[0], $item->qty, Am_Currency::render($item->{$prefix . '_price'}, $this->currency));
        for ($i=1; $i<count($title); $i++)
            $out .= $indent . sprintf("{$space}%{$column_num}s{$space}%-{$column_title}s$newline", ' ', $title[$i]);
        $num++;
    }
    $out .= $border;
    if ($this->{$prefix . '_subtotal'} != $this->{$prefix . '_total'})
        $out .= $indent . sprintf("{$total_space}%-{$column_total}s{$space}%{$price_width}s$newline", ___('Subtotal'), Am_Currency::render($this->{$prefix . '_subtotal'}, $this->currency));
    if ($this->{$prefix . '_discount'} > 0)
        $out .= $indent . sprintf("{$total_space}%-{$column_total}s{$space}%{$price_width}s$newline", ___('Discount'), Am_Currency::render($this->{$prefix . '_discount'}, $this->currency));
    if ($this->{$prefix . '_shipping'} > 0)
        $out .= $indent . sprintf("{$total_space}%-{$column_total}s{$space}%{$price_width}s$newline", ___('Shipping'), Am_Currency::render($this->{$prefix . '_shipping'}, $this->currency));
    if ($this->{$prefix . '_tax'} > 0)
        $out .= $indent . sprintf("{$total_space}%-{$column_total}s{$space}%{$price_width}s$newline", ___('Tax'), Am_Currency::render($this->{$prefix . '_tax'}, $this->currency));
    $out .= $border;
    $out .= $newline;
    $out .= $indent . sprintf("{$total_space}%-{$column_total}s{$space}%{$price_width}s$newline", ___('Total'), Am_Currency::render($this->{$prefix . '_total'}, $this->currency));
    if ($this->rebill_times) {
        $terms = explode("
", $this->wordWrap(___($this->getTerms()), $row_width, "
", true));
        foreach ($terms as $term_part)
            $out .= $indent . $term_part . $newline;
        $out .= $border;
    }
    return $out;
}
  • 写回答

3条回答 默认 最新

  • douli1854 2014-04-21 07:17
    关注

    Spacing will never work as it will be very diffcult to manage your code.

    Instead map those fields/values in a HTML table and set the border to 0 , also you should render your mail as HTML for the above things to work.

    To do this.. go to http://www.tablesgenerator.com/html_tables and generate the table as per you want , Click generate and you will get the HTML source code for it..

    enter image description here

    After that, you can paste those source on your email message , Don't forget to set the border to 0. Render your mail headers to HTML , to send this as an HTML mail.

    // To send HTML mail, the Content-type header must be set
    $headers  = 'MIME-Version: 1.0' . "
    ";
    $headers .= 'Content-type: text/html; charset=iso-8859-1' . "
    ";
    

    Mail code grabbed from PHP Manual.

    评论

报告相同问题?

悬赏问题

  • ¥15 Oracle中如何从clob类型截取特定字符串后面的字符
  • ¥15 想通过pywinauto自动电机应用程序按钮,但是找不到应用程序按钮信息
  • ¥15 如何在炒股软件中,爬到我想看的日k线
  • ¥15 seatunnel 怎么配置Elasticsearch
  • ¥15 PSCAD安装问题 ERROR: Visual Studio 2013, 2015, 2017 or 2019 is not found in the system.
  • ¥15 (标签-MATLAB|关键词-多址)
  • ¥15 关于#MATLAB#的问题,如何解决?(相关搜索:信噪比,系统容量)
  • ¥500 52810做蓝牙接受端
  • ¥15 基于PLC的三轴机械手程序
  • ¥15 多址通信方式的抗噪声性能和系统容量对比