Commit 7fdb2569 ilCode

大数据详情接口及雷达图UI

1 个父辈 e967b33a
......@@ -17,6 +17,7 @@
5E47C9772C1FD7F6002EA39E /* InfoModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E47C9762C1FD7F6002EA39E /* InfoModel.swift */; };
5E47C9792C20157C002EA39E /* InfoDetailController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E47C9782C20157C002EA39E /* InfoDetailController.swift */; };
5E47C97D2C202ED3002EA39E /* AsEmptyView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E47C97C2C202ED3002EA39E /* AsEmptyView.swift */; };
5E56F0B12C2EB88100EA3C10 /* HadoopDetailRequestModel.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E56F0B02C2EB88100EA3C10 /* HadoopDetailRequestModel.swift */; };
5E5A69D52C2A5F7F0063B726 /* HadoopHeaderView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E5A69D42C2A5F7F0063B726 /* HadoopHeaderView.swift */; };
5E5A69D72C2AB0560063B726 /* HadoopDetailController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E5A69D62C2AB0560063B726 /* HadoopDetailController.swift */; };
5E5A69D92C2ACA9B0063B726 /* HadoopMatchFilterView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 5E5A69D82C2ACA9B0063B726 /* HadoopMatchFilterView.swift */; };
......@@ -107,6 +108,7 @@
5E47C9762C1FD7F6002EA39E /* InfoModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InfoModel.swift; sourceTree = "<group>"; };
5E47C9782C20157C002EA39E /* InfoDetailController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InfoDetailController.swift; sourceTree = "<group>"; };
5E47C97C2C202ED3002EA39E /* AsEmptyView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AsEmptyView.swift; sourceTree = "<group>"; };
5E56F0B02C2EB88100EA3C10 /* HadoopDetailRequestModel.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HadoopDetailRequestModel.swift; sourceTree = "<group>"; };
5E5A69D42C2A5F7F0063B726 /* HadoopHeaderView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HadoopHeaderView.swift; sourceTree = "<group>"; };
5E5A69D62C2AB0560063B726 /* HadoopDetailController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HadoopDetailController.swift; sourceTree = "<group>"; };
5E5A69D82C2ACA9B0063B726 /* HadoopMatchFilterView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HadoopMatchFilterView.swift; sourceTree = "<group>"; };
......@@ -435,6 +437,7 @@
5E720D072C2B9FBE00D30A16 /* HadoopRequestModel.swift */,
5E720D0B2C2C200700D30A16 /* HadoopMatchFilterGroupModel.swift */,
5EC3AD922C2CEB7200DCFB26 /* RaceTypeModel.swift */,
5E56F0B02C2EB88100EA3C10 /* HadoopDetailRequestModel.swift */,
);
path = BigDataResearch;
sourceTree = "<group>";
......@@ -645,6 +648,7 @@
5E720D0C2C2C200700D30A16 /* HadoopMatchFilterGroupModel.swift in Sources */,
5E6CF0222C1305DD00BF3CF5 /* AoleiSports.xcdatamodeld in Sources */,
5E1E66B02C194337009339F0 /* LayoutTools.swift in Sources */,
5E56F0B12C2EB88100EA3C10 /* HadoopDetailRequestModel.swift in Sources */,
5E93B4922C1AA0D200CD6536 /* UIViewController+Ext.swift in Sources */,
5E47C9752C1FD35E002EA39E /* InfoProvider.swift in Sources */,
5E9A1A3C2C0F00AD00321AC5 /* ImportTools.swift in Sources */,
......
......@@ -25,6 +25,8 @@ class BaseController: UIViewController {
view.backgroundColor = kMainBgColor
view.addSubview(emptyView)
gk_maxPopDistance = 100
emptyView.snp.makeConstraints { make in
make.edges.equalToSuperview()
}
......
......@@ -176,7 +176,8 @@ extension HadoopController: UITableViewDataSource, UITableViewDelegate {
}
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
navigationController?.pushViewController(HadoopDetailController(), animated: true)
let model = provider?.matchList.value[indexPath.row]
navigationController?.pushViewController(HadoopDetailController(yqId: model?.yqId ?? 0), animated: true)
}
}
......
......@@ -6,8 +6,13 @@
//
import UIKit
import DGCharts
class HadoopDetailController: BaseController {
let yqId: Int
var provider: HadoopProvider<HadoopTarget>?
let activities = ["进攻", "排名", "技术", "状态", "防守"]
private lazy var header: UIView = {
let view = UIView(frame: CGRect(x: 0, y: -30, width: kScreenW, height: kNavBarH + 90))
view.backgroundColor = UIColor.colorWith(hexString: "122063")
......@@ -30,41 +35,173 @@ class HadoopDetailController: BaseController {
return view
}()
private lazy var radarView: UIView = {
let view = UIView()
view.backgroundColor = kWhite
view.corners(radius: 10)
view.border(borderColor: UIColor.colorWith(hexString: "F2F1F1"))
return view
}()
private lazy var radarChartView: RadarChartView = {
let chartView = RadarChartView()
chartView.chartDescription.enabled = false
chartView.webLineWidth = 1
chartView.innerWebLineWidth = 1
chartView.webColor = UIColor.colorWith(hexString: "CADEF1")
chartView.innerWebColor = UIColor.colorWith(hexString: "CADEF1")
chartView.webAlpha = 1
chartView.backgroundColor = .clear
chartView.rotationEnabled = false
return chartView
}()
init(yqId: Int) {
self.yqId = yqId
super.init(nibName: nil, bundle: nil)
}
required init?(coder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func viewDidLoad() {
super.viewDidLoad()
gk_navTitle = "大数据研究"
gk_navBackgroundColor = .clear
gk_navBackgroundColor = UIColor.colorWith(hexString: "122063")
gk_navTitleColor = kWhite
gk_backImage = R.image.btn_back_white()
view.addSubview(header)
view.addSubview(teamView)
// view.addSubview(header)
// view.addSubview(teamView)
// view.addSubview(radarView)
// radarView.addSubview(radarChartView)
//
// radarView.snp.makeConstraints { make in
// make.left.equalToSuperview().offset(10)
// make.right.equalToSuperview().offset(-10)
// make.top.equalTo(teamView.snp.bottom).offset(10)
// }
// radarChartView.snp.makeConstraints { make in
// make.centerX.equalToSuperview()
// make.top.equalToSuperview().offset(10)
// make.width.height.equalTo(300)
// make.bottom.equalToSuperview().offset(-10)
// }
//
// self.initRadarChartView()
// self.showRadarChartView()
initProvider()
handleRefresh()
}
override var preferredStatusBarStyle: UIStatusBarStyle {
return .lightContent
}
}
class RadialGradientLayer: CALayer {
var colors: [CGColor]?
var locations: [CGFloat]?
override func draw(in ctx: CGContext) {
guard let colors = colors, let locations = locations else { return }
override func handleRefresh() {
super.handleRefresh()
let colorSpace = CGColorSpaceCreateDeviceRGB()
let gradient = CGGradient(colorsSpace: colorSpace, colors: colors as CFArray, locations: locations)!
provider?.bigDataDetailRequest(yqId: yqId, completion: { logicResult in
if case .failure(let err) = logicResult {
if case AsError.netErr(let message) = err {
self.showEmpty(type: .netErr, message: message)
} else {
self.showEmpty(type: .other, message: err.localizedDescription)
}
}
})
}
private func initRadarChartView() {
let xAxis = radarChartView.xAxis
xAxis.labelFont = kBoldFontSize(12)
xAxis.xOffset = 0
xAxis.yOffset = 0
xAxis.valueFormatter = self
xAxis.labelTextColor = UIColor.colorWith(hexString: "475086")
let center = CGPoint(x: bounds.size.width / 2, y: bounds.size.height / 2)
let radius = min(bounds.size.width, bounds.size.height) / 2
let yAxis = radarChartView.yAxis
yAxis.labelFont = kBoldFontSize(12)
yAxis.axisMinimum = 0
yAxis.drawLabelsEnabled = false
yAxis.labelTextColor = UIColor.colorWith(hexString: "475086")
let l = radarChartView.legend
l.form = .circle
l.horizontalAlignment = .center
l.verticalAlignment = .bottom
l.orientation = .horizontal
l.drawInside = true
l.font = kFontSize(12)
l.xEntrySpace = 10
l.textColor = kMainTitleColor
}
func showRadarChartView() {
let hostList = [44, 85, 71, 86, 80]
let guestList = [17, 91, 45, 83, 77]
let axisRanges: [(min: Double, max: Double)] = [
(min: 0, max: 54),
(min: 0, max: 100),
(min: 0, max: 100),
(min: 0, max: 100),
(min: 0, max: 100)
]
// 归一化数据
let normalizedHostList = zip(hostList, axisRanges).map { value, range in
return RadarChartDataEntry(value: (Double(value) - range.min) / (range.max - range.min))
}
let normalizedGuestList = zip(guestList, axisRanges).map { value, range in
return RadarChartDataEntry(value: (Double(value) - range.min) / (range.max - range.min))
}
let set1 = RadarChartDataSet(entries: normalizedHostList, label: "主队")
set1.setColor(UIColor.colorWith(hexString: "1EA1FC"))
set1.fillColor = UIColor.colorWith(hexString: "73C4FD")
set1.drawFilledEnabled = true
set1.fillAlpha = 0.7
set1.lineWidth = 2
set1.drawHighlightCircleEnabled = true
set1.setDrawHighlightIndicators(false)
let set2 = RadarChartDataSet(entries: normalizedGuestList, label: "客队")
set2.setColor(UIColor.colorWith(hexString: "FC9377"))
set2.fillColor = UIColor.colorWith(hexString: "FBBAAA")
set2.drawFilledEnabled = true
set2.fillAlpha = 0.7
set2.lineWidth = 2
set2.drawHighlightCircleEnabled = true
set2.setDrawHighlightIndicators(false)
let data: RadarChartData = [set1, set2]
data.setDrawValues(false)
radarChartView.data = data
radarChartView.animate(xAxisDuration: 0, yAxisDuration: 1.4, easingOption: .linear)
}
}
extension HadoopDetailController: AxisValueFormatter {
func stringForValue(_ value: Double, axis: AxisBase?) -> String {
return activities[Int(value) % activities.count]
}
}
extension HadoopDetailController {
private func initProvider() {
provider = HadoopProvider(vc: self, showErr: false)
ctx.drawRadialGradient(
gradient,
startCenter: center, startRadius: 0,
endCenter: center, endRadius: radius,
options: .drawsAfterEndLocation
)
// provider?.matchList
// .asObservable()
// .subscribe(onNext: { [weak self] tmpModels in
// guard let self = self else { return }
//
//
// })
// .disposed(by: disposeBag)
}
}
//
// HadoopDetailRequestModel.swift
// AoleiSports
//
// Created by ilCode on 2024/6/28.
//
import Foundation
struct HadoopDetailRequestModel: Mappable {
var gameInfo: GameInfoModel?
var bigDataDetail: BigDataDetailModel?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
gameInfo <- map["game_info"]
bigDataDetail <- map["big_data_detail"]
}
}
struct GameInfoModel: Mappable {
var matchTime: Int?
var hostTeam: TeamModel?
var awayTeam: TeamModel?
var competition: DetailComModel?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
matchTime <- map["match_time"]
hostTeam <- map["host_team"]
awayTeam <- map["away_team"]
competition <- map["competition"]
}
}
struct TeamModel: Mappable {
var name: String?
var shortName: String?
var logo: String?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
name <- map["name"]
shortName <- map["short_name"]
logo <- map["logo"]
}
}
struct DetailComModel: Mappable {
var name: String?
var shortName: String?
var logo: String?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
name <- map["name"]
shortName <- map["short_name"]
logo <- map["logo"]
}
}
struct BigDataDetailModel: Mappable {
var radarChartData: RadarChartDataModel?
var statusAnalysis: StatusAnalysisModel?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
radarChartData <- map["radar_chart_data"]
statusAnalysis <- map["status_analysis"]
}
}
struct RadarChartDataModel: Mappable {
var hostResult: TeamRadarModel?
var guestResult: TeamRadarModel?
var predictValue: String?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
hostResult <- map["host_result"]
guestResult <- map["guest_result"]
predictValue <- map["predict_value"]
}
}
struct TeamRadarModel: Mappable {
var rankPoint: Int?
var teamWorth: Int?
var techScore: Int?
var attackTotal: Int?
var defendTotal: Int?
var statusScore: Int?
var stigmaResult: StigmaResultModel?
var winAvgBalls: String?
var loseAvgBalls: String?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
rankPoint <- map["rank_point"]
teamWorth <- map["team_worth"]
techScore <- map["tech_score"]
attackTotal <- map["attack_total"]
defendTotal <- map["defend_total"]
statusScore <- map["status_score"]
stigmaResult <- map["stigma_result"]
winAvgBalls <- map["win_avg_balls"]
loseAvgBalls <- map["lose_avg_balls"]
}
}
struct StigmaResultModel: Mappable {
var curResult: String?
var totalResult: Int?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
curResult <- map["cur_result"]
totalResult <- map["total_result"]
}
}
struct StatusAnalysisModel: Mappable {
var homeResult: TeamResultModel?
var awayResult: TeamResultModel?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
homeResult <- map["home_result"]
awayResult <- map["away_result"]
}
}
struct TeamResultModel: Mappable {
var statusTxt: String?
var resultValue: String?
var statusScore: Int?
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
statusTxt <- map["status_txt"]
resultValue <- map["result_value"]
statusScore <- map["status_score"]
}
}
......@@ -8,15 +8,29 @@
import UIKit
enum HadoopTarget: TargetType {
// 大数据列表
case bigDataList
// 大数据详情
case bigDataDetail(yqId: Int)
var task: Moya.Task {
let parameters = ["query": """
query{
\(APIs.kBigDataList)
}
"""]
return .requestParameters(parameters: parameters, encoding: JSONEncoding.default)
switch self {
case .bigDataList:
let parameters = ["query": """
query{
\(APIs.kBigDataList)
}
"""]
return .requestParameters(parameters: parameters, encoding: JSONEncoding.default)
case .bigDataDetail(let yqId):
let parameters = ["query": """
query{
\(APIs.kBigDataDetail)(yiqiu_id:\(yqId))
}
"""]
return .requestParameters(parameters: parameters, encoding: JSONEncoding.default)
}
}
}
......@@ -28,6 +42,7 @@ class HadoopProvider<Target: TargetType>: BaseMoyaProvider<Target> {
var comList = BehaviorRelay<[HadoopComModel]>(value: [])
var matchList = BehaviorRelay<[HadoopMatchModel]>(value: [])
// 大数据列表请求
func bigDataListRequest(completion: @escaping (Result<Bool, AsError>) -> Void) {
moyaPost(api: APIs.kBigDataList, target: HadoopTarget.bigDataList) { midResult in
// DDLogInfo("大数据研究列表接口数据:\(midResult)")
......@@ -74,4 +89,20 @@ class HadoopProvider<Target: TargetType>: BaseMoyaProvider<Target> {
}
}
}
// 大数据详情请求
func bigDataDetailRequest(yqId: Int, completion: @escaping (Result<Bool, AsError>) -> Void) {
moyaPost(api: APIs.kBigDataDetail, target: HadoopTarget.bigDataDetail(yqId: yqId)) { midResult in
// DDLogInfo("大数据详情接口数据:\(midResult)")
switch midResult {
case let .success(midSuccessResult):
let requestModel = HadoopDetailRequestModel(JSON: midSuccessResult)
completion(.success(true))
case .failure(let err):
completion(.failure(err))
}
}
}
}
......@@ -74,6 +74,7 @@ struct HadoopComModel: Mappable {
}
struct HadoopMatchModel: Mappable {
var yqId: Int?
var matchTime: String?
var comId: Int?
var comName: String?
......@@ -89,6 +90,7 @@ struct HadoopMatchModel: Mappable {
init?(map: ObjectMapper.Map) { }
mutating func mapping(map: ObjectMapper.Map) {
yqId <- map["yiqiu_id"]
matchTime <- map["match_time"]
comId <- map["competition_id"]
comName <- map["competition_name"]
......
......@@ -30,5 +30,7 @@ struct APIs {
// 大数据列表
static let kBigDataList = "get_big_data_list"
// 大数据详情
static let kBigDataDetail = "get_big_data_detail"
}
......@@ -18,6 +18,7 @@ target 'AoleiSports' do
pod 'ESPullToRefresh', '~> 2.9.3'
pod 'SwiftyUserDefaults', '~> 5.3.0'
pod 'Kingfisher', '~> 7.12.0'
pod 'DGCharts', '~> 5.1.0'
end
......
......@@ -3,6 +3,9 @@ PODS:
- CocoaLumberjack/Core (3.8.5)
- CocoaLumberjack/Swift (3.8.5):
- CocoaLumberjack/Core
- DGCharts (5.1.0):
- DGCharts/Core (= 5.1.0)
- DGCharts/Core (5.1.0)
- ESPullToRefresh (2.9.3)
- Kingfisher (7.12.0)
- Moya/Core (15.0.0):
......@@ -32,6 +35,7 @@ PODS:
DEPENDENCIES:
- Alamofire (~> 5.9.1)
- CocoaLumberjack/Swift
- DGCharts (~> 5.1.0)
- ESPullToRefresh (~> 2.9.3)
- Kingfisher (~> 7.12.0)
- Moya/RxSwift (~> 15.0)
......@@ -50,6 +54,7 @@ SPEC REPOS:
trunk:
- Alamofire
- CocoaLumberjack
- DGCharts
- ESPullToRefresh
- Kingfisher
- Moya
......@@ -68,6 +73,7 @@ SPEC REPOS:
SPEC CHECKSUMS:
Alamofire: f36a35757af4587d8e4f4bfa223ad10be2422b8c
CocoaLumberjack: 6a459bc897d6d80bd1b8c78482ec7ad05dffc3f0
DGCharts: 1c6daf585b6cfc78807af44ea690d357c410627f
ESPullToRefresh: 0d68daa602b343c81753a1b95e09fd0bfcddfd40
Kingfisher: 53a10ea35051a436b5fb626ca2dd8f3144d755e9
Moya: 138f0573e53411fb3dc17016add0b748dfbd78ee
......@@ -83,6 +89,6 @@ SPEC CHECKSUMS:
SwiftyUserDefaults: 63f80248cf5bfb3458825d9a78f2eb7e1293a040
Toast-Swift: 7a03a532afe3a560d4044bc7c237e2864d295173
PODFILE CHECKSUM: e0240e4c63b8761b0e735050fb2e59981354c37b
PODFILE CHECKSUM: 6e60c8c96962c64ea9bf961afe8a6d4759817bda
COCOAPODS: 1.15.2
支持 Markdown 格式
你添加了 0 到此讨论。请谨慎行事。
Finish editing this message first!