Skip to content

[DVMod] Initial Build of DVMod System. #12

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 10 commits into from
Jul 24, 2021
Merged
Original file line number Diff line number Diff line change
@@ -1,60 +1,202 @@
import Foundation
import SwiftUI

/// [DE] A configuration class working for `DefinedView` protocol system.
///
/// Fields of this struct should be able to access from outside (for development purpose),
/// but should NOT be able to modify from outside!
/// So we make them all `private(set)` for modifier and `public` for accessor.
public struct DefinedViewConfiguration {
/// A boolean representing if the `width` and `height` are activated for defining the internal frame size.
///
/// - Important: This variable should not be changed!
var inactive: Bool
/// - Important: This variable should NOT be changed!
private(set) public var inactive: Bool

/// The frame width of the view.
///
var width: CGFloat
/// When it is `.infinity`, we will automatically push left and right boundaries to the limit.
/// You can manually set the width by using `.infinity`,
/// or you can use `.full` in setting the frame to avoid buggy.
private(set) public var width: CGFloat

/// The frame height of the view.
///
var height: CGFloat
/// When it is `.infinity`, we will automatically push top and bottom boundaries to the limit.
/// You can manually set the width by using `.infinity`,
/// or you can use `.full` in setting the frame to avoid buggy.
private(set) public var height: CGFloat

/// Width constrain flag. Is this view constrained by the **width**?
///
/// True for constrain. False for not.
///
/// In other words, if it is not constrained, then we will not render the frame by the width value.
private(set) public var isWidthConstrained: Bool

/// Height constrain flag. Is this view constrained by the **height**?
///
var isWidthConstrained: Bool
/// True for constrain. False for not.
///
/// In other words, if it is not constrained, then we will not render the frame by the height value.
private(set) public var isHeightConstrained: Bool

/// Width setup flag. Is this view constrained by a post-setting **width**?
///
/// True for manually setting. False for default setting.
///
var isHeightConstrained: Bool
/// In other words, check if we need to apply another frame set on this view.
/// If it has already been set once, we do NOT need to, then try a wrap.
private(set) public var isWidthSet: Bool

/// Height setup flag. Is this view constrained by a post-setting **height**?
///
public init() {
self.inactive = false
/// True for manually setting. False for default setting.
///
/// In other words, check if we need to apply another frame set on this view.
/// If it has already been set once, we do NOT need to, then try a wrap.
private(set) public var isHeightSet: Bool

/// The frame alignment of the view.
///
/// It treats as the same as the default `alignment`,
/// but we are actually able to manually setup the usage of this value in a view component.
///
/// - Note: The developer can manually use this value instead of using it in the default way.
private(set) public var alignment: Alignment

/// Alignment setup flag. Is this view constrained by a post-setting **alignment**?
///
/// True for manually setting. False for default setting.
private(set) public var isAlignmentSet: Bool

/// [DE Inactive] Create a ViewConfiguration that does NOT apply onto the view.
///
/// - Note: In this case, the root view should NOT use these values anymore!
public init(inactive: Bool) {
self.inactive = inactive
self.width = 0
self.isWidthConstrained = false
self.isWidthSet = false
self.height = 0
self.isHeightConstrained = false
self.isHeightSet = false
self.alignment = .center
self.isAlignmentSet = false
}

/// [DE] Create a ViewConfiguration with by default no frame constrained.
///
public init(inactive: Bool) {
self.inactive = inactive
/// - Parameters:
/// - alignment: The default alignment of the frame. (Optional, default as `.center`)
/// - isAlignmentSet: Will we treat it as a manual set? (So the alignment will not be overrided later)
public init(
alignment: Alignment = .center,
isAlignmentSet: Bool = false
) {
self.inactive = false
self.width = 0
self.isWidthConstrained = false
self.isWidthSet = false
self.height = 0
self.isHeightConstrained = false
self.isHeightSet = false
self.alignment = alignment
self.isAlignmentSet = isAlignmentSet
}

/// [DE] Create a ViewConfiguration with by default width frame constrained.
///
/// - Parameters:
/// - width: The width of the view frame.
/// - isWidthSet: Will we treat this width as a manual set? (So the width will not be overrided later)
/// - alignment: The default alignment of the frame.
/// - isAlignmentSet: Will we treat this alignment as a manual set? (So the alignment will not be overrided later)
public init(
width: CGFloat,
isWidthSet: Bool = false,
alignment: Alignment = .center,
isAlignmentSet: Bool = false
) {
self.inactive = false
self.width = width
self.isWidthConstrained = true
self.isWidthSet = isWidthSet
self.height = 0
self.isHeightConstrained = false
self.isHeightSet = false
self.alignment = alignment
self.isAlignmentSet = isAlignmentSet
}

/// [DE] Create a ViewConfiguration with by default height frame constrained.
///
/// - Parameters:
/// - height: The height of the view frame.
/// - isHeightSet: Will we treat this height as a manual set? (So the height will not be overrided later)
/// - alignment: The default alignment of the frame.
/// - isAlignmentSet: Will we treat this alignment as a manual set? (So the alignment will not be overrided later)
public init(
height: CGFloat,
isHeightSet: Bool = false,
alignment: Alignment = .center,
isAlignmentSet: Bool = false
) {
self.inactive = false
self.width = 0
self.isWidthConstrained = false
self.isWidthSet = false
self.height = height
self.isHeightConstrained = true
self.isHeightSet = isHeightSet
self.alignment = alignment
self.isAlignmentSet = isAlignmentSet
}

/// [DE] Create a ViewConfiguration with by default full frame constrained.
///
public init(width: CGFloat, height: CGFloat) {
/// - Parameters:
/// - width: The width of the view frame.
/// - isWidthSet: Will we treat this width as a manual set? (So the width will not be overrided later)
/// - height: The height of the view frame.
/// - isHeightSet: Will we treat this height as a manual set? (So the height will not be overrided later)
/// - alignment: The default alignment of the frame.
/// - isAlignmentSet: Will we treat this alignment as a manual set? (So the alignment will not be overrided later)
public init(
width: CGFloat,
isWidthSet: Bool = false,
height: CGFloat,
isHeightSet: Bool = false,
alignment: Alignment = .center,
isAlignmentSet: Bool = false
) {
self.inactive = false
self.width = width
self.isWidthConstrained = true
self.isWidthSet = isWidthSet
self.height = height
self.isHeightConstrained = true
self.isHeightSet = isHeightSet
self.alignment = alignment
self.isAlignmentSet = isAlignmentSet
}

/// [Internal]
init(oldConfiguration: DefinedViewConfiguration,
width: CGFloat? = nil,
height: CGFloat? = nil) {
internal init(
oldConfiguration: DefinedViewConfiguration,
width: CGFloat? = nil,
isWidthSet: Bool? = nil,
height: CGFloat? = nil,
isHeightSet: Bool? = nil,
alignment: Alignment? = nil,
isAlignmentSet: Bool? = nil
) {
self.inactive = oldConfiguration.inactive // this value may NOT be changed during copying.
self.width = width ?? oldConfiguration.width
self.isWidthConstrained = oldConfiguration.isWidthConstrained || width != nil
self.isWidthSet = isWidthSet ?? oldConfiguration.isWidthSet
self.height = height ?? oldConfiguration.height
self.isHeightConstrained = oldConfiguration.isHeightConstrained || height != nil
self.isHeightSet = isHeightSet ?? oldConfiguration.isHeightSet
self.alignment = alignment ?? oldConfiguration.alignment
self.isAlignmentSet = isAlignmentSet ?? (oldConfiguration.isAlignmentSet || alignment != nil)
}
}
51 changes: 29 additions & 22 deletions Sources/DefinedElements/Frameworks/View/DV.Protocol.swift
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
import Foundation
import SwiftUI

// MARK: - Protocol
Expand All @@ -7,13 +6,15 @@ import SwiftUI
///
/// You can also use it if you want to create your own `DefinedView` component.
///
/// - TODO: Fix `status` pointer problem.
/// - TODO: Finish the development of Configurations.
public protocol DefinedView : View {
/// Configurate all things related to view frame.
///
/// If you do not want to constrain the view with a bridge frame, you can disable it:
///
/// var viewConfiguration = DefinedViewConfiguration(inactive: true)
/// ``` swift
/// var viewConfiguration = DefinedViewConfiguration(inactive: true)
/// ```
///
/// otherwise, you can set the default frame size by using basic initializer
/// `init(default:loading:active:done:error:disabled:)`.
Expand All @@ -25,7 +26,9 @@ public protocol DefinedView : View {
///
/// If you do not want to constrain the view with background views, you can disable it:
///
/// var backgroundConfiguration = DefinedViewBackgroundConfiguration(inactive: true)
/// ``` swift
/// var backgroundConfiguration = DefinedViewBackgroundConfiguration(inactive: true)
/// ```
///
/// otherwise, you can set the default background views by using basic initializer
/// `init(default:loading:active:done:error:disabled:)`.
Expand All @@ -36,8 +39,9 @@ public protocol DefinedView : View {
/// Configurate all things related to border setup.
///
/// If you do not want to constrain the view with a border, you can disable it:
///
/// var borderConfiguration = DefinedViewBorderConfiguration(inactive: true)
/// ``` swift
/// var borderConfiguration = DefinedViewBorderConfiguration(inactive: true)
/// ```
///
/// otherwise, you can set the border setup by using basic initializer
/// `init(default:loading:active:done:error:disabled:)`.
Expand All @@ -48,20 +52,18 @@ public protocol DefinedView : View {
/// Configurate all things related to overlay view.
///
/// If you do not want to constrain the view with an overlay, you can disable it:
///
/// var overlayConfiguration = DefinedViewOverlayConfiguration(inactive: true)
/// ``` swift
/// var overlayConfiguration = DefinedViewOverlayConfiguration(inactive: true)
/// ```
///
/// otherwise, you can set the default overlay views by using basic initializer
/// `init(default:loading:active:done:error:disabled:)`.
///
/// - Note: This is only a configuration for the root view, not for the hierarchy level.
var overlayConfiguration: DefinedViewOverlayConfiguration { get set }

///
/// The status of an UI component.
var status: GeneralStatus { get set }

// TODO: It seems like having some problem on using `$` prefix on Swift 5.5
// var $status: Binding<GeneralStatus> { get set }
}

// MARK: - Extensions for fields
Expand All @@ -72,8 +74,9 @@ extension DefinedView {
get {
DefinedViewConfiguration(inactive: true)
}
set(value) {
self.viewConfiguration = value
set {
// WARNING: should not be assigned without defining it locally!
DefinedWarning.send(from: "DefinedViewProtocol", "You should NOT do things with viewConfiguration if you did not define it locally. Nothing is going to be changed if you proceed.")
}
}

Expand All @@ -82,8 +85,9 @@ extension DefinedView {
get {
DefinedViewBackgroundConfiguration(inactive: true)
}
set(value) {
self.backgroundConfiguration = value
set {
// WARNING: should not be assigned without defining it locally!
DefinedWarning.send(from: "DefinedViewProtocol", "You should NOT do things with backgroundConfiguration if you did not define it locally. Nothing is going to be changed if you proceed.")
}
}

Expand All @@ -92,8 +96,9 @@ extension DefinedView {
get {
DefinedViewBorderConfiguration(inactive: true)
}
set(value) {
self.borderConfiguration = value
set {
// WARNING: should not be assigned without defining it locally!
DefinedWarning.send(from: "DefinedViewProtocol", "You should NOT do things with borderConfiguration if you did not define it locally. Nothing is going to be changed if you proceed.")
}
}

Expand All @@ -102,8 +107,9 @@ extension DefinedView {
get {
DefinedViewOverlayConfiguration(inactive: true)
}
set(value) {
self.overlayConfiguration = value
set {
// WARNING: should not be assigned without defining it locally!
DefinedWarning.send(from: "DefinedViewProtocol", "You should NOT do things with overlayConfiguration if you did not define it locally. Nothing is going to be changed if you proceed.")
}
}

Expand All @@ -112,8 +118,9 @@ extension DefinedView {
get {
return .default
}
set(value) {
self.status = value
set {
// WARNING: should not be assigned without defining it locally!
DefinedWarning.send(from: "DefinedViewProtocol", "You should NOT do things with status if you did not define it locally. Nothing is going to be changed if you proceed.")
}
}
}
Loading