कोई भी कृपया मेरी मदद करें, मेरे पास एक ड्रॉप डाउन है लेकिन मैं इसे दूसरी पंक्ति नहीं चुन सकता। मैं समझ नहीं पा रहा हूं कि क्यों, मैं लाने के साथ खेलने की कोशिश करता हूं सबव्यू टोफ्रंट या बैक। मैं परत का उपयोग करने का प्रयास करता हूं। zPosition यह अभी भी दूसरी पंक्ति का चयन नहीं कर सकता है, लेकिन जब मैं पहली पंक्ति चुनता हूं तो यह काम करता है। क्या यह मेरा ऑटो लेआउट सेटअप गलत है?

यहाँ मेरा यूआई और कोड सेटअप है

dropdownshit

// This is my custom Button

class GDropdownSchedule: UIButton {
    let headerLbl   = GTitleLabel(name: "Schedule Type".localized(), fontSize: 13, color: #colorLiteral(red: 0.4588235294, green: 0.4941176471, blue: 0.5647058824, alpha: 1))
    let bodyLbl     = GSubtitleLabel(name: "Additional Note".localized(), fontSize: 16, color: #colorLiteral(red: 0.09803921569, green: 0.09803921569, blue: 0.09803921569, alpha: 1))
    let dropDownIV  = GIconImageView(img: #imageLiteral(resourceName: "down-chevron"))
    var isOpen              = false
    let dropView    = DropDownView()
    var delegate: AddScheduleVCDelegate?
    var height: NSLayoutConstraint!
    override init(frame: CGRect) {
        super.init(frame: frame)
        configure()
    }
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
    private func configure() {
        backgroundColor     = #colorLiteral(red: 0.9764705882, green: 0.9764705882, blue: 0.9764705882, alpha: 1)
        layer.cornerRadius  = 5
        layer.borderWidth   = 1
        layer.borderColor   = #colorLiteral(red: 0.9411764706, green: 0.9411764706, blue: 0.9450980392, alpha: 1)
        dropView.completion = { text in
            self.bodyLbl.text = text
            self.bodyLbl.font = UIFont(name: "NunitoSans-Regular", size: 12)
            self.delegate?.toggleHide(selected: text)
            self.dismissDropDown()
        }
    }
    override func didMoveToSuperview() {
        addSubview(headerLbl)
        headerLbl.anchor(top: topAnchor, trailing: nil, bottom: nil, leading: leadingAnchor, topPadding: 10, rightPadding: 0, bottomPadding: 0, leftPadding: 10, width: 70, height: 18)
        addSubview(bodyLbl)
        bodyLbl.anchor(top: headerLbl.bottomAnchor, trailing: nil, bottom: bottomAnchor, leading: leadingAnchor, topPadding: 2, rightPadding: 10, bottomPadding: 10, leftPadding: 10, width: 0, height: 0)
        addSubview(dropDownIV)
        dropDownIV.tintColor = #colorLiteral(red: 0.2549019608, green: 0.3019607843, blue: 0.3568627451, alpha: 1)
        dropDownIV.anchor(top: nil, trailing: trailingAnchor, bottom: bottomAnchor, leading: nil, topPadding: 0, rightPadding: 18, bottomPadding: 17, leftPadding: 0, width: 12, height: 10)
        addSubview(dropView)
        dropView.translatesAutoresizingMaskIntoConstraints = false
        dropView.layer.zPosition = 1
        height = dropView.heightAnchor.constraint(equalToConstant: 0)
        NSLayoutConstraint.activate([
            dropView.topAnchor.constraint(equalTo: headerLbl.bottomAnchor),
            dropView.leadingAnchor.constraint(equalTo: leadingAnchor),
            dropView.trailingAnchor.constraint(equalTo: trailingAnchor)
        ])
    }
    override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
        if isOpen == false {
            isOpen = true
            NSLayoutConstraint.deactivate([height])
            if self.dropView.tableView.contentSize.height > 150 {
                height.constant = 150
            } else {
                height.constant = dropView.tableView.contentSize.height
            }
            NSLayoutConstraint.activate([height])
            UIView.animate(withDuration: 0.5, delay: 0, usingSpringWithDamping: 0.5, initialSpringVelocity: 0.5, options: .curveEaseInOut, animations: {
                self.dropView.layoutIfNeeded()
                self.dropView.center.y += self.dropView.frame.height / 2
            })
        } else {
            isOpen = false
            NSLayoutConstraint.deactivate([height])
            height.constant = 0
            NSLayoutConstraint.activate([height])
            UIView.animate(withDuration: 0.5, delay: 0, usingSpringWithDamping: 0.5, initialSpringVelocity: 0.5, options: .curveEaseInOut, animations: {
                self.dropView.center.y -= self.dropView.frame.height / 2
                self.dropView.layoutIfNeeded()
            })
        }
    }
    func dismissDropDown() {
        isOpen = false
        NSLayoutConstraint.deactivate([height])
        height.constant = 0
        NSLayoutConstraint.activate([height])
        UIView.animate(withDuration: 0.5, delay: 0, usingSpringWithDamping: 0.5, initialSpringVelocity: 0.5, options: .curveEaseInOut, animations: {
            self.dropView.center.y -= self.dropView.frame.height / 2
            self.dropView.layoutIfNeeded()
        })
    }
}
class DropDownView: UIView, UITableViewDelegate, UITableViewDataSource {
    let tableView           = UITableView()
    var options             = [String]()
    var completion: ((String) -> Void)?
    var isHideSchedule      = false
    override init(frame: CGRect) {
        super.init(frame: frame)
        configure()
    }
    required init?(coder: NSCoder) {
        fatalError("init(coder:) has not been implemented")
    }
    private func configure() {
        translatesAutoresizingMaskIntoConstraints = false
        addSubview(tableView)
        tableView.backgroundColor = #colorLiteral(red: 0.9764705882, green: 0.9764705882, blue: 0.9764705882, alpha: 1)
        tableView.separatorStyle = .none
        tableView.delegate      = self
        tableView.dataSource    = self
        tableView.anchor(top: topAnchor, trailing: trailingAnchor, bottom: bottomAnchor, leading: leadingAnchor, topPadding: 0, rightPadding: 0, bottomPadding: 0, leftPadding: 0, width: 0, height: 0)
    }
    func tableView(_ tableView: UITableView, numberOfRowsInSection section: Int) -> Int {
        return options.count
    }
    func tableView(_ tableView: UITableView, cellForRowAt indexPath: IndexPath) -> UITableViewCell {
        let cell = UITableViewCell()
        cell.textLabel?.text = options[indexPath.row]
        cell.textLabel?.font = UIFont(name: "NunitoSans-Regular", size: 12)
        cell.textLabel?.textColor = #colorLiteral(red: 0.09803921569, green: 0.09803921569, blue: 0.09803921569, alpha: 1)
        cell.backgroundColor = #colorLiteral(red: 0.9764705882, green: 0.9764705882, blue: 0.9764705882, alpha: 1)
        return cell
    }
    func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
        completion?(options[indexPath.row])
        tableView.deselectRow(at: indexPath, animated: true)
    }
}

// This is in my viewController, the chooseScheduleDropDown is my customButton
[chooseScheduleDropDown, entryView, chooseDateView, chooseClass, startTimeView, endTimeView, descriptionView, saveBtn].forEach {
            v in
            v.translatesAutoresizingMaskIntoConstraints = false
            scrollView.addSubview(v)
        }
        scrollView.insertSubview(entryView, belowSubview: chooseScheduleDropDown)
0
ferryawijayanto 26 मार्च 2020, 10:01

1 उत्तर

सबसे बढ़िया उत्तर

हिट-टेस्ट तंत्र के कारण

आप बटन GDropdownSchedule पर ड्रॉप व्यू जोड़ते हैं

लेआउट है

