SKStoreReviewController.requestReview() rates don't come to Appstore - request

if UsesCount < 10
{
UsesCount += 1
}
else
{
if UsesCount == 10
{
SKStoreReviewController.requestReview()
UsesCount += 1
}
}
UserDefaults.standard.set(UsesCount, forKey: "UsesCount")
UserDefaults.standard.synchronize()
All work right jpg attacked
but in AppStore and AppStore Connect i don't see this rates in all versions.
What it can be?

Solved. In Appstore showed locale rates and comments. Rate which I want to found is from Russia, i can see it only in AppStore Connect by filter All rates or Russia.

Related

Authenticated Dev User Cannot WRITE/CREATE to CloudKit Public Database in Simulator

I have my device working on both a simulator and on my test iPhone. I want to save a new record to to the Cloudkit database. I can create records on the physical test device, but not in the simulator. When I submitted it for Apple's review they rejected it because of that as well. Both devices are signed into iCloud. This is confirmed right before saving the record with this code:
CKContainer.default().accountStatus { (accountStatus, error) in
switch accountStatus {
case .available:
print("iCloud Available")
case .noAccount:
print("No iCloud account")
case .restricted:
print("iCloud restricted")
case .couldNotDetermine:
print("Unable to determine iCloud status")
}
}
The code I use to make the save is pretty straight forward and it works without any issues on real devices:
static func saveUser(user: UserElement, completion: #escaping (Result<UserElement, Error>) ->
()) {
let itemRecord = CKRecord(recordType: "userInfo")
itemRecord["uniqueID"] = user.bossID as CKRecordValue
itemRecord["screenName"] = user.screenName as CKRecordValue
itemRecord["shareCode"] = user.shareCode as CKRecordValue
itemRecord["subscribedBosses"] = user.subscribedBosses as CKRecordValue
let container = CKContainer(identifier: "iCloud.Caz4Short.WatChaDoin")
container.publicCloudDatabase.save(itemRecord) { (record, err) in
DispatchQueue.main.async {
if let err = err {
print("error on run")
completion(.failure(err))
return
}
guard let record = record else {
print("record")
completion(.failure(CloudKitHelperError.recordFailure))
return
}
let id = record.recordID
guard let boss = record["uniqueID"] as? String else {
print("record ID")
completion(.failure(CloudKitHelperError.recordIDFailure))
return
}
guard let name = record["screenName"] as? String else {
print("screenname")
completion(.failure(CloudKitHelperError.castFailure))
return
}
guard let bossCode = record["shareCode"] as? String else {
print("Code")
completion(.failure(CloudKitHelperError.castFailure))
return
}
guard let subs = record["subscribedBosses"] as? [String] else {
completion(.failure(CloudKitHelperError.castFailure))
return
}
let element = UserElement(recordID: id, bossID: boss, screenName: name, shareCode: bossCode, subscribedBosses: subs)
completion(.success(element))
}
}
}
The code fails at "Error On Run" with the resulting error message
Error saving record <CKRecordID: 0x9t83ecb31790; recordName=8AB667FA-0D8F-4B72-8B90-C694AB960EFF, zoneID=_defaultZone:defaultOwner> to server: CREATE operation not permitted
I get a similar error when I try to modify a record except it says WRITE instead of CREATE. I am able to read records without a problem though. This made me think I forgot to set the Security Roles for that zone, but that is not the case. Authenticated users & have READ, CREATE, and WRITE selected for all zones. Creator also has READ and WRITE. I've also signed into iCloud on a computer and accepted the terms and conditions for the iCloud account a long time ago so its not like its a new account that needs to be setup. Any ideas would be greatly appreciated so it doesn't get rejected again!

Split string in uilabel multiple lines swift

