python - 在 Swift 中编码时出现 Python 错误:意外缩进 (Xcode 11)
问题描述
编辑:对于那些想要实际代码的人,请查阅此链接以获取所有相关源代码。 https://github.com/objcio/S01E118-introduction-prototype
为什么我会收到以下错误:
错误:模块导入失败:意外缩进(sniff_objc_exception_throw.py,第 7 行)文件“temp.py”,第 1 行,在
我正在使用 SwiftTalk 的一个项目示例,它在任何地方都没有任何明显的 python 代码,这让我认为这可能是一个 Xcode 导入问题。有人见过这个吗?我能做些什么来解决这个问题吗?
项目代码使用旧版本的 Swift(马特在下面指出......)。这是我在更新以删除所有编译错误并运行 Convert/Update to Swift 5 Utility 后的代码:
import UIKit
extension UIView {
func setSubviews<S: Sequence>(_ other: S) where S.Element == UIView {
let views = Set(other)
let sub = Set(subviews)
for v in sub.subtracting(views) {
v.removeFromSuperview()
}
for v in views.subtracting(sub) {
addSubview(v)
}
}
}
extension UILabel {
convenience init(text: String, size: UIFont.TextStyle, multiline: Bool = false) {
self.init()
font = UIFont.preferredFont(forTextStyle: size)
self.text = text
adjustsFontForContentSizeCategory = true
if multiline {
numberOfLines = 0
}
}
}
indirect enum Layout {
case view(UIView, Layout)
case newline(Layout)
case choice(Layout, Layout)
case empty
}
extension Layout {
func apply(containerWidth: CGFloat) -> [UIView] {
var result: [UIView] = []
var origin: CGPoint = .zero
var current: Layout = self
var lineHeight: CGFloat = 0
while true {
switch current {
case let .view(v, rest):
result.append(v)
let availableWidth = containerWidth - origin.x
let size = v.sizeThatFits(CGSize(width: availableWidth, height: .greatestFiniteMagnitude))
v.frame = CGRect(origin: origin, size: size)
lineHeight = max(lineHeight, size.height)
origin.x += size.width
current = rest
case let .newline(rest):
origin.x = 0
origin.y += lineHeight
lineHeight = 0
current = rest
case let .choice(first, second):
if first.fits(currentX: origin.x, containerWidth: containerWidth) {
current = first
} else {
current = second
}
case .empty:
return result
}
}
}
func fits(currentX: CGFloat, containerWidth: CGFloat) -> Bool {
var x = currentX
var current: Layout = self
while true {
switch current {
case let .view(v, rest):
let availableWidth = containerWidth - x
let size = v.sizeThatFits(CGSize(width: availableWidth, height: .greatestFiniteMagnitude))
x += size.width
if x >= containerWidth { return false }
current = rest
case let .newline(rest):
x = 0
current = rest
case let .choice(first, second):
if first.fits(currentX: x, containerWidth: containerWidth) {
return true
} else {
current = second
}
case .empty:
return true
}
}
}
}
final class LayoutContainer: UIView {
let layout: Layout
init(_ layout: Layout) {
self.layout = layout
super.init(frame: .zero)
// NotificationCenter.default.addObserver(self, selector: #selector(setNeedsLayout), name: Notification.Name.UIContentSizeCategory.didChangeNotification, object: nil)
}
required init?(coder aDecoder: NSCoder) {
fatalError("init(coder:) has not been implemented")
}
override func layoutSubviews() {
let views = layout.apply(containerWidth: bounds.width)
setSubviews(views)
}
}
class ViewController: UIViewController {
override func viewDidLoad() {
super.viewDidLoad()
let titleLabel = UILabel(text: "Building a Layout Library", size: .headline, multiline: true)
let episodeNumber = UILabel(text: "Episode 123", size: .body)
let episodeDate = UILabel(text: "September 23", size: .body)
let horizontal = Layout.view(episodeNumber, Layout.view(episodeDate, .empty))
let vertical = Layout.view(episodeNumber, .newline(Layout.view(episodeDate, .empty)))
let layout = Layout.view(titleLabel, .newline(
.choice(horizontal, vertical)
))
let container = LayoutContainer(layout)
container.translatesAutoresizingMaskIntoConstraints = false
view.addSubview(container)
view.addConstraints([
container.topAnchor.constraint(equalTo: view.layoutMarginsGuide.topAnchor),
container.leadingAnchor.constraint(equalTo: view.layoutMarginsGuide.leadingAnchor),
container.trailingAnchor.constraint(equalTo: view.layoutMarginsGuide.trailingAnchor),
])
}
}
需要明确的是:如果您将此代码复制并粘贴到项目的现有 ViewController.swift 内容上,则项目将编译,然后仅以指示的错误运行(模块导入失败:....)
解决方案
问题的核心是 Swift 语言版本问题。您所指的项目太老了,无法在现代 Swift 中编译。由于布局管理器无法解析代码,这会产生各种次要问题。解决方案是更新代码以匹配编译器中的 Swift 版本。
特别是更改UIFontTextStyle
为UIFont.TextStyle
和更改Notification.Name.UIContentSizeCategoryDidChange
为UIContentSizeCategory.didChangeNotification
。
推荐阅读
- spring-boot - 接收大数据时骆驼路线中断
- amazon-web-services - 从 ECS Docker 容器写入 cloudwatch 时缺少日志行
- php - PHP:为什么“${obj->prop}”是解析错误,而“$obj->prop”是合法的?
- android - 为什么这个布局需要 2-7 秒才能在 UI 中呈现?
- html - Div vs Div span 在用户界面角度显示文本
- node.js - 与多 pk 模型创建关联时出现问题
- php - 从 xml 文件中获取特定字段
- python-3.x - 在 python 3 parsegps(str) 中需要一个类似字节的对象而不是字符串
- reactjs - Apexcharts 工具提示样式未应用
- javascript - React - 如何创建动态(使用路由器)详细信息页面