จะตรวจจับเหตุการณ์ได้อย่างไรเมื่อผู้ใช้สิ้นสุดการลากตัวชี้ตัวเลื่อน
จะตรวจจับเหตุการณ์ได้อย่างไรเมื่อผู้ใช้สิ้นสุดการลากตัวชี้ตัวเลื่อน
คำตอบ:
หากคุณไม่ต้องการข้อมูลใด ๆ ระหว่างการลากมากกว่าที่คุณควรตั้งค่า:
[mySlider setContinuous: NO];
วิธีนี้คุณจะได้รับvalueChanged
เหตุการณ์เมื่อผู้ใช้หยุดเลื่อนแถบเลื่อนเท่านั้น
เวอร์ชันSwift 5 :
mySlider.isContinuous = false
self.mySlider.isContinuous = false
คุณสามารถเพิ่มการดำเนินการที่รับสองพารามิเตอร์ผู้ส่งและเหตุการณ์สำหรับ UIControlEventValueChanged:
[slider addTarget:self action:@selector(onSliderValChanged:forEvent:) forControlEvents:UIControlEventValueChanged]
จากนั้นตรวจสอบเฟสของวัตถุสัมผัสในตัวจัดการของคุณ:
- (void)onSliderValChanged:(UISlider*)slider forEvent:(UIEvent*)event {
UITouch *touchEvent = [[event allTouches] anyObject];
switch (touchEvent.phase) {
case UITouchPhaseBegan:
// handle drag began
break;
case UITouchPhaseMoved:
// handle drag moved
break;
case UITouchPhaseEnded:
// handle drag ended
break;
default:
break;
}
}
Swift 4 และ 5
slider.addTarget(self, action: #selector(onSliderValChanged(slider:event:)), for: .valueChanged)
@objc func onSliderValChanged(slider: UISlider, event: UIEvent) {
if let touchEvent = event.allTouches?.first {
switch touchEvent.phase {
case .began:
// handle drag began
case .moved:
// handle drag moved
case .ended:
// handle drag ended
default:
break
}
}
}
หมายเหตุใน Interface Builder เมื่อเพิ่มการดำเนินการคุณยังมีตัวเลือกในการเพิ่มพารามิเตอร์ผู้ส่งและเหตุการณ์ให้กับการดำเนินการ
isContinuous = true
ในUISlider
ไฟล์.
ฉันใช้การแจ้งเตือน "Touch Up Inside" และ "Touch up outside"
ตัวสร้างอินเทอร์เฟซ:
เชื่อมต่อการแจ้งเตือนทั้งสองในตัวสร้างอินเทอร์เฟซกับวิธีการรับของคุณ วิธีการอาจมีลักษณะดังนี้:
- (IBAction)lengthSliderDidEndSliding:(id)sender {
NSLog(@"Slider did end sliding... Do your stuff here");
}
ในรหัส:
หากคุณต้องการวางสายโดยใช้โปรแกรมคุณจะมีสิ่งนี้ใน viewWillAppear (หรือที่ใดก็ตามที่เหมาะกับคุณ) โทร:
[_mySlider addTarget:self
action:@selector(sliderDidEndSliding:)
forControlEvents:(UIControlEventTouchUpInside | UIControlEventTouchUpOutside)];
วิธีการรับจะมีลักษณะดังนี้:
- (void)sliderDidEndSliding:(NSNotification *)notification {
NSLog(@"Slider did end sliding... Do your stuff here");
}
ตั้งแต่UISlider
เป็น subclass ของคุณสามารถตั้งค่าเป้าหมายและการดำเนินการของUIControl
UIControlEventTouchUpInside
หากคุณต้องการทำในรหัสจะมีลักษณะดังนี้:
[self.slider addTarget:self action:@selector(dragEndedForSlider:)
forControlEvents:UIControlEventTouchUpInside];
ซึ่งจะส่งdragEndedForSlider:
ข้อความถึงคุณเมื่อการสัมผัสสิ้นสุดลง
หากคุณต้องการทำในปลายปากกาคุณสามารถควบคุมแล้วคลิกแถบเลื่อนเพื่อรับเมนูการเชื่อมต่อจากนั้นลากจากซ็อกเก็ต“ Touch Up Inside” ไปยังวัตถุเป้าหมาย
นอกจากนี้คุณควรเพิ่มเป้าหมายและการดำเนินการและUIControlEventTouchUpOutside
UIControlEventTouchCancel
UISlider
ฉันเปลี่ยนไปตั้งแต่ฉันเขียนคำตอบนี้
UIControlEventTouchCancel
การจัดการใน iOS 9. แต่ฉันสามารถที่จะเรียกใช้UIControlEventTouchUpInside
และUIControlEventTouchUpOutside
เพียง
เพิ่มเป้าหมายtouchUpInside
และtouchUpOutside
เหตุการณ์ คุณสามารถทำได้ทั้งแบบเป็นโปรแกรมหรือจากสตอรีบอร์ด นี่คือวิธีที่คุณทำโดยใช้โปรแกรม
slider.addTarget(self, action: #selector(sliderDidEndSliding), for: [.touchUpInside, .touchUpOutside])
เขียนฟังก์ชันของคุณเพื่อจัดการกับจุดสิ้นสุดของการลากแถบเลื่อน
func sliderDidEndSliding() {
print("end sliding")
}
คุณสามารถใช้ได้:
- (void)addTarget:(id)target action:(SEL)action
forControlEvents:(UIControlEvents)controlEvents
เพื่อตรวจจับเมื่อเหตุการณ์ touchDown และ touchUp เกิดขึ้นใน UISlider
UIControlEventTouchUpInside
ผมคิดว่าคุณต้องควบคุมเหตุการณ์
คำตอบ Swift 3
ฉันมีปัญหาเดียวกันและในที่สุดก็ใช้งานได้ดังนั้นมันอาจจะช่วยใครสักคนได้ เชื่อมต่อ your_Slider กับ 'Value Changed' ในสตอรีบอร์ดและเมื่อเลื่อนตัวเลื่อน "Slider Touched" ที่ดำเนินการและเมื่อปล่อย "Slider Released"
@IBAction func your_Slider(_ sender: UISlider) {
if (yourSlider.isTracking) {
print("Slider Touched")
} else {
print("Slider Released")
}
}
บางครั้งคุณอาจต้องการให้เหตุการณ์การลากของตัวเลื่อนเริ่มทำงานอย่างต่อเนื่อง แต่มีตัวเลือกในการเรียกใช้โค้ดที่แตกต่างกันขึ้นอยู่กับว่าแถบเลื่อนยังคงถูกลากอยู่หรือเพิ่งเสร็จสิ้นการลาก
ในการทำเช่นนี้ฉันได้ขยายคำตอบของ Andy ข้างต้นซึ่งใช้ประโยชน์จากisTracking
คุณสมบัติของแถบเลื่อน ฉันต้องการบันทึกสองสถานะ: sliderHasFinishedTracking
และsliderLastStoredValue
.
รหัสของฉันถูกต้อง:
ไม่เริ่มการกระทำเมื่อเริ่มการลาก
เริ่มการทำงานหากผู้ใช้เพียงแค่ขยับตัวเลื่อนด้วยการแตะเพียงครั้งเดียว (หมายความว่าisTracking
ยังคงอยู่false
)
class SliderExample: UIViewController {
var slider: UISlider = UISlider()
var sliderHasFinishedTracking: Bool = true
var sliderLastStoredValue: Float!
override func loadView() {
super.loadView()
slider.minimumValue = 100.0
slider.maximumValue = 200.0
slider.isContinuous = true
slider.value = 100.0
self.sliderLastStoredValue = slider.value
slider.addTarget(self, action: #selector(respondToSlideEvents), for: .valueChanged)
// add your slider to the view however you like
}
func respondToSlideEvents(sender: UISlider) {
let currentValue: Float = Float(sender.value)
print("Event fired. Current value for slider: \(currentValue)%.")
if(slider.isTracking) {
self.sliderHasFinishedTracking = false
print("Action while the slider is being dragged ⏳")
} else {
if(self.sliderHasFinishedTracking && currentValue == self.sliderLastStoredValue){
print("Slider has finished tracking and its value hasn't changed, " +
"yet event was fired anyway. 🤷") // No need to take action.
} else {
self.sliderHasFinishedTracking = true
print("Action upon slider drag/tap finishing ⌛️")
}
}
self.sliderLastStoredValue = currentValue
}
}
ใน Swift 4 คุณสามารถใช้ฟังก์ชันนี้ได้
1 Frist step: - การเพิ่มเป้าหมายในแถบเลื่อน
self.distanceSlider.addTarget(self, action: #selector(self.sliderDidEndSliding(notification:)), for: ([.touchUpInside,.touchUpOutside]))
2 ขั้นตอนที่สอง: - สร้างฟังก์ชัน
@objc func sliderDidEndSliding(notification: NSNotification)
{
print("Hello-->\(distanceSlider.value)")
}
บางทีคุณควรเพิ่มเป้าหมายสำหรับเหตุการณ์ UIControlEventTouchUpInside、 UIControlEventTouchUpOutside、 UIControlEventTouchCancel
ฉันพบปัญหาเดียวกันมาก่อนเพราะฉันไม่ได้เพิ่มเป้าหมายสำหรับเหตุการณ์UIControlEventTouchCancel
ฉันมีปัญหาคล้ายกันเมื่อเร็ว ๆ นี้ นี่คือสิ่งที่ฉันทำใน Swift:
theSlider.continuous = false;
รหัสที่เก็บค่าต่อเนื่องนี้อ่าน:
public var continuous: Bool // if set, value change events are generated
// any time the value changes due to dragging. default = YES
ค่าเริ่มต้นดูเหมือนจะเป็นใช่ (จริง) การตั้งค่าเป็นเท็จจะทำสิ่งที่คุณต้องการ
ลองแบบนี้ดูสิ
customSlider.minimumValue = 0.0;
customSlider.maximumValue = 10.0;
[customSlider addTarget:self action:@selector(changeSlider:) forControlEvents:UIControlEventValueChanged];
-(void)changeSlider:(id)sender{
UISlider *slider=(UISlider *)sender;
float sliderValue=(float)(slider.value );
NSLog(@"sliderValue = %f",sliderValue);
}
RxSwift:
self.slider.rx.controlEvent([.touchUpInside, .touchUpOutside])
.bind(to: self.viewModel.endSlidingSlider)
.disposed(by: self.disposeBag)
สร้างการดำเนินการและทางออกสำหรับแถบเลื่อน (หรือคุณสามารถพิมพ์ผู้ส่งจากการดำเนินการไปยัง UISlider) และใน UI ยกเลิกการเลือกช่องทำเครื่องหมายการอัปเดตอย่างต่อเนื่อง วิธีนี้เราจะได้ค่าตัวเลื่อนก็ต่อเมื่อตัวเลื่อนหยุดลาก
@IBAction func actionSlider(_ sender: Any) {
let value = sliderSpeed.value.rounded()
}