Accessing For in Loop Collection View Swift - swift

I have this array that I created: let yourShares = ["90%","40%", "23%","15%","10%"] Then to acess this:
for yourShare in yourShares {
dataSource[0].yourShareTitle = "90%"
dataSource[1].yourShareTitle = "40%"
dataSource[2].yourShareTitle = "23%"
dataSource[3].yourShareTitle = "10%"
}
Then to access this I put this code in an extension for collection view
let yourShare = model.dataSource?[indexPath.row]
cell.yourShareLabel.text = "Your Share \(yourShare!.yourShareTitle)"
cell.titleLabel?.font = UIFont.systemFont(ofSize: 1)
The problem is when I run this it just prints optional. Why, and how could I fix that? ~ Thanks

You need to unwrap it
if let yourShare = model.dataSource?[indexPath.row]?.yourShareTitle as? String {
cell.yourShareLabel.text = "Your Share \(yourShare)"
cell.titleLabel?.font = UIFont.systemFont(ofSize: 1)
}

Related

total of label click on two buttons

I have two UIButton if I click onto button1 the value of label1 is 250, if I click again onto button1 the value of label1 should be 0. The same logic is applied to my button2 and label2. I want to store the addition of label1 and label2 into label3. . My code is:
func PickUpCarCost() {
if (!isclick){
imgCheck.image = UIImage(named: "check.png")
isclick=true
//Pickup fare conver into integer
let PickUp = String(self.PickUpPrice)
PickUpFare.text = PickUp
self.pickCost = Int( PickUpFare.text!)
self.PAyAmount = ((self.PayFareWithSecurity)+(self.pickCost))
print("PaybleAmount: \(self.PAyAmount)")
self.AmountPay1 = ((self.PAyAmount)+(self.DeliverCost))
PaybleAmount.text=String(self.AmountPay1!)
}
else
{
imgCheck.image = UIImage(named: "uncheck.png")
PickUpFare.text = "0"
self.PickUpElse=Int(PickUpFare.text!)
print("PickUpElse: \(self.PickUpElse)")
self.PAyAmount = (self.PayFareWithSecurity)+(self.PickUpElse)
PaybleAmount.text=String(self.PAyAmount!)
isclick=false
}
}
func CarDeliverCost() {
if (!isclick){
imgUnCheck.image = UIImage(named: "check.png")
isclick=true
let DeliverPrice = String(self.deliveryPrice)
DeliverFare.text = DeliverPrice
self.DeliverCost = Int(DeliverFare.text!)
self.PAyAmount = ((self.PayFareWithSecurity)+(self.DeliverCost))
print("PaybleAmount: \(self.PAyAmount)")
PaybleAmount.text=String(self.PAyAmount!)
}
else
{
imgUnCheck.image = UIImage(named: "uncheck.png")
let deliveryelse = String(0)
DeliverFare.text = deliveryelse
self.deliver = Int(DeliverFare.text!)
PaybleAmount.text=String(self.PAyAmount!)
isclick=false
}
}
The first issue that you're facing is that you are using the same boolean isClick for two different scenarios. Your logic is that the user could decide to click onto both buttons or a single one. So if I click onto the first button then your flag is turn on, since the second button also uses the same boolean then you'll get that uncheck behavior automatically.
Thus you should use two different booleans such as hasPressOntoFirstButton and hasPressOntoSecondButton, where both set to false at the beginning, and each variable is used in their respective scene.
You mentioned that you want to add the label1 to label2, the easier way would be add the variable that set these labels. i.e
let label1 = UILabel()
let label2 = UILabel()
let label3 = UILabel()
let data1: Double = 83.0
let data2: Double = 82.0
var total: Double { // have a computed variable to adds automatically
return data1 + data2
}
label1.text = "\(data1)"
label2.text = "\(data2)"
label3.text = "\(data1 + data2)" // or "\(total)"
Remarks:
(1) your naming convention are really misleading, you should separate UI object naming from data. i.e you can have deliveryFareLabel.text instead of DeliverFare.text
(2) avoid using !, unwrapped all optional using either nil coalescing ??, or if let or guard statements

