DemoBaseViewController.swift 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366
  1. //
  2. // DemoBaseViewController.swift
  3. // ChartsDemo-iOS
  4. //
  5. // Created by Jacob Christie on 2017-07-03.
  6. // Copyright © 2017 jc. All rights reserved.
  7. //
  8. #if canImport(UIKit)
  9. import UIKit
  10. #endif
  11. import Charts
  12. enum Option {
  13. case toggleValues
  14. case toggleIcons
  15. case toggleHighlight
  16. case animateX
  17. case animateY
  18. case animateXY
  19. case saveToGallery
  20. case togglePinchZoom
  21. case toggleAutoScaleMinMax
  22. case toggleData
  23. case toggleBarBorders
  24. // CandleChart
  25. case toggleShadowColorSameAsCandle
  26. case toggleShowCandleBar
  27. // CombinedChart
  28. case toggleLineValues
  29. case toggleBarValues
  30. case removeDataSet
  31. // CubicLineSampleFillFormatter
  32. case toggleFilled
  33. case toggleCircles
  34. case toggleCubic
  35. case toggleHorizontalCubic
  36. case toggleStepped
  37. // HalfPieChartController
  38. case toggleXValues
  39. case togglePercent
  40. case toggleHole
  41. case spin
  42. case drawCenter
  43. // RadarChart
  44. case toggleXLabels
  45. case toggleYLabels
  46. case toggleRotate
  47. case toggleHighlightCircle
  48. var label: String {
  49. switch self {
  50. case .toggleValues: return "Toggle Y-Values"
  51. case .toggleIcons: return "Toggle Icons"
  52. case .toggleHighlight: return "Toggle Highlight"
  53. case .animateX: return "Animate X"
  54. case .animateY: return "Animate Y"
  55. case .animateXY: return "Animate XY"
  56. case .saveToGallery: return "Save to Camera Roll"
  57. case .togglePinchZoom: return "Toggle PinchZoom"
  58. case .toggleAutoScaleMinMax: return "Toggle auto scale min/max"
  59. case .toggleData: return "Toggle Data"
  60. case .toggleBarBorders: return "Toggle Bar Borders"
  61. // CandleChart
  62. case .toggleShadowColorSameAsCandle: return "Toggle shadow same color"
  63. case .toggleShowCandleBar: return "Toggle show candle bar"
  64. // CombinedChart
  65. case .toggleLineValues: return "Toggle Line Values"
  66. case .toggleBarValues: return "Toggle Bar Values"
  67. case .removeDataSet: return "Remove Random Set"
  68. // CubicLineSampleFillFormatter
  69. case .toggleFilled: return "Toggle Filled"
  70. case .toggleCircles: return "Toggle Circles"
  71. case .toggleCubic: return "Toggle Cubic"
  72. case .toggleHorizontalCubic: return "Toggle Horizontal Cubic"
  73. case .toggleStepped: return "Toggle Stepped"
  74. // HalfPieChartController
  75. case .toggleXValues: return "Toggle X-Values"
  76. case .togglePercent: return "Toggle Percent"
  77. case .toggleHole: return "Toggle Hole"
  78. case .spin: return "Spin"
  79. case .drawCenter: return "Draw CenterText"
  80. // RadarChart
  81. case .toggleXLabels: return "Toggle X-Labels"
  82. case .toggleYLabels: return "Toggle Y-Labels"
  83. case .toggleRotate: return "Toggle Rotate"
  84. case .toggleHighlightCircle: return "Toggle highlight circle"
  85. }
  86. }
  87. }
  88. class DemoBaseViewController: UIViewController, ChartViewDelegate {
  89. private var optionsTableView: UITableView? = nil
  90. let parties = ["Party A", "Party B", "Party C", "Party D", "Party E", "Party F",
  91. "Party G", "Party H", "Party I", "Party J", "Party K", "Party L",
  92. "Party M", "Party N", "Party O", "Party P", "Party Q", "Party R",
  93. "Party S", "Party T", "Party U", "Party V", "Party W", "Party X",
  94. "Party Y", "Party Z"]
  95. @IBOutlet weak var optionsButton: UIButton!
  96. var options: [Option]!
  97. var shouldHideData: Bool = false
  98. required init?(coder aDecoder: NSCoder) {
  99. super.init(coder: aDecoder)
  100. self.initialize()
  101. }
  102. override init(nibName nibNameOrNil: String?, bundle nibBundleOrNil: Bundle?) {
  103. super.init(nibName: nibNameOrNil, bundle: nibBundleOrNil)
  104. self.initialize()
  105. }
  106. private func initialize() {
  107. self.edgesForExtendedLayout = []
  108. }
  109. func optionTapped(_ option: Option) {}
  110. func handleOption(_ option: Option, forChartView chartView: ChartViewBase) {
  111. switch option {
  112. case .toggleValues:
  113. for set in chartView.data!.dataSets {
  114. set.drawValuesEnabled = !set.drawValuesEnabled
  115. }
  116. chartView.setNeedsDisplay()
  117. case .toggleIcons:
  118. for set in chartView.data!.dataSets {
  119. set.drawIconsEnabled = !set.drawIconsEnabled
  120. }
  121. chartView.setNeedsDisplay()
  122. case .toggleHighlight:
  123. chartView.data!.highlightEnabled = !chartView.data!.isHighlightEnabled
  124. chartView.setNeedsDisplay()
  125. case .animateX:
  126. chartView.animate(xAxisDuration: 3)
  127. case .animateY:
  128. chartView.animate(yAxisDuration: 3)
  129. case .animateXY:
  130. chartView.animate(xAxisDuration: 3, yAxisDuration: 3)
  131. case .saveToGallery:
  132. UIImageWriteToSavedPhotosAlbum(chartView.getChartImage(transparent: false)!, nil, nil, nil)
  133. case .togglePinchZoom:
  134. let barLineChart = chartView as! BarLineChartViewBase
  135. barLineChart.pinchZoomEnabled = !barLineChart.pinchZoomEnabled
  136. chartView.setNeedsDisplay()
  137. case .toggleAutoScaleMinMax:
  138. let barLineChart = chartView as! BarLineChartViewBase
  139. barLineChart.autoScaleMinMaxEnabled = !barLineChart.isAutoScaleMinMaxEnabled
  140. chartView.notifyDataSetChanged()
  141. case .toggleData:
  142. shouldHideData = !shouldHideData
  143. updateChartData()
  144. case .toggleBarBorders:
  145. for set in chartView.data!.dataSets {
  146. if let set = set as? BarChartDataSet {
  147. set.barBorderWidth = set.barBorderWidth == 1.0 ? 0.0 : 1.0
  148. }
  149. }
  150. chartView.setNeedsDisplay()
  151. default:
  152. break
  153. }
  154. }
  155. @IBAction func optionsButtonTapped(_ sender: Any) {
  156. if let optionsTableView = self.optionsTableView {
  157. optionsTableView.removeFromSuperview()
  158. self.optionsTableView = nil
  159. return
  160. }
  161. let optionsTableView = UITableView()
  162. optionsTableView.backgroundColor = UIColor(white: 0, alpha: 0.9)
  163. optionsTableView.delegate = self
  164. optionsTableView.dataSource = self
  165. optionsTableView.translatesAutoresizingMaskIntoConstraints = false
  166. self.optionsTableView = optionsTableView
  167. var constraints = [NSLayoutConstraint]()
  168. constraints.append(NSLayoutConstraint(item: optionsTableView,
  169. attribute: .leading,
  170. relatedBy: .equal,
  171. toItem: self.view,
  172. attribute: .leading,
  173. multiplier: 1,
  174. constant: 40))
  175. constraints.append(NSLayoutConstraint(item: optionsTableView,
  176. attribute: .trailing,
  177. relatedBy: .equal,
  178. toItem: sender as! UIView,
  179. attribute: .trailing,
  180. multiplier: 1,
  181. constant: 0))
  182. constraints.append(NSLayoutConstraint(item: optionsTableView,
  183. attribute: .top,
  184. relatedBy: .equal,
  185. toItem: sender,
  186. attribute: .bottom,
  187. multiplier: 1,
  188. constant: 5))
  189. self.view.addSubview(optionsTableView)
  190. constraints.forEach { $0.isActive = true }
  191. let constraint = NSLayoutConstraint(item: optionsTableView,
  192. attribute: .height,
  193. relatedBy: .equal,
  194. toItem: nil,
  195. attribute: .height,
  196. multiplier: 1,
  197. constant: 220)
  198. constraint.isActive = true
  199. }
  200. func updateChartData() {
  201. fatalError("updateChartData not overridden")
  202. }
  203. func setup(pieChartView chartView: PieChartView) {
  204. chartView.usePercentValuesEnabled = true
  205. chartView.drawSlicesUnderHoleEnabled = false
  206. chartView.holeRadiusPercent = 0.58
  207. chartView.transparentCircleRadiusPercent = 0.61
  208. chartView.chartDescription?.enabled = false
  209. chartView.setExtraOffsets(left: 5, top: 10, right: 5, bottom: 5)
  210. chartView.drawCenterTextEnabled = true
  211. let paragraphStyle = NSParagraphStyle.default.mutableCopy() as! NSMutableParagraphStyle
  212. paragraphStyle.lineBreakMode = .byTruncatingTail
  213. paragraphStyle.alignment = .center
  214. let centerText = NSMutableAttributedString(string: "Charts\nby Daniel Cohen Gindi")
  215. centerText.setAttributes([.font : UIFont(name: "HelveticaNeue-Light", size: 13)!,
  216. .paragraphStyle : paragraphStyle], range: NSRange(location: 0, length: centerText.length))
  217. centerText.addAttributes([.font : UIFont(name: "HelveticaNeue-Light", size: 11)!,
  218. .foregroundColor : UIColor.gray], range: NSRange(location: 10, length: centerText.length - 10))
  219. centerText.addAttributes([.font : UIFont(name: "HelveticaNeue-Light", size: 11)!,
  220. .foregroundColor : UIColor(red: 51/255, green: 181/255, blue: 229/255, alpha: 1)], range: NSRange(location: centerText.length - 19, length: 19))
  221. chartView.centerAttributedText = centerText;
  222. chartView.drawHoleEnabled = true
  223. chartView.rotationAngle = 0
  224. chartView.rotationEnabled = true
  225. chartView.highlightPerTapEnabled = true
  226. let l = chartView.legend
  227. l.horizontalAlignment = .right
  228. l.verticalAlignment = .top
  229. l.orientation = .vertical
  230. l.drawInside = false
  231. l.xEntrySpace = 7
  232. l.yEntrySpace = 0
  233. l.yOffset = 0
  234. // chartView.legend = l
  235. }
  236. func setup(radarChartView chartView: RadarChartView) {
  237. chartView.chartDescription?.enabled = false
  238. }
  239. func setup(barLineChartView chartView: BarLineChartViewBase) {
  240. chartView.chartDescription?.enabled = false
  241. chartView.dragEnabled = true
  242. chartView.setScaleEnabled(true)
  243. chartView.pinchZoomEnabled = false
  244. // ChartYAxis *leftAxis = chartView.leftAxis;
  245. let xAxis = chartView.xAxis
  246. xAxis.labelPosition = .bottom
  247. chartView.rightAxis.enabled = false
  248. }
  249. // TODO: Cannot override from extensions
  250. //extension DemoBaseViewController: ChartViewDelegate {
  251. func chartValueSelected(_ chartView: ChartViewBase, entry: ChartDataEntry, highlight: Highlight) {
  252. NSLog("chartValueSelected");
  253. }
  254. func chartValueNothingSelected(_ chartView: ChartViewBase) {
  255. NSLog("chartValueNothingSelected");
  256. }
  257. func chartScaled(_ chartView: ChartViewBase, scaleX: CGFloat, scaleY: CGFloat) {
  258. }
  259. func chartTranslated(_ chartView: ChartViewBase, dX: CGFloat, dY: CGFloat) {
  260. }
  261. }
  262. extension DemoBaseViewController: UITableViewDelegate, UITableViewDataSource {
  263. func numberOfSections(in tableView: UITableView) -> Int {
  264. if optionsTableView != nil {
  265. return 1
  266. }
  267. return 0
  268. }
  269. @available(iOS 2.0, *)
  270. func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
  271. if optionsTableView != nil {
  272. return options.count
  273. }
  274. return 0
  275. }
  276. func tableView(_ tableView: UITableView, heightForRowAt indexPath: IndexPath) -> CGFloat {
  277. if optionsTableView != nil {
  278. return 40.0;
  279. }
  280. return 44.0;
  281. }
  282. @available(iOS 2.0, *)
  283. func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
  284. var cell = tableView.dequeueReusableCell(withIdentifier: "Cell")
  285. if cell == nil {
  286. cell = UITableViewCell(style: .default, reuseIdentifier: "Cell")
  287. cell?.backgroundView = nil
  288. cell?.backgroundColor = .clear
  289. cell?.textLabel?.textColor = .white
  290. }
  291. cell?.textLabel?.text = self.options[indexPath.row].label
  292. return cell!
  293. }
  294. func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
  295. if optionsTableView != nil {
  296. tableView.deselectRow(at: indexPath, animated: true)
  297. optionsTableView?.removeFromSuperview()
  298. self.optionsTableView = nil
  299. self.optionTapped(self.options[indexPath.row])
  300. }
  301. }
  302. }