Skip to content

Commit

Permalink
Merge pull request #11 from NullIsOne/ui-customization
Browse files Browse the repository at this point in the history
UI customization
  • Loading branch information
NullIsOne committed Apr 3, 2024
2 parents acc7080 + 26465e8 commit 38d4502
Show file tree
Hide file tree
Showing 26 changed files with 947 additions and 33 deletions.
51 changes: 48 additions & 3 deletions DOCUMENTATION.md
Original file line number Diff line number Diff line change
@@ -1,11 +1,32 @@
# PlayerView customisation

![Player Overview](doc_support/player.png)

All components of `KinescopePlayerView` is partially customisable. You can change colors, fonts, sizes using method `KinescopePlayerView.setLayout(with config: KinescopePlayerViewConfiguration)`.

All properties of `KinescopePlayerViewConfiguration` have default values included in SDK, so customisation is optional.
All properties of `KinescopePlayerViewConfiguration` have default values included in SDK, so customisation is optional.

You can easily edit these values using builders.
For examle to change color of timeline in control panel you can use this code:
```swift
playerView.setLayout(with: .builder().setControlPanel(
.builder()
.setTimeline(
.builder()
.setActiveColor(color)
.build()
)
.build())
)
```
or you can use predefined configurable configuration `accentTimeLineAndPlayButton` to change color of timeline and play button in control panel.

Using these builders you can change any property of `KinescopePlayerViewConfiguration` and apply it to player view. To learn about properties more you should read next chapters of this doc.

## Managing of options menu

![Player Options Menu](doc_support/options_menu.png)

Options menu is a set of buttons with different actions like AirPlay, Picture in Picture, etc. You can manage this menu by adding or removing some options.

By default, options menu is collapsed, but you can show it by tapping on the options button with dots in the bottom right corner of the player view.
Expand Down Expand Up @@ -89,28 +110,52 @@ Set `nil` to hide overlay (usefull for videos collection with autoplaying).
Default implementation could be checked in Example project.

### controlPanel
Configuration of control panel with timeline and time labels.

![Player Control Panel](doc_support/control_panel.png)

Configuration of control panel with timeline, time labels and live indicator.

You can modify textColor, fontSize, colors and sizes of control panel and it's components.

Set `nil` to hide control panel.

Default implementation could be checked in Example project.

### announceView

![Player Announce View](doc_support/announce_view.png)

Configuration of announce view with information of planned time of start for live streams.

Youc can modify textColor, fontSize and icon for announce view.

Default implementation could be checked in Example project.

### errorOverlay

![Player Error Overlay](doc_support/error_overlay.png)

Configuration for error view with refresh button. Showing on broken livestreams or repeated failed attempts to play video.

You can modify textColor, fontSize and backgroundColor of error overlay and it's components.

Set `nil` to hide control panel

Default implementation could be checked in Example project.

### sideMenu

![Player Side Menu](doc_support/side_menu.png)

Configuration of side menu with setings.

You can modify main side menu and items on secondary menu level.

Default implementation could be checked in Example project.

### shadowOverlay

Configuration of shadow overlay beneath side menu.
Configuration of shadow overlay beneath side menu showing on fullscreen mode.

Default implementation could be checked in Example project.