I want to split my dynamic UILabel text like given below e.g
UILabel text -
Aptitude tests English skills relevant to your requirements. It enables an organisation / institution to assess all four English skills – reading, writing, listening and speaking together with the core mandatory component (grammar and vocabulary) or test just one skill, e.g. reading.
to split into array of string with every line break even with every dimension of screen size whether iphone or ipad .
The result i want is array of strings -
["Aptitude tests English skills relevant to your requirements. It enables an organisation / institution","to assess all four English skills – reading, writing, listening and speaking together with the core ","mandatory component (grammar and vocabulary) or test just one skill, e.g. reading."]
With every line break in UILabel i need to split the string regardless to the dynamic screen size
Your approach can be hard, instead i recommend you to use other methods like using of sizeWithAttributes
extension String {
func widthOfString(usingFont font: UIFont) -> CGFloat {
let fontAttributes = [NSAttributedString.Key.font: font]
let size = self.size(withAttributes: fontAttributes)
return size.width
}
func heightOfString(usingFont font: UIFont) -> CGFloat {
let fontAttributes = [NSAttributedString.Key.font: font]
let size = self.size(withAttributes: fontAttributes)
return size.height
}
func sizeOfString(usingFont font: UIFont) -> CGSize {
let fontAttributes = [NSAttributedString.Key.font: font]
return self.size(withAttributes: fontAttributes)
}
}
Assuming you know the width and your font-size in your label, you could use some logics like below:
let inputText = "Aptitude tests English skills relevant to your requirements. It enables an organisation / institution to assess all four English skills – reading, writing, listening and speaking together with the core mandatory component (grammar and vocabulary) or test just one skill, e.g. reading."
let labelWidth = UIScreen.main.bounds.width
var resultArray:[String] = []
var readerString = ""
for i in 0 ..< inputText.count
{
readerString += inputText[i]
//Check if overflowing boundries and wrapping for new line
if readerString.widthOfString(usingFont: UIFont.systemFont(ofSize: 14)) >= labelWidth {
resultArray.append(readerString)
readerString = ""
}
}

Google Sheets custom function displays "Loading..." forever in mobile app

I have written a custom function for Google Sheets in Apps Script. The goal is to have a sheet which automatically calculates who owes how much money to whom (e.g. to split a bill).
My sheet looks like this:
The first bill (Restaurant) is to be split among all 5 and the second bill is to be split among all 5 except Peter, because there is no 0 in B3.
The input for my Apps Script function will be cells B1 to F3 (thus, values AND names). The function works fine - it calculates the correct results. I open that spreadsheet via browser (sheets.google.com) AND via my phone app (Google Sheets). However, on my phone it often happens that the result cell (with the formula =calc_debt(B1:F3)) only displays "Loading ...". What's the problem?
For the sake of completeness, here is custom function's code:
function calc_debt(input) {
var credit = [0, 0, 0, 0, 0]; // credit[0] = Peter, credit[1] = Mark ...
for (var i = 1; i < input.length; i++) { // starting at i = 1 to skip the first row, which is the names!
// first: calculate how much everybody has to pay
var sum = 0;
var people = 0;
for (var j = 0; j <= 4; j++) {
if (input[i][j] !== "") {
sum += input[i][j];
people += 1;
}
}
var avg_payment = sum / people;
// second: calculate who has payed too much or too little
for (var j = 0; j <= 4; j++) {
if (input[i][j] !== "") {
credit[j] += input[i][j] - avg_payment;
}
}
}
// this function is needed later
function test_zero (value) {
return value < 0.00001;
};
var res = ""; // this variable will contain the result string, something like "Peter to Mark: 13,8 | Katy to ..."
while (!credit.every(test_zero)) {
var lowest = credit.indexOf(Math.min.apply(null, credit)); // find the person with the lowest credit balance (will be minus!)
var highest = credit.indexOf(Math.max.apply(null, credit)); // find the person with the highest credit balance (will be plus!)
var exchange = Math.min(Math.abs(credit[lowest]), Math.abs(credit[highest])); // find out by how much we can equalize these two against each other
credit[lowest] += exchange;
credit[highest] -= exchange;
res += input[0][lowest] + " to " + input[0][highest] + ": " + exchange.toFixed(2) + " | "; // input[0] = the row with the names.
}
return res;
}
I'm having a similar issue in the android app that loading a custom formula sometimes just shows 'Loading...', while in the web it always works fine. I've found a workaround to load the formulas in the android app:
Menu - > Export - > Save as - > PDF.
This will take a moment and behind the modal loading indicator you will see that the formulars eventually resolve. You can wait for the export to finish or cancel it as soon as you see your formular was resolved.
Also making the document available offline via the menu toggle could resolve the formulars.
Another thing you could do is using caching in your script. So whenever you use the web version to render more complex formulars the results are being stored and immediately loaded for the mobile app. Unfortunately, the Google cache is limited in time and does invalidate after a few hours. See here for more information:
https://developers.google.com/apps-script/reference/cache/
This two things work quite well. However, I'm searching for a better solution. Let me know if you find one.
Solved follow the solution provided here ..
Menu - > Export - > Save as - > PDF
This forces the script to run on mobile and be readable by the mobile sheet

