Initial commit
@@ -0,0 +1,42 @@
|
||||
---
|
||||
name: Bug Report
|
||||
about: Create a bug report.
|
||||
---
|
||||
|
||||
## Checklist
|
||||
- [ ] This is not a Apple's bug.
|
||||
- [ ] Reviewed the README and documents.
|
||||
- [ ] Searched existing issues for ensure not duplicated.
|
||||
|
||||
## Expected Behavior
|
||||
<!--- Tell us what should happen -->
|
||||
|
||||
## Current Behavior
|
||||
<!--- Tell us what happens instead of the expected behavior -->
|
||||
|
||||
## Steps to Reproduce
|
||||
<!--- Provide a link to a live example, or an unambiguous set of steps to -->
|
||||
<!--- reproduce this bug. Include code to reproduce, if relevant -->
|
||||
1.
|
||||
2.
|
||||
3.
|
||||
4.
|
||||
|
||||
## Detailed Description (Include Screenshots)
|
||||
<!--- Provide a detailed description of the bug -->
|
||||
|
||||
## Reproducible Demo Project
|
||||
<!--- If you have, provide links of bug reproducible project that we can refer -->
|
||||
|
||||
## Environments
|
||||
- version:
|
||||
|
||||
- Swift version:
|
||||
|
||||
- iOS version:
|
||||
|
||||
- Xcode version:
|
||||
|
||||
- Devices/Simulators:
|
||||
|
||||
- CocoaPods/Carthage version:
|
||||
@@ -0,0 +1,18 @@
|
||||
---
|
||||
name: Feature Request
|
||||
about: Create a feature request.
|
||||
---
|
||||
|
||||
## Checklist
|
||||
- [ ] Reviewed the README and documents.
|
||||
- [ ] Searched existing issues for ensure not duplicated.
|
||||
|
||||
## Description
|
||||
<!--- Provide a detailed description of the feature you are proposing -->
|
||||
|
||||
## Motivation and Context
|
||||
<!--- Why is this feature required? What problem does it solve? -->
|
||||
<!--- If it fixes an open issue, please link to the issue here. -->
|
||||
|
||||
## Proposed Solution
|
||||
<!--- Describe the solution you proposing. -->
|
||||
@@ -0,0 +1,30 @@
|
||||
---
|
||||
name: Question
|
||||
about: Create a bug question.
|
||||
---
|
||||
|
||||
## Checklist
|
||||
- [ ] Reviewed the README and documents.
|
||||
- [ ] Searched existing issues for ensure not duplicated.
|
||||
|
||||
## Expected Behavior
|
||||
<!--- Tell us what should happen -->
|
||||
|
||||
## Current Behavior
|
||||
<!--- Tell us what happens instead of the expected behavior -->
|
||||
|
||||
## Detailed Description (Include Screenshots)
|
||||
<!--- Provide a detailed description of your question -->
|
||||
|
||||
## Environment
|
||||
- version:
|
||||
|
||||
- Swift version:
|
||||
|
||||
- iOS version:
|
||||
|
||||
- Xcode version:
|
||||
|
||||
- Devices/Simulators:
|
||||
|
||||
- CocoaPods/Carthage version:
|
||||
@@ -0,0 +1,23 @@
|
||||
## Checklist
|
||||
- [ ] All tests are passed.
|
||||
- [ ] Added tests.
|
||||
- [ ] Documented the code using [Xcode markup](https://developer.apple.com/library/mac/documentation/Xcode/Reference/xcode_markup_formatting_ref).
|
||||
- [ ] Searched existing pull requests for ensure not duplicated.
|
||||
|
||||
## Description
|
||||
<!--- Describe your changes in detail -->
|
||||
|
||||
## Related Issue
|
||||
<!--- This project only accepts pull requests related to open issues -->
|
||||
<!--- If suggesting a new feature or change, please discuss it in an issue first -->
|
||||
<!--- If fixing a bug, there should be an issue describing it with steps to reproduce -->
|
||||
<!--- Please link to the issue here: -->
|
||||
|
||||
## Motivation and Context
|
||||
<!--- Why is this change required? What problem does it solve? -->
|
||||
<!--- If it fixes an open issue, please link to the issue here. -->
|
||||
|
||||
## Impact on Existing Code
|
||||
<!--- Tell us the impact on existing code as far as you understand. -->
|
||||
|
||||
## Screenshots (if appropriate)
|
||||
@@ -0,0 +1,38 @@
|
||||
.DS_Store
|
||||
*/build/*
|
||||
*.pbxuser
|
||||
!default.pbxuser
|
||||
*.mode1v3
|
||||
!default.mode1v3
|
||||
*.mode2v3
|
||||
!default.mode2v3
|
||||
*.perspectivev3
|
||||
!default.perspectivev3
|
||||
xcuserdata
|
||||
xcbaselines
|
||||
profile
|
||||
*.moved-aside
|
||||
DerivedData
|
||||
.idea/
|
||||
*.hmap
|
||||
*.xccheckout
|
||||
*.xcuserstate
|
||||
build/
|
||||
|
||||
## Documentation
|
||||
docs/docsets/
|
||||
docs/undocumented.json
|
||||
|
||||
## Gems
|
||||
.bundle
|
||||
vendor
|
||||
|
||||
## CocoaPods
|
||||
Pods
|
||||
|
||||
## Carthage
|
||||
Carthage/*
|
||||
!Carthage/Checkouts
|
||||
|
||||
## Swift Package Manager
|
||||
.build
|
||||
@@ -0,0 +1,3 @@
|
||||
[submodule "Carthage/Checkouts/DifferenceKit"]
|
||||
path = Carthage/Checkouts/DifferenceKit
|
||||
url = https://github.com/ra1028/DifferenceKit.git
|
||||
@@ -0,0 +1,30 @@
|
||||
# https://github.com/realm/jazzy
|
||||
|
||||
author: Ryo Aoyama
|
||||
author_url: https://github.com/ra1028
|
||||
github_url: https://github.com/ra1028/DiffableDataSources
|
||||
module: DiffableDataSources
|
||||
readme: README.md
|
||||
output: docs
|
||||
theme: fullwidth
|
||||
clean: true
|
||||
skip_undocumented: true
|
||||
xcodebuild_arguments:
|
||||
- -workspace
|
||||
- DiffableDataSources.xcworkspace
|
||||
- -scheme
|
||||
- DiffableDataSources
|
||||
- -sdk
|
||||
- iphonesimulator
|
||||
|
||||
exclude:
|
||||
- Sources/AppKit/CocoaCollectionViewDiffableDataSource.swift
|
||||
|
||||
custom_categories:
|
||||
- name: DataSources
|
||||
children:
|
||||
- TableViewDiffableDataSource
|
||||
- CollectionViewDiffableDataSource
|
||||
- name: Snapshot
|
||||
children:
|
||||
- DiffableDataSourceSnapshot
|
||||
@@ -0,0 +1 @@
|
||||
5.0
|
||||
@@ -0,0 +1,34 @@
|
||||
# https://github.com/realm/SwiftLint
|
||||
|
||||
excluded:
|
||||
- .build
|
||||
- Carthage
|
||||
- Examples
|
||||
|
||||
disabled_rules:
|
||||
- type_name
|
||||
- identifier_name
|
||||
- generic_type_name
|
||||
- force_cast
|
||||
|
||||
nesting:
|
||||
type_level:
|
||||
warning: 2
|
||||
|
||||
line_length:
|
||||
warning: 200
|
||||
|
||||
file_length:
|
||||
warning: 600
|
||||
|
||||
type_body_length:
|
||||
warning: 400
|
||||
|
||||
function_body_length:
|
||||
warning: 50
|
||||
|
||||
cyclomatic_complexity:
|
||||
warning: 12
|
||||
|
||||
statement_position:
|
||||
statement_mode: uncuddled_else
|
||||
@@ -0,0 +1,76 @@
|
||||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
In the interest of fostering an open and welcoming environment, we as
|
||||
contributors and maintainers pledge to making participation in our project and
|
||||
our community a harassment-free experience for everyone, regardless of age, body
|
||||
size, disability, ethnicity, sex characteristics, gender identity and expression,
|
||||
level of experience, education, socio-economic status, nationality, personal
|
||||
appearance, race, religion, or sexual identity and orientation.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to creating a positive environment
|
||||
include:
|
||||
|
||||
* Using welcoming and inclusive language
|
||||
* Being respectful of differing viewpoints and experiences
|
||||
* Gracefully accepting constructive criticism
|
||||
* Focusing on what is best for the community
|
||||
* Showing empathy towards other community members
|
||||
|
||||
Examples of unacceptable behavior by participants include:
|
||||
|
||||
* The use of sexualized language or imagery and unwelcome sexual attention or
|
||||
advances
|
||||
* Trolling, insulting/derogatory comments, and personal or political attacks
|
||||
* Public or private harassment
|
||||
* Publishing others' private information, such as a physical or electronic
|
||||
address, without explicit permission
|
||||
* Other conduct which could reasonably be considered inappropriate in a
|
||||
professional setting
|
||||
|
||||
## Our Responsibilities
|
||||
|
||||
Project maintainers are responsible for clarifying the standards of acceptable
|
||||
behavior and are expected to take appropriate and fair corrective action in
|
||||
response to any instances of unacceptable behavior.
|
||||
|
||||
Project maintainers have the right and responsibility to remove, edit, or
|
||||
reject comments, commits, code, wiki edits, issues, and other contributions
|
||||
that are not aligned to this Code of Conduct, or to ban temporarily or
|
||||
permanently any contributor for other behaviors that they deem inappropriate,
|
||||
threatening, offensive, or harmful.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies both within project spaces and in public spaces
|
||||
when an individual is representing the project or its community. Examples of
|
||||
representing a project or community include using an official project e-mail
|
||||
address, posting via an official social media account, or acting as an appointed
|
||||
representative at an online or offline event. Representation of a project may be
|
||||
further defined and clarified by project maintainers.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||
reported by contacting the project team at [INSERT EMAIL ADDRESS]. All
|
||||
complaints will be reviewed and investigated and will result in a response that
|
||||
is deemed necessary and appropriate to the circumstances. The project team is
|
||||
obligated to maintain confidentiality with regard to the reporter of an incident.
|
||||
Further details of specific enforcement policies may be posted separately.
|
||||
|
||||
Project maintainers who do not follow or enforce the Code of Conduct in good
|
||||
faith may face temporary or permanent repercussions as determined by other
|
||||
members of the project's leadership.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
|
||||
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
||||
|
||||
For answers to common questions about this code of conduct, see
|
||||
https://www.contributor-covenant.org/faq
|
||||
@@ -0,0 +1,91 @@
|
||||
# 🎈 Contributing
|
||||
|
||||
First of all, thanks for your interest.
|
||||
|
||||
There are several ways to contribute to this project. We welcome contributions in all ways.
|
||||
We have made some contribution guidelines to smoothly incorporate your opinions and code into this project.
|
||||
|
||||
## 📝 Open Issue
|
||||
|
||||
When you found a bug or having a feature request, search for the issue from the existing issues and feel free to open the issue after making sure it isn't already reported.
|
||||
|
||||
In order to we understand your issue accurately, please include as much information as possible in the issue template.
|
||||
The screenshot are also big clue to understand the issue.
|
||||
|
||||
If you know exactly how to fix the bug you report or implement the feature you propose, please pull request instead of an issue.
|
||||
|
||||
## 🚀 Pull Request
|
||||
|
||||
We are waiting for a pull request to make this project more better with us.
|
||||
If you want to add a new feature, let's discuss about it first on issue.
|
||||
|
||||
### Lint
|
||||
|
||||
Please introduce [SwiftLint](https://github.com/realm/SwiftLint) into your environment before start writing the code.
|
||||
Xcode automatically runs lint in the build phase.
|
||||
|
||||
The code written according to lint should match our coding style, but for particular cases where style is unknown, refer to the existing code base.
|
||||
|
||||
### Test
|
||||
|
||||
The test will tells us the validity of your code.
|
||||
All codes entering the master must pass the all tests.
|
||||
If you change the code or add new features, you should add tests.
|
||||
|
||||
### Documentation
|
||||
|
||||
Please write the document using [Xcode markup](https://developer.apple.com/library/archive/documentation/Xcode/Reference/xcode_markup_formatting_ref/) to the code you added.
|
||||
Documentation template is inserted automatically by using Xcode shortcut **⌥⌘/**.
|
||||
Our document style is slightly different from the template. The example is below.
|
||||
|
||||
```swift
|
||||
/// The example class for documentation.
|
||||
final class Foo {
|
||||
/// A property value.
|
||||
let prop: Int
|
||||
|
||||
/// Create a new foo with a param.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - param: An Int value for prop.
|
||||
init(param: Int) {
|
||||
prop = param
|
||||
}
|
||||
|
||||
/// Returns a string value concatenating `param1` and `param2`.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - param1: An Int value for prefix.
|
||||
/// - param2: A String value for suffix.
|
||||
///
|
||||
/// - Returns: A string concatenating given params.
|
||||
func bar(param1: Int, param2: String) -> String {
|
||||
return "\(param1)" + param2
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## [Developer's Certificate of Origin 1.1](https://elinux.org/Developer_Certificate_Of_Origin)
|
||||
By making a contribution to this project, I certify that:
|
||||
|
||||
(a) The contribution was created in whole or in part by me and I
|
||||
have the right to submit it under the open source license
|
||||
indicated in the file; or
|
||||
|
||||
(b) The contribution is based upon previous work that, to the best
|
||||
of my knowledge, is covered under an appropriate open source
|
||||
license and I have the right under that license to submit that
|
||||
work with modifications, whether created in whole or in part
|
||||
by me, under the same open source license (unless I am
|
||||
permitted to submit under a different license), as indicated
|
||||
in the file; or
|
||||
|
||||
(c) The contribution was provided directly to me by some other
|
||||
person who certified (a), (b) or (c) and I have not modified
|
||||
it.
|
||||
|
||||
(d) I understand and agree that this project and the contribution
|
||||
are public and that a record of the contribution (including all
|
||||
personal information I submit with it, including my sign-off) is
|
||||
maintained indefinitely and may be redistributed consistent with
|
||||
this project or the open source license(s) involved.
|
||||
@@ -0,0 +1 @@
|
||||
github "ra1028/DifferenceKit" "1.1.3"
|
||||
@@ -0,0 +1,27 @@
|
||||
Pod::Spec.new do |spec|
|
||||
spec.name = 'DiffableDataSources'
|
||||
spec.version = '0.1.0'
|
||||
spec.author = { 'ra1028' => 'r.fe51028.r@gmail.com' }
|
||||
spec.homepage = 'https://github.com/ra1028/DiffableDataSources'
|
||||
spec.documentation_url = 'https://ra1028.github.io/DiffableDataSources'
|
||||
spec.summary = 'A library for backporting UITableView/UICollectionViewDiffableDataSource.'
|
||||
spec.source = { :git => 'https://github.com/ra1028/DiffableDataSources.git', :tag => spec.version.to_s }
|
||||
spec.license = { :type => 'Apache 2.0', :file => 'LICENSE' }
|
||||
spec.requires_arc = true
|
||||
spec.source_files = 'Sources/**/*.swift'
|
||||
spec.swift_versions = ["5.0", "5.1"]
|
||||
|
||||
differenekit_version = '~> 1.1'
|
||||
|
||||
spec.ios.dependency 'DifferenceKit/UIKitExtension', differenekit_version
|
||||
spec.tvos.dependency 'DifferenceKit/UIKitExtension', differenekit_version
|
||||
spec.osx.dependency 'DifferenceKit/AppKitExtension', differenekit_version
|
||||
|
||||
spec.ios.frameworks = 'UIKit'
|
||||
spec.tvos.frameworks = 'UIKit'
|
||||
spec.osx.frameworks = 'Appkit'
|
||||
|
||||
spec.ios.deployment_target = '9.0'
|
||||
spec.tvos.deployment_target = '9.0'
|
||||
spec.osx.deployment_target = '10.11'
|
||||
end
|
||||
@@ -0,0 +1,591 @@
|
||||
// !$*UTF8*$!
|
||||
{
|
||||
archiveVersion = 1;
|
||||
classes = {
|
||||
};
|
||||
objectVersion = 50;
|
||||
objects = {
|
||||
|
||||
/* Begin PBXBuildFile section */
|
||||
6B41587222B5210500183AA2 /* TableViewDiffableDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B41587122B5210500183AA2 /* TableViewDiffableDataSource.swift */; };
|
||||
6B46555C22B6BC81005202D1 /* HashableExtension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B46555B22B6BC81005202D1 /* HashableExtension.swift */; };
|
||||
6B46555E22B7F904005202D1 /* UniversalError.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B46555D22B7F904005202D1 /* UniversalError.swift */; };
|
||||
6B466B2222B969600035D72F /* CollectionViewDiffableDataSourceTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B466B2122B969600035D72F /* CollectionViewDiffableDataSourceTests.swift */; };
|
||||
6B466B2422B96A520035D72F /* CocoaCollectionViewDiffableDataSourceTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B466B2322B96A520035D72F /* CocoaCollectionViewDiffableDataSourceTests.swift */; };
|
||||
6BA3A78022B54DA400AD51ED /* CollectionViewDiffableDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A77F22B54DA400AD51ED /* CollectionViewDiffableDataSource.swift */; };
|
||||
6BA3A79422B5A35F00AD51ED /* DiffableDataSourceCore.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A79322B5A35F00AD51ED /* DiffableDataSourceCore.swift */; };
|
||||
6BA3A7B122B6A5CE00AD51ED /* CocoaCollectionViewDiffableDataSource.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A7B022B6A5CE00AD51ED /* CocoaCollectionViewDiffableDataSource.swift */; };
|
||||
6BA3A7B622B820DA00AD51ED /* TableViewDiffableDataSourceTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A7B522B820DA00AD51ED /* TableViewDiffableDataSourceTests.swift */; };
|
||||
6BA4F52922BC0768008D5117 /* MainThreadSerialDispatcher.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA4F52822BC0768008D5117 /* MainThreadSerialDispatcher.swift */; };
|
||||
6BA4F52B22BC0AF3008D5117 /* MainThreadSerialDispatcherTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA4F52A22BC0AF3008D5117 /* MainThreadSerialDispatcherTests.swift */; };
|
||||
6BB762D622B455170050DC03 /* DiffableDataSources.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BB762CC22B455170050DC03 /* DiffableDataSources.framework */; };
|
||||
6BB762EB22B455520050DC03 /* SnapshotStructure.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BB762E822B455520050DC03 /* SnapshotStructure.swift */; };
|
||||
6BB762EC22B455520050DC03 /* DiffableDataSourceSnapshot.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BB762E922B455520050DC03 /* DiffableDataSourceSnapshot.swift */; };
|
||||
6BB762F122B455590050DC03 /* DiffableDataSourceTests.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BB762EF22B455590050DC03 /* DiffableDataSourceTests.swift */; };
|
||||
6BB762F722B53C1C0050DC03 /* DifferenceKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BB762F622B53C1C0050DC03 /* DifferenceKit.framework */; };
|
||||
/* End PBXBuildFile section */
|
||||
|
||||
/* Begin PBXContainerItemProxy section */
|
||||
6BB762D722B455170050DC03 /* PBXContainerItemProxy */ = {
|
||||
isa = PBXContainerItemProxy;
|
||||
containerPortal = 6BB762C322B455170050DC03 /* Project object */;
|
||||
proxyType = 1;
|
||||
remoteGlobalIDString = 6BB762CB22B455170050DC03;
|
||||
remoteInfo = DiffableDataSources;
|
||||
};
|
||||
/* End PBXContainerItemProxy section */
|
||||
|
||||
/* Begin PBXFileReference section */
|
||||
6B41587122B5210500183AA2 /* TableViewDiffableDataSource.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TableViewDiffableDataSource.swift; sourceTree = "<group>"; };
|
||||
6B46555B22B6BC81005202D1 /* HashableExtension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = HashableExtension.swift; sourceTree = "<group>"; };
|
||||
6B46555D22B7F904005202D1 /* UniversalError.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = UniversalError.swift; sourceTree = "<group>"; };
|
||||
6B466B2122B969600035D72F /* CollectionViewDiffableDataSourceTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollectionViewDiffableDataSourceTests.swift; sourceTree = "<group>"; };
|
||||
6B466B2322B96A520035D72F /* CocoaCollectionViewDiffableDataSourceTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CocoaCollectionViewDiffableDataSourceTests.swift; sourceTree = "<group>"; };
|
||||
6BA3A77F22B54DA400AD51ED /* CollectionViewDiffableDataSource.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CollectionViewDiffableDataSource.swift; sourceTree = "<group>"; };
|
||||
6BA3A79322B5A35F00AD51ED /* DiffableDataSourceCore.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = DiffableDataSourceCore.swift; sourceTree = "<group>"; };
|
||||
6BA3A7B022B6A5CE00AD51ED /* CocoaCollectionViewDiffableDataSource.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CocoaCollectionViewDiffableDataSource.swift; sourceTree = "<group>"; };
|
||||
6BA3A7B522B820DA00AD51ED /* TableViewDiffableDataSourceTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TableViewDiffableDataSourceTests.swift; sourceTree = "<group>"; };
|
||||
6BA4F52822BC0768008D5117 /* MainThreadSerialDispatcher.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainThreadSerialDispatcher.swift; sourceTree = "<group>"; };
|
||||
6BA4F52A22BC0AF3008D5117 /* MainThreadSerialDispatcherTests.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainThreadSerialDispatcherTests.swift; sourceTree = "<group>"; };
|
||||
6BB762CC22B455170050DC03 /* DiffableDataSources.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = DiffableDataSources.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BB762D522B455170050DC03 /* Tests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = Tests.xctest; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BB762E822B455520050DC03 /* SnapshotStructure.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SnapshotStructure.swift; sourceTree = "<group>"; };
|
||||
6BB762E922B455520050DC03 /* DiffableDataSourceSnapshot.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DiffableDataSourceSnapshot.swift; sourceTree = "<group>"; };
|
||||
6BB762EA22B455520050DC03 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
6BB762EF22B455590050DC03 /* DiffableDataSourceTests.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DiffableDataSourceTests.swift; sourceTree = "<group>"; };
|
||||
6BB762F022B455590050DC03 /* Info.plist */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */ = {isa = PBXFileReference; lastKnownFileType = text.xcconfig; path = DiffableDataSources.xcconfig; sourceTree = "<group>"; };
|
||||
6BB762F622B53C1C0050DC03 /* DifferenceKit.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; path = DifferenceKit.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
/* Begin PBXFrameworksBuildPhase section */
|
||||
6BB762C922B455170050DC03 /* Frameworks */ = {
|
||||
isa = PBXFrameworksBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BB762F722B53C1C0050DC03 /* DifferenceKit.framework in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB762D222B455170050DC03 /* Frameworks */ = {
|
||||
isa = PBXFrameworksBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BB762D622B455170050DC03 /* DiffableDataSources.framework in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXFrameworksBuildPhase section */
|
||||
|
||||
/* Begin PBXGroup section */
|
||||
6B41587322B52BC100183AA2 /* UIKit */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6B41587122B5210500183AA2 /* TableViewDiffableDataSource.swift */,
|
||||
6BA3A77F22B54DA400AD51ED /* CollectionViewDiffableDataSource.swift */,
|
||||
);
|
||||
path = UIKit;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BA3A7AF22B6A5A200AD51ED /* AppKit */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BA3A7B022B6A5CE00AD51ED /* CocoaCollectionViewDiffableDataSource.swift */,
|
||||
);
|
||||
path = AppKit;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762C222B455170050DC03 = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762E622B455520050DC03 /* Sources */,
|
||||
6BB762EE22B455590050DC03 /* Tests */,
|
||||
6BB762F322B455610050DC03 /* XCConfigs */,
|
||||
6BB762CD22B455170050DC03 /* Products */,
|
||||
6BB762F522B53C1C0050DC03 /* Frameworks */,
|
||||
);
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762CD22B455170050DC03 /* Products */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762CC22B455170050DC03 /* DiffableDataSources.framework */,
|
||||
6BB762D522B455170050DC03 /* Tests.xctest */,
|
||||
);
|
||||
name = Products;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762E622B455520050DC03 /* Sources */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762E922B455520050DC03 /* DiffableDataSourceSnapshot.swift */,
|
||||
6B41587322B52BC100183AA2 /* UIKit */,
|
||||
6BA3A7AF22B6A5A200AD51ED /* AppKit */,
|
||||
6BB762E722B455520050DC03 /* Internal */,
|
||||
6BB762EA22B455520050DC03 /* Info.plist */,
|
||||
);
|
||||
path = Sources;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762E722B455520050DC03 /* Internal */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BA3A79322B5A35F00AD51ED /* DiffableDataSourceCore.swift */,
|
||||
6BB762E822B455520050DC03 /* SnapshotStructure.swift */,
|
||||
6BA4F52822BC0768008D5117 /* MainThreadSerialDispatcher.swift */,
|
||||
6B46555B22B6BC81005202D1 /* HashableExtension.swift */,
|
||||
6B46555D22B7F904005202D1 /* UniversalError.swift */,
|
||||
);
|
||||
path = Internal;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762EE22B455590050DC03 /* Tests */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762EF22B455590050DC03 /* DiffableDataSourceTests.swift */,
|
||||
6BA3A7B522B820DA00AD51ED /* TableViewDiffableDataSourceTests.swift */,
|
||||
6B466B2122B969600035D72F /* CollectionViewDiffableDataSourceTests.swift */,
|
||||
6B466B2322B96A520035D72F /* CocoaCollectionViewDiffableDataSourceTests.swift */,
|
||||
6BA4F52A22BC0AF3008D5117 /* MainThreadSerialDispatcherTests.swift */,
|
||||
6BB762F022B455590050DC03 /* Info.plist */,
|
||||
);
|
||||
path = Tests;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762F322B455610050DC03 /* XCConfigs */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */,
|
||||
);
|
||||
path = XCConfigs;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762F522B53C1C0050DC03 /* Frameworks */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB762F622B53C1C0050DC03 /* DifferenceKit.framework */,
|
||||
);
|
||||
name = Frameworks;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXGroup section */
|
||||
|
||||
/* Begin PBXHeadersBuildPhase section */
|
||||
6BB762C722B455170050DC03 /* Headers */ = {
|
||||
isa = PBXHeadersBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXHeadersBuildPhase section */
|
||||
|
||||
/* Begin PBXNativeTarget section */
|
||||
6BB762CB22B455170050DC03 /* DiffableDataSources */ = {
|
||||
isa = PBXNativeTarget;
|
||||
buildConfigurationList = 6BB762E022B455170050DC03 /* Build configuration list for PBXNativeTarget "DiffableDataSources" */;
|
||||
buildPhases = (
|
||||
6BB762C722B455170050DC03 /* Headers */,
|
||||
6BB762C822B455170050DC03 /* Sources */,
|
||||
6BB762C922B455170050DC03 /* Frameworks */,
|
||||
6BB762CA22B455170050DC03 /* Resources */,
|
||||
6BA3A7B222B6C94100AD51ED /* SwiftLint */,
|
||||
);
|
||||
buildRules = (
|
||||
);
|
||||
dependencies = (
|
||||
);
|
||||
name = DiffableDataSources;
|
||||
productName = DiffableDataSources;
|
||||
productReference = 6BB762CC22B455170050DC03 /* DiffableDataSources.framework */;
|
||||
productType = "com.apple.product-type.framework";
|
||||
};
|
||||
6BB762D422B455170050DC03 /* Tests */ = {
|
||||
isa = PBXNativeTarget;
|
||||
buildConfigurationList = 6BB762E322B455170050DC03 /* Build configuration list for PBXNativeTarget "Tests" */;
|
||||
buildPhases = (
|
||||
6BB762D122B455170050DC03 /* Sources */,
|
||||
6BB762D222B455170050DC03 /* Frameworks */,
|
||||
6BB762D322B455170050DC03 /* Resources */,
|
||||
);
|
||||
buildRules = (
|
||||
);
|
||||
dependencies = (
|
||||
6BB762D822B455170050DC03 /* PBXTargetDependency */,
|
||||
);
|
||||
name = Tests;
|
||||
productName = DiffableDataSourcesTests;
|
||||
productReference = 6BB762D522B455170050DC03 /* Tests.xctest */;
|
||||
productType = "com.apple.product-type.bundle.unit-test";
|
||||
};
|
||||
/* End PBXNativeTarget section */
|
||||
|
||||
/* Begin PBXProject section */
|
||||
6BB762C322B455170050DC03 /* Project object */ = {
|
||||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastSwiftUpdateCheck = 1020;
|
||||
LastUpgradeCheck = 1020;
|
||||
ORGANIZATIONNAME = "Ryo Aoyama";
|
||||
TargetAttributes = {
|
||||
6BB762CB22B455170050DC03 = {
|
||||
CreatedOnToolsVersion = 10.2.1;
|
||||
};
|
||||
6BB762D422B455170050DC03 = {
|
||||
CreatedOnToolsVersion = 10.2.1;
|
||||
};
|
||||
};
|
||||
};
|
||||
buildConfigurationList = 6BB762C622B455170050DC03 /* Build configuration list for PBXProject "DiffableDataSources" */;
|
||||
compatibilityVersion = "Xcode 9.3";
|
||||
developmentRegion = en;
|
||||
hasScannedForEncodings = 0;
|
||||
knownRegions = (
|
||||
en,
|
||||
Base,
|
||||
);
|
||||
mainGroup = 6BB762C222B455170050DC03;
|
||||
productRefGroup = 6BB762CD22B455170050DC03 /* Products */;
|
||||
projectDirPath = "";
|
||||
projectRoot = "";
|
||||
targets = (
|
||||
6BB762CB22B455170050DC03 /* DiffableDataSources */,
|
||||
6BB762D422B455170050DC03 /* Tests */,
|
||||
);
|
||||
};
|
||||
/* End PBXProject section */
|
||||
|
||||
/* Begin PBXResourcesBuildPhase section */
|
||||
6BB762CA22B455170050DC03 /* Resources */ = {
|
||||
isa = PBXResourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB762D322B455170050DC03 /* Resources */ = {
|
||||
isa = PBXResourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXResourcesBuildPhase section */
|
||||
|
||||
/* Begin PBXShellScriptBuildPhase section */
|
||||
6BA3A7B222B6C94100AD51ED /* SwiftLint */ = {
|
||||
isa = PBXShellScriptBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
);
|
||||
inputFileListPaths = (
|
||||
);
|
||||
inputPaths = (
|
||||
);
|
||||
name = SwiftLint;
|
||||
outputFileListPaths = (
|
||||
);
|
||||
outputPaths = (
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
shellPath = /bin/sh;
|
||||
shellScript = "if which swiftlint >/dev/null; then\nswiftlint --config .swiftlint.yml\nelse\necho \"warning: SwiftLint not installed, download from https://github.com/realm/SwiftLint\"\nfi\n";
|
||||
};
|
||||
/* End PBXShellScriptBuildPhase section */
|
||||
|
||||
/* Begin PBXSourcesBuildPhase section */
|
||||
6BB762C822B455170050DC03 /* Sources */ = {
|
||||
isa = PBXSourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA4F52922BC0768008D5117 /* MainThreadSerialDispatcher.swift in Sources */,
|
||||
6B41587222B5210500183AA2 /* TableViewDiffableDataSource.swift in Sources */,
|
||||
6BA3A78022B54DA400AD51ED /* CollectionViewDiffableDataSource.swift in Sources */,
|
||||
6BB762EC22B455520050DC03 /* DiffableDataSourceSnapshot.swift in Sources */,
|
||||
6B46555E22B7F904005202D1 /* UniversalError.swift in Sources */,
|
||||
6BA3A7B122B6A5CE00AD51ED /* CocoaCollectionViewDiffableDataSource.swift in Sources */,
|
||||
6BB762EB22B455520050DC03 /* SnapshotStructure.swift in Sources */,
|
||||
6BA3A79422B5A35F00AD51ED /* DiffableDataSourceCore.swift in Sources */,
|
||||
6B46555C22B6BC81005202D1 /* HashableExtension.swift in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB762D122B455170050DC03 /* Sources */ = {
|
||||
isa = PBXSourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA4F52B22BC0AF3008D5117 /* MainThreadSerialDispatcherTests.swift in Sources */,
|
||||
6BA3A7B622B820DA00AD51ED /* TableViewDiffableDataSourceTests.swift in Sources */,
|
||||
6BB762F122B455590050DC03 /* DiffableDataSourceTests.swift in Sources */,
|
||||
6B466B2422B96A520035D72F /* CocoaCollectionViewDiffableDataSourceTests.swift in Sources */,
|
||||
6B466B2222B969600035D72F /* CollectionViewDiffableDataSourceTests.swift in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXSourcesBuildPhase section */
|
||||
|
||||
/* Begin PBXTargetDependency section */
|
||||
6BB762D822B455170050DC03 /* PBXTargetDependency */ = {
|
||||
isa = PBXTargetDependency;
|
||||
target = 6BB762CB22B455170050DC03 /* DiffableDataSources */;
|
||||
targetProxy = 6BB762D722B455170050DC03 /* PBXContainerItemProxy */;
|
||||
};
|
||||
/* End PBXTargetDependency section */
|
||||
|
||||
/* Begin XCBuildConfiguration section */
|
||||
6BB762DE22B455170050DC03 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_ENABLE_OBJC_WEAK = YES;
|
||||
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_COMMA = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
|
||||
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
|
||||
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
|
||||
CLANG_WARN_EMPTY_BODY = YES;
|
||||
CLANG_WARN_ENUM_CONVERSION = YES;
|
||||
CLANG_WARN_INFINITE_RECURSION = YES;
|
||||
CLANG_WARN_INT_CONVERSION = YES;
|
||||
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
|
||||
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
|
||||
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
|
||||
CLANG_WARN_STRICT_PROTOTYPES = YES;
|
||||
CLANG_WARN_SUSPICIOUS_MOVE = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CLANG_WARN_UNREACHABLE_CODE = YES;
|
||||
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
COPY_PHASE_STRIP = NO;
|
||||
CURRENT_PROJECT_VERSION = 1;
|
||||
DEBUG_INFORMATION_FORMAT = dwarf;
|
||||
ENABLE_STRICT_OBJC_MSGSEND = YES;
|
||||
ENABLE_TESTABILITY = YES;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GCC_DYNAMIC_NO_PIC = NO;
|
||||
GCC_NO_COMMON_BLOCKS = YES;
|
||||
GCC_OPTIMIZATION_LEVEL = 0;
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"DEBUG=1",
|
||||
"$(inherited)",
|
||||
);
|
||||
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
|
||||
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
|
||||
GCC_WARN_UNDECLARED_SELECTOR = YES;
|
||||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.2;
|
||||
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
|
||||
MTL_FAST_MATH = YES;
|
||||
ONLY_ACTIVE_ARCH = YES;
|
||||
SDKROOT = iphoneos;
|
||||
SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
VERSIONING_SYSTEM = "apple-generic";
|
||||
VERSION_INFO_PREFIX = "";
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BB762DF22B455170050DC03 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_ENABLE_OBJC_WEAK = YES;
|
||||
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_COMMA = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
|
||||
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
|
||||
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
|
||||
CLANG_WARN_EMPTY_BODY = YES;
|
||||
CLANG_WARN_ENUM_CONVERSION = YES;
|
||||
CLANG_WARN_INFINITE_RECURSION = YES;
|
||||
CLANG_WARN_INT_CONVERSION = YES;
|
||||
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
|
||||
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
|
||||
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
|
||||
CLANG_WARN_STRICT_PROTOTYPES = YES;
|
||||
CLANG_WARN_SUSPICIOUS_MOVE = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CLANG_WARN_UNREACHABLE_CODE = YES;
|
||||
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
COPY_PHASE_STRIP = NO;
|
||||
CURRENT_PROJECT_VERSION = 1;
|
||||
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
|
||||
ENABLE_NS_ASSERTIONS = NO;
|
||||
ENABLE_STRICT_OBJC_MSGSEND = YES;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GCC_NO_COMMON_BLOCKS = YES;
|
||||
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
|
||||
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
|
||||
GCC_WARN_UNDECLARED_SELECTOR = YES;
|
||||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.2;
|
||||
MTL_ENABLE_DEBUG_INFO = NO;
|
||||
MTL_FAST_MATH = YES;
|
||||
SDKROOT = iphoneos;
|
||||
SWIFT_COMPILATION_MODE = wholemodule;
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-O";
|
||||
VALIDATE_PRODUCT = YES;
|
||||
VERSIONING_SYSTEM = "apple-generic";
|
||||
VERSION_INFO_PREFIX = "";
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
6BB762E122B455170050DC03 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
APPLICATION_EXTENSION_API_ONLY = YES;
|
||||
CODE_SIGN_IDENTITY = "";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEFINES_MODULE = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
DYLIB_COMPATIBILITY_VERSION = 1;
|
||||
DYLIB_CURRENT_VERSION = 1;
|
||||
DYLIB_INSTALL_NAME_BASE = "@rpath";
|
||||
INFOPLIST_FILE = Sources/Info.plist;
|
||||
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
"@loader_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.ryo.DiffableDataSources;
|
||||
PRODUCT_NAME = "$(TARGET_NAME:c99extidentifier)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "1,2";
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BB762E222B455170050DC03 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
APPLICATION_EXTENSION_API_ONLY = YES;
|
||||
CODE_SIGN_IDENTITY = "";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEFINES_MODULE = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
DYLIB_COMPATIBILITY_VERSION = 1;
|
||||
DYLIB_CURRENT_VERSION = 1;
|
||||
DYLIB_INSTALL_NAME_BASE = "@rpath";
|
||||
INFOPLIST_FILE = Sources/Info.plist;
|
||||
INSTALL_PATH = "$(LOCAL_LIBRARY_DIR)/Frameworks";
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
"@loader_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.ryo.DiffableDataSources;
|
||||
PRODUCT_NAME = "$(TARGET_NAME:c99extidentifier)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SKIP_INSTALL = YES;
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "1,2";
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
6BB762E422B455170050DC03 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES;
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
INFOPLIST_FILE = Tests/Info.plist;
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
"@loader_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.ryo.DiffableDataSourcesTests;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "$(inherited)";
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BB762E522B455170050DC03 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
baseConfigurationReference = 6BB762F422B455610050DC03 /* DiffableDataSources.xcconfig */;
|
||||
buildSettings = {
|
||||
ALWAYS_EMBED_SWIFT_STANDARD_LIBRARIES = YES;
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
INFOPLIST_FILE = Tests/Info.plist;
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
"@loader_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = com.ryo.DiffableDataSourcesTests;
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "$(inherited)";
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
/* End XCBuildConfiguration section */
|
||||
|
||||
/* Begin XCConfigurationList section */
|
||||
6BB762C622B455170050DC03 /* Build configuration list for PBXProject "DiffableDataSources" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BB762DE22B455170050DC03 /* Debug */,
|
||||
6BB762DF22B455170050DC03 /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
6BB762E022B455170050DC03 /* Build configuration list for PBXNativeTarget "DiffableDataSources" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BB762E122B455170050DC03 /* Debug */,
|
||||
6BB762E222B455170050DC03 /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
6BB762E322B455170050DC03 /* Build configuration list for PBXNativeTarget "Tests" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BB762E422B455170050DC03 /* Debug */,
|
||||
6BB762E522B455170050DC03 /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
/* End XCConfigurationList section */
|
||||
};
|
||||
rootObject = 6BB762C322B455170050DC03 /* Project object */;
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "self:DiffableDataSources.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
||||
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,99 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762CB22B455170050DC03"
|
||||
BuildableName = "DiffableDataSources.framework"
|
||||
BlueprintName = "DiffableDataSources"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762D422B455170050DC03"
|
||||
BuildableName = "Tests.xctest"
|
||||
BlueprintName = "Tests"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762CB22B455170050DC03"
|
||||
BuildableName = "DiffableDataSources.framework"
|
||||
BlueprintName = "DiffableDataSources"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762CB22B455170050DC03"
|
||||
BuildableName = "DiffableDataSources.framework"
|
||||
BlueprintName = "DiffableDataSources"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762CB22B455170050DC03"
|
||||
BuildableName = "DiffableDataSources.framework"
|
||||
BlueprintName = "DiffableDataSources"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
||||
@@ -0,0 +1,56 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
<TestableReference
|
||||
skipped = "NO">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB762D422B455170050DC03"
|
||||
BuildableName = "Tests.xctest"
|
||||
BlueprintName = "Tests"
|
||||
ReferencedContainer = "container:DiffableDataSources.xcodeproj">
|
||||
</BuildableReference>
|
||||
</TestableReference>
|
||||
</Testables>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
||||
@@ -0,0 +1,10 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "group:DiffableDataSources.xcodeproj">
|
||||
</FileRef>
|
||||
<FileRef
|
||||
location = "group:Carthage/Checkouts/DifferenceKit/DifferenceKit.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
||||
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,573 @@
|
||||
// !$*UTF8*$!
|
||||
{
|
||||
archiveVersion = 1;
|
||||
classes = {
|
||||
};
|
||||
objectVersion = 50;
|
||||
objects = {
|
||||
|
||||
/* Begin PBXBuildFile section */
|
||||
6B02216222BA0EF500AEB14D /* InsertionSortViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B02216122BA0EF500AEB14D /* InsertionSortViewController.swift */; };
|
||||
6B02216422BA11D500AEB14D /* Extension.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B02216322BA11D500AEB14D /* Extension.swift */; };
|
||||
6B02216622BA177F00AEB14D /* InsertionSortViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 6B02216522BA177F00AEB14D /* InsertionSortViewController.xib */; };
|
||||
6B02216822BB7FA800AEB14D /* TopViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B02216722BB7FA800AEB14D /* TopViewController.swift */; };
|
||||
6B02216A22BB824600AEB14D /* TopViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 6B02216922BB824600AEB14D /* TopViewController.xib */; };
|
||||
6B46555622B6AB0C005202D1 /* MountainsRawData.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B46555522B6AB0C005202D1 /* MountainsRawData.swift */; };
|
||||
6B46555822B6AB15005202D1 /* MountainsRawData.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B46555722B6AB15005202D1 /* MountainsRawData.swift */; };
|
||||
6B46555A22B6AC83005202D1 /* LabelItem.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6B46555922B6AC83005202D1 /* LabelItem.swift */; };
|
||||
6BA3A78222B5515D00AD51ED /* LabelCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A78122B5515D00AD51ED /* LabelCell.swift */; };
|
||||
6BA3A78422B5516500AD51ED /* LabelCell.xib in Resources */ = {isa = PBXBuildFile; fileRef = 6BA3A78322B5516500AD51ED /* LabelCell.xib */; };
|
||||
6BA3A78822B5565E00AD51ED /* MountainsViewController.xib in Resources */ = {isa = PBXBuildFile; fileRef = 6BA3A78722B5565E00AD51ED /* MountainsViewController.xib */; };
|
||||
6BA3A78E22B55FB000AD51ED /* DiffableDataSources.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */; };
|
||||
6BA3A78F22B55FB000AD51ED /* DiffableDataSources.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
|
||||
6BA3A79022B55FB000AD51ED /* DifferenceKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */; };
|
||||
6BA3A79122B55FB000AD51ED /* DifferenceKit.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
|
||||
6BA3A79C22B69EDF00AD51ED /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A79B22B69EDF00AD51ED /* AppDelegate.swift */; };
|
||||
6BA3A79E22B69EDF00AD51ED /* MountainsViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BA3A79D22B69EDF00AD51ED /* MountainsViewController.swift */; };
|
||||
6BA3A7A022B69EE200AD51ED /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 6BA3A79F22B69EE200AD51ED /* Assets.xcassets */; };
|
||||
6BA3A7A322B69EE200AD51ED /* Main.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 6BA3A7A122B69EE200AD51ED /* Main.storyboard */; };
|
||||
6BA3A7A922B6A04F00AD51ED /* DiffableDataSources.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */; };
|
||||
6BA3A7AA22B6A04F00AD51ED /* DiffableDataSources.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
|
||||
6BA3A7AB22B6A04F00AD51ED /* DifferenceKit.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */; };
|
||||
6BA3A7AC22B6A04F00AD51ED /* DifferenceKit.framework in Embed Frameworks */ = {isa = PBXBuildFile; fileRef = 6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */; settings = {ATTRIBUTES = (CodeSignOnCopy, RemoveHeadersOnCopy, ); }; };
|
||||
6BB7630722B545240050DC03 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BB7630622B545240050DC03 /* AppDelegate.swift */; };
|
||||
6BB7630922B545240050DC03 /* MountainsViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 6BB7630822B545240050DC03 /* MountainsViewController.swift */; };
|
||||
6BB7630E22B545260050DC03 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 6BB7630D22B545260050DC03 /* Assets.xcassets */; };
|
||||
6BB7631122B545260050DC03 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 6BB7630F22B545260050DC03 /* LaunchScreen.storyboard */; };
|
||||
/* End PBXBuildFile section */
|
||||
|
||||
/* Begin PBXCopyFilesBuildPhase section */
|
||||
6BA3A79222B55FB000AD51ED /* Embed Frameworks */ = {
|
||||
isa = PBXCopyFilesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
dstPath = "";
|
||||
dstSubfolderSpec = 10;
|
||||
files = (
|
||||
6BA3A79122B55FB000AD51ED /* DifferenceKit.framework in Embed Frameworks */,
|
||||
6BA3A78F22B55FB000AD51ED /* DiffableDataSources.framework in Embed Frameworks */,
|
||||
);
|
||||
name = "Embed Frameworks";
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BA3A7AD22B6A05000AD51ED /* Embed Frameworks */ = {
|
||||
isa = PBXCopyFilesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
dstPath = "";
|
||||
dstSubfolderSpec = 10;
|
||||
files = (
|
||||
6BA3A7AC22B6A04F00AD51ED /* DifferenceKit.framework in Embed Frameworks */,
|
||||
6BA3A7AA22B6A04F00AD51ED /* DiffableDataSources.framework in Embed Frameworks */,
|
||||
);
|
||||
name = "Embed Frameworks";
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXCopyFilesBuildPhase section */
|
||||
|
||||
/* Begin PBXFileReference section */
|
||||
6B02216122BA0EF500AEB14D /* InsertionSortViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = InsertionSortViewController.swift; sourceTree = "<group>"; };
|
||||
6B02216322BA11D500AEB14D /* Extension.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = Extension.swift; sourceTree = "<group>"; };
|
||||
6B02216522BA177F00AEB14D /* InsertionSortViewController.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = InsertionSortViewController.xib; sourceTree = "<group>"; };
|
||||
6B02216722BB7FA800AEB14D /* TopViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = TopViewController.swift; sourceTree = "<group>"; };
|
||||
6B02216922BB824600AEB14D /* TopViewController.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = TopViewController.xib; sourceTree = "<group>"; };
|
||||
6B46555522B6AB0C005202D1 /* MountainsRawData.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MountainsRawData.swift; sourceTree = SOURCE_ROOT; };
|
||||
6B46555722B6AB15005202D1 /* MountainsRawData.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = MountainsRawData.swift; sourceTree = SOURCE_ROOT; };
|
||||
6B46555922B6AC83005202D1 /* LabelItem.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LabelItem.swift; sourceTree = "<group>"; };
|
||||
6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; path = DiffableDataSources.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; path = DifferenceKit.framework; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BA3A78122B5515D00AD51ED /* LabelCell.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LabelCell.swift; sourceTree = "<group>"; };
|
||||
6BA3A78322B5516500AD51ED /* LabelCell.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = LabelCell.xib; sourceTree = "<group>"; };
|
||||
6BA3A78722B5565E00AD51ED /* MountainsViewController.xib */ = {isa = PBXFileReference; lastKnownFileType = file.xib; path = MountainsViewController.xib; sourceTree = "<group>"; };
|
||||
6BA3A79922B69EDF00AD51ED /* Example-macOS.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "Example-macOS.app"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BA3A79B22B69EDF00AD51ED /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
|
||||
6BA3A79D22B69EDF00AD51ED /* MountainsViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MountainsViewController.swift; sourceTree = "<group>"; };
|
||||
6BA3A79F22B69EE200AD51ED /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
|
||||
6BA3A7A222B69EE200AD51ED /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/Main.storyboard; sourceTree = "<group>"; };
|
||||
6BA3A7A422B69EE200AD51ED /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
6BA3A7A522B69EE200AD51ED /* Example_macOS.entitlements */ = {isa = PBXFileReference; lastKnownFileType = text.plist.entitlements; path = Example_macOS.entitlements; sourceTree = "<group>"; };
|
||||
6BB7630322B545240050DC03 /* Example-iOS.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = "Example-iOS.app"; sourceTree = BUILT_PRODUCTS_DIR; };
|
||||
6BB7630622B545240050DC03 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = "<group>"; };
|
||||
6BB7630822B545240050DC03 /* MountainsViewController.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MountainsViewController.swift; sourceTree = "<group>"; };
|
||||
6BB7630D22B545260050DC03 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = "<group>"; };
|
||||
6BB7631022B545260050DC03 /* Base */ = {isa = PBXFileReference; lastKnownFileType = file.storyboard; name = Base; path = Base.lproj/LaunchScreen.storyboard; sourceTree = "<group>"; };
|
||||
6BB7631222B545260050DC03 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = "<group>"; };
|
||||
/* End PBXFileReference section */
|
||||
|
||||
/* Begin PBXFrameworksBuildPhase section */
|
||||
6BA3A79622B69EDF00AD51ED /* Frameworks */ = {
|
||||
isa = PBXFrameworksBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA3A7AB22B6A04F00AD51ED /* DifferenceKit.framework in Frameworks */,
|
||||
6BA3A7A922B6A04F00AD51ED /* DiffableDataSources.framework in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB7630022B545240050DC03 /* Frameworks */ = {
|
||||
isa = PBXFrameworksBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA3A79022B55FB000AD51ED /* DifferenceKit.framework in Frameworks */,
|
||||
6BA3A78E22B55FB000AD51ED /* DiffableDataSources.framework in Frameworks */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXFrameworksBuildPhase section */
|
||||
|
||||
/* Begin PBXGroup section */
|
||||
6BA3A79A22B69EDF00AD51ED /* Example-macOS */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BA3A79D22B69EDF00AD51ED /* MountainsViewController.swift */,
|
||||
6B46555922B6AC83005202D1 /* LabelItem.swift */,
|
||||
6B46555722B6AB15005202D1 /* MountainsRawData.swift */,
|
||||
6BA3A79B22B69EDF00AD51ED /* AppDelegate.swift */,
|
||||
6BA3A7A122B69EE200AD51ED /* Main.storyboard */,
|
||||
6BA3A79F22B69EE200AD51ED /* Assets.xcassets */,
|
||||
6BA3A7A422B69EE200AD51ED /* Info.plist */,
|
||||
6BA3A7A522B69EE200AD51ED /* Example_macOS.entitlements */,
|
||||
);
|
||||
path = "Example-macOS";
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB762FA22B545240050DC03 = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB7630522B545240050DC03 /* Example-iOS */,
|
||||
6BA3A79A22B69EDF00AD51ED /* Example-macOS */,
|
||||
6BB7630422B545240050DC03 /* Products */,
|
||||
6BB7632122B5467B0050DC03 /* Frameworks */,
|
||||
);
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB7630422B545240050DC03 /* Products */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BB7630322B545240050DC03 /* Example-iOS.app */,
|
||||
6BA3A79922B69EDF00AD51ED /* Example-macOS.app */,
|
||||
);
|
||||
name = Products;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB7630522B545240050DC03 /* Example-iOS */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6B02216722BB7FA800AEB14D /* TopViewController.swift */,
|
||||
6B02216922BB824600AEB14D /* TopViewController.xib */,
|
||||
6BB7630822B545240050DC03 /* MountainsViewController.swift */,
|
||||
6BA3A78722B5565E00AD51ED /* MountainsViewController.xib */,
|
||||
6B02216122BA0EF500AEB14D /* InsertionSortViewController.swift */,
|
||||
6B02216522BA177F00AEB14D /* InsertionSortViewController.xib */,
|
||||
6BA3A78122B5515D00AD51ED /* LabelCell.swift */,
|
||||
6BA3A78322B5516500AD51ED /* LabelCell.xib */,
|
||||
6B02216322BA11D500AEB14D /* Extension.swift */,
|
||||
6B46555522B6AB0C005202D1 /* MountainsRawData.swift */,
|
||||
6BB7630622B545240050DC03 /* AppDelegate.swift */,
|
||||
6BB7630D22B545260050DC03 /* Assets.xcassets */,
|
||||
6BB7630F22B545260050DC03 /* LaunchScreen.storyboard */,
|
||||
6BB7631222B545260050DC03 /* Info.plist */,
|
||||
);
|
||||
path = "Example-iOS";
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB7632122B5467B0050DC03 /* Frameworks */ = {
|
||||
isa = PBXGroup;
|
||||
children = (
|
||||
6BA3A77B22B549B700AD51ED /* DiffableDataSources.framework */,
|
||||
6BA3A77D22B549B700AD51ED /* DifferenceKit.framework */,
|
||||
);
|
||||
name = Frameworks;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXGroup section */
|
||||
|
||||
/* Begin PBXNativeTarget section */
|
||||
6BA3A79822B69EDF00AD51ED /* Example-macOS */ = {
|
||||
isa = PBXNativeTarget;
|
||||
buildConfigurationList = 6BA3A7A822B69EE200AD51ED /* Build configuration list for PBXNativeTarget "Example-macOS" */;
|
||||
buildPhases = (
|
||||
6BA3A79522B69EDF00AD51ED /* Sources */,
|
||||
6BA3A79622B69EDF00AD51ED /* Frameworks */,
|
||||
6BA3A79722B69EDF00AD51ED /* Resources */,
|
||||
6BA3A7AD22B6A05000AD51ED /* Embed Frameworks */,
|
||||
);
|
||||
buildRules = (
|
||||
);
|
||||
dependencies = (
|
||||
);
|
||||
name = "Example-macOS";
|
||||
productName = "Example-macOS";
|
||||
productReference = 6BA3A79922B69EDF00AD51ED /* Example-macOS.app */;
|
||||
productType = "com.apple.product-type.application";
|
||||
};
|
||||
6BB7630222B545240050DC03 /* Example-iOS */ = {
|
||||
isa = PBXNativeTarget;
|
||||
buildConfigurationList = 6BB7631522B545260050DC03 /* Build configuration list for PBXNativeTarget "Example-iOS" */;
|
||||
buildPhases = (
|
||||
6BB762FF22B545240050DC03 /* Sources */,
|
||||
6BB7630022B545240050DC03 /* Frameworks */,
|
||||
6BB7630122B545240050DC03 /* Resources */,
|
||||
6BA3A79222B55FB000AD51ED /* Embed Frameworks */,
|
||||
);
|
||||
buildRules = (
|
||||
);
|
||||
dependencies = (
|
||||
);
|
||||
name = "Example-iOS";
|
||||
productName = "DiffableDataSourcesExample-iOS";
|
||||
productReference = 6BB7630322B545240050DC03 /* Example-iOS.app */;
|
||||
productType = "com.apple.product-type.application";
|
||||
};
|
||||
/* End PBXNativeTarget section */
|
||||
|
||||
/* Begin PBXProject section */
|
||||
6BB762FB22B545240050DC03 /* Project object */ = {
|
||||
isa = PBXProject;
|
||||
attributes = {
|
||||
LastSwiftUpdateCheck = 1020;
|
||||
LastUpgradeCheck = 1020;
|
||||
ORGANIZATIONNAME = "Ryo Aoyama";
|
||||
TargetAttributes = {
|
||||
6BA3A79822B69EDF00AD51ED = {
|
||||
CreatedOnToolsVersion = 10.2.1;
|
||||
};
|
||||
6BB7630222B545240050DC03 = {
|
||||
CreatedOnToolsVersion = 10.2.1;
|
||||
};
|
||||
};
|
||||
};
|
||||
buildConfigurationList = 6BB762FE22B545240050DC03 /* Build configuration list for PBXProject "DiffableDataSourcesExamples" */;
|
||||
compatibilityVersion = "Xcode 9.3";
|
||||
developmentRegion = en;
|
||||
hasScannedForEncodings = 0;
|
||||
knownRegions = (
|
||||
en,
|
||||
Base,
|
||||
);
|
||||
mainGroup = 6BB762FA22B545240050DC03;
|
||||
productRefGroup = 6BB7630422B545240050DC03 /* Products */;
|
||||
projectDirPath = "";
|
||||
projectRoot = "";
|
||||
targets = (
|
||||
6BB7630222B545240050DC03 /* Example-iOS */,
|
||||
6BA3A79822B69EDF00AD51ED /* Example-macOS */,
|
||||
);
|
||||
};
|
||||
/* End PBXProject section */
|
||||
|
||||
/* Begin PBXResourcesBuildPhase section */
|
||||
6BA3A79722B69EDF00AD51ED /* Resources */ = {
|
||||
isa = PBXResourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA3A7A022B69EE200AD51ED /* Assets.xcassets in Resources */,
|
||||
6BA3A7A322B69EE200AD51ED /* Main.storyboard in Resources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB7630122B545240050DC03 /* Resources */ = {
|
||||
isa = PBXResourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA3A78422B5516500AD51ED /* LabelCell.xib in Resources */,
|
||||
6B02216622BA177F00AEB14D /* InsertionSortViewController.xib in Resources */,
|
||||
6B02216A22BB824600AEB14D /* TopViewController.xib in Resources */,
|
||||
6BA3A78822B5565E00AD51ED /* MountainsViewController.xib in Resources */,
|
||||
6BB7631122B545260050DC03 /* LaunchScreen.storyboard in Resources */,
|
||||
6BB7630E22B545260050DC03 /* Assets.xcassets in Resources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXResourcesBuildPhase section */
|
||||
|
||||
/* Begin PBXSourcesBuildPhase section */
|
||||
6BA3A79522B69EDF00AD51ED /* Sources */ = {
|
||||
isa = PBXSourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BA3A79E22B69EDF00AD51ED /* MountainsViewController.swift in Sources */,
|
||||
6B46555A22B6AC83005202D1 /* LabelItem.swift in Sources */,
|
||||
6B46555822B6AB15005202D1 /* MountainsRawData.swift in Sources */,
|
||||
6BA3A79C22B69EDF00AD51ED /* AppDelegate.swift in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
6BB762FF22B545240050DC03 /* Sources */ = {
|
||||
isa = PBXSourcesBuildPhase;
|
||||
buildActionMask = 2147483647;
|
||||
files = (
|
||||
6BB7630922B545240050DC03 /* MountainsViewController.swift in Sources */,
|
||||
6BA3A78222B5515D00AD51ED /* LabelCell.swift in Sources */,
|
||||
6B02216422BA11D500AEB14D /* Extension.swift in Sources */,
|
||||
6B02216222BA0EF500AEB14D /* InsertionSortViewController.swift in Sources */,
|
||||
6BB7630722B545240050DC03 /* AppDelegate.swift in Sources */,
|
||||
6B46555622B6AB0C005202D1 /* MountainsRawData.swift in Sources */,
|
||||
6B02216822BB7FA800AEB14D /* TopViewController.swift in Sources */,
|
||||
);
|
||||
runOnlyForDeploymentPostprocessing = 0;
|
||||
};
|
||||
/* End PBXSourcesBuildPhase section */
|
||||
|
||||
/* Begin PBXVariantGroup section */
|
||||
6BA3A7A122B69EE200AD51ED /* Main.storyboard */ = {
|
||||
isa = PBXVariantGroup;
|
||||
children = (
|
||||
6BA3A7A222B69EE200AD51ED /* Base */,
|
||||
);
|
||||
name = Main.storyboard;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
6BB7630F22B545260050DC03 /* LaunchScreen.storyboard */ = {
|
||||
isa = PBXVariantGroup;
|
||||
children = (
|
||||
6BB7631022B545260050DC03 /* Base */,
|
||||
);
|
||||
name = LaunchScreen.storyboard;
|
||||
sourceTree = "<group>";
|
||||
};
|
||||
/* End PBXVariantGroup section */
|
||||
|
||||
/* Begin XCBuildConfiguration section */
|
||||
6BA3A7A622B69EE200AD51ED /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CODE_SIGN_ENTITLEMENTS = "Example-macOS/Example_macOS.entitlements";
|
||||
CODE_SIGN_IDENTITY = "-";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
INFOPLIST_FILE = "Example-macOS/Info.plist";
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/../Frameworks",
|
||||
);
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.13;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = "com.ryo.DiffableDataSourcesExample-macOS";
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SDKROOT = macosx;
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BA3A7A722B69EE200AD51ED /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CODE_SIGN_ENTITLEMENTS = "Example-macOS/Example_macOS.entitlements";
|
||||
CODE_SIGN_IDENTITY = "-";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
COMBINE_HIDPI_IMAGES = YES;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
INFOPLIST_FILE = "Example-macOS/Info.plist";
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/../Frameworks",
|
||||
);
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.13;
|
||||
PRODUCT_BUNDLE_IDENTIFIER = "com.ryo.DiffableDataSourcesExample-macOS";
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SDKROOT = macosx;
|
||||
SWIFT_VERSION = 5.0;
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
6BB7631322B545260050DC03 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_ENABLE_OBJC_WEAK = YES;
|
||||
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_COMMA = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
|
||||
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
|
||||
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
|
||||
CLANG_WARN_EMPTY_BODY = YES;
|
||||
CLANG_WARN_ENUM_CONVERSION = YES;
|
||||
CLANG_WARN_INFINITE_RECURSION = YES;
|
||||
CLANG_WARN_INT_CONVERSION = YES;
|
||||
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
|
||||
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
|
||||
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
|
||||
CLANG_WARN_STRICT_PROTOTYPES = YES;
|
||||
CLANG_WARN_SUSPICIOUS_MOVE = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CLANG_WARN_UNREACHABLE_CODE = YES;
|
||||
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
COPY_PHASE_STRIP = NO;
|
||||
DEBUG_INFORMATION_FORMAT = dwarf;
|
||||
ENABLE_STRICT_OBJC_MSGSEND = YES;
|
||||
ENABLE_TESTABILITY = YES;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GCC_DYNAMIC_NO_PIC = NO;
|
||||
GCC_NO_COMMON_BLOCKS = YES;
|
||||
GCC_OPTIMIZATION_LEVEL = 0;
|
||||
GCC_PREPROCESSOR_DEFINITIONS = (
|
||||
"DEBUG=1",
|
||||
"$(inherited)",
|
||||
);
|
||||
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
|
||||
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
|
||||
GCC_WARN_UNDECLARED_SELECTOR = YES;
|
||||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.13;
|
||||
MTL_ENABLE_DEBUG_INFO = INCLUDE_SOURCE;
|
||||
MTL_FAST_MATH = YES;
|
||||
ONLY_ACTIVE_ARCH = YES;
|
||||
SDKROOT = iphoneos;
|
||||
SWIFT_ACTIVE_COMPILATION_CONDITIONS = DEBUG;
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-Onone";
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BB7631422B545260050DC03 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ALWAYS_SEARCH_USER_PATHS = NO;
|
||||
CLANG_ANALYZER_NONNULL = YES;
|
||||
CLANG_ANALYZER_NUMBER_OBJECT_CONVERSION = YES_AGGRESSIVE;
|
||||
CLANG_CXX_LANGUAGE_STANDARD = "gnu++14";
|
||||
CLANG_CXX_LIBRARY = "libc++";
|
||||
CLANG_ENABLE_MODULES = YES;
|
||||
CLANG_ENABLE_OBJC_ARC = YES;
|
||||
CLANG_ENABLE_OBJC_WEAK = YES;
|
||||
CLANG_WARN_BLOCK_CAPTURE_AUTORELEASING = YES;
|
||||
CLANG_WARN_BOOL_CONVERSION = YES;
|
||||
CLANG_WARN_COMMA = YES;
|
||||
CLANG_WARN_CONSTANT_CONVERSION = YES;
|
||||
CLANG_WARN_DEPRECATED_OBJC_IMPLEMENTATIONS = YES;
|
||||
CLANG_WARN_DIRECT_OBJC_ISA_USAGE = YES_ERROR;
|
||||
CLANG_WARN_DOCUMENTATION_COMMENTS = YES;
|
||||
CLANG_WARN_EMPTY_BODY = YES;
|
||||
CLANG_WARN_ENUM_CONVERSION = YES;
|
||||
CLANG_WARN_INFINITE_RECURSION = YES;
|
||||
CLANG_WARN_INT_CONVERSION = YES;
|
||||
CLANG_WARN_NON_LITERAL_NULL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_IMPLICIT_RETAIN_SELF = YES;
|
||||
CLANG_WARN_OBJC_LITERAL_CONVERSION = YES;
|
||||
CLANG_WARN_OBJC_ROOT_CLASS = YES_ERROR;
|
||||
CLANG_WARN_RANGE_LOOP_ANALYSIS = YES;
|
||||
CLANG_WARN_STRICT_PROTOTYPES = YES;
|
||||
CLANG_WARN_SUSPICIOUS_MOVE = YES;
|
||||
CLANG_WARN_UNGUARDED_AVAILABILITY = YES_AGGRESSIVE;
|
||||
CLANG_WARN_UNREACHABLE_CODE = YES;
|
||||
CLANG_WARN__DUPLICATE_METHOD_MATCH = YES;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
COPY_PHASE_STRIP = NO;
|
||||
DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym";
|
||||
ENABLE_NS_ASSERTIONS = NO;
|
||||
ENABLE_STRICT_OBJC_MSGSEND = YES;
|
||||
GCC_C_LANGUAGE_STANDARD = gnu11;
|
||||
GCC_NO_COMMON_BLOCKS = YES;
|
||||
GCC_WARN_64_TO_32_BIT_CONVERSION = YES;
|
||||
GCC_WARN_ABOUT_RETURN_TYPE = YES_ERROR;
|
||||
GCC_WARN_UNDECLARED_SELECTOR = YES;
|
||||
GCC_WARN_UNINITIALIZED_AUTOS = YES_AGGRESSIVE;
|
||||
GCC_WARN_UNUSED_FUNCTION = YES;
|
||||
GCC_WARN_UNUSED_VARIABLE = YES;
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.13;
|
||||
MTL_ENABLE_DEBUG_INFO = NO;
|
||||
MTL_FAST_MATH = YES;
|
||||
SDKROOT = iphoneos;
|
||||
SWIFT_COMPILATION_MODE = wholemodule;
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-O";
|
||||
VALIDATE_PRODUCT = YES;
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
6BB7631622B545260050DC03 /* Debug */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
GCC_OPTIMIZATION_LEVEL = s;
|
||||
INFOPLIST_FILE = "Example-iOS/Info.plist";
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = "com.ryo.DiffableDataSourcesExample-iOS";
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SWIFT_OPTIMIZATION_LEVEL = "-O";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "1,2";
|
||||
TVOS_DEPLOYMENT_TARGET = "";
|
||||
};
|
||||
name = Debug;
|
||||
};
|
||||
6BB7631722B545260050DC03 /* Release */ = {
|
||||
isa = XCBuildConfiguration;
|
||||
buildSettings = {
|
||||
ASSETCATALOG_COMPILER_APPICON_NAME = AppIcon;
|
||||
CODE_SIGN_IDENTITY = "iPhone Developer";
|
||||
CODE_SIGN_STYLE = Manual;
|
||||
DEVELOPMENT_TEAM = "";
|
||||
INFOPLIST_FILE = "Example-iOS/Info.plist";
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 12.0;
|
||||
LD_RUNPATH_SEARCH_PATHS = (
|
||||
"$(inherited)",
|
||||
"@executable_path/Frameworks",
|
||||
);
|
||||
PRODUCT_BUNDLE_IDENTIFIER = "com.ryo.DiffableDataSourcesExample-iOS";
|
||||
PRODUCT_NAME = "$(TARGET_NAME)";
|
||||
PROVISIONING_PROFILE_SPECIFIER = "";
|
||||
SWIFT_VERSION = 5.0;
|
||||
TARGETED_DEVICE_FAMILY = "1,2";
|
||||
TVOS_DEPLOYMENT_TARGET = "";
|
||||
};
|
||||
name = Release;
|
||||
};
|
||||
/* End XCBuildConfiguration section */
|
||||
|
||||
/* Begin XCConfigurationList section */
|
||||
6BA3A7A822B69EE200AD51ED /* Build configuration list for PBXNativeTarget "Example-macOS" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BA3A7A622B69EE200AD51ED /* Debug */,
|
||||
6BA3A7A722B69EE200AD51ED /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
6BB762FE22B545240050DC03 /* Build configuration list for PBXProject "DiffableDataSourcesExamples" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BB7631322B545260050DC03 /* Debug */,
|
||||
6BB7631422B545260050DC03 /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
6BB7631522B545260050DC03 /* Build configuration list for PBXNativeTarget "Example-iOS" */ = {
|
||||
isa = XCConfigurationList;
|
||||
buildConfigurations = (
|
||||
6BB7631622B545260050DC03 /* Debug */,
|
||||
6BB7631722B545260050DC03 /* Release */,
|
||||
);
|
||||
defaultConfigurationIsVisible = 0;
|
||||
defaultConfigurationName = Release;
|
||||
};
|
||||
/* End XCConfigurationList section */
|
||||
};
|
||||
rootObject = 6BB762FB22B545240050DC03 /* Project object */;
|
||||
}
|
||||
@@ -0,0 +1,7 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "self:DiffableDataSourcesExample-iOS.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
||||
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,91 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Scheme
|
||||
LastUpgradeVersion = "1020"
|
||||
version = "1.3">
|
||||
<BuildAction
|
||||
parallelizeBuildables = "YES"
|
||||
buildImplicitDependencies = "YES">
|
||||
<BuildActionEntries>
|
||||
<BuildActionEntry
|
||||
buildForTesting = "YES"
|
||||
buildForRunning = "YES"
|
||||
buildForProfiling = "YES"
|
||||
buildForArchiving = "YES"
|
||||
buildForAnalyzing = "YES">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB7630222B545240050DC03"
|
||||
BuildableName = "Example-iOS.app"
|
||||
BlueprintName = "Example-iOS"
|
||||
ReferencedContainer = "container:DiffableDataSourcesExamples.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildActionEntry>
|
||||
</BuildActionEntries>
|
||||
</BuildAction>
|
||||
<TestAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES">
|
||||
<Testables>
|
||||
</Testables>
|
||||
<MacroExpansion>
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB7630222B545240050DC03"
|
||||
BuildableName = "Example-iOS.app"
|
||||
BlueprintName = "Example-iOS"
|
||||
ReferencedContainer = "container:DiffableDataSourcesExamples.xcodeproj">
|
||||
</BuildableReference>
|
||||
</MacroExpansion>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</TestAction>
|
||||
<LaunchAction
|
||||
buildConfiguration = "Debug"
|
||||
selectedDebuggerIdentifier = "Xcode.DebuggerFoundation.Debugger.LLDB"
|
||||
selectedLauncherIdentifier = "Xcode.DebuggerFoundation.Launcher.LLDB"
|
||||
launchStyle = "0"
|
||||
useCustomWorkingDirectory = "NO"
|
||||
ignoresPersistentStateOnLaunch = "NO"
|
||||
debugDocumentVersioning = "YES"
|
||||
debugServiceExtension = "internal"
|
||||
allowLocationSimulation = "YES">
|
||||
<BuildableProductRunnable
|
||||
runnableDebuggingMode = "0">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB7630222B545240050DC03"
|
||||
BuildableName = "Example-iOS.app"
|
||||
BlueprintName = "Example-iOS"
|
||||
ReferencedContainer = "container:DiffableDataSourcesExamples.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildableProductRunnable>
|
||||
<AdditionalOptions>
|
||||
</AdditionalOptions>
|
||||
</LaunchAction>
|
||||
<ProfileAction
|
||||
buildConfiguration = "Release"
|
||||
shouldUseLaunchSchemeArgsEnv = "YES"
|
||||
savedToolIdentifier = ""
|
||||
useCustomWorkingDirectory = "NO"
|
||||
debugDocumentVersioning = "YES">
|
||||
<BuildableProductRunnable
|
||||
runnableDebuggingMode = "0">
|
||||
<BuildableReference
|
||||
BuildableIdentifier = "primary"
|
||||
BlueprintIdentifier = "6BB7630222B545240050DC03"
|
||||
BuildableName = "Example-iOS.app"
|
||||
BlueprintName = "Example-iOS"
|
||||
ReferencedContainer = "container:DiffableDataSourcesExamples.xcodeproj">
|
||||
</BuildableReference>
|
||||
</BuildableProductRunnable>
|
||||
</ProfileAction>
|
||||
<AnalyzeAction
|
||||
buildConfiguration = "Debug">
|
||||
</AnalyzeAction>
|
||||
<ArchiveAction
|
||||
buildConfiguration = "Release"
|
||||
revealArchiveInOrganizer = "YES">
|
||||
</ArchiveAction>
|
||||
</Scheme>
|
||||
@@ -0,0 +1,13 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Workspace
|
||||
version = "1.0">
|
||||
<FileRef
|
||||
location = "group:DiffableDataSourcesExamples.xcodeproj">
|
||||
</FileRef>
|
||||
<FileRef
|
||||
location = "group:../DiffableDataSources.xcodeproj">
|
||||
</FileRef>
|
||||
<FileRef
|
||||
location = "group:../Carthage/Checkouts/DifferenceKit/DifferenceKit.xcodeproj">
|
||||
</FileRef>
|
||||
</Workspace>
|
||||
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>IDEDidComputeMac32BitWarning</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,17 @@
|
||||
import UIKit
|
||||
|
||||
@UIApplicationMain
|
||||
final class AppDelegate: UIResponder, UIApplicationDelegate {
|
||||
var window: UIWindow?
|
||||
|
||||
func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]? = nil) -> Bool {
|
||||
let window = UIWindow()
|
||||
let navigationController = UINavigationController(rootViewController: TopViewController())
|
||||
navigationController.navigationBar.tintColor = .black
|
||||
window.rootViewController = navigationController
|
||||
window.makeKeyAndVisible()
|
||||
self.window = window
|
||||
|
||||
return true
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,98 @@
|
||||
{
|
||||
"images" : [
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "20x20",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "20x20",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "29x29",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "29x29",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "40x40",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "40x40",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "60x60",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "iphone",
|
||||
"size" : "60x60",
|
||||
"scale" : "3x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "20x20",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "20x20",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "29x29",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "29x29",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "40x40",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "40x40",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "76x76",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "76x76",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ipad",
|
||||
"size" : "83.5x83.5",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "ios-marketing",
|
||||
"size" : "1024x1024",
|
||||
"scale" : "1x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"version" : 1,
|
||||
"author" : "xcode"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"info" : {
|
||||
"version" : 1,
|
||||
"author" : "xcode"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,25 @@
|
||||
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
|
||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="13122.16" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" launchScreen="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="01J-lp-oVM">
|
||||
<dependencies>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="13104.12"/>
|
||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<scenes>
|
||||
<!--View Controller-->
|
||||
<scene sceneID="EHf-IW-A2E">
|
||||
<objects>
|
||||
<viewController id="01J-lp-oVM" sceneMemberID="viewController">
|
||||
<view key="view" contentMode="scaleToFill" id="Ze5-6b-2t3">
|
||||
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||
<color key="backgroundColor" red="1" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
|
||||
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
|
||||
</view>
|
||||
</viewController>
|
||||
<placeholder placeholderIdentifier="IBFirstResponder" id="iYj-Kq-Ea1" userLabel="First Responder" sceneMemberID="firstResponder"/>
|
||||
</objects>
|
||||
<point key="canvasLocation" x="53" y="375"/>
|
||||
</scene>
|
||||
</scenes>
|
||||
</document>
|
||||
@@ -0,0 +1,13 @@
|
||||
import UIKit
|
||||
|
||||
extension UITableViewCell {
|
||||
static var name: String {
|
||||
return String(describing: self)
|
||||
}
|
||||
}
|
||||
|
||||
extension UICollectionViewCell {
|
||||
static var name: String {
|
||||
return String(describing: self)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,43 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>$(DEVELOPMENT_LANGUAGE)</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
<key>LSRequiresIPhoneOS</key>
|
||||
<true/>
|
||||
<key>UILaunchStoryboardName</key>
|
||||
<string>LaunchScreen</string>
|
||||
<key>UIMainStoryboardFile</key>
|
||||
<string></string>
|
||||
<key>UIRequiredDeviceCapabilities</key>
|
||||
<array>
|
||||
<string>armv7</string>
|
||||
</array>
|
||||
<key>UISupportedInterfaceOrientations</key>
|
||||
<array>
|
||||
<string>UIInterfaceOrientationPortrait</string>
|
||||
</array>
|
||||
<key>UISupportedInterfaceOrientations~ipad</key>
|
||||
<array>
|
||||
<string>UIInterfaceOrientationPortrait</string>
|
||||
<string>UIInterfaceOrientationPortraitUpsideDown</string>
|
||||
<string>UIInterfaceOrientationLandscapeLeft</string>
|
||||
<string>UIInterfaceOrientationLandscapeRight</string>
|
||||
</array>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,172 @@
|
||||
import UIKit
|
||||
import DiffableDataSources
|
||||
|
||||
final class InsertionSortViewController: UIViewController {
|
||||
final class Section: Hashable {
|
||||
var id = UUID()
|
||||
var nodes: [Node]
|
||||
private(set) var isSorted = false
|
||||
private var currentIndex = 1
|
||||
|
||||
init(count: Int) {
|
||||
nodes = (0..<count).map { Node(value: $0, maxValue: count) }.shuffled()
|
||||
}
|
||||
|
||||
func hash(into hasher: inout Hasher) {
|
||||
hasher.combine(id)
|
||||
}
|
||||
|
||||
func sortNext() {
|
||||
guard !isSorted, nodes.count > 1 else {
|
||||
return isSorted = true
|
||||
}
|
||||
|
||||
var index = currentIndex
|
||||
let currentNode = nodes[index]
|
||||
index -= 1
|
||||
|
||||
while index >= 0 && currentNode.value < nodes[index].value {
|
||||
let node = nodes[index]
|
||||
nodes[index] = currentNode
|
||||
nodes[index + 1] = node
|
||||
index -= 1
|
||||
}
|
||||
|
||||
currentIndex += 1
|
||||
|
||||
if currentIndex >= nodes.count {
|
||||
isSorted = true
|
||||
}
|
||||
}
|
||||
|
||||
static func == (lhs: Section, rhs: Section) -> Bool {
|
||||
return lhs.id == rhs.id
|
||||
}
|
||||
}
|
||||
|
||||
struct Node: Hashable {
|
||||
var id = UUID()
|
||||
var value: Int
|
||||
var color: UIColor
|
||||
|
||||
init(value: Int, maxValue: Int) {
|
||||
let hue = CGFloat(value) / CGFloat(maxValue)
|
||||
self.value = value
|
||||
color = UIColor(hue: hue, saturation: 1, brightness: 1, alpha: 1)
|
||||
id = UUID()
|
||||
}
|
||||
|
||||
func hash(into hasher: inout Hasher) {
|
||||
hasher.combine(id)
|
||||
}
|
||||
|
||||
static func == (lhs: Node, rhs: Node) -> Bool {
|
||||
return lhs.id == rhs.id
|
||||
}
|
||||
}
|
||||
|
||||
@IBOutlet private var collectionView: UICollectionView!
|
||||
private var isSorting = false
|
||||
|
||||
let nodeSize = CGSize(width: 16, height: 34)
|
||||
|
||||
private lazy var dataSource = CollectionViewDiffableDataSource<Section, Node>(collectionView: collectionView) { collectionView, indexPath, node in
|
||||
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: UICollectionViewCell.name, for: indexPath)
|
||||
cell.backgroundColor = node.color
|
||||
return cell
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
title = "Insertion Sort"
|
||||
|
||||
collectionView.delegate = self
|
||||
collectionView.register(UICollectionViewCell.self, forCellWithReuseIdentifier: UICollectionViewCell.name)
|
||||
navigationItem.rightBarButtonItem = UIBarButtonItem(title: nil, style: .plain, target: self, action: #selector(toggleSort))
|
||||
|
||||
updateSortButtonTitle()
|
||||
}
|
||||
|
||||
override func viewDidLayoutSubviews() {
|
||||
super.viewDidLayoutSubviews()
|
||||
randmize(animated: false)
|
||||
}
|
||||
|
||||
@objc func toggleSort() {
|
||||
isSorting.toggle()
|
||||
updateSortButtonTitle()
|
||||
|
||||
if isSorting {
|
||||
startInsertionSort()
|
||||
}
|
||||
}
|
||||
|
||||
func updateSortButtonTitle() {
|
||||
navigationItem.rightBarButtonItem?.title = isSorting ? "Stop" : "Sort"
|
||||
}
|
||||
|
||||
func randmize(animated: Bool) {
|
||||
let snapshot = DiffableDataSourceSnapshot<Section, Node>()
|
||||
let rows = Int(collectionView.bounds.height / nodeSize.height) - 1
|
||||
let columns = Int(collectionView.bounds.width / nodeSize.width)
|
||||
|
||||
for _ in 0..<rows {
|
||||
let section = Section(count: columns)
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(section.nodes)
|
||||
}
|
||||
|
||||
dataSource.apply(snapshot, animatingDifferences: animated)
|
||||
}
|
||||
|
||||
func startInsertionSort() {
|
||||
guard isSorting else {
|
||||
return
|
||||
}
|
||||
|
||||
var isNextSortRequired = false
|
||||
let snapshot = dataSource.snapshot()
|
||||
|
||||
for section in snapshot.sectionIdentifiers where !section.isSorted {
|
||||
section.sortNext()
|
||||
let items = section.nodes
|
||||
snapshot.deleteItems(items)
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
isNextSortRequired = true
|
||||
}
|
||||
|
||||
if isNextSortRequired {
|
||||
dataSource.apply(snapshot)
|
||||
}
|
||||
|
||||
DispatchQueue.main.asyncAfter(deadline: .now() + .milliseconds(isNextSortRequired ? 150 : 1000)) { [weak self] in
|
||||
guard let self = self else {
|
||||
return
|
||||
}
|
||||
|
||||
if !isNextSortRequired {
|
||||
self.randmize(animated: false)
|
||||
}
|
||||
self.startInsertionSort()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
extension InsertionSortViewController: UICollectionViewDelegateFlowLayout {
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 0
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 0
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
|
||||
return .zero
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
|
||||
return nodeSize
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,44 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="14490.70" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
||||
<device id="retina6_1" orientation="portrait">
|
||||
<adaptation id="fullscreen"/>
|
||||
</device>
|
||||
<dependencies>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14490.49"/>
|
||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<objects>
|
||||
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="InsertionSortViewController" customModule="Example_iOS" customModuleProvider="target">
|
||||
<connections>
|
||||
<outlet property="collectionView" destination="6GZ-26-LaT" id="93h-pF-UdX"/>
|
||||
<outlet property="view" destination="iN0-l3-epB" id="SEV-ah-gIe"/>
|
||||
</connections>
|
||||
</placeholder>
|
||||
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
|
||||
<view contentMode="scaleToFill" id="iN0-l3-epB">
|
||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||
<subviews>
|
||||
<collectionView clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="scaleToFill" bounces="NO" showsHorizontalScrollIndicator="NO" showsVerticalScrollIndicator="NO" bouncesZoom="NO" dataMode="none" translatesAutoresizingMaskIntoConstraints="NO" id="6GZ-26-LaT">
|
||||
<rect key="frame" x="0.0" y="44" width="414" height="852"/>
|
||||
<color key="backgroundColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
<collectionViewFlowLayout key="collectionViewLayout" minimumLineSpacing="10" minimumInteritemSpacing="10" id="IOA-0B-TAt">
|
||||
<size key="itemSize" width="50" height="50"/>
|
||||
<size key="headerReferenceSize" width="0.0" height="0.0"/>
|
||||
<size key="footerReferenceSize" width="0.0" height="0.0"/>
|
||||
<inset key="sectionInset" minX="0.0" minY="0.0" maxX="0.0" maxY="0.0"/>
|
||||
</collectionViewFlowLayout>
|
||||
</collectionView>
|
||||
</subviews>
|
||||
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
<constraints>
|
||||
<constraint firstItem="6GZ-26-LaT" firstAttribute="top" secondItem="vUN-kp-3ea" secondAttribute="top" id="N1l-xD-bVR"/>
|
||||
<constraint firstAttribute="trailing" secondItem="6GZ-26-LaT" secondAttribute="trailing" id="WAV-gN-b0a"/>
|
||||
<constraint firstAttribute="bottom" secondItem="6GZ-26-LaT" secondAttribute="bottom" id="cwF-t5-pdY"/>
|
||||
<constraint firstItem="6GZ-26-LaT" firstAttribute="leading" secondItem="iN0-l3-epB" secondAttribute="leading" id="lef-dU-E4k"/>
|
||||
</constraints>
|
||||
<viewLayoutGuide key="safeArea" id="vUN-kp-3ea"/>
|
||||
</view>
|
||||
</objects>
|
||||
</document>
|
||||
@@ -0,0 +1,12 @@
|
||||
import UIKit
|
||||
|
||||
final class LabelCell: UICollectionViewCell {
|
||||
@IBOutlet var label: UILabel!
|
||||
|
||||
override func awakeFromNib() {
|
||||
super.awakeFromNib()
|
||||
|
||||
layer.borderWidth = 1
|
||||
layer.borderColor = UIColor.gray.cgColor
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,42 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="14490.70" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
||||
<device id="retina6_1" orientation="portrait">
|
||||
<adaptation id="fullscreen"/>
|
||||
</device>
|
||||
<dependencies>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14490.49"/>
|
||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<objects>
|
||||
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner"/>
|
||||
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
|
||||
<collectionViewCell opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" id="pYo-4D-KR8" customClass="LabelCell" customModule="Example_iOS" customModuleProvider="target">
|
||||
<rect key="frame" x="0.0" y="0.0" width="300" height="32"/>
|
||||
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
||||
<view key="contentView" opaque="NO" clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="center" insetsLayoutMarginsFromSafeArea="NO">
|
||||
<rect key="frame" x="0.0" y="0.0" width="300" height="32"/>
|
||||
<autoresizingMask key="autoresizingMask"/>
|
||||
<subviews>
|
||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Label" textAlignment="natural" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="qKi-9G-J20">
|
||||
<rect key="frame" x="10" y="0.0" width="280" height="32"/>
|
||||
<fontDescription key="fontDescription" style="UICTFontTextStyleBody"/>
|
||||
<nil key="textColor"/>
|
||||
<nil key="highlightedColor"/>
|
||||
</label>
|
||||
</subviews>
|
||||
</view>
|
||||
<constraints>
|
||||
<constraint firstItem="qKi-9G-J20" firstAttribute="leading" secondItem="pYo-4D-KR8" secondAttribute="leading" constant="10" id="UJN-ZW-lz4"/>
|
||||
<constraint firstAttribute="trailing" secondItem="qKi-9G-J20" secondAttribute="trailing" constant="10" id="VbK-qH-sMr"/>
|
||||
<constraint firstItem="qKi-9G-J20" firstAttribute="top" secondItem="pYo-4D-KR8" secondAttribute="top" id="YkZ-vn-KK6"/>
|
||||
<constraint firstAttribute="bottom" secondItem="qKi-9G-J20" secondAttribute="bottom" id="au1-M8-Hh2"/>
|
||||
</constraints>
|
||||
<viewLayoutGuide key="safeArea" id="wQ5-Q0-9Pt"/>
|
||||
<connections>
|
||||
<outlet property="label" destination="qKi-9G-J20" id="hp7-fh-rao"/>
|
||||
</connections>
|
||||
<point key="canvasLocation" x="-1" y="74"/>
|
||||
</collectionViewCell>
|
||||
</objects>
|
||||
</document>
|
||||
@@ -0,0 +1,84 @@
|
||||
import UIKit
|
||||
import DiffableDataSources
|
||||
|
||||
final class MountainsViewController: UIViewController {
|
||||
enum Section {
|
||||
case main
|
||||
}
|
||||
|
||||
struct Mountain: Hashable {
|
||||
var name: String
|
||||
|
||||
func contains(_ filter: String) -> Bool {
|
||||
guard !filter.isEmpty else {
|
||||
return true
|
||||
}
|
||||
|
||||
let lowercasedFilter = filter.lowercased()
|
||||
return name.lowercased().contains(lowercasedFilter)
|
||||
}
|
||||
}
|
||||
|
||||
@IBOutlet private var searchBar: UISearchBar!
|
||||
@IBOutlet private var collectionView: UICollectionView!
|
||||
|
||||
private lazy var dataSource = CollectionViewDiffableDataSource<Section, Mountain>(collectionView: collectionView) { collectionView, indexPath, mountain in
|
||||
let cell = collectionView.dequeueReusableCell(withReuseIdentifier: LabelCell.name, for: indexPath) as! LabelCell
|
||||
cell.label.text = mountain.name
|
||||
return cell
|
||||
}
|
||||
|
||||
private let allMountains: [Mountain] = mountainsRawData.components(separatedBy: .newlines).map { line in
|
||||
let name = line.components(separatedBy: ",")[0]
|
||||
return Mountain(name: name)
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
title = "Mountains Search"
|
||||
|
||||
searchBar.delegate = self
|
||||
collectionView.delegate = self
|
||||
collectionView.register(UINib(nibName: LabelCell.name, bundle: .main), forCellWithReuseIdentifier: LabelCell.name)
|
||||
|
||||
search(filter: "")
|
||||
}
|
||||
|
||||
func search(filter: String) {
|
||||
let mountains = allMountains.lazy
|
||||
.filter { $0.contains(filter) }
|
||||
.sorted { $0.name < $1.name }
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Section, Mountain>()
|
||||
snapshot.appendSections([.main])
|
||||
snapshot.appendItems(mountains)
|
||||
dataSource.apply(snapshot)
|
||||
}
|
||||
}
|
||||
|
||||
extension MountainsViewController: UISearchBarDelegate {
|
||||
func searchBar(_ searchBar: UISearchBar, textDidChange searchText: String) {
|
||||
search(filter: searchText)
|
||||
}
|
||||
}
|
||||
|
||||
extension MountainsViewController: UICollectionViewDelegateFlowLayout {
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 10
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 10
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, insetForSectionAt section: Int) -> UIEdgeInsets {
|
||||
return UIEdgeInsets(top: 10, left: 10, bottom: 10, right: 10)
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize {
|
||||
let column = 2
|
||||
let width = (collectionView.bounds.width - 10 * CGFloat(column + 1)) / CGFloat(column)
|
||||
return CGSize(width: width, height: 32)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="14490.70" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
||||
<device id="retina6_1" orientation="portrait">
|
||||
<adaptation id="fullscreen"/>
|
||||
</device>
|
||||
<dependencies>
|
||||
<deployment identifier="iOS"/>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14490.49"/>
|
||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<objects>
|
||||
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="MountainsViewController" customModule="DiffableDataSourcesExample_iOS" customModuleProvider="target">
|
||||
<connections>
|
||||
<outlet property="collectionView" destination="kRf-0w-rJc" id="OBe-Sd-A2L"/>
|
||||
<outlet property="searchBar" destination="t4I-uz-ABD" id="NtR-qE-qZn"/>
|
||||
<outlet property="view" destination="a1D-Hd-aJU" id="Oyu-9w-QKH"/>
|
||||
</connections>
|
||||
</placeholder>
|
||||
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
|
||||
<view contentMode="scaleToFill" id="a1D-Hd-aJU">
|
||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
||||
<subviews>
|
||||
<searchBar contentMode="redraw" translatesAutoresizingMaskIntoConstraints="NO" id="t4I-uz-ABD">
|
||||
<rect key="frame" x="0.0" y="44" width="414" height="56"/>
|
||||
<textInputTraits key="textInputTraits"/>
|
||||
</searchBar>
|
||||
<collectionView clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" keyboardDismissMode="onDrag" dataMode="none" translatesAutoresizingMaskIntoConstraints="NO" id="kRf-0w-rJc">
|
||||
<rect key="frame" x="0.0" y="120" width="414" height="776"/>
|
||||
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
<collectionViewFlowLayout key="collectionViewLayout" minimumLineSpacing="0.0" minimumInteritemSpacing="0.0" id="vHO-Ju-ApP">
|
||||
<size key="itemSize" width="50" height="50"/>
|
||||
<size key="headerReferenceSize" width="0.0" height="0.0"/>
|
||||
<size key="footerReferenceSize" width="0.0" height="0.0"/>
|
||||
<inset key="sectionInset" minX="0.0" minY="0.0" maxX="0.0" maxY="0.0"/>
|
||||
</collectionViewFlowLayout>
|
||||
</collectionView>
|
||||
</subviews>
|
||||
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
<constraints>
|
||||
<constraint firstAttribute="bottom" secondItem="kRf-0w-rJc" secondAttribute="bottom" id="CBM-WJ-k93"/>
|
||||
<constraint firstItem="t4I-uz-ABD" firstAttribute="leading" secondItem="a1D-Hd-aJU" secondAttribute="leading" id="H5j-5C-2jy"/>
|
||||
<constraint firstAttribute="trailing" secondItem="kRf-0w-rJc" secondAttribute="trailing" id="Hog-jr-nJY"/>
|
||||
<constraint firstItem="t4I-uz-ABD" firstAttribute="top" secondItem="ujY-YI-BSN" secondAttribute="top" id="IkY-zg-lm8"/>
|
||||
<constraint firstItem="kRf-0w-rJc" firstAttribute="top" secondItem="t4I-uz-ABD" secondAttribute="bottom" constant="20" id="aJ9-Wc-4Jd"/>
|
||||
<constraint firstAttribute="trailing" secondItem="t4I-uz-ABD" secondAttribute="trailing" id="d5P-My-ReY"/>
|
||||
<constraint firstItem="kRf-0w-rJc" firstAttribute="leading" secondItem="a1D-Hd-aJU" secondAttribute="leading" id="esv-zM-Pc2"/>
|
||||
</constraints>
|
||||
<viewLayoutGuide key="safeArea" id="ujY-YI-BSN"/>
|
||||
<point key="canvasLocation" x="17" y="173"/>
|
||||
</view>
|
||||
</objects>
|
||||
</document>
|
||||
@@ -0,0 +1,82 @@
|
||||
import UIKit
|
||||
import DiffableDataSources
|
||||
|
||||
final class TopViewController: UIViewController {
|
||||
enum Section {
|
||||
case main
|
||||
}
|
||||
|
||||
enum Item {
|
||||
case mountains
|
||||
case insertionSort
|
||||
}
|
||||
|
||||
@IBOutlet private var tableView: UITableView!
|
||||
|
||||
private lazy var dataSource = TableViewDiffableDataSource<Section, Item>(tableView: tableView) { tableView, indexPath, item in
|
||||
let cell = tableView.dequeueReusableCell(withIdentifier: UITableViewCell.name, for: indexPath)
|
||||
cell.textLabel?.text = item.title
|
||||
cell.accessoryType = .disclosureIndicator
|
||||
return cell
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
title = "DiffableDataSources"
|
||||
|
||||
tableView.delegate = self
|
||||
tableView.register(UITableViewCell.self, forCellReuseIdentifier: UITableViewCell.name)
|
||||
tableView.rowHeight = 60
|
||||
tableView.contentInset.top = 30
|
||||
|
||||
reset()
|
||||
}
|
||||
|
||||
override func viewWillAppear(_ animated: Bool) {
|
||||
super.viewWillAppear(animated)
|
||||
|
||||
if let indexPath = tableView.indexPathForSelectedRow {
|
||||
tableView.deselectRow(at: indexPath, animated: true)
|
||||
}
|
||||
}
|
||||
|
||||
func reset() {
|
||||
let snapshot = DiffableDataSourceSnapshot<Section, Item>()
|
||||
snapshot.appendSections([.main])
|
||||
snapshot.appendItems([.mountains, .insertionSort])
|
||||
dataSource.apply(snapshot)
|
||||
}
|
||||
}
|
||||
|
||||
extension TopViewController: UITableViewDelegate {
|
||||
func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
|
||||
guard let item = dataSource.itemIdentifier(for: indexPath) else {
|
||||
return
|
||||
}
|
||||
|
||||
let viewController: UIViewController
|
||||
|
||||
switch item {
|
||||
case .mountains:
|
||||
viewController = MountainsViewController()
|
||||
|
||||
case .insertionSort:
|
||||
viewController = InsertionSortViewController()
|
||||
}
|
||||
|
||||
navigationController?.pushViewController(viewController, animated: true)
|
||||
}
|
||||
}
|
||||
|
||||
private extension TopViewController.Item {
|
||||
var title: String {
|
||||
switch self {
|
||||
case .mountains:
|
||||
return "🗻 Mountains"
|
||||
|
||||
case .insertionSort:
|
||||
return "📱 Insertion Sort"
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,39 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="14490.70" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
||||
<device id="retina6_1" orientation="portrait">
|
||||
<adaptation id="fullscreen"/>
|
||||
</device>
|
||||
<dependencies>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14490.49"/>
|
||||
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<objects>
|
||||
<placeholder placeholderIdentifier="IBFilesOwner" id="-1" userLabel="File's Owner" customClass="TopViewController" customModule="Example_iOS" customModuleProvider="target">
|
||||
<connections>
|
||||
<outlet property="tableView" destination="tX9-V1-EJv" id="EHH-CF-6fE"/>
|
||||
<outlet property="view" destination="Ude-8O-7bT" id="VCy-jI-QZK"/>
|
||||
</connections>
|
||||
</placeholder>
|
||||
<placeholder placeholderIdentifier="IBFirstResponder" id="-2" customClass="UIResponder"/>
|
||||
<view contentMode="scaleToFill" id="Ude-8O-7bT">
|
||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||
<autoresizingMask key="autoresizingMask" flexibleMaxX="YES" flexibleMaxY="YES"/>
|
||||
<subviews>
|
||||
<tableView clipsSubviews="YES" contentMode="scaleToFill" alwaysBounceVertical="YES" style="plain" separatorStyle="default" rowHeight="-1" estimatedRowHeight="-1" sectionHeaderHeight="28" sectionFooterHeight="28" translatesAutoresizingMaskIntoConstraints="NO" id="tX9-V1-EJv">
|
||||
<rect key="frame" x="0.0" y="0.0" width="414" height="896"/>
|
||||
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
</tableView>
|
||||
</subviews>
|
||||
<color key="backgroundColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||
<constraints>
|
||||
<constraint firstAttribute="bottom" secondItem="tX9-V1-EJv" secondAttribute="bottom" id="0fN-0u-kPN"/>
|
||||
<constraint firstItem="tX9-V1-EJv" firstAttribute="top" secondItem="Ude-8O-7bT" secondAttribute="top" id="NML-7Q-dfc"/>
|
||||
<constraint firstItem="tX9-V1-EJv" firstAttribute="leading" secondItem="Ude-8O-7bT" secondAttribute="leading" id="h66-Ya-k2Y"/>
|
||||
<constraint firstAttribute="trailing" secondItem="tX9-V1-EJv" secondAttribute="trailing" id="phG-hF-KAp"/>
|
||||
</constraints>
|
||||
<viewLayoutGuide key="safeArea" id="iZn-f5-WVt"/>
|
||||
<point key="canvasLocation" x="68" y="141"/>
|
||||
</view>
|
||||
</objects>
|
||||
</document>
|
||||
@@ -0,0 +1,4 @@
|
||||
import Cocoa
|
||||
|
||||
@NSApplicationMain
|
||||
final class AppDelegate: NSObject, NSApplicationDelegate {}
|
||||
@@ -0,0 +1,58 @@
|
||||
{
|
||||
"images" : [
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "16x16",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "16x16",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "32x32",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "32x32",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "128x128",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "128x128",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "256x256",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "256x256",
|
||||
"scale" : "2x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "512x512",
|
||||
"scale" : "1x"
|
||||
},
|
||||
{
|
||||
"idiom" : "mac",
|
||||
"size" : "512x512",
|
||||
"scale" : "2x"
|
||||
}
|
||||
],
|
||||
"info" : {
|
||||
"version" : 1,
|
||||
"author" : "xcode"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,6 @@
|
||||
{
|
||||
"info" : {
|
||||
"version" : 1,
|
||||
"author" : "xcode"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,773 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<document type="com.apple.InterfaceBuilder3.Cocoa.Storyboard.XIB" version="3.0" toolsVersion="14810.11" targetRuntime="MacOSX.Cocoa" propertyAccessControl="none" useAutolayout="YES" initialViewController="B8D-0N-5wS">
|
||||
<dependencies>
|
||||
<deployment identifier="macosx"/>
|
||||
<plugIn identifier="com.apple.InterfaceBuilder.CocoaPlugin" version="14810.11"/>
|
||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||
</dependencies>
|
||||
<scenes>
|
||||
<!--Application-->
|
||||
<scene sceneID="JPo-4y-FX3">
|
||||
<objects>
|
||||
<application id="hnw-xV-0zn" sceneMemberID="viewController">
|
||||
<menu key="mainMenu" title="Main Menu" systemMenu="main" id="AYu-sK-qS6">
|
||||
<items>
|
||||
<menuItem title="Example-macOS" id="1Xt-HY-uBw">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Example-macOS" systemMenu="apple" id="uQy-DD-JDr">
|
||||
<items>
|
||||
<menuItem title="About Example-macOS" id="5kV-Vb-QxS">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="orderFrontStandardAboutPanel:" target="Ady-hI-5gd" id="Exp-CZ-Vem"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="VOq-y0-SEH"/>
|
||||
<menuItem title="Preferences…" keyEquivalent="," id="BOF-NM-1cW"/>
|
||||
<menuItem isSeparatorItem="YES" id="wFC-TO-SCJ"/>
|
||||
<menuItem title="Services" id="NMo-om-nkz">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Services" systemMenu="services" id="hz9-B4-Xy5"/>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="4je-JR-u6R"/>
|
||||
<menuItem title="Hide Example-macOS" keyEquivalent="h" id="Olw-nP-bQN">
|
||||
<connections>
|
||||
<action selector="hide:" target="Ady-hI-5gd" id="PnN-Uc-m68"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Hide Others" keyEquivalent="h" id="Vdr-fp-XzO">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="hideOtherApplications:" target="Ady-hI-5gd" id="VT4-aY-XCT"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Show All" id="Kd2-mp-pUS">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="unhideAllApplications:" target="Ady-hI-5gd" id="Dhg-Le-xox"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="kCx-OE-vgT"/>
|
||||
<menuItem title="Quit Example-macOS" keyEquivalent="q" id="4sb-4s-VLi">
|
||||
<connections>
|
||||
<action selector="terminate:" target="Ady-hI-5gd" id="Te7-pn-YzF"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="File" id="dMs-cI-mzQ">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="File" id="bib-Uj-vzu">
|
||||
<items>
|
||||
<menuItem title="New" keyEquivalent="n" id="Was-JA-tGl">
|
||||
<connections>
|
||||
<action selector="newDocument:" target="Ady-hI-5gd" id="4Si-XN-c54"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Open…" keyEquivalent="o" id="IAo-SY-fd9">
|
||||
<connections>
|
||||
<action selector="openDocument:" target="Ady-hI-5gd" id="bVn-NM-KNZ"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Open Recent" id="tXI-mr-wws">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Open Recent" systemMenu="recentDocuments" id="oas-Oc-fiZ">
|
||||
<items>
|
||||
<menuItem title="Clear Menu" id="vNY-rz-j42">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="clearRecentDocuments:" target="Ady-hI-5gd" id="Daa-9d-B3U"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="m54-Is-iLE"/>
|
||||
<menuItem title="Close" keyEquivalent="w" id="DVo-aG-piG">
|
||||
<connections>
|
||||
<action selector="performClose:" target="Ady-hI-5gd" id="HmO-Ls-i7Q"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Save…" keyEquivalent="s" id="pxx-59-PXV">
|
||||
<connections>
|
||||
<action selector="saveDocument:" target="Ady-hI-5gd" id="teZ-XB-qJY"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Save As…" keyEquivalent="S" id="Bw7-FT-i3A">
|
||||
<connections>
|
||||
<action selector="saveDocumentAs:" target="Ady-hI-5gd" id="mDf-zr-I0C"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Revert to Saved" keyEquivalent="r" id="KaW-ft-85H">
|
||||
<connections>
|
||||
<action selector="revertDocumentToSaved:" target="Ady-hI-5gd" id="iJ3-Pv-kwq"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="aJh-i4-bef"/>
|
||||
<menuItem title="Page Setup…" keyEquivalent="P" id="qIS-W8-SiK">
|
||||
<modifierMask key="keyEquivalentModifierMask" shift="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="runPageLayout:" target="Ady-hI-5gd" id="Din-rz-gC5"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Print…" keyEquivalent="p" id="aTl-1u-JFS">
|
||||
<connections>
|
||||
<action selector="print:" target="Ady-hI-5gd" id="qaZ-4w-aoO"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Edit" id="5QF-Oa-p0T">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Edit" id="W48-6f-4Dl">
|
||||
<items>
|
||||
<menuItem title="Undo" keyEquivalent="z" id="dRJ-4n-Yzg">
|
||||
<connections>
|
||||
<action selector="undo:" target="Ady-hI-5gd" id="M6e-cu-g7V"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Redo" keyEquivalent="Z" id="6dh-zS-Vam">
|
||||
<connections>
|
||||
<action selector="redo:" target="Ady-hI-5gd" id="oIA-Rs-6OD"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="WRV-NI-Exz"/>
|
||||
<menuItem title="Cut" keyEquivalent="x" id="uRl-iY-unG">
|
||||
<connections>
|
||||
<action selector="cut:" target="Ady-hI-5gd" id="YJe-68-I9s"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Copy" keyEquivalent="c" id="x3v-GG-iWU">
|
||||
<connections>
|
||||
<action selector="copy:" target="Ady-hI-5gd" id="G1f-GL-Joy"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Paste" keyEquivalent="v" id="gVA-U4-sdL">
|
||||
<connections>
|
||||
<action selector="paste:" target="Ady-hI-5gd" id="UvS-8e-Qdg"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Paste and Match Style" keyEquivalent="V" id="WeT-3V-zwk">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="pasteAsPlainText:" target="Ady-hI-5gd" id="cEh-KX-wJQ"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Delete" id="pa3-QI-u2k">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="delete:" target="Ady-hI-5gd" id="0Mk-Ml-PaM"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Select All" keyEquivalent="a" id="Ruw-6m-B2m">
|
||||
<connections>
|
||||
<action selector="selectAll:" target="Ady-hI-5gd" id="VNm-Mi-diN"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="uyl-h8-XO2"/>
|
||||
<menuItem title="Find" id="4EN-yA-p0u">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Find" id="1b7-l0-nxx">
|
||||
<items>
|
||||
<menuItem title="Find…" tag="1" keyEquivalent="f" id="Xz5-n4-O0W">
|
||||
<connections>
|
||||
<action selector="performFindPanelAction:" target="Ady-hI-5gd" id="cD7-Qs-BN4"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Find and Replace…" tag="12" keyEquivalent="f" id="YEy-JH-Tfz">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="performFindPanelAction:" target="Ady-hI-5gd" id="WD3-Gg-5AJ"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Find Next" tag="2" keyEquivalent="g" id="q09-fT-Sye">
|
||||
<connections>
|
||||
<action selector="performFindPanelAction:" target="Ady-hI-5gd" id="NDo-RZ-v9R"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Find Previous" tag="3" keyEquivalent="G" id="OwM-mh-QMV">
|
||||
<connections>
|
||||
<action selector="performFindPanelAction:" target="Ady-hI-5gd" id="HOh-sY-3ay"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Use Selection for Find" tag="7" keyEquivalent="e" id="buJ-ug-pKt">
|
||||
<connections>
|
||||
<action selector="performFindPanelAction:" target="Ady-hI-5gd" id="U76-nv-p5D"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Jump to Selection" keyEquivalent="j" id="S0p-oC-mLd">
|
||||
<connections>
|
||||
<action selector="centerSelectionInVisibleArea:" target="Ady-hI-5gd" id="IOG-6D-g5B"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Spelling and Grammar" id="Dv1-io-Yv7">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Spelling" id="3IN-sU-3Bg">
|
||||
<items>
|
||||
<menuItem title="Show Spelling and Grammar" keyEquivalent=":" id="HFo-cy-zxI">
|
||||
<connections>
|
||||
<action selector="showGuessPanel:" target="Ady-hI-5gd" id="vFj-Ks-hy3"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Check Document Now" keyEquivalent=";" id="hz2-CU-CR7">
|
||||
<connections>
|
||||
<action selector="checkSpelling:" target="Ady-hI-5gd" id="fz7-VC-reM"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="bNw-od-mp5"/>
|
||||
<menuItem title="Check Spelling While Typing" id="rbD-Rh-wIN">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleContinuousSpellChecking:" target="Ady-hI-5gd" id="7w6-Qz-0kB"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Check Grammar With Spelling" id="mK6-2p-4JG">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleGrammarChecking:" target="Ady-hI-5gd" id="muD-Qn-j4w"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Correct Spelling Automatically" id="78Y-hA-62v">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticSpellingCorrection:" target="Ady-hI-5gd" id="2lM-Qi-WAP"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Substitutions" id="9ic-FL-obx">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Substitutions" id="FeM-D8-WVr">
|
||||
<items>
|
||||
<menuItem title="Show Substitutions" id="z6F-FW-3nz">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="orderFrontSubstitutionsPanel:" target="Ady-hI-5gd" id="oku-mr-iSq"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="gPx-C9-uUO"/>
|
||||
<menuItem title="Smart Copy/Paste" id="9yt-4B-nSM">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleSmartInsertDelete:" target="Ady-hI-5gd" id="3IJ-Se-DZD"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Smart Quotes" id="hQb-2v-fYv">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticQuoteSubstitution:" target="Ady-hI-5gd" id="ptq-xd-QOA"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Smart Dashes" id="rgM-f4-ycn">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticDashSubstitution:" target="Ady-hI-5gd" id="oCt-pO-9gS"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Smart Links" id="cwL-P1-jid">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticLinkDetection:" target="Ady-hI-5gd" id="Gip-E3-Fov"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Data Detectors" id="tRr-pd-1PS">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticDataDetection:" target="Ady-hI-5gd" id="R1I-Nq-Kbl"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Text Replacement" id="HFQ-gK-NFA">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleAutomaticTextReplacement:" target="Ady-hI-5gd" id="DvP-Fe-Py6"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Transformations" id="2oI-Rn-ZJC">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Transformations" id="c8a-y6-VQd">
|
||||
<items>
|
||||
<menuItem title="Make Upper Case" id="vmV-6d-7jI">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="uppercaseWord:" target="Ady-hI-5gd" id="sPh-Tk-edu"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Make Lower Case" id="d9M-CD-aMd">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="lowercaseWord:" target="Ady-hI-5gd" id="iUZ-b5-hil"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Capitalize" id="UEZ-Bs-lqG">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="capitalizeWord:" target="Ady-hI-5gd" id="26H-TL-nsh"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Speech" id="xrE-MZ-jX0">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Speech" id="3rS-ZA-NoH">
|
||||
<items>
|
||||
<menuItem title="Start Speaking" id="Ynk-f8-cLZ">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="startSpeaking:" target="Ady-hI-5gd" id="654-Ng-kyl"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Stop Speaking" id="Oyz-dy-DGm">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="stopSpeaking:" target="Ady-hI-5gd" id="dX8-6p-jy9"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Format" id="jxT-CU-nIS">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Format" id="GEO-Iw-cKr">
|
||||
<items>
|
||||
<menuItem title="Font" id="Gi5-1S-RQB">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Font" systemMenu="font" id="aXa-aM-Jaq">
|
||||
<items>
|
||||
<menuItem title="Show Fonts" keyEquivalent="t" id="Q5e-8K-NDq">
|
||||
<connections>
|
||||
<action selector="orderFrontFontPanel:" target="YLy-65-1bz" id="WHr-nq-2xA"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Bold" tag="2" keyEquivalent="b" id="GB9-OM-e27">
|
||||
<connections>
|
||||
<action selector="addFontTrait:" target="YLy-65-1bz" id="hqk-hr-sYV"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Italic" tag="1" keyEquivalent="i" id="Vjx-xi-njq">
|
||||
<connections>
|
||||
<action selector="addFontTrait:" target="YLy-65-1bz" id="IHV-OB-c03"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Underline" keyEquivalent="u" id="WRG-CD-K1S">
|
||||
<connections>
|
||||
<action selector="underline:" target="Ady-hI-5gd" id="FYS-2b-JAY"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="5gT-KC-WSO"/>
|
||||
<menuItem title="Bigger" tag="3" keyEquivalent="+" id="Ptp-SP-VEL">
|
||||
<connections>
|
||||
<action selector="modifyFont:" target="YLy-65-1bz" id="Uc7-di-UnL"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Smaller" tag="4" keyEquivalent="-" id="i1d-Er-qST">
|
||||
<connections>
|
||||
<action selector="modifyFont:" target="YLy-65-1bz" id="HcX-Lf-eNd"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="kx3-Dk-x3B"/>
|
||||
<menuItem title="Kern" id="jBQ-r6-VK2">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Kern" id="tlD-Oa-oAM">
|
||||
<items>
|
||||
<menuItem title="Use Default" id="GUa-eO-cwY">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="useStandardKerning:" target="Ady-hI-5gd" id="6dk-9l-Ckg"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Use None" id="cDB-IK-hbR">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="turnOffKerning:" target="Ady-hI-5gd" id="U8a-gz-Maa"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Tighten" id="46P-cB-AYj">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="tightenKerning:" target="Ady-hI-5gd" id="hr7-Nz-8ro"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Loosen" id="ogc-rX-tC1">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="loosenKerning:" target="Ady-hI-5gd" id="8i4-f9-FKE"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Ligatures" id="o6e-r0-MWq">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Ligatures" id="w0m-vy-SC9">
|
||||
<items>
|
||||
<menuItem title="Use Default" id="agt-UL-0e3">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="useStandardLigatures:" target="Ady-hI-5gd" id="7uR-wd-Dx6"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Use None" id="J7y-lM-qPV">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="turnOffLigatures:" target="Ady-hI-5gd" id="iX2-gA-Ilz"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Use All" id="xQD-1f-W4t">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="useAllLigatures:" target="Ady-hI-5gd" id="KcB-kA-TuK"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Baseline" id="OaQ-X3-Vso">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Baseline" id="ijk-EB-dga">
|
||||
<items>
|
||||
<menuItem title="Use Default" id="3Om-Ey-2VK">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="unscript:" target="Ady-hI-5gd" id="0vZ-95-Ywn"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Superscript" id="Rqc-34-cIF">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="superscript:" target="Ady-hI-5gd" id="3qV-fo-wpU"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Subscript" id="I0S-gh-46l">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="subscript:" target="Ady-hI-5gd" id="Q6W-4W-IGz"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Raise" id="2h7-ER-AoG">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="raiseBaseline:" target="Ady-hI-5gd" id="4sk-31-7Q9"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Lower" id="1tx-W0-xDw">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="lowerBaseline:" target="Ady-hI-5gd" id="OF1-bc-KW4"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="Ndw-q3-faq"/>
|
||||
<menuItem title="Show Colors" keyEquivalent="C" id="bgn-CT-cEk">
|
||||
<connections>
|
||||
<action selector="orderFrontColorPanel:" target="Ady-hI-5gd" id="mSX-Xz-DV3"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="iMs-zA-UFJ"/>
|
||||
<menuItem title="Copy Style" keyEquivalent="c" id="5Vv-lz-BsD">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="copyFont:" target="Ady-hI-5gd" id="GJO-xA-L4q"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Paste Style" keyEquivalent="v" id="vKC-jM-MkH">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="pasteFont:" target="Ady-hI-5gd" id="JfD-CL-leO"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Text" id="Fal-I4-PZk">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Text" id="d9c-me-L2H">
|
||||
<items>
|
||||
<menuItem title="Align Left" keyEquivalent="{" id="ZM1-6Q-yy1">
|
||||
<connections>
|
||||
<action selector="alignLeft:" target="Ady-hI-5gd" id="zUv-R1-uAa"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Center" keyEquivalent="|" id="VIY-Ag-zcb">
|
||||
<connections>
|
||||
<action selector="alignCenter:" target="Ady-hI-5gd" id="spX-mk-kcS"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Justify" id="J5U-5w-g23">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="alignJustified:" target="Ady-hI-5gd" id="ljL-7U-jND"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Align Right" keyEquivalent="}" id="wb2-vD-lq4">
|
||||
<connections>
|
||||
<action selector="alignRight:" target="Ady-hI-5gd" id="r48-bG-YeY"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="4s2-GY-VfK"/>
|
||||
<menuItem title="Writing Direction" id="H1b-Si-o9J">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Writing Direction" id="8mr-sm-Yjd">
|
||||
<items>
|
||||
<menuItem title="Paragraph" enabled="NO" id="ZvO-Gk-QUH">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
</menuItem>
|
||||
<menuItem id="YGs-j5-SAR">
|
||||
<string key="title"> Default</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeBaseWritingDirectionNatural:" target="Ady-hI-5gd" id="qtV-5e-UBP"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem id="Lbh-J2-qVU">
|
||||
<string key="title"> Left to Right</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeBaseWritingDirectionLeftToRight:" target="Ady-hI-5gd" id="S0X-9S-QSf"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem id="jFq-tB-4Kx">
|
||||
<string key="title"> Right to Left</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeBaseWritingDirectionRightToLeft:" target="Ady-hI-5gd" id="5fk-qB-AqJ"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="swp-gr-a21"/>
|
||||
<menuItem title="Selection" enabled="NO" id="cqv-fj-IhA">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
</menuItem>
|
||||
<menuItem id="Nop-cj-93Q">
|
||||
<string key="title"> Default</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeTextWritingDirectionNatural:" target="Ady-hI-5gd" id="lPI-Se-ZHp"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem id="BgM-ve-c93">
|
||||
<string key="title"> Left to Right</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeTextWritingDirectionLeftToRight:" target="Ady-hI-5gd" id="caW-Bv-w94"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem id="RB4-Sm-HuC">
|
||||
<string key="title"> Right to Left</string>
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="makeTextWritingDirectionRightToLeft:" target="Ady-hI-5gd" id="EXD-6r-ZUu"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="fKy-g9-1gm"/>
|
||||
<menuItem title="Show Ruler" id="vLm-3I-IUL">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="toggleRuler:" target="Ady-hI-5gd" id="FOx-HJ-KwY"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Copy Ruler" keyEquivalent="c" id="MkV-Pr-PK5">
|
||||
<modifierMask key="keyEquivalentModifierMask" control="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="copyRuler:" target="Ady-hI-5gd" id="71i-fW-3W2"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Paste Ruler" keyEquivalent="v" id="LVM-kO-fVI">
|
||||
<modifierMask key="keyEquivalentModifierMask" control="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="pasteRuler:" target="Ady-hI-5gd" id="cSh-wd-qM2"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="View" id="H8h-7b-M4v">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="View" id="HyV-fh-RgO">
|
||||
<items>
|
||||
<menuItem title="Show Toolbar" keyEquivalent="t" id="snW-S8-Cw5">
|
||||
<modifierMask key="keyEquivalentModifierMask" option="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="toggleToolbarShown:" target="Ady-hI-5gd" id="BXY-wc-z0C"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Customize Toolbar…" id="1UK-8n-QPP">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="runToolbarCustomizationPalette:" target="Ady-hI-5gd" id="pQI-g3-MTW"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="hB3-LF-h0Y"/>
|
||||
<menuItem title="Show Sidebar" keyEquivalent="s" id="kIP-vf-haE">
|
||||
<modifierMask key="keyEquivalentModifierMask" control="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="toggleSidebar:" target="Ady-hI-5gd" id="iwa-gc-5KM"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Enter Full Screen" keyEquivalent="f" id="4J7-dP-txa">
|
||||
<modifierMask key="keyEquivalentModifierMask" control="YES" command="YES"/>
|
||||
<connections>
|
||||
<action selector="toggleFullScreen:" target="Ady-hI-5gd" id="dU3-MA-1Rq"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Window" id="aUF-d1-5bR">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Window" systemMenu="window" id="Td7-aD-5lo">
|
||||
<items>
|
||||
<menuItem title="Minimize" keyEquivalent="m" id="OY7-WF-poV">
|
||||
<connections>
|
||||
<action selector="performMiniaturize:" target="Ady-hI-5gd" id="VwT-WD-YPe"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem title="Zoom" id="R4o-n2-Eq4">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="performZoom:" target="Ady-hI-5gd" id="DIl-cC-cCs"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
<menuItem isSeparatorItem="YES" id="eu3-7i-yIM"/>
|
||||
<menuItem title="Bring All to Front" id="LE2-aR-0XJ">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<connections>
|
||||
<action selector="arrangeInFront:" target="Ady-hI-5gd" id="DRN-fu-gQh"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
<menuItem title="Help" id="wpr-3q-Mcd">
|
||||
<modifierMask key="keyEquivalentModifierMask"/>
|
||||
<menu key="submenu" title="Help" systemMenu="help" id="F2S-fz-NVQ">
|
||||
<items>
|
||||
<menuItem title="Example-macOS Help" keyEquivalent="?" id="FKE-Sm-Kum">
|
||||
<connections>
|
||||
<action selector="showHelp:" target="Ady-hI-5gd" id="y7X-2Q-9no"/>
|
||||
</connections>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
</menuItem>
|
||||
</items>
|
||||
</menu>
|
||||
<connections>
|
||||
<outlet property="delegate" destination="Voe-Tx-rLC" id="PrD-fu-P6m"/>
|
||||
</connections>
|
||||
</application>
|
||||
<customObject id="Voe-Tx-rLC" customClass="AppDelegate" customModule="Example_macOS" customModuleProvider="target"/>
|
||||
<customObject id="YLy-65-1bz" customClass="NSFontManager"/>
|
||||
<customObject id="Ady-hI-5gd" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
|
||||
</objects>
|
||||
<point key="canvasLocation" x="75" y="0.0"/>
|
||||
</scene>
|
||||
<!--Window Controller-->
|
||||
<scene sceneID="R2V-B0-nI4">
|
||||
<objects>
|
||||
<windowController id="B8D-0N-5wS" sceneMemberID="viewController">
|
||||
<window key="window" title="Window" allowsToolTipsWhenApplicationIsInactive="NO" autorecalculatesKeyViewLoop="NO" releasedWhenClosed="NO" visibleAtLaunch="NO" animationBehavior="default" id="IQv-IB-iLA">
|
||||
<windowStyleMask key="styleMask" titled="YES" closable="YES" miniaturizable="YES" resizable="YES"/>
|
||||
<windowPositionMask key="initialPositionMask" leftStrut="YES" rightStrut="YES" topStrut="YES" bottomStrut="YES"/>
|
||||
<rect key="contentRect" x="196" y="240" width="480" height="270"/>
|
||||
<rect key="screenRect" x="0.0" y="0.0" width="1680" height="1027"/>
|
||||
<connections>
|
||||
<outlet property="delegate" destination="B8D-0N-5wS" id="98r-iN-zZc"/>
|
||||
</connections>
|
||||
</window>
|
||||
<connections>
|
||||
<segue destination="XfG-lQ-9wD" kind="relationship" relationship="window.shadowedContentViewController" id="cq2-FE-JQM"/>
|
||||
</connections>
|
||||
</windowController>
|
||||
<customObject id="Oky-zY-oP4" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
|
||||
</objects>
|
||||
<point key="canvasLocation" x="75" y="250"/>
|
||||
</scene>
|
||||
<!--Mountains View Controller-->
|
||||
<scene sceneID="hIz-AP-VOD">
|
||||
<objects>
|
||||
<viewController id="XfG-lQ-9wD" customClass="MountainsViewController" customModule="Example_macOS" customModuleProvider="target" sceneMemberID="viewController">
|
||||
<view key="view" id="m2S-Jp-Qdl">
|
||||
<rect key="frame" x="0.0" y="0.0" width="480" height="270"/>
|
||||
<autoresizingMask key="autoresizingMask"/>
|
||||
<subviews>
|
||||
<scrollView wantsLayer="YES" autohidesScrollers="YES" horizontalLineScroll="10" horizontalPageScroll="10" verticalLineScroll="10" verticalPageScroll="10" hasHorizontalScroller="NO" usesPredominantAxisScrolling="NO" translatesAutoresizingMaskIntoConstraints="NO" id="4GE-cR-LXC">
|
||||
<rect key="frame" x="0.0" y="0.0" width="480" height="226"/>
|
||||
<clipView key="contentView" id="4a9-Kh-LYH">
|
||||
<rect key="frame" x="1" y="1" width="478" height="224"/>
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
|
||||
<subviews>
|
||||
<collectionView id="dtA-VK-I9R">
|
||||
<rect key="frame" x="0.0" y="0.0" width="478" height="224"/>
|
||||
<autoresizingMask key="autoresizingMask" widthSizable="YES"/>
|
||||
<collectionViewFlowLayout key="collectionViewLayout" minimumInteritemSpacing="10" minimumLineSpacing="10" id="eNu-C9-mnA">
|
||||
<size key="itemSize" width="50" height="50"/>
|
||||
</collectionViewFlowLayout>
|
||||
<color key="primaryBackgroundColor" name="controlBackgroundColor" catalog="System" colorSpace="catalog"/>
|
||||
</collectionView>
|
||||
</subviews>
|
||||
</clipView>
|
||||
<scroller key="horizontalScroller" hidden="YES" wantsLayer="YES" verticalHuggingPriority="750" horizontal="YES" id="L20-kk-UVn">
|
||||
<rect key="frame" x="-100" y="-100" width="233" height="15"/>
|
||||
<autoresizingMask key="autoresizingMask"/>
|
||||
</scroller>
|
||||
<scroller key="verticalScroller" hidden="YES" wantsLayer="YES" verticalHuggingPriority="750" doubleValue="1" horizontal="NO" id="asA-yX-Sp8">
|
||||
<rect key="frame" x="463" y="1" width="16" height="224"/>
|
||||
<autoresizingMask key="autoresizingMask"/>
|
||||
</scroller>
|
||||
</scrollView>
|
||||
<searchField wantsLayer="YES" verticalHuggingPriority="750" textCompletion="NO" translatesAutoresizingMaskIntoConstraints="NO" id="E8d-oD-QL3">
|
||||
<rect key="frame" x="0.0" y="226" width="480" height="44"/>
|
||||
<constraints>
|
||||
<constraint firstAttribute="height" constant="44" id="bgu-eY-Zmy"/>
|
||||
</constraints>
|
||||
<searchFieldCell key="cell" scrollable="YES" lineBreakMode="clipping" selectable="YES" editable="YES" borderStyle="bezel" usesSingleLineMode="YES" bezelStyle="round" id="YVe-iR-NNY">
|
||||
<font key="font" metaFont="system"/>
|
||||
<color key="textColor" name="controlTextColor" catalog="System" colorSpace="catalog"/>
|
||||
<color key="backgroundColor" name="textBackgroundColor" catalog="System" colorSpace="catalog"/>
|
||||
</searchFieldCell>
|
||||
<connections>
|
||||
<action selector="searchFieldDidChangeText:" target="XfG-lQ-9wD" id="Gr9-gO-Z7U"/>
|
||||
</connections>
|
||||
</searchField>
|
||||
</subviews>
|
||||
<constraints>
|
||||
<constraint firstItem="4GE-cR-LXC" firstAttribute="leading" secondItem="m2S-Jp-Qdl" secondAttribute="leading" id="VIk-Ok-vIc"/>
|
||||
<constraint firstItem="4GE-cR-LXC" firstAttribute="top" secondItem="E8d-oD-QL3" secondAttribute="bottom" id="XQU-W6-iZ1"/>
|
||||
<constraint firstAttribute="bottom" secondItem="4GE-cR-LXC" secondAttribute="bottom" id="YzV-Nw-2Vr"/>
|
||||
<constraint firstItem="E8d-oD-QL3" firstAttribute="leading" secondItem="m2S-Jp-Qdl" secondAttribute="leading" id="ZFg-Fj-FCw"/>
|
||||
<constraint firstItem="E8d-oD-QL3" firstAttribute="top" secondItem="m2S-Jp-Qdl" secondAttribute="top" id="gxF-Uq-fEV"/>
|
||||
<constraint firstAttribute="trailing" secondItem="E8d-oD-QL3" secondAttribute="trailing" id="iJG-BW-3qO"/>
|
||||
<constraint firstAttribute="trailing" secondItem="4GE-cR-LXC" secondAttribute="trailing" id="icw-4L-Z2L"/>
|
||||
</constraints>
|
||||
</view>
|
||||
<connections>
|
||||
<outlet property="collectionView" destination="dtA-VK-I9R" id="gbo-bM-Eme"/>
|
||||
<outlet property="searchField" destination="E8d-oD-QL3" id="eKx-B7-AkC"/>
|
||||
</connections>
|
||||
</viewController>
|
||||
<customObject id="rPt-NT-nkU" userLabel="First Responder" customClass="NSResponder" sceneMemberID="firstResponder"/>
|
||||
</objects>
|
||||
<point key="canvasLocation" x="75" y="655"/>
|
||||
</scene>
|
||||
</scenes>
|
||||
</document>
|
||||
@@ -0,0 +1,10 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>com.apple.security.app-sandbox</key>
|
||||
<true/>
|
||||
<key>com.apple.security.files.user-selected.read-only</key>
|
||||
<true/>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,32 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>$(DEVELOPMENT_LANGUAGE)</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIconFile</key>
|
||||
<string></string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>APPL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
<key>LSMinimumSystemVersion</key>
|
||||
<string>$(MACOSX_DEPLOYMENT_TARGET)</string>
|
||||
<key>NSHumanReadableCopyright</key>
|
||||
<string>Copyright © 2019 Ryo Aoyama. All rights reserved.</string>
|
||||
<key>NSMainStoryboardFile</key>
|
||||
<string>Main</string>
|
||||
<key>NSPrincipalClass</key>
|
||||
<string>NSApplication</string>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,31 @@
|
||||
import AppKit
|
||||
|
||||
final class LabelItem: NSCollectionViewItem {
|
||||
static var itemIdentifier: NSUserInterfaceItemIdentifier {
|
||||
return NSUserInterfaceItemIdentifier(String(describing: self))
|
||||
}
|
||||
|
||||
let label = NSTextField()
|
||||
|
||||
override func loadView() {
|
||||
view = NSView()
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
label.textColor = .gray
|
||||
label.font = .systemFont(ofSize: 16)
|
||||
label.isEditable = false
|
||||
label.translatesAutoresizingMaskIntoConstraints = false
|
||||
view.addSubview(label)
|
||||
|
||||
let constraints = [
|
||||
label.topAnchor.constraint(equalTo: view.topAnchor),
|
||||
label.bottomAnchor.constraint(equalTo: view.bottomAnchor),
|
||||
label.leadingAnchor.constraint(equalTo: view.leadingAnchor),
|
||||
label.trailingAnchor.constraint(equalTo: view.trailingAnchor)
|
||||
]
|
||||
NSLayoutConstraint.activate(constraints)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,81 @@
|
||||
import AppKit
|
||||
import DiffableDataSources
|
||||
|
||||
final class MountainsViewController: NSViewController {
|
||||
enum Section {
|
||||
case main
|
||||
}
|
||||
|
||||
struct Mountain: Hashable {
|
||||
var name: String
|
||||
|
||||
func contains(_ filter: String) -> Bool {
|
||||
guard !filter.isEmpty else {
|
||||
return true
|
||||
}
|
||||
|
||||
let lowercasedFilter = filter.lowercased()
|
||||
return name.lowercased().contains(lowercasedFilter)
|
||||
}
|
||||
}
|
||||
|
||||
@IBOutlet private var searchField: NSSearchField!
|
||||
@IBOutlet private var collectionView: NSCollectionView!
|
||||
|
||||
private lazy var dataSource = CocoaCollectionViewDiffableDataSource<Section, Mountain>(collectionView: collectionView) { collectionView, indexPath, mountain in
|
||||
let item = collectionView.makeItem(withIdentifier: LabelItem.itemIdentifier, for: indexPath) as! LabelItem
|
||||
item.label.stringValue = mountain.name
|
||||
return item
|
||||
}
|
||||
|
||||
private let allMountains: [Mountain] = mountainsRawData.components(separatedBy: .newlines).map { line in
|
||||
let name = line.components(separatedBy: ",")[0]
|
||||
return Mountain(name: name)
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
title = "Mountains Search"
|
||||
|
||||
collectionView.delegate = self
|
||||
collectionView.register(LabelItem.self, forItemWithIdentifier: LabelItem.itemIdentifier)
|
||||
|
||||
search(filter: "")
|
||||
}
|
||||
|
||||
func search(filter: String) {
|
||||
let mountains = allMountains.lazy
|
||||
.filter { $0.contains(filter) }
|
||||
.sorted { $0.name < $1.name }
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Section, Mountain>()
|
||||
snapshot.appendSections([.main])
|
||||
snapshot.appendItems(mountains)
|
||||
dataSource.apply(snapshot)
|
||||
}
|
||||
|
||||
@IBAction func searchFieldDidChangeText(_ sender: NSSearchField) {
|
||||
search(filter: sender.stringValue)
|
||||
}
|
||||
}
|
||||
|
||||
extension MountainsViewController: NSCollectionViewDelegateFlowLayout {
|
||||
func collectionView(_ collectionView: NSCollectionView, layout collectionViewLayout: NSCollectionViewLayout, minimumInteritemSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 10
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: NSCollectionView, layout collectionViewLayout: NSCollectionViewLayout, minimumLineSpacingForSectionAt section: Int) -> CGFloat {
|
||||
return 10
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: NSCollectionView, layout collectionViewLayout: NSCollectionViewLayout, insetForSectionAt section: Int) -> NSEdgeInsets {
|
||||
return NSEdgeInsets(top: 10, left: 10, bottom: 10, right: 10)
|
||||
}
|
||||
|
||||
func collectionView(_ collectionView: NSCollectionView, layout collectionViewLayout: NSCollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> NSSize {
|
||||
let column = 3
|
||||
let width = (collectionView.bounds.width - 10 * CGFloat(column + 1)) / CGFloat(column)
|
||||
return CGSize(width: width, height: 44)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,391 @@
|
||||
// https://developer.apple.com/documentation/uikit/views_and_controls/collection_views/using_collection_view_compositional_layouts_and_diffable_data_sources
|
||||
|
||||
let mountainsRawData = """
|
||||
Mount Everest,8848
|
||||
K2,8611
|
||||
Kangchenjunga,8586
|
||||
Lhotse,8516
|
||||
Makalu,8485
|
||||
Cho Oyu,8201
|
||||
Dhaulagiri,8167
|
||||
Manaslu,8163
|
||||
Nanga Parbat,8126
|
||||
Annapurna,8091
|
||||
Gasherbrum I,8080
|
||||
Broad Peak,8051
|
||||
Gasherbrum II,8035
|
||||
Shishapangma,8027
|
||||
Gasherbrum III,7952
|
||||
Gyachung Kang,7952
|
||||
Annapurna II,7937
|
||||
Gasherbrum IV,7932
|
||||
Himalchuli,7893
|
||||
Distaghil Sar,7885
|
||||
Ngadi Chuli,7871
|
||||
Nuptse,7861
|
||||
Khunyang Chhish,7852
|
||||
Masherbrum,7821
|
||||
Nanda Devi,7816
|
||||
Chomo Lonzo,7804
|
||||
Batura Sar,7795
|
||||
Kanjut Sar,7790
|
||||
Rakaposhi,7788
|
||||
Namcha Barwa,7782
|
||||
Kamet,7756
|
||||
Saltoro Kangri,7742
|
||||
Jannu,7710
|
||||
Tirich Mir,7708
|
||||
Molamenqing,7703
|
||||
Gurla Mandhata,7694
|
||||
Saser Kangri,7672
|
||||
Chogolisa,7665
|
||||
Kongur Tagh,7649
|
||||
Shispare,7611
|
||||
Silberzacken,7597
|
||||
Changtse,7583
|
||||
Trivor,7577
|
||||
Gangkhar Puensum,7570
|
||||
Gongga Shan,7556
|
||||
Annapurna III,7555
|
||||
Kula Kangri,7554
|
||||
Muztagh Ata,7546
|
||||
Skyang Kangri,7545
|
||||
Liankang Kangri,7535
|
||||
Yukshin Gardan Sar,7530
|
||||
Annapurna IV,7525
|
||||
Mamostong Kangri,7516
|
||||
Ismoil Somoni Peak,7495
|
||||
Noshaq,7492
|
||||
Pumari Chhish,7492
|
||||
Passu Sar,7476
|
||||
Malubiting,7458
|
||||
Gangapurna,7455
|
||||
Muchu Chhish (Batura V),7453
|
||||
Jengish Chokusu,7439
|
||||
K12,7428
|
||||
Sia Kangri,7422
|
||||
Istor-o-Nal,7403
|
||||
Ghent Kangri,7401
|
||||
Haramosh Peak,7397
|
||||
Kabru,7394
|
||||
Ultar,7388
|
||||
Rimo I,7385
|
||||
Sherpi Kangri,7380
|
||||
Labuche Kang,7367
|
||||
Kirat Chuli,7365
|
||||
Skil Brum,7360
|
||||
Gimmigela Chuli,7350
|
||||
Bojohagur Duanasir,7329
|
||||
Chamlang,7319
|
||||
Jomolhari / Chomolhari,7314
|
||||
Baltoro Kangri,7312
|
||||
Siguang Ri,7308
|
||||
The Crown,7295
|
||||
Gyala Peri,7294
|
||||
Porong Ri,7292
|
||||
Baintha Brakk,7285
|
||||
Yutmaru Sar,7283
|
||||
K6,7282
|
||||
Kangpenqing,7281
|
||||
Mana Peak,7272
|
||||
Muztagh Tower,7273
|
||||
Diran,7257
|
||||
Apsarasas Kangri,7245
|
||||
Langtang Lirung,7227
|
||||
Khartaphu,7213
|
||||
Tongshanjiabu,7207
|
||||
Langtang Ri,7205
|
||||
Kangphu Kang,7204
|
||||
Annapurna South,7219
|
||||
Melungtse,7181
|
||||
Liushi Shan,7167
|
||||
Baruntse,7162
|
||||
Pumori,7161
|
||||
Hardeol,7151
|
||||
Gasherbrum V,7147
|
||||
Latok I,7145
|
||||
Nemjung,7140
|
||||
Udren Zom,7140
|
||||
Chaukhamba,7138
|
||||
Nun Kun,7135
|
||||
Tilicho Peak,7134
|
||||
Gauri Sankar,7134
|
||||
Lenin Peak,7134
|
||||
Api,7132
|
||||
Pauhunri,7128
|
||||
Trisul,7120
|
||||
Korzhenevskaya,7105
|
||||
Lunpo Gangri,7095
|
||||
Satopanth,7075
|
||||
Tirsuli,7074
|
||||
Dunagiri,7066
|
||||
Kangto,7060
|
||||
Nyegyi Kansang,7047
|
||||
Link Sar,7041
|
||||
Kezhen Peak,7038
|
||||
Shah Dhar,7038
|
||||
Spantik,7027
|
||||
Khan Tengri,7010
|
||||
Machapuchare,6993
|
||||
Laila Peak (Haramosh Valley),6985
|
||||
Kang Guru,6981
|
||||
Gasherbrum VI,6979
|
||||
Karun Kuh,6977
|
||||
Avicenna Peak,6974
|
||||
Ulugh Muztagh,6973
|
||||
Aconcagua,6962
|
||||
Napko Kangri,6956
|
||||
Kedarnath,6940
|
||||
K7,6934
|
||||
Panchchuli,6904
|
||||
Thalay Sagar,6904
|
||||
Lunkho e Dosare,6901
|
||||
Lunag Ri,6895
|
||||
Ojos del Salado,6891
|
||||
Siniolchu,6888
|
||||
Kanjiroba,6883
|
||||
Bairiga,6882
|
||||
Koyo Zom,6872
|
||||
Nanda Kot,6861
|
||||
Kubi Gangri,6859
|
||||
Angel Sar,6858
|
||||
Bhagirathi I,6856
|
||||
Jethi Bahurani,6850
|
||||
Chongra Peak,6830
|
||||
Reo Purgyil,6816
|
||||
Ama Dablam,6812
|
||||
Monte Pissis,6795
|
||||
Biarchedi,6781
|
||||
Huascarán Sur,6768
|
||||
Cerro Bonete,6759
|
||||
Nevado Tres Cruces,6748
|
||||
Kawagarbo,6740
|
||||
Llullaillaco,6739
|
||||
Cho Polu,6735
|
||||
Kangju Kangri,6725
|
||||
Changla,6721
|
||||
Mercedario,6720
|
||||
Mount Pandim,6691
|
||||
Num Ri,6677
|
||||
Lungser Kangri,6666
|
||||
Meru Peak,6660
|
||||
Gul Lasht Zom,6657
|
||||
Huascarán Norte,6655
|
||||
Khumbutse,6640
|
||||
Mount Kailash,6638
|
||||
Yerupajá,6635
|
||||
Nevado Tres Cruces Central,6629
|
||||
Thamserku,6623
|
||||
Geladaindong Peak,6621
|
||||
Incahuasi,6621
|
||||
Pangpoche,6620
|
||||
Manirang,6597
|
||||
Nilkantha,6596
|
||||
Phuparash Peak,6574
|
||||
Sickle Moon Peak,6574
|
||||
Buni Zom,6542
|
||||
Nevado Sajama,6542
|
||||
Ghamubar Zom,6518
|
||||
Singu Chuli,6501
|
||||
Taboche,6501
|
||||
Cerro El Muerto,6488
|
||||
Mera Peak,6476
|
||||
Hiunchuli,6441
|
||||
Cholatse,6440
|
||||
Illimani,6438
|
||||
Ancohuma,6427
|
||||
Coropuna,6425
|
||||
Antofalla,6409
|
||||
Kang Yatze,6400
|
||||
Huandoy,6395
|
||||
Ausangate,6384
|
||||
Illampu,6368
|
||||
Kusum Kangguru,6367
|
||||
Kinnaur Kailash,6349
|
||||
Parinaquta,6348
|
||||
Siula Grande,6344
|
||||
Bamba Dhura,6334
|
||||
Ampato,6288
|
||||
Amne Machin,6282
|
||||
Pomerape,6282
|
||||
Salcantay,6271
|
||||
Chimborazo,6267
|
||||
Mount Siguniang,6250
|
||||
Grid Nie Mountain,6224
|
||||
Yuzhu Peak,6224
|
||||
Genyen Massif,6204
|
||||
Kongde Ri,6187
|
||||
Aucanquilcha,6176
|
||||
Imja Tse,6189
|
||||
Denali (Mt. McKinley),6168
|
||||
Stok Kangri,6137
|
||||
Lobuche,6119
|
||||
Marmolejo,6108
|
||||
Laila Peak (Hushe Valley),6096
|
||||
Pisang Peak,6091
|
||||
Huayna Potosí,6088
|
||||
Aracar,6082
|
||||
Chachakumani,6074
|
||||
Chachani,6057
|
||||
Mianzimu,6054
|
||||
Acotango,6052
|
||||
Socompa,6051
|
||||
Acamarachi,6046
|
||||
Shayaz,6026
|
||||
Hualca Hualca,6025
|
||||
Uturunku,6020
|
||||
Mitre Peak,6010
|
||||
Laila Peak,5971
|
||||
Mount Logan,5959
|
||||
Alpamayo,5947
|
||||
Cerro Lípez,5929
|
||||
Licancabur,5920
|
||||
Falak Sar,5918
|
||||
Cotopaxi,5897
|
||||
Mount Kilimanjaro,5895
|
||||
Hkakabo Razi,5881
|
||||
San José,5856
|
||||
El Misti,5822
|
||||
Altun Shan,5798
|
||||
Cayambe,5790
|
||||
Pico Cristóbal Colón,5776
|
||||
Antisana,5753
|
||||
Nevado Pisco,5752
|
||||
Nevado Anallajsi,5750
|
||||
Pokalde,5745
|
||||
Ubinas,5672
|
||||
Pichu Pichu,5664
|
||||
Mount Elbrus,5642
|
||||
Mehrbani Peak,5639
|
||||
Pico de Orizaba,5636
|
||||
Mount Damavand,5610
|
||||
Nevado Mismi,5597
|
||||
Jade Dragon Snow Mountain,5596
|
||||
Lascar Volcano,5592
|
||||
Mount Xuebaoding,5588
|
||||
Kala Patthar,5545
|
||||
Mount Saint Elias,5489
|
||||
Concord Peak,5469
|
||||
Machoi Peak,5458
|
||||
El Plomo,5450
|
||||
Bogda Feng,5445
|
||||
Mount Little Xuebaoding,5443
|
||||
Cerro El Plomo,5434
|
||||
Popocatépetl,5426
|
||||
Kolahoi Peak,5425
|
||||
Chacaltaya,5421
|
||||
Mount Pomiu,5413
|
||||
Ritacuba Blanco,5410
|
||||
Haba Xueshan,5396
|
||||
Nevado del Ruiz,5389
|
||||
Nevado del Huila,5364
|
||||
El Altar,5320
|
||||
Mount Foraker,5304
|
||||
Mount Haramukh,5300
|
||||
Nevado del Tolima,5276
|
||||
Maipo,5264
|
||||
Illiniza,5248
|
||||
Sirbal Peak,5236
|
||||
Sangay,5230
|
||||
Iztaccíhuatl,5230
|
||||
Mount Lucania,5226
|
||||
Dykh-Tau,5205
|
||||
Shkhara,5201
|
||||
Mount Kenya,5199
|
||||
Malika Parbat,5190
|
||||
Amarnath Peak,5186
|
||||
King Peak,5173
|
||||
Boris Yeltsin Peak,5168
|
||||
Koshtan-Tau,5150
|
||||
Mount Ararat,5137
|
||||
Mount Stanley,5109
|
||||
Mount Steele,5073
|
||||
Janga,5051
|
||||
Mount Kazbek,5047
|
||||
Tungurahua,5023
|
||||
Carihuairazo,5018
|
||||
Mount Bona,5005
|
||||
Mount Blackburn,4996
|
||||
Pico Bolívar,4981
|
||||
Pik Talgar,4979
|
||||
Shota Rustaveli Peak,4960
|
||||
Gunshar,4950
|
||||
Mount Sanford,4949
|
||||
Pico Humboldt,4940
|
||||
Vinson Massif,4892
|
||||
Pico Bonpland,4890
|
||||
Puncak Jaya,4884
|
||||
Pico La Concha,4870
|
||||
Gistola,4860
|
||||
Tetnuldi,4858
|
||||
Mount Tyree,4852
|
||||
Huaynaputina,4850
|
||||
Alam Kuh,4850
|
||||
Mount Wood,4842
|
||||
Mount Vancouver,4812
|
||||
Sabalan,4811
|
||||
Mont Blanc,4810
|
||||
Corazón,4790
|
||||
Pichincha,4784
|
||||
Jimara,4780
|
||||
Mount Churchill,4766
|
||||
Puncak Mandala,4760
|
||||
Klyuchevskaya Sopka,4750
|
||||
Puncak Trikora,4750
|
||||
Mont Blanc de Courmayeur,4748
|
||||
Sunset Peak,4745
|
||||
Mount Slaggard,4742
|
||||
Pico Piedras Blancas,4740
|
||||
Pico El Toro,4730
|
||||
Tatakooti Peak,4725
|
||||
Rumiñahui,4721
|
||||
Pico El Leon,4720
|
||||
Ushba,4710
|
||||
Volcán Domuyo,4709
|
||||
Pico Los Nevados,4700
|
||||
Pico Pan de Azucar,4680
|
||||
Naltar Peak,4678
|
||||
Mount Fairweather,4663
|
||||
Pico Mucuñuque,4660
|
||||
Pico El Buitre,4650
|
||||
Khazret Sultan,4643
|
||||
Sierra Negra,4640
|
||||
Dufourspitze (Monte Rosa),4634
|
||||
Dunantspitze (Monte Rosa),4632
|
||||
Nordend (Monte Rosa),4609
|
||||
Mount Hubbard,4577
|
||||
Nevado de Toluca,4577
|
||||
Mount Meru,4566
|
||||
Zumsteinspitze (Monte Rosa),4563
|
||||
Signalkuppe (Monte Rosa),4554
|
||||
Dom,4545
|
||||
Ras Dashen,4533
|
||||
Eastern Liskamm (Lyskamm),4527
|
||||
Mount Bear,4521
|
||||
Mount Wilhelm,4509
|
||||
Mount Karisimbi,4507
|
||||
Mount Walsh,4507
|
||||
Belukha Mountain,4506
|
||||
Weisshorn,4506
|
||||
Tebulosmta,4493
|
||||
Täschhorn,4491
|
||||
Bazarduzu Dagi,4485
|
||||
Matterhorn,4478
|
||||
Mount Rutford,4477
|
||||
Mont Maudit,4465
|
||||
Babis Mta,4454
|
||||
Mount Shani,4451
|
||||
Dena,4448
|
||||
Vladimir Putin Peak,4446
|
||||
Mount Hunter,4442
|
||||
Parrotspitze (Monte Rosa),4432
|
||||
Mount Whitney,4421
|
||||
Mount Alverstone,4420
|
||||
University Peak,4411
|
||||
Aello Peak,4403
|
||||
Mount Elbert,4402
|
||||
Mount Massive,4395
|
||||
Mount Harvard,4395
|
||||
Mount Rainier,4392
|
||||
Kholeno,4387
|
||||
"""
|
||||
@@ -0,0 +1,10 @@
|
||||
<H1 align="center">
|
||||
DiffableDataSources Examples
|
||||
</H1>
|
||||
|
||||
## How to Run
|
||||
|
||||
1. Clone the DiffableDataSources repository.
|
||||
1. Checkout the dependencies using terminal command `$ make setup` at the project root directory.
|
||||
1. Open example project workspace.
|
||||
1. Run.
|
||||
@@ -0,0 +1,4 @@
|
||||
source "https://rubygems.org"
|
||||
|
||||
gem 'cocoapods', '1.7.2'
|
||||
gem 'jazzy', '0.9.4'
|
||||
@@ -0,0 +1,103 @@
|
||||
GEM
|
||||
remote: https://rubygems.org/
|
||||
specs:
|
||||
CFPropertyList (3.0.0)
|
||||
activesupport (4.2.11.1)
|
||||
i18n (~> 0.7)
|
||||
minitest (~> 5.1)
|
||||
thread_safe (~> 0.3, >= 0.3.4)
|
||||
tzinfo (~> 1.1)
|
||||
atomos (0.1.3)
|
||||
claide (1.0.2)
|
||||
cocoapods (1.7.2)
|
||||
activesupport (>= 4.0.2, < 5)
|
||||
claide (>= 1.0.2, < 2.0)
|
||||
cocoapods-core (= 1.7.2)
|
||||
cocoapods-deintegrate (>= 1.0.3, < 2.0)
|
||||
cocoapods-downloader (>= 1.2.2, < 2.0)
|
||||
cocoapods-plugins (>= 1.0.0, < 2.0)
|
||||
cocoapods-search (>= 1.0.0, < 2.0)
|
||||
cocoapods-stats (>= 1.0.0, < 2.0)
|
||||
cocoapods-trunk (>= 1.3.1, < 2.0)
|
||||
cocoapods-try (>= 1.1.0, < 2.0)
|
||||
colored2 (~> 3.1)
|
||||
escape (~> 0.0.4)
|
||||
fourflusher (>= 2.3.0, < 3.0)
|
||||
gh_inspector (~> 1.0)
|
||||
molinillo (~> 0.6.6)
|
||||
nap (~> 1.0)
|
||||
ruby-macho (~> 1.4)
|
||||
xcodeproj (>= 1.10.0, < 2.0)
|
||||
cocoapods-core (1.7.2)
|
||||
activesupport (>= 4.0.2, < 6)
|
||||
fuzzy_match (~> 2.0.4)
|
||||
nap (~> 1.0)
|
||||
cocoapods-deintegrate (1.0.4)
|
||||
cocoapods-downloader (1.2.2)
|
||||
cocoapods-plugins (1.0.0)
|
||||
nap
|
||||
cocoapods-search (1.0.0)
|
||||
cocoapods-stats (1.1.0)
|
||||
cocoapods-trunk (1.3.1)
|
||||
nap (>= 0.8, < 2.0)
|
||||
netrc (~> 0.11)
|
||||
cocoapods-try (1.1.0)
|
||||
colored2 (3.1.2)
|
||||
concurrent-ruby (1.1.5)
|
||||
escape (0.0.4)
|
||||
ffi (1.11.1)
|
||||
fourflusher (2.3.0)
|
||||
fuzzy_match (2.0.4)
|
||||
gh_inspector (1.1.3)
|
||||
i18n (0.9.5)
|
||||
concurrent-ruby (~> 1.0)
|
||||
jazzy (0.9.4)
|
||||
cocoapods (~> 1.0)
|
||||
mustache (~> 0.99)
|
||||
open4
|
||||
redcarpet (~> 3.2)
|
||||
rouge (>= 2.0.6, < 4.0)
|
||||
sass (~> 3.4)
|
||||
sqlite3 (~> 1.3)
|
||||
xcinvoke (~> 0.3.0)
|
||||
liferaft (0.0.6)
|
||||
minitest (5.11.3)
|
||||
molinillo (0.6.6)
|
||||
mustache (0.99.8)
|
||||
nanaimo (0.2.6)
|
||||
nap (1.1.0)
|
||||
netrc (0.11.0)
|
||||
open4 (1.3.4)
|
||||
rb-fsevent (0.10.3)
|
||||
rb-inotify (0.10.0)
|
||||
ffi (~> 1.0)
|
||||
redcarpet (3.4.0)
|
||||
rouge (3.4.1)
|
||||
ruby-macho (1.4.0)
|
||||
sass (3.7.4)
|
||||
sass-listen (~> 4.0.0)
|
||||
sass-listen (4.0.0)
|
||||
rb-fsevent (~> 0.9, >= 0.9.4)
|
||||
rb-inotify (~> 0.9, >= 0.9.7)
|
||||
sqlite3 (1.4.1)
|
||||
thread_safe (0.3.6)
|
||||
tzinfo (1.2.5)
|
||||
thread_safe (~> 0.1)
|
||||
xcinvoke (0.3.0)
|
||||
liferaft (~> 0.0.6)
|
||||
xcodeproj (1.10.0)
|
||||
CFPropertyList (>= 2.3.3, < 4.0)
|
||||
atomos (~> 0.1.3)
|
||||
claide (>= 1.0.2, < 2.0)
|
||||
colored2 (~> 3.1)
|
||||
nanaimo (~> 0.2.6)
|
||||
|
||||
PLATFORMS
|
||||
ruby
|
||||
|
||||
DEPENDENCIES
|
||||
cocoapods (= 1.7.2)
|
||||
jazzy (= 0.9.4)
|
||||
|
||||
BUNDLED WITH
|
||||
2.0.1
|
||||
@@ -0,0 +1,201 @@
|
||||
Apache License
|
||||
Version 2.0, January 2004
|
||||
http://www.apache.org/licenses/
|
||||
|
||||
TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION
|
||||
|
||||
1. Definitions.
|
||||
|
||||
"License" shall mean the terms and conditions for use, reproduction,
|
||||
and distribution as defined by Sections 1 through 9 of this document.
|
||||
|
||||
"Licensor" shall mean the copyright owner or entity authorized by
|
||||
the copyright owner that is granting the License.
|
||||
|
||||
"Legal Entity" shall mean the union of the acting entity and all
|
||||
other entities that control, are controlled by, or are under common
|
||||
control with that entity. For the purposes of this definition,
|
||||
"control" means (i) the power, direct or indirect, to cause the
|
||||
direction or management of such entity, whether by contract or
|
||||
otherwise, or (ii) ownership of fifty percent (50%) or more of the
|
||||
outstanding shares, or (iii) beneficial ownership of such entity.
|
||||
|
||||
"You" (or "Your") shall mean an individual or Legal Entity
|
||||
exercising permissions granted by this License.
|
||||
|
||||
"Source" form shall mean the preferred form for making modifications,
|
||||
including but not limited to software source code, documentation
|
||||
source, and configuration files.
|
||||
|
||||
"Object" form shall mean any form resulting from mechanical
|
||||
transformation or translation of a Source form, including but
|
||||
not limited to compiled object code, generated documentation,
|
||||
and conversions to other media types.
|
||||
|
||||
"Work" shall mean the work of authorship, whether in Source or
|
||||
Object form, made available under the License, as indicated by a
|
||||
copyright notice that is included in or attached to the work
|
||||
(an example is provided in the Appendix below).
|
||||
|
||||
"Derivative Works" shall mean any work, whether in Source or Object
|
||||
form, that is based on (or derived from) the Work and for which the
|
||||
editorial revisions, annotations, elaborations, or other modifications
|
||||
represent, as a whole, an original work of authorship. For the purposes
|
||||
of this License, Derivative Works shall not include works that remain
|
||||
separable from, or merely link (or bind by name) to the interfaces of,
|
||||
the Work and Derivative Works thereof.
|
||||
|
||||
"Contribution" shall mean any work of authorship, including
|
||||
the original version of the Work and any modifications or additions
|
||||
to that Work or Derivative Works thereof, that is intentionally
|
||||
submitted to Licensor for inclusion in the Work by the copyright owner
|
||||
or by an individual or Legal Entity authorized to submit on behalf of
|
||||
the copyright owner. For the purposes of this definition, "submitted"
|
||||
means any form of electronic, verbal, or written communication sent
|
||||
to the Licensor or its representatives, including but not limited to
|
||||
communication on electronic mailing lists, source code control systems,
|
||||
and issue tracking systems that are managed by, or on behalf of, the
|
||||
Licensor for the purpose of discussing and improving the Work, but
|
||||
excluding communication that is conspicuously marked or otherwise
|
||||
designated in writing by the copyright owner as "Not a Contribution."
|
||||
|
||||
"Contributor" shall mean Licensor and any individual or Legal Entity
|
||||
on behalf of whom a Contribution has been received by Licensor and
|
||||
subsequently incorporated within the Work.
|
||||
|
||||
2. Grant of Copyright License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
copyright license to reproduce, prepare Derivative Works of,
|
||||
publicly display, publicly perform, sublicense, and distribute the
|
||||
Work and such Derivative Works in Source or Object form.
|
||||
|
||||
3. Grant of Patent License. Subject to the terms and conditions of
|
||||
this License, each Contributor hereby grants to You a perpetual,
|
||||
worldwide, non-exclusive, no-charge, royalty-free, irrevocable
|
||||
(except as stated in this section) patent license to make, have made,
|
||||
use, offer to sell, sell, import, and otherwise transfer the Work,
|
||||
where such license applies only to those patent claims licensable
|
||||
by such Contributor that are necessarily infringed by their
|
||||
Contribution(s) alone or by combination of their Contribution(s)
|
||||
with the Work to which such Contribution(s) was submitted. If You
|
||||
institute patent litigation against any entity (including a
|
||||
cross-claim or counterclaim in a lawsuit) alleging that the Work
|
||||
or a Contribution incorporated within the Work constitutes direct
|
||||
or contributory patent infringement, then any patent licenses
|
||||
granted to You under this License for that Work shall terminate
|
||||
as of the date such litigation is filed.
|
||||
|
||||
4. Redistribution. You may reproduce and distribute copies of the
|
||||
Work or Derivative Works thereof in any medium, with or without
|
||||
modifications, and in Source or Object form, provided that You
|
||||
meet the following conditions:
|
||||
|
||||
(a) You must give any other recipients of the Work or
|
||||
Derivative Works a copy of this License; and
|
||||
|
||||
(b) You must cause any modified files to carry prominent notices
|
||||
stating that You changed the files; and
|
||||
|
||||
(c) You must retain, in the Source form of any Derivative Works
|
||||
that You distribute, all copyright, patent, trademark, and
|
||||
attribution notices from the Source form of the Work,
|
||||
excluding those notices that do not pertain to any part of
|
||||
the Derivative Works; and
|
||||
|
||||
(d) If the Work includes a "NOTICE" text file as part of its
|
||||
distribution, then any Derivative Works that You distribute must
|
||||
include a readable copy of the attribution notices contained
|
||||
within such NOTICE file, excluding those notices that do not
|
||||
pertain to any part of the Derivative Works, in at least one
|
||||
of the following places: within a NOTICE text file distributed
|
||||
as part of the Derivative Works; within the Source form or
|
||||
documentation, if provided along with the Derivative Works; or,
|
||||
within a display generated by the Derivative Works, if and
|
||||
wherever such third-party notices normally appear. The contents
|
||||
of the NOTICE file are for informational purposes only and
|
||||
do not modify the License. You may add Your own attribution
|
||||
notices within Derivative Works that You distribute, alongside
|
||||
or as an addendum to the NOTICE text from the Work, provided
|
||||
that such additional attribution notices cannot be construed
|
||||
as modifying the License.
|
||||
|
||||
You may add Your own copyright statement to Your modifications and
|
||||
may provide additional or different license terms and conditions
|
||||
for use, reproduction, or distribution of Your modifications, or
|
||||
for any such Derivative Works as a whole, provided Your use,
|
||||
reproduction, and distribution of the Work otherwise complies with
|
||||
the conditions stated in this License.
|
||||
|
||||
5. Submission of Contributions. Unless You explicitly state otherwise,
|
||||
any Contribution intentionally submitted for inclusion in the Work
|
||||
by You to the Licensor shall be under the terms and conditions of
|
||||
this License, without any additional terms or conditions.
|
||||
Notwithstanding the above, nothing herein shall supersede or modify
|
||||
the terms of any separate license agreement you may have executed
|
||||
with Licensor regarding such Contributions.
|
||||
|
||||
6. Trademarks. This License does not grant permission to use the trade
|
||||
names, trademarks, service marks, or product names of the Licensor,
|
||||
except as required for reasonable and customary use in describing the
|
||||
origin of the Work and reproducing the content of the NOTICE file.
|
||||
|
||||
7. Disclaimer of Warranty. Unless required by applicable law or
|
||||
agreed to in writing, Licensor provides the Work (and each
|
||||
Contributor provides its Contributions) on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
|
||||
implied, including, without limitation, any warranties or conditions
|
||||
of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A
|
||||
PARTICULAR PURPOSE. You are solely responsible for determining the
|
||||
appropriateness of using or redistributing the Work and assume any
|
||||
risks associated with Your exercise of permissions under this License.
|
||||
|
||||
8. Limitation of Liability. In no event and under no legal theory,
|
||||
whether in tort (including negligence), contract, or otherwise,
|
||||
unless required by applicable law (such as deliberate and grossly
|
||||
negligent acts) or agreed to in writing, shall any Contributor be
|
||||
liable to You for damages, including any direct, indirect, special,
|
||||
incidental, or consequential damages of any character arising as a
|
||||
result of this License or out of the use or inability to use the
|
||||
Work (including but not limited to damages for loss of goodwill,
|
||||
work stoppage, computer failure or malfunction, or any and all
|
||||
other commercial damages or losses), even if such Contributor
|
||||
has been advised of the possibility of such damages.
|
||||
|
||||
9. Accepting Warranty or Additional Liability. While redistributing
|
||||
the Work or Derivative Works thereof, You may choose to offer,
|
||||
and charge a fee for, acceptance of support, warranty, indemnity,
|
||||
or other liability obligations and/or rights consistent with this
|
||||
License. However, in accepting such obligations, You may act only
|
||||
on Your own behalf and on Your sole responsibility, not on behalf
|
||||
of any other Contributor, and only if You agree to indemnify,
|
||||
defend, and hold each Contributor harmless for any liability
|
||||
incurred by, or claims asserted against, such Contributor by reason
|
||||
of your accepting any such warranty or additional liability.
|
||||
|
||||
END OF TERMS AND CONDITIONS
|
||||
|
||||
APPENDIX: How to apply the Apache License to your work.
|
||||
|
||||
To apply the Apache License to your work, attach the following
|
||||
boilerplate notice, with the fields enclosed by brackets "[]"
|
||||
replaced with your own identifying information. (Don't include
|
||||
the brackets!) The text should be enclosed in the appropriate
|
||||
comment syntax for the file format. We also recommend that a
|
||||
file or class name and description of purpose be included on the
|
||||
same "printed page" as the copyright notice for easier
|
||||
identification within third-party archives.
|
||||
|
||||
Copyright [yyyy] [name of copyright owner]
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
@@ -0,0 +1,17 @@
|
||||
setup:
|
||||
git submodule update --init --recursive
|
||||
|
||||
carthage-submodule:
|
||||
carthage update --no-build --use-submodules
|
||||
|
||||
gems-install:
|
||||
bundle install --path vendor/bundle
|
||||
|
||||
docs-gen:
|
||||
bundle exec jazzy --config .jazzy.yml
|
||||
|
||||
lib-lint:
|
||||
bundle exec pod lib lint
|
||||
|
||||
pod-release:
|
||||
bundle exec pod trunk push --allow-warnings
|
||||
@@ -0,0 +1,16 @@
|
||||
{
|
||||
"object": {
|
||||
"pins": [
|
||||
{
|
||||
"package": "DifferenceKit",
|
||||
"repositoryURL": "https://github.com/ra1028/DifferenceKit.git",
|
||||
"state": {
|
||||
"branch": null,
|
||||
"revision": "4eb31f8e85e4cb13732f9664d6e01e507cd592a0",
|
||||
"version": "1.1.3"
|
||||
}
|
||||
}
|
||||
]
|
||||
},
|
||||
"version": 1
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
// swift-tools-version:5.0
|
||||
|
||||
import PackageDescription
|
||||
|
||||
let package = Package(
|
||||
name: "DiffableDataSources",
|
||||
platforms: [
|
||||
.iOS(.v9), .macOS(.v10_11), .tvOS(.v9)
|
||||
],
|
||||
products: [
|
||||
.library(name: "DiffableDataSources", targets: ["DiffableDataSources"])
|
||||
],
|
||||
dependencies: [
|
||||
.package(url: "https://github.com/ra1028/DifferenceKit.git", .upToNextMinor(from: "1.1.0"))
|
||||
],
|
||||
targets: [
|
||||
.target(
|
||||
name: "DiffableDataSources",
|
||||
dependencies: ["DifferenceKit"],
|
||||
path: "Sources"
|
||||
),
|
||||
.testTarget(
|
||||
name: "DiffableDataSourcesTests",
|
||||
dependencies: ["DiffableDataSources"],
|
||||
path: "Tests"
|
||||
)
|
||||
],
|
||||
swiftLanguageVersions: [.v5]
|
||||
)
|
||||
@@ -0,0 +1,208 @@
|
||||
<H1 align="center">
|
||||
DiffableDataSources
|
||||
</H1>
|
||||
<H4 align="center">
|
||||
💾 A library for backporting UITableView/UICollectionViewDiffableDataSource</br>
|
||||
powered by <a href="https://github.com/ra1028/DifferenceKit">DifferenceKit</a>.
|
||||
</H4>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://developer.apple.com/swift"><img alt="Swift5" src="https://img.shields.io/badge/language-Swift5-orange.svg"/></a>
|
||||
<a href="https://github.com/ra1028/DiffableDataSources/releases/latest"><img alt="Release" src="https://img.shields.io/github/release/ra1028/DiffableDataSources.svg"/></a>
|
||||
<a href="https://cocoapods.org/pods/DiffableDataSources"><img alt="CocoaPods" src="https://img.shields.io/cocoapods/v/DiffableDataSources.svg"/></a>
|
||||
<a href="https://github.com/Carthage/Carthage"><img alt="Carthage" src="https://img.shields.io/badge/carthage-compatible-yellow.svg"/></a>
|
||||
<a href="https://swift.org/package-manager"><img alt="Swift Package Manager" src="https://img.shields.io/badge/SwiftPM-compatible-yellowgreen.svg"/></a>
|
||||
</br>
|
||||
<a href="https://dev.azure.com/ra1028/GitHub/_build/latest?definitionId=3&branchName=master"><img alt="Build Status" src="https://dev.azure.com/ra1028/GitHub/_apis/build/status/ra1028.DiffableDataSources?branchName=master"/></a>
|
||||
<a href="https://developer.apple.com/"><img alt="Platform" src="https://img.shields.io/badge/platform-iOS%20%7C%20macOS%20%7C%20tvOS-green.svg"/></a>
|
||||
<a href="https://github.com/ra1028/DiffableDataSources/blob/master/LICENSE"><img alt="Lincense" src="https://img.shields.io/badge/License-Apache%202.0-black.svg"/></a>
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
Made with ❤️ by <a href="https://github.com/ra1028">Ryo Aoyama</a>
|
||||
</p>
|
||||
|
||||
---
|
||||
|
||||
## Introduction
|
||||
|
||||
<img src="https://raw.githubusercontent.com/ra1028/DiffableDataSources/master/assets/insertion_sort.gif" height="400" align="right">
|
||||
<img src="https://raw.githubusercontent.com/ra1028/DiffableDataSources/master/assets/mountains.gif" height="400" align="right">
|
||||
|
||||
Apple has announced a diffable data source at WWDC 2019.
|
||||
It's a great API that easily updating our table view and collection view items using automatic diffing.
|
||||
However, it's a little while before we can use it in a production service.
|
||||
That because it requires the latest OS to use.
|
||||
DiffableDataSources make it possible to introduce almost the same functionality from now on.
|
||||
|
||||
Uses a sophisticated open source [DifferenceKit](https://github.com/ra1028/DifferenceKit) for the algorithm engine.
|
||||
It's extremely fast and completely avoids synchronization bugs, exceptions, and crashes.
|
||||
|
||||
<br clear="all">
|
||||
|
||||
---
|
||||
|
||||
## Difference from the Official
|
||||
|
||||
#### Spec
|
||||
|
||||
- Supports iOS 9.0+ / macOS 10.11+ / tvOS 9.0+
|
||||
- Open sourced algorithm.
|
||||
- Duplicate sections or items are allowed.
|
||||
- Using `performBatchUpdates` for diffing updates.
|
||||
|
||||
#### Namings
|
||||
|
||||
`DiffableDataSources` have different class names to avoid conflicts with the official API.
|
||||
Correspondence table is below.
|
||||
|
||||
|Official |Backported |
|
||||
|:---------------------------------------------------------------------------|:------------------------------------|
|
||||
|[NSDiffableDataSourceSnapshot][NSDiffableDataSourceSnapshot_doc] |DiffableDataSourceSnapshot |
|
||||
|[UITableViewDiffableDataSource][UITableViewDiffableDataSource_doc] |TableViewDiffableDataSource |
|
||||
|[UICollectionViewDiffableDataSource][UICollectionViewDiffableDataSource_doc]|CollectionViewDiffableDataSource |
|
||||
|[NSCollectionViewDiffableDataSource][NSCollectionViewDiffableDataSource_doc]|CocoaCollectionViewDiffableDataSource|
|
||||
|
||||
[NSDiffableDataSourceSnapshot_doc]: https://developer.apple.com/documentation/uikit/uitableviewdiffabledatasource
|
||||
[UITableViewDiffableDataSource_doc]: https://developer.apple.com/documentation/uikit/uitableviewdiffabledatasource
|
||||
[UICollectionViewDiffableDataSource_doc]: https://developer.apple.com/documentation/uikit/uicollectionviewdiffabledatasource
|
||||
[NSCollectionViewDiffableDataSource_doc]: https://developer.apple.com/documentation/appkit/nscollectionviewdiffabledatasource
|
||||
|
||||
---
|
||||
|
||||
## Getting Started
|
||||
|
||||
- [API Documentation](https://ra1028.github.io/DiffableDataSources)
|
||||
- [Example Apps](https://github.com/ra1028/DiffableDataSources/tree/master/Examples)
|
||||
- [WWDC 2019 Session](https://developer.apple.com/videos/play/wwdc2019/220)
|
||||
|
||||
#### Build Project
|
||||
|
||||
```sh
|
||||
$ git clone https://github.com/ra1028/DiffableDataSources.git
|
||||
$ cd DiffableDataSources/
|
||||
$ make setup
|
||||
$ open DiffableDataSources.xcworkspace
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Basic Usage
|
||||
|
||||
First, define the type representing section.
|
||||
It should conforms to `Hashable` for identifies from the all sections.
|
||||
Type of enum can used conveniently befause it conforms `Hashable` by default.
|
||||
|
||||
```swift
|
||||
enum Section {
|
||||
case main
|
||||
}
|
||||
```
|
||||
|
||||
Then, define the item type conforms to `Hashable`.
|
||||
|
||||
```swift
|
||||
struct User: Hashable {
|
||||
var name: String
|
||||
}
|
||||
```
|
||||
|
||||
Create a data source object, it will be set to table view automatically.
|
||||
You should dequeue the non nil cells via closure.
|
||||
|
||||
```swift
|
||||
final class UsersViewController: UIViewController {
|
||||
let tableView: UITableView = ...
|
||||
|
||||
lazy var dataSource = TableViewDiffableDataSource<Section, User>(tableView: tableView) { tableView, indexPath, user in
|
||||
let cell = tableView.dequeueReusableCell(withIdentifier: "Cell", for: indexPath)
|
||||
cell.textLabel?.text = user.name
|
||||
return cell
|
||||
}
|
||||
|
||||
override func viewDidLoad() {
|
||||
super.viewDidLoad()
|
||||
|
||||
tableView.register(UITableViewCell.self, forCellReuseIdentifier: "Cell")
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
Manages and updates the data sources intuitively by intermediating `DiffableDataSourceSnapshot`.
|
||||
The UI isn't updated until you apply the edited snapshot object.
|
||||
Update the UI with diffing animation automatically calculated by applying an edited snapshot.
|
||||
|
||||
```swift
|
||||
let users = [
|
||||
User(name: "Steve Jobs"),
|
||||
User(name: "Stephen Wozniak"),
|
||||
User(name: "Tim Cook"),
|
||||
User(name: "Jonathan Ive")
|
||||
]
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Section, User>()
|
||||
snapshot.appendSections([.main])
|
||||
snapshot.appendItems(users)
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
```
|
||||
|
||||
Check the documentation for more detailed API.
|
||||
|
||||
<H3 align="center">
|
||||
<a href="https://ra1028.github.io/DiffableDataSources">[See More Usage]</a>
|
||||
</H3>
|
||||
|
||||
---
|
||||
|
||||
## Requirements
|
||||
|
||||
- Swift 5.0+
|
||||
- iOS 9.0+
|
||||
- macOS 10.11+
|
||||
- tvOS 9.0+
|
||||
|
||||
---
|
||||
|
||||
## Installation
|
||||
|
||||
### [CocoaPods](https://cocoapods.org)
|
||||
Add the following to your `Podfile`:
|
||||
```ruby
|
||||
pod 'DiffableDataSources'
|
||||
```
|
||||
|
||||
### [Carthage](https://github.com/Carthage/Carthage)
|
||||
Add the following to your `Cartfile`:
|
||||
```
|
||||
github "ra1028/DiffableDataSources"
|
||||
```
|
||||
|
||||
### [Swift Package Manager](https://swift.org/package-manager/)
|
||||
Add the following to the dependencies of your `Package.swift`:
|
||||
```swift
|
||||
.package(url: "https://github.com/ra1028/DiffableDataSources.git", from: "x.x.x")
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
## Contributing
|
||||
|
||||
Pull requests, bug reports and feature requests are welcome 🚀
|
||||
Please see the [CONTRIBUTING](https://github.com/ra1028/DiffableDataSources/blob/master/CONTRIBUTING.md) file for learn how to contribute to DiffableDataSources.
|
||||
|
||||
---
|
||||
|
||||
## Relations
|
||||
|
||||
#### [DifferenceKit](https://github.com/ra1028/DifferenceKit)
|
||||
A fast and flexible O(n) difference algorithm framework for Swift collection.
|
||||
|
||||
#### [Carbon](https://github.com/ra1028/Carbon)
|
||||
A declarative library for building component-based user interfaces in UITableView and UICollectionView.
|
||||
|
||||
---
|
||||
|
||||
## License
|
||||
|
||||
DiffableDataSources is released under the [Apache 2.0 License](https://github.com/ra1028/DiffableDataSources/blob/master/LICENSE).
|
||||
@@ -0,0 +1,111 @@
|
||||
#if os(macOS)
|
||||
|
||||
import AppKit
|
||||
import DifferenceKit
|
||||
|
||||
/// A class for backporting `NSCollectionViewDiffableDataSource` introduced in macOS 10.15+.
|
||||
/// Represents the data model object for `NSCollectionView` that can be applies the
|
||||
/// changes with automatic diffing.
|
||||
open class CocoaCollectionViewDiffableDataSource<SectionIdentifierType: Hashable, ItemIdentifierType: Hashable>: NSObject, NSCollectionViewDataSource {
|
||||
/// The type of closure providing the item.
|
||||
public typealias ItemProvider = (NSCollectionView, IndexPath, ItemIdentifierType) -> NSCollectionViewItem?
|
||||
|
||||
private weak var collectionView: NSCollectionView?
|
||||
private let itemProvider: ItemProvider
|
||||
private let core = DiffableDataSourceCore<SectionIdentifierType, ItemIdentifierType>()
|
||||
|
||||
/// Creates a new data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance to be managed.
|
||||
/// - itemProvider: A closure to make the item.
|
||||
public init(collectionView: NSCollectionView, itemProvider: @escaping ItemProvider) {
|
||||
self.collectionView = collectionView
|
||||
self.itemProvider = itemProvider
|
||||
super.init()
|
||||
|
||||
collectionView.dataSource = self
|
||||
}
|
||||
|
||||
/// Applies given snapshot to perform automatic diffing update.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - snapshot: A snapshot object to be applied to data model.
|
||||
/// - animatingDifferences: A Boolean value indicating whether to update with
|
||||
/// diffing animation.
|
||||
public func apply(_ snapshot: DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>, animatingDifferences: Bool = true) {
|
||||
core.apply(
|
||||
snapshot,
|
||||
view: collectionView,
|
||||
animatingDifferences: animatingDifferences,
|
||||
performUpdates: { collectionView, changeset, setSections in
|
||||
collectionView.reload(using: changeset, setData: setSections)
|
||||
})
|
||||
}
|
||||
|
||||
/// Returns a new snapshot object of current state.
|
||||
///
|
||||
/// - Returns: A new snapshot object of current state.
|
||||
public func snapshot() -> DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType> {
|
||||
return core.snapshot()
|
||||
}
|
||||
|
||||
/// Returns an item identifier for given index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - indexPath: An index path for the item identifier.
|
||||
///
|
||||
/// - Returns: An item identifier for given index path.
|
||||
public func itemIdentifier(for indexPath: IndexPath) -> ItemIdentifierType? {
|
||||
return core.itemIdentifier(for: indexPath)
|
||||
}
|
||||
|
||||
/// Returns an index path for given item identifier.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - itemIdentifier: An identifier of item.
|
||||
///
|
||||
/// - Returns: An index path for given item identifier.
|
||||
public func indexPath(for itemIdentifier: ItemIdentifierType) -> IndexPath? {
|
||||
return core.indexPath(for: itemIdentifier)
|
||||
}
|
||||
|
||||
/// Returns the number of sections in the data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
///
|
||||
/// - Returns: The number of sections in the data source.
|
||||
public func numberOfSections(in collectionView: NSCollectionView) -> Int {
|
||||
return core.numberOfSections()
|
||||
}
|
||||
|
||||
/// Returns the number of items in the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
/// - section: An index of section.
|
||||
///
|
||||
/// - Returns: The number of items in the specified section.
|
||||
public func collectionView(_ collectionView: NSCollectionView, numberOfItemsInSection section: Int) -> Int {
|
||||
return core.numberOfItems(inSection: section)
|
||||
}
|
||||
|
||||
/// Returns an item at specified index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
/// - indexPath: An index path for item.
|
||||
///
|
||||
/// - Returns: An item at specified index path.
|
||||
open func collectionView(_ collectionView: NSCollectionView, itemForRepresentedObjectAt indexPath: IndexPath) -> NSCollectionViewItem {
|
||||
let itemIdentifier = core.unsafeItemIdentifier(for: indexPath)
|
||||
guard let item = itemProvider(collectionView, indexPath, itemIdentifier) else {
|
||||
universalError("NSCollectionView dataSource returned a nil item at index path: \(indexPath), collectionView: \(collectionView), itemIdentifier: \(itemIdentifier)")
|
||||
}
|
||||
|
||||
return item
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,204 @@
|
||||
/// A class for backporting `NSDiffableDataSourceSnapshot` introduced in iOS 13.0+, macOS 10.15+, tvOS 13.0+.
|
||||
/// Represents the mutable state of diffable data source of UI.
|
||||
public class DiffableDataSourceSnapshot<SectionIdentifierType: Hashable, ItemIdentifierType: Hashable> {
|
||||
internal let structure = SnapshotStructure<SectionIdentifierType, ItemIdentifierType>()
|
||||
|
||||
/// Creates a new empty snapshot object.
|
||||
public init() {}
|
||||
|
||||
/// The number of item identifiers in the snapshot.
|
||||
public var numberOfItems: Int {
|
||||
return itemIdentifiers.count
|
||||
}
|
||||
|
||||
/// The number of section identifiers in the snapshot.
|
||||
public var numberOfSections: Int {
|
||||
return sectionIdentifiers.count
|
||||
}
|
||||
|
||||
/// All section identifiers in the snapshot.
|
||||
public var sectionIdentifiers: [SectionIdentifierType] {
|
||||
return structure.allSectionIDs
|
||||
}
|
||||
|
||||
/// All item identifiers in the snapshot.
|
||||
public var itemIdentifiers: [ItemIdentifierType] {
|
||||
return structure.allItemIDs
|
||||
}
|
||||
|
||||
/// Returns the number of item identifiers in the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An identifier of section.
|
||||
///
|
||||
/// - Returns: The number of item identifiers in the specified section.
|
||||
public func numberOfItems(inSection identifier: SectionIdentifierType) -> Int {
|
||||
return itemIdentifiers(inSection: identifier).count
|
||||
}
|
||||
|
||||
/// Returns the item identifiers in the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An identifier of section.
|
||||
///
|
||||
/// - Returns: The item identifiers in the specified section.
|
||||
public func itemIdentifiers(inSection identifier: SectionIdentifierType) -> [ItemIdentifierType] {
|
||||
return structure.items(in: identifier)
|
||||
}
|
||||
|
||||
/// Returns a section identifier containing the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An identifier of item.
|
||||
///
|
||||
/// - Returns: A section identifier containing the specified item.
|
||||
public func sectionIdentifier(containingItem identifier: ItemIdentifierType) -> SectionIdentifierType? {
|
||||
return structure.section(containing: identifier)
|
||||
}
|
||||
|
||||
/// Returns an index of the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An identifier of item.
|
||||
///
|
||||
/// - Returns: An index of the specified item.
|
||||
public func indexOfItem(_ identifier: ItemIdentifierType) -> Int? {
|
||||
return itemIdentifiers.firstIndex { $0.isEqualHash(to: identifier) }
|
||||
}
|
||||
|
||||
/// Returns an index of the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An identifier of section.
|
||||
///
|
||||
/// - Returns: An index of the specified section.
|
||||
public func indexOfSection(_ identifier: SectionIdentifierType) -> Int? {
|
||||
return sectionIdentifiers.firstIndex { $0.isEqualHash(to: identifier) }
|
||||
}
|
||||
|
||||
/// Appends the given item identifiers to the specified section or last section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The item identifiers to be appended.
|
||||
/// - sectionIdentifier: An identifier of section to append the given identiciers.
|
||||
public func appendItems(_ identifiers: [ItemIdentifierType], toSection sectionIdentifier: SectionIdentifierType? = nil) {
|
||||
structure.append(itemIDs: identifiers, to: sectionIdentifier)
|
||||
}
|
||||
|
||||
/// Inserts the given item identifiers before the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The item identifiers to be inserted.
|
||||
/// - beforeIdentifier: An identifier of item.
|
||||
public func insertItems(_ identifiers: [ItemIdentifierType], beforeItem beforeIdentifier: ItemIdentifierType) {
|
||||
structure.insert(itemIDs: identifiers, before: beforeIdentifier)
|
||||
}
|
||||
|
||||
/// Inserts the given item identifiers after the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The item identifiers to be inserted.
|
||||
/// - afterIdentifier: An identifier of item.
|
||||
public func insertItems(_ identifiers: [ItemIdentifierType], afterItem afterIdentifier: ItemIdentifierType) {
|
||||
structure.insert(itemIDs: identifiers, after: afterIdentifier)
|
||||
}
|
||||
|
||||
/// Deletes the specified items.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The item identifiers to be deleted.
|
||||
public func deleteItems(_ identifiers: [ItemIdentifierType]) {
|
||||
structure.remove(itemIDs: identifiers)
|
||||
}
|
||||
|
||||
/// Deletes the all items in the snapshot.
|
||||
public func deleteAllItems() {
|
||||
structure.removeAllItems()
|
||||
}
|
||||
|
||||
/// Moves the given item identifier before the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An item identifier to be moved.
|
||||
/// - toIdentifier: An identifier of item.
|
||||
public func moveItem(_ identifier: ItemIdentifierType, beforeItem toIdentifier: ItemIdentifierType) {
|
||||
structure.move(itemID: identifier, before: toIdentifier)
|
||||
}
|
||||
|
||||
/// Moves the given item identifier after the specified item.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: An item identifier to be moved.
|
||||
/// - toIdentifier: An identifier of item.
|
||||
public func moveItem(_ identifier: ItemIdentifierType, afterItem toIdentifier: ItemIdentifierType) {
|
||||
structure.move(itemID: identifier, after: toIdentifier)
|
||||
}
|
||||
|
||||
/// Reloads the specified items.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The item identifiers to be reloaded.
|
||||
public func reloadItems(_ identifiers: [ItemIdentifierType]) {
|
||||
structure.update(itemIDs: identifiers)
|
||||
}
|
||||
|
||||
/// Appends the given section identifiers to the end of sections.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The section identifiers to be appended.
|
||||
public func appendSections(_ identifiers: [SectionIdentifierType]) {
|
||||
structure.append(sectionIDs: identifiers)
|
||||
}
|
||||
|
||||
/// Inserts the given section identifiers before the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The section identifiers to be inserted.
|
||||
/// - toIdentifier: An identifier of setion.
|
||||
public func insertSections(_ identifiers: [SectionIdentifierType], beforeSection toIdentifier: SectionIdentifierType) {
|
||||
structure.insert(sectionIDs: identifiers, before: toIdentifier)
|
||||
}
|
||||
|
||||
/// Inserts the given section identifiers after the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The section identifiers to be inserted.
|
||||
/// - toIdentifier: An identifier of setion.
|
||||
public func insertSections(_ identifiers: [SectionIdentifierType], afterSection toIdentifier: SectionIdentifierType) {
|
||||
structure.insert(sectionIDs: identifiers, after: toIdentifier)
|
||||
}
|
||||
|
||||
/// Deletes the specified sections.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The section identifiers to be deleted.
|
||||
public func deleteSections(_ identifiers: [SectionIdentifierType]) {
|
||||
structure.remove(sectionIDs: identifiers)
|
||||
}
|
||||
|
||||
/// Moves the given section identifier before the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: A section identifier to be moved.
|
||||
/// - toIdentifier: An identifier of section.
|
||||
public func moveSection(_ identifier: SectionIdentifierType, beforeSection toIdentifier: SectionIdentifierType) {
|
||||
structure.move(sectionID: identifier, before: toIdentifier)
|
||||
}
|
||||
|
||||
/// Moves the given section identifier after the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifier: A section identifier to be moved.
|
||||
/// - toIdentifier: An identifier of section.
|
||||
public func moveSection(_ identifier: SectionIdentifierType, afterSection toIdentifier: SectionIdentifierType) {
|
||||
structure.move(sectionID: identifier, after: toIdentifier)
|
||||
}
|
||||
|
||||
/// Reloads the specified sections.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - identifiers: The section identifiers to be reloaded.
|
||||
public func reloadSections(_ identifiers: [SectionIdentifierType]) {
|
||||
structure.update(sectionIDs: identifiers)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>$(DEVELOPMENT_LANGUAGE)</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>FMWK</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>$(CURRENT_PROJECT_VERSION)</string>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,98 @@
|
||||
import Foundation
|
||||
import QuartzCore
|
||||
import DifferenceKit
|
||||
|
||||
final class DiffableDataSourceCore<SectionIdentifierType: Hashable, ItemIdentifierType: Hashable> {
|
||||
typealias Section = SnapshotStructure<SectionIdentifierType, ItemIdentifierType>.Section
|
||||
|
||||
private let dispatcher = MainThreadSerialDispatcher()
|
||||
private var currentSnapshot = DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>()
|
||||
private var sections: [Section] = []
|
||||
|
||||
func apply<View: AnyObject>(
|
||||
_ snapshot: DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>,
|
||||
view: View?,
|
||||
animatingDifferences: Bool,
|
||||
performUpdates: @escaping (View, StagedChangeset<[Section]>, @escaping ([Section]) -> Void) -> Void
|
||||
) {
|
||||
dispatcher.dispatch { [weak self] in
|
||||
guard let self = self else {
|
||||
return
|
||||
}
|
||||
|
||||
self.currentSnapshot = snapshot
|
||||
|
||||
let newSections = snapshot.structure.sections
|
||||
|
||||
guard let view = view else {
|
||||
return self.sections = newSections
|
||||
}
|
||||
|
||||
func performDiffingUpdates() {
|
||||
let changeset = StagedChangeset(source: self.sections, target: newSections)
|
||||
performUpdates(view, changeset) { sections in
|
||||
self.sections = sections
|
||||
}
|
||||
}
|
||||
|
||||
if animatingDifferences {
|
||||
performDiffingUpdates()
|
||||
}
|
||||
else {
|
||||
CATransaction.begin()
|
||||
CATransaction.setDisableActions(true)
|
||||
performDiffingUpdates()
|
||||
CATransaction.commit()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func snapshot() -> DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType> {
|
||||
let snapshot = DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>()
|
||||
snapshot.structure.sections = currentSnapshot.structure.sections
|
||||
return snapshot
|
||||
}
|
||||
|
||||
func itemIdentifier(for indexPath: IndexPath) -> ItemIdentifierType? {
|
||||
guard 0..<sections.endIndex ~= indexPath.section else {
|
||||
return nil
|
||||
}
|
||||
|
||||
let items = sections[indexPath.section].elements
|
||||
|
||||
guard 0..<items.endIndex ~= indexPath.item else {
|
||||
return nil
|
||||
}
|
||||
|
||||
return items[indexPath.item].differenceIdentifier
|
||||
}
|
||||
|
||||
func unsafeItemIdentifier(for indexPath: IndexPath, file: StaticString = #file, line: UInt = #line) -> ItemIdentifierType {
|
||||
guard let itemIdentifier = itemIdentifier(for: indexPath) else {
|
||||
universalError("Item not found at the specified index path(\(indexPath)).")
|
||||
}
|
||||
|
||||
return itemIdentifier
|
||||
}
|
||||
|
||||
func indexPath(for itemIdentifier: ItemIdentifierType) -> IndexPath? {
|
||||
let indexPathMap: [ItemIdentifierType: IndexPath] = sections.enumerated()
|
||||
.reduce(into: [:]) { result, section in
|
||||
for (itemIndex, item) in section.element.elements.enumerated() {
|
||||
result[item.differenceIdentifier] = IndexPath(
|
||||
item: itemIndex,
|
||||
section: section.offset
|
||||
)
|
||||
}
|
||||
}
|
||||
return indexPathMap[itemIdentifier]
|
||||
}
|
||||
|
||||
func numberOfSections() -> Int {
|
||||
return sections.count
|
||||
}
|
||||
|
||||
func numberOfItems(inSection section: Int) -> Int {
|
||||
return sections[section].elements.count
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,5 @@
|
||||
extension Hashable {
|
||||
func isEqualHash(to other: Self) -> Bool {
|
||||
return hashValue == other.hashValue && self == other
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
import Foundation
|
||||
|
||||
final class MainThreadSerialDispatcher {
|
||||
private let executingCount = UnsafeMutablePointer<Int32>.allocate(capacity: 1)
|
||||
|
||||
init() {
|
||||
executingCount.initialize(to: 0)
|
||||
}
|
||||
|
||||
deinit {
|
||||
executingCount.deinitialize(count: 1)
|
||||
executingCount.deallocate()
|
||||
}
|
||||
|
||||
func dispatch(_ action: @escaping () -> Void) {
|
||||
let count = OSAtomicIncrement32(executingCount)
|
||||
|
||||
if Thread.isMainThread && count == 1 {
|
||||
action()
|
||||
OSAtomicDecrement32(executingCount)
|
||||
}
|
||||
else {
|
||||
DispatchQueue.main.async { [weak self] in
|
||||
guard let self = self else {
|
||||
return
|
||||
}
|
||||
|
||||
action()
|
||||
OSAtomicDecrement32(self.executingCount)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,294 @@
|
||||
import Foundation
|
||||
import DifferenceKit
|
||||
|
||||
final class SnapshotStructure<SectionID: Hashable, ItemID: Hashable> {
|
||||
struct Item: Differentiable, Equatable {
|
||||
var differenceIdentifier: ItemID
|
||||
var isReloaded: Bool
|
||||
|
||||
init(id: ItemID, isReloaded: Bool) {
|
||||
self.differenceIdentifier = id
|
||||
self.isReloaded = isReloaded
|
||||
}
|
||||
|
||||
init(id: ItemID) {
|
||||
self.init(id: id, isReloaded: false)
|
||||
}
|
||||
|
||||
func isContentEqual(to source: Item) -> Bool {
|
||||
return !isReloaded && differenceIdentifier == source.differenceIdentifier
|
||||
}
|
||||
}
|
||||
|
||||
struct Section: DifferentiableSection, Equatable {
|
||||
var differenceIdentifier: SectionID
|
||||
var elements: [Item] = []
|
||||
var isReloaded: Bool
|
||||
|
||||
init(id: SectionID, items: [Item], isReloaded: Bool) {
|
||||
self.differenceIdentifier = id
|
||||
self.elements = items
|
||||
self.isReloaded = isReloaded
|
||||
}
|
||||
|
||||
init(id: SectionID) {
|
||||
self.init(id: id, items: [], isReloaded: false)
|
||||
}
|
||||
|
||||
init<C: Collection>(source: Section, elements: C) where C.Element == Item {
|
||||
self.init(id: source.differenceIdentifier, items: Array(elements), isReloaded: source.isReloaded)
|
||||
}
|
||||
|
||||
func isContentEqual(to source: Section) -> Bool {
|
||||
return !isReloaded && differenceIdentifier == source.differenceIdentifier
|
||||
}
|
||||
}
|
||||
|
||||
var sections: [Section] = []
|
||||
|
||||
var allSectionIDs: [SectionID] {
|
||||
return sections.map { $0.differenceIdentifier }
|
||||
}
|
||||
|
||||
var allItemIDs: [ItemID] {
|
||||
return sections.lazy
|
||||
.flatMap { $0.elements }
|
||||
.map { $0.differenceIdentifier }
|
||||
}
|
||||
|
||||
func items(in sectionID: SectionID, file: StaticString = #file, line: UInt = #line) -> [ItemID] {
|
||||
guard let sectionIndex = sectionIndex(of: sectionID) else {
|
||||
specifiedSectionIsNotFound(sectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
return sections[sectionIndex].elements.map { $0.differenceIdentifier }
|
||||
}
|
||||
|
||||
func section(containing itemID: ItemID) -> SectionID? {
|
||||
return itemPositionMap()[itemID]?.section.differenceIdentifier
|
||||
}
|
||||
|
||||
func append(itemIDs: [ItemID], to sectionID: SectionID? = nil, file: StaticString = #file, line: UInt = #line) {
|
||||
let index: Array<Section>.Index
|
||||
|
||||
if let sectionID = sectionID {
|
||||
guard let sectionIndex = sectionIndex(of: sectionID) else {
|
||||
specifiedSectionIsNotFound(sectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
index = sectionIndex
|
||||
}
|
||||
else {
|
||||
guard !sections.isEmpty else {
|
||||
thereAreCurrentlyNoSections(file: file, line: line)
|
||||
}
|
||||
|
||||
index = sections.index(before: sections.endIndex)
|
||||
}
|
||||
|
||||
let items = itemIDs.lazy.map(Item.init)
|
||||
sections[index].elements.append(contentsOf: items)
|
||||
}
|
||||
|
||||
func insert(itemIDs: [ItemID], before beforeItemID: ItemID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let itemPosition = itemPositionMap()[beforeItemID] else {
|
||||
specifiedItemIsNotFound(beforeItemID, file: file, line: line)
|
||||
}
|
||||
|
||||
let items = itemIDs.lazy.map(Item.init)
|
||||
sections[itemPosition.sectionIndex].elements.insert(contentsOf: items, at: itemPosition.itemRelativeIndex)
|
||||
}
|
||||
|
||||
func insert(itemIDs: [ItemID], after afterItemID: ItemID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let itemPosition = itemPositionMap()[afterItemID] else {
|
||||
specifiedItemIsNotFound(afterItemID, file: file, line: line)
|
||||
}
|
||||
|
||||
let itemIndex = sections[itemPosition.sectionIndex].elements.index(after: itemPosition.itemRelativeIndex)
|
||||
let items = itemIDs.lazy.map(Item.init)
|
||||
sections[itemPosition.sectionIndex].elements.insert(contentsOf: items, at: itemIndex)
|
||||
}
|
||||
|
||||
func remove(itemIDs: [ItemID]) {
|
||||
let itemPositionMap = self.itemPositionMap()
|
||||
var removeIndexSetMap = [Int: IndexSet]()
|
||||
|
||||
for itemID in itemIDs {
|
||||
guard let itemPosition = itemPositionMap[itemID] else {
|
||||
continue
|
||||
}
|
||||
|
||||
removeIndexSetMap[itemPosition.sectionIndex, default: []].insert(itemPosition.itemRelativeIndex)
|
||||
}
|
||||
|
||||
for (sectionIndex, removeIndexSet) in removeIndexSetMap {
|
||||
for range in removeIndexSet.rangeView.reversed() {
|
||||
sections[sectionIndex].elements.removeSubrange(range)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func removeAllItems() {
|
||||
for sectionIndex in sections.indices {
|
||||
sections[sectionIndex].elements.removeAll()
|
||||
}
|
||||
}
|
||||
|
||||
func move(itemID: ItemID, before beforeItemID: ItemID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let removed = remove(itemID: itemID) else {
|
||||
specifiedItemIsNotFound(itemID, file: file, line: line)
|
||||
}
|
||||
|
||||
guard let itemPosition = itemPositionMap()[beforeItemID] else {
|
||||
specifiedItemIsNotFound(beforeItemID, file: file, line: line)
|
||||
}
|
||||
|
||||
sections[itemPosition.sectionIndex].elements.insert(removed, at: itemPosition.itemRelativeIndex)
|
||||
}
|
||||
|
||||
func move(itemID: ItemID, after afterItemID: ItemID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let removed = remove(itemID: itemID) else {
|
||||
specifiedItemIsNotFound(itemID, file: file, line: line)
|
||||
}
|
||||
|
||||
guard let itemPosition = itemPositionMap()[afterItemID] else {
|
||||
specifiedItemIsNotFound(afterItemID, file: file, line: line)
|
||||
}
|
||||
|
||||
let itemIndex = sections[itemPosition.sectionIndex].elements.index(after: itemPosition.itemRelativeIndex)
|
||||
sections[itemPosition.sectionIndex].elements.insert(removed, at: itemIndex)
|
||||
}
|
||||
|
||||
func update(itemIDs: [ItemID], file: StaticString = #file, line: UInt = #line) {
|
||||
let itemPositionMap = self.itemPositionMap()
|
||||
|
||||
for itemID in itemIDs {
|
||||
guard let itemPosition = itemPositionMap[itemID] else {
|
||||
specifiedItemIsNotFound(itemID, file: file, line: line)
|
||||
}
|
||||
|
||||
sections[itemPosition.sectionIndex].elements[itemPosition.itemRelativeIndex].isReloaded = true
|
||||
}
|
||||
}
|
||||
|
||||
func append(sectionIDs: [SectionID]) {
|
||||
let newSections = sectionIDs.lazy.map(Section.init)
|
||||
sections.append(contentsOf: newSections)
|
||||
}
|
||||
|
||||
func insert(sectionIDs: [SectionID], before beforeSectionID: SectionID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let sectionIndex = sectionIndex(of: beforeSectionID) else {
|
||||
specifiedSectionIsNotFound(beforeSectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
let newSections = sectionIDs.lazy.map(Section.init)
|
||||
sections.insert(contentsOf: newSections, at: sectionIndex)
|
||||
}
|
||||
|
||||
func insert(sectionIDs: [SectionID], after afterSectionID: SectionID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let beforeIndex = sectionIndex(of: afterSectionID) else {
|
||||
specifiedSectionIsNotFound(afterSectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
let sectionIndex = sections.index(after: beforeIndex)
|
||||
let newSections = sectionIDs.lazy.map(Section.init)
|
||||
sections.insert(contentsOf: newSections, at: sectionIndex)
|
||||
}
|
||||
|
||||
func remove(sectionIDs: [SectionID]) {
|
||||
for sectionID in sectionIDs {
|
||||
remove(sectionID: sectionID)
|
||||
}
|
||||
}
|
||||
|
||||
func move(sectionID: SectionID, before beforeSectionID: SectionID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let removed = remove(sectionID: sectionID) else {
|
||||
specifiedSectionIsNotFound(sectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
guard let sectionIndex = sectionIndex(of: beforeSectionID) else {
|
||||
specifiedSectionIsNotFound(beforeSectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
sections.insert(removed, at: sectionIndex)
|
||||
}
|
||||
|
||||
func move(sectionID: SectionID, after afterSectionID: SectionID, file: StaticString = #file, line: UInt = #line) {
|
||||
guard let removed = remove(sectionID: sectionID) else {
|
||||
specifiedSectionIsNotFound(sectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
guard let beforeIndex = sectionIndex(of: afterSectionID) else {
|
||||
specifiedSectionIsNotFound(afterSectionID, file: file, line: line)
|
||||
}
|
||||
|
||||
let sectionIndex = sections.index(after: beforeIndex)
|
||||
sections.insert(removed, at: sectionIndex)
|
||||
}
|
||||
|
||||
func update(sectionIDs: [SectionID]) {
|
||||
for sectionID in sectionIDs {
|
||||
guard let sectionIndex = sectionIndex(of: sectionID) else {
|
||||
continue
|
||||
}
|
||||
|
||||
sections[sectionIndex].isReloaded = true
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private extension SnapshotStructure {
|
||||
struct ItemPosition {
|
||||
var item: Item
|
||||
var itemRelativeIndex: Int
|
||||
var section: Section
|
||||
var sectionIndex: Int
|
||||
}
|
||||
|
||||
func sectionIndex(of sectionID: SectionID) -> Array<Section>.Index? {
|
||||
return sections.firstIndex { $0.differenceIdentifier.isEqualHash(to: sectionID) }
|
||||
}
|
||||
|
||||
@discardableResult
|
||||
func remove(itemID: ItemID) -> Item? {
|
||||
guard let itemPosition = itemPositionMap()[itemID] else {
|
||||
return nil
|
||||
}
|
||||
|
||||
return sections[itemPosition.sectionIndex].elements.remove(at: itemPosition.itemRelativeIndex)
|
||||
}
|
||||
|
||||
@discardableResult
|
||||
func remove(sectionID: SectionID) -> Section? {
|
||||
guard let sectionIndex = sectionIndex(of: sectionID) else {
|
||||
return nil
|
||||
}
|
||||
|
||||
return sections.remove(at: sectionIndex)
|
||||
}
|
||||
|
||||
func itemPositionMap() -> [ItemID: ItemPosition] {
|
||||
return sections.enumerated().reduce(into: [:]) { result, section in
|
||||
for (itemRelativeIndex, item) in section.element.elements.enumerated() {
|
||||
result[item.differenceIdentifier] = ItemPosition(
|
||||
item: item,
|
||||
itemRelativeIndex: itemRelativeIndex,
|
||||
section: section.element,
|
||||
sectionIndex: section.offset
|
||||
)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func specifiedItemIsNotFound(_ id: ItemID, file: StaticString, line: UInt) -> Never {
|
||||
universalError("Specified item\(id) is not found.", file: file, line: line)
|
||||
}
|
||||
|
||||
func specifiedSectionIsNotFound(_ id: SectionID, file: StaticString, line: UInt) -> Never {
|
||||
universalError("Specified section\(id) is not found.", file: file, line: line)
|
||||
}
|
||||
|
||||
func thereAreCurrentlyNoSections(file: StaticString, line: UInt) -> Never {
|
||||
universalError("There are currently no sections.", file: file, line: line)
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,3 @@
|
||||
func universalError(_ message: String, file: StaticString = #file, line: UInt = #line) -> Never {
|
||||
fatalError("[DiffableDataSources] \(message)", file: file, line: line)
|
||||
}
|
||||
@@ -0,0 +1,133 @@
|
||||
#if os(iOS) || os(tvOS)
|
||||
|
||||
import UIKit
|
||||
import DifferenceKit
|
||||
|
||||
/// A class for backporting `UICollectionViewDiffableDataSource` introduced in iOS 13.0+, tvOS 13.0+.
|
||||
/// Represents the data model object for `UICollectionView` that can be applies the
|
||||
/// changes with automatic diffing.
|
||||
open class CollectionViewDiffableDataSource<SectionIdentifierType: Hashable, ItemIdentifierType: Hashable>: NSObject, UICollectionViewDataSource {
|
||||
/// The type of closure providing the cell.
|
||||
public typealias CellProvider = (UICollectionView, IndexPath, ItemIdentifierType) -> UICollectionViewCell?
|
||||
|
||||
/// The type of closure providing the supplementary view for element of kind.
|
||||
public typealias SupplementaryViewProvider = (UICollectionView, String, IndexPath) -> UICollectionReusableView?
|
||||
|
||||
/// A closure to dequeue the views for element of kind.
|
||||
public var supplementaryViewProvider: SupplementaryViewProvider?
|
||||
|
||||
private weak var collectionView: UICollectionView?
|
||||
private let cellProvider: CellProvider
|
||||
private let core = DiffableDataSourceCore<SectionIdentifierType, ItemIdentifierType>()
|
||||
|
||||
/// Creates a new data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance to be managed.
|
||||
/// - cellProvider: A closure to dequeue the cell for items.
|
||||
public init(collectionView: UICollectionView, cellProvider: @escaping CellProvider) {
|
||||
self.collectionView = collectionView
|
||||
self.cellProvider = cellProvider
|
||||
super.init()
|
||||
|
||||
collectionView.dataSource = self
|
||||
}
|
||||
|
||||
/// Applies given snapshot to perform automatic diffing update.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - snapshot: A snapshot object to be applied to data model.
|
||||
/// - animatingDifferences: A Boolean value indicating whether to update with
|
||||
/// diffing animation.
|
||||
public func apply(_ snapshot: DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>, animatingDifferences: Bool = true) {
|
||||
core.apply(
|
||||
snapshot,
|
||||
view: collectionView,
|
||||
animatingDifferences: animatingDifferences,
|
||||
performUpdates: { collectionView, changeset, setSections in
|
||||
collectionView.reload(using: changeset, setData: setSections)
|
||||
})
|
||||
}
|
||||
|
||||
/// Returns a new snapshot object of current state.
|
||||
///
|
||||
/// - Returns: A new snapshot object of current state.
|
||||
public func snapshot() -> DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType> {
|
||||
return core.snapshot()
|
||||
}
|
||||
|
||||
/// Returns an item identifier for given index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - indexPath: An index path for the item identifier.
|
||||
///
|
||||
/// - Returns: An item identifier for given index path.
|
||||
public func itemIdentifier(for indexPath: IndexPath) -> ItemIdentifierType? {
|
||||
return core.itemIdentifier(for: indexPath)
|
||||
}
|
||||
|
||||
/// Returns an index path for given item identifier.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - itemIdentifier: An identifier of item.
|
||||
///
|
||||
/// - Returns: An index path for given item identifier.
|
||||
public func indexPath(for itemIdentifier: ItemIdentifierType) -> IndexPath? {
|
||||
return core.indexPath(for: itemIdentifier)
|
||||
}
|
||||
|
||||
/// Returns the number of sections in the data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
///
|
||||
/// - Returns: The number of sections in the data source.
|
||||
public func numberOfSections(in collectionView: UICollectionView) -> Int {
|
||||
return core.numberOfSections()
|
||||
}
|
||||
|
||||
/// Returns the number of items in the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
/// - section: An index of section.
|
||||
///
|
||||
/// - Returns: The number of items in the specified section.
|
||||
public func collectionView(_ collectionView: UICollectionView, numberOfItemsInSection section: Int) -> Int {
|
||||
return core.numberOfItems(inSection: section)
|
||||
}
|
||||
|
||||
/// Returns a cell for item at specified index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
/// - indexPath: An index path for cell.
|
||||
///
|
||||
/// - Returns: A cell for row at specified index path.
|
||||
open func collectionView(_ collectionView: UICollectionView, cellForItemAt indexPath: IndexPath) -> UICollectionViewCell {
|
||||
let itemIdentifier = core.unsafeItemIdentifier(for: indexPath)
|
||||
guard let cell = cellProvider(collectionView, indexPath, itemIdentifier) else {
|
||||
universalError("UICollectionView dataSource returned a nil cell for item at index path: \(indexPath), collectionView: \(collectionView), itemIdentifier: \(itemIdentifier)")
|
||||
}
|
||||
|
||||
return cell
|
||||
}
|
||||
|
||||
/// Returns a supplementary view for element of kind at specified index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - collectionView: A collection view instance managed by `self`.
|
||||
/// - kind: The kind of element to be display.
|
||||
/// - indexPath: An index path for supplementary view.
|
||||
///
|
||||
/// - Returns: A supplementary view for element of kind at specified index path.
|
||||
open func collectionView(_ collectionView: UICollectionView, viewForSupplementaryElementOfKind kind: String, at indexPath: IndexPath) -> UICollectionReusableView {
|
||||
guard let view = supplementaryViewProvider?(collectionView, kind, indexPath) else {
|
||||
return UICollectionReusableView()
|
||||
}
|
||||
|
||||
return view
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,114 @@
|
||||
#if os(iOS) || os(tvOS)
|
||||
|
||||
import UIKit
|
||||
import DifferenceKit
|
||||
|
||||
/// A class for backporting `UITableViewDiffableDataSource` introduced in iOS 13.0+, tvOS 13.0+.
|
||||
/// Represents the data model object for `UITableView` that can be applies the
|
||||
/// changes with automatic diffing.
|
||||
open class TableViewDiffableDataSource<SectionIdentifierType: Hashable, ItemIdentifierType: Hashable>: NSObject, UITableViewDataSource {
|
||||
/// The type of closure providing the cell.
|
||||
public typealias CellProvider = (UITableView, IndexPath, ItemIdentifierType) -> UITableViewCell?
|
||||
|
||||
/// The default animation to updating the views.
|
||||
public var defaultRowAnimation: UITableView.RowAnimation = .automatic
|
||||
|
||||
private weak var tableView: UITableView?
|
||||
private let cellProvider: CellProvider
|
||||
private let core = DiffableDataSourceCore<SectionIdentifierType, ItemIdentifierType>()
|
||||
|
||||
/// Creates a new data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - tableView: A table view instance to be managed.
|
||||
/// - cellProvider: A closure to dequeue the cell for rows.
|
||||
public init(tableView: UITableView, cellProvider: @escaping CellProvider) {
|
||||
self.tableView = tableView
|
||||
self.cellProvider = cellProvider
|
||||
super.init()
|
||||
|
||||
tableView.dataSource = self
|
||||
}
|
||||
|
||||
/// Applies given snapshot to perform automatic diffing update.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - snapshot: A snapshot object to be applied to data model.
|
||||
/// - animatingDifferences: A Boolean value indicating whether to update with
|
||||
/// diffing animation.
|
||||
public func apply(_ snapshot: DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType>, animatingDifferences: Bool = true) {
|
||||
core.apply(
|
||||
snapshot,
|
||||
view: tableView,
|
||||
animatingDifferences: animatingDifferences,
|
||||
performUpdates: { tableView, changeset, setSections in
|
||||
tableView.reload(using: changeset, with: self.defaultRowAnimation, setData: setSections)
|
||||
})
|
||||
}
|
||||
|
||||
/// Returns a new snapshot object of current state.
|
||||
///
|
||||
/// - Returns: A new snapshot object of current state.
|
||||
public func snapshot() -> DiffableDataSourceSnapshot<SectionIdentifierType, ItemIdentifierType> {
|
||||
return core.snapshot()
|
||||
}
|
||||
|
||||
/// Returns an item identifier for given index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - indexPath: An index path for the item identifier.
|
||||
///
|
||||
/// - Returns: An item identifier for given index path.
|
||||
public func itemIdentifier(for indexPath: IndexPath) -> ItemIdentifierType? {
|
||||
return core.itemIdentifier(for: indexPath)
|
||||
}
|
||||
|
||||
/// Returns an index path for given item identifier.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - itemIdentifier: An identifier of item.
|
||||
///
|
||||
/// - Returns: An index path for given item identifier.
|
||||
public func indexPath(for itemIdentifier: ItemIdentifierType) -> IndexPath? {
|
||||
return core.indexPath(for: itemIdentifier)
|
||||
}
|
||||
|
||||
/// Returns the number of sections in the data source.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - tableView: A table view instance managed by `self`.
|
||||
///
|
||||
/// - Returns: The number of sections in the data source.
|
||||
public func numberOfSections(in tableView: UITableView) -> Int {
|
||||
return core.numberOfSections()
|
||||
}
|
||||
|
||||
/// Returns the number of items in the specified section.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - tableView: A table view instance managed by `self`.
|
||||
/// - section: An index of section.
|
||||
///
|
||||
/// - Returns: The number of items in the specified section.
|
||||
public func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
|
||||
return core.numberOfItems(inSection: section)
|
||||
}
|
||||
|
||||
/// Returns a cell for row at specified index path.
|
||||
///
|
||||
/// - Parameters:
|
||||
/// - tableView: A table view instance managed by `self`.
|
||||
/// - indexPath: An index path for cell.
|
||||
///
|
||||
/// - Returns: A cell for row at specified index path.
|
||||
open func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
|
||||
let itemIdentifier = core.unsafeItemIdentifier(for: indexPath)
|
||||
guard let cell = cellProvider(tableView, indexPath, itemIdentifier) else {
|
||||
universalError("UITableView dataSource returned a nil cell for row at index path: \(indexPath), tableView: \(tableView), itemIdentifier: \(itemIdentifier)")
|
||||
}
|
||||
|
||||
return cell
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,185 @@
|
||||
#if os(macOS)
|
||||
|
||||
import XCTest
|
||||
import AppKit
|
||||
@testable import DiffableDataSources
|
||||
|
||||
final class CocoaCollectionViewDiffableDataSourceTests: XCTestCase {
|
||||
func testInit() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
XCTAssertTrue(collectionView.dataSource === dataSource)
|
||||
}
|
||||
|
||||
func testApply() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 0)
|
||||
|
||||
snapshot.appendSections([0])
|
||||
snapshot.appendItems([0])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
snapshot.appendItems([1])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 2)
|
||||
}
|
||||
|
||||
func testSnapshot() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
let snapshot1 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot1.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot1.itemIdentifiers, [])
|
||||
|
||||
dataSource.snapshot().appendSections([0, 1, 2])
|
||||
let snapshot2 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot2.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot2.itemIdentifiers, [])
|
||||
|
||||
let snapshotToApply = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshotToApply.appendSections([0, 1, 2])
|
||||
snapshotToApply.appendItems([0, 1, 2])
|
||||
dataSource.apply(snapshotToApply)
|
||||
|
||||
let snapshot3 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot3.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot3.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
dataSource.snapshot().appendSections([3, 4, 5])
|
||||
|
||||
let snapshot4 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot4.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot4.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
snapshot4.appendSections([3, 4, 5])
|
||||
snapshot4.appendItems([3, 4, 5])
|
||||
dataSource.apply(snapshot4)
|
||||
|
||||
let snapshot5 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot5.sectionIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
XCTAssertEqual(snapshot5.itemIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
}
|
||||
|
||||
func testItemIdentifier() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 1, section: 0)), 1)
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 100, section: 100)), nil)
|
||||
}
|
||||
|
||||
func testIndexPath() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.indexPath(for: 2), IndexPath(item: 2, section: 0))
|
||||
XCTAssertEqual(dataSource.indexPath(for: 100), nil)
|
||||
}
|
||||
|
||||
func testNumberOfSections() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: collectionView), 0)
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: collectionView), 3)
|
||||
}
|
||||
|
||||
func testNumberOfRowsInSection() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
NSCollectionViewItem()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.collectionView(collectionView, numberOfItemsInSection: 0), 3)
|
||||
}
|
||||
|
||||
func testCellForRowAt() {
|
||||
let collectionView = MockCollectionView()
|
||||
let item = NSCollectionViewItem()
|
||||
let dataSource = CocoaCollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
item
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(
|
||||
dataSource.collectionView(collectionView, itemForRepresentedObjectAt: IndexPath(item: 1, section: 0)),
|
||||
item
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
final class MockCollectionView: NSCollectionView {
|
||||
var isPerformBatchUpdatesCalledCount = 0
|
||||
|
||||
init() {
|
||||
super.init(frame: .zero)
|
||||
|
||||
let window = NSWindow()
|
||||
window.contentView = self
|
||||
}
|
||||
|
||||
@available(*, unavailable)
|
||||
required init?(coder decoder: NSCoder) {
|
||||
fatalError("init(coder:) has not been implemented")
|
||||
}
|
||||
|
||||
override func performBatchUpdates(_ updates: (() -> Void)?, completionHandler: ((Bool) -> Void)? = nil) {
|
||||
isPerformBatchUpdatesCalledCount += 1
|
||||
updates?()
|
||||
completionHandler?(true)
|
||||
}
|
||||
|
||||
override func insertItems(at indexPaths: Set<IndexPath>) {}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,186 @@
|
||||
#if os(iOS) || os(tvOS)
|
||||
|
||||
import XCTest
|
||||
import UIKit
|
||||
@testable import DiffableDataSources
|
||||
|
||||
final class CollectionViewDiffableDataSourceTests: XCTestCase {
|
||||
func testInit() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
XCTAssertTrue(collectionView.dataSource === dataSource)
|
||||
}
|
||||
|
||||
func testApply() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 0)
|
||||
|
||||
snapshot.appendSections([0])
|
||||
snapshot.appendItems([0])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
snapshot.appendItems([1])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(collectionView.isPerformBatchUpdatesCalledCount, 2)
|
||||
}
|
||||
|
||||
func testSnapshot() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
let snapshot1 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot1.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot1.itemIdentifiers, [])
|
||||
|
||||
dataSource.snapshot().appendSections([0, 1, 2])
|
||||
let snapshot2 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot2.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot2.itemIdentifiers, [])
|
||||
|
||||
let snapshotToApply = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshotToApply.appendSections([0, 1, 2])
|
||||
snapshotToApply.appendItems([0, 1, 2])
|
||||
dataSource.apply(snapshotToApply)
|
||||
|
||||
let snapshot3 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot3.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot3.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
dataSource.snapshot().appendSections([3, 4, 5])
|
||||
|
||||
let snapshot4 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot4.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot4.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
snapshot4.appendSections([3, 4, 5])
|
||||
snapshot4.appendItems([3, 4, 5])
|
||||
dataSource.apply(snapshot4)
|
||||
|
||||
let snapshot5 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot5.sectionIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
XCTAssertEqual(snapshot5.itemIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
}
|
||||
|
||||
func testItemIdentifier() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 1, section: 0)), 1)
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 100, section: 100)), nil)
|
||||
}
|
||||
|
||||
func testIndexPath() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.indexPath(for: 2), IndexPath(item: 2, section: 0))
|
||||
XCTAssertEqual(dataSource.indexPath(for: 100), nil)
|
||||
}
|
||||
|
||||
func testNumberOfSections() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: collectionView), 0)
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: collectionView), 3)
|
||||
}
|
||||
|
||||
func testNumberOfRowsInSection() {
|
||||
let collectionView = MockCollectionView()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
UICollectionViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.collectionView(collectionView, numberOfItemsInSection: 0), 3)
|
||||
}
|
||||
|
||||
func testCellForRowAt() {
|
||||
let collectionView = MockCollectionView()
|
||||
let cell = UICollectionViewCell()
|
||||
let dataSource = CollectionViewDiffableDataSource<Int, Int>(collectionView: collectionView) { _, _, _ in
|
||||
cell
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(
|
||||
dataSource.collectionView(collectionView, cellForItemAt: IndexPath(item: 1, section: 0)),
|
||||
cell
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
final class MockCollectionView: UICollectionView {
|
||||
var isPerformBatchUpdatesCalledCount = 0
|
||||
|
||||
init() {
|
||||
super.init(frame: .zero, collectionViewLayout: UICollectionViewFlowLayout())
|
||||
|
||||
let window = UIWindow()
|
||||
window.addSubview(self)
|
||||
}
|
||||
|
||||
@available(*, unavailable)
|
||||
required init?(coder aDecoder: NSCoder) {
|
||||
fatalError("init(coder:) has not been implemented")
|
||||
}
|
||||
|
||||
override func performBatchUpdates(_ updates: (() -> Void)?, completion: ((Bool) -> Void)? = nil) {
|
||||
isPerformBatchUpdatesCalledCount += 1
|
||||
updates?()
|
||||
completion?(true)
|
||||
}
|
||||
|
||||
override func insertSections(_ sections: IndexSet) {}
|
||||
override func insertItems(at indexPaths: [IndexPath]) {}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,895 @@
|
||||
import XCTest
|
||||
@testable import DiffableDataSources
|
||||
|
||||
// swiftlint:disable file_length
|
||||
// swiftlint:disable type_body_length
|
||||
|
||||
final class DiffableDataSourceSnapshotTests: XCTestCase {
|
||||
func testAppendSections() {
|
||||
typealias Test = (initial: [Int], append: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [], [0, 1]),
|
||||
([], [0, 1, 2], [0, 1, 2]),
|
||||
([0, 1], [2, 3, 4], [0, 1, 2, 3, 4]),
|
||||
([0, 1], [4, 3, 2], [0, 1, 4, 3, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.appendSections(test.append)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testAppendSectionsDuplication() {
|
||||
typealias Test = (initial: [Int], append: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [0], [0, 1, 0]),
|
||||
([0, 1], [0, 1], [0, 1, 0, 1]),
|
||||
([0, 1], [2, 2], [0, 1, 2, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.appendSections(test.append)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertSectionsBeforeSection() {
|
||||
typealias Test = (initial: [Int], insert: [Int], before: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [3, 4], 1, [0, 3, 4, 1]),
|
||||
([0, 1], [3, 4], 0, [3, 4, 0, 1]),
|
||||
([0, 1, 2], [3, 4], 2, [0, 1, 3, 4, 2]),
|
||||
([0, 1, 2], [], 2, [0, 1, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.insertSections(test.insert, beforeSection: test.before)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertSectionsBeforeSectionDuplication() {
|
||||
typealias Test = (initial: [Int], insert: [Int], before: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [1], 0, [1, 0, 1]),
|
||||
([0, 1], [2, 2], 1, [0, 2, 2, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.insertSections(test.insert, beforeSection: test.before)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertSectionsAfterSection() {
|
||||
typealias Test = (initial: [Int], insert: [Int], after: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [3, 4], 1, [0, 1, 3, 4]),
|
||||
([0, 1], [3, 4], 0, [0, 3, 4, 1]),
|
||||
([0, 1, 2], [3, 4], 2, [0, 1, 2, 3, 4]),
|
||||
([0, 1, 2], [], 2, [0, 1, 2]),
|
||||
([0], [1], 0, [0, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.insertSections(test.insert, afterSection: test.after)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertSectionsAfterSectionDuplication() {
|
||||
typealias Test = (initial: [Int], insert: [Int], after: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [1], 0, [0, 1, 1]),
|
||||
([0, 1], [2, 2], 1, [0, 1, 2, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.insertSections(test.insert, afterSection: test.after)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testDeleteSections() {
|
||||
typealias Test = (initial: [Int], delete: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [1], [0]),
|
||||
([0, 1], [0], [1]),
|
||||
([0, 1, 2], [1], [0, 2]),
|
||||
([0, 1], [1], [0]),
|
||||
([], [1], []),
|
||||
([0, 1], [100], [0, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.deleteSections(test.delete)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testMoveSectionBeforeSection() {
|
||||
typealias Test = (initial: [Int], move: Int, before: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], 1, 0, [1, 0]),
|
||||
([0, 1, 2], 2, 0, [2, 0, 1]),
|
||||
([0, 1, 2], 0, 2, [1, 0, 2]),
|
||||
([0, 1, 2], 1, 2, [0, 1, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.moveSection(test.move, beforeSection: test.before)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testMoveSectionAfterSection() {
|
||||
typealias Test = (initial: [Int], move: Int, after: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], 0, 1, [1, 0]),
|
||||
([0, 1, 2], 2, 0, [0, 2, 1]),
|
||||
([0, 1, 2], 0, 2, [1, 2, 0]),
|
||||
([0, 1, 2], 1, 0, [0, 1, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.moveSection(test.move, afterSection: test.after)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testReloadSections() {
|
||||
typealias Section = SnapshotStructure<Int, Int>.Section
|
||||
typealias Test = (initial: [Int], reload: [Int], sections: [Section])
|
||||
|
||||
let tests: [Test] = [
|
||||
([], [], []),
|
||||
([0], [1], [
|
||||
Section(id: 0, items: [], isReloaded: false)
|
||||
]
|
||||
),
|
||||
([0], [0], [
|
||||
Section(id: 0, items: [], isReloaded: true)
|
||||
]
|
||||
),
|
||||
([0, 1, 2], [2], [
|
||||
Section(id: 0, items: [], isReloaded: false),
|
||||
Section(id: 1, items: [], isReloaded: false),
|
||||
Section(id: 2, items: [], isReloaded: true)
|
||||
]
|
||||
),
|
||||
([2, 1, 0], [0, 1], [
|
||||
Section(id: 2, items: [], isReloaded: false),
|
||||
Section(id: 1, items: [], isReloaded: true),
|
||||
Section(id: 0, items: [], isReloaded: true)
|
||||
]
|
||||
)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
snapshot.reloadSections(test.reload)
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.structure.sections, test.sections)
|
||||
}
|
||||
}
|
||||
|
||||
func testAppendItems() {
|
||||
typealias Test = (initial: [Int], append: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [2, 3], [0, 1, 2, 3]),
|
||||
([], [2, 3], [2, 3]),
|
||||
([1], [0], [1, 0])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.appendItems(test.append)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testAppendItemsDuplication() {
|
||||
typealias Test = (initial: [Int], append: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([1], [1, 2], [1, 1, 2]),
|
||||
([1], [2, 2], [1, 2, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.appendItems(test.append)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testAppendItemsToSection() {
|
||||
typealias Test = (initial: [[Int]], append: [Int], section: Int, expected: [[Int]])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[], [0, 1]], [2, 3], 1, [[], [0, 1, 2, 3]]),
|
||||
([[], []], [2, 3], 1, [[], [2, 3]]),
|
||||
([[], [1]], [0], 1, [[], [1, 0]]),
|
||||
([[], [1]], [2], 0, [[2], [1]]),
|
||||
([[], [1]], [2, 3], 0, [[2, 3], [1]]),
|
||||
([[], []], [0], 0, [[0], []])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items)
|
||||
}
|
||||
|
||||
snapshot.appendItems(test.append, toSection: test.section)
|
||||
|
||||
for (section, items) in test.expected.enumerated() {
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: section), items)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func testAppendItemsToSectionDuplication() {
|
||||
typealias Test = (initial: [[Int]], append: [Int], section: Int, expected: [[Int]])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[], [1]], [1, 2], 1, [[], [1, 1, 2]]),
|
||||
([[], [1]], [2, 2], 1, [[], [1, 2, 2]])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items)
|
||||
}
|
||||
|
||||
snapshot.appendItems(test.append, toSection: test.section)
|
||||
|
||||
for (section, items) in test.expected.enumerated() {
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: section), items)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertItemsBeforeItem() {
|
||||
typealias Test = (initial: [Int], insert: [Int], before: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [2, 3], 1, [0, 2, 3, 1]),
|
||||
([0, 1], [2, 3], 0, [2, 3, 0, 1]),
|
||||
([0, 1, 2], [3, 4], 1, [0, 3, 4, 1, 2]),
|
||||
([0, 1, 2], [], 1, [0, 1, 2]),
|
||||
([0], [1], 0, [1, 0])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.insertItems(test.insert, beforeItem: test.before)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertItemsBeforeItemDuplication() {
|
||||
typealias Test = (initial: [Int], insert: [Int], before: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([1], [1, 2], 1, [1, 2, 1]),
|
||||
([1], [2, 2], 1, [2, 2, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.insertItems(test.insert, beforeItem: test.before)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertItemsAfterItem() {
|
||||
typealias Test = (initial: [Int], insert: [Int], after: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1], [2, 3], 1, [0, 1, 2, 3]),
|
||||
([0, 1], [2, 3], 0, [0, 2, 3, 1]),
|
||||
([0, 1, 2], [3, 4], 1, [0, 1, 3, 4, 2]),
|
||||
([0, 1, 2], [], 1, [0, 1, 2]),
|
||||
([0], [1], 0, [0, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.insertItems(test.insert, afterItem: test.after)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testInsertItemsAfterItemDuplication() {
|
||||
typealias Test = (initial: [Int], insert: [Int], after: Int, expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([1], [1, 2], 1, [1, 1, 2]),
|
||||
([1], [2, 2], 1, [1, 2, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1])
|
||||
snapshot.appendItems(test.initial)
|
||||
snapshot.insertItems(test.insert, afterItem: test.after)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testDeleteItems() {
|
||||
typealias Test = (initial: [[Int]], delete: [Int], expected: [[Int]])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[], [0, 1]], [0], [[], [1]]),
|
||||
([[0, 1], [2, 3]], [0, 2], [[1], [3]]),
|
||||
([[], []], [100], [[], []]),
|
||||
([[0, 1], [2, 3]], [0, 1], [[], [2, 3]]),
|
||||
([[0, 1], [2, 3]], [0], [[1], [2, 3]]),
|
||||
([[0, 1], [2, 3]], [0, 1, 2, 3], [[], []]),
|
||||
([[0, 1], [2, 3]], [0, 1, 2, 3, 4, 5], [[], []])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
snapshot.deleteItems(test.delete)
|
||||
|
||||
for (section, items) in test.expected.enumerated() {
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: section), items)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func testDeleteAllItems() {
|
||||
typealias Test = [[Int]]
|
||||
|
||||
let tests: [Test] = [
|
||||
([[], [0, 1]]),
|
||||
([[0], [1]]),
|
||||
([[], []]),
|
||||
([[0, 1], [2, 3]]),
|
||||
([[0, 1, 2], []]),
|
||||
([[], [0, 1, 2]])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
snapshot.deleteAllItems()
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers, [])
|
||||
}
|
||||
}
|
||||
|
||||
func testMoveItemsBeforeItem() {
|
||||
typealias Test = (initial: [[Int]], move: Int, before: Int, expected: [[Int]])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 0, 2, [[1], [0, 2, 3]]),
|
||||
([[0, 1], [2, 3]], 1, 0, [[1, 0], [2, 3]]),
|
||||
([[0, 1], [2, 3]], 3, 0, [[3, 0, 1], [2]]),
|
||||
([[0, 1], [2, 3]], 2, 3, [[0, 1], [2, 3]]),
|
||||
([[0], [1]], 0, 1, [[], [0, 1]]),
|
||||
([[0], [1]], 1, 0, [[1, 0], []]),
|
||||
([[], [0, 1]], 1, 0, [[], [1, 0]])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
snapshot.moveItem(test.move, beforeItem: test.before)
|
||||
|
||||
for (section, items) in test.expected.enumerated() {
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: section), items)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func testMoveItemsAfterItem() {
|
||||
typealias Test = (initial: [[Int]], move: Int, after: Int, expected: [[Int]])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 0, 2, [[1], [2, 0, 3]]),
|
||||
([[0, 1], [2, 3]], 1, 0, [[0, 1], [2, 3]]),
|
||||
([[0, 1], [2, 3]], 3, 0, [[0, 3, 1], [2]]),
|
||||
([[0, 1], [2, 3]], 2, 3, [[0, 1], [3, 2]]),
|
||||
([[0], [1]], 0, 1, [[], [1, 0]]),
|
||||
([[0], [1]], 1, 0, [[0, 1], []]),
|
||||
([[], [0, 1]], 1, 0, [[], [0, 1]])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
snapshot.moveItem(test.move, afterItem: test.after)
|
||||
|
||||
for (section, items) in test.expected.enumerated() {
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: section), items)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func testReloadItems() {
|
||||
typealias Section = SnapshotStructure<Int, Int>.Section
|
||||
typealias Item = SnapshotStructure<Int, Int>.Item
|
||||
typealias Test = (initial: [[Int]], reload: [Int], sections: [Section])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[], []], [], [
|
||||
Section(id: 0, items: [], isReloaded: false),
|
||||
Section(id: 1, items: [], isReloaded: false)
|
||||
]
|
||||
),
|
||||
([[], [0]], [0], [
|
||||
Section(id: 0, items: [], isReloaded: false),
|
||||
Section(
|
||||
id: 1,
|
||||
items: [
|
||||
Item(id: 0, isReloaded: true)
|
||||
],
|
||||
isReloaded: false
|
||||
)
|
||||
]
|
||||
),
|
||||
([[0, 1], [2]], [1, 2], [
|
||||
Section(
|
||||
id: 0,
|
||||
items: [
|
||||
Item(id: 0, isReloaded: false),
|
||||
Item(id: 1, isReloaded: true)
|
||||
],
|
||||
isReloaded: false
|
||||
),
|
||||
Section(
|
||||
id: 1,
|
||||
items: [
|
||||
Item(id: 2, isReloaded: true)
|
||||
],
|
||||
isReloaded: false
|
||||
)
|
||||
]
|
||||
),
|
||||
([[0, 1], [2, 3]], [0, 2, 3], [
|
||||
Section(
|
||||
id: 0,
|
||||
items: [
|
||||
Item(id: 0, isReloaded: true),
|
||||
Item(id: 1, isReloaded: false)
|
||||
],
|
||||
isReloaded: false
|
||||
),
|
||||
Section(
|
||||
id: 1,
|
||||
items: [
|
||||
Item(id: 2, isReloaded: true),
|
||||
Item(id: 3, isReloaded: true)
|
||||
],
|
||||
isReloaded: false
|
||||
)
|
||||
]
|
||||
)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
snapshot.reloadItems(test.reload)
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers, test.initial.flatMap { $0 })
|
||||
|
||||
XCTAssertEqual(snapshot.structure.sections, test.sections)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfItems() {
|
||||
typealias Test = (initial: [[Int]], expected: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 4),
|
||||
([[0, 1], []], 2),
|
||||
([[], [2, 3]], 2),
|
||||
([[], []], 0)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfItems, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfItemsDuplication() {
|
||||
typealias Test = (initial: [[Int]], expected: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [1, 2]], 4),
|
||||
([[0, 0], []], 2)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfItems, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfSections() {
|
||||
typealias Test = (initial: [Int], expected: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([], 0),
|
||||
([0, 1, 2], 3)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfSections, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfSectionsDuplication() {
|
||||
typealias Test = (initial: [Int], expected: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 0], 2),
|
||||
([0, 1, 1], 3)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfSections, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testItemIdentifiers() {
|
||||
typealias Test = (initial: [[Int]], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], [0, 1, 2, 3]),
|
||||
([[0, 1], []], [0, 1]),
|
||||
([[], [2, 3]], [2, 3]),
|
||||
([[], []], [])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testItemIdentifiersDuplication() {
|
||||
typealias Test = (initial: [[Int]], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [1, 2]], [0, 1, 1, 2]),
|
||||
([[0, 0], [1, 2]], [0, 0, 1, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testSectionIdentifiers() {
|
||||
typealias Test = (initial: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([], []),
|
||||
([0, 1], [0, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testSectionIdentifiersDuplication() {
|
||||
typealias Test = (initial: [Int], expected: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 0], [0, 0]),
|
||||
([0, 1, 1], [0, 1, 1])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.sectionIdentifiers, test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfItemsInSection() {
|
||||
typealias Test = (initial: [[Int]], expectedInRight: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 2),
|
||||
([[0, 1], []], 0),
|
||||
([[], [2, 3]], 2),
|
||||
([[], []], 0)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfItems(inSection: 1), test.expectedInRight)
|
||||
}
|
||||
}
|
||||
|
||||
func testNumberOfItemsInSectionDuplication() {
|
||||
typealias Test = (initial: [[Int]], expectedInRight: Int)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0], [1, 1]], 2),
|
||||
([[0, 1], [1, 2]], 2)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.numberOfItems(inSection: 1), test.expectedInRight)
|
||||
}
|
||||
}
|
||||
|
||||
func testItemIdentifiersInSection() {
|
||||
typealias Test = (initial: [[Int]], expectedInRight: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], [2, 3]),
|
||||
([[0, 1], []], []),
|
||||
([[], [2, 3]], [2, 3]),
|
||||
([[], []], [])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expectedInRight)
|
||||
}
|
||||
}
|
||||
|
||||
func testItemIdentifiersInSectionDuplication() {
|
||||
typealias Test = (initial: [[Int]], expectedInRight: [Int])
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [1, 2]], [1, 2]),
|
||||
([[0, 1], [2, 2]], [2, 2])
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.itemIdentifiers(inSection: 1), test.expectedInRight)
|
||||
}
|
||||
}
|
||||
|
||||
func testSectionIdentifiersContainingItem() {
|
||||
typealias Test = (initial: [[Int]], item: Int, expected: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 2, 1),
|
||||
([[0, 1], []], 0, 0),
|
||||
([[], [2, 3]], 2, 1),
|
||||
([[], []], 0, nil),
|
||||
([[0], [1]], 2, nil)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.sectionIdentifier(containingItem: test.item), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testSectionIdentifiersContainingDulication() {
|
||||
typealias Test = (initial: [[Int]], item: Int, expected: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [1, 2]], 2, 1),
|
||||
([[0, 1], [1, 2]], 1, 1)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.sectionIdentifier(containingItem: test.item), test.expected)
|
||||
}
|
||||
}
|
||||
|
||||
func testIndexOfItem() {
|
||||
typealias Test = (initial: [[Int]], item: Int, expectedIndex: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [2, 3]], 2, 2),
|
||||
([[0, 1], []], 0, 0),
|
||||
([[], [2, 3]], 2, 0),
|
||||
([[], []], 0, nil),
|
||||
([[0], [1]], 2, nil)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.indexOfItem(test.item), test.expectedIndex)
|
||||
}
|
||||
}
|
||||
|
||||
func testIndexOfItemDuplication() {
|
||||
typealias Test = (initial: [[Int]], item: Int, expectedIndex: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([[0, 1], [1, 2]], 2, 3),
|
||||
([[0, 1], [1, 2]], 1, 1)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
for (section, items) in test.initial.enumerated() {
|
||||
snapshot.appendSections([section])
|
||||
snapshot.appendItems(items, toSection: section)
|
||||
}
|
||||
|
||||
XCTAssertEqual(snapshot.indexOfItem(test.item), test.expectedIndex)
|
||||
}
|
||||
}
|
||||
|
||||
func testIndexOfSection() {
|
||||
typealias Test = (initial: [Int], section: Int, expectedIndex: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1, 2], 1, 1),
|
||||
([0, 1, 2], 2, 2),
|
||||
([0, 1, 2], 3, nil),
|
||||
([], 0, nil)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.indexOfSection(test.section), test.expectedIndex)
|
||||
}
|
||||
}
|
||||
|
||||
func testIndexOfSectionDuplication() {
|
||||
typealias Test = (initial: [Int], section: Int, expectedIndex: Int?)
|
||||
|
||||
let tests: [Test] = [
|
||||
([0, 1, 1, 2], 1, 1),
|
||||
([0, 1, 1, 2], 2, 3)
|
||||
]
|
||||
|
||||
for test in tests {
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections(test.initial)
|
||||
|
||||
XCTAssertEqual(snapshot.indexOfSection(test.section), test.expectedIndex)
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
|
||||
<plist version="1.0">
|
||||
<dict>
|
||||
<key>CFBundleDevelopmentRegion</key>
|
||||
<string>$(DEVELOPMENT_LANGUAGE)</string>
|
||||
<key>CFBundleExecutable</key>
|
||||
<string>$(EXECUTABLE_NAME)</string>
|
||||
<key>CFBundleIdentifier</key>
|
||||
<string>$(PRODUCT_BUNDLE_IDENTIFIER)</string>
|
||||
<key>CFBundleInfoDictionaryVersion</key>
|
||||
<string>6.0</string>
|
||||
<key>CFBundleName</key>
|
||||
<string>$(PRODUCT_NAME)</string>
|
||||
<key>CFBundlePackageType</key>
|
||||
<string>BNDL</string>
|
||||
<key>CFBundleShortVersionString</key>
|
||||
<string>1.0</string>
|
||||
<key>CFBundleVersion</key>
|
||||
<string>1</string>
|
||||
</dict>
|
||||
</plist>
|
||||
@@ -0,0 +1,58 @@
|
||||
import XCTest
|
||||
@testable import DiffableDataSources
|
||||
|
||||
final class MainThreadSerialDispatcherTests: XCTestCase {
|
||||
func testMainThread() {
|
||||
let dispatcher = MainThreadSerialDispatcher()
|
||||
let queue = DispatchQueue.global()
|
||||
let expectation = self.expectation(description: "testMainThread")
|
||||
|
||||
queue.async {
|
||||
dispatcher.dispatch {
|
||||
XCTAssertTrue(Thread.isMainThread)
|
||||
expectation.fulfill()
|
||||
}
|
||||
}
|
||||
|
||||
waitForExpectations(timeout: 1)
|
||||
}
|
||||
|
||||
func testMainThreadSerial() {
|
||||
let dispatcher = MainThreadSerialDispatcher()
|
||||
let queue = DispatchQueue.global()
|
||||
let expectation = self.expectation(description: "testMainThreadSerial")
|
||||
|
||||
var array = [Int]()
|
||||
|
||||
let group = DispatchGroup()
|
||||
|
||||
queue.async(group: group) {
|
||||
dispatcher.dispatch {
|
||||
array.append(0)
|
||||
}
|
||||
}
|
||||
|
||||
group.wait()
|
||||
|
||||
queue.async(group: group) {
|
||||
dispatcher.dispatch {
|
||||
array.append(1)
|
||||
}
|
||||
|
||||
dispatcher.dispatch {
|
||||
array.append(2)
|
||||
}
|
||||
}
|
||||
|
||||
group.wait()
|
||||
|
||||
dispatcher.dispatch {
|
||||
array.append(3)
|
||||
expectation.fulfill()
|
||||
}
|
||||
|
||||
waitForExpectations(timeout: 1) { _ in
|
||||
XCTAssertEqual(array, [0, 1, 2, 3])
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,186 @@
|
||||
#if os(iOS) || os(tvOS)
|
||||
|
||||
import XCTest
|
||||
import UIKit
|
||||
@testable import DiffableDataSources
|
||||
|
||||
final class TableViewDiffableDataSourceTests: XCTestCase {
|
||||
func testInit() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
XCTAssertTrue(tableView.dataSource === dataSource)
|
||||
}
|
||||
|
||||
func testApply() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(tableView.isPerformBatchUpdatesCalledCount, 0)
|
||||
|
||||
snapshot.appendSections([0])
|
||||
snapshot.appendItems([0])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(tableView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(tableView.isPerformBatchUpdatesCalledCount, 1)
|
||||
|
||||
snapshot.appendItems([1])
|
||||
|
||||
dataSource.apply(snapshot)
|
||||
XCTAssertEqual(tableView.isPerformBatchUpdatesCalledCount, 2)
|
||||
}
|
||||
|
||||
func testSnapshot() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
let snapshot1 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot1.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot1.itemIdentifiers, [])
|
||||
|
||||
dataSource.snapshot().appendSections([0, 1, 2])
|
||||
let snapshot2 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot2.sectionIdentifiers, [])
|
||||
XCTAssertEqual(snapshot2.itemIdentifiers, [])
|
||||
|
||||
let snapshotToApply = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshotToApply.appendSections([0, 1, 2])
|
||||
snapshotToApply.appendItems([0, 1, 2])
|
||||
dataSource.apply(snapshotToApply)
|
||||
|
||||
let snapshot3 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot3.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot3.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
dataSource.snapshot().appendSections([3, 4, 5])
|
||||
|
||||
let snapshot4 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot4.sectionIdentifiers, [0, 1, 2])
|
||||
XCTAssertEqual(snapshot4.itemIdentifiers, [0, 1, 2])
|
||||
|
||||
snapshot4.appendSections([3, 4, 5])
|
||||
snapshot4.appendItems([3, 4, 5])
|
||||
dataSource.apply(snapshot4)
|
||||
|
||||
let snapshot5 = dataSource.snapshot()
|
||||
XCTAssertEqual(snapshot5.sectionIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
XCTAssertEqual(snapshot5.itemIdentifiers, [0, 1, 2, 3, 4, 5])
|
||||
}
|
||||
|
||||
func testItemIdentifier() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 1, section: 0)), 1)
|
||||
XCTAssertEqual(dataSource.itemIdentifier(for: IndexPath(item: 100, section: 100)), nil)
|
||||
}
|
||||
|
||||
func testIndexPath() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.indexPath(for: 2), IndexPath(item: 2, section: 0))
|
||||
XCTAssertEqual(dataSource.indexPath(for: 100), nil)
|
||||
}
|
||||
|
||||
func testNumberOfSections() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: tableView), 0)
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.numberOfSections(in: tableView), 3)
|
||||
}
|
||||
|
||||
func testNumberOfRowsInSection() {
|
||||
let tableView = MockTableView()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
UITableViewCell()
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(dataSource.tableView(tableView, numberOfRowsInSection: 0), 3)
|
||||
}
|
||||
|
||||
func testCellForRowAt() {
|
||||
let tableView = MockTableView()
|
||||
let cell = UITableViewCell()
|
||||
let dataSource = TableViewDiffableDataSource<Int, Int>(tableView: tableView) { _, _, _ in
|
||||
cell
|
||||
}
|
||||
|
||||
let snapshot = DiffableDataSourceSnapshot<Int, Int>()
|
||||
snapshot.appendSections([0, 1, 2])
|
||||
snapshot.appendItems([0, 1, 2], toSection: 0)
|
||||
dataSource.apply(snapshot)
|
||||
|
||||
XCTAssertEqual(
|
||||
dataSource.tableView(tableView, cellForRowAt: IndexPath(item: 1, section: 0)),
|
||||
cell
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
final class MockTableView: UITableView {
|
||||
var isPerformBatchUpdatesCalledCount = 0
|
||||
|
||||
init() {
|
||||
super.init(frame: .zero, style: .plain)
|
||||
|
||||
let window = UIWindow()
|
||||
window.addSubview(self)
|
||||
}
|
||||
|
||||
@available(*, unavailable)
|
||||
required init?(coder aDecoder: NSCoder) {
|
||||
fatalError("init(coder:) has not been implemented")
|
||||
}
|
||||
|
||||
override func performBatchUpdates(_ updates: (() -> Void)?, completion: ((Bool) -> Void)? = nil) {
|
||||
isPerformBatchUpdatesCalledCount += 1
|
||||
updates?()
|
||||
completion?(true)
|
||||
}
|
||||
|
||||
override func insertSections(_ sections: IndexSet, with animation: RowAnimation) {}
|
||||
override func insertRows(at indexPaths: [IndexPath], with animation: RowAnimation) {}
|
||||
}
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,22 @@
|
||||
MACOSX_DEPLOYMENT_TARGET = 10.11
|
||||
IPHONEOS_DEPLOYMENT_TARGET = 9.0
|
||||
TVOS_DEPLOYMENT_TARGET = 9.0
|
||||
|
||||
SDKROOT =
|
||||
SUPPORTED_PLATFORMS = macosx iphoneos iphonesimulator appletvos appletvsimulator
|
||||
TARGETED_DEVICE_FAMILY = 1,2,3
|
||||
VALID_ARCHS[sdk=macosx*] = i386 x86_64
|
||||
VALID_ARCHS[sdk=iphoneos*] = arm64 armv7 armv7s
|
||||
VALID_ARCHS[sdk=iphonesimulator*] = i386 x86_64
|
||||
VALID_ARCHS[sdk=appletv*] = arm64
|
||||
VALID_ARCHS[sdk=appletvsimulator*] = x86_64
|
||||
|
||||
CODE_SIGN_IDENTITY =
|
||||
CODE_SIGN_STYLE = Manual
|
||||
INSTALL_PATH = $(LOCAL_LIBRARY_DIR)/Frameworks
|
||||
SKIP_INSTALL = YES
|
||||
DYLIB_COMPATIBILITY_VERSION = 1
|
||||
DYLIB_CURRENT_VERSION = 1
|
||||
DYLIB_INSTALL_NAME_BASE = @rpath
|
||||
LD_RUNPATH_SEARCH_PATHS = $(inherited) @executable_path/../Frameworks @loader_path/Frameworks @loader_path/../Frameworks
|
||||
DEFINES_MODULE = NO
|
||||
|
After Width: | Height: | Size: 2.7 MiB |
|
After Width: | Height: | Size: 1.3 MiB |
@@ -0,0 +1,41 @@
|
||||
trigger:
|
||||
- master
|
||||
|
||||
jobs:
|
||||
- job: macOS
|
||||
pool:
|
||||
vmImage: 'macOS 10.14'
|
||||
strategy:
|
||||
maxParallel: 10
|
||||
matrix:
|
||||
xcode10_2:
|
||||
DEVELOPER_DIR: /Applications/Xcode_10.2.app
|
||||
steps:
|
||||
- checkout: self
|
||||
submodules: true
|
||||
- script: xcodebuild -version
|
||||
displayName: xcodebuild -version
|
||||
condition: succeededOrFailed()
|
||||
- script: |
|
||||
set -o pipefail &&
|
||||
xcodebuild build-for-testing test-without-building -workspace DiffableDataSources.xcworkspace -scheme DiffableDataSources -configuration Release ENABLE_TESTABILITY=YES |
|
||||
xcpretty -c -r junit -o build/reports/xcodebuild-macOS.xml
|
||||
displayName: xcodebuild test maxOS
|
||||
condition: succeededOrFailed()
|
||||
- script: |
|
||||
set -o pipefail &&
|
||||
xcodebuild build-for-testing test-without-building -workspace DiffableDataSources.xcworkspace -scheme DiffableDataSources -configuration Release -sdk iphonesimulator -destination 'platform=iOS Simulator,name=iPhone Xs' ENABLE_TESTABILITY=YES |
|
||||
xcpretty -c -r junit -o build/reports/xcodebuild-iOS.xml
|
||||
displayName: xcodebuild test iOS
|
||||
condition: succeededOrFailed()
|
||||
- script: |
|
||||
set -o pipefail &&
|
||||
xcodebuild build-for-testing test-without-building -workspace DiffableDataSources.xcworkspace -scheme DiffableDataSources -configuration Release -sdk appletvsimulator -destination 'platform=tvOS Simulator,name=Apple TV' ENABLE_TESTABILITY=YES |
|
||||
xcpretty -c -r junit -o build/reports/xcodebuild-tvOS.xml
|
||||
displayName: xcodebuild test tvOS
|
||||
condition: succeededOrFailed()
|
||||
- task: PublishTestResults@2
|
||||
inputs:
|
||||
testRunner: JUnit
|
||||
testResultsFiles: build/reports/**
|
||||
condition: succeededOrFailed()
|
||||
@@ -0,0 +1,686 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>CollectionViewDiffableDataSource Class Reference</title>
|
||||
<link rel="stylesheet" type="text/css" href="../css/jazzy.css" />
|
||||
<link rel="stylesheet" type="text/css" href="../css/highlight.css" />
|
||||
<meta charset="utf-8">
|
||||
<script src="../js/jquery.min.js" defer></script>
|
||||
<script src="../js/jazzy.js" defer></script>
|
||||
|
||||
<script src="../js/lunr.min.js" defer></script>
|
||||
<script src="../js/typeahead.jquery.js" defer></script>
|
||||
<script src="../js/jazzy.search.js" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<a name="//apple_ref/swift/Class/CollectionViewDiffableDataSource" class="dashAnchor"></a>
|
||||
|
||||
<a title="CollectionViewDiffableDataSource Class Reference"></a>
|
||||
|
||||
<header class="header">
|
||||
<p class="header-col header-col--primary">
|
||||
<a class="header-link" href="../index.html">
|
||||
DiffableDataSources Docs
|
||||
</a>
|
||||
(100% documented)
|
||||
</p>
|
||||
|
||||
<p class="header-col--secondary">
|
||||
<form role="search" action="../search.json">
|
||||
<input type="text" placeholder="Search documentation" data-typeahead>
|
||||
</form>
|
||||
</p>
|
||||
|
||||
<p class="header-col header-col--secondary">
|
||||
<a class="header-link" href="https://github.com/ra1028/DiffableDataSources">
|
||||
<img class="header-icon" src="../img/gh.png"/>
|
||||
View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
|
||||
</header>
|
||||
|
||||
<p class="breadcrumbs">
|
||||
<a class="breadcrumb" href="../index.html">DiffableDataSources Reference</a>
|
||||
<img class="carat" src="../img/carat.png" />
|
||||
CollectionViewDiffableDataSource Class Reference
|
||||
</p>
|
||||
|
||||
<div class="content-wrapper">
|
||||
<nav class="navigation">
|
||||
<ul class="nav-groups">
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="../DataSources.html">DataSources</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/TableViewDiffableDataSource.html">TableViewDiffableDataSource</a>
|
||||
</li>
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/CollectionViewDiffableDataSource.html">CollectionViewDiffableDataSource</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="../Snapshot.html">Snapshot</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
<article class="main-content">
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<h1>CollectionViewDiffableDataSource</h1>
|
||||
<div class="declaration">
|
||||
<div class="language">
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">class</span> <span class="kt">CollectionViewDiffableDataSource</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span> <span class="p">:</span> <span class="kt">NSObject</span><span class="p">,</span> <span class="kt">UICollectionViewDataSource</span> <span class="k">where</span> <span class="kt">SectionIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<p>A class for backporting <code>UICollectionViewDiffableDataSource</code> introduced in iOS 13.0+, tvOS 13.0+.
|
||||
Represents the data model object for <code>UICollectionView</code> that can be applies the
|
||||
changes with automatic diffing.</p>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<div class="task-group">
|
||||
<ul class="item-container">
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC12CellProvidera"></a>
|
||||
<a name="//apple_ref/swift/Alias/CellProvider" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC12CellProvidera">CellProvider</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>The type of closure providing the cell.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">typealias</span> <span class="kt">CellProvider</span> <span class="o">=</span> <span class="p">(</span><span class="kt">UICollectionView</span><span class="p">,</span> <span class="kt">IndexPath</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UICollectionViewCell</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC013SupplementaryE8Providera"></a>
|
||||
<a name="//apple_ref/swift/Alias/SupplementaryViewProvider" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC013SupplementaryE8Providera">SupplementaryViewProvider</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>The type of closure providing the supplementary view for element of kind.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">typealias</span> <span class="kt">SupplementaryViewProvider</span> <span class="o">=</span> <span class="p">(</span><span class="kt">UICollectionView</span><span class="p">,</span> <span class="kt">String</span><span class="p">,</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UICollectionReusableView</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC013supplementaryE8ProviderSo020UICollectionReusableE0CSgSo0iE0C_SS10Foundation9IndexPathVtcSgvp"></a>
|
||||
<a name="//apple_ref/swift/Property/supplementaryViewProvider" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC013supplementaryE8ProviderSo020UICollectionReusableE0CSgSo0iE0C_SS10Foundation9IndexPathVtcSgvp">supplementaryViewProvider</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>A closure to dequeue the views for element of kind.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="k">var</span> <span class="nv">supplementaryViewProvider</span><span class="p">:</span> <span class="kt">CollectionViewDiffableDataSource</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">>.</span><span class="kt"><a href="../Classes/CollectionViewDiffableDataSource.html#/s:19DiffableDataSources014CollectionViewaB6SourceC013SupplementaryE8Providera">SupplementaryViewProvider</a></span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE012cellProviderACyxq_GSo012UICollectionE0C_So0jE4CellCSgAH_10Foundation9IndexPathVq_tctcfc"></a>
|
||||
<a name="//apple_ref/swift/Method/init(collectionView:cellProvider:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE012cellProviderACyxq_GSo012UICollectionE0C_So0jE4CellCSgAH_10Foundation9IndexPathVq_tctcfc">init(collectionView:cellProvider:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Creates a new data source.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="nf">init</span><span class="p">(</span><span class="nv">collectionView</span><span class="p">:</span> <span class="kt">UICollectionView</span><span class="p">,</span> <span class="nv">cellProvider</span><span class="p">:</span> <span class="kd">@escaping</span> <span class="kt"><a href="../Classes/CollectionViewDiffableDataSource.html#/s:19DiffableDataSources014CollectionViewaB6SourceC12CellProvidera">CellProvider</a></span><span class="p">)</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>collectionView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A collection view instance to be managed.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>cellProvider</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A closure to dequeue the cell for items.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC5apply_20animatingDifferencesyAA0abF8SnapshotCyxq_G_SbtF"></a>
|
||||
<a name="//apple_ref/swift/Method/apply(_:animatingDifferences:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC5apply_20animatingDifferencesyAA0abF8SnapshotCyxq_G_SbtF">apply(_:animatingDifferences:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Applies given snapshot to perform automatic diffing update.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">apply</span><span class="p">(</span><span class="n">_</span> <span class="nv">snapshot</span><span class="p">:</span> <span class="kt"><a href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a></span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span><span class="p">,</span> <span class="nv">animatingDifferences</span><span class="p">:</span> <span class="kt">Bool</span> <span class="o">=</span> <span class="kc">true</span><span class="p">)</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>snapshot</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A snapshot object to be applied to data model.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>animatingDifferences</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A Boolean value indicating whether to update with
|
||||
diffing animation.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC8snapshotAA0abF8SnapshotCyxq_GyF"></a>
|
||||
<a name="//apple_ref/swift/Method/snapshot()" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC8snapshotAA0abF8SnapshotCyxq_GyF">snapshot()</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns a new snapshot object of current state.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">snapshot</span><span class="p">()</span> <span class="o">-></span> <span class="kt"><a href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a></span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>A new snapshot object of current state.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC14itemIdentifier3forq_Sg10Foundation9IndexPathV_tF"></a>
|
||||
<a name="//apple_ref/swift/Method/itemIdentifier(for:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC14itemIdentifier3forq_Sg10Foundation9IndexPathV_tF">itemIdentifier(for:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns an item identifier for given index path.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">itemIdentifier</span><span class="p">(</span><span class="k">for</span> <span class="nv">indexPath</span><span class="p">:</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">ItemIdentifierType</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>indexPath</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index path for the item identifier.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>An item identifier for given index path.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC9indexPath3for10Foundation05IndexH0VSgq__tF"></a>
|
||||
<a name="//apple_ref/swift/Method/indexPath(for:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC9indexPath3for10Foundation05IndexH0VSgq__tF">indexPath(for:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns an index path for given item identifier.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">indexPath</span><span class="p">(</span><span class="k">for</span> <span class="nv">itemIdentifier</span><span class="p">:</span> <span class="kt">ItemIdentifierType</span><span class="p">)</span> <span class="o">-></span> <span class="kt">IndexPath</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>itemIdentifier</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An identifier of item.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>An index path for given item identifier.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC16numberOfSections2inSiSo012UICollectionE0C_tF"></a>
|
||||
<a name="//apple_ref/swift/Method/numberOfSections(in:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC16numberOfSections2inSiSo012UICollectionE0C_tF">numberOfSections(in:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns the number of sections in the data source.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">numberOfSections</span><span class="p">(</span><span class="k">in</span> <span class="nv">collectionView</span><span class="p">:</span> <span class="kt">UICollectionView</span><span class="p">)</span> <span class="o">-></span> <span class="kt">Int</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>collectionView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A collection view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>The number of sections in the data source.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_22numberOfItemsInSectionSiSo012UICollectionE0C_SitF"></a>
|
||||
<a name="//apple_ref/swift/Method/collectionView(_:numberOfItemsInSection:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_22numberOfItemsInSectionSiSo012UICollectionE0C_SitF">collectionView(_:numberOfItemsInSection:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns the number of items in the specified section.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">collectionView</span><span class="p">(</span><span class="n">_</span> <span class="nv">collectionView</span><span class="p">:</span> <span class="kt">UICollectionView</span><span class="p">,</span> <span class="n">numberOfItemsInSection</span> <span class="nv">section</span><span class="p">:</span> <span class="kt">Int</span><span class="p">)</span> <span class="o">-></span> <span class="kt">Int</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>collectionView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A collection view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>section</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index of section.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>The number of items in the specified section.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_13cellForItemAtSo012UICollectionE4CellCSo0lE0C_10Foundation9IndexPathVtF"></a>
|
||||
<a name="//apple_ref/swift/Method/collectionView(_:cellForItemAt:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_13cellForItemAtSo012UICollectionE4CellCSo0lE0C_10Foundation9IndexPathVtF">collectionView(_:cellForItemAt:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns a cell for item at specified index path.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">func</span> <span class="nf">collectionView</span><span class="p">(</span><span class="n">_</span> <span class="nv">collectionView</span><span class="p">:</span> <span class="kt">UICollectionView</span><span class="p">,</span> <span class="n">cellForItemAt</span> <span class="nv">indexPath</span><span class="p">:</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UICollectionViewCell</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>collectionView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A collection view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>indexPath</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index path for cell.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>A cell for row at specified index path.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_33viewForSupplementaryElementOfKind2atSo020UICollectionReusableE0CSo0oE0C_SS10Foundation9IndexPathVtF"></a>
|
||||
<a name="//apple_ref/swift/Method/collectionView(_:viewForSupplementaryElementOfKind:at:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC010collectionE0_33viewForSupplementaryElementOfKind2atSo020UICollectionReusableE0CSo0oE0C_SS10Foundation9IndexPathVtF">collectionView(_:viewForSupplementaryElementOfKind:at:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns a supplementary view for element of kind at specified index path.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">func</span> <span class="nf">collectionView</span><span class="p">(</span><span class="n">_</span> <span class="nv">collectionView</span><span class="p">:</span> <span class="kt">UICollectionView</span><span class="p">,</span> <span class="n">viewForSupplementaryElementOfKind</span> <span class="nv">kind</span><span class="p">:</span> <span class="kt">String</span><span class="p">,</span> <span class="n">at</span> <span class="nv">indexPath</span><span class="p">:</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UICollectionReusableView</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>collectionView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A collection view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>kind</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>The kind of element to be display.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>indexPath</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index path for supplementary view.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>A supplementary view for element of kind at specified index path.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
<section class="footer">
|
||||
<p>© 2019 <a class="link" href="https://github.com/ra1028" target="_blank" rel="external">Ryo Aoyama</a>. All rights reserved. (Last updated: 2019-06-24)</p>
|
||||
<p>Generated by <a class="link" href="https://github.com/realm/jazzy" target="_blank" rel="external">jazzy ♪♫ v0.9.4</a>, a <a class="link" href="https://realm.io" target="_blank" rel="external">Realm</a> project.</p>
|
||||
</section>
|
||||
</body>
|
||||
</div>
|
||||
</html>
|
||||
@@ -0,0 +1,585 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>TableViewDiffableDataSource Class Reference</title>
|
||||
<link rel="stylesheet" type="text/css" href="../css/jazzy.css" />
|
||||
<link rel="stylesheet" type="text/css" href="../css/highlight.css" />
|
||||
<meta charset="utf-8">
|
||||
<script src="../js/jquery.min.js" defer></script>
|
||||
<script src="../js/jazzy.js" defer></script>
|
||||
|
||||
<script src="../js/lunr.min.js" defer></script>
|
||||
<script src="../js/typeahead.jquery.js" defer></script>
|
||||
<script src="../js/jazzy.search.js" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<a name="//apple_ref/swift/Class/TableViewDiffableDataSource" class="dashAnchor"></a>
|
||||
|
||||
<a title="TableViewDiffableDataSource Class Reference"></a>
|
||||
|
||||
<header class="header">
|
||||
<p class="header-col header-col--primary">
|
||||
<a class="header-link" href="../index.html">
|
||||
DiffableDataSources Docs
|
||||
</a>
|
||||
(100% documented)
|
||||
</p>
|
||||
|
||||
<p class="header-col--secondary">
|
||||
<form role="search" action="../search.json">
|
||||
<input type="text" placeholder="Search documentation" data-typeahead>
|
||||
</form>
|
||||
</p>
|
||||
|
||||
<p class="header-col header-col--secondary">
|
||||
<a class="header-link" href="https://github.com/ra1028/DiffableDataSources">
|
||||
<img class="header-icon" src="../img/gh.png"/>
|
||||
View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
|
||||
</header>
|
||||
|
||||
<p class="breadcrumbs">
|
||||
<a class="breadcrumb" href="../index.html">DiffableDataSources Reference</a>
|
||||
<img class="carat" src="../img/carat.png" />
|
||||
TableViewDiffableDataSource Class Reference
|
||||
</p>
|
||||
|
||||
<div class="content-wrapper">
|
||||
<nav class="navigation">
|
||||
<ul class="nav-groups">
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="../DataSources.html">DataSources</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/TableViewDiffableDataSource.html">TableViewDiffableDataSource</a>
|
||||
</li>
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/CollectionViewDiffableDataSource.html">CollectionViewDiffableDataSource</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="../Snapshot.html">Snapshot</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
<article class="main-content">
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<h1>TableViewDiffableDataSource</h1>
|
||||
<div class="declaration">
|
||||
<div class="language">
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">class</span> <span class="kt">TableViewDiffableDataSource</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span> <span class="p">:</span> <span class="kt">NSObject</span><span class="p">,</span> <span class="kt">UITableViewDataSource</span> <span class="k">where</span> <span class="kt">SectionIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<p>A class for backporting <code>UITableViewDiffableDataSource</code> introduced in iOS 13.0+, tvOS 13.0+.
|
||||
Represents the data model object for <code>UITableView</code> that can be applies the
|
||||
changes with automatic diffing.</p>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<div class="task-group">
|
||||
<ul class="item-container">
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC12CellProvidera"></a>
|
||||
<a name="//apple_ref/swift/Alias/CellProvider" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC12CellProvidera">CellProvider</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>The type of closure providing the cell.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">typealias</span> <span class="kt">CellProvider</span> <span class="o">=</span> <span class="p">(</span><span class="kt">UITableView</span><span class="p">,</span> <span class="kt">IndexPath</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UITableViewCell</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC19defaultRowAnimationSo07UITableehI0Vvp"></a>
|
||||
<a name="//apple_ref/swift/Property/defaultRowAnimation" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC19defaultRowAnimationSo07UITableehI0Vvp">defaultRowAnimation</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>The default animation to updating the views.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="k">var</span> <span class="nv">defaultRowAnimation</span><span class="p">:</span> <span class="kt">UITableView</span><span class="o">.</span><span class="kt">RowAnimation</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC05tableE012cellProviderACyxq_GSo07UITableE0C_So0jE4CellCSgAH_10Foundation9IndexPathVq_tctcfc"></a>
|
||||
<a name="//apple_ref/swift/Method/init(tableView:cellProvider:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC05tableE012cellProviderACyxq_GSo07UITableE0C_So0jE4CellCSgAH_10Foundation9IndexPathVq_tctcfc">init(tableView:cellProvider:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Creates a new data source.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="nf">init</span><span class="p">(</span><span class="nv">tableView</span><span class="p">:</span> <span class="kt">UITableView</span><span class="p">,</span> <span class="nv">cellProvider</span><span class="p">:</span> <span class="kd">@escaping</span> <span class="kt"><a href="../Classes/TableViewDiffableDataSource.html#/s:19DiffableDataSources09TableViewaB6SourceC12CellProvidera">CellProvider</a></span><span class="p">)</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>tableView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A table view instance to be managed.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>cellProvider</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A closure to dequeue the cell for rows.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC5apply_20animatingDifferencesyAA0abF8SnapshotCyxq_G_SbtF"></a>
|
||||
<a name="//apple_ref/swift/Method/apply(_:animatingDifferences:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC5apply_20animatingDifferencesyAA0abF8SnapshotCyxq_G_SbtF">apply(_:animatingDifferences:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Applies given snapshot to perform automatic diffing update.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">apply</span><span class="p">(</span><span class="n">_</span> <span class="nv">snapshot</span><span class="p">:</span> <span class="kt"><a href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a></span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span><span class="p">,</span> <span class="nv">animatingDifferences</span><span class="p">:</span> <span class="kt">Bool</span> <span class="o">=</span> <span class="kc">true</span><span class="p">)</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>snapshot</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A snapshot object to be applied to data model.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>animatingDifferences</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A Boolean value indicating whether to update with
|
||||
diffing animation.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC8snapshotAA0abF8SnapshotCyxq_GyF"></a>
|
||||
<a name="//apple_ref/swift/Method/snapshot()" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC8snapshotAA0abF8SnapshotCyxq_GyF">snapshot()</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns a new snapshot object of current state.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">snapshot</span><span class="p">()</span> <span class="o">-></span> <span class="kt"><a href="../Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a></span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>A new snapshot object of current state.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC14itemIdentifier3forq_Sg10Foundation9IndexPathV_tF"></a>
|
||||
<a name="//apple_ref/swift/Method/itemIdentifier(for:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC14itemIdentifier3forq_Sg10Foundation9IndexPathV_tF">itemIdentifier(for:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns an item identifier for given index path.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">itemIdentifier</span><span class="p">(</span><span class="k">for</span> <span class="nv">indexPath</span><span class="p">:</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">ItemIdentifierType</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>indexPath</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index path for the item identifier.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>An item identifier for given index path.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC9indexPath3for10Foundation05IndexH0VSgq__tF"></a>
|
||||
<a name="//apple_ref/swift/Method/indexPath(for:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC9indexPath3for10Foundation05IndexH0VSgq__tF">indexPath(for:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns an index path for given item identifier.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">indexPath</span><span class="p">(</span><span class="k">for</span> <span class="nv">itemIdentifier</span><span class="p">:</span> <span class="kt">ItemIdentifierType</span><span class="p">)</span> <span class="o">-></span> <span class="kt">IndexPath</span><span class="p">?</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>itemIdentifier</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An identifier of item.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>An index path for given item identifier.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC16numberOfSections2inSiSo07UITableE0C_tF"></a>
|
||||
<a name="//apple_ref/swift/Method/numberOfSections(in:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC16numberOfSections2inSiSo07UITableE0C_tF">numberOfSections(in:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns the number of sections in the data source.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">numberOfSections</span><span class="p">(</span><span class="k">in</span> <span class="nv">tableView</span><span class="p">:</span> <span class="kt">UITableView</span><span class="p">)</span> <span class="o">-></span> <span class="kt">Int</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>tableView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A table view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>The number of sections in the data source.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC05tableE0_21numberOfRowsInSectionSiSo07UITableE0C_SitF"></a>
|
||||
<a name="//apple_ref/swift/Method/tableView(_:numberOfRowsInSection:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC05tableE0_21numberOfRowsInSectionSiSo07UITableE0C_SitF">tableView(_:numberOfRowsInSection:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns the number of items in the specified section.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">func</span> <span class="nf">tableView</span><span class="p">(</span><span class="n">_</span> <span class="nv">tableView</span><span class="p">:</span> <span class="kt">UITableView</span><span class="p">,</span> <span class="n">numberOfRowsInSection</span> <span class="nv">section</span><span class="p">:</span> <span class="kt">Int</span><span class="p">)</span> <span class="o">-></span> <span class="kt">Int</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>tableView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A table view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>section</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index of section.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>The number of items in the specified section.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC05tableE0_12cellForRowAtSo07UITableE4CellCSo0lE0C_10Foundation9IndexPathVtF"></a>
|
||||
<a name="//apple_ref/swift/Method/tableView(_:cellForRowAt:)" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC05tableE0_12cellForRowAtSo07UITableE4CellCSo0lE0C_10Foundation9IndexPathVtF">tableView(_:cellForRowAt:)</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>Returns a cell for row at specified index path.</p>
|
||||
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">func</span> <span class="nf">tableView</span><span class="p">(</span><span class="n">_</span> <span class="nv">tableView</span><span class="p">:</span> <span class="kt">UITableView</span><span class="p">,</span> <span class="n">cellForRowAt</span> <span class="nv">indexPath</span><span class="p">:</span> <span class="kt">IndexPath</span><span class="p">)</span> <span class="o">-></span> <span class="kt">UITableViewCell</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Parameters</h4>
|
||||
<table class="graybox">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>tableView</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>A table view instance managed by <code>self</code>.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td>
|
||||
<code>
|
||||
<em>indexPath</em>
|
||||
</code>
|
||||
</td>
|
||||
<td>
|
||||
<div>
|
||||
<p>An index path for cell.</p>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
</div>
|
||||
<div>
|
||||
<h4>Return Value</h4>
|
||||
<p>A cell for row at specified index path.</p>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
<section class="footer">
|
||||
<p>© 2019 <a class="link" href="https://github.com/ra1028" target="_blank" rel="external">Ryo Aoyama</a>. All rights reserved. (Last updated: 2019-06-24)</p>
|
||||
<p>Generated by <a class="link" href="https://github.com/realm/jazzy" target="_blank" rel="external">jazzy ♪♫ v0.9.4</a>, a <a class="link" href="https://realm.io" target="_blank" rel="external">Realm</a> project.</p>
|
||||
</section>
|
||||
</body>
|
||||
</div>
|
||||
</html>
|
||||
@@ -0,0 +1,164 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>DataSources Reference</title>
|
||||
<link rel="stylesheet" type="text/css" href="css/jazzy.css" />
|
||||
<link rel="stylesheet" type="text/css" href="css/highlight.css" />
|
||||
<meta charset="utf-8">
|
||||
<script src="js/jquery.min.js" defer></script>
|
||||
<script src="js/jazzy.js" defer></script>
|
||||
|
||||
<script src="js/lunr.min.js" defer></script>
|
||||
<script src="js/typeahead.jquery.js" defer></script>
|
||||
<script src="js/jazzy.search.js" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<a name="//apple_ref/swift/Section/DataSources" class="dashAnchor"></a>
|
||||
|
||||
<a title="DataSources Reference"></a>
|
||||
|
||||
<header class="header">
|
||||
<p class="header-col header-col--primary">
|
||||
<a class="header-link" href="index.html">
|
||||
DiffableDataSources Docs
|
||||
</a>
|
||||
(100% documented)
|
||||
</p>
|
||||
|
||||
<p class="header-col--secondary">
|
||||
<form role="search" action="search.json">
|
||||
<input type="text" placeholder="Search documentation" data-typeahead>
|
||||
</form>
|
||||
</p>
|
||||
|
||||
<p class="header-col header-col--secondary">
|
||||
<a class="header-link" href="https://github.com/ra1028/DiffableDataSources">
|
||||
<img class="header-icon" src="img/gh.png"/>
|
||||
View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
|
||||
</header>
|
||||
|
||||
<p class="breadcrumbs">
|
||||
<a class="breadcrumb" href="index.html">DiffableDataSources Reference</a>
|
||||
<img class="carat" src="img/carat.png" />
|
||||
DataSources Reference
|
||||
</p>
|
||||
|
||||
<div class="content-wrapper">
|
||||
<nav class="navigation">
|
||||
<ul class="nav-groups">
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="DataSources.html">DataSources</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/TableViewDiffableDataSource.html">TableViewDiffableDataSource</a>
|
||||
</li>
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/CollectionViewDiffableDataSource.html">CollectionViewDiffableDataSource</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="Snapshot.html">Snapshot</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
<article class="main-content">
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<h1>DataSources</h1>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<div class="task-group">
|
||||
<ul class="item-container">
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources09TableViewaB6SourceC"></a>
|
||||
<a name="//apple_ref/swift/Class/TableViewDiffableDataSource" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources09TableViewaB6SourceC">TableViewDiffableDataSource</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>A class for backporting <code>UITableViewDiffableDataSource</code> introduced in iOS 13.0+, tvOS 13.0+.
|
||||
Represents the data model object for <code>UITableView</code> that can be applies the
|
||||
changes with automatic diffing.</p>
|
||||
|
||||
<a href="Classes/TableViewDiffableDataSource.html" class="slightly-smaller">See more</a>
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">class</span> <span class="kt">TableViewDiffableDataSource</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span> <span class="p">:</span> <span class="kt">NSObject</span><span class="p">,</span> <span class="kt">UITableViewDataSource</span> <span class="k">where</span> <span class="kt">SectionIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
<div class="task-group">
|
||||
<ul class="item-container">
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources014CollectionViewaB6SourceC"></a>
|
||||
<a name="//apple_ref/swift/Class/CollectionViewDiffableDataSource" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources014CollectionViewaB6SourceC">CollectionViewDiffableDataSource</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>A class for backporting <code>UICollectionViewDiffableDataSource</code> introduced in iOS 13.0+, tvOS 13.0+.
|
||||
Represents the data model object for <code>UICollectionView</code> that can be applies the
|
||||
changes with automatic diffing.</p>
|
||||
|
||||
<a href="Classes/CollectionViewDiffableDataSource.html" class="slightly-smaller">See more</a>
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">open</span> <span class="kd">class</span> <span class="kt">CollectionViewDiffableDataSource</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span> <span class="p">:</span> <span class="kt">NSObject</span><span class="p">,</span> <span class="kt">UICollectionViewDataSource</span> <span class="k">where</span> <span class="kt">SectionIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
<section class="footer">
|
||||
<p>© 2019 <a class="link" href="https://github.com/ra1028" target="_blank" rel="external">Ryo Aoyama</a>. All rights reserved. (Last updated: 2019-06-24)</p>
|
||||
<p>Generated by <a class="link" href="https://github.com/realm/jazzy" target="_blank" rel="external">jazzy ♪♫ v0.9.4</a>, a <a class="link" href="https://realm.io" target="_blank" rel="external">Realm</a> project.</p>
|
||||
</section>
|
||||
</body>
|
||||
</div>
|
||||
</html>
|
||||
@@ -0,0 +1,129 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>Snapshot Reference</title>
|
||||
<link rel="stylesheet" type="text/css" href="css/jazzy.css" />
|
||||
<link rel="stylesheet" type="text/css" href="css/highlight.css" />
|
||||
<meta charset="utf-8">
|
||||
<script src="js/jquery.min.js" defer></script>
|
||||
<script src="js/jazzy.js" defer></script>
|
||||
|
||||
<script src="js/lunr.min.js" defer></script>
|
||||
<script src="js/typeahead.jquery.js" defer></script>
|
||||
<script src="js/jazzy.search.js" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<a name="//apple_ref/swift/Section/Snapshot" class="dashAnchor"></a>
|
||||
|
||||
<a title="Snapshot Reference"></a>
|
||||
|
||||
<header class="header">
|
||||
<p class="header-col header-col--primary">
|
||||
<a class="header-link" href="index.html">
|
||||
DiffableDataSources Docs
|
||||
</a>
|
||||
(100% documented)
|
||||
</p>
|
||||
|
||||
<p class="header-col--secondary">
|
||||
<form role="search" action="search.json">
|
||||
<input type="text" placeholder="Search documentation" data-typeahead>
|
||||
</form>
|
||||
</p>
|
||||
|
||||
<p class="header-col header-col--secondary">
|
||||
<a class="header-link" href="https://github.com/ra1028/DiffableDataSources">
|
||||
<img class="header-icon" src="img/gh.png"/>
|
||||
View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
|
||||
</header>
|
||||
|
||||
<p class="breadcrumbs">
|
||||
<a class="breadcrumb" href="index.html">DiffableDataSources Reference</a>
|
||||
<img class="carat" src="img/carat.png" />
|
||||
Snapshot Reference
|
||||
</p>
|
||||
|
||||
<div class="content-wrapper">
|
||||
<nav class="navigation">
|
||||
<ul class="nav-groups">
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="DataSources.html">DataSources</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/TableViewDiffableDataSource.html">TableViewDiffableDataSource</a>
|
||||
</li>
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/CollectionViewDiffableDataSource.html">CollectionViewDiffableDataSource</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="Snapshot.html">Snapshot</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
<article class="main-content">
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<h1>Snapshot</h1>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
<div class="task-group">
|
||||
<ul class="item-container">
|
||||
<li class="item">
|
||||
<div>
|
||||
<code>
|
||||
<a name="/s:19DiffableDataSources0aB14SourceSnapshotC"></a>
|
||||
<a name="//apple_ref/swift/Class/DiffableDataSourceSnapshot" class="dashAnchor"></a>
|
||||
<a class="token" href="#/s:19DiffableDataSources0aB14SourceSnapshotC">DiffableDataSourceSnapshot</a>
|
||||
</code>
|
||||
</div>
|
||||
<div class="height-container">
|
||||
<div class="pointer-container"></div>
|
||||
<section class="section">
|
||||
<div class="pointer"></div>
|
||||
<div class="abstract">
|
||||
<p>A class for backporting <code>NSDiffableDataSourceSnapshot</code> introduced in iOS 13.0+, macOS 10.15+, tvOS 13.0+.
|
||||
Represents the mutable state of diffable data source of UI.</p>
|
||||
|
||||
<a href="Classes/DiffableDataSourceSnapshot.html" class="slightly-smaller">See more</a>
|
||||
</div>
|
||||
<div class="declaration">
|
||||
<h4>Declaration</h4>
|
||||
<div class="language">
|
||||
<p class="aside-title">Swift</p>
|
||||
<pre class="highlight swift"><code><span class="kd">public</span> <span class="kd">class</span> <span class="kt">DiffableDataSourceSnapshot</span><span class="o"><</span><span class="kt">SectionIdentifierType</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span><span class="o">></span> <span class="k">where</span> <span class="kt">SectionIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span><span class="p">,</span> <span class="kt">ItemIdentifierType</span> <span class="p">:</span> <span class="kt">Hashable</span></code></pre>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
<section class="footer">
|
||||
<p>© 2019 <a class="link" href="https://github.com/ra1028" target="_blank" rel="external">Ryo Aoyama</a>. All rights reserved. (Last updated: 2019-06-24)</p>
|
||||
<p>Generated by <a class="link" href="https://github.com/realm/jazzy" target="_blank" rel="external">jazzy ♪♫ v0.9.4</a>, a <a class="link" href="https://realm.io" target="_blank" rel="external">Realm</a> project.</p>
|
||||
</section>
|
||||
</body>
|
||||
</div>
|
||||
</html>
|
||||
@@ -0,0 +1,28 @@
|
||||
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="136" height="20">
|
||||
<linearGradient id="b" x2="0" y2="100%">
|
||||
<stop offset="0" stop-color="#bbb" stop-opacity=".1"/>
|
||||
<stop offset="1" stop-opacity=".1"/>
|
||||
</linearGradient>
|
||||
<clipPath id="a">
|
||||
<rect width="136" height="20" rx="3" fill="#fff"/>
|
||||
</clipPath>
|
||||
<g clip-path="url(#a)">
|
||||
<path fill="#555" d="M0 0h93v20H0z"/>
|
||||
<path fill="#4c1" d="M93 0h43v20H93z"/>
|
||||
<path fill="url(#b)" d="M0 0h136v20H0z"/>
|
||||
</g>
|
||||
<g fill="#fff" text-anchor="middle" font-family="DejaVu Sans,Verdana,Geneva,sans-serif" font-size="110">
|
||||
<text x="475" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="830">
|
||||
documentation
|
||||
</text>
|
||||
<text x="475" y="140" transform="scale(.1)" textLength="830">
|
||||
documentation
|
||||
</text>
|
||||
<text x="1135" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="330">
|
||||
100%
|
||||
</text>
|
||||
<text x="1135" y="140" transform="scale(.1)" textLength="330">
|
||||
100%
|
||||
</text>
|
||||
</g>
|
||||
</svg>
|
||||
|
After Width: | Height: | Size: 1.1 KiB |
@@ -0,0 +1,200 @@
|
||||
/* Credit to https://gist.github.com/wataru420/2048287 */
|
||||
.highlight {
|
||||
/* Comment */
|
||||
/* Error */
|
||||
/* Keyword */
|
||||
/* Operator */
|
||||
/* Comment.Multiline */
|
||||
/* Comment.Preproc */
|
||||
/* Comment.Single */
|
||||
/* Comment.Special */
|
||||
/* Generic.Deleted */
|
||||
/* Generic.Deleted.Specific */
|
||||
/* Generic.Emph */
|
||||
/* Generic.Error */
|
||||
/* Generic.Heading */
|
||||
/* Generic.Inserted */
|
||||
/* Generic.Inserted.Specific */
|
||||
/* Generic.Output */
|
||||
/* Generic.Prompt */
|
||||
/* Generic.Strong */
|
||||
/* Generic.Subheading */
|
||||
/* Generic.Traceback */
|
||||
/* Keyword.Constant */
|
||||
/* Keyword.Declaration */
|
||||
/* Keyword.Pseudo */
|
||||
/* Keyword.Reserved */
|
||||
/* Keyword.Type */
|
||||
/* Literal.Number */
|
||||
/* Literal.String */
|
||||
/* Name.Attribute */
|
||||
/* Name.Builtin */
|
||||
/* Name.Class */
|
||||
/* Name.Constant */
|
||||
/* Name.Entity */
|
||||
/* Name.Exception */
|
||||
/* Name.Function */
|
||||
/* Name.Namespace */
|
||||
/* Name.Tag */
|
||||
/* Name.Variable */
|
||||
/* Operator.Word */
|
||||
/* Text.Whitespace */
|
||||
/* Literal.Number.Float */
|
||||
/* Literal.Number.Hex */
|
||||
/* Literal.Number.Integer */
|
||||
/* Literal.Number.Oct */
|
||||
/* Literal.String.Backtick */
|
||||
/* Literal.String.Char */
|
||||
/* Literal.String.Doc */
|
||||
/* Literal.String.Double */
|
||||
/* Literal.String.Escape */
|
||||
/* Literal.String.Heredoc */
|
||||
/* Literal.String.Interpol */
|
||||
/* Literal.String.Other */
|
||||
/* Literal.String.Regex */
|
||||
/* Literal.String.Single */
|
||||
/* Literal.String.Symbol */
|
||||
/* Name.Builtin.Pseudo */
|
||||
/* Name.Variable.Class */
|
||||
/* Name.Variable.Global */
|
||||
/* Name.Variable.Instance */
|
||||
/* Literal.Number.Integer.Long */ }
|
||||
.highlight .c {
|
||||
color: #999988;
|
||||
font-style: italic; }
|
||||
.highlight .err {
|
||||
color: #a61717;
|
||||
background-color: #e3d2d2; }
|
||||
.highlight .k {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .o {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .cm {
|
||||
color: #999988;
|
||||
font-style: italic; }
|
||||
.highlight .cp {
|
||||
color: #999999;
|
||||
font-weight: bold; }
|
||||
.highlight .c1 {
|
||||
color: #999988;
|
||||
font-style: italic; }
|
||||
.highlight .cs {
|
||||
color: #999999;
|
||||
font-weight: bold;
|
||||
font-style: italic; }
|
||||
.highlight .gd {
|
||||
color: #000000;
|
||||
background-color: #ffdddd; }
|
||||
.highlight .gd .x {
|
||||
color: #000000;
|
||||
background-color: #ffaaaa; }
|
||||
.highlight .ge {
|
||||
color: #000000;
|
||||
font-style: italic; }
|
||||
.highlight .gr {
|
||||
color: #aa0000; }
|
||||
.highlight .gh {
|
||||
color: #999999; }
|
||||
.highlight .gi {
|
||||
color: #000000;
|
||||
background-color: #ddffdd; }
|
||||
.highlight .gi .x {
|
||||
color: #000000;
|
||||
background-color: #aaffaa; }
|
||||
.highlight .go {
|
||||
color: #888888; }
|
||||
.highlight .gp {
|
||||
color: #555555; }
|
||||
.highlight .gs {
|
||||
font-weight: bold; }
|
||||
.highlight .gu {
|
||||
color: #aaaaaa; }
|
||||
.highlight .gt {
|
||||
color: #aa0000; }
|
||||
.highlight .kc {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .kd {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .kp {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .kr {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .kt {
|
||||
color: #445588; }
|
||||
.highlight .m {
|
||||
color: #009999; }
|
||||
.highlight .s {
|
||||
color: #d14; }
|
||||
.highlight .na {
|
||||
color: #008080; }
|
||||
.highlight .nb {
|
||||
color: #0086B3; }
|
||||
.highlight .nc {
|
||||
color: #445588;
|
||||
font-weight: bold; }
|
||||
.highlight .no {
|
||||
color: #008080; }
|
||||
.highlight .ni {
|
||||
color: #800080; }
|
||||
.highlight .ne {
|
||||
color: #990000;
|
||||
font-weight: bold; }
|
||||
.highlight .nf {
|
||||
color: #990000; }
|
||||
.highlight .nn {
|
||||
color: #555555; }
|
||||
.highlight .nt {
|
||||
color: #000080; }
|
||||
.highlight .nv {
|
||||
color: #008080; }
|
||||
.highlight .ow {
|
||||
color: #000000;
|
||||
font-weight: bold; }
|
||||
.highlight .w {
|
||||
color: #bbbbbb; }
|
||||
.highlight .mf {
|
||||
color: #009999; }
|
||||
.highlight .mh {
|
||||
color: #009999; }
|
||||
.highlight .mi {
|
||||
color: #009999; }
|
||||
.highlight .mo {
|
||||
color: #009999; }
|
||||
.highlight .sb {
|
||||
color: #d14; }
|
||||
.highlight .sc {
|
||||
color: #d14; }
|
||||
.highlight .sd {
|
||||
color: #d14; }
|
||||
.highlight .s2 {
|
||||
color: #d14; }
|
||||
.highlight .se {
|
||||
color: #d14; }
|
||||
.highlight .sh {
|
||||
color: #d14; }
|
||||
.highlight .si {
|
||||
color: #d14; }
|
||||
.highlight .sx {
|
||||
color: #d14; }
|
||||
.highlight .sr {
|
||||
color: #009926; }
|
||||
.highlight .s1 {
|
||||
color: #d14; }
|
||||
.highlight .ss {
|
||||
color: #990073; }
|
||||
.highlight .bp {
|
||||
color: #999999; }
|
||||
.highlight .vc {
|
||||
color: #008080; }
|
||||
.highlight .vg {
|
||||
color: #008080; }
|
||||
.highlight .vi {
|
||||
color: #008080; }
|
||||
.highlight .il {
|
||||
color: #009999; }
|
||||
@@ -0,0 +1,368 @@
|
||||
*, *:before, *:after {
|
||||
box-sizing: inherit; }
|
||||
|
||||
body {
|
||||
margin: 0;
|
||||
background: #fff;
|
||||
color: #333;
|
||||
font: 16px/1.7 "Helvetica Neue", Helvetica, Arial, sans-serif;
|
||||
letter-spacing: .2px;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
box-sizing: border-box; }
|
||||
|
||||
h1 {
|
||||
font-size: 2rem;
|
||||
font-weight: 700;
|
||||
margin: 1.275em 0 0.6em; }
|
||||
|
||||
h2 {
|
||||
font-size: 1.75rem;
|
||||
font-weight: 700;
|
||||
margin: 1.275em 0 0.3em; }
|
||||
|
||||
h3 {
|
||||
font-size: 1.5rem;
|
||||
font-weight: 700;
|
||||
margin: 1em 0 0.3em; }
|
||||
|
||||
h4 {
|
||||
font-size: 1.25rem;
|
||||
font-weight: 700;
|
||||
margin: 1.275em 0 0.85em; }
|
||||
|
||||
h5 {
|
||||
font-size: 1rem;
|
||||
font-weight: 700;
|
||||
margin: 1.275em 0 0.85em; }
|
||||
|
||||
h6 {
|
||||
font-size: 1rem;
|
||||
font-weight: 700;
|
||||
margin: 1.275em 0 0.85em;
|
||||
color: #777; }
|
||||
|
||||
p {
|
||||
margin: 0 0 1em; }
|
||||
|
||||
ul, ol {
|
||||
padding: 0 0 0 2em;
|
||||
margin: 0 0 0.85em; }
|
||||
|
||||
blockquote {
|
||||
margin: 0 0 0.85em;
|
||||
padding: 0 15px;
|
||||
color: #858585;
|
||||
border-left: 4px solid #e5e5e5; }
|
||||
|
||||
img {
|
||||
max-width: 100%; }
|
||||
|
||||
a {
|
||||
color: #4183c4;
|
||||
text-decoration: none; }
|
||||
a:hover, a:focus {
|
||||
outline: 0;
|
||||
text-decoration: underline; }
|
||||
|
||||
table {
|
||||
background: #fff;
|
||||
width: 100%;
|
||||
border-collapse: collapse;
|
||||
border-spacing: 0;
|
||||
overflow: auto;
|
||||
margin: 0 0 0.85em; }
|
||||
|
||||
tr:nth-child(2n) {
|
||||
background-color: #fbfbfb; }
|
||||
|
||||
th, td {
|
||||
padding: 6px 13px;
|
||||
border: 1px solid #ddd; }
|
||||
|
||||
pre {
|
||||
margin: 0 0 1.275em;
|
||||
padding: .85em 1em;
|
||||
overflow: auto;
|
||||
background: #f7f7f7;
|
||||
font-size: .85em;
|
||||
font-family: Consolas, "Liberation Mono", Menlo, Courier, monospace; }
|
||||
|
||||
code {
|
||||
font-family: Consolas, "Liberation Mono", Menlo, Courier, monospace; }
|
||||
|
||||
p > code, li > code {
|
||||
background: #f7f7f7;
|
||||
padding: .2em; }
|
||||
p > code:before, p > code:after, li > code:before, li > code:after {
|
||||
letter-spacing: -.2em;
|
||||
content: "\00a0"; }
|
||||
|
||||
pre code {
|
||||
padding: 0;
|
||||
white-space: pre; }
|
||||
|
||||
.content-wrapper {
|
||||
display: flex;
|
||||
flex-direction: column; }
|
||||
@media (min-width: 768px) {
|
||||
.content-wrapper {
|
||||
flex-direction: row; } }
|
||||
|
||||
.header {
|
||||
display: flex;
|
||||
padding: 8px;
|
||||
font-size: 0.875em;
|
||||
background: #444;
|
||||
color: #999; }
|
||||
|
||||
.header-col {
|
||||
margin: 0;
|
||||
padding: 0 8px; }
|
||||
|
||||
.header-col--primary {
|
||||
flex: 1; }
|
||||
|
||||
.header-link {
|
||||
color: #fff; }
|
||||
|
||||
.header-icon {
|
||||
padding-right: 6px;
|
||||
vertical-align: -4px;
|
||||
height: 16px; }
|
||||
|
||||
.breadcrumbs {
|
||||
font-size: 0.875em;
|
||||
padding: 8px 16px;
|
||||
margin: 0;
|
||||
background: #fbfbfb;
|
||||
border-bottom: 1px solid #ddd; }
|
||||
|
||||
.carat {
|
||||
height: 10px;
|
||||
margin: 0 5px; }
|
||||
|
||||
.navigation {
|
||||
order: 2; }
|
||||
@media (min-width: 768px) {
|
||||
.navigation {
|
||||
order: 1;
|
||||
width: 25%;
|
||||
max-width: 300px;
|
||||
padding-bottom: 64px;
|
||||
overflow: hidden;
|
||||
word-wrap: normal;
|
||||
background: #fbfbfb;
|
||||
border-right: 1px solid #ddd; } }
|
||||
|
||||
.nav-groups {
|
||||
list-style-type: none;
|
||||
padding-left: 0; }
|
||||
|
||||
.nav-group-name {
|
||||
border-bottom: 1px solid #ddd;
|
||||
padding: 8px 0 8px 16px; }
|
||||
|
||||
.nav-group-name-link {
|
||||
color: #333; }
|
||||
|
||||
.nav-group-tasks {
|
||||
margin: 8px 0;
|
||||
padding: 0 0 0 8px; }
|
||||
|
||||
.nav-group-task {
|
||||
font-size: 1em;
|
||||
list-style-type: none;
|
||||
white-space: nowrap; }
|
||||
|
||||
.nav-group-task-link {
|
||||
color: #808080; }
|
||||
|
||||
.main-content {
|
||||
order: 1; }
|
||||
@media (min-width: 768px) {
|
||||
.main-content {
|
||||
order: 2;
|
||||
flex: 1;
|
||||
padding-bottom: 60px; } }
|
||||
|
||||
.section {
|
||||
padding: 0 32px;
|
||||
border-bottom: 1px solid #ddd; }
|
||||
|
||||
.section-content {
|
||||
max-width: 834px;
|
||||
margin: 0 auto;
|
||||
padding: 16px 0; }
|
||||
|
||||
.section-name {
|
||||
color: #666;
|
||||
display: block; }
|
||||
|
||||
.declaration .highlight {
|
||||
overflow-x: initial;
|
||||
padding: 8px 0;
|
||||
margin: 0;
|
||||
background-color: transparent;
|
||||
border: none; }
|
||||
|
||||
.task-group-section {
|
||||
border-top: 1px solid #ddd; }
|
||||
|
||||
.task-group {
|
||||
padding-top: 0px; }
|
||||
|
||||
.task-name-container a[name]:before {
|
||||
content: "";
|
||||
display: block; }
|
||||
|
||||
.item-container {
|
||||
padding: 0; }
|
||||
|
||||
.item {
|
||||
padding-top: 8px;
|
||||
width: 100%;
|
||||
list-style-type: none; }
|
||||
.item a[name]:before {
|
||||
content: "";
|
||||
display: block; }
|
||||
.item .token {
|
||||
padding-left: 3px;
|
||||
margin-left: 0px;
|
||||
font-size: 1rem; }
|
||||
.item .declaration-note {
|
||||
font-size: .85em;
|
||||
color: #808080;
|
||||
font-style: italic; }
|
||||
|
||||
.pointer-container {
|
||||
border-bottom: 1px solid #ddd;
|
||||
left: -23px;
|
||||
padding-bottom: 13px;
|
||||
position: relative;
|
||||
width: 110%; }
|
||||
|
||||
.pointer {
|
||||
left: 21px;
|
||||
top: 7px;
|
||||
display: block;
|
||||
position: absolute;
|
||||
width: 12px;
|
||||
height: 12px;
|
||||
border-left: 1px solid #ddd;
|
||||
border-top: 1px solid #ddd;
|
||||
background: #fff;
|
||||
transform: rotate(45deg); }
|
||||
|
||||
.height-container {
|
||||
display: none;
|
||||
position: relative;
|
||||
width: 100%;
|
||||
overflow: hidden; }
|
||||
.height-container .section {
|
||||
background: #fff;
|
||||
border: 1px solid #ddd;
|
||||
border-top-width: 0;
|
||||
padding-top: 10px;
|
||||
padding-bottom: 5px;
|
||||
padding: 8px 16px; }
|
||||
|
||||
.aside, .language {
|
||||
padding: 6px 12px;
|
||||
margin: 12px 0;
|
||||
border-left: 5px solid #dddddd;
|
||||
overflow-y: hidden; }
|
||||
.aside .aside-title, .language .aside-title {
|
||||
font-size: 9px;
|
||||
letter-spacing: 2px;
|
||||
text-transform: uppercase;
|
||||
padding-bottom: 0;
|
||||
margin: 0;
|
||||
color: #aaa;
|
||||
-webkit-user-select: none; }
|
||||
.aside p:last-child, .language p:last-child {
|
||||
margin-bottom: 0; }
|
||||
|
||||
.language {
|
||||
border-left: 5px solid #cde9f4; }
|
||||
.language .aside-title {
|
||||
color: #4183c4; }
|
||||
|
||||
.aside-warning {
|
||||
border-left: 5px solid #ff6666; }
|
||||
.aside-warning .aside-title {
|
||||
color: #ff0000; }
|
||||
|
||||
.graybox {
|
||||
border-collapse: collapse;
|
||||
width: 100%; }
|
||||
.graybox p {
|
||||
margin: 0;
|
||||
word-break: break-word;
|
||||
min-width: 50px; }
|
||||
.graybox td {
|
||||
border: 1px solid #ddd;
|
||||
padding: 5px 25px 5px 10px;
|
||||
vertical-align: middle; }
|
||||
.graybox tr td:first-of-type {
|
||||
text-align: right;
|
||||
padding: 7px;
|
||||
vertical-align: top;
|
||||
word-break: normal;
|
||||
width: 40px; }
|
||||
|
||||
.slightly-smaller {
|
||||
font-size: 0.9em; }
|
||||
|
||||
.footer {
|
||||
padding: 8px 16px;
|
||||
background: #444;
|
||||
color: #ddd;
|
||||
font-size: 0.8em; }
|
||||
.footer p {
|
||||
margin: 8px 0; }
|
||||
.footer a {
|
||||
color: #fff; }
|
||||
|
||||
html.dash .header, html.dash .breadcrumbs, html.dash .navigation {
|
||||
display: none; }
|
||||
html.dash .height-container {
|
||||
display: block; }
|
||||
|
||||
form[role=search] input {
|
||||
font: 16px/1.7 "Helvetica Neue", Helvetica, Arial, sans-serif;
|
||||
font-size: 14px;
|
||||
line-height: 24px;
|
||||
padding: 0 10px;
|
||||
margin: 0;
|
||||
border: none;
|
||||
border-radius: 1em; }
|
||||
.loading form[role=search] input {
|
||||
background: white url(../img/spinner.gif) center right 4px no-repeat; }
|
||||
form[role=search] .tt-menu {
|
||||
margin: 0;
|
||||
min-width: 300px;
|
||||
background: #fbfbfb;
|
||||
color: #333;
|
||||
border: 1px solid #ddd; }
|
||||
form[role=search] .tt-highlight {
|
||||
font-weight: bold; }
|
||||
form[role=search] .tt-suggestion {
|
||||
font: 16px/1.7 "Helvetica Neue", Helvetica, Arial, sans-serif;
|
||||
padding: 0 8px; }
|
||||
form[role=search] .tt-suggestion span {
|
||||
display: table-cell;
|
||||
white-space: nowrap; }
|
||||
form[role=search] .tt-suggestion .doc-parent-name {
|
||||
width: 100%;
|
||||
text-align: right;
|
||||
font-weight: normal;
|
||||
font-size: 0.9em;
|
||||
padding-left: 16px; }
|
||||
form[role=search] .tt-suggestion:hover,
|
||||
form[role=search] .tt-suggestion.tt-cursor {
|
||||
cursor: pointer;
|
||||
background-color: #4183c4;
|
||||
color: #fff; }
|
||||
form[role=search] .tt-suggestion:hover .doc-parent-name,
|
||||
form[role=search] .tt-suggestion.tt-cursor .doc-parent-name {
|
||||
color: #fff; }
|
||||
|
After Width: | Height: | Size: 274 B |
|
After Width: | Height: | Size: 1.3 KiB |
|
After Width: | Height: | Size: 1.5 KiB |
|
After Width: | Height: | Size: 1.8 KiB |
@@ -0,0 +1,293 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<title>DiffableDataSources Reference</title>
|
||||
<link rel="stylesheet" type="text/css" href="css/jazzy.css" />
|
||||
<link rel="stylesheet" type="text/css" href="css/highlight.css" />
|
||||
<meta charset="utf-8">
|
||||
<script src="js/jquery.min.js" defer></script>
|
||||
<script src="js/jazzy.js" defer></script>
|
||||
|
||||
<script src="js/lunr.min.js" defer></script>
|
||||
<script src="js/typeahead.jquery.js" defer></script>
|
||||
<script src="js/jazzy.search.js" defer></script>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
|
||||
<a title="DiffableDataSources Reference"></a>
|
||||
|
||||
<header class="header">
|
||||
<p class="header-col header-col--primary">
|
||||
<a class="header-link" href="index.html">
|
||||
DiffableDataSources Docs
|
||||
</a>
|
||||
(100% documented)
|
||||
</p>
|
||||
|
||||
<p class="header-col--secondary">
|
||||
<form role="search" action="search.json">
|
||||
<input type="text" placeholder="Search documentation" data-typeahead>
|
||||
</form>
|
||||
</p>
|
||||
|
||||
<p class="header-col header-col--secondary">
|
||||
<a class="header-link" href="https://github.com/ra1028/DiffableDataSources">
|
||||
<img class="header-icon" src="img/gh.png"/>
|
||||
View on GitHub
|
||||
</a>
|
||||
</p>
|
||||
|
||||
</header>
|
||||
|
||||
<p class="breadcrumbs">
|
||||
<a class="breadcrumb" href="index.html">DiffableDataSources Reference</a>
|
||||
<img class="carat" src="img/carat.png" />
|
||||
DiffableDataSources Reference
|
||||
</p>
|
||||
|
||||
<div class="content-wrapper">
|
||||
<nav class="navigation">
|
||||
<ul class="nav-groups">
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="DataSources.html">DataSources</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/TableViewDiffableDataSource.html">TableViewDiffableDataSource</a>
|
||||
</li>
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/CollectionViewDiffableDataSource.html">CollectionViewDiffableDataSource</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
<li class="nav-group-name">
|
||||
<a class="nav-group-name-link" href="Snapshot.html">Snapshot</a>
|
||||
<ul class="nav-group-tasks">
|
||||
<li class="nav-group-task">
|
||||
<a class="nav-group-task-link" href="Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a>
|
||||
</li>
|
||||
</ul>
|
||||
</li>
|
||||
</ul>
|
||||
</nav>
|
||||
<article class="main-content">
|
||||
|
||||
<section class="section">
|
||||
<div class="section-content">
|
||||
|
||||
<H1 align="center">
|
||||
DiffableDataSources
|
||||
</H1>
|
||||
|
||||
<H4 align="center">
|
||||
💾 A library for backporting UITableView/UICollectionViewDiffableDataSource</br>
|
||||
powered by <a href="https://github.com/ra1028/DifferenceKit">DifferenceKit</a>.
|
||||
</H4>
|
||||
|
||||
<p align="center">
|
||||
<a href="https://developer.apple.com/swift"><img alt="Swift5" src="https://img.shields.io/badge/language-Swift5-orange.svg"/></a>
|
||||
<a href="https://github.com/ra1028/DiffableDataSources/releases/latest"><img alt="Release" src="https://img.shields.io/github/release/ra1028/DiffableDataSources.svg"/></a>
|
||||
<a href="https://cocoapods.org/pods/DiffableDataSources"><img alt="CocoaPods" src="https://img.shields.io/cocoapods/v/DiffableDataSources.svg"/></a>
|
||||
<a href="https://github.com/Carthage/Carthage"><img alt="Carthage" src="https://img.shields.io/badge/carthage-compatible-yellow.svg"/></a>
|
||||
<a href="https://swift.org/package-manager"><img alt="Swift Package Manager" src="https://img.shields.io/badge/SwiftPM-compatible-yellowgreen.svg"/></a>
|
||||
</br>
|
||||
<a href="https://dev.azure.com/ra1028/GitHub/_build/latest?definitionId=3&branchName=master"><img alt="Build Status" src="https://dev.azure.com/ra1028/GitHub/_apis/build/status/ra1028.DiffableDataSources?branchName=master"/></a>
|
||||
<a href="https://developer.apple.com/"><img alt="Platform" src="https://img.shields.io/badge/platform-iOS%20%7C%20macOS%20%7C%20tvOS-green.svg"/></a>
|
||||
<a href="https://github.com/ra1028/DiffableDataSources/blob/master/LICENSE"><img alt="Lincense" src="https://img.shields.io/badge/License-Apache%202.0-black.svg"/></a>
|
||||
</p>
|
||||
|
||||
<p align="center">
|
||||
Made with ❤️ by <a href="https://github.com/ra1028">Ryo Aoyama</a>
|
||||
</p>
|
||||
|
||||
<hr>
|
||||
<h2 id='introduction' class='heading'>Introduction</h2>
|
||||
|
||||
<p><img src="https://raw.githubusercontent.com/ra1028/DiffableDataSources/master/assets/insertion_sort.gif" height="400" align="right">
|
||||
<img src="https://raw.githubusercontent.com/ra1028/DiffableDataSources/master/assets/mountains.gif" height="400" align="right"></p>
|
||||
|
||||
<p>Apple has announced a diffable data source at WWDC 2019.<br>
|
||||
It’s a great API that easily updating our table view and collection view items using automatic diffing.<br>
|
||||
However, it’s a little while before we can use it in a production service.<br>
|
||||
That because it requires the latest OS to use.<br>
|
||||
DiffableDataSources make it possible to introduce almost the same functionality from now on. </p>
|
||||
|
||||
<p>Uses a sophisticated open source <a href="https://github.com/ra1028/DifferenceKit">DifferenceKit</a> for the algorithm engine.<br>
|
||||
It’s extremely fast and completely avoids synchronization bugs, exceptions, and crashes. </p>
|
||||
|
||||
<p><br clear="all"></p>
|
||||
|
||||
<hr>
|
||||
<h2 id='difference-from-the-official' class='heading'>Difference from the Official</h2>
|
||||
<h4 id='spec' class='heading'>Spec</h4>
|
||||
|
||||
<ul>
|
||||
<li>Supports iOS 9.0+ / macOS 10.11+ / tvOS 9.0+</li>
|
||||
<li>Open sourced algorithm.</li>
|
||||
<li>Duplicate sections or items are allowed.<br></li>
|
||||
<li>Using <code>performBatchUpdates</code> for diffing updates.</li>
|
||||
</ul>
|
||||
<h4 id='namings' class='heading'>Namings</h4>
|
||||
|
||||
<p><code>DiffableDataSources</code> have different class names to avoid conflicts with the official API.<br>
|
||||
Correspondence table is below. </p>
|
||||
|
||||
<table><thead>
|
||||
<tr>
|
||||
<th style="text-align: left">Official</th>
|
||||
<th style="text-align: left">Backported</th>
|
||||
</tr>
|
||||
</thead><tbody>
|
||||
<tr>
|
||||
<td style="text-align: left"><a href="https://developer.apple.com/documentation/uikit/uitableviewdiffabledatasource">NSDiffableDataSourceSnapshot</a></td>
|
||||
<td style="text-align: left">DiffableDataSourceSnapshot</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="text-align: left"><a href="https://developer.apple.com/documentation/uikit/uitableviewdiffabledatasource">UITableViewDiffableDataSource</a></td>
|
||||
<td style="text-align: left">TableViewDiffableDataSource</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="text-align: left"><a href="https://developer.apple.com/documentation/uikit/uicollectionviewdiffabledatasource">UICollectionViewDiffableDataSource</a></td>
|
||||
<td style="text-align: left">CollectionViewDiffableDataSource</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td style="text-align: left"><a href="https://developer.apple.com/documentation/appkit/nscollectionviewdiffabledatasource">NSCollectionViewDiffableDataSource</a></td>
|
||||
<td style="text-align: left">CocoaCollectionViewDiffableDataSource</td>
|
||||
</tr>
|
||||
</tbody></table>
|
||||
|
||||
<hr>
|
||||
<h2 id='getting-started' class='heading'>Getting Started</h2>
|
||||
|
||||
<ul>
|
||||
<li><a href="https://ra1028.github.io/DiffableDataSources">API Documentation</a></li>
|
||||
<li><a href="https://github.com/ra1028/DiffableDataSources/tree/master/Examples">Example Apps</a></li>
|
||||
<li><a href="https://developer.apple.com/videos/play/wwdc2019/220">WWDC 2019 Session</a></li>
|
||||
</ul>
|
||||
<h4 id='build-project' class='heading'>Build Project</h4>
|
||||
<pre class="highlight shell"><code><span class="nv">$ </span>git clone https://github.com/ra1028/DiffableDataSources.git
|
||||
<span class="nv">$ </span><span class="nb">cd </span>DiffableDataSources/
|
||||
<span class="nv">$ </span>make setup
|
||||
<span class="nv">$ </span>open DiffableDataSources.xcworkspace
|
||||
</code></pre>
|
||||
|
||||
<hr>
|
||||
<h2 id='basic-usage' class='heading'>Basic Usage</h2>
|
||||
|
||||
<p>First, define the type representing section.<br>
|
||||
It should conforms to <code>Hashable</code> for identifies from the all sections.<br>
|
||||
Type of enum can used conveniently befause it conforms <code>Hashable</code> by default. </p>
|
||||
<pre class="highlight swift"><code><span class="kd">enum</span> <span class="kt">Section</span> <span class="p">{</span>
|
||||
<span class="k">case</span> <span class="n">main</span>
|
||||
<span class="p">}</span>
|
||||
</code></pre>
|
||||
|
||||
<p>Then, define the item type conforms to <code>Hashable</code>. </p>
|
||||
<pre class="highlight swift"><code><span class="kd">struct</span> <span class="kt">User</span><span class="p">:</span> <span class="kt">Hashable</span> <span class="p">{</span>
|
||||
<span class="k">var</span> <span class="nv">name</span><span class="p">:</span> <span class="kt">String</span>
|
||||
<span class="p">}</span>
|
||||
</code></pre>
|
||||
|
||||
<p>Create a data source object, it will be set to table view automatically.<br>
|
||||
You should dequeue the non nil cells via closure. </p>
|
||||
<pre class="highlight swift"><code><span class="kd">final</span> <span class="kd">class</span> <span class="kt">UsersViewController</span><span class="p">:</span> <span class="kt">UIViewController</span> <span class="p">{</span>
|
||||
<span class="k">let</span> <span class="nv">tableView</span><span class="p">:</span> <span class="kt">UITableView</span> <span class="o">=</span> <span class="o">...</span>
|
||||
|
||||
<span class="kd">lazy</span> <span class="k">var</span> <span class="nv">dataSource</span> <span class="o">=</span> <span class="kt">TableViewDiffableDataSource</span><span class="o"><</span><span class="kt">Section</span><span class="p">,</span> <span class="kt">User</span><span class="o">></span><span class="p">(</span><span class="nv">tableView</span><span class="p">:</span> <span class="n">tableView</span><span class="p">)</span> <span class="p">{</span> <span class="n">tableView</span><span class="p">,</span> <span class="n">indexPath</span><span class="p">,</span> <span class="n">user</span> <span class="k">in</span>
|
||||
<span class="k">let</span> <span class="nv">cell</span> <span class="o">=</span> <span class="n">tableView</span><span class="o">.</span><span class="nf">dequeueReusableCell</span><span class="p">(</span><span class="nv">withIdentifier</span><span class="p">:</span> <span class="s">"Cell"</span><span class="p">,</span> <span class="nv">for</span><span class="p">:</span> <span class="n">indexPath</span><span class="p">)</span>
|
||||
<span class="n">cell</span><span class="o">.</span><span class="n">textLabel</span><span class="p">?</span><span class="o">.</span><span class="n">text</span> <span class="o">=</span> <span class="n">user</span><span class="o">.</span><span class="n">name</span>
|
||||
<span class="k">return</span> <span class="n">cell</span>
|
||||
<span class="p">}</span>
|
||||
|
||||
<span class="k">override</span> <span class="kd">func</span> <span class="nf">viewDidLoad</span><span class="p">()</span> <span class="p">{</span>
|
||||
<span class="k">super</span><span class="o">.</span><span class="nf">viewDidLoad</span><span class="p">()</span>
|
||||
|
||||
<span class="n">tableView</span><span class="o">.</span><span class="nf">register</span><span class="p">(</span><span class="kt">UITableViewCell</span><span class="o">.</span><span class="k">self</span><span class="p">,</span> <span class="nv">forCellReuseIdentifier</span><span class="p">:</span> <span class="s">"Cell"</span><span class="p">)</span>
|
||||
<span class="p">}</span>
|
||||
<span class="p">}</span>
|
||||
</code></pre>
|
||||
|
||||
<p>Manages and updates the data sources intuitively by intermediating <code><a href="Classes/DiffableDataSourceSnapshot.html">DiffableDataSourceSnapshot</a></code>.<br>
|
||||
The UI isn’t updated until you apply the edited snapshot object.<br>
|
||||
Update the UI with diffing animation automatically calculated by applying an edited snapshot. </p>
|
||||
<pre class="highlight swift"><code><span class="k">let</span> <span class="nv">users</span> <span class="o">=</span> <span class="p">[</span>
|
||||
<span class="kt">User</span><span class="p">(</span><span class="nv">name</span><span class="p">:</span> <span class="s">"Steve Jobs"</span><span class="p">),</span>
|
||||
<span class="kt">User</span><span class="p">(</span><span class="nv">name</span><span class="p">:</span> <span class="s">"Stephen Wozniak"</span><span class="p">),</span>
|
||||
<span class="kt">User</span><span class="p">(</span><span class="nv">name</span><span class="p">:</span> <span class="s">"Tim Cook"</span><span class="p">),</span>
|
||||
<span class="kt">User</span><span class="p">(</span><span class="nv">name</span><span class="p">:</span> <span class="s">"Jonathan Ive"</span><span class="p">)</span>
|
||||
<span class="p">]</span>
|
||||
|
||||
<span class="k">let</span> <span class="nv">snapshot</span> <span class="o">=</span> <span class="kt">DiffableDataSourceSnapshot</span><span class="o"><</span><span class="kt">Section</span><span class="p">,</span> <span class="kt">User</span><span class="o">></span><span class="p">()</span>
|
||||
<span class="n">snapshot</span><span class="o">.</span><span class="nf">appendSections</span><span class="p">([</span><span class="o">.</span><span class="n">main</span><span class="p">])</span>
|
||||
<span class="n">snapshot</span><span class="o">.</span><span class="nf">appendItems</span><span class="p">(</span><span class="n">users</span><span class="p">)</span>
|
||||
|
||||
<span class="n">dataSource</span><span class="o">.</span><span class="nf">apply</span><span class="p">(</span><span class="n">snapshot</span><span class="p">)</span>
|
||||
</code></pre>
|
||||
|
||||
<p>Check the documentation for more detailed API. </p>
|
||||
|
||||
<H3 align="center">
|
||||
<a href="https://ra1028.github.io/DiffableDataSources">[See More Usage]</a>
|
||||
</H3>
|
||||
|
||||
<hr>
|
||||
<h2 id='requirements' class='heading'>Requirements</h2>
|
||||
|
||||
<ul>
|
||||
<li>Swift 5.0+</li>
|
||||
<li>iOS 9.0+</li>
|
||||
<li>macOS 10.11+</li>
|
||||
<li>tvOS 9.0+</li>
|
||||
</ul>
|
||||
|
||||
<hr>
|
||||
<h2 id='installation' class='heading'>Installation</h2>
|
||||
<h3 id='a-href-https-cocoapods-org-cocoapods-a' class='heading'><a href="https://cocoapods.org">CocoaPods</a></h3>
|
||||
|
||||
<p>Add the following to your <code>Podfile</code>:</p>
|
||||
<pre class="highlight ruby"><code><span class="n">pod</span> <span class="s1">'DiffableDataSources'</span>
|
||||
</code></pre>
|
||||
<h3 id='a-href-https-github-com-carthage-carthage-carthage-a' class='heading'><a href="https://github.com/Carthage/Carthage">Carthage</a></h3>
|
||||
|
||||
<p>Add the following to your <code>Cartfile</code>:</p>
|
||||
<pre class="highlight plaintext"><code>github "ra1028/DiffableDataSources"
|
||||
</code></pre>
|
||||
<h3 id='a-href-https-swift-org-package-manager-swift-package-manager-a' class='heading'><a href="https://swift.org/package-manager/">Swift Package Manager</a></h3>
|
||||
|
||||
<p>Add the following to the dependencies of your <code>Package.swift</code>:</p>
|
||||
<pre class="highlight swift"><code><span class="o">.</span><span class="nf">package</span><span class="p">(</span><span class="nv">url</span><span class="p">:</span> <span class="s">"https://github.com/ra1028/DiffableDataSources.git"</span><span class="p">,</span> <span class="nv">from</span><span class="p">:</span> <span class="s">"x.x.x"</span><span class="p">)</span>
|
||||
</code></pre>
|
||||
|
||||
<hr>
|
||||
<h2 id='contributing' class='heading'>Contributing</h2>
|
||||
|
||||
<p>Pull requests, bug reports and feature requests are welcome 🚀<br>
|
||||
Please see the <a href="https://github.com/ra1028/DiffableDataSources/blob/master/CONTRIBUTING.md">CONTRIBUTING</a> file for learn how to contribute to DiffableDataSources. </p>
|
||||
|
||||
<hr>
|
||||
<h2 id='relations' class='heading'>Relations</h2>
|
||||
<h4 id='a-href-https-github-com-ra1028-differencekit-differencekit-a' class='heading'><a href="https://github.com/ra1028/DifferenceKit">DifferenceKit</a></h4>
|
||||
|
||||
<p>A fast and flexible O(n) difference algorithm framework for Swift collection.</p>
|
||||
<h4 id='a-href-https-github-com-ra1028-carbon-carbon-a' class='heading'><a href="https://github.com/ra1028/Carbon">Carbon</a></h4>
|
||||
|
||||
<p>A declarative library for building component-based user interfaces in UITableView and UICollectionView.</p>
|
||||
|
||||
<hr>
|
||||
<h2 id='license' class='heading'>License</h2>
|
||||
|
||||
<p>DiffableDataSources is released under the <a href="https://github.com/ra1028/DiffableDataSources/blob/master/LICENSE">Apache 2.0 License</a>. </p>
|
||||
|
||||
</div>
|
||||
</section>
|
||||
|
||||
|
||||
</article>
|
||||
</div>
|
||||
<section class="footer">
|
||||
<p>© 2019 <a class="link" href="https://github.com/ra1028" target="_blank" rel="external">Ryo Aoyama</a>. All rights reserved. (Last updated: 2019-06-24)</p>
|
||||
<p>Generated by <a class="link" href="https://github.com/realm/jazzy" target="_blank" rel="external">jazzy ♪♫ v0.9.4</a>, a <a class="link" href="https://realm.io" target="_blank" rel="external">Realm</a> project.</p>
|
||||
</section>
|
||||
</body>
|
||||
</div>
|
||||
</html>
|
||||
@@ -0,0 +1,43 @@
|
||||
window.jazzy = {'docset': false}
|
||||
if (typeof window.dash != 'undefined') {
|
||||
document.documentElement.className += ' dash'
|
||||
window.jazzy.docset = true
|
||||
}
|
||||
if (navigator.userAgent.match(/xcode/i)) {
|
||||
document.documentElement.className += ' xcode'
|
||||
window.jazzy.docset = true
|
||||
}
|
||||
|
||||
// On doc load, toggle the URL hash discussion if present
|
||||
$(document).ready(function() {
|
||||
if (!window.jazzy.docset) {
|
||||
var linkToHash = $('a[href="' + window.location.hash +'"]');
|
||||
linkToHash.trigger("click");
|
||||
}
|
||||
});
|
||||
|
||||
// On token click, toggle its discussion and animate token.marginLeft
|
||||
$(".token").click(function(event) {
|
||||
if (window.jazzy.docset) {
|
||||
return;
|
||||
}
|
||||
var link = $(this);
|
||||
var animationDuration = 300;
|
||||
$content = link.parent().parent().next();
|
||||
$content.slideToggle(animationDuration);
|
||||
|
||||
// Keeps the document from jumping to the hash.
|
||||
var href = $(this).attr('href');
|
||||
if (history.pushState) {
|
||||
history.pushState({}, '', href);
|
||||
} else {
|
||||
location.hash = href;
|
||||
}
|
||||
event.preventDefault();
|
||||
});
|
||||
|
||||
// Dumb down quotes within code blocks that delimit strings instead of quotations
|
||||
// https://github.com/realm/jazzy/issues/714
|
||||
$("code q").replaceWith(function () {
|
||||
return ["\"", $(this).contents(), "\""];
|
||||
});
|
||||
@@ -0,0 +1,62 @@
|
||||
$(function(){
|
||||
var searchIndex = lunr(function() {
|
||||
this.ref('url');
|
||||
this.field('name');
|
||||
});
|
||||
|
||||
var $typeahead = $('[data-typeahead]');
|
||||
var $form = $typeahead.parents('form');
|
||||
var searchURL = $form.attr('action');
|
||||
|
||||
function displayTemplate(result) {
|
||||
return result.name;
|
||||
}
|
||||
|
||||
function suggestionTemplate(result) {
|
||||
var t = '<div class="list-group-item clearfix">';
|
||||
t += '<span class="doc-name">' + result.name + '</span>';
|
||||
if (result.parent_name) {
|
||||
t += '<span class="doc-parent-name label">' + result.parent_name + '</span>';
|
||||
}
|
||||
t += '</div>';
|
||||
return t;
|
||||
}
|
||||
|
||||
$typeahead.one('focus', function() {
|
||||
$form.addClass('loading');
|
||||
|
||||
$.getJSON(searchURL).then(function(searchData) {
|
||||
$.each(searchData, function (url, doc) {
|
||||
searchIndex.add({url: url, name: doc.name});
|
||||
});
|
||||
|
||||
$typeahead.typeahead(
|
||||
{
|
||||
highlight: true,
|
||||
minLength: 3
|
||||
},
|
||||
{
|
||||
limit: 10,
|
||||
display: displayTemplate,
|
||||
templates: { suggestion: suggestionTemplate },
|
||||
source: function(query, sync) {
|
||||
var results = searchIndex.search(query).map(function(result) {
|
||||
var doc = searchData[result.ref];
|
||||
doc.url = result.ref;
|
||||
return doc;
|
||||
});
|
||||
sync(results);
|
||||
}
|
||||
}
|
||||
);
|
||||
$form.removeClass('loading');
|
||||
$typeahead.trigger('focus');
|
||||
});
|
||||
});
|
||||
|
||||
var baseURL = searchURL.slice(0, -"search.json".length);
|
||||
|
||||
$typeahead.on('typeahead:select', function(e, result) {
|
||||
window.location = baseURL + result.url;
|
||||
});
|
||||
});
|
||||