1

我正在使用 java.util.Calendar 使用其 set() 方法查找给定一周的开始。

  • 这在 Android Nougat+ 上完美运行,但不适用于 Marshmallow 以下的任何 Android 版本。

  • 我已经在物理设备和模拟器上进行了测试。

  • 我已经使用调试器来验证问题出在日历代码上,而不是显示它的问题。

  • 我使用 Kotlin 和 Java 创建了不同的最小示例,但问题仍然存在。

这是 Kotlin 的最小示例,其中 TextView 显示日期,而 Button 用于将该日期增加一周:

class MainActivity : AppCompatActivity() {

    var week = 10

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        // Set TextView to show the date of the 10th week in 2018.
        setCalendarText(week) 

        // Increase the week on every button click, and show the new date.
        button.setOnClickListener { setCalendarText(++week) }
    }

    /**
     * Set the text of a TextView, defined in XML, to the date of
     * a given week in 2018.
     */
    fun setCalendarText(week: Int) {
        val cal = Calendar.getInstance().apply {
            firstDayOfWeek = Calendar.MONDAY
            set(Calendar.YEAR, 2018)
            set(Calendar.WEEK_OF_YEAR, week)
            set(Calendar.DAY_OF_WEEK, Calendar.MONDAY)
            set(Calendar.HOUR_OF_DAY, 0)
            set(Calendar.MINUTE, 0)
            set(Calendar.SECOND, 1)
        }
        textView.text = SimpleDateFormat("dd MMMM yyyy", Locale.UK).format(cal.time)
    }
}

当按预期工作时,活动启动时 TextView 设置为显示“2018 年 3 月 5 日”。单击该按钮时,此值将更改为每个连续一周的第一天。

在 Android Marshmallow 及以下版本上:

  • TextView 的初始值设置为本周的开始时间 2018 年 9 月 3 日)。
  • 单击按钮时日期不会更改。
  • 如果日期设置为,日历可以正确检索当前一周的最后一天Calendar.SUNDAY。它不会在任何其他星期工作。

编辑:我试图创建一个 Java MVCE,它允许您通过运行快速检查基本问题是否出现CalendarTester.test()

import android.util.Log;
import java.text.SimpleDateFormat;
import java.util.Calendar;
import java.util.Locale;

class CalendarTester {

    /**
     * Check that the Calendar returns the correct date for
     * the start of the 10th week of 2018 instead of returning
     * the start of the current week.
     */
    public static void test() {
        // en_US on my machine, but should probably be en_GB.
        String locale = Locale.getDefault().toString();
        Log.v("CalendarTester", "The locale is " + locale);

        Long startOfTenthWeek = getStartOfGivenWeek(10);
        String startOfTenthWeekFormatted = formatDate(startOfTenthWeek);

        boolean isCorrect = "05 March 2018".equals(startOfTenthWeekFormatted);

        Log.v("CalendarTester", String.format("The calculated date is %s, which is %s",
                startOfTenthWeekFormatted, isCorrect ? "CORRECT" : "WRONG"));
    }

    public static Long getStartOfGivenWeek(int week) {
        Calendar cal = Calendar.getInstance();
        cal.setFirstDayOfWeek(Calendar.MONDAY);
        cal.set(Calendar.YEAR, 2018);
        cal.set(Calendar.WEEK_OF_YEAR, week);
        cal.set(Calendar.DAY_OF_WEEK, Calendar.MONDAY);
        cal.set(Calendar.HOUR_OF_DAY, 0);
        cal.set(Calendar.MINUTE, 0);
        cal.set(Calendar.SECOND, 1);

        return cal.getTimeInMillis();
    }

    public static String formatDate(Long timeInMillis) {
        return new SimpleDateFormat("dd MMMM yyyy", Locale.UK).format(timeInMillis);
    }
}
4

1 回答 1

2
于 2018-09-08T22:05:42.387 回答