        addSubview(dropView)
        dropView.translatesAutoresizingMaskIntoConstraints = false
        dropView.layer.zPosition = 1
        height = dropView.heightAnchor.constraint(equalToConstant: 0)
        NSLayoutConstraint.activate([
            dropView.topAnchor.constraint(equalTo: headerLbl.bottomAnchor),
            dropView.leadingAnchor.constraint(equalTo: leadingAnchor),
            dropView.trailingAnchor.constraint(equalTo: trailingAnchor)
        ])

दिखने और मौजूदा कोड से,

ड्रॉपव्यू का फ्रेम बटन GDropdownSchedule की सीमा से आंशिक रूप से बाहर है।

तो आप इसे देख सकते हैं, और आपका क्लिक काम नहीं करता है।


हिट-टेस्ट तंत्र को ओवरराइड करना ठीक है

 class GDropdownSchedule: UIButton {

 // ...

   override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
        // if the button is hidden/disabled/transparent it can't be hit
        if self.isHidden || !self.isUserInteractionEnabled || self.alpha < 0.01 { return nil }

        let dropViewF = dropView.frame


        var index = 9
        if bounds.contains(point){
            index = 0
        }

        if dropViewF.contains(point){
            index = 1
        }

        switch index {
        case 0:
            for subV in subviews.reversed(){
                let realPoint = subV.convert(point, from: self)
                let hit = subV.hitTest(realPoint, with: event)
                if let v = hit{
                    return v
                }
            }
            return self
        case 1:
            if dropView.alpha > 0.01{
                let realPoint = dropView.convert(point, from: self)
                let hit = dropView.hitTest(realPoint, with: event)
                if let v = hit{
                    return v
                }
            }
        default:
            ()
        }
        return nil
    }

 }

Apple के Doc . से

हिटटेस्ट(_:with:)

यह विधि प्रत्येक सबव्यू के बिंदु (अंदर: के साथ:) विधि को कॉल करके दृश्य पदानुक्रम का पता लगाती है ताकि यह निर्धारित किया जा सके कि किस सबव्यू को टच इवेंट प्राप्त करना चाहिए।

यदि बिंदु (अंदर: के साथ:) सत्य लौटाता है, तो सबव्यू के पदानुक्रम को समान रूप से तब तक ट्रेस किया जाता है जब तक कि निर्दिष्ट बिंदु वाला सबसे सामने वाला दृश्य नहीं मिल जाता। यदि किसी दृश्य में बिंदु नहीं है, तो दृश्य पदानुक्रम की उसकी शाखा को अनदेखा कर दिया जाता है।

आपको शायद ही कभी इस विधि को स्वयं कॉल करने की आवश्यकता हो, लेकिन आप सबव्यू से स्पर्श ईवेंट छिपाने के लिए इसे ओवरराइड कर सकते हैं।

3
dengApro 26 मार्च 2020, 08:52