diff --git a/AutoCat.xcodeproj/project.pbxproj b/AutoCat.xcodeproj/project.pbxproj index 3553b17..6980197 100644 --- a/AutoCat.xcodeproj/project.pbxproj +++ b/AutoCat.xcodeproj/project.pbxproj @@ -30,9 +30,11 @@ 7A11474723FF2AA500B424AF /* User.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A11474623FF2AA500B424AF /* User.swift */; }; 7A11474923FF2B2D00B424AF /* Response.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A11474823FF2B2D00B424AF /* Response.swift */; }; 7A11474B23FF368B00B424AF /* Settings.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A11474A23FF368B00B424AF /* Settings.swift */; }; + 7A27ADC7249D43210035F39E /* RegionsController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A27ADC6249D43210035F39E /* RegionsController.swift */; }; + 7A33381124990DAE00D878F1 /* FiltersController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A33381024990DAE00D878F1 /* FiltersController.swift */; }; + 7A333814249A532400D878F1 /* Filter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A333813249A532400D878F1 /* Filter.swift */; }; 7A3F07AB24360DC800E59687 /* Dated.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A3F07AA24360DC800E59687 /* Dated.swift */; }; 7A3F07AD2436350B00E59687 /* SearchController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A3F07AC2436350B00E59687 /* SearchController.swift */; }; - 7A3F07AF24366DF900E59687 /* Filter.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A3F07AE24366DF900E59687 /* Filter.swift */; }; 7A43F9F8246C8A6200BA5B49 /* JWT.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A43F9F7246C8A6200BA5B49 /* JWT.swift */; }; 7A530B78240010D900CBFE6E /* InputMask in Frameworks */ = {isa = PBXBuildFile; productRef = 7A530B77240010D900CBFE6E /* InputMask */; }; 7A530B7A24001D3300CBFE6E /* CheckController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A530B7924001D3300CBFE6E /* CheckController.swift */; }; @@ -66,6 +68,7 @@ 7A96AE2F246B2BCD00297C33 /* WebKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 7A96AE2E246B2BCD00297C33 /* WebKit.framework */; }; 7A96AE31246B2FE400297C33 /* Constants.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A96AE30246B2FE400297C33 /* Constants.swift */; }; 7A96AE33246C095700297C33 /* Base64FS.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7A96AE32246C095700297C33 /* Base64FS.swift */; }; + 7AB562BA249C9E9B00473D53 /* Region.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7AB562B9249C9E9B00473D53 /* Region.swift */; }; 7AB67E8C2435C38700258F61 /* CustomTextField.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7AB67E8B2435C38700258F61 /* CustomTextField.swift */; }; 7AB67E8E2435D1A000258F61 /* CustomButton.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7AB67E8D2435D1A000258F61 /* CustomButton.swift */; }; 7AEFE728240455E200910EB7 /* SettingsController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 7AEFE727240455E200910EB7 /* SettingsController.swift */; }; @@ -92,9 +95,11 @@ 7A11474823FF2B2D00B424AF /* Response.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Response.swift; sourceTree = ""; }; 7A11474A23FF368B00B424AF /* Settings.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Settings.swift; sourceTree = ""; }; 7A11474D23FFEE8800B424AF /* SVProgressHUD.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = SVProgressHUD.framework; path = Carthage/Build/iOS/SVProgressHUD.framework; sourceTree = ""; }; + 7A27ADC6249D43210035F39E /* RegionsController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = RegionsController.swift; sourceTree = ""; }; + 7A33381024990DAE00D878F1 /* FiltersController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = FiltersController.swift; sourceTree = ""; }; + 7A333813249A532400D878F1 /* Filter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Filter.swift; sourceTree = ""; }; 7A3F07AA24360DC800E59687 /* Dated.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Dated.swift; sourceTree = ""; }; 7A3F07AC2436350B00E59687 /* SearchController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SearchController.swift; sourceTree = ""; }; - 7A3F07AE24366DF900E59687 /* Filter.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Filter.swift; sourceTree = ""; }; 7A43F9F7246C8A6200BA5B49 /* JWT.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = JWT.swift; sourceTree = ""; }; 7A530B7924001D3300CBFE6E /* CheckController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CheckController.swift; sourceTree = ""; }; 7A530B7D24017FEE00CBFE6E /* VehicleCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = VehicleCell.swift; sourceTree = ""; }; @@ -126,6 +131,7 @@ 7A96AE2E246B2BCD00297C33 /* WebKit.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = WebKit.framework; path = Platforms/MacOSX.platform/Developer/SDKs/MacOSX10.15.sdk/System/Library/Frameworks/WebKit.framework; sourceTree = DEVELOPER_DIR; }; 7A96AE30246B2FE400297C33 /* Constants.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Constants.swift; sourceTree = ""; }; 7A96AE32246C095700297C33 /* Base64FS.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Base64FS.swift; sourceTree = ""; }; + 7AB562B9249C9E9B00473D53 /* Region.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Region.swift; sourceTree = ""; }; 7AB67E8B2435C38700258F61 /* CustomTextField.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CustomTextField.swift; sourceTree = ""; }; 7AB67E8D2435D1A000258F61 /* CustomButton.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CustomButton.swift; sourceTree = ""; }; 7AEFE727240455E200910EB7 /* SettingsController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SettingsController.swift; sourceTree = ""; }; @@ -211,6 +217,8 @@ 7A3F07AC2436350B00E59687 /* SearchController.swift */, 7A96AE2C246B2B7400297C33 /* GoogleSignInController.swift */, 7A6E03272485951700DB22ED /* OwnersController.swift */, + 7A33381024990DAE00D878F1 /* FiltersController.swift */, + 7A27ADC6249D43210035F39E /* RegionsController.swift */, ); path = Controllers; sourceTree = ""; @@ -245,7 +253,8 @@ 7A530B7F2401803A00CBFE6E /* Vehicle.swift */, 7A0516192414FF0900FC55AC /* DateSection.swift */, 7A6DD90D24337930009DE740 /* PlateNumber.swift */, - 7A3F07AE24366DF900E59687 /* Filter.swift */, + 7A333813249A532400D878F1 /* Filter.swift */, + 7AB562B9249C9E9B00473D53 /* Region.swift */, ); path = Models; sourceTree = ""; @@ -439,12 +448,14 @@ 7A11470123FDE7E500B424AF /* AppDelegate.swift in Sources */, 7A6DD90824329144009DE740 /* CenterTextLayer.swift in Sources */, 7A3F07AD2436350B00E59687 /* SearchController.swift in Sources */, + 7AB562BA249C9E9B00473D53 /* Region.swift in Sources */, 7A6DD90C24335A6D009DE740 /* FlagLayer.swift in Sources */, 7AB67E8C2435C38700258F61 /* CustomTextField.swift in Sources */, 7A8A2209248D10EC0073DFD9 /* ResizeImage.swift in Sources */, 7A6DD90E24337930009DE740 /* PlateNumber.swift in Sources */, 7AEFE728240455E200910EB7 /* SettingsController.swift in Sources */, 7A3F07AB24360DC800E59687 /* Dated.swift in Sources */, + 7A33381124990DAE00D878F1 /* FiltersController.swift in Sources */, 7A11474923FF2B2D00B424AF /* Response.swift in Sources */, 7A64AE762469DFB600ABE48E /* ContentTransformers.swift in Sources */, 7A11471823FDEBFA00B424AF /* ReportController.swift in Sources */, @@ -467,10 +478,11 @@ 7A11474423FF06CA00B424AF /* Api.swift in Sources */, 7AB67E8E2435D1A000258F61 /* CustomButton.swift in Sources */, 7A8A220B248D67B60073DFD9 /* VehicleReportImage.swift in Sources */, + 7A27ADC7249D43210035F39E /* RegionsController.swift in Sources */, 7A05161A2414FF0900FC55AC /* DateSection.swift in Sources */, + 7A333814249A532400D878F1 /* Filter.swift in Sources */, 7A11474B23FF368B00B424AF /* Settings.swift in Sources */, 7A64AE752469DFB600ABE48E /* MediaBrowserViewController.swift in Sources */, - 7A3F07AF24366DF900E59687 /* Filter.swift in Sources */, 7A64AE732469DFB600ABE48E /* DismissAnimationController.swift in Sources */, 7A64AE812469E16100ABE48E /* ProgressAnimatedView.swift in Sources */, 7A7547E024032CB6004E8406 /* VehiclePhotoCell.swift in Sources */, @@ -619,7 +631,7 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; CODE_SIGN_ENTITLEMENTS = AutoCat/AutoCat.entitlements; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 15; + CURRENT_PROJECT_VERSION = 16; DEVELOPMENT_TEAM = 46DTTB8X4S; INFOPLIST_FILE = AutoCat/Info.plist; IPHONEOS_DEPLOYMENT_TARGET = 13.0; @@ -641,7 +653,7 @@ ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon; CODE_SIGN_ENTITLEMENTS = AutoCat/AutoCat.entitlements; CODE_SIGN_STYLE = Automatic; - CURRENT_PROJECT_VERSION = 15; + CURRENT_PROJECT_VERSION = 16; DEVELOPMENT_TEAM = 46DTTB8X4S; INFOPLIST_FILE = AutoCat/Info.plist; IPHONEOS_DEPLOYMENT_TARGET = 13.0; diff --git a/AutoCat/Base.lproj/Main.storyboard b/AutoCat/Base.lproj/Main.storyboard index 932f211..477e393 100644 --- a/AutoCat/Base.lproj/Main.storyboard +++ b/AutoCat/Base.lproj/Main.storyboard @@ -223,14 +223,14 @@ - + - + - + @@ -280,15 +280,92 @@ - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -634,6 +711,7 @@ + diff --git a/AutoCat/Controllers/FiltersController.swift b/AutoCat/Controllers/FiltersController.swift new file mode 100644 index 0000000..c6ee3da --- /dev/null +++ b/AutoCat/Controllers/FiltersController.swift @@ -0,0 +1,123 @@ +import UIKit +import Eureka +import RxSwift + +class FiltersController: FormViewController { + + var done = false + var filter: Filter! + var onDone: (() -> Void)? + var regions: [Region] = [] + + let bag = DisposeBag() + + override func viewDidLoad() { + super.viewDidLoad() + + form +++ Section("Main filters") { $0.tag = "MainFilters" } + <<< PushRow("Brand") { row in + row.title = "Brand" + row.value = self.filter.brand ?? "Any" + row.selectorTitle = "Brands" + row.optionsProvider = .lazy({ form, completion in + Api.getBrands().observeOn(MainScheduler.instance).subscribe(onNext: { brands in + completion(["Any"] + brands) + }, onError: { error in + print("Get brands error: ", error) + }).disposed(by: self.bag) + }) + }.onPresent(removeSectionName(from:to:)) + .onChange { self.filter.brand = $0.value == "Any" ? nil : $0.value } + .cellUpdate { $1.value = self.filter.brand ?? "Any" } + + <<< PushRow("Model") { row in + row.title = "Model" + row.value = self.filter.model ?? "Any" + row.disabled = "$Brand == 'Any'" + row.optionsProvider = .lazy({ form, completion in + guard let brand = self.filter.brand else { + completion(["Any"]) + return + } + Api.getModels(of: brand).observeOn(MainScheduler.instance).subscribe(onNext: { models in + completion(["Any"] + models) + }, onError: { error in + print("Get models error: ", error) + }).disposed(by: self.bag) + }) + }.onPresent(removeSectionName(from:to:)) + .onChange { self.filter.model = $0.value == "Any" ? nil : $0.value } + .cellUpdate { $1.value = self.filter.model ?? "Any" } + + <<< PushRow("Color") { row in + row.title = "Color" + row.value = self.filter.color ?? "Any" + row.optionsProvider = .lazy({ form, completion in + Api.getColors().observeOn(MainScheduler.instance).subscribe(onNext: { colors in + completion(["Any"] + colors) + }, onError: { error in + print("Get colors error: ", error) + }).disposed(by: self.bag) + }) + }.onPresent(removeSectionName(from:to:)) + .onChange { self.filter.color = $0.value == "Any" ? nil : $0.value } + .cellUpdate { $1.value = self.filter.color ?? "Any" } + + form +++ Section() { $0.tag = "Regions" } + <<< LabelRow("RegionsRow") { row in + row.title = "Regions" + row.value = self.filter.regions?.map(String.init).joined(separator: ",") ?? "Any" + row.cellUpdate { cell, _ in + cell.accessoryType = .disclosureIndicator + } + } + .onCellSelection { cell, row in + let sb = UIStoryboard(name: "Main", bundle: nil) + let vc = sb.instantiateViewController(identifier: "RegionsController") as RegionsController + vc.regionCodes = self.filter.regions ?? [] + vc.onDone = { regions in + row.value = regions?.map(String.init).joined(separator: ",") ?? "Any" + self.filter.regions = regions + } + self.navigationController?.pushViewController(vc, animated: true) + } + + form +++ Section() + <<< ButtonRow("ClearAll") { $0.title = "Clear all filters" }.onCellSelection { cell, row in + self.filter.clear() + if let section = self.form.sectionBy(tag: "MainFilters") { + // For some reason certain cells do not redraw after first reload + section.reload() + section.reload() + } + } + } + + override func viewWillAppear(_ animated: Bool) { + super.viewWillAppear(animated) + self.done = false + } + +// override func viewDidDisappear(_ animated: Bool) { +// super.viewDidDisappear(animated) +// if self.done { +// self.onDone?() +// } +// } + + override func viewWillDisappear(_ animated: Bool) { + super.viewWillDisappear(animated) + if self.done { + self.onDone?() + } + } + + @IBAction func onDone(_ sender: UIBarButtonItem) { + self.done = true + self.navigationController?.popViewController(animated: true) + } + + func removeSectionName(from: FormViewController, to: SelectorViewController>>) { + to.sectionKeyForValue = { _ in "" } + } +} diff --git a/AutoCat/Controllers/RegionsController.swift b/AutoCat/Controllers/RegionsController.swift new file mode 100644 index 0000000..72ddd45 --- /dev/null +++ b/AutoCat/Controllers/RegionsController.swift @@ -0,0 +1,128 @@ +import UIKit +import RxSwift + +class RegionsDataSourse: UITableViewDiffableDataSource { + override func tableView(_ tableView: UITableView, titleForHeaderInSection section: Int) -> String? { + return snapshot().sectionIdentifiers[section].name + } +} + +class RegionsController: UIViewController, UISearchResultsUpdating, UITableViewDelegate { + + @IBOutlet weak var tableView: UITableView! + + var regions: [Region] = [] + var regionsFiltered: [Region] = [] + var done = false + var onDone: (([Int]?) -> Void)? + var regionCodes: [Int] = [] + var datasource: RegionsDataSourse! + + let searchController = UISearchController(searchResultsController: nil) + let bag = DisposeBag() + + override func viewDidLoad() { + super.viewDidLoad() + + searchController.searchResultsUpdater = self + searchController.obscuresBackgroundDuringPresentation = false + searchController.searchBar.placeholder = "Search regions" + navigationItem.searchController = searchController + navigationItem.hidesSearchBarWhenScrolling = false + definesPresentationContext = true + + self.datasource = RegionsDataSourse(tableView: self.tableView) { tableView, indexPath, code -> UITableViewCell? in + var cell = tableView.dequeueReusableCell(withIdentifier: "RegionCell") + if cell == nil { + cell = UITableViewCell(style: .value1, reuseIdentifier: "RegionCell") + } + + let selectedIndexPaths = tableView.indexPathsForSelectedRows + let rowIsSelected = selectedIndexPaths != nil && selectedIndexPaths!.contains(indexPath) + cell?.accessoryType = rowIsSelected ? .checkmark : .none + cell?.selectionStyle = .none + + cell?.textLabel?.text = String(code) + return cell + } + + Api.getRegions().observeOn(MainScheduler.instance).subscribe(onNext: { regions in + self.regions = regions + self.regionsFiltered = regions + self.updateTableView() + self.applySelection() + }, onError: { error in + print("Get regions error: ", error) + }).disposed(by: self.bag) + } + + override func viewWillDisappear(_ animated: Bool) { + super.viewWillDisappear(animated) + if self.done { + self.onDone?(self.regionCodes) + } + } + + @IBAction func onDone(_ sender: UIBarButtonItem) { + self.done = true + self.navigationController?.popViewController(animated: true) + } + + func updateTableView() { + var snapshot = NSDiffableDataSourceSnapshot() + snapshot.appendSections(self.regionsFiltered) + for region in self.regionsFiltered { + snapshot.appendItems(region.codes, toSection: region) + } + self.datasource.apply(snapshot); + } + + func applySelection() { + self.regionCodes.forEach { code in + if let section = self.regionsFiltered.firstIndex(where: { $0.codes.contains(code) }) { + if let row = self.regionsFiltered[section].codes.firstIndex(of: code) { + let indexPath = IndexPath(row: row, section: section) + self.tableView.selectRow(at: indexPath, animated: false, scrollPosition: .middle) + let cell = tableView.cellForRow(at: indexPath)! + cell.accessoryType = .checkmark + } + } + } + } + + // MARK: - UITableViewDelegate + + func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) { + let cell = tableView.cellForRow(at: indexPath)! + cell.accessoryType = .checkmark + + if let codeStr = cell.textLabel?.text, let code = Int(codeStr) { + if !self.regionCodes.contains(code) { + self.regionCodes.append(code) + } + } + } + + func tableView(_ tableView: UITableView, didDeselectRowAt indexPath: IndexPath) { + let cell = tableView.cellForRow(at: indexPath)! + cell.accessoryType = .none + + if let codeStr = cell.textLabel?.text, let code = Int(codeStr) { + self.regionCodes.removeAll(where: { $0 == code }) + } + } + + // MARK: - UISearchResultsUpdating + + func updateSearchResults(for searchController: UISearchController) { + let newQuery = searchController.searchBar.text?.uppercased() ?? "" + + if newQuery.isEmpty { + self.regionsFiltered = self.regions + } else { + self.regionsFiltered = self.regions.filter { $0.name.lowercased().contains(newQuery.lowercased()) } + } + self.updateTableView() + self.applySelection() + } +} diff --git a/AutoCat/Controllers/SearchController.swift b/AutoCat/Controllers/SearchController.swift index 24c69f2..fefc2f0 100644 --- a/AutoCat/Controllers/SearchController.swift +++ b/AutoCat/Controllers/SearchController.swift @@ -81,4 +81,17 @@ class SearchController: UIViewController, UISearchResultsUpdating { self.filter.searchString = newQuery self.filterRelay.accept(self.filter) } + + // MARK: - + + @IBAction func onFilter(_ sender: UIBarButtonItem) { + let sb = UIStoryboard(name: "Main", bundle: nil) + let controller = sb.instantiateViewController(identifier: "FiltersController") as FiltersController + controller.filter = self.filter + controller.onDone = { + self.filter = controller.filter + self.filterRelay.accept(self.filter) + } + self.navigationController?.pushViewController(controller, animated: true) + } } diff --git a/AutoCat/Models/Filter.swift b/AutoCat/Models/Filter.swift index d50157e..2fefe84 100644 --- a/AutoCat/Models/Filter.swift +++ b/AutoCat/Models/Filter.swift @@ -2,4 +2,34 @@ import Foundation struct Filter { var searchString = "" + var brand: String? + var model: String? + var color: String? + var regions: [Int]? + + mutating func clear() { + self.brand = nil + self.model = nil + self.color = nil + self.regions = nil + } + + func queryDictionary() -> [String: String] { + var dict: [String: String] = ["query": self.searchString] + + if let brand = self.brand { + dict["brand"] = brand + } + if let model = self.model { + dict["model"] = model + } + if let color = self.color { + dict["color"] = color + } + if let regions = self.regions { + dict["regions"] = regions.map(String.init).joined(separator: ",") + } + + return dict + } } diff --git a/AutoCat/Models/Region.swift b/AutoCat/Models/Region.swift new file mode 100644 index 0000000..3000ce7 --- /dev/null +++ b/AutoCat/Models/Region.swift @@ -0,0 +1,10 @@ +import Foundation + +struct Region: Codable, Hashable { + var name: String + var codes: [Int] + + static func == (lhs: Region, rhs: Region) -> Bool { + return lhs.name == rhs.name + } +} diff --git a/AutoCat/Utils/Api.swift b/AutoCat/Utils/Api.swift index 5a7ded9..5cb8a7b 100644 --- a/AutoCat/Utils/Api.swift +++ b/AutoCat/Utils/Api.swift @@ -6,7 +6,7 @@ class Api { return NSError(domain: "", code: code, userInfo: [NSLocalizedDescriptionKey: msg, NSLocalizedRecoverySuggestionErrorKey: suggestion]) } - private static func createRequest(api: String, method: String, body: [String: T]? = nil) -> URLRequest? where T: LosslessStringConvertible { + private static func createRequest(api: String, method: String, body: [String: String]? = nil) -> URLRequest? { guard var urlComponents = URLComponents(string: Constants.baseUrl + api) else { return nil } if let body = body, method.uppercased() == "GET" { @@ -26,7 +26,7 @@ class Api { return request } - private static func makeRequest(api: String, method: String, body: [String: U]? = nil) -> Observable where T: Decodable, U: LosslessStringConvertible { + private static func makeRequest(api: String, method: String = "GET", body: [String: String]? = nil) -> Observable where T: Decodable { guard let request = self.createRequest(api: api, method: method, body: body) else { return Observable.error(self.genError("Error creating request", suggestion: "")) } @@ -100,11 +100,7 @@ class Api { } public static func getVehicles(with filter: Filter) -> Observable<[Vehicle]> { - let body = [ - "limit": "0", // Unlimited - "query": filter.searchString - ] - return self.makeRequest(api: "vehicles", method: "GET", body: body) + return self.makeRequest(api: "vehicles", method: "GET", body: filter.queryDictionary()) } public static func checkVehicle(by number: String, force: Bool = false) -> Observable { @@ -122,4 +118,20 @@ class Api { } } } + + public static func getBrands() -> Observable<[String]> { + return self.makeRequest(api: "vehicles/brands") + } + + public static func getModels(of brand: String) -> Observable<[String]> { + return self.makeRequest(api: "vehicles/models", body: ["brand": brand]) + } + + public static func getColors() -> Observable<[String]> { + return self.makeRequest(api: "vehicles/colors") + } + + public static func getRegions() -> Observable<[Region]> { + return self.makeRequest(api: "vehicles/regions") + } } diff --git a/AutoCat/Utils/Constants.swift b/AutoCat/Utils/Constants.swift index 074f9be..d2dcfcc 100644 --- a/AutoCat/Utils/Constants.swift +++ b/AutoCat/Utils/Constants.swift @@ -3,8 +3,8 @@ import Foundation enum Constants { static var baseUrl: String { #if DEBUG - //return "http://127.0.0.1:3000/" - return "https://vps.aliencat.pro:8443/" + return "http://127.0.0.1:3000/" + //return "https://vps.aliencat.pro:8443/" #else return "https://vps.aliencat.pro:8443/" #endif