mirror of
https://github.com/SideStore/SideStore.git
synced 2026-02-19 03:33:36 +01:00
Changes NewsCollectionViewCell image aspect ratio to 3:2
Also updates fonts to use dynamic text styles.
This commit is contained in:
@@ -19,6 +19,9 @@ class NewsCollectionViewCell: UICollectionViewCell
|
|||||||
{
|
{
|
||||||
super.awakeFromNib()
|
super.awakeFromNib()
|
||||||
|
|
||||||
|
let descriptor = UIFontDescriptor.preferredFontDescriptor(withTextStyle: .title2).bolded()
|
||||||
|
self.titleLabel.font = UIFont(descriptor: descriptor, size: 0.0)
|
||||||
|
|
||||||
self.contentView.preservesSuperviewLayoutMargins = true
|
self.contentView.preservesSuperviewLayoutMargins = true
|
||||||
|
|
||||||
self.contentBackgroundView.layer.cornerRadius = 30
|
self.contentBackgroundView.layer.cornerRadius = 30
|
||||||
|
|||||||
@@ -1,9 +1,9 @@
|
|||||||
<?xml version="1.0" encoding="UTF-8"?>
|
<?xml version="1.0" encoding="UTF-8"?>
|
||||||
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="15400" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="22505" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
|
||||||
<device id="retina4_7" orientation="portrait" appearance="light"/>
|
<device id="retina4_7" orientation="portrait" appearance="light"/>
|
||||||
<dependencies>
|
<dependencies>
|
||||||
<deployment identifier="iOS"/>
|
<deployment identifier="iOS"/>
|
||||||
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="15404"/>
|
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="22504"/>
|
||||||
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
|
||||||
</dependencies>
|
</dependencies>
|
||||||
<objects>
|
<objects>
|
||||||
@@ -22,31 +22,31 @@
|
|||||||
<view contentMode="scaleToFill" preservesSuperviewLayoutMargins="YES" insetsLayoutMarginsFromSafeArea="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Xba-Qs-SQo">
|
<view contentMode="scaleToFill" preservesSuperviewLayoutMargins="YES" insetsLayoutMarginsFromSafeArea="NO" translatesAutoresizingMaskIntoConstraints="NO" id="Xba-Qs-SQo">
|
||||||
<rect key="frame" x="16" y="0.0" width="303" height="299"/>
|
<rect key="frame" x="16" y="0.0" width="303" height="299"/>
|
||||||
<subviews>
|
<subviews>
|
||||||
<stackView opaque="NO" contentMode="scaleToFill" insetsLayoutMarginsFromSafeArea="NO" axis="vertical" translatesAutoresizingMaskIntoConstraints="NO" id="tNk-9u-1tk">
|
<stackView opaque="NO" contentMode="scaleToFill" insetsLayoutMarginsFromSafeArea="NO" axis="vertical" distribution="equalSpacing" translatesAutoresizingMaskIntoConstraints="NO" id="tNk-9u-1tk">
|
||||||
<rect key="frame" x="0.0" y="0.0" width="303" height="298.5"/>
|
<rect key="frame" x="0.0" y="0.0" width="303" height="299"/>
|
||||||
<subviews>
|
<subviews>
|
||||||
<stackView opaque="NO" contentMode="scaleToFill" insetsLayoutMarginsFromSafeArea="NO" axis="vertical" alignment="top" spacing="10" translatesAutoresizingMaskIntoConstraints="NO" id="akF-Tr-G5M">
|
<stackView opaque="NO" contentMode="scaleToFill" insetsLayoutMarginsFromSafeArea="NO" axis="vertical" distribution="fillProportionally" alignment="top" spacing="10" translatesAutoresizingMaskIntoConstraints="NO" id="akF-Tr-G5M">
|
||||||
<rect key="frame" x="0.0" y="0.0" width="303" height="117.5"/>
|
<rect key="frame" x="0.0" y="0.0" width="303" height="97"/>
|
||||||
<subviews>
|
<subviews>
|
||||||
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" verticalCompressionResistancePriority="1000" text="Delta" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="2" baselineAdjustment="alignBaselines" minimumScaleFactor="0.5" translatesAutoresizingMaskIntoConstraints="NO" id="AkN-BE-I1a">
|
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" verticalCompressionResistancePriority="1000" text="Delta" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="2" baselineAdjustment="alignBaselines" minimumScaleFactor="0.5" translatesAutoresizingMaskIntoConstraints="NO" id="AkN-BE-I1a">
|
||||||
<rect key="frame" x="25" y="25" width="54.5" height="26.5"/>
|
<rect key="frame" x="25" y="25" width="50" height="26.5"/>
|
||||||
<fontDescription key="fontDescription" type="boldSystem" pointSize="22"/>
|
<fontDescription key="fontDescription" style="UICTFontTextStyleTitle2"/>
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||||
<nil key="highlightedColor"/>
|
<nil key="highlightedColor"/>
|
||||||
</label>
|
</label>
|
||||||
<label opaque="NO" userInteractionEnabled="NO" alpha="0.75" contentMode="left" horizontalHuggingPriority="251" verticalCompressionResistancePriority="999" text="Label" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="SHB-kk-YhL">
|
<label opaque="NO" userInteractionEnabled="NO" alpha="0.75" contentMode="left" horizontalHuggingPriority="251" verticalCompressionResistancePriority="999" text="Label" textAlignment="natural" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="SHB-kk-YhL">
|
||||||
<rect key="frame" x="25" y="61.5" width="35.5" height="36"/>
|
<rect key="frame" x="25" y="61.5" width="37.5" height="15.5"/>
|
||||||
<fontDescription key="fontDescription" type="system" pointSize="14"/>
|
<fontDescription key="fontDescription" style="UICTFontTextStyleSubhead"/>
|
||||||
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
<color key="textColor" white="1" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
||||||
<nil key="highlightedColor"/>
|
<nil key="highlightedColor"/>
|
||||||
</label>
|
</label>
|
||||||
</subviews>
|
</subviews>
|
||||||
<edgeInsets key="layoutMargins" top="25" left="25" bottom="20" right="25"/>
|
<edgeInsets key="layoutMargins" top="25" left="25" bottom="20" right="25"/>
|
||||||
</stackView>
|
</stackView>
|
||||||
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" placeholderIntrinsicWidth="335" placeholderIntrinsicHeight="200" translatesAutoresizingMaskIntoConstraints="NO" id="l36-Bm-De0">
|
<imageView clipsSubviews="YES" userInteractionEnabled="NO" contentMode="scaleAspectFill" horizontalHuggingPriority="251" verticalHuggingPriority="251" translatesAutoresizingMaskIntoConstraints="NO" id="l36-Bm-De0">
|
||||||
<rect key="frame" x="0.0" y="117.5" width="303" height="181"/>
|
<rect key="frame" x="0.0" y="97" width="303" height="202"/>
|
||||||
<constraints>
|
<constraints>
|
||||||
<constraint firstAttribute="width" secondItem="l36-Bm-De0" secondAttribute="height" multiplier="67:40" priority="999" id="QGD-YE-Hw2"/>
|
<constraint firstAttribute="width" secondItem="l36-Bm-De0" secondAttribute="height" multiplier="3:2" priority="999" id="QGD-YE-Hw2"/>
|
||||||
</constraints>
|
</constraints>
|
||||||
</imageView>
|
</imageView>
|
||||||
</subviews>
|
</subviews>
|
||||||
@@ -56,12 +56,11 @@
|
|||||||
<constraint firstItem="tNk-9u-1tk" firstAttribute="top" secondItem="Xba-Qs-SQo" secondAttribute="top" id="Dw8-lF-Fzl"/>
|
<constraint firstItem="tNk-9u-1tk" firstAttribute="top" secondItem="Xba-Qs-SQo" secondAttribute="top" id="Dw8-lF-Fzl"/>
|
||||||
<constraint firstAttribute="trailing" secondItem="tNk-9u-1tk" secondAttribute="trailing" id="Zt8-Wa-oB9"/>
|
<constraint firstAttribute="trailing" secondItem="tNk-9u-1tk" secondAttribute="trailing" id="Zt8-Wa-oB9"/>
|
||||||
<constraint firstItem="tNk-9u-1tk" firstAttribute="leading" secondItem="Xba-Qs-SQo" secondAttribute="leading" id="m6p-Ee-dTh"/>
|
<constraint firstItem="tNk-9u-1tk" firstAttribute="leading" secondItem="Xba-Qs-SQo" secondAttribute="leading" id="m6p-Ee-dTh"/>
|
||||||
<constraint firstAttribute="bottom" secondItem="tNk-9u-1tk" secondAttribute="bottom" constant="0.5" id="v9g-yC-db9"/>
|
<constraint firstAttribute="bottom" secondItem="tNk-9u-1tk" secondAttribute="bottom" id="v9g-yC-db9"/>
|
||||||
</constraints>
|
</constraints>
|
||||||
</view>
|
</view>
|
||||||
</subviews>
|
</subviews>
|
||||||
</view>
|
</view>
|
||||||
<color key="backgroundColor" white="0.0" alpha="0.0" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
|
|
||||||
<constraints>
|
<constraints>
|
||||||
<constraint firstItem="Xba-Qs-SQo" firstAttribute="top" secondItem="wRF-2R-NUG" secondAttribute="top" id="0xe-Rt-MhF"/>
|
<constraint firstItem="Xba-Qs-SQo" firstAttribute="top" secondItem="wRF-2R-NUG" secondAttribute="top" id="0xe-Rt-MhF"/>
|
||||||
<constraint firstItem="Xba-Qs-SQo" firstAttribute="leading" secondItem="wRF-2R-NUG" secondAttribute="leadingMargin" id="5MO-c0-5rG"/>
|
<constraint firstItem="Xba-Qs-SQo" firstAttribute="leading" secondItem="wRF-2R-NUG" secondAttribute="leadingMargin" id="5MO-c0-5rG"/>
|
||||||
|
|||||||
@@ -90,6 +90,16 @@ class NewsViewController: UICollectionViewController, PeekPopPreviewing
|
|||||||
self.prototypeCell = NewsCollectionViewCell.instantiate(with: NewsCollectionViewCell.nib!)
|
self.prototypeCell = NewsCollectionViewCell.instantiate(with: NewsCollectionViewCell.nib!)
|
||||||
self.prototypeCell.contentView.translatesAutoresizingMaskIntoConstraints = false
|
self.prototypeCell.contentView.translatesAutoresizingMaskIntoConstraints = false
|
||||||
|
|
||||||
|
// Need to add dummy constraint + layout subviews before we can remove Interface Builder's width constraint.
|
||||||
|
self.prototypeCell.widthAnchor.constraint(greaterThanOrEqualToConstant: 0).isActive = true
|
||||||
|
self.prototypeCell.layoutIfNeeded()
|
||||||
|
|
||||||
|
let constraints = self.prototypeCell.constraintsAffectingLayout(for: .horizontal)
|
||||||
|
for constraint in constraints where constraint.identifier?.contains("Encapsulated-Layout-Width") == true
|
||||||
|
{
|
||||||
|
self.prototypeCell.removeConstraint(constraint)
|
||||||
|
}
|
||||||
|
|
||||||
self.collectionView.dataSource = self.dataSource
|
self.collectionView.dataSource = self.dataSource
|
||||||
self.collectionView.prefetchDataSource = self.dataSource
|
self.collectionView.prefetchDataSource = self.dataSource
|
||||||
|
|
||||||
@@ -149,10 +159,12 @@ private extension NewsViewController
|
|||||||
|
|
||||||
let dataSource = RSTFetchedResultsCollectionViewPrefetchingDataSource<NewsItem, UIImage>(fetchedResultsController: fetchedResultsController)
|
let dataSource = RSTFetchedResultsCollectionViewPrefetchingDataSource<NewsItem, UIImage>(fetchedResultsController: fetchedResultsController)
|
||||||
dataSource.proxy = self
|
dataSource.proxy = self
|
||||||
dataSource.cellConfigurationHandler = { (cell, newsItem, indexPath) in
|
dataSource.cellConfigurationHandler = { [weak self] (cell, newsItem, indexPath) in
|
||||||
|
guard let self else { return }
|
||||||
|
|
||||||
let cell = cell as! NewsCollectionViewCell
|
let cell = cell as! NewsCollectionViewCell
|
||||||
cell.layoutMargins.left = self.view.layoutMargins.left
|
cell.contentView.layoutMargins.left = self.view.layoutMargins.left
|
||||||
cell.layoutMargins.right = self.view.layoutMargins.right
|
cell.contentView.layoutMargins.right = self.view.layoutMargins.right
|
||||||
|
|
||||||
cell.titleLabel.text = newsItem.title
|
cell.titleLabel.text = newsItem.title
|
||||||
cell.captionLabel.text = newsItem.caption
|
cell.captionLabel.text = newsItem.caption
|
||||||
@@ -454,16 +466,13 @@ extension NewsViewController: UICollectionViewDelegateFlowLayout
|
|||||||
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize
|
func collectionView(_ collectionView: UICollectionView, layout collectionViewLayout: UICollectionViewLayout, sizeForItemAt indexPath: IndexPath) -> CGSize
|
||||||
{
|
{
|
||||||
let item = self.dataSource.item(at: indexPath)
|
let item = self.dataSource.item(at: indexPath)
|
||||||
|
let globallyUniqueID = item.globallyUniqueID ?? item.identifier
|
||||||
|
|
||||||
if let previousSize = self.cachedCellSizes[item.identifier]
|
if let previousSize = self.cachedCellSizes[globallyUniqueID]
|
||||||
{
|
{
|
||||||
return previousSize
|
return previousSize
|
||||||
}
|
}
|
||||||
|
|
||||||
// Take layout margins into account.
|
|
||||||
self.prototypeCell.layoutMargins.left = self.view.layoutMargins.left
|
|
||||||
self.prototypeCell.layoutMargins.right = self.view.layoutMargins.right
|
|
||||||
|
|
||||||
let widthConstraint = self.prototypeCell.contentView.widthAnchor.constraint(equalToConstant: collectionView.bounds.width)
|
let widthConstraint = self.prototypeCell.contentView.widthAnchor.constraint(equalToConstant: collectionView.bounds.width)
|
||||||
NSLayoutConstraint.activate([widthConstraint])
|
NSLayoutConstraint.activate([widthConstraint])
|
||||||
defer { NSLayoutConstraint.deactivate([widthConstraint]) }
|
defer { NSLayoutConstraint.deactivate([widthConstraint]) }
|
||||||
@@ -471,7 +480,7 @@ extension NewsViewController: UICollectionViewDelegateFlowLayout
|
|||||||
self.dataSource.cellConfigurationHandler(self.prototypeCell, item, indexPath)
|
self.dataSource.cellConfigurationHandler(self.prototypeCell, item, indexPath)
|
||||||
|
|
||||||
let size = self.prototypeCell.contentView.systemLayoutSizeFitting(UIView.layoutFittingCompressedSize)
|
let size = self.prototypeCell.contentView.systemLayoutSizeFitting(UIView.layoutFittingCompressedSize)
|
||||||
self.cachedCellSizes[item.identifier] = size
|
self.cachedCellSizes[globallyUniqueID] = size
|
||||||
return size
|
return size
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -82,6 +82,16 @@ public class NewsItem: NSManagedObject, Decodable, Fetchable
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public extension NewsItem
|
||||||
|
{
|
||||||
|
var globallyUniqueID: String? {
|
||||||
|
guard let sourceIdentifier = self.sourceIdentifier else { return nil }
|
||||||
|
|
||||||
|
let globallyUniqueID = self.identifier + "|" + sourceIdentifier
|
||||||
|
return globallyUniqueID
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public extension NewsItem
|
public extension NewsItem
|
||||||
{
|
{
|
||||||
@nonobjc class func fetchRequest() -> NSFetchRequest<NewsItem>
|
@nonobjc class func fetchRequest() -> NSFetchRequest<NewsItem>
|
||||||
|
|||||||
Reference in New Issue
Block a user