mirror of
https://github.com/apple/swift.git
synced 2025-12-14 20:36:38 +01:00
For every struct type for which the frameworks provides an NSValue category for boxing and unboxing values of that type, provide an _ObjectiveCBridgeable conformance in the Swift overlay that bridges that struct to NSValue, allowing the structs to be used naturally with id-as-Any APIs and Cocoa container classes. This is mostly a matter of gyb-ing out boilerplate using `NSValue.init(bytes:objCType:)` to construct the instance, `NSValue.objCType` to check its type when casting, and `NSValue.getValue(_:)` to extract the unboxed value, though there are a number of special snowflake cases that need special accommodation: - To maintain proper layering, CoreGraphics structs need to be bridged in the Foundation overlay. - AVFoundation provides the NSValue boxing categories for structs owned by CoreMedia, but it does so using its own internal subclasses of NSValue, and these subclasses do not interop properly with the standard `NSValue` subclasses instantiated by Foundation. To do the right thing, we therefore have to let AVFoundation provide the bridging implementation for the CoreMedia types, and we have to use its category methods to do so. - SceneKit provides NSValue categories to box and unbox SCNVector3, SCNVector4, and SCNMatrix4; however, the methods it provides do so in an unusual way. SCNVector3 and SCNVector4 are packaged into `CGRect`s and then the CGRect is boxed using `valueWithCGRect:`. SCNMatrix4 is copied into a CATransform3D, which is then boxed using `valueWithCATransform3D:` from CoreAnimation. To be consistent with what SceneKit does, use its category methods for these types as well, and when casting, check the type against the type encoding SceneKit uses rather than the type encoding of the expected type.
92 lines
3.4 KiB
Plaintext
92 lines
3.4 KiB
Plaintext
//===----------------------------------------------------------------------===//
|
|
//
|
|
// This source file is part of the Swift.org open source project
|
|
//
|
|
// Copyright (c) 2014 - 2016 Apple Inc. and the Swift project authors
|
|
// Licensed under Apache License v2.0 with Runtime Library Exception
|
|
//
|
|
// See http://swift.org/LICENSE.txt for license information
|
|
// See http://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
|
|
//
|
|
//===----------------------------------------------------------------------===//
|
|
|
|
import Foundation
|
|
@_exported import UIKit
|
|
|
|
%{
|
|
from gyb_foundation_support import ObjectiveCBridgeableImplementationForNSValue
|
|
}%
|
|
|
|
// UITableView extensions
|
|
public extension IndexPath {
|
|
|
|
/// Initialize for use with `UITableView` or `UICollectionView`.
|
|
public init(row: Int, section: Int) {
|
|
self.init(indexes: [section, row])
|
|
}
|
|
|
|
/// The section of this index path, when used with `UITableView`.
|
|
///
|
|
/// - precondition: The index path must have exactly two elements.
|
|
public var section: Int {
|
|
get {
|
|
precondition(count == 2, "Invalid index path for use with UITableView. This index path must contain exactly two indices specifying the section and row.")
|
|
return self[0]
|
|
}
|
|
set {
|
|
precondition(count == 2, "Invalid index path for use with UITableView. This index path must contain exactly two indices specifying the section and row.")
|
|
self[0] = newValue
|
|
}
|
|
}
|
|
|
|
/// The row of this index path, when used with `UITableView`.
|
|
///
|
|
/// - precondition: The index path must have exactly two elements.
|
|
public var row: Int {
|
|
get {
|
|
precondition(count == 2, "Invalid index path for use with UITableView. This index path must contain exactly two indices specifying the section and row.")
|
|
return self[1]
|
|
}
|
|
set {
|
|
precondition(count == 2, "Invalid index path for use with UITableView. This index path must contain exactly two indices specifying the section and row.")
|
|
self[1] = newValue
|
|
}
|
|
}
|
|
}
|
|
|
|
// UICollectionView extensions
|
|
public extension IndexPath {
|
|
|
|
/// Initialize for use with `UITableView` or `UICollectionView`.
|
|
public init(item: Int, section: Int) {
|
|
self.init(indexes: [section, item])
|
|
}
|
|
|
|
/// The item of this index path, when used with `UICollectionView`.
|
|
///
|
|
/// - precondition: The index path must have exactly two elements.
|
|
public var item: Int {
|
|
get {
|
|
precondition(count == 2, "Invalid index path for use with UICollectionView. This index path must contain exactly two indices specifying the section and item.")
|
|
return self[1]
|
|
}
|
|
set {
|
|
precondition(count == 2, "Invalid index path for use with UICollectionView. This index path must contain exactly two indices specifying the section and item.")
|
|
self[1] = newValue
|
|
}
|
|
}}
|
|
|
|
public extension URLResourceValues {
|
|
|
|
/// Returns a dictionary of UIImage objects keyed by size.
|
|
@available(iOS 8.0, *)
|
|
public var thumbnailDictionary : [URLThumbnailSizeKey : UIImage]? {
|
|
return allValues[URLResourceKey.thumbnailDictionaryKey] as? [URLThumbnailSizeKey : UIImage]
|
|
}
|
|
}
|
|
|
|
// Bridge UIKit structs to NSValue.
|
|
|
|
${ ObjectiveCBridgeableImplementationForNSValue("UIEdgeInsets") }
|
|
${ ObjectiveCBridgeableImplementationForNSValue("UIOffset") }
|