mirror of
https://github.com/pepaskopec-blip/Graduately.git
synced 2026-10-27 07:04:35 +00:00
Open software as four years from Windows and Office to policy.
Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
parent
ec7aa63159
commit
264f4a73d8
84 changed files with 3327 additions and 4 deletions
|
|
@ -269,6 +269,26 @@ final class AppModel: ObservableObject {
|
|||
refresh()
|
||||
}
|
||||
|
||||
func markSw(_ id: Int) {
|
||||
progress.markSw(id)
|
||||
refresh()
|
||||
}
|
||||
|
||||
func markSw2(_ id: Int) {
|
||||
progress.markSw2(id)
|
||||
refresh()
|
||||
}
|
||||
|
||||
func markSw3(_ id: Int) {
|
||||
progress.markSw3(id)
|
||||
refresh()
|
||||
}
|
||||
|
||||
func markSw4(_ id: Int) {
|
||||
progress.markSw4(id)
|
||||
refresh()
|
||||
}
|
||||
|
||||
func markTg4(_ id: Int) {
|
||||
progress.markTg4(id)
|
||||
refresh()
|
||||
|
|
|
|||
|
|
@ -67,6 +67,10 @@ final class Content {
|
|||
let pg2: [J]
|
||||
let pg3: [J]
|
||||
let pg4: [J]
|
||||
let sw: [J]
|
||||
let sw2: [J]
|
||||
let sw3: [J]
|
||||
let sw4: [J]
|
||||
let cs: [J]
|
||||
let cs2: [J]
|
||||
let cs3: [J]
|
||||
|
|
@ -145,6 +149,10 @@ final class Content {
|
|||
pg2 = raw.arr("pg2")
|
||||
pg3 = raw.arr("pg3")
|
||||
pg4 = raw.arr("pg4")
|
||||
sw = raw.arr("sw")
|
||||
sw2 = raw.arr("sw2")
|
||||
sw3 = raw.arr("sw3")
|
||||
sw4 = raw.arr("sw4")
|
||||
cs = raw.arr("cs")
|
||||
cs2 = raw.arr("cs2")
|
||||
cs3 = raw.arr("cs3")
|
||||
|
|
@ -219,6 +227,10 @@ final class Content {
|
|||
func pg2Lesson(_ id: Int) -> J? { pg2.first { $0.int("id") == id } }
|
||||
func pg3Lesson(_ id: Int) -> J? { pg3.first { $0.int("id") == id } }
|
||||
func pg4Lesson(_ id: Int) -> J? { pg4.first { $0.int("id") == id } }
|
||||
func swLesson(_ id: Int) -> J? { sw.first { $0.int("id") == id } }
|
||||
func sw2Lesson(_ id: Int) -> J? { sw2.first { $0.int("id") == id } }
|
||||
func sw3Lesson(_ id: Int) -> J? { sw3.first { $0.int("id") == id } }
|
||||
func sw4Lesson(_ id: Int) -> J? { sw4.first { $0.int("id") == id } }
|
||||
func csLesson(_ id: Int) -> J? { cs.first { $0.int("id") == id } }
|
||||
func cs2Lesson(_ id: Int) -> J? { cs2.first { $0.int("id") == id } }
|
||||
func cs3Lesson(_ id: Int) -> J? { cs3.first { $0.int("id") == id } }
|
||||
|
|
|
|||
|
|
@ -110,6 +110,14 @@ final class ProgressStore {
|
|||
func markPg3(_ id: Int) { mark("pg3.\(id)") }
|
||||
func pg4Done(_ id: Int) -> Bool { done("pg4.\(id)") }
|
||||
func markPg4(_ id: Int) { mark("pg4.\(id)") }
|
||||
func swDone(_ id: Int) -> Bool { done("sw.\(id)") }
|
||||
func markSw(_ id: Int) { mark("sw.\(id)") }
|
||||
func sw2Done(_ id: Int) -> Bool { done("sw2.\(id)") }
|
||||
func markSw2(_ id: Int) { mark("sw2.\(id)") }
|
||||
func sw3Done(_ id: Int) -> Bool { done("sw3.\(id)") }
|
||||
func markSw3(_ id: Int) { mark("sw3.\(id)") }
|
||||
func sw4Done(_ id: Int) -> Bool { done("sw4.\(id)") }
|
||||
func markSw4(_ id: Int) { mark("sw4.\(id)") }
|
||||
func csDone(_ id: Int) -> Bool { done("cs.\(id)") }
|
||||
func markCs(_ id: Int) { mark("cs.\(id)") }
|
||||
func cs2Done(_ id: Int) -> Bool { done("cs2.\(id)") }
|
||||
|
|
@ -376,6 +384,38 @@ func summarize(_ content: Content, _ p: ProgressStore) -> ProgressSum {
|
|||
sum.doneUnits += 1
|
||||
}
|
||||
}
|
||||
for l in content.sw {
|
||||
sum.totalEx += 1
|
||||
sum.openUnits += 1
|
||||
if p.swDone(l.int("id")) {
|
||||
sum.doneEx += 1
|
||||
sum.doneUnits += 1
|
||||
}
|
||||
}
|
||||
for l in content.sw2 {
|
||||
sum.totalEx += 1
|
||||
sum.openUnits += 1
|
||||
if p.sw2Done(l.int("id")) {
|
||||
sum.doneEx += 1
|
||||
sum.doneUnits += 1
|
||||
}
|
||||
}
|
||||
for l in content.sw3 {
|
||||
sum.totalEx += 1
|
||||
sum.openUnits += 1
|
||||
if p.sw3Done(l.int("id")) {
|
||||
sum.doneEx += 1
|
||||
sum.doneUnits += 1
|
||||
}
|
||||
}
|
||||
for l in content.sw4 {
|
||||
sum.totalEx += 1
|
||||
sum.openUnits += 1
|
||||
if p.sw4Done(l.int("id")) {
|
||||
sum.doneEx += 1
|
||||
sum.doneUnits += 1
|
||||
}
|
||||
}
|
||||
for l in content.cs {
|
||||
sum.totalEx += 1
|
||||
sum.openUnits += 1
|
||||
|
|
|
|||
|
|
@ -137,6 +137,19 @@ enum Route: Hashable {
|
|||
case pg4Map
|
||||
case pg4Lesson(Int)
|
||||
case pg4Ex(Int)
|
||||
case swYears
|
||||
case swMap
|
||||
case swLesson(Int)
|
||||
case swEx(Int)
|
||||
case sw2Map
|
||||
case sw2Lesson(Int)
|
||||
case sw2Ex(Int)
|
||||
case sw3Map
|
||||
case sw3Lesson(Int)
|
||||
case sw3Ex(Int)
|
||||
case sw4Map
|
||||
case sw4Lesson(Int)
|
||||
case sw4Ex(Int)
|
||||
case csYears
|
||||
case csMap
|
||||
case csLesson(Int)
|
||||
|
|
@ -285,6 +298,19 @@ enum Route: Hashable {
|
|||
case .pg4Map: return "pg4map"
|
||||
case .pg4Lesson(let id): return "pg4unit\(id)"
|
||||
case .pg4Ex(let id): return "pg4ex\(id)"
|
||||
case .swYears: return "swyears"
|
||||
case .swMap: return "swmap"
|
||||
case .swLesson(let id): return "swunit\(id)"
|
||||
case .swEx(let id): return "swex\(id)"
|
||||
case .sw2Map: return "sw2map"
|
||||
case .sw2Lesson(let id): return "sw2unit\(id)"
|
||||
case .sw2Ex(let id): return "sw2ex\(id)"
|
||||
case .sw3Map: return "sw3map"
|
||||
case .sw3Lesson(let id): return "sw3unit\(id)"
|
||||
case .sw3Ex(let id): return "sw3ex\(id)"
|
||||
case .sw4Map: return "sw4map"
|
||||
case .sw4Lesson(let id): return "sw4unit\(id)"
|
||||
case .sw4Ex(let id): return "sw4ex\(id)"
|
||||
case .csYears: return "csyears"
|
||||
case .csMap: return "csmap"
|
||||
case .csLesson(let id): return "csunit\(id)"
|
||||
|
|
@ -570,6 +596,32 @@ enum Route: Hashable {
|
|||
return [.pgYears, .pg4Map, .pg4Lesson(id)]
|
||||
case .pg4Ex(let id):
|
||||
return [.pgYears, .pg4Map, .pg4Lesson(id), .pg4Ex(id)]
|
||||
case .swYears:
|
||||
return [.swYears]
|
||||
case .swMap:
|
||||
return [.swYears, .swMap]
|
||||
case .swLesson(let id):
|
||||
return [.swYears, .swMap, .swLesson(id)]
|
||||
case .swEx(let id):
|
||||
return [.swYears, .swMap, .swLesson(id), .swEx(id)]
|
||||
case .sw2Map:
|
||||
return [.swYears, .sw2Map]
|
||||
case .sw2Lesson(let id):
|
||||
return [.swYears, .sw2Map, .sw2Lesson(id)]
|
||||
case .sw2Ex(let id):
|
||||
return [.swYears, .sw2Map, .sw2Lesson(id), .sw2Ex(id)]
|
||||
case .sw3Map:
|
||||
return [.swYears, .sw3Map]
|
||||
case .sw3Lesson(let id):
|
||||
return [.swYears, .sw3Map, .sw3Lesson(id)]
|
||||
case .sw3Ex(let id):
|
||||
return [.swYears, .sw3Map, .sw3Lesson(id), .sw3Ex(id)]
|
||||
case .sw4Map:
|
||||
return [.swYears, .sw4Map]
|
||||
case .sw4Lesson(let id):
|
||||
return [.swYears, .sw4Map, .sw4Lesson(id)]
|
||||
case .sw4Ex(let id):
|
||||
return [.swYears, .sw4Map, .sw4Lesson(id), .sw4Ex(id)]
|
||||
case .csYears:
|
||||
return [.csYears]
|
||||
case .csMap:
|
||||
|
|
@ -658,6 +710,11 @@ func routeFromPage(_ page: String) -> Route? {
|
|||
case "pg2map": return .pg2Map
|
||||
case "pg3map": return .pg3Map
|
||||
case "pg4map": return .pg4Map
|
||||
case "swyears": return .swYears
|
||||
case "swmap": return .swMap
|
||||
case "sw2map": return .sw2Map
|
||||
case "sw3map": return .sw3Map
|
||||
case "sw4map": return .sw4Map
|
||||
case "csyears": return .csYears
|
||||
case "csmap": return .csMap
|
||||
case "cs2map": return .cs2Map
|
||||
|
|
@ -772,6 +829,30 @@ func routeFromPage(_ page: String) -> Route? {
|
|||
if let m = page.wholeMatch(of: /fyzex(\d+)/), let n = Int(m.1) {
|
||||
return .fyzEx(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw4unit(\d+)/), let n = Int(m.1) {
|
||||
return .sw4Lesson(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw4ex(\d+)/), let n = Int(m.1) {
|
||||
return .sw4Ex(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw3unit(\d+)/), let n = Int(m.1) {
|
||||
return .sw3Lesson(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw3ex(\d+)/), let n = Int(m.1) {
|
||||
return .sw3Ex(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw2unit(\d+)/), let n = Int(m.1) {
|
||||
return .sw2Lesson(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /sw2ex(\d+)/), let n = Int(m.1) {
|
||||
return .sw2Ex(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /swunit(\d+)/), let n = Int(m.1) {
|
||||
return .swLesson(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /swex(\d+)/), let n = Int(m.1) {
|
||||
return .swEx(n)
|
||||
}
|
||||
if let m = page.wholeMatch(of: /pg4unit(\d+)/), let n = Int(m.1) {
|
||||
return .pg4Lesson(n)
|
||||
}
|
||||
|
|
|
|||
|
|
@ -712,6 +712,7 @@ func subjectSymbol(_ icon: String) -> String {
|
|||
case "ruler": return "ruler.fill"
|
||||
case "code": return "chevron.left.forwardslash.chevron.right"
|
||||
case "brush": return "paintbrush.fill"
|
||||
case "apps": return "square.grid.2x2.fill"
|
||||
default: return "lock.fill"
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1018,6 +1018,39 @@ struct PgQuizScreen: View {
|
|||
}
|
||||
}
|
||||
|
||||
struct SwQuizScreen: View {
|
||||
@ObservedObject var vm: AppModel
|
||||
let year: Int
|
||||
let id: Int
|
||||
|
||||
var body: some View {
|
||||
let lesson: J? = {
|
||||
switch year {
|
||||
case 2: return vm.content.sw2Lesson(id)
|
||||
case 3: return vm.content.sw3Lesson(id)
|
||||
case 4: return vm.content.sw4Lesson(id)
|
||||
default: return vm.content.swLesson(id)
|
||||
}
|
||||
}()
|
||||
if let lesson {
|
||||
let spec = J([
|
||||
"type": "choice",
|
||||
"title": vm.tr(lesson.str("exTitleKey")),
|
||||
"sub": lesson.str("quizHeadKey"),
|
||||
"questions": lesson.rawArray("quiz"),
|
||||
])
|
||||
DispatchExercise(vm: vm, spec: spec, titleFallback: vm.tr(lesson.str("exTitleKey"))) {
|
||||
switch year {
|
||||
case 2: vm.markSw2(id)
|
||||
case 3: vm.markSw3(id)
|
||||
case 4: vm.markSw4(id)
|
||||
default: vm.markSw(id)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
struct FyzQuizScreen: View {
|
||||
@ObservedObject var vm: AppModel
|
||||
let year: Int
|
||||
|
|
|
|||
|
|
@ -751,6 +751,10 @@ func routeProgress(_ vm: AppModel, _ r: Route) -> (done: Int, total: Int)? {
|
|||
case .pg2Map: return tally(c.pg2, p.pg2Done)
|
||||
case .pg3Map: return tally(c.pg3, p.pg3Done)
|
||||
case .pg4Map: return tally(c.pg4, p.pg4Done)
|
||||
case .swMap: return tally(c.sw, p.swDone)
|
||||
case .sw2Map: return tally(c.sw2, p.sw2Done)
|
||||
case .sw3Map: return tally(c.sw3, p.sw3Done)
|
||||
case .sw4Map: return tally(c.sw4, p.sw4Done)
|
||||
case .csMap: return tally(c.cs, p.csDone)
|
||||
case .cs2Map: return tally(c.cs2, p.cs2Done)
|
||||
case .cs3Map: return tally(c.cs3, p.cs3Done)
|
||||
|
|
@ -820,6 +824,12 @@ private func subjectSum(_ vm: AppModel, _ s: J) -> ProgressSum {
|
|||
+ vm.content.pg2.filter { vm.progress.pg2Done($0.int("id")) }.count
|
||||
+ vm.content.pg3.filter { vm.progress.pg3Done($0.int("id")) }.count
|
||||
+ vm.content.pg4.filter { vm.progress.pg4Done($0.int("id")) }.count
|
||||
case "swyears", "swmap", "sw2map", "sw3map", "sw4map":
|
||||
sum.totalEx = vm.content.sw.count + vm.content.sw2.count + vm.content.sw3.count + vm.content.sw4.count
|
||||
sum.doneEx = vm.content.sw.filter { vm.progress.swDone($0.int("id")) }.count
|
||||
+ vm.content.sw2.filter { vm.progress.sw2Done($0.int("id")) }.count
|
||||
+ vm.content.sw3.filter { vm.progress.sw3Done($0.int("id")) }.count
|
||||
+ vm.content.sw4.filter { vm.progress.sw4Done($0.int("id")) }.count
|
||||
case "tgyears", "tgmap", "tg2map", "tg3map", "tg4map":
|
||||
sum.totalEx = vm.content.tg.count + vm.content.tg2.count + vm.content.tg3.count + vm.content.tg4.count
|
||||
sum.doneEx = vm.content.tg.filter { vm.progress.tgDone($0.int("id")) }.count
|
||||
|
|
@ -1129,6 +1139,27 @@ private func buildSearch(_ vm: AppModel) -> [Hit] {
|
|||
add(vm.tr(l.str("titleKey")), vm.tr("search_lesson"), "fyz4unit\(l.int("id"))", extra: "fyzika")
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_exercise"), "fyz4ex\(l.int("id"))")
|
||||
}
|
||||
add(vm.tr("Programové vybavení"), vm.tr("search_lesson"), "swyears", extra: "office windows excel mysql")
|
||||
add(vm.tr("sw_year1"), vm.tr("search_lesson"), "swmap", extra: "rocnik")
|
||||
add(vm.tr("sw_year2"), vm.tr("search_lesson"), "sw2map", extra: "rocnik")
|
||||
add(vm.tr("sw_year3"), vm.tr("search_lesson"), "sw3map", extra: "rocnik")
|
||||
add(vm.tr("sw_year4"), vm.tr("search_lesson"), "sw4map", extra: "rocnik")
|
||||
for l in vm.content.sw {
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_lesson"), "swunit\(l.int("id"))", extra: "windows")
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_exercise"), "swex\(l.int("id"))")
|
||||
}
|
||||
for l in vm.content.sw2 {
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_lesson"), "sw2unit\(l.int("id"))", extra: "word excel")
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_exercise"), "sw2ex\(l.int("id"))")
|
||||
}
|
||||
for l in vm.content.sw3 {
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_lesson"), "sw3unit\(l.int("id"))", extra: "access mysql")
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_exercise"), "sw3ex\(l.int("id"))")
|
||||
}
|
||||
for l in vm.content.sw4 {
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_lesson"), "sw4unit\(l.int("id"))", extra: "wordpress")
|
||||
add(vm.tr(l.str("titleKey")), vm.tr("search_exercise"), "sw4ex\(l.int("id"))")
|
||||
}
|
||||
add(vm.tr("Prezentační grafika"), vm.tr("search_lesson"), "pgyears", extra: "photoshop premiere illustrator")
|
||||
add(vm.tr("pg_year1"), vm.tr("search_lesson"), "pgmap", extra: "rocnik")
|
||||
add(vm.tr("pg_year2"), vm.tr("search_lesson"), "pg2map", extra: "rocnik")
|
||||
|
|
@ -1976,6 +2007,47 @@ struct CsYearsScreen: View {
|
|||
}
|
||||
}
|
||||
|
||||
struct SwYearsScreen: View {
|
||||
@ObservedObject var vm: AppModel
|
||||
|
||||
var body: some View {
|
||||
#if os(macOS)
|
||||
let years: [(String, String, Route)] = [
|
||||
("sw_year1", "sw_sub", .swMap),
|
||||
("sw_year2", "sw2_sub", .sw2Map),
|
||||
("sw_year3", "sw3_sub", .sw3Map),
|
||||
("sw_year4", "sw4_sub", .sw4Map),
|
||||
]
|
||||
MacFillGrid(count: years.count, minWidth: 260, minHeight: 200) { i in
|
||||
NavigationLink(value: years[i].2) {
|
||||
MacLinkCard(title: vm.tr(years[i].0), subtitle: vm.tr(years[i].1), badge: "\(i + 1).", progress: routeProgress(vm, years[i].2))
|
||||
}
|
||||
.buttonStyle(PressScaleStyle())
|
||||
}
|
||||
.navigationTitle(vm.tr("Programové vybavení"))
|
||||
.navigationSubtitle(vm.tr("sw_years_sub"))
|
||||
#else
|
||||
List {
|
||||
NavigationLink(value: Route.swMap) {
|
||||
ListRowLabel(title: vm.tr("sw_year1"), subtitle: vm.tr("sw_sub"), progress: routeProgress(vm, Route.swMap))
|
||||
}
|
||||
NavigationLink(value: Route.sw2Map) {
|
||||
ListRowLabel(title: vm.tr("sw_year2"), subtitle: vm.tr("sw2_sub"), progress: routeProgress(vm, Route.sw2Map))
|
||||
}
|
||||
NavigationLink(value: Route.sw3Map) {
|
||||
ListRowLabel(title: vm.tr("sw_year3"), subtitle: vm.tr("sw3_sub"), progress: routeProgress(vm, Route.sw3Map))
|
||||
}
|
||||
NavigationLink(value: Route.sw4Map) {
|
||||
ListRowLabel(title: vm.tr("sw_year4"), subtitle: vm.tr("sw4_sub"), progress: routeProgress(vm, Route.sw4Map))
|
||||
}
|
||||
}
|
||||
.navigationTitle(vm.tr("Programové vybavení"))
|
||||
.navigationSubtitle(vm.tr("sw_years_sub"))
|
||||
.appListStyle()
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
struct PgYearsScreen: View {
|
||||
@ObservedObject var vm: AppModel
|
||||
|
||||
|
|
@ -3175,6 +3247,72 @@ struct RouteDestination: View {
|
|||
if let l = vm.content.cs4Lesson(id) {
|
||||
CodeLessonScreen(vm: vm, lesson: l, onSuccess: { vm.markCs4(id) })
|
||||
}
|
||||
case .swYears:
|
||||
SwYearsScreen(vm: vm)
|
||||
case .swMap:
|
||||
LessonListScreen(
|
||||
vm: vm,
|
||||
title: vm.tr("sw_year1"),
|
||||
subtitle: vm.tr("sw_sub"),
|
||||
rows: vm.content.sw.map { l in
|
||||
let id = l.int("id")
|
||||
return LessonRow(id: "s\(id)", title: vm.tr(l.str("titleKey")), done: vm.progress.swDone(id), destination: .swLesson(id))
|
||||
}
|
||||
)
|
||||
case .swLesson(let id):
|
||||
if let l = vm.content.swLesson(id) {
|
||||
SlidesScreen(vm: vm, title: vm.tr(l.str("titleKey")), subtitle: vm.tr(l.str("subKey")), slides: l.arr("slides"), next: .swEx(id))
|
||||
}
|
||||
case .swEx(let id):
|
||||
SwQuizScreen(vm: vm, year: 1, id: id)
|
||||
case .sw2Map:
|
||||
LessonListScreen(
|
||||
vm: vm,
|
||||
title: vm.tr("sw_year2"),
|
||||
subtitle: vm.tr("sw2_sub"),
|
||||
rows: vm.content.sw2.map { l in
|
||||
let id = l.int("id")
|
||||
return LessonRow(id: "s2\(id)", title: vm.tr(l.str("titleKey")), done: vm.progress.sw2Done(id), destination: .sw2Lesson(id))
|
||||
}
|
||||
)
|
||||
case .sw2Lesson(let id):
|
||||
if let l = vm.content.sw2Lesson(id) {
|
||||
SlidesScreen(vm: vm, title: vm.tr(l.str("titleKey")), subtitle: vm.tr(l.str("subKey")), slides: l.arr("slides"), next: .sw2Ex(id))
|
||||
}
|
||||
case .sw2Ex(let id):
|
||||
SwQuizScreen(vm: vm, year: 2, id: id)
|
||||
case .sw3Map:
|
||||
LessonListScreen(
|
||||
vm: vm,
|
||||
title: vm.tr("sw_year3"),
|
||||
subtitle: vm.tr("sw3_sub"),
|
||||
rows: vm.content.sw3.map { l in
|
||||
let id = l.int("id")
|
||||
return LessonRow(id: "s3\(id)", title: vm.tr(l.str("titleKey")), done: vm.progress.sw3Done(id), destination: .sw3Lesson(id))
|
||||
}
|
||||
)
|
||||
case .sw3Lesson(let id):
|
||||
if let l = vm.content.sw3Lesson(id) {
|
||||
SlidesScreen(vm: vm, title: vm.tr(l.str("titleKey")), subtitle: vm.tr(l.str("subKey")), slides: l.arr("slides"), next: .sw3Ex(id))
|
||||
}
|
||||
case .sw3Ex(let id):
|
||||
SwQuizScreen(vm: vm, year: 3, id: id)
|
||||
case .sw4Map:
|
||||
LessonListScreen(
|
||||
vm: vm,
|
||||
title: vm.tr("sw_year4"),
|
||||
subtitle: vm.tr("sw4_sub"),
|
||||
rows: vm.content.sw4.map { l in
|
||||
let id = l.int("id")
|
||||
return LessonRow(id: "s4\(id)", title: vm.tr(l.str("titleKey")), done: vm.progress.sw4Done(id), destination: .sw4Lesson(id))
|
||||
}
|
||||
)
|
||||
case .sw4Lesson(let id):
|
||||
if let l = vm.content.sw4Lesson(id) {
|
||||
SlidesScreen(vm: vm, title: vm.tr(l.str("titleKey")), subtitle: vm.tr(l.str("subKey")), slides: l.arr("slides"), next: .sw4Ex(id))
|
||||
}
|
||||
case .sw4Ex(let id):
|
||||
SwQuizScreen(vm: vm, year: 4, id: id)
|
||||
case .pgYears:
|
||||
PgYearsScreen(vm: vm)
|
||||
case .pgMap:
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue