首页 > 解决方案 > 在 Swift 中使用 Google Place Photos 请求显示图像

问题描述

我正在尝试使用 Google Places API 提供的“photo_reference”显示特定位置的照片。

目前,我正在使用 Google Places API 的“ Place Details ”请求来获取有关特定位置的信息,但无法显示这些位置的照片。Google 在“Place Details”响应中提供了一个“photo_reference”,该响应应该用于获取特定图像,但此处的文档在展示如何操作方面并不是很有帮助。

我目前正在发出这样的 Google Place Details 请求:(我有一个创建 url 的函数,然后是一个发出请求的函数)

    func googlePlacesDetailsURL(forKey apiKey: String, place_ID: String) -> URL {
        print("passed  place_ID  before url creation ", place_ID)

        let baseURL = "https://maps.googleapis.com/maps/api/place/details/json?"
        let place_idString = "place_id=" + place_ID
        let fields = "fields=geometry,name,rating,price_level,types,opening_hours,formatted_address,formatted_phone_number,website,photos"
        let key = "key=" + apiKey

        print("Details request URL:", URL(string: baseURL + place_idString + "&" + fields + "&" + key)!)
        return URL(string: baseURL + place_idString + "&" + fields + "&" + key)!
    }


    func getGooglePlacesDetailsData(place_id: String, using completionHandler: @escaping (GooglePlacesDetailsResponse) -> ())  {

        let url = googlePlacesDetailsURL(forKey: googlePlacesKey, place_ID: place_id)

        let task = session.dataTask(with: url) { (responseData, _, error) in
            if let error = error {
                print(error.localizedDescription)
                return
            }

            guard let data = responseData, let detailsResponse = try? JSONDecoder().decode(GooglePlacesDetailsResponse.self, from: data) else {
                print("Could not decode JSON response. responseData was: ", responseData)
                return
            }
            print("GPD response - detailsResponse.result: ", detailsResponse.result)

                completionHandler(detailsResponse)

        }
        task.resume()

    }

有谁知道如何在 Swift 中使用“photo_reference”发出 Google Place Photo 请求,并显示返回的照片?

标签: iosswiftuiphotogoogle-placesgoogle-photos-api

解决方案


我知道我很晚才给出这个答案,对不起,我真的很忙,但我设法为你完成了,这只是我的看法,我对 IOS 还是新手,所以虽然我的设计可能不是完美,我向您保证它可以工作。要记住的一件事是,并非每个地方都有 photo_reference,因此您必须错误处理,以防图像被赋值为 nil 值或在创建 URl 时它会抛出一个例外,看看下面的代码,我把它全部放在一个方法中,但如果你能把它分成几个方法来设置图像和获取数据,那就太好了。把你的反馈给我,因为我也喜欢学习这个,谢谢你,祝你好运。

PS:这是在目标 C 中,所以你需要做一些工作,抱歉,我不够快,无法在其中生成它

-(void)fetchedData:(NSData *)responseData {
    //parse out the json data
    NSError* error;
    NSDictionary* json = [NSJSONSerialization
                          JSONObjectWithData:responseData

                          options:kNilOptions
                          error:&error];

    //Hardcoded placeId for testing purposes
    NSString *placeId = @"ChIJoS8a5GWM4kcRKOs9fcRijdk";

    //Filtered the json to access all the location Ids/place Ids
    NSArray *locations = [json valueForKeyPath:@"results.place_id"];

    //Iterator to iterate through the locations to see if the required place id is present in the Dictionary

    for (NSString *locationId in locations) {

        if ([placeId isEqualToString:locationId]){

            NSLog(@"Found The Matching LocationID");

            //predicate to iterate through all the places ids that match in order to access the entire object that has the location id so you can use it later onwards to access any part of the object (ratings, prices.... )
            NSPredicate *objectWithPlacesId = [NSPredicate predicateWithFormat:@"place_id == %@",locationId];

            //This array holds the entire object that contains the required place id
            NSArray *filteredArrayWithPlacesDetails = [[json objectForKey:@"results"] filteredArrayUsingPredicate:objectWithPlacesId];

            //Small question here if this is actually needed but i found it a problem to access the array as it returns a single object array
            NSDictionary *dictionaryWithDetails = [filteredArrayWithPlacesDetails firstObject];

            NSArray *photosArray = [dictionaryWithDetails valueForKeyPath:@"photos.photo_reference"];
            //NSString photo refence is accessed here , single object array so the first index always contain the photoReference
            NSString *photo_Reference = [photosArray objectAtIndex:0];

            //Create the Image Url , you can even format the max width and height the same way using %f
            NSString *imageUrl = [NSString stringWithFormat:@"https://maps.googleapis.com/maps/api/place/photo?maxwidth=400&photoreference=%@&key=%@",photo_Reference,kGOOGLE_API_KEY];

            //Assing the image request for the sd_setImageWithURL to access the remote image
            [self.imageView sd_setImageWithURL:[NSURL URLWithString:imageUrl]
                              placeholderImage:[UIImage imageNamed:@"placeholder.png"]];

            break;
        }

        else{
            NSLog(@"Not Matching");
        }



    }

}

推荐阅读