- 整段色块计数改为按当前格所在周期:cycleDone → 1/1,否则 0/1; 不再把全局 used/total 重复到每一格。 - 抽出 blockCellText / blockCellPercent,工作台、大屏、客户自助页共用同一口径; 通行证保持 0/1 / 1/1,深渊按所在周期 1/1 / 0/1。 - 大屏恢复通行证 / 深渊页签;screenCalSubs 补上缺失的 start(之前为零值, 导致大屏周期判定和色阶都算错),大屏格子现在显示与工作台一致的 1/1、0/1 以及 34%→4% 的周期色阶。 - 大屏色块样式:has-block / scr-block,亮暗两套都可读。 - 版本 1.11.5;README 的深渊说明同步,「工作台、大屏、客户自助页同一口径」。 验证:测试数据第一周期完成、第二周期未完成,工作台、 大屏、客户自助页均显示 20–26 为 1/1、27–31 为 0/1;周期浓度 34%/24%/14%/4%;gofmt / go vet / go test 全绿。
This commit is contained in:
@@ -21,6 +21,11 @@ type screenDay struct {
|
||||
Done int
|
||||
Urgent int
|
||||
Heat int
|
||||
// 通行证 / 深渊整段色块:BlockText 是该周期的 1/1 或 0/1
|
||||
BlockColor string
|
||||
BlockText string
|
||||
BlockTitle string
|
||||
BlockPercent int
|
||||
// Strip 打手色竖条(去重)
|
||||
Strip []string
|
||||
}
|
||||
@@ -66,7 +71,13 @@ func (s *Server) screenCalSubs(from, to string, pkgID int64, tag string) ([]calS
|
||||
warn := s.warnDays()
|
||||
list := make([]calSub, 0, len(subs))
|
||||
for _, sub := range subs {
|
||||
cs := calSub{sub: sub, pauses: pauses[sub.ID], checkins: checkins[sub.ID], eval: sub.Eval(today, warn)}
|
||||
cs := calSub{
|
||||
sub: sub,
|
||||
start: domain.ParseDateOr(sub.StartDate, today),
|
||||
pauses: pauses[sub.ID],
|
||||
checkins: checkins[sub.ID],
|
||||
eval: sub.Eval(today, warn),
|
||||
}
|
||||
if sub.EndDate != "" {
|
||||
cs.hasEnd = true
|
||||
cs.end = domain.ParseDateOr(sub.EndDate, today)
|
||||
@@ -138,15 +149,30 @@ func (s *Server) handleScreen(w http.ResponseWriter, r *http.Request) {
|
||||
count, doneN, urgentN := 0, 0, 0
|
||||
strip := []string{}
|
||||
seenColor := map[string]bool{}
|
||||
sd := screenDay{
|
||||
Date: ds,
|
||||
Day: d.Day(),
|
||||
InMonth: d.Month() == today.Month(),
|
||||
IsToday: ds == domain.Date(today),
|
||||
IsPast: d.Before(today),
|
||||
}
|
||||
for _, cs := range list {
|
||||
if heatMode == "due" {
|
||||
if cs.sub.EndDate == ds {
|
||||
count++
|
||||
}
|
||||
}
|
||||
// 通行证 / 深渊是整段型:不计入每日待完成热力,但用整段色块显示周期状态。
|
||||
if cs.isBlock() {
|
||||
if cs.blockCovers(ds) && sd.BlockText == "" {
|
||||
sd.BlockColor = cs.sub.PackageColor
|
||||
sd.BlockText = blockCellText(cs, ds)
|
||||
sd.BlockTitle = cs.sub.PackageName + " · " + sd.BlockText
|
||||
sd.BlockPercent = blockCellPercent(cs, d)
|
||||
}
|
||||
continue
|
||||
}
|
||||
// 通行证 / 深渊是整段型,不计入「每日待完成」热力
|
||||
if cs.isBlock() {
|
||||
if heatMode == "due" {
|
||||
continue
|
||||
}
|
||||
if !cs.covers(ds) {
|
||||
@@ -173,18 +199,12 @@ func (s *Server) handleScreen(w http.ResponseWriter, r *http.Request) {
|
||||
if d.Month() == today.Month() {
|
||||
data.HeatTotal += count
|
||||
}
|
||||
week = append(week, screenDay{
|
||||
Date: ds,
|
||||
Day: d.Day(),
|
||||
InMonth: d.Month() == today.Month(),
|
||||
IsToday: ds == domain.Date(today),
|
||||
IsPast: d.Before(today),
|
||||
Count: count + doneN,
|
||||
Done: doneN,
|
||||
Urgent: urgentN,
|
||||
Heat: heatLevel(count),
|
||||
Strip: strip,
|
||||
})
|
||||
sd.Count = count + doneN
|
||||
sd.Done = doneN
|
||||
sd.Urgent = urgentN
|
||||
sd.Heat = heatLevel(count)
|
||||
sd.Strip = strip
|
||||
week = append(week, sd)
|
||||
}
|
||||
data.Weeks = append(data.Weeks, week)
|
||||
}
|
||||
@@ -214,16 +234,9 @@ func (s *Server) handleScreen(w http.ResponseWriter, r *http.Request) {
|
||||
data.Recent = adj
|
||||
}
|
||||
|
||||
// 页签:按标签合并 + 独立显示另开;通行证/深渊不计每日热力,不放大屏页签
|
||||
// 页签:按标签合并 + 独立显示另开;通行证 / 深渊也放进大屏,用整段色块显示周期状态
|
||||
pkgs, _ := s.db.ListPackages(true)
|
||||
screenPkgs := make([]store.Package, 0, len(pkgs))
|
||||
for _, p := range pkgs {
|
||||
if p.Season || p.Abyss {
|
||||
continue
|
||||
}
|
||||
screenPkgs = append(screenPkgs, p)
|
||||
}
|
||||
data.Tabs, data.HasTabs = buildCalendarTabs(screenPkgs, nil, 0)
|
||||
data.Tabs, data.HasTabs = buildCalendarTabs(pkgs, nil, 0)
|
||||
for i := range data.Tabs {
|
||||
t := &data.Tabs[i]
|
||||
href := "/screen?heat=" + heatMode
|
||||
|
||||
Reference in New Issue
Block a user