Welcome to the Treehouse Community

Want to collaborate on code errors? Have bugs you need feedback on? Looking for an extra set of eyes on your latest project? Get support with fellow developers, designers, and programmers of all backgrounds and skill levels here with the Treehouse Community! While you're at it, check out some resources Treehouse students have shared here.

Looking to learn something new?

Treehouse offers a seven day free trial for new students. Get access to thousands of hours of content and join thousands of Treehouse students and alumni in the community today.

Start your free trial

iOS

Ribbit + Keyword

I would love to be able to search the users with keywords. Did anyone try that or have the know how?

6 Answers

Stone Preston
Stone Preston
42,016 Points

Nicolaus Nsarray make sure you set your search bar to have a cancel button in storyboard. just select the bar then in the attributes inspector check the cancel button box. that may be the issue

Stone Preston
Stone Preston
42,016 Points

See my reply to this post. It explains on how to add a search bar and search for usernames. Its not really step by step, but it will give you a general idea of what you need to do

I got an error when using that post. - " Use of undeclared identifier 'searchBarCancelButtonClicked'

<p>  - (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar {   </p>

See the full code here:

            <p>



#import "FindViewController.h"
#import "FindDetailsViewController.h"
#import "FindCell.h"

@interface FindViewController () <UISearchBarDelegate>

@property (weak, nonatomic) IBOutlet UISearchBar *searchBar;

@end

@implementation FindViewController {


}

- (id)initWithCoder:(NSCoder *)aCoder
{
    self = [super initWithCoder:aCoder];
    if (self) {


    }
    return self;
}


- (void)viewDidLoad
{

    self.searchBar.delegate = self;

    - (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar {

        searchBar.text = nil;

        //dismiss keyboard
        [self.searchBar resignFirstResponder];

    }

    - (void)searchBarTextDidBeginEditing:(UISearchBar *)searchBar {

        //Enable the cancel button when the user touches the search field
        self.searchBar.showsCancelButton = TRUE;
    }

    - (void)searchBarTextDidEndEditing:(UISearchBar *)searchBar {

        //dsiable the cancel button when the user ends editing
        self.searchBar.showsCancelButton = FALSE;
    }

    - (void)searchBarSearchButtonClicked:(UISearchBar *)searchBar {

        //dismiss keyboard
        [self.searchBar resignFirstResponder];


        //Strip the whitespace off the end of the search text
        NSString *searchText = [self.searchBar.text stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];


        //Check to make sure the field isnt empty and Query parse for username in the text field
        if (![searchText isEqualToString:@""]) {

            PFQuery *query = [PFUser query];
            [query whereKey:@"username" equalTo:searchText];
            [query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
                if (!error) {

                    //check to make sure the query actually found a user
                    if (objects.count > 0) {

                        //found a user
                        //set the user as the table views data source and reload the table view


                        //A user was not found, display error message
                    } else {

                        //no user found

                    }

                    [self.tableView reloadData];

                } else {

                    //error occurred
                }
            }];

        }


    }


    self.navigationItem.hidesBackButton = YES;

    UIImage *image = [UIImage imageNamed: @"Invest.png"];
    UIImageView *imageView = [[UIImageView alloc] initWithImage: image];

    self.navigationItem.titleView = imageView;

    [super viewDidLoad];

    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(refreshTable:)
                                                 name:@"refreshTable"
                                               object:nil];



}

- (void)refreshTable:(NSNotification *) notification
{
    // Reload the recipes
    [self loadObjects];
}


- (void)viewDidUnload
{
    [super viewDidUnload];



    // Release any retained subviews of the main view.
    [[NSNotificationCenter defaultCenter] removeObserver:self name:@"refreshTable" object:nil];
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}

- (PFQuery *)queryForTable
{
    PFQuery *query= [PFUser query];


     [query orderByAscending:@"money"];
     [query whereKey:@"money" equalTo: [NSNumber numberWithBool:TRUE]];



    self.pullToRefreshEnabled = YES;

    // Whether the built-in pagination is enabled
    self.paginationEnabled = NO;

    // The number of objects to show per page
    self.objectsPerPage = 3;


    //[query whereKey:@"username" equalTo:[[PFUser currentUser]username]];

    // If no objects are loaded in memory, we look to the cache first to fill the table
    // and then subsequently do a query against the network.
    /*    if ([self.objects count] == 0) {
     query.cachePolicy = kPFCachePolicyCacheThenNetwork;
     }*/

    //    [query orderByAscending:@"name"];

    return query;
}



// Override to customize the look of a cell representing an object. The default is to display
// a UITableViewCellStyleDefault style cell with the label being the first key in the object.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object
{
    static NSString *simpleTableIdentifier = @"FindCell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:simpleTableIdentifier];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:simpleTableIdentifier];
    }

    // Configure the cell
    PFFile *thumbnail = [object objectForKey:@"profileimageFile"];
    PFImageView *thumbnailImageView = (PFImageView*)[cell viewWithTag:100];
    thumbnailImageView.image = [UIImage imageNamed:@"placeholder2.jpg"];
    thumbnailImageView.file = thumbnail;
    [thumbnailImageView loadInBackground];

    UILabel *nameLabel = (UILabel*) [cell viewWithTag:101];
    nameLabel.text = [object objectForKey:@"name"];

    UILabel *prepTimeLabel = (UILabel*) [cell viewWithTag:102];
    prepTimeLabel.text = [object objectForKey:@"title"];

    return cell;
}

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
    // Remove the row from data model
    PFObject *object = [self.objects objectAtIndex:indexPath.row];
    [object deleteInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
        [self refreshTable:nil];
    }];
}

