I have an image slider where multiple images are added to a scrollview. Each is stored in an array of my custom data type (named Slide). I cycle through them like this:
for (index, slide) in slides.enumerated() {
let imageView = UIImageView()
imageView.image = UIImage(named: slide.image) //set the imageView with the imageName in this slide
imageView.contentMode = .scaleAspectFit
let xPos = self.view.frame.width * CGFloat(index) //calculate x depending upon slide index
imageView.frame = CGRect(x: xPos, y: -200, width: self.SVSlider.frame.width, height: self.SVSlider.frame.height)
SVSlider.contentSize.width = SVSlider.frame.width * CGFloat(index + 1) //add slide image to scrollview
SVSlider.addSubview(imageView)
//add tap function to slide
imageView.isUserInteractionEnabled = true
imageView.tag = index
let tapImage = UITapGestureRecognizer(target: self, action: #selector(slideAction(_:)))
imageView.addGestureRecognizer(tapImage)
}
Each slide image is attached to the method "slideAction", below:
#objc func slideAction(_ sender: UITapGestureRecognizer) {
let selName = slides[(sender.view?.tag)!].target
NSObject.perform(Selector(selName))
}
But the application throws an error when I click an image. By debugging I can see that the "tag" is correctly set to the slide index number. I want to perform the target action held in the slide object. (Currently the target is a String of the method name - ending with ':').
How can I get the "slideAction" to goto the method in the slide object?
Try this ,create target method in the custom class callMethodDirectly and call it
#objc func slideAction(_ sender: UITapGestureRecognizer) {
let selName = slides[(sender.view?.tag)!]
selName.callMethodDirectly()
}
class slide:NSObjcet
{
func callMethodDirectly()
{
// implement target code here
}
}
Related
I'm still new with Swift 4 and i found this on the internet & tried to make this Button to show "something" when the image button is A. But when i clicked the Button again, only its image button changed but the "something" still not hidden. Can someone help ?
I already done with other button that using this animation but the button is showing another button from Library.
But this 1 is different, not showing another button from Library but showing ChromaColorPicker
var sizeOff = UIImage(named: "Brush-Size")
var sizeOn = UIImage(named: "Brush-Size-On")
============================ somewhere else ======================
extension ViewController {
#IBAction func BrushColourClicked(_ sender: UIButton) {
if sender.currentImage == ColourOn {
sender.setImage(ColourOff, for: .normal)
} else {
sender.setImage(ColourOn, for: .normal)
} // Image first set
configureUI()
}
func configureUI() {
let colorPicker = ChromaColorPicker(frame: CGRect(x: 25.0, y: 410.0, width: 140.0, height: 140.0)) // Position & Size of Color Picker
ColourButtonCenter = colorPicker.center
colorPicker.center = BrushColour.center
colorPicker.delegate = self
colorPicker.padding = 5.0
colorPicker.stroke = 3.0
colorPicker.hexLabel.isHidden = true
colorPicker.layout()
view.addSubview(colorPicker)
colorPicker.alpha = 0
if BrushColour.currentImage == ColourOn {
UIView.animate(withDuration: 0.35, animations: {
colorPicker.alpha = 1
colorPicker.center = self.ColourButtonCenter
})
} // Animation show
else {
UIView.animate(withDuration: 0.35, animations: {
colorPicker.alpha = 0
colorPicker.center = self.BrushColour.center
})
} // Animation hide
}
}
i dont know if
colorPicker.alpha = 0
is working or not
Every time you call configureUI you're adding a new colour picker to the view, then animating the alpha on it.
So when you're trying to hide the colorPicker what's actually happening is that you're adding a new colour picker with alpha 0 and animating it to alpha 0 (doing nothing), the previous colorPicker will still be visible so it will look as though nothing as changed.
Create a variable for colorPicker once and add it to the view, then configure that instance in your configureUI function.
I added a label and an image to the navigation item title view, like this - https://stackoverflow.com/a/38548905/1373592
And I added these three lines of code, to make the title clickable.
....
let recognizer = UITapGestureRecognizer(target: self, action: #selector(MyViewController.titleTapped(_:)))
navView.isUserInteractionEnabled = true
navView.addGestureRecognizer(recognizer)
And this titleTapped function.
#objc func titleTapped(_ tapGestureRecognizer: UITapGestureRecognizer) {
print("Tapped")
}
What am I doing wrong?
I tried adding gesture recognizer to the label, and to the image (separately). That didn't work either.
Thanks.
Your NavView has no frame, so there is nothing "there" to tap.
Add this line:
// Create a navView to add to the navigation bar
let navView = UIView()
// new line
navView.frame = CGRect(x: 0, y: 0, width: 200, height: 40)
// Create the label
let label = UILabel()
and you should be on your way.
100% sure working in my app and well tested.
var tapGesture = UITapGestureRecognizer()
take your view and set IBOutlet like:
#IBOutlet weak var viewTap: UIView!
Write pretty code on viewDidLoad() like:
tapGesture = UITapGestureRecognizer(target: self, action: #selector(self.myviewTapped(_:)))
tapGesture.numberOfTapsRequired = 1
tapGesture.numberOfTouchesRequired = 1
viewTap.addGestureRecognizer(tapGesture)
viewTap.isUserInteractionEnabled = true
this method is calling when tap gesture recognized
#objc func myviewTapped(_ sender: UITapGestureRecognizer) {
if self.viewTap.backgroundColor == UIColor.yellow {
self.viewTap.backgroundColor = UIColor.green
}else{
self.viewTap.backgroundColor = UIColor.yellow
}
}
Note: In your case you have to sure for view which view infront like UILabel or UIView that is nav and then assign the gesture to it.If your label cover the whole view then let's try to give gesture to label only.
Swift 3 / Xcode 8.3.3
When I click on the screen, an image appears (code 1) at the place of the click (if I click 5 times, 5 images appear) and each image has a tag. Now I would like to delete the images one by one at each click on a button (code 2) but only the last image is deleted...
I did a lot of research but none of the results worked for me.
code 1:
var imageView : UIImageView!
var lstTagImage: [Int] = []
var concatenateInt: String = ""
var lstPoint: [Point] = []
concatenateInt = "\(Int(i))\(Int(j))"
lstPoint.append(Point(x: i, y: j, weigth: weigthChip))
imageView = UIImageView(frame:CGRect(x: X,
y: Y,
width: 20, height: 20));
imageView.tag = Int(concatenateInt)!
lstTagImage.append(Int(concatenateInt)!)
imageView.image = UIImage(named: imageString)
self.view.addSubview(imageView)
code 2:
#IBAction func undoButton(_ sender: UIButton) {
if (lstPoint.count != 0){
lstPoint.remove(at: lstPoint.count - 1)
imageView.removeFromSuperview()
} else {
print("list empty")
}
}
An alternate, more elegant approach would be something like this:
let addedImages = [UIImageView]()
// When adding an image to the view
addedImages.append(imageView)
self.view.addSubview(imageView)
Then it's easy to delete.
// When deleting image from view
if let imageView = addedImages.last {
imageView.removeFromSuperview()
addedImages.removeLast()
}
You should use viewWithTag to retreive the last tag, remove that tag from the array and remove the image from its superview.
if lstPoint.count != 0,
let lastTag = lstTagImage.last {
lstPoint.remove(at: lstPoint.count - 1)
lstTagImage.removeLast()
let imageView = view.viewWithTag(lastTag)
imageView.removeFromSuperview()
}
I currently have an image set into my UIImageView the following way:
art_image.image = UIImage(named:(artworkPin.title!))
where art_image is the image View and artworkPin.title refers to the name of the image. However, I want to add a second image to the UIImageView if it exists I thought of programming it as
art_image.image = UIImage(named:(artworkPin.title + "1")?)
would this work? In this case I would name a second image the name of the first image but with a '1' on the end. Example: 'Photo.jpeg' and 'Photo1.jpeg' would both be in the image view if Photo1.jpeg existed.
Thanks for your help.
I came across a similar task myself once. What I did was, I created a UIScrollView with the frame of the UIImageView and its contentSize would be imageView.frame.size.width * numberOfImages.
let scrollView = UIScrollView(frame: view.bounds)
view.addSubview(scrollView)
scrollView.contentSize = CGSize(width: scrollView.bounds.size.width * CGFloat(numberOfImages), height: scrollView.bounds.size.height))
for i in 0...<numberOfImages.count-1 {
let imageView = UIImageView(frame: CGRect(x: scrollView.bounds.size.width * CGFloat(i), y: scrollView.bounds.origin.y, width: scrollView.bounds.size.width, height: scrollView.bounds.size.height))
imageView.image = UIImage(named: "artwork" + "\(i)")
scrollView.addSubview(imageView)
}
You can animate it to scroll with a Timer if you want.
scrollView.setContentOffset(scrollPoint, animated: true)
you can only show 1 image inside the imageivew at a time, so if you have the lines as follows:
art_image.image = UIImage(named:(artworkPin.title!))
art_image.image = UIImage(named:(artworkPin.title! + "1")?)
art_image would consist only of Photo1 provided such an image exists and that the artworkPin.title unwrapped is also not nil otherwise you could see some different results.
if you do want to add multiple images to an image view for the purpose of animation, you need to use the animationImages property of UIImageView which takes an array of UIImages for example
art_image.animationImages = [UIImage.init(named:"Photo")!,
UIImage.init(named:"Photo1")!]
Hope this helps
EDIT
var imagesListArray = [UIImage]()
for position in 1...5
{
if let image = UIImage.init(named: ("Photo\(position)"))
{
imagesListArray.append(image)
}
}
art_image.animationImages = imagesListArray
art_image.animationDuration = 3.0
art_image.startAnimating()
This would be a safer a way to add the images so it will ONLY add an image if it is not nil and adds Photo1, Photo2 ..... Photo5
With regards to your other questions:
If you want the user to be able to
What do you mean by animation?
I have added two more lines of code, and it gives this result:
art_image.animationDuration = 1.0
art_image.startAnimating()
It will give you something like this:
If you want the user to swipe, then you need to make some changes such as:
using a scrollview, collectionview for example is the easiest or using a gesture recognizer on swipe you need to change the image
EDIT
Have a look at this example. Imagine each button is your annotation so when I tap it, the image changes.
I have 3 images named Photo11.png, Photo21.png and Photo31.png and this is my code inside the button handler
#IBAction func buttonTapped(_ sender: UIButton)
{
if let image = UIImage.init(named: sender.currentTitle!+"1")
{
art_image.image = image
}
}
As you can see I am setting the image with the title of my button + "1" as so it displays either Photo11.png or Photo21.png etc
All,
I have an image and then I display it on the screen and then I go to a function to blur the image. Then I run another function to add a box to it. but it doesn't show the blur and the box and this is because of the addSubView and the insertSubView - I presume. Basically I cannot put both the blur and the box on the view. If i uncomment out the addBox it doesn't show the blur. Can anyone help with my understanding of addSubView and InsertSubView (array).
Here is my code :
class ViewController: UIViewController {
var Box : UIView?
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
let bananaImage : UIImage = UIImage(named: "edify-backgound.png")
var imageV : UIImageView = UIImageView(image: bananaImage)
imageV.frame = CGRectMake(0, 0, bananaImage.size.width, bananaImage.size.height)
imageV.center = self.view.center
self.view.addSubview(imageV)
blur()
//addBox(CGRectMake(200, 300, 30, 30))
}
func addBox(location: CGRect)
{
let newBox = UIView(frame: location)
newBox.backgroundColor = UIColor.clearColor()
self.view.insertSubview(newBox, atIndex: 1)
Box = newBox
}
func blur()
{
var blur = UIVisualEffectView(effect: UIBlurEffect(style: .Light)) as UIVisualEffectView
blur.frame = self.view.frame
self.view.addSubview(blur)
}
Part of the problem is that you have no way of knowing whether addBox is doing anything or not. Here is your code:
let newBox = UIView(frame: location)
newBox.backgroundColor = UIColor.clearColor()
self.view.insertSubview(newBox, atIndex: 1)
A view that consists of nothing but a clear background color is completely invisible. So you see nothing - which, as Sherlock Holmes says, is exactly what you may expect to see.