dosRelativeDateFormatting不适用于将来的日期

问题描述

   /// A date formatter for displaying the complete relative date plus the time plus day,no seconds.
///
/// Examples: Today at 2:07 PM; Yesterday at 2:07 PM; Monday,Oct 7,2018 at 5:05 AM
///
static let relativeFullDateShortFormatterWithDay: DateFormatter = {
    let formatter = DateFormatter()
    formatter.timeStyle = .short
    formatter.dateStyle = .medium
    formatter.doesRelativeDateFormatting = true
    formatter.timeZone = TimeZone.current
    formatter.locale = Locale.autoupdatingCurrent
    return formatter
}()

我从服务器收到了到期日期。如果到期日是今天,我想显示今天,如果到期日是星期内,我想显示工作日名称。 我为此将dosRelativeDateFormatting设置为true。从服务器上,我得到9月4日的到期日期,即星期五。当我使用relativeFullDateShortFormatterWithDay将Date转换为字符串时,它将返回2020年9月4日,而不是星期五。 我还需要在格式化程序中进行设置吗?对于过去的日期,这很好。

解决方法

给出问题中的格式化程序和特殊的工作日格式化程序

let weekDayFormatter = DateFormatter()
weekDayFormatter.dateFormat = "EEEE HH:mm" 

(如果语言环境始终相同,则英语格式可以更改为“ EEEE'at'HH:mm”)

然后我们可以使用一个函数来格式化日期,方法是先检查拳头格式化程序是否返回“ Today”之类的东西,然后返回该值,否则检查给定日期是否在下一周之内,然后返回工作日

func format(date: Date) -> String {
    formatter.doesRelativeDateFormatting = true
    let relative = formatter.string(from: date)
    formatter.doesRelativeDateFormatting = false
    let absolute = formatter.string(from: date)

    if relative != absolute {
        return relative
    }

    let calendar = Calendar.current
    let startDate = calendar.startOfDay(for: Date())
    guard let endDate = calendar.date(byAdding: .day,value: 7,to: startDate) else {
        return formatter.string(from: date)
    }

    if date > startDate && date < endDate {
        return weekDayFormatter.string(from: date)
    } else {
        return formatter.string(from: date)
    }
}

示例

print(format(date: Date(timeIntervalSinceNow: 60 * 60 * 24 * 1)))
print(format(date: Date(timeIntervalSinceNow: 60 * 60 * 24 * 4)))
print(format(date: Date(timeIntervalSinceNow: 60 * 60 * 24 * 12)))

明天17:07
星期六17:07
2020年9月13日在17:07