- (void) objectsDidLoad:(NSError *)error
{

    [super objectsDidLoad:error];



    NSLog(@"error: %@", [error localizedDescription]);
}

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
    if ([segue.identifier isEqualToString:@"showFindDetails"]) {
        NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
        FindDetailsViewController *destViewController = segue.destinationViewController;

        PFObject *object = [self.objects objectAtIndex:indexPath.row];
        FindCell *find = [[FindCell alloc] init];
        find.name = [object objectForKey:@"name"];
        find.imageFile = [object objectForKey:@"profileimageFile"];
        find.prepTime = [object objectForKey:@"title"];
        find.ingredients = [object objectForKey:@"moneyProfile"];
        destViewController.find= find;

    }
}


@end

</p>
            ```

Cool! I'm using a cell though(did a bit of hacking). Not the same code right?

I'm trying to implement my code with this code so that i can search the cells aswell https://parse.com/questions/programmatic-search-capability-using-parse

            <p>@interface FindDetailsViewController : UIViewController



@property (weak, nonatomic) IBOutlet UILabel *prepTimeLabel;

@property (weak, nonatomic) IBOutlet UITextView *ingredientTextView;

@property (nonatomic, strong) FindCell *find;

@end
#import "FindDetailsViewController.h"
#import <Parse/Parse.h>

@interface FindDetailsViewController ()

@end

@implementation FindDetailsViewController


@synthesize prepTimeLabel;

@synthesize ingredientTextView;
@synthesize find;


- (id)initWithNibName:(NSString *)nibNameOrNil bundle:(NSBundle *)nibBundleOrNil
{
    self = [super initWithNibName:nibNameOrNil bundle:nibBundleOrNil];
    if (self) {
        // Custom initialization
    }
    return self;
}

- (void)viewDidLoad
{

    self.navigationItem.hidesBackButton = YES;

    [super viewDidLoad];

    self.title = find.name;
    self.prepTimeLabel.text = find.prepTime;



    NSMutableString *ingredientText = [NSMutableString string];
    for (NSString* ingredient in find.ingredients) {
        [ingredientText appendFormat:@"%@\n", ingredient];
    }
    self.ingredientTextView.text = ingredientText;

}

- (void)viewDidUnload
{

    [self setPrepTimeLabel:nil];


    [self setIngredientTextView:nil];
    [super viewDidUnload];
    // Release any retained subviews of the main view.
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation == UIInterfaceOrientationPortrait);
}

@end</p>
            ``` 

It works. :) But the search don't work when searching for a user?

Stone Preston
Stone Preston
42,016 Points

search DOES work. you can log the object returned by the query and see that it did indeed find a user. You just have to do something with that user after the query runs. I cant tell you what to do with it cause I dont know how your table is setup etc.

query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
                if (!error) {

                    //check to make sure the query actually found a user
                    if (objects.count > 0) {

                        //found a user
                        //set the user as the table views data source and reload the table view
                       NSLog("user: %@", [objects objectAtIndex:0]);


                        //A user was not found, display error message
                    } else {

                        //no user found

                    }

                    [self.tableView reloadData];

                } else {

                    //error occurred
                }
            }];

Thanks again:) Ok. Maybe it will help if I show my Code. I see what you are talking about but I can't understand how to do it

This is my code.

            <p>#import "FindViewController.h"
#import "FindDetailsViewController.h"
#import "FindCell.h"

@interface FindViewController () 

@end

@implementation FindViewController {


}

- (id)initWithCoder:(NSCoder *)aCoder
{
    self = [super initWithCoder:aCoder];
    if (self) {


    }
    return self;
}


- (void)viewDidLoad
{

    self.searchBar.delegate = self;
    self.navigationItem.hidesBackButton = YES;

    UIImage *image = [UIImage imageNamed: @"Invest.png"];
    UIImageView *imageView = [[UIImageView alloc] initWithImage: image];

    self.navigationItem.titleView = imageView;

    [super viewDidLoad];

    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(refreshTable:)
                                                 name:@"refreshTable"
                                               object:nil];
}

- (void)refreshTable:(NSNotification *) notification
{
    // Reload the recipes
    [self loadObjects];
}