How to change the speed of AVPlayerViewController?

Below is an factory method to setup an AVPlayerViewController.
Everything except the speed control works fine.
In an older version of this app I was able to go from half speed to double speed by simply setting the player.rate.
Double doesn't work anymore but half speed does and I'm not sure why.
The docs say that canPlayFastForward and canPlaySlowForward need to be true however i don't see a way to set them to true.
extension AVPlayerViewController {
static func create(url: URL, rate: Float, time: CMTime, delegate: AVPlayerViewControllerDelegate?) -> AVPlayerViewController {
let avPlayerVC = AVPlayerViewController()
avPlayerVC.delegate = delegate
let playerItem = AVPlayerItem(url: url)
// playerItem.canPlayFastForward = true
// playerItem.canPlaySlowForward = true
let player = AVPlayer(playerItem: playerItem)
player.rate = rate
player.seek(to: time)
avPlayerVC.player = player
return avPlayerVC
}
}
So what seems to be the solution is that one cannot set the rate of the AVPlayer to 2 but one can set it to 1.99.

Faces detected on simulator but not on iphone using CoreImage framework

I'm using CoreImage to detect faces on pictures. It works great on the simulator, but on my iphone 5, it almost never works with pictures taken with the iphone's camera ( it works with pictures picked on the web ).
The following code shows how I detect the faces. For every pictures, the application logs
step 1 : image will be processed
But it only logs
step 2 : face detected
for few of them, whereas almost every faces are detected on the simulator or if I use pictures from the web.
var context: CIContext = {
return CIContext(options: nil)
}()
let detector = CIDetector(ofType: CIDetectorTypeFace,
context: context,
options: [CIDetectorAccuracy: CIDetectorAccuracyHigh])
let imageView = mainPic
for var index = 0; index < picsArray.count; index++ {
if !(picsArray.objectAtIndex(index).objectAtIndex(1) as! Bool) {
var wholeImageData: AnyObject = picsArray.objectAtIndex(index)[0]
if wholeImageData.isKindOfClass(NSData) {
let wholeImage: UIImage = UIImage(data: wholeImageData as! NSData)!
if wholeImage.isKindOfClass(UIImage) {
NSLog("step 1 : image will be processed")
let processedImage = wholeImage
let inputImage = CIImage(image: processedImage)
var faceFeatures: [CIFaceFeature]!
if let orientation: AnyObject = inputImage.properties()?[kCGImagePropertyOrientation] {
faceFeatures = detector.featuresInImage(inputImage, options: [CIDetectorImageOrientation: orientation]) as! [CIFaceFeature]
} else {
faceFeatures = detector.featuresInImage(inputImage) as! [CIFaceFeature]
}
let inputImageSize = inputImage.extent().size
var transform = CGAffineTransformIdentity
transform = CGAffineTransformScale(transform, 1, -1)
transform = CGAffineTransformTranslate(transform, 0, -inputImageSize.height)
for faceFeature in faceFeatures {
NSLog("step 2 : face detected")
// ...
I've been looking for a solution for three hours now, and I'm quite desperate :).
Any suggestion would be really appreciated !
Thanks in advance.
I found a really weird way to solve my problem.
By setting the allowsEditing property of UIImagePickerController() to true when picking my pictures, everything works fine... I can't understand why, but it works.

Resources