Expand Down
2 changes: 1 addition & 1 deletion Example/KinescopeExample/Flows/VideoViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ final class VideoViewController: UIViewController {

navigationController?.delegate = self

playerView.setLayout(with: .default)
playerView.setLayout(with: .accentTimeLineAndPlayButton(with: .orange))

PipManager.shared.closePipIfNeeded(with: videoId)

Expand Down
2 changes: 2 additions & 0 deletions Sources/KinescopeSDK/Models/KinescopePlayerConfig.swift
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
// Created by Никита Коробейников on 29.03.2021.
//

import Foundation

/// Configuration entity required to connect resource with player
public struct KinescopePlayerConfig {

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
// Created by Artemii Shabanov on 22.04.2021.
//

import UIKit
import AVFoundation

public protocol KinescopeVideoPlayerDelegate: AnyObject {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import UIKit

/// Appearance preferences for announcement snack
public struct KinescopeAnnounceConfiguration {

let image: UIImage
let titleFont: UIFont
let titleColor: UIColor
Expand Down Expand Up @@ -40,6 +40,10 @@ public struct KinescopeAnnounceConfiguration {
// MARK: - Defaults

public extension KinescopeAnnounceConfiguration {

static func builder() -> KinescopeAnnounceConfigurationBuilder {
.init(configuration: .default)
}

static let `default`: KinescopeAnnounceConfiguration = .init(
image: UIImage.image(named: "announce"),
Expand All @@ -50,3 +54,64 @@ public extension KinescopeAnnounceConfiguration {
backgroundColor: .init(red: 0.13, green: 0.13, blue: 0.13, alpha: 0.8)
)
}

// MARK: - Builder

public class KinescopeAnnounceConfigurationBuilder {
private var image: UIImage = UIImage()
private var titleFont: UIFont = UIFont.systemFont(ofSize: 14)
private var titleColor: UIColor = .black
private var subtitleFont: UIFont = UIFont.systemFont(ofSize: 12)
private var subtitleColor: UIColor = .gray
private var backgroundColor: UIColor = .white

public init(configuration: KinescopeAnnounceConfiguration = .default) {
self.image = configuration.image
self.titleFont = configuration.titleFont
self.titleColor = configuration.titleColor
self.subtitleFont = configuration.subtitleFont
self.subtitleColor = configuration.subtitleColor
self.backgroundColor = configuration.backgroundColor
}

public func setImage(_ image: UIImage) -> Self {
self.image = image
return self
}

public func setTitleFont(_ font: UIFont) -> Self {
self.titleFont = font
return self
}

public func setTitleColor(_ color: UIColor) -> Self {
self.titleColor = color
return self
}

public func setSubtitleFont(_ font: UIFont) -> Self {
self.subtitleFont = font
return self
}

public func setSubtitleColor(_ color: UIColor) -> Self {
self.subtitleColor = color
return self
}

public func setBackgroundColor(_ color: UIColor) -> Self {
self.backgroundColor = color
return self
}

public func build() -> KinescopeAnnounceConfiguration {
return KinescopeAnnounceConfiguration(
image: image,
titleFont: titleFont,
titleColor: titleColor,
subtitleFont: subtitleFont,
subtitleColor: subtitleColor,
backgroundColor: backgroundColor
)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,10 @@ public struct KinescopeControlPanelConfiguration {
// MARK: - Defaults

public extension KinescopeControlPanelConfiguration {

static func builder() -> KinescopeControlPanelConfigurationBuilder {
.init(configuration: .default)
}

static let `default`: KinescopeControlPanelConfiguration = .init(
tintColor: .gray,
Expand All @@ -64,3 +68,78 @@ public extension KinescopeControlPanelConfiguration {
)

}

// MARK: - Builder

public class KinescopeControlPanelConfigurationBuilder {
private var tintColor: UIColor
private var backgroundColor: UIColor
private var preferedHeight: CGFloat
private var hideOnPlayTimeout: TimeInterval?
private var liveIndicator: KinescopeLiveIndicatorConfiguration
private var timeIndicator: KinescopePlayerTimeindicatorConfiguration
private var timeline: KinescopePlayerTimelineConfiguration
private var optionsMenu: KinescopePlayerOptionsConfiguration

public init(configuration: KinescopeControlPanelConfiguration = .default) {
self.tintColor = configuration.tintColor
self.backgroundColor = configuration.backgroundColor
self.preferedHeight = configuration.preferedHeight
self.hideOnPlayTimeout = configuration.hideOnPlayTimeout
self.liveIndicator = configuration.liveIndicator
self.timeIndicator = configuration.timeIndicator
self.timeline = configuration.timeline
self.optionsMenu = configuration.optionsMenu
}

public func setTintColor(_ color: UIColor) -> Self {
self.tintColor = color
return self
}

public func setBackgroundColor(_ color: UIColor) -> Self {
self.backgroundColor = color
return self
}

public func setPreferedHeight(_ height: CGFloat) -> Self {
self.preferedHeight = height
return self
}

public func setHideOnPlayTimeout(_ timeout: TimeInterval?) -> Self {
self.hideOnPlayTimeout = timeout
return self
}

public func setLiveIndicator(_ configuration: KinescopeLiveIndicatorConfiguration) -> Self {
self.liveIndicator = configuration
return self
}

public func setTimeIndicator(_ configuration: KinescopePlayerTimeindicatorConfiguration) -> Self {
self.timeIndicator = configuration
return self
}

public func setTimeline(_ configuration: KinescopePlayerTimelineConfiguration) -> Self {
self.timeline = configuration
return self
}

public func setOptionsMenu(_ configuration: KinescopePlayerOptionsConfiguration) -> Self {
self.optionsMenu = configuration
return self
}

public func build() -> KinescopeControlPanelConfiguration {
return .init(tintColor: tintColor,
backgroundColor: backgroundColor,
preferedHeight: preferedHeight,
hideOnPlayTimeout: hideOnPlayTimeout,
liveIndicator: liveIndicator,
timeIndicator: timeIndicator,
timeline: timeline,
optionsMenu: optionsMenu)
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -53,6 +53,10 @@ public struct KinescopeErrorConfiguration {
// MARK: - Defaults

public extension KinescopeErrorConfiguration {

static func builder() -> KinescopeErrorConfigurationBuilder {
.init(configuration: .default)
}

static let `default`: KinescopeErrorConfiguration = .init(
image: UIImage.image(named: "warn"),
Expand All @@ -67,3 +71,88 @@ public extension KinescopeErrorConfiguration {
)

}

// MARK: - Builder

public class KinescopeErrorConfigurationBuilder {
private var image: UIImage = UIImage.image(named: "warn")
private var titleFont: UIFont = .systemFont(ofSize: 16, weight: .medium)
private var titleColor: UIColor = .white
private var subtitleFont: UIFont = .systemFont(ofSize: 14, weight: .regular)
private var subtitleColor: UIColor = .white.withAlphaComponent(0.64)
private var buttonTitleFont: UIFont = .systemFont(ofSize: 14, weight: .medium)
private var buttonTitleColor: UIColor = .white
private var buttonColor: UIColor = .white.withAlphaComponent(0.08)
private var backgroundColor: UIColor = .init(red: 0.13, green: 0.13, blue: 0.13, alpha: 0.8)

public init(configuration: KinescopeErrorConfiguration = .default) {
self.image = configuration.image
self.titleFont = configuration.titleFont
self.titleColor = configuration.titleColor
self.subtitleFont = configuration.subtitleFont
self.subtitleColor = configuration.subtitleColor
self.buttonTitleFont = configuration.buttonTtileFont
self.buttonTitleColor = configuration.buttonTitleColor
self.buttonColor = configuration.buttonColor
self.backgroundColor = configuration.backgroundColor
}

public func setImage(_ image: UIImage) -> Self {
self.image = image
return self
}

public func setTitleFont(_ font: UIFont) -> Self {
self.titleFont = font
return self
}

public func setTitleColor(_ color: UIColor) -> Self {
self.titleColor = color
return self
}

public func setSubtitleFont(_ font: UIFont) -> Self {
self.subtitleFont = font
return self
}

public func setSubtitleColor(_ color: UIColor) -> Self {
self.subtitleColor = color
return self
}

public func setButtonTitleFont(_ font: UIFont) -> Self {
self.buttonTitleFont = font
return self
}

public func setButtonTitleColor(_ color: UIColor) -> Self {
self.buttonTitleColor = color
return self
}

public func setButtonColor(_ color: UIColor) -> Self {
self.buttonColor = color
return self
}

public func setBackgroundColor(_ color: UIColor) -> Self {
self.backgroundColor = color
return self
}

public func build() -> KinescopeErrorConfiguration {
return KinescopeErrorConfiguration(
image: image,
titleFont: titleFont,
titleColor: titleColor,
subtitleFont: subtitleFont,
subtitleColor: subtitleColor,
buttonTtileFont: buttonTitleFont,
buttonTitleColor: buttonTitleColor,
buttonColor: buttonColor,
backgroundColor: backgroundColor
)
}
}
Loading

0 comments on commit 38d4502

Please sign in to comment.