以Swift编程方式向子视图中添加/删除图像

3
使用在此帖子中找到的代码,我能够以编程方式绘制和擦除一个子视图,包括位置、宽度和高度,如下所示的函数addLoadButton和removeSubview。我还发现了如何在主视图控制器上以编程方式绘制图片,如下所示的函数trailerLoadImage。然而,在许多小时和尝试之后,我尝试以编程方式添加和删除该子视图中的图像,但没有成功。
我的最终目标是能够按下三个不同的拖车装载类型按钮,将三个不同的图像(按钮1加载图像1,按钮2加载图像2等)插入位于屏幕特定位置的子视图中,并能够逐个删除这些图像(可能不按照放置顺序),通过用手指点击图像或按下清除所有添加的图像的按钮来实现。子视图可以是永久的,也可以是以编程方式创建和删除的(如下所示)。
我应该使用什么代码将图像或多个不同的图像插入到已经创建的子视图中,以相反的顺序删除添加的图像,并清除子视图中的所有图像?如果无法完成此操作,则可接受的替代方案是通过点击图像或按下清除所有添加的图像的按钮从主VC中删除图像。
//Class declaration
class ViewController: UIViewController, UIPickerViewDelegate, UIPickerViewDataSource, UITextFieldDelegate {

    //Boolean to include load type one in calculations
    var trailerLoad : Bool = false
    var trailerLoadDistanceFromFront = 20

    //Boolean to include load type two in calculations
    var trailerLoadTwo : Bool = false
    var trailerLoadTwoDistanceFromFront = 80

    //Boolean to include load type three in calculations
    var trailerLoadThree : Bool = false
    var trailerLoadThreeDistanceFromFront = 120

    var trailerLoadWidth : Int = 0
    var trailerLoadX : Int = 0

    //Boolean true only when subView on trailer is active
    var subViewActive : Bool = false


    override func viewDidLoad() {
        super.viewDidLoad()

        //Picker view data sources and delegates included in here and work fine
    }


    //Adds subview for loads
    @IBAction func addLoadButton(_ sender: Any) {

        let trailerLoadView: UIView = UIView(frame: CGRect(x: 252, y: 233, width: 378, height: 100))
        trailerLoadView.backgroundColor = .blue
        trailerLoadView.alpha = 0.5
        trailerLoadView.tag = 100
        trailerLoadView.isUserInteractionEnabled = true
        self.view.addSubview(trailerLoadView)

        subViewActive = true
    }


    //If subViewActive is true, calls alert to get distance load type one is from front, moves on to insert and position image, changes trailerLoad bool to true
    @IBAction func trailerLoadOneButton(_ sender: Any) {
        //If subViewActive is true:
            //Calls alert to get distance load type one is from front, puts in var trailerLoadDistanceFromFront
            //Calls trailerLoadImage() to insert and position load type one image
            //Changes bool trailerLoad to true
        //If subViewActive is false:
            //Calls alert to tell user that they need to click Add Load button (create subview) before adding load types one, two, or three
    }


    //Add trailer load type one image, scales and positions it relatively accurately in view.
    //To be duplicated and modified for load types two and three in the future, with different images (trailerLoadTypeTwoPic and trailerLoadTypeThreePic)
    func trailerLoadImage() {

        trailerLoadWidth = 378 * 60 / trailerTotalLength
        trailerLoadX = 378 * trailerLoadDistanceFromFront / trailerTotalLength

        let imageView = UIImageView(frame: CGRect(x: (252 + trailerLoadX), y: (333 - trailerLoadWidth), width: trailerLoadWidth, height: trailerLoadWidth));
        let image = UIImage(named: “trailerLoadTypeOnePic”);

        imageView.image = image;
        self.view.addSubview(imageView)
    }


    //Calls func removeSubview to remove subview
    @IBAction func resetButton(_ sender: Any) {

        removeSubview()
    }


    //Removes subview for loads
    @objc func removeSubview(){

        subViewActive = false

        if let viewWithTag = self.view.viewWithTag(100) {
            viewWithTag.removeFromSuperview()
        }else{
            print("No!")
        }
    }
}

非常感谢任何提供帮助或建议的人。

如果你想让用户通过点击图像视图来删除它,那么你应该使图像视图可点击。但是你没有这样做。 - matt
我正在努力实现该功能,但目前(暂时)更愿意通过单独标记的重置按钮来清除子视图中的图像。我目前遇到的主要困难是通过编程方式插入和删除子视图中的图像。 - Robert
好的,哪一部分有问题,是插入子视图还是移除子视图?请尽可能具体地说明问题所在。 - matt
好的,答案正确。 - matt
如果 self.view 只包含这些图像视图,则可以通过请求 let ims = self.view.subviews.filter{$0 is UIImageView} 来获取它们的数组。现在,您已经按添加顺序获得了图像视图,并且可以更改其中一个的图像,将其从其父视图中删除等操作。 - matt
显示剩余2条评论
1个回答

2

不要使用标签!只需在全局范围内为您的视图创建变量。

var imageViews = [UIImageView]()

当您需要添加它们时,请先将它们附加到您的数组中,然后再将它们添加到 view

imageViews.append(imageView)
view.addSubview(imageView)

当您需要从父视图中移除所有视图时,对于数组中的每个视图,请使用removeFromSuperview()方法。

imageViews.forEach { $0.removeFromSuperview() }
imageViews.removeAll()

或者如果您需要删除特定索引处的一个视图。
imageViews[index].removeFromSuperview()
imageViews.remove(at: index)

嗨,Robert,我已经尝试将你的代码集成到我的代码中,但是无论我从我的代码中删除或替换什么,我都会收到不同的错误。我已经更新了帖子,以更好地澄清我的最终目标并包含更多的代码。你能否请展示一下如何更改我的代码来包含你的代码并实现最终目标? - Robert

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接