- (void)viewDidUnload
{
    [super viewDidUnload];



    // Release any retained subviews of the main view.
    [[NSNotificationCenter defaultCenter] removeObserver:self name:@"refreshTable" object:nil];
}

- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
    return (interfaceOrientation != UIInterfaceOrientationPortraitUpsideDown);
}

- (PFQuery *)queryForTable
{
    PFQuery *query= [PFUser query];


     [query orderByAscending:@"money"];
     [query whereKey:@"money" equalTo: [NSNumber numberWithBool:TRUE]];



    self.pullToRefreshEnabled = YES;

    // Whether the built-in pagination is enabled
    self.paginationEnabled = NO;

    // The number of objects to show per page
    self.objectsPerPage = 3;


    //[query whereKey:@"username" equalTo:[[PFUser currentUser]username]];

    // If no objects are loaded in memory, we look to the cache first to fill the table
    // and then subsequently do a query against the network.
    /*    if ([self.objects count] == 0) {
     query.cachePolicy = kPFCachePolicyCacheThenNetwork;
     }*/

    //    [query orderByAscending:@"name"];

    return query;
}



// Override to customize the look of a cell representing an object. The default is to display
// a UITableViewCellStyleDefault style cell with the label being the first key in the object.
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath object:(PFObject *)object
{
    static NSString *simpleTableIdentifier = @"FindCell";

    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:simpleTableIdentifier];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:simpleTableIdentifier];
    }

    // Configure the cell
    PFFile *thumbnail = [object objectForKey:@"profileimageFile"];
    PFImageView *thumbnailImageView = (PFImageView*)[cell viewWithTag:100];
    thumbnailImageView.image = [UIImage imageNamed:@"placeholder2.jpg"];
    thumbnailImageView.file = thumbnail;
    [thumbnailImageView loadInBackground];

    UILabel *nameLabel = (UILabel*) [cell viewWithTag:101];
    nameLabel.text = [object objectForKey:@"name"];

    UILabel *prepTimeLabel = (UILabel*) [cell viewWithTag:102];
    prepTimeLabel.text = [object objectForKey:@"title"];

    return cell;
}

- (void)tableView:(UITableView *)tableView commitEditingStyle:(UITableViewCellEditingStyle)editingStyle forRowAtIndexPath:(NSIndexPath *)indexPath
{
    // Remove the row from data model
    PFObject *object = [self.objects objectAtIndex:indexPath.row];
    [object deleteInBackgroundWithBlock:^(BOOL succeeded, NSError *error) {
        [self refreshTable:nil];
    }];
}

- (void) objectsDidLoad:(NSError *)error
{

    [super objectsDidLoad:error];



    NSLog(@"error: %@", [error localizedDescription]);
}

- (void)prepareForSegue:(UIStoryboardSegue *)segue sender:(id)sender {
    if ([segue.identifier isEqualToString:@"showFindDetails"]) {
        NSIndexPath *indexPath = [self.tableView indexPathForSelectedRow];
        FindDetailsViewController *destViewController = segue.destinationViewController;

        PFObject *object = [self.objects objectAtIndex:indexPath.row];
        FindCell *find = [[FindCell alloc] init];
        find.name = [object objectForKey:@"name"];
        find.imageFile = [object objectForKey:@"profileimageFile"];
        find.prepTime = [object objectForKey:@"title"];
        find.ingredients = [object objectForKey:@"moneyProfile"];
        destViewController.find= find;

    }
}

- (void)searchBarCancelButtonClicked:(UISearchBar *)searchBar {

    //dismiss keyboard
    [self.searchBar resignFirstResponder];

}

- (void)searchBarTextDidBeginEditing:(UISearchBar *)searchBar {

    //Enable the cancel button when the user touches the search field
    self.searchBar.showsCancelButton = TRUE;
}

- (void)searchBarTextDidEndEditing:(UISearchBar *)searchBar {

    //dsiable the cancel button when the user ends editing
    self.searchBar.showsCancelButton = FALSE;
}

- (void)searchBarSearchButtonClicked:(UISearchBar *)searchBar {

    //dismiss keyboard
    [self.searchBar resignFirstResponder];


    //Strip the whitespace off the end of the search text
    NSString *searchText = [self.searchBar.text stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];


    //Check to make sure the field isnt empty and Query parse for username in the text field
    if (![searchText isEqualToString:@""]) {


        PFQuery *query = [PFUser query];
        [query whereKey:@"name" equalTo:searchText];
        [query whereKey:@"title" equalTo:searchText];
        [query findObjectsInBackgroundWithBlock:^(NSArray *objects, NSError *error) {
            if (!error) {

                //check to make sure the query actually found a user
                if (objects.count > 0) {

                    //found a user
                    //set the user as the table views data source and reload the table view


                    //A user was not found, display error message
                } else {

                    //no user found

                }

                [self.tableView reloadData];

            } else {

                //error occurred
            }
        }];

    }


}


@end
</p>
            ```

I would be so happy if you could help me:) Stone Preston