I have an Array.
Inside my array have 8 object seriated:
- text
- text
- link Url Image.
- link Url Image.
- text
- link Url Image.
- link Url Image.
- text
I had downloaded all image and save to document folder.
And now, How can I get all image from document folder and show in tableViewCell seriated same myArray?
I used this code to get all image from document folder.
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *myPath = [paths objectAtIndex:0];
NSFileManager *fileManager = [NSFileManager defaultManager];
NSArray *directoryContents = [fileManager contentsOfDirectoryAtPath:myPath error:nil];
NSMutableArray *subpredicates = [NSMutableArray array];
[_arrMessageFree addObject:[NSPredicate predicateWithFormat:#"SELF ENDSWITH '.png'"]];
[_ar addObject:[NSPredicate predicateWithFormat:#"SELF ENDSWITH '.jpg'"]];
NSPredicate *filter = [NSCompoundPredicate orPredicateWithSubpredicates:subpredicates];
NSArray *onlyImages = [directoryContents filteredArrayUsingPredicate:filter];
But, I cannot show both text and image seriated in myArray.
-(UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
//after cell initialization add following code
for (UIView *subview in [cell.contentView subviews])
{
[subview removeFromSuperview];
}
UIImage *img=[UIImage imageWithContentsOfFile:[onlyImages objectAtIndex:indextPath.row]];
[cell.contentView addSubview:img];
}
As you have told, you are able to get the image names into onlyImages array after the following line:
NSArray *onlyImages = [directoryContents filteredArrayUsingPredicate:filter];
So let's use it to fetch and create UIImages:
UIImage *temp = nil;
for (int i = 0; i < [onlyImages count]; i++) {
temp = [UIImage imageNamed:[onlyImages objectAtIndex:i]]; // so now you have your image loaded into `temp` UIImage object
}
Hope this was helpful!
Cheers!
Related
I'm a newbie to Objective-C so any help is greatly appreciated.
I have a TableView that is successfully pulling back the list from my Data.plist file within my Xcode project but I need it to pull from the Documents Directory.
I have seen many posts about this but can't seem to get it to work for me.
Here is my .m file below. Like I said, it pulls back the data but I need it to be dynamically changed based on my Documents plist copy.
Thanks in advance!
#synthesize content = _content;
- (NSArray *)content
{
if (!_content) {
_content = [[NSArray alloc] initWithContentsOfFile:[[NSBundle mainBundle] pathForResource:#"Data" ofType:#"plist"]];
}
return _content;
}
- (void)viewDidLoad
{
[super viewDidLoad];
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Return the number of rows in the section.
return [self.content count];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier forIndexPath:indexPath];
// Configure the cell...
cell.textLabel.text = [[self.content objectAtIndex:indexPath.row] valueForKey:#"Name"];
cell.detailTextLabel.text = [[self.content objectAtIndex:indexPath.row] valueForKey:#"Score"];
return cell;
}
Try this:
Step 1: In .h File declare a global variable
#property (nonatomic,retain) NSMutableDictionary *contents;
Step 2: In .m file set synthesis.
#synthesize contents;
Step 3: Move plist file from mainbudle into documents directory
-(void) createPlistDocuments
{
// Get path to documents directory
NSArray *arrayPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
// Finds the contained Documents directory
NSString *documentsDirectory = [arrayPaths objectAtIndex:0];
NSError *error;
// Create an object that we will later use to look for a file and return a boolean value on whether or not it exists
NSFileManager *manager = [NSFileManager defaultManager];
// File we want to move, stored in original top level directory
NSString *demoFile = [[NSBundle mainBundle] pathForResource:#"data" ofType:#"plist"];
// Define where we want it moved to and name it
NSString *demoFileMoved = [NSString stringWithFormat:#"%#/data.plist", documentsDirectory];
// Attempt the copy
if ([manager copyItemAtPath:demoFile toPath:demoFileMoved error:&error] != YES)
NSLog(#"Unable to move file: %#", [error localizedDescription]);
}
Step 4: Read plist data from document directory
- (void)viewDidLoad
{
[super viewDidLoad];
[self createPlistDocuments];
NSArray *paths = NSSearchPathForDirectoriesInDomains(
NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectoryPath = [paths objectAtIndex:0];
NSString *path = [NSString stringWithFormat:#"%#/data.plist",documentsDirectoryPath];
contents = [NSArray arrayWithContentsOfFile:path];
NSLog(#"%d", contents.count);
}
For brief explanation follow this sample... TechDevMobile(IOS-Message-Chat)
This question already has an answer here:
Don't have the pictures from directory on CollectionView
(1 answer)
Closed 9 years ago.
I am showing the Pictures in all of the Directories however It does not display the pictures. I am putting NSLog in the code so that I can find out which code is working and I only get "j" in the log. I do not see the "a" in the log. What do you think is wrong?
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
allImagesArray = [[NSMutableArray alloc] init];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSArray *locations = [[NSArray alloc]initWithObjects:#"Bottoms", #"Dress", #"Coats", #"Others", #"hats", #"Tops",nil ];
NSString *fPath = documentsDirectory;
for(NSString *component in locations)
{
fPath = [fPath stringByAppendingPathComponent:component];
}
NSArray *directoryContent = [[NSFileManager defaultManager] directoryContentsAtPath: fPath];
collectionTrash.delegate =self;
collectionTrash.dataSource=self;
for(NSString *str in directoryContent){
NSLog(#"i");
NSString *finalFilePath = [fPath stringByAppendingPathComponent:str];
NSData *data = [NSData dataWithContentsOfFile:finalFilePath];
if(data)
{
UIImage *image = [UIImage imageWithData:data];
[allImagesArray addObject:image];
NSLog(#"array:%#",[allImagesArray description]);
}}
for(NSString *folder in locations) {
// get the folder contents
for(NSString *file in directoryContent) {
// load the image
}
}}
- (NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView
{
NSLog(#"j");
return 1;
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return [allImagesArray count];
}
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *reuseID = #"ReuseID";
TrashCell *mycell = (TrashCell *) [collectionView dequeueReusableCellWithReuseIdentifier:reuseID forIndexPath:indexPath];
UIImageView *imageInCell = (UIImageView*)[mycell viewWithTag:1];
imageInCell.image = [allImagesArray objectAtIndex:indexPath.row];
NSLog(#"a");
return mycell;
}
Feel free to as for more code.
If you look at the exception, it tells you very precisely what's wrong:
You are trying to calling a 'length' method on an array, which simply does not exist. You want to use count here instead. It's not in the code you posted, though - so just do a search for length and you'll probably find it rather easily if the project isn't huge.
NSString *fPath = [documentsDirectory stringByAppendingPathComponent:locations]; gives you a warning, because locations is an array. Think about it - just doesn't make sense: which of its elements do you want to add to the path?
As I think about it, both errors probably relate to each other: You simply ignored the compile time error - or warning - for the fPath, and now the stringByAppendingPathComponent: method calls length on its parameter, which is a method of the expected NSString.
Bottom line: Do not ignore compiler warnings! If you fix those, you probably reduce crashes, too.
I would want to show all the pictures in my directory however I am creating Folders in the Directory so that I can sort the pictures. I want to show all of the pictures in several folders. I am using the code
- (void)viewDidLoad
{
[super viewDidLoad];
// Do any additional setup after loading the view.
allImagesArray = [[NSMutableArray alloc] init];
NSArray *paths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [paths objectAtIndex:0];
NSString *location=#"Bottoms"#"Top"#"Right"#"Left"#"Down"#"Up";
NSString *fPath = [documentsDirectory stringByAppendingPathComponent:location];
NSArray *directoryContent = [[NSFileManager defaultManager] directoryContentsAtPath: fPath];
collectionTrash.delegate =self;
collectionTrash.dataSource=self;
for(NSString *str in directoryContent){
NSLog(#"i");
NSString *finalFilePath = [fPath stringByAppendingPathComponent:str];
NSData *data = [NSData dataWithContentsOfFile:finalFilePath];
if(data)
{
UIImage *image = [UIImage imageWithData:data];
[allImagesArray addObject:image];
NSLog(#"array:%#",[allImagesArray description]);
}}}
- (NSInteger)numberOfSectionsInCollectionView:(UICollectionView *)collectionView
{
NSLog(#"j");
return 1;
}
- (NSInteger)collectionView:(UICollectionView *)collectionView numberOfItemsInSection:(NSInteger)section
{
return [allImagesArray count];
}
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *reuseID = #"ReuseID";
TrashCell *mycell = (TrashCell *) [collectionView dequeueReusableCellWithReuseIdentifier:reuseID forIndexPath:indexPath];
UIImageView *imageInCell = (UIImageView*)[mycell viewWithTag:1];
imageInCell.image = [allImagesArray objectAtIndex:indexPath.row];
NSLog(#"a");
return mycell;
}
If you see my code you can notice that I have put NSLOG i and j. The j comes up but the i does not.... Is my way wrong showing all the pictures that are in several folders? I do not have any error.
If you have multiple folders then you need to iterate over the folders and then the folder contents to process all of it.
While this line:
NSString *location=#"Bottoms"#"Top"#"Right"#"Left"#"Down"#"Up";
Is technically legal, I guess you're thinking it will do some array / iteration thing for you. It won't. It just concatenates all of the strings together. You probably want something more like:
NSArray *locations = #[ #"Bottoms", #"Top", #"Right", #"Left", #"Down", #"Up" ];
Then you can run a loop over the folders and then the contents:
for(NSString *folder in locations) {
// get the folder contents
for(NSString *file in directoryContent) {
// load the image
}
}
In my project I am saving the images into the documents folder on my phone then i am loading them in a separate tableview. I am getting a bit of success, the very last image that is taken is loaded into the table, but is loaded into every row instead of just the last one. Here is the code i used to load the image in the tableview :
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"List";
ListCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
//Load PLIST
NSArray *path = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDirectory = [path objectAtIndex:0];
NSString *plistPath = [NSString stringWithFormat:#"%#/images.plist", documentsDirectory];
//Load PLIST into mutable array
NSMutableArray *imageArray = [NSMutableArray arrayWithContentsOfFile:plistPath];
for (NSDictionary *dict in imageArray) {
//Do whatever you want here, to load an image for example
NSString *imageFilePath = [NSHomeDirectory() stringByAppendingPathComponent:[dict objectForKey:#"Original Image"]];
UIImage *image = [UIImage imageWithContentsOfFile:imageFilePath];
[cell.imageofItem setImage:image];
}
}
Here is an example of what is happening
: Say i take 2 photos, one is called "10282012_13113138_image.jpg" and the other is called "10282012_13113468_image.jpg". Then i go to load the images in the cell, and the last photo is loaded in the two cells.
Any help would be much appreciated!
Instead of
for (NSDictionary *dict in imageArray) {
NSString *imageFilePath = [NSHomeDirectory() stringByAppendingPathComponent:[dict objectForKey:#"Original Image"]];
UIImage *image = [UIImage imageWithContentsOfFile:imageFilePath];
[cell.imageofItem setImage:image];
}
Try
NSDictionary *dict = [imageArray objectAtIndex:indexPath.row];
NSString *imageFilePath = [NSHomeDirectory() stringByAppendingPathComponent:[dict objectForKey:#"Original Image"]];
UIImage *image = [UIImage imageWithContentsOfFile:imageFilePath];
[cell.imageofItem setImage:image];
The problem was that for each indexPath.row, you were iterating till the last element in the array, constantly overwriting the cell image until you get to the last image. Then for the next indexPath.row, you do the same thing, and setting that to the last image in the array, and so on....
Actually this is to follow up my question before
UITableView show only first row.
Now my problem is that I only want to view the 10 list in my plist. If there are 11 items, the first item will be replace by the second and so on so my list only 10 items.
And this is my code to save to the plist:
NSArray *paths = NSSearchPathForDirectoriesInDomains (NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsPath = [paths objectAtIndex:0];
NSString *plistPath = [documentsPath stringByAppendingPathComponent:#"Data.plist"];
NSMutableArray *array = [NSMutableArray arrayWithContentsOfFile:plistPath];
if (nil == array) {
array = [[NSMutableArray alloc] init];
}
NSMutableArray *list = [[NSMutableArray alloc]init];
[list addObject:resi.text];
[array addObject:list];
[array writeToFile:plistPath atomically: TRUE];
And this is the whole code for my table view that have been modified
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
// Return the number of sections.
return 1;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
// Return the number of rows in the section.
return [array count];
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
static NSString *CellIdentifier = #"Cell";
UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:CellIdentifier];
if (cell == nil) {
cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:CellIdentifier];
}
NSArray *list = (NSArray *)[self.array objectAtIndex:indexPath.row];
if(list && [list count] > 0) { //to check and avoid any crash
cell.textLabel.text = [list objectAtIndex:0];
}
// Configure the cell...
return cell;
}
- (void)viewWillAppear:(BOOL)animated
{
// get paths from root direcory
NSArray *paths = NSSearchPathForDirectoriesInDomains (NSDocumentDirectory, NSUserDomainMask, YES);
// get documents path
NSString *documentsPath = [paths objectAtIndex:0];
// get the path to our Data/plist file
NSString *plistPath = [documentsPath stringByAppendingPathComponent:#"Data.plist"];
array = [NSMutableArray arrayWithContentsOfFile:plistPath];
[myHistoryTable reloadData];
}
if ([array count] > 10) {
array = [array subarrayWithRange:NSMakeRange([array count] - 10, 10)];
}
if you don't want to overwrite the original array create a second one which serves as the dataSource of the tableView:
array = /* load from plist */;
if ([array count] > 10) {
self.dataSourceArray = [array subarrayWithRange:NSMakeRange([array count] - 10, 10)];
}
else {
self.dataSourceArray = array;
}