Sobes.tech
Middle

Kaip nustatyti, ar naudotojas paspaudė sluoksnį (layer) programėlėje?

sobes.tech AI

Atsakymas iš AI

Nustatant paspaudimą ant CALayer, galite naudoti keletą būdų:

  1. Naudoti hitTest(_:event:) vaizde (View):

    • UIView turi metodą hitTest(_:with:), kuris rekursyviai pereina per subview hierarchiją ir grąžina giliausią subview, kuris apima nurodytą tašką:
    • Šis metodas pagal numatytuosius nustatymus atsižvelgia į susijusius sluoksnius su vaizdais:
    • Galite perrašyti hitTest(_:with:) savo pritaikytame vaizde, kad turėtumėte detalesnę kontrolę arba apdorotumėte paspaudimus tiesiogiai ant sluoksnių, nesusijusių su vaizdais:
  2. Koordinatų konvertavimas naudojant convert:

    • Kai gaunate prisilietimo įvykį (pavyzdžiui, UIView metoduose), turite koordinates, susijusias su langu (UIWindow) arba vaizdu:
    • Norėdami nustatyti, ar prisilietimas pataikė į tam tikrą sluoksnį, turite konvertuoti šias koordinates į to sluoksnio koordinatų sistemą:
    • Tam naudojami convert(_:from:) arba convert(_:to:) metodai CALayer:
    • Po konvertavimo galima patikrinti, ar gauta taškas yra sluoksnio ribose (bounds) arba naudoti specifinius patikrinimus, pvz., contains(_:):
  3. Prikabinimas UITapGestureRecognizer prie vaizdo:

    • Galite prikabinti UITapGestureRecognizer prie UIView, susijusio su sluoksniu:
    • Apdorojimo metu gauti prisilietimo vietą pagal vaizdą:
    • Tada naudoti koordinačių konvertavimo metodą (dalys 2), kad patikrintumėte, ar taškas yra norimo sluoksnio ar jo subsluoksnių viduje:
  4. Sukurti UIView kiekvienam interaktyviam sluoksniui:

    • Jei turite sluoksnius, kurie turi būti interaktyvūs, paprasčiausias būdas — sukurti atitinkamą UIView kiekvienam tokiam sluoksniui:
    • Išdėstyti ir nustatyti UIView dydį pagal sluoksnį:
    • Prikabinti gestų apdorojimo funkcijas (UITapGestureRecognizer) arba perrašyti prisilietimo įvykių apdorojimo metodus (touchesBegan, touchesEnded ir kt.) šiame vaizde:
    • Tai yra labiausiai idiomatiškas būdas apdoroti naudotojo įvestį UIKit, nes UIView yra specialiai tam skirtas:

Pavyzdys naudojant hitTest UIView:

// Pritaikytame `UIView`
override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
    // Konvertuoti prisilietimo tašką į subsluoksnio koordinates
    let pointInLayer = mySublayer.convert(point, from: layer!)
    
    // Patikrinti, ar taškas yra sluoksnio ribose
    if mySublayer.contains(pointInLayer) {
        // Jei taškas yra subsluoksnyje, galite grąžinti save arba kitą vaizdą,
        // arba atlikti reikiamus veiksmus:
        print("Paspausta ant mySublayer")
        // Galite grąžinti nil, jei nenorite, kad šis vaizdas toliau apdorotų,
        // arba `super.hitTest(point, with: event)` jei norite išsaugoti standartinį elgesį
    }
    
    // Leisti standartiniam `hitTest` apdoroti likusius atvejus
    return super.hitTest(point, with: event)
}

Pavyzdys naudojant koordinačių konvertavimą į žestų apdorojimo funkcijoje:

// Pritaikytame `UIView` su pririštu `UITapGestureRecognizer`
@objc func handleTap(_ sender: UITapGestureRecognizer) {
    let tapLocationInView = sender.location(in: self)
    
    // Konvertuoti prisilietimo tašką iš vaizdo koordinačių į subsluoksnio koordinates
    let tapLocationInSublayer = mySublayer.convert(tapLocationInView, from: layer!)
    
    // Patikrinti, ar taškas yra subsluoksnio ribose
    if mySublayer.contains(tapLocationInSublayer) {
        print("Paspausta ant mySublayer")
        // Atlikti veiksmus, susijusius su paspaudimu ant subsluoksnio
    }
}