После комментариев и размещенного кода ...
Похоже, вы делаете много вещей, которые вам не нужны.
При надлежащих ограничениях вам потребуется гораздо меньше кода, и вам вовсе не нужен ваш протокол / делегат.
Сначала - и это только подсказка - вы можете определить ограничения в кодев гораздо более простой и удобочитаемой форме:
myView.addSubview(mySubView)
NSLayoutConstraint.activate([
mySubView.topAnchor.constraint(equalTo: myView.topAnchor, constant: 0.0),
mySubView.bottomAnchor.constraint(equalTo: myView.bottomAnchor, constant: 0.0),
mySubView.leadingAnchor.constraint(equalTo: myView.leadingAnchor, constant: 0.0),
mySubView.trailingAnchor.constraint(equalTo: myView.trailingAnchor, constant: 0.0),
])
Второй - также совет - если вы создаете подкласс "теневого" представления, он может самостоятельно обрабатывать обновление вашей тени:
class MyShadowedView: UIView {
override init(frame: CGRect) {
super.init(frame: frame)
commonInit()
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
commonInit()
}
func commonInit() -> Void {
// non-changing properties - set on init
layer.masksToBounds = false
layer.shadowColor = UIColor.black.cgColor
layer.shadowOpacity = 0.25
layer.shadowOffset = CGSize(width: 0, height: 0)
layer.shadowRadius = 5.0
}
override func layoutSubviews() {
super.layoutSubviews()
// update the shadowPath
layer.shadowPath = UIBezierPath(rect: bounds).cgPath
}
}
Когда вы добавляете myView
к вашей раскадровке как UIView
, просто присвойте его классу MyShadowedView
, и вам не нужно делать какие-либо вызовы, чтобы добавить тень - он сделает это сам.
В-третьих - на основании размещенного вами кода, похоже, что у вашего myView
есть ограничение по высоте, и вы ограничиваете mySubView
его верхом и низом.Это означает, что mySubView
будет высотой myView
, и это никогда не изменится.Ваша функция «делегата» пытается изменить ее, но она всегда передает свою ограниченную высоту.
Итак ...
В вашем ViewController вы хотите добавить UIView
, присвойте его классу MyShadowedView
, присвойте ему ограничения Top, Leading и Trailing, как обычно (или Top, Width и CenterX, если это то, что вам нужно).
Для его высоты укажитеограничение высоты того, с чего следует начинать, , но делает это ограничение заполнителем, который будет удален во время выполнения.Это позволяет вам видеть его во время проектирования (и избегать жалоб IB на отсутствующие ограничения), но во время выполнения добавляемое подпредставление будет контролировать его высоту:
Ваш xib будет выглядеть следующим образом (ну, упрощенно - я уверен, что в нем больше элементов):
Примечание: предоставлениеНижнее ограничение aView
с приоритетом 999
также помогает избежать предупреждений об ограничениях IB.
Когда вы нажимаете кнопку, ваш код переключает постоянную ограничения высоты aView
между 100
и * 1056.*.Это расширит / свернет высоту его суперпредставления, которое будет контролировать высоту, если его суперпредставление (myView
в контроллере представления).
Ваш полный код в конечном итоге будет:
//
// TannerViewController.swift
//
// Created by Don Mag on 12/12/18.
//
import UIKit
class MySubView: UIView {
@IBOutlet weak var aView: UIView!
@IBOutlet weak var aViewHeightConstraint: NSLayoutConstraint!
var isViewCollapsed = false
@IBAction func toggleView(_ sender: Any) {
aViewHeightConstraint.constant = isViewCollapsed ? 100 : 0
isViewCollapsed = !isViewCollapsed
}
}
class TannerViewController: UIViewController {
@IBOutlet weak var myView: MyShadowedView!
override func viewDidLoad() {
super.viewDidLoad()
let mySubView: MySubView = UINib(nibName: "MySubView", bundle: nil).instantiate(withOwner: MySubView(), options: nil)[0] as! MySubView
mySubView.translatesAutoresizingMaskIntoConstraints = false
myView.addSubview(mySubView)
NSLayoutConstraint.activate([
mySubView.topAnchor.constraint(equalTo: myView.topAnchor, constant: 0.0),
mySubView.bottomAnchor.constraint(equalTo: myView.bottomAnchor, constant: 0.0),
mySubView.leadingAnchor.constraint(equalTo: myView.leadingAnchor, constant: 0.0),
mySubView.trailingAnchor.constraint(equalTo: myView.trailingAnchor, constant: 0.0),
])
}
}
class MyShadowedView: UIView {
override init(frame: CGRect) {
super.init(frame: frame)
commonInit()
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
commonInit()
}
func commonInit() -> Void {
// non-changing properties - set on init
layer.masksToBounds = false
layer.shadowColor = UIColor.black.cgColor
layer.shadowOpacity = 0.25
layer.shadowOffset = CGSize(width: 0, height: 0)
layer.shadowRadius = 5.0
}
override func layoutSubviews() {
super.layoutSubviews()
// update the shadowPath
layer.shadowPath = UIBezierPath(rect: bounds).cgPath
}
}
В результате:
Чтобы легко проверить этоВот источник раскадровки:
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.Storyboard.XIB" version="3.0" toolsVersion="14109" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES" initialViewController="jPc-3G-hfP">
<device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/>
</device>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14088"/>
<capability name="Safe area layout guides" minToolsVersion="9.0"/>
<capability name="documents saved in the Xcode 8 format" minToolsVersion="8.0"/>
</dependencies>
<scenes>
<!--Tanner View Controller-->
<scene sceneID="f8L-af-3cE">
<objects>
<viewController id="jPc-3G-hfP" customClass="TannerViewController" customModule="SW4Temp" customModuleProvider="target" sceneMemberID="viewController">
<view key="view" contentMode="scaleToFill" id="0I2-oK-Mx2">
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
<subviews>
<view clipsSubviews="YES" contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="uKj-M5-owl" customClass="MyShadowedView" customModule="SW4Temp" customModuleProvider="target">
<rect key="frame" x="40" y="120" width="295" height="100"/>
<color key="backgroundColor" red="1" green="0.83234566450000003" blue="0.47320586440000001" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="height" constant="100" placeholder="YES" id="qvT-aM-Weq" userLabel="Placeholder Height = 100"/>
</constraints>
</view>
</subviews>
<color key="backgroundColor" red="0.99953407049999998" green="0.98835557699999999" blue="0.47265523669999998" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstItem="uKj-M5-owl" firstAttribute="top" secondItem="twx-NV-wpY" secondAttribute="top" constant="100" id="141-8C-ZNl"/>
<constraint firstItem="twx-NV-wpY" firstAttribute="trailing" secondItem="uKj-M5-owl" secondAttribute="trailing" constant="40" id="5Zs-Or-GhR"/>
<constraint firstItem="uKj-M5-owl" firstAttribute="leading" secondItem="twx-NV-wpY" secondAttribute="leading" constant="40" id="R95-i1-Xb2"/>
</constraints>
<viewLayoutGuide key="safeArea" id="twx-NV-wpY"/>
</view>
<connections>
<outlet property="myView" destination="uKj-M5-owl" id="uCY-bV-QJd"/>
</connections>
</viewController>
<placeholder placeholderIdentifier="IBFirstResponder" id="q6f-6s-ke9" userLabel="First Responder" sceneMemberID="firstResponder"/>
</objects>
<point key="canvasLocation" x="53.600000000000001" y="101.19940029985008"/>
</scene>
</scenes>
</document>
и mySubView.xib:
<?xml version="1.0" encoding="UTF-8"?>
<document type="com.apple.InterfaceBuilder3.CocoaTouch.XIB" version="3.0" toolsVersion="14109" targetRuntime="iOS.CocoaTouch" propertyAccessControl="none" useAutolayout="YES" useTraitCollections="YES" useSafeAreas="YES" colorMatched="YES">
<device id="retina4_7" orientation="portrait">
<adaptation id="fullscreen"/>
</device>
<dependencies>
<deployment identifier="iOS"/>
<plugIn identifier="com.apple.InterfaceBuilder.IBCocoaTouchPlugin" version="14088"/>
<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"/>
<view contentMode="scaleToFill" id="iN0-l3-epB" customClass="MySubView" customModule="SW4Temp" customModuleProvider="target">
<rect key="frame" x="0.0" y="0.0" width="332" height="202"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
<subviews>
<button opaque="NO" contentMode="scaleToFill" verticalHuggingPriority="1000" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="T7q-1U-5iM">
<rect key="frame" x="106" y="20" width="120" height="30"/>
<color key="backgroundColor" red="0.92143100499999997" green="0.92145264149999995" blue="0.92144101860000005" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="width" constant="120" id="WJn-fl-dH1"/>
</constraints>
<state key="normal" title="Button"/>
<connections>
<action selector="toggleView:" destination="iN0-l3-epB" eventType="touchUpInside" id="LSR-3h-g1f"/>
</connections>
</button>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Vtd-O9-gRZ">
<rect key="frame" x="40" y="70" width="252" height="100"/>
<color key="backgroundColor" red="0.46202266219999999" green="0.83828371759999998" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="height" constant="100" id="e3B-MV-NZK"/>
</constraints>
</view>
</subviews>
<color key="backgroundColor" red="0.83216959239999999" green="0.98548370600000001" blue="0.47333085539999997" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="bottom" secondItem="Vtd-O9-gRZ" secondAttribute="bottom" priority="999" constant="20" id="0aE-RM-0AZ"/>
<constraint firstItem="T7q-1U-5iM" firstAttribute="top" secondItem="iN0-l3-epB" secondAttribute="top" constant="20" id="Acg-yV-bn2"/>
<constraint firstItem="Vtd-O9-gRZ" firstAttribute="top" secondItem="T7q-1U-5iM" secondAttribute="bottom" constant="20" id="KVh-lw-Sst"/>
<constraint firstItem="T7q-1U-5iM" firstAttribute="centerX" secondItem="iN0-l3-epB" secondAttribute="centerX" id="NUj-4y-fDg"/>
<constraint firstItem="Vtd-O9-gRZ" firstAttribute="leading" secondItem="iN0-l3-epB" secondAttribute="leading" constant="40" id="cS4-7R-wW7"/>
<constraint firstAttribute="trailing" secondItem="Vtd-O9-gRZ" secondAttribute="trailing" constant="40" id="kkG-9K-cEP"/>
</constraints>
<freeformSimulatedSizeMetrics key="simulatedDestinationMetrics"/>
<connections>
<outlet property="aView" destination="Vtd-O9-gRZ" id="SNl-ng-33p"/>
<outlet property="aViewHeightConstraint" destination="e3B-MV-NZK" id="S4R-ct-gzE"/>
</connections>
<point key="canvasLocation" x="12" y="-179"/>
</view>
</objects>
</document>