Display ETA and estimated money option for my "Ride there with Uber" button

I have integrated a "Ride there with Uber" button to my app. I feel, it would be more convenient for the users, if i displayed the ETA and estimated pricing for the destination. How may I achieve this? I am following this guide as of now : https://github.com/uber/rides-ios-sdk
It seems like I need, some kind of product ID to be able to achieve this. But how do i get it?
Made some progress, I got my self the product id, but it still doesn't work. Here is my current code:
Button will Deeplink into the Uber App and will simply open up the app. In order to see real-time fare estimates and pickup ETA information you will need to pass additional parameters to it. The Ride Request Button can accept optional parameters to pre-load some information into the ride request. You can see how to do it in the Uber documentation. Also this is explained here on the GitHub.
I got the solution ||
ViewController.swift
var button = RideRequestButton()
override func viewDidLoad() {
super.viewDidLoad()
// Do any additional setup after loading the view, typically from a nib.
let builder = RideParametersBuilder()
let pickupLocation = CLLocation(latitude: 37.787654, longitude: -122.402760)
let dropoffLocation = CLLocation(latitude: 37.775200, longitude: -122.417587)
builder.pickupLocation = pickupLocation
builder.dropoffLocation = dropoffLocation
builder.dropoffNickname = "Somewhere"
builder.dropoffAddress = "123 Fake St."
var productID = ""
let ridesClient = RidesClient()
ridesClient.fetchProducts(pickupLocation: pickupLocation) { (product, response) in
productID = product[1].productID!
builder.productID = productID
}
ridesClient.fetchPriceEstimates(pickupLocation: pickupLocation, dropoffLocation: dropoffLocation) { (price, response) in
print(price[0].estimate!)
self.button.rideParameters = builder.build()
self.button.loadRideInformation()
}
button.center = self.view.center
self.view.addSubview(button)
}
Also, do make little change into UberRides->RideRequestButton.swift`
override public func setContent() {
super.setContent()
uberMetadataLabel.numberOfLines = 0
uberMetadataLabel.sizeToFit()`
and
private func setMultilineAttributedString(title: String, subtitle: String = "", surge: Bool = false) {
let metadataFont = UIFont(name: "HelveticaNeue-Regular", size: 10) ?? UIFont.systemFont(ofSize: 10)
and last one change width (+30) of uberMetadataLabel below like
override public func sizeThatFits(_ size: CGSize) -> CGSize
var width: CGFloat = 4*horizontalEdgePadding + imageLabelPadding + logoSize.width + titleSize.width+30
If any query please comment here
The issue is kind of funny and I think uber should change there documentation. You need to fetch products and price estimates and then loadRideInformation(). Guess what! the default button width is smaller than required. (Don't forget to add both the ClientID and ServerToken)
let pickupLocation = CLLocation(latitude:23.782221 , longitude:90.395263 )
let dropoffLocation = CLLocation(latitude: 23.8116404, longitude: 90.4279034)
let uberClient = RidesClient()
let builder = RideParametersBuilder()
let uberReqButton = RideRequestButton()
uberReqButton.frame = CGRect(x: 0, y: 0, width: self.view.frame.width, height: uberReqButton.frame.height)
self.uberview.addSubview(uberReqButton)
SKActivityIndicator.show()
uberClient.fetchProducts(pickupLocation: pickupLocation, completion: { (Products, _) in
if (Products[0].productID != nil){
uberClient.fetchPriceEstimates(pickupLocation: pickupLocation, dropoffLocation: dropoffLocation) { (priceEstimates, Response) in
SKActivityIndicator.dismiss()// used for loading animation, ignore if not not needed
builder.pickupLocation = pickupLocation
builder.pickupAddress = "pickup Address"
builder.pickupNickname = "pickup nick"
builder.dropoffLocation = dropoffLocation
builder.dropoffAddress = "drop Address"
builder.dropoffNickname = "drop nick"
builder.productID = Products[0].productID
uberReqButton.rideParameters = builder.build()
DispatchQueue.main.async {
uberReqButton.loadRideInformation()
}
}
}
})

Quickest way to check multiple bools and changing image depending on that bool

I have multiple achievements that the user can achieve during the game. When the user goes to the achievement VC, he should see an image when the achievement is accomplished.
I am now using this code in the viewDidLoad function:
if unlockedAchievement1 == true
{
achievement1Text.textColor = UIColor.greenColor()
achievement1Image.image = UIImage(named: "achievement1Unlocked")
}
if unlockedAchievement2 == true
{
achievement2Text.textColor = UIColor.greenColor()
achievement2Image.image = UIImage(named: "achievement2Unlocked")
}
This would work, but it takes a lot of time to copy paste this overtime. How can I shorten this? Should I make a class? I read about for in loops, but I did not quite understood that. Any help is welcome!
I feel like I have seen this before. But anyway...
//use array of bools. First declare as empty array.
//Use Core data to achieve saving the Booleans if you need to.
let achievements:[Bool] = []
let achievementsImage:[UIImage] = []
let achievementsText:[UITextView] = []
func viewDidLoad() {
//Say you have 5 achievements.
for index in 0 ..< 5 {
achievements.append(false)
achievementsImage.append(UIImage(named: "achievementLocked"))
achievementText.append(UITextView())
//Then you can edit it, such as.
achievementText[index].frame = CGRect(0, 0, 100, 100)
achievementText[index].text = "AwesomeSauce"
self.view.addSubview(achievementText[index])
achievementText[index].textColor = UIColor.blackColor()
}
}
//Call this function and it will run through your achievements and determine what needs to be changed
func someFunction() {
for index in 0 ..< achievements.count {
if(achievements[index]) {
achievements[index] = true
achievementsImage[index] = UIImage(named: String(format: "achievement%iUnlocked", index))
achievementsText[index].textColor = UIColor.greenColor
}
}
}
I'd recommend making your unlockedAchievement1, unlockedAchievement2, etc. objects tuples, with the first value being the original Bool, and the second value being the image name. You'd use this code:
// First create your data array
var achievements = [(Bool, String)]()
// Then you can make your achievements.
// Initially, they're all unearned, so the Bool is false.
let achievement1 = (false, "achievement1UnlockedImageName")
achievements.append(achievement1)
let achievement2 = (false, "achievement2UnlockedImageName")
achievements.append(achievement2)
// Now that you have your finished data array, you can use a simple for-loop to iterate.
// Create a new array to hold the images you'll want to show.
var imagesToShow = [String]()
for achievement in achievements {
if achievement.0 == true {
imagesToShow.append(achievement.1)
}
}

Getting current value and start observing on MutableProperty

I have MutableProperty. When I create new object I want to get current value of MutableProperty and start observing.
Such as:
let mutableProperty = MutableProperty<Driver?>(Driver(id: 1, name: "John"))
let label = UILabel()
label.text = mutableProperty.value?.name
mutableProperty.signal.observeNext{driver in
label.text = driver?.name
}
Is it possible write it better ?
If you want to use the value immediately:
let mutableProperty = MutableProperty<Driver?>(Driver(id: 1, name: "John"))
let label = UILabel()
mutableProperty.producer.startWithNext{ driver in
label.text = driver?.name
}

Xcode 6 Swift: error "Gamescene does not have a member named 'spawnBlocks'"

Ok so I'm working in Swift and I initialized spawnBlocksas a function and yet I am getting the error:"Gamescene does not have a member named 'spawnBlocks'"
I looked at some other questions on SO but they don't seem to address this specific issue.I'm not sure how else to write this. The code:
let spawn = SKAction.runBlock({() in self.spawnBlocks()}) //Error occurs on this line
let delay = SKAction.waitForDuration(NSTimeInterval(2))
let spawnThenDelay = SKAction.sequence([spawn, delay])
let spawnThenDelayForever = SKAction.repeatActionForever(spawnThenDelay)
self.runAction(spawnThenDelayForever)
func spawnBlocks() {
let blockPair = SKNode()
blockPair.position = CGPointMake(self.frame.size.width + block1Texture.size().width * 2, 0) //change to height
blockPair.zPosition = -10 //zposition = in front of or in back of, other objects are at 0
}
}