sort of workoing
parent
de0a17fc9b
commit
65563f84fc
|
@ -15,6 +15,8 @@ import GRDBQuery
|
|||
/// }
|
||||
/// }
|
||||
|
||||
|
||||
var idColumn = Column("id")
|
||||
struct RibbonRequest: Queryable {
|
||||
// enum Ordering {
|
||||
// case byScore
|
||||
|
@ -23,7 +25,7 @@ struct RibbonRequest: Queryable {
|
|||
|
||||
/// The ordering used by the player request.
|
||||
// var ordering: Ordering
|
||||
// var book: String
|
||||
var id: Int64!
|
||||
|
||||
|
||||
// MARK: - Queryable Implementation
|
||||
|
@ -47,7 +49,11 @@ struct RibbonRequest: Queryable {
|
|||
|
||||
// This method is not required by Queryable, but it makes it easier
|
||||
func fetchValue(_ db: Database) throws -> [Ribbon] {
|
||||
return try Ribbon.fetchAll(db)
|
||||
if (id == nil) {
|
||||
return try Ribbon.fetchAll(db)
|
||||
} else {
|
||||
return try Ribbon.filter(idColumn == id).fetchAll(db)
|
||||
}
|
||||
|
||||
// if book == "" {
|
||||
// return try Ribbon.filter(bookColumn == Ribbon.randomBook()).fetchAll(db)
|
||||
|
|
|
@ -0,0 +1,51 @@
|
|||
//
|
||||
// Ribbon.swift
|
||||
// gloss
|
||||
//
|
||||
// Created by Saint on 2/24/23.
|
||||
//
|
||||
|
||||
import GRDB
|
||||
/// The Line struct.
|
||||
///
|
||||
/// Identifiable conformance supports SwiftUI list animations, and type-safe
|
||||
/// GRDB primary key methods.
|
||||
/// Equatable conformance supports tests.
|
||||
struct SelectedRibbon: Identifiable, Equatable {
|
||||
/// The player id.
|
||||
///
|
||||
/// Int64 is the recommended type for auto-incremented database ids.
|
||||
/// Use nil for players that are not inserted yet in the database.
|
||||
var id: Int64?
|
||||
var ribbonId: Int64
|
||||
}
|
||||
|
||||
extension SelectedRibbon {
|
||||
}
|
||||
|
||||
// MARK: - Persistence
|
||||
|
||||
/// Make Line a Codable Record.
|
||||
///
|
||||
/// See <https://github.com/groue/GRDB.swift/blob/master/README.md#records>
|
||||
extension SelectedRibbon: Codable, FetchableRecord, MutablePersistableRecord {
|
||||
// Define database columns from CodingKeys
|
||||
fileprivate enum Columns {
|
||||
static let id = Column(CodingKeys.id)
|
||||
static let ribbonId = Column(CodingKeys.ribbonId)
|
||||
}
|
||||
|
||||
/// Updates a player id after it has been inserted in the database.
|
||||
mutating func didInsert(_ inserted: InsertionSuccess) {
|
||||
id = inserted.rowID
|
||||
}
|
||||
}
|
||||
|
||||
// MARK: - Line Database Requests
|
||||
|
||||
/// Define some player requests used by the application.
|
||||
///
|
||||
/// See <https://github.com/groue/GRDB.swift/blob/master/README.md#requests>
|
||||
/// See <https://github.com/groue/GRDB.swift/blob/master/Documentation/GoodPracticesForDesigningRecordTypes.md>
|
||||
extension DerivableRequest<SelectedRibbon> {
|
||||
}
|
|
@ -0,0 +1,68 @@
|
|||
import Combine
|
||||
import GRDB
|
||||
import GRDBQuery
|
||||
|
||||
/// A player request can be used with the `@Query` property wrapper in order to
|
||||
/// feed a view with a list of players.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// struct MyView: View {
|
||||
/// @Query(SelectedRibbonRequest(ordering: .byName)) private var players: [SelectedRibbon]
|
||||
///
|
||||
/// var body: some View {
|
||||
/// List(players) { player in ... )
|
||||
/// }
|
||||
/// }
|
||||
|
||||
struct SelectedRibbonRequest: Queryable {
|
||||
// enum Ordering {
|
||||
// case byScore
|
||||
// case byName
|
||||
// }
|
||||
|
||||
/// The ordering used by the player request.
|
||||
// var ordering: Ordering
|
||||
var id: Int64!
|
||||
|
||||
// MARK: - Queryable Implementation
|
||||
|
||||
static var defaultValue: [SelectedRibbon] { [] }
|
||||
|
||||
func publisher(in appDatabase: AppDatabase) -> AnyPublisher<[SelectedRibbon], Error> {
|
||||
// Build the publisher from the general-purpose read-only access
|
||||
// granted by `appDatabase.reader`.
|
||||
// Some apps will prefer to call a dedicated method of `appDatabase`.
|
||||
ValueObservation
|
||||
.tracking(fetchValue(_:))
|
||||
.publisher(
|
||||
in: appDatabase.reader,
|
||||
// The `.immediate` scheduling feeds the view right on
|
||||
// subscription, and avoids an undesired animation when the
|
||||
// application starts.
|
||||
scheduling: .immediate)
|
||||
.eraseToAnyPublisher()
|
||||
}
|
||||
|
||||
// This method is not required by Queryable, but it makes it easier
|
||||
func fetchValue(_ db: Database) throws -> [SelectedRibbon] {
|
||||
if (id == nil) {
|
||||
return try SelectedRibbon.fetchAll(db)
|
||||
} else {
|
||||
return try SelectedRibbon.filter(idColumn == id).fetchAll(db)
|
||||
}
|
||||
|
||||
// if book == "" {
|
||||
// return try SelectedRibbon.filter(bookColumn == SelectedRibbon.randomBook()).fetchAll(db)
|
||||
// } else {
|
||||
// return try SelectedRibbon.filter(bookColumn == book).fetchAll(db)
|
||||
// }
|
||||
// switch ordering {
|
||||
// case .byScore:
|
||||
// return try SelectedRibbon.all().fetchAll(db)
|
||||
// case .byName:
|
||||
// // return try SelectedRibbon.all().orderedByName().fetchAll(db)
|
||||
// return try SelectedRibbon.all().fetchAll(db)
|
||||
// }
|
||||
}
|
||||
}
|
|
@ -27,6 +27,8 @@
|
|||
85942EE729AD083600307621 /* Introspect in Frameworks */ = {isa = PBXBuildFile; productRef = 85942EE629AD083600307621 /* Introspect */; };
|
||||
85942EE929AD51A100307621 /* Ribbon.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85942EE829AD51A100307621 /* Ribbon.swift */; };
|
||||
85942EEB29AD55A400307621 /* RibbonRequest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85942EEA29AD55A400307621 /* RibbonRequest.swift */; };
|
||||
85942EED29AEA04200307621 /* SelectedRibbon.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85942EEC29AEA04200307621 /* SelectedRibbon.swift */; };
|
||||
85942EEF29AEA18300307621 /* SelectedRibbonRequest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85942EEE29AEA18300307621 /* SelectedRibbonRequest.swift */; };
|
||||
85F01DF82978787800F317B4 /* AveriaSerifLibre-Regular.ttf in Resources */ = {isa = PBXBuildFile; fileRef = 85F01DF72978787800F317B4 /* AveriaSerifLibre-Regular.ttf */; };
|
||||
85F01DFB2978790400F317B4 /* xe-Dogma-Bold.ttf in Resources */ = {isa = PBXBuildFile; fileRef = 85F01DFA2978790400F317B4 /* xe-Dogma-Bold.ttf */; };
|
||||
/* End PBXBuildFile section */
|
||||
|
@ -50,6 +52,8 @@
|
|||
85942EE329ACF54A00307621 /* ScrollableView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = ScrollableView.swift; sourceTree = "<group>"; };
|
||||
85942EE829AD51A100307621 /* Ribbon.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Ribbon.swift; sourceTree = "<group>"; };
|
||||
85942EEA29AD55A400307621 /* RibbonRequest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RibbonRequest.swift; sourceTree = "<group>"; };
|
||||
85942EEC29AEA04200307621 /* SelectedRibbon.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectedRibbon.swift; sourceTree = "<group>"; };
|
||||
85942EEE29AEA18300307621 /* SelectedRibbonRequest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SelectedRibbonRequest.swift; sourceTree = "<group>"; };
|
||||
85F01DF72978787800F317B4 /* AveriaSerifLibre-Regular.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "AveriaSerifLibre-Regular.ttf"; sourceTree = "<group>"; };
|
||||
85F01DFA2978790400F317B4 /* xe-Dogma-Bold.ttf */ = {isa = PBXFileReference; lastKnownFileType = file; path = "xe-Dogma-Bold.ttf"; sourceTree = "<group>"; };
|
||||
85F01DFC29787B3500F317B4 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist; path = Info.plist; sourceTree = "<group>"; };
|
||||
|
@ -83,6 +87,8 @@
|
|||
85431A7C2905F4F500EE0760 = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
85942EEC29AEA04200307621 /* SelectedRibbon.swift */,
|
||||
85942EEE29AEA18300307621 /* SelectedRibbonRequest.swift */,
|
||||
85942EEA29AD55A400307621 /* RibbonRequest.swift */,
|
||||
85942EE329ACF54A00307621 /* ScrollableView.swift */,
|
||||
8590D96A29A8374B001EF84F /* json */,
|
||||
|
@ -251,7 +257,9 @@
|
|||
8590D96929A18A6D001EF84F /* LineRequest.swift in Sources */,
|
||||
8590D96E29A927CF001EF84F /* Seg.swift in Sources */,
|
||||
852774C129A150B100458CA7 /* Line.swift in Sources */,
|
||||
85942EEF29AEA18300307621 /* SelectedRibbonRequest.swift in Sources */,
|
||||
8590D96C29A92146001EF84F /* JsonImport.swift in Sources */,
|
||||
85942EED29AEA04200307621 /* SelectedRibbon.swift in Sources */,
|
||||
85431A892905F4F500EE0760 /* glossApp.swift in Sources */,
|
||||
85431A9C2905F5D800EE0760 /* SwiftUIView.swift in Sources */,
|
||||
85942EE429ACF54A00307621 /* ScrollableView.swift in Sources */,
|
||||
|
|
Binary file not shown.
|
@ -48,6 +48,11 @@ struct AppDatabase {
|
|||
t.column("book", .text).notNull()
|
||||
t.column("scrollOffset", .integer).notNull()
|
||||
}
|
||||
|
||||
try db.create(table: "SelectedRibbon") { t in
|
||||
t.autoIncrementedPrimaryKey("id")
|
||||
t.column("ribbonId", .integer).notNull()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
@ -87,6 +92,24 @@ func load<T: Decodable>(_ filename: String) -> T {
|
|||
|
||||
extension AppDatabase {
|
||||
|
||||
func saveRibbon(_ ribbon: inout Ribbon) async throws {
|
||||
// if ribbon.name.isEmpty {
|
||||
// throw ValidationError.missingName
|
||||
// }
|
||||
ribbon = try await dbWriter.write { [ribbon] db in
|
||||
try ribbon.saved(db)
|
||||
}
|
||||
}
|
||||
|
||||
func saveSelectedRibbon(_ selectedRibbon: inout SelectedRibbon) async throws {
|
||||
// if selectedRibbon.name.isEmpty {
|
||||
// throw ValidationError.missingName
|
||||
// }
|
||||
selectedRibbon = try await dbWriter.write { [selectedRibbon] db in
|
||||
try selectedRibbon.saved(db)
|
||||
}
|
||||
}
|
||||
|
||||
/// Create random Lines if the database is empty.
|
||||
func createRandomLinesIfEmpty() throws {
|
||||
|
||||
|
@ -103,6 +126,7 @@ extension AppDatabase {
|
|||
// try createRandomLines(db)
|
||||
_ = try Ribbon(id: nil, book: "bible.john", scrollOffset: 0).inserted(db)
|
||||
_ = try Ribbon(id: nil, book: "bible.john", scrollOffset: 2000).inserted(db)
|
||||
_ = try SelectedRibbon(id: 1, ribbonId: 1).inserted(db)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -135,7 +159,7 @@ extension AppDatabase {
|
|||
|
||||
// MARK: - Database Access: Reads
|
||||
|
||||
// This demo app does not provide any specific reading method, and instead
|
||||
// This demo app does not provide any specific reading method, and insteadKK
|
||||
// gives an unrestricted read-only access to the rest of the application.
|
||||
// In your app, you are free to choose another path, and define focused
|
||||
// reading methods.
|
||||
|
|
|
@ -14,6 +14,25 @@ let logger = Logger(subsystem: Bundle.main.bundleIdentifier!, category: "network
|
|||
|
||||
// var curBook = "John"
|
||||
|
||||
extension UserDefaults {
|
||||
|
||||
public func optionalInt(forKey defaultName: String) -> Int? {
|
||||
let defaults = self
|
||||
if let value = defaults.value(forKey: defaultName) {
|
||||
return value as? Int
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
public func optionalBool(forKey defaultName: String) -> Bool? {
|
||||
let defaults = self
|
||||
if let value = defaults.value(forKey: defaultName) {
|
||||
return value as? Bool
|
||||
}
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
extension UINavigationController {
|
||||
override open func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
@ -46,23 +65,132 @@ struct BlueButtonStyle: ButtonStyle {
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
struct SwitchButton : View {
|
||||
var ribbon: Ribbon
|
||||
@Binding var selectedRibbon : Ribbon?
|
||||
@Binding var book : String
|
||||
@Binding var scrollOffset : CGFloat
|
||||
struct PositionObservingView<Content: View>: View {
|
||||
var coordinateSpace: CoordinateSpace
|
||||
@Binding var position: CGPoint
|
||||
@ViewBuilder var content: () -> Content
|
||||
|
||||
var body: some View {
|
||||
Button("meow") {
|
||||
book = ribbon.book
|
||||
selectedRibbon = ribbon
|
||||
Print(ribbon.scrollOffset)
|
||||
Print(scrollOffset)
|
||||
scrollOffset = CGFloat(ribbon.scrollOffset)
|
||||
//Print("hellosdf dddd")
|
||||
content()
|
||||
.background(GeometryReader { geometry in
|
||||
Color.clear.preference(
|
||||
key: PreferenceKey.self,
|
||||
value: geometry.frame(in: coordinateSpace).origin
|
||||
)
|
||||
})
|
||||
.onPreferenceChange(PreferenceKey.self) { position in
|
||||
self.position = position
|
||||
// Print(self.position)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
private extension PositionObservingView {
|
||||
struct PreferenceKey: SwiftUI.PreferenceKey {
|
||||
static var defaultValue: CGPoint { .zero }
|
||||
|
||||
static func reduce(value: inout CGPoint, nextValue: () -> CGPoint) {
|
||||
// No-op
|
||||
}
|
||||
.buttonStyle(BlueButtonStyle())
|
||||
}
|
||||
}
|
||||
|
||||
struct OffsetObservingScrollView<Content: View>: View {
|
||||
var axes: Axis.Set = [.vertical]
|
||||
var showsIndicators = true
|
||||
@Binding var offset: CGPoint
|
||||
@ViewBuilder var content: () -> Content
|
||||
|
||||
// The name of our coordinate space doesn't have to be
|
||||
// stable between view updates (it just needs to be
|
||||
// consistent within this view), so we'll simply use a
|
||||
// plain UUID for it:
|
||||
private let coordinateSpaceName = UUID()
|
||||
|
||||
var body: some View {
|
||||
ScrollView(axes, showsIndicators: showsIndicators) {
|
||||
PositionObservingView(
|
||||
coordinateSpace: .named(coordinateSpaceName),
|
||||
position: Binding(
|
||||
get: { offset },
|
||||
set: { newOffset in
|
||||
offset = CGPoint(
|
||||
x: -newOffset.x,
|
||||
y: -newOffset.y
|
||||
)
|
||||
}
|
||||
),
|
||||
content: content
|
||||
)
|
||||
}
|
||||
.coordinateSpace(name: coordinateSpaceName)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
struct SwitchButton : View {
|
||||
@State var ribbon: Ribbon
|
||||
// @State var selectedRibbon: SelectedRibbon
|
||||
@Binding var book : String
|
||||
@Binding var scrollOffset : CGFloat
|
||||
@Binding var readOffset: CGPoint
|
||||
|
||||
@Environment(\.appDatabase) private var appDatabase
|
||||
|
||||
|
||||
@Query(SelectedRibbonRequest()) private var sr: [SelectedRibbon]
|
||||
|
||||
@State var saveOffset = CGFloat()
|
||||
var body: some View {
|
||||
// ForEach(sr) { selectedRibbon in
|
||||
Button("meow",
|
||||
action: {
|
||||
Task {
|
||||
var selectedRibbon = sr[0]
|
||||
|
||||
saveOffset = CGFloat(readOffset.y)
|
||||
Print("save/read offset", readOffset.y)
|
||||
|
||||
Print("START")
|
||||
_ = Print(ribbon)
|
||||
_ = Print(selectedRibbon)
|
||||
Print("START2")
|
||||
|
||||
if (selectedRibbon.ribbonId != ribbon.id!) {
|
||||
Print(ribbon.id!)
|
||||
Print("switching")
|
||||
book = ribbon.book
|
||||
scrollOffset = CGFloat(ribbon.scrollOffset)
|
||||
// scrollOffset = CGFloat(1500)
|
||||
Print("setted offset value", scrollOffset)
|
||||
selectedRibbon.ribbonId = ribbon.id!
|
||||
_ = try await appDatabase.saveSelectedRibbon(&selectedRibbon)
|
||||
_ = Print(selectedRibbon)
|
||||
}
|
||||
var editedRibbon = ribbon
|
||||
editedRibbon.scrollOffset = Int(saveOffset)
|
||||
Print("current ribbon offset after potential switch", editedRibbon.scrollOffset)
|
||||
|
||||
_ = try await appDatabase.saveRibbon(&editedRibbon)
|
||||
_ = Print(editedRibbon)
|
||||
|
||||
Print("ribbon offset saved")
|
||||
|
||||
Print("set offset value", scrollOffset)
|
||||
Print("read offset value", readOffset.y)
|
||||
|
||||
|
||||
Print("END")
|
||||
_ = Print(ribbon)
|
||||
_ = Print(selectedRibbon)
|
||||
Print("END2")
|
||||
}
|
||||
}
|
||||
|
||||
)
|
||||
.buttonStyle(BlueButtonStyle())
|
||||
// }
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -75,32 +203,47 @@ struct ContentView: View {
|
|||
// @State var scrollTo1 : Int64?
|
||||
@State var selectedLine : Int64?
|
||||
@State var scrollOffset = CGFloat()
|
||||
@State var selectedRibbon: Ribbon!
|
||||
|
||||
// @State var selectedRibbon: Ribbon!,
|
||||
// @State var selectedRibbon: Ribbon!
|
||||
|
||||
// @State var selectedRibbonId = Int64(UserDefaults.standard.optionalInt(forKey: "selectedRibbonId") ?? 1)
|
||||
|
||||
|
||||
@Query(SelectedRibbonRequest()) private var selectedRibbon: [SelectedRibbon]
|
||||
|
||||
@State var endedDrag = true
|
||||
|
||||
@State var readOffset = CGPoint()
|
||||
|
||||
@Query(LineRequest(ordering: .byScore, book: "bible.john")) private var lines: [Line]
|
||||
|
||||
|
||||
@Query(RibbonRequest()) private var ribbons: [Ribbon]
|
||||
|
||||
// @Query<LineRequest> private var lines: [Line]
|
||||
// @Query*RibbonRequest> private var selectedRibbon: [Ribbon]
|
||||
|
||||
// @Query(RibbonRequest(id: Int64(UserDefaults.standard.optionalInt(forKey: "lastRibbonId") ?? 1))) private var selectedRibbon: [Ribbon]
|
||||
|
||||
init() {
|
||||
UITableView.appearance().backgroundColor = UIColor(Color(red: 0.2, green: 0.2, blue: 0.2))
|
||||
// _lines = Query(LineRequest(ordering: .byScore, book: curBook))
|
||||
// _selectedRibbon = Query(RibbonRequest(id: Int64(UserDefaults.standard.optionalInt(forKey: "lastRibbonId") ?? 1)))
|
||||
}
|
||||
|
||||
// @Environment(\.managedObjectContext) private var viewContext
|
||||
|
||||
|
||||
var body: some View {
|
||||
GeometryReader { geometry in
|
||||
ZStack{
|
||||
VStack{
|
||||
ForEach(ribbons) { ribbon in
|
||||
SwitchButton(ribbon: ribbon,
|
||||
selectedRibbon: $selectedRibbon,
|
||||
book: $lines.book,
|
||||
scrollOffset: $scrollOffset)
|
||||
.buttonStyle(BlueButtonStyle())
|
||||
ForEach(ribbons) { ribbon in
|
||||
ForEach(selectedRibbon) { sr in
|
||||
SwitchButton(ribbon: ribbon,
|
||||
// selectedRibbon:sr,
|
||||
book: $lines.book,
|
||||
scrollOffset: $scrollOffset,
|
||||
readOffset: $readOffset
|
||||
)
|
||||
.buttonStyle(BlueButtonStyle())
|
||||
}
|
||||
}
|
||||
}
|
||||
.frame(width: geometry.size.width, height: geometry.size.height, alignment: .topLeading)
|
||||
|
@ -109,7 +252,8 @@ struct ContentView: View {
|
|||
// VStack (spacing: 0){
|
||||
ScrollViewReader { proxy in
|
||||
//ScrollableView($offset, animationDuration: 0) {
|
||||
ScrollView {
|
||||
OffsetObservingScrollView(offset: $readOffset)
|
||||
{
|
||||
// List {
|
||||
LazyVStack {
|
||||
ForEach(lines) { line in
|
||||
|
@ -143,7 +287,10 @@ struct ContentView: View {
|
|||
.introspectScrollView { scrollView in
|
||||
//let width = scrollView.contentSize.width - scrollView.frame.width
|
||||
//Print(scrollView.contentOffset.x)
|
||||
scrollView.contentOffset.y = scrollOffset
|
||||
// Print("here")
|
||||
if (scrollOffset != scrollView.contentOffset.y) {
|
||||
scrollView.contentOffset.y = scrollOffset
|
||||
}
|
||||
}
|
||||
.listStyle(PlainListStyle())
|
||||
|
||||
|
@ -154,15 +301,15 @@ struct ContentView: View {
|
|||
.offset(x:30 , y:0)
|
||||
.offset(x: pulledOut.width)
|
||||
.offset(x: viewState.width, y: viewState.height)
|
||||
.onAppear {
|
||||
if (selectedRibbon != nil) {
|
||||
Print(selectedRibbon)
|
||||
//scrollOffset.y = scrollOffset
|
||||
}
|
||||
}
|
||||
.gesture(
|
||||
DragGesture()
|
||||
.onChanged { gesture in
|
||||
|
||||
if (endedDrag) {
|
||||
endedDrag = false
|
||||
scrollOffset = readOffset.y - 20
|
||||
_ = Print("meow")
|
||||
}
|
||||
// logger.error("hello222")
|
||||
// NSLog("hellooo")
|
||||
//Print(viewState.width)
|
||||
|
@ -171,6 +318,7 @@ struct ContentView: View {
|
|||
// logger.log("hello")
|
||||
}
|
||||
.onEnded { _ in
|
||||
endedDrag = true
|
||||
var pulledOutWidth = CGFloat(0)
|
||||
if (viewState.width < 0) {
|
||||
pulledOutWidth = CGFloat(0)
|
||||
|
|
|
@ -49,44 +49,5 @@ extension Ribbon: Codable, FetchableRecord, MutablePersistableRecord {
|
|||
///
|
||||
/// See <https://github.com/groue/GRDB.swift/blob/master/README.md#requests>
|
||||
/// See <https://github.com/groue/GRDB.swift/blob/master/Documentation/GoodPracticesForDesigningRecordTypes.md>
|
||||
extension DerivableRequest<Line> {
|
||||
/// A request of players ordered by name.
|
||||
///
|
||||
/// For example:
|
||||
///
|
||||
/// let players: [Line] = try dbWriter.read { db in
|
||||
/// try Line.all().orderedByName().fetchAll(db)
|
||||
/// }
|
||||
//func orderedByName() -> Self {
|
||||
// // Sort by name in a localized case insensitive fashion
|
||||
// // See https://github.com/groue/GRDB.swift/blob/master/README.md#string-comparison
|
||||
// order(Line.Columns.name.collating(.localizedCaseInsensitiveCompare))
|
||||
//}
|
||||
|
||||
///// A request of players ordered by score.
|
||||
/////
|
||||
///// For example:
|
||||
/////
|
||||
///// let players: [Line] = try dbWriter.read { db in
|
||||
///// try Line.all().orderedByScore().fetchAll(db)
|
||||
///// }
|
||||
///// let bestLine: Line? = try dbWriter.read { db in
|
||||
///// try Line.all().orderedByScore().fetchOne(db)
|
||||
///// }
|
||||
//func orderedByScore() -> Self {
|
||||
// // Sort by descending score, and then by name, in a
|
||||
// // localized case insensitive fashion
|
||||
// // See https://github.com/groue/GRDB.swift/blob/master/README.md#string-comparison
|
||||
// order(
|
||||
// Line.Columns.score.desc,
|
||||
// Line.Columns.name.collating(.localizedCaseInsensitiveCompare))
|
||||
//}
|
||||
extension DerivableRequest<Ribbon> {
|
||||
}
|
||||
|
||||
// Ribbon.swift
|
||||
// gloss
|
||||
//
|
||||
// Created by Saint on 2/27/23.
|
||||
//
|
||||
|
||||
import Foundation
|
||||
|
|
Loading…
Reference in New Issue