我不确定这个问题是否重复,但是我基本上是在尝试获取一个UIScrollView,该UIScrollView的UIView中心在水平和垂直方向上都具有高度限制,并且我想知道如何仅使用代码来实现它。我会附加代码,但是我已经做了很多事情,现在不确定哪一个是正确的...
看起来像这样
这就是布局的结构方式:
Caoontainer视图是将通过更改高度约束值来调整大小的视图。
这是一些代码:
override func viewDidLoad() {
super.viewDidLoad()
print("\(logClassName) viewDidLoad")
view.backgroundColor = UIColor.AppColors.mainViewPopupBackground
view.addSubview(scrollView)
if #available(iOS 11.0, *) {
let guide = self.view.safeAreaLayoutGuide
scrollView.topAnchor.constraint(equalTo: guide.topAnchor).isActive = true
scrollView.trailingAnchor.constraint(equalTo: guide.trailingAnchor).isActive = true
scrollView.bottomAnchor.constraint(equalTo: guide.bottomAnchor).isActive = true
scrollView.leadingAnchor.constraint(equalTo: guide.leadingAnchor).isActive = true
scrollView.widthAnchor.constraint(equalTo: guide.widthAnchor).isActive = true
scrollView.heightAnchor.constraint(equalTo: guide.heightAnchor).isActive = true
}
else{
scrollView.centerXAnchor.constraint(equalTo: view.centerXAnchor).isActive = true
scrollView.widthAnchor.constraint(equalTo: view.widthAnchor).isActive = true
scrollView.topAnchor.constraint(equalTo: view.topAnchor).isActive = true
scrollView.bottomAnchor.constraint(equalTo: view.bottomAnchor).isActive = true
}
let dummyView = UIView()
dummyView.translatesAutoresizingMaskIntoConstraints = false
scrollView.addSubview(dummyView)
dummyView.widthAnchor.constraint(equalTo: scrollView.widthAnchor).isActive = true
dummyView.topAnchor.constraint(equalTo: scrollView.topAnchor).isActive = true
dummyView.trailingAnchor.constraint(equalTo: scrollView.trailingAnchor).isActive = true
dummyView.bottomAnchor.constraint(equalTo: scrollView.bottomAnchor).isActive = true
dummyView.leadingAnchor.constraint(equalTo: scrollView.leadingAnchor).isActive = true
dummyView.addSubview(contentView)
contentView.centerYAnchor.constraint(equalTo: dummyView.centerYAnchor).isActive = true
contentView.centerXAnchor.constraint(equalTo: dummyView.centerXAnchor).isActive = true
contentView.widthAnchor.constraint(equalTo: dummyView.widthAnchor,multiplier:0.85).isActive = true
contentView.heightAnchor.constraint(equalToConstant: 500).isActive = true
contentView.addSubview(titleView)
titleView.topAnchor.constraint(equalTo: contentView.topAnchor).isActive = true
titleView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor).isActive = true
titleView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor).isActive = true
titleView.heightAnchor.constraint(equalToConstant: 46).isActive = true
titleView.text = title == nil ? defaultTitle:title!
titleView.addBottomBorder(color: UIColor.AppColors.defaultSeparator, height: 1, margins: 0)
contentView.addSubview(buttonsView)
buttonsView.bottomAnchor.constraint(equalTo: contentView.bottomAnchor).isActive = true
buttonsView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor).isActive = true
buttonsView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor).isActive = true
buttonsView.heightAnchor.constraint(equalToConstant: 46).isActive = true
let multiplier:CGFloat = buttonDisplay == .both ? 0.5 : 1
let constant:CGFloat = buttonDisplay == .both ? -0.5 : 0
if buttonDisplay == .both || buttonDisplay == .cancelOnly {
buttonsView.addSubview(cancelButton)
cancelButton.topAnchor.constraint(equalTo: buttonsView.topAnchor).isActive = true
cancelButton.bottomAnchor.constraint(equalTo: buttonsView.bottomAnchor).isActive = true
cancelButton.leadingAnchor.constraint(equalTo: buttonsView.leadingAnchor).isActive = true
cancelButton.widthAnchor.constraint(equalTo: buttonsView.widthAnchor, multiplier: multiplier, constant: constant).isActive = true
cancelButton.setTitle(AppHelper.printLocalized(withKey: "com.message.cancel", targetSpecific: false), for: .normal)
}
if buttonDisplay == .both || buttonDisplay == .confirmOnly {
buttonsView.addSubview(confirmButton)
confirmButton.topAnchor.constraint(equalTo: buttonsView.topAnchor).isActive = true
confirmButton.bottomAnchor.constraint(equalTo: buttonsView.bottomAnchor).isActive = true
confirmButton.trailingAnchor.constraint(equalTo: buttonsView.trailingAnchor).isActive = true
confirmButton.widthAnchor.constraint(equalTo: buttonsView.widthAnchor, multiplier: multiplier, constant: constant).isActive = true
confirmButton.setTitle(AppHelper.printLocalized(withKey: "com.message.ok", targetSpecific: false), for: .normal)
}
buttonsView.addTopBorder(color: UIColor.AppColors.defaultSeparator, height: 1, margins: 0)
contentView.addSubview(containerView)
containerView.topAnchor.constraint(equalTo: titleView.bottomAnchor).isActive = true
containerView.bottomAnchor.constraint(equalTo: buttonsView.topAnchor).isActive = true
containerView.leadingAnchor.constraint(equalTo: contentView.leadingAnchor).isActive = true
containerView.trailingAnchor.constraint(equalTo: contentView.trailingAnchor).isActive = true
//containerView.heightAnchor.constraint(equalToConstant: defaultContentViewHeight).isActive = true
scrollView.contentInset = UIEdgeInsets.zero
}
以及上面代码中使用的变量:
override var title: String?{
didSet{
titleView.text = title!
}
}
var buttonDisplay:ButtonDisplay = ButtonDisplay.both
lazy var scrollView:UIScrollView = {
let aScrollView = UIScrollView()
aScrollView.translatesAutoresizingMaskIntoConstraints = false
aScrollView.bounces = true
aScrollView.isScrollEnabled = true
return aScrollView
}()
var defaultContentViewHeight:CGFloat{
var constant:CGFloat!
switch AppHelper.traitStatus{
case .wreghreg:
constant = 650
case .wcomhreg:
constant = 1600
case .wreghcom:
constant = 350
case .wcomhcom:
constant = 1300
}
return constant
}
lazy var contentView:MainView = {
var rtView = MainView()
rtView.backgroundColor = UIColor.AppColors.viewPopupBackground
rtView.translatesAutoresizingMaskIntoConstraints = false
return rtView
}()
lazy var titleView:MainLabel = {
var rtLabel = MainLabel(withConfiguration: .popupTitle)
rtLabel.translatesAutoresizingMaskIntoConstraints = false
rtLabel.backgroundColor = .green
return rtLabel
}()
lazy var buttonsView:UIView = {
var rtView = UIView()
rtView.translatesAutoresizingMaskIntoConstraints = false
return rtView
}()
lazy var cancelButton:MainButton = {
var rtView = MainButton(withConfiguration: .popupSecondary)
rtView.cornerRadius = 0
rtView.borderWidth = 0
rtView.addTarget(self, action: #selector(cancelAction), for: .touchUpInside)
rtView.translatesAutoresizingMaskIntoConstraints = false
return rtView
}()
lazy var confirmButton:MainButton = {
var rtView = MainButton(withConfiguration: .popup)
rtView.cornerRadius = 0
rtView.borderWidth = 0
rtView.addTarget(self, action: #selector(confirmAction(sender:)), for: .touchUpInside)
rtView.translatesAutoresizingMaskIntoConstraints = false
return rtView
}()
/*** USE THIS VIEW FOR APPENDING THE SPECIFIC CONTENT ***/
lazy var containerView:MainView = {
var rtView = MainView()
rtView.borderWidth = 0
rtView.cornerRadius = 0
rtView.backgroundColor = UIColor.red
rtView.translatesAutoresizingMaskIntoConstraints = false
return rtView
}()
谢谢
答案 0 :(得分:2)
一种方法:
在scrollView中将“根”视图的宽度和高度约束设置为与scrollView相等,但是将“高度”约束的优先级设置为250。
然后将页眉,“扩展内容”和页脚视图放入stackView中。将stackView在“根”视图中垂直居中,并将其顶部和底部约束设置为>= 8
(保留8点填充)。
现在,随着“扩展内容”视图更改高度(基于其内容),stackView将变高,但仍保持垂直居中。
添加了足够多的内容以超过scrollView的高度后,“根”视图上的低优先级将使其高度增加并变得可滚动。
这是情节提要中的布局:
这里是少量内容的外观:
,并且当它具有更多内容时(滚动到底部):
这是调试视图:
正确设置约束后,无需任何代码即可调整大小或滚动-所有这些操作均由自动版式处理。
要在运行中查看它,请将以下代码用于视图控制器:
//
// ViewController.swift
//
// Created by Don Mag on 11/9/18.
//
import UIKit
class ViewController: UIViewController {
@IBOutlet var expandingLabel: UILabel!
var nLines = 1
@IBAction func addLineTapped(_ sender: Any) {
nLines += 1
setLabelText()
}
@IBAction func removeLineTapped(_ sender: Any) {
if nLines > 2 {
nLines -= 1
setLabelText()
}
}
func setLabelText() -> Void {
var s = ""
if nLines == 0 {
s = "Expanding Label"
} else {
s = (1...nLines).map({ "Line \($0)" }).joined(separator: "\n")
}
expandingLabel.text = s
}
override func viewDidLoad() {
super.viewDidLoad()
setLabelText()
}
}
点击“添加行”和“删除行”按钮听起来像:)
以下是故事板的来源:
<?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="BYZ-38-t0r">
<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>
<!--View Controller-->
<scene sceneID="tne-QT-ifu">
<objects>
<viewController id="BYZ-38-t0r" customClass="ViewController" customModule="DrawOn" customModuleProvider="target" sceneMemberID="viewController">
<view key="view" contentMode="scaleToFill" id="8bC-Xf-vdC">
<rect key="frame" x="0.0" y="0.0" width="375" height="667"/>
<autoresizingMask key="autoresizingMask" widthSizable="YES" heightSizable="YES"/>
<subviews>
<scrollView clipsSubviews="YES" multipleTouchEnabled="YES" contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Vuw-Sq-3ds">
<rect key="frame" x="8" y="80" width="359" height="579"/>
<subviews>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="Fl6-G4-xCj" userLabel="Content View">
<rect key="frame" x="0.0" y="0.0" width="359" height="579"/>
<subviews>
<stackView opaque="NO" contentMode="scaleToFill" axis="vertical" distribution="equalSpacing" translatesAutoresizingMaskIntoConstraints="NO" id="jvv-bQ-6hQ">
<rect key="frame" x="40" y="220" width="279" height="140.5"/>
<subviews>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="bGL-74-7Fk" userLabel="Header View">
<rect key="frame" x="0.0" y="0.0" width="279" height="40"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Header View 40-pts Height" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="nt9-AP-bCN" userLabel="Header Label">
<rect key="frame" x="34.5" y="10" width="210" height="20.5"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" red="0.99999600649999998" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" red="0.0" green="0.0" blue="0.0" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstItem="nt9-AP-bCN" firstAttribute="centerY" secondItem="bGL-74-7Fk" secondAttribute="centerY" id="Ope-LL-yOC"/>
<constraint firstItem="nt9-AP-bCN" firstAttribute="centerX" secondItem="bGL-74-7Fk" secondAttribute="centerX" id="ZBt-dj-US2"/>
<constraint firstAttribute="height" constant="40" id="qul-fE-qXK"/>
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="HAK-GL-d2e" userLabel="Expanding Label Containing View">
<rect key="frame" x="0.0" y="40" width="279" height="60.5"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Expanding Label" textAlignment="center" lineBreakMode="tailTruncation" numberOfLines="0" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="ctw-D5-rv5" userLabel="Expanding Label">
<rect key="frame" x="8" y="8" width="263" height="44.5"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<nil key="textColor"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" red="0.46202266219999999" green="0.83828371759999998" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstAttribute="trailing" secondItem="ctw-D5-rv5" secondAttribute="trailing" constant="8" id="1sy-pt-g7z"/>
<constraint firstItem="ctw-D5-rv5" firstAttribute="top" secondItem="HAK-GL-d2e" secondAttribute="top" constant="8" id="NYL-G7-rQx"/>
<constraint firstAttribute="bottom" secondItem="ctw-D5-rv5" secondAttribute="bottom" constant="8" id="YK8-wy-8Pa"/>
<constraint firstItem="ctw-D5-rv5" firstAttribute="leading" secondItem="HAK-GL-d2e" secondAttribute="leading" constant="8" id="qfr-5Z-1gw"/>
</constraints>
</view>
<view contentMode="scaleToFill" translatesAutoresizingMaskIntoConstraints="NO" id="O4w-A4-H6n" userLabel="Footer View">
<rect key="frame" x="0.0" y="100.5" width="279" height="40"/>
<subviews>
<label opaque="NO" userInteractionEnabled="NO" contentMode="left" horizontalHuggingPriority="251" verticalHuggingPriority="251" text="Footer View 40-pts Height" textAlignment="center" lineBreakMode="tailTruncation" baselineAdjustment="alignBaselines" adjustsFontSizeToFit="NO" translatesAutoresizingMaskIntoConstraints="NO" id="q6s-5S-Sx9" userLabel="Footer Label">
<rect key="frame" x="38" y="10" width="203.5" height="20.5"/>
<fontDescription key="fontDescription" type="system" pointSize="17"/>
<color key="textColor" red="0.99999600649999998" green="1" blue="1" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<nil key="highlightedColor"/>
</label>
</subviews>
<color key="backgroundColor" white="0.0" alpha="1" colorSpace="custom" customColorSpace="genericGamma22GrayColorSpace"/>
<constraints>
<constraint firstItem="q6s-5S-Sx9" firstAttribute="centerY" secondItem="O4w-A4-H6n" secondAttribute="centerY" id="35l-M2-X4u"/>
<constraint firstItem="q6s-5S-Sx9" firstAttribute="centerX" secondItem="O4w-A4-H6n" secondAttribute="centerX" id="TqO-pv-FLb"/>
<constraint firstAttribute="height" constant="40" id="x7P-kS-KhJ"/>
</constraints>
</view>
</subviews>
</stackView>
</subviews>
<color key="backgroundColor" red="0.0" green="0.56031829119999998" blue="0.0" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstItem="jvv-bQ-6hQ" firstAttribute="centerY" secondItem="Fl6-G4-xCj" secondAttribute="centerY" id="bDX-eg-0dD"/>
<constraint firstAttribute="bottom" relation="greaterThanOrEqual" secondItem="jvv-bQ-6hQ" secondAttribute="bottom" constant="8" id="c8T-Oc-P0W"/>
<constraint firstItem="jvv-bQ-6hQ" firstAttribute="leading" secondItem="Fl6-G4-xCj" secondAttribute="leading" constant="40" id="gHz-UY-a8e"/>
<constraint firstItem="jvv-bQ-6hQ" firstAttribute="top" relation="greaterThanOrEqual" secondItem="Fl6-G4-xCj" secondAttribute="top" constant="8" id="tDD-Zr-Jne"/>
<constraint firstAttribute="trailing" secondItem="jvv-bQ-6hQ" secondAttribute="trailing" constant="40" id="tke-Qx-y9t"/>
</constraints>
</view>
</subviews>
<color key="backgroundColor" red="0.45009386540000001" green="0.98132258650000004" blue="0.4743030667" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstItem="Fl6-G4-xCj" firstAttribute="width" secondItem="Vuw-Sq-3ds" secondAttribute="width" id="1LN-nS-m1O"/>
<constraint firstAttribute="trailing" secondItem="Fl6-G4-xCj" secondAttribute="trailing" id="Rgx-xv-bed"/>
<constraint firstAttribute="bottom" secondItem="Fl6-G4-xCj" secondAttribute="bottom" id="hL3-ST-FnS"/>
<constraint firstItem="Fl6-G4-xCj" firstAttribute="top" secondItem="Vuw-Sq-3ds" secondAttribute="top" id="qgo-Qw-qCM"/>
<constraint firstItem="Fl6-G4-xCj" firstAttribute="height" secondItem="Vuw-Sq-3ds" secondAttribute="height" priority="250" id="tiq-6l-uQh"/>
<constraint firstItem="Fl6-G4-xCj" firstAttribute="leading" secondItem="Vuw-Sq-3ds" secondAttribute="leading" id="yYB-d7-S2y"/>
</constraints>
</scrollView>
<stackView opaque="NO" contentMode="scaleToFill" distribution="fillEqually" spacing="40" translatesAutoresizingMaskIntoConstraints="NO" id="NNa-E5-guI">
<rect key="frame" x="37.5" y="32" width="300" height="30"/>
<subviews>
<button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="jeW-uV-cnV">
<rect key="frame" x="0.0" y="0.0" width="130" height="30"/>
<color key="backgroundColor" red="0.99953407049999998" green="0.98835557699999999" blue="0.47265523669999998" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<state key="normal" title="Add a Line"/>
<connections>
<action selector="addLineTapped:" destination="BYZ-38-t0r" eventType="touchUpInside" id="NGU-XZ-sUi"/>
</connections>
</button>
<button opaque="NO" contentMode="scaleToFill" contentHorizontalAlignment="center" contentVerticalAlignment="center" buttonType="roundedRect" lineBreakMode="middleTruncation" translatesAutoresizingMaskIntoConstraints="NO" id="1SN-WP-tr5">
<rect key="frame" x="170" y="0.0" width="130" height="30"/>
<color key="backgroundColor" red="0.99953407049999998" green="0.98835557699999999" blue="0.47265523669999998" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<state key="normal" title="Remove a Line"/>
<connections>
<action selector="removeLineTapped:" destination="BYZ-38-t0r" eventType="touchUpInside" id="80A-rI-a0B"/>
</connections>
</button>
</subviews>
<constraints>
<constraint firstAttribute="width" constant="300" id="xdn-ra-Mpq"/>
</constraints>
</stackView>
</subviews>
<color key="backgroundColor" red="1" green="0.83234566450000003" blue="0.47320586440000001" alpha="1" colorSpace="custom" customColorSpace="sRGB"/>
<constraints>
<constraint firstItem="Vuw-Sq-3ds" firstAttribute="leading" secondItem="6Tk-OE-BBY" secondAttribute="leading" constant="8" id="0as-vV-CWL"/>
<constraint firstItem="NNa-E5-guI" firstAttribute="centerX" secondItem="8bC-Xf-vdC" secondAttribute="centerX" id="EEn-yg-Ba2"/>
<constraint firstItem="6Tk-OE-BBY" firstAttribute="bottom" secondItem="Vuw-Sq-3ds" secondAttribute="bottom" constant="8" id="i1E-50-PXU"/>
<constraint firstItem="6Tk-OE-BBY" firstAttribute="trailing" secondItem="Vuw-Sq-3ds" secondAttribute="trailing" constant="8" id="kep-Qo-OTQ"/>
<constraint firstItem="NNa-E5-guI" firstAttribute="top" secondItem="6Tk-OE-BBY" secondAttribute="top" constant="12" id="l5O-iv-7h9"/>
<constraint firstItem="Vuw-Sq-3ds" firstAttribute="top" secondItem="6Tk-OE-BBY" secondAttribute="top" constant="60" id="pYU-HL-mIH"/>
</constraints>
<viewLayoutGuide key="safeArea" id="6Tk-OE-BBY"/>
</view>
<connections>
<outlet property="expandingLabel" destination="ctw-D5-rv5" id="oDW-fm-PtZ"/>
</connections>
</viewController>
<placeholder placeholderIdentifier="IBFirstResponder" id="dkx-z0-nzr" sceneMemberID="firstResponder"/>
</objects>
</scene>
</scenes>
</document>
答案 1 :(得分:0)
信息似乎有点不足,尽管这可能有所帮助:
在界面构建器中,为您的容器视图添加高度限制,例如height = 100。
然后从检查器中将'='更改为高度'> ='100
现在,无论何时将任何内容追加为蓝色时,它都会自动调整大小。
注意:还将蓝色视图的约束设置为“> =”某个值。
答案 2 :(得分:0)