I am including a file like this:
#import "BannerPhoneContentController.h"
however, when I try to use it like this:
bannerContentController = [[BannerPhoneContentController alloc] init];
I get the error:
Use of undeclared identifier 'BannerPhoneContentController';
what could be causing the code to seemingly ignore my import?
this is the header for banner content controller.
#import <UIKit/UIKit.h>
#import <Foundation/Foundation.h>
#import "BannerContentController.h"
#interface BannerPhoneContentController : BannerContentController <UIScrollViewDelegate>
{
UIScrollView *scrollView;
UIPageControl *pageControl;
NSMutableArray *viewControllers;
// To be used when scrolls originate from the UIPageControl
BOOL pageControlUsed;
}
#property (nonatomic, retain) UIScrollView *scrollView;
#property (nonatomic, retain) UIPageControl *pageControl;
#property (nonatomic, retain) NSMutableArray *viewControllers;
- (IBAction)changePage:(id)sender;
#end
EDIT bannerContentController is of type BannerContentController NOT BannerPhoneContentController. The latter is a subtype of the former. It is definitely worth noting that this exact code works just fine in another app, so it's nothing to do with the code itself - just how it's being included apparently. I'm stumped.
EDIT ok found the problem - not sure how to fix it. I generated the preprocessed file and the header file it's included is in fact this:
#import <UIKit/UIKit.h>
#import <Foundation/Foundation.h>
#import "ContentController.h"
#interface PhoneContentController : ContentController <UIScrollViewDelegate>
{
UIScrollView *scrollView;
UIPageControl *pageControl;
NSMutableArray *viewControllers;
// To be used when scrolls originate from the UIPageControl
BOOL pageControlUsed;
}
#property (nonatomic, retain) UIScrollView *scrollView;
#property (nonatomic, retain) UIPageControl *pageControl;
#property (nonatomic, retain) NSMutableArray *viewControllers;
- (IBAction)changePage:(id)sender;
#end
note the difference - all the 'Banner's are missing. This is what the file used to look like. However, I've checked and the file that's in the project is the one I posted at the top. I tried cleaning the solution and building again. How can I fix this and why has it happened?
EDIT The file that I'm including all this in is part of a code library. I have now created a new project, imported the code library and included all of this in that library once again in exactly the same way. and it works. I have looked over the two projects and the code in question is identical. This must be a project setting?
It looks for me like recursive import. Say, BannerContentController.h imports BannerPhoneContentController.h, and BannerPhoneContentController.h imports BannerContentController.h.
If it is the case, then you should resolve recursive dependencies. E.g. using forward declaration.
does using #class BannerPhoneContentController in .h and #import "BannerPhoneContentController.h" in .m gives the same result ?
After a lot of messing around, and thanks to a comment from Yuras I generated the preprocessed code and realised the problem was that the OLD version of the code was being included.
More useful is WHY. It's just a bug in XCode that happens sometimes when incremental linking is turned on - basically this is where time is saved by only changing the parts of the pre-processed file when the corresponding bits of your code have been altered. Unfortunately, this does not alway work correctly.
The solution, annoyingly, was to delete the files, clean the build, delete the derived data (window / oraniser / projects / project name / delete derived data), restart xcode (possibly also restart your computer, or throw it out of the window and buy a new one) then re-import the files.
XCode can be a real pain...
Related
i have 15 to 20 Variable i wants access it in my whole project. what is the best place for defining it and why?.. Appdelegate File, .Pch file or define these Extern.
really thanks in Advance.
Accessing your app delegate from various points of your app creates a strong coupling between these components of your app.
Basically you are using globals through your app which is usually a good indication for an improvable application design.
Variables usually do not live in thin air. They exist in a context. For example if you are using username and password you should get them from the system's keychain. The whole authentification process should be wrapped in an authentification class in which you would define the properties.
If you need to access information from various places of your app, you have to pass them as arguments of the initializer for example. This btw renders your individual components testable which is a good thing.
My advice is to rethink your app design first to not end in dependency hell later on.
You can define them as properties in your AppDelegate class. For example:
#interface AppDelegate : UIResponder <UIApplicationDelegate>
#property (retain, nonatomic) NSString *publicString;
If you want to make them readonly for external objects then you can define as follows:
1) in AppDelegate.h
#interface AppDelegate : UIResponder <UIApplicationDelegate>
#property (retain, readonly, nonatomic) NSString *publicString;
2) in AppDelegate.m
#interface AppDelegate ()
#property (retain, readwrite, nonatomic) NSString *publicString;
#end
#implementation AppDelegate
#synthesize publicString;
// other methods below
#end
Create one header file by name 'defines.h' and implement all defines and constants in it.
import this file in .Pch file
This is the best one, and will be separate from other classes.
I'm learning about iPad development from the book Head First iPhone & iPad Development (2nd Edition). I'm stuck in chapter 7, page 347. This is the chapter on taking the DrinkMixer iPhone app and turning it into a universal app for both the iPhone and the iPad.
We added a split view controller (UISplitViewController) and the coding behind it all goes well (no build errors). The one difference I'm doing is that I'm using storyboards. Up to this point it's been going well, but now the book says to add a split view property IBOutlet (code below) for the detail view controller (*splitViewDetailView) and hook that #property up to the detail view.
MasterViewController.h
#import <UIKit/UIKit.h>
#class DetailViewController;
#interface MasterViewController : UITableViewController {
NSMutableArray *drinks;
DetailViewController *splitViewDetailView;
}
#property (nonatomic, retain) NSMutableArray *drinks;
#property (nonatomic, retain) IBOutlet DetailViewController *splitViewDetailView;
#end
MasterViewController.m (top part)
#import "MasterViewController.h"
#import "DetailViewController.h"
#import "AddDrinkViewController.h"
#import "DrinkConstants.h"
#implementation MasterViewController
#synthesize drinks;
#synthesize splitViewDetailView;
The problem I'm having is that when I try to hook up the property to the detail view, it won't let me. The connection wire won't snap into the view. I've done many other IBOutlets and IBActions so far and it was easy to do. Anyone know what I'm doing wrong?
I've tried to search for a similar issues here on stack overflow and the web for the past 2 days and so far I've come up empty.
I found out that I was going about this the wrong way. The solution was simpler than I thought.
Link
Thank you Marcus Buffett. I'd vote you up but I don't have enough reputation points yet.
I have read other questions here, but they seem to be for Xcode 3.2 or earlier, but nothing for 4.2. :(
I started a simple project and was wanting to connect the File Owner's Outlets within my xib. The bummer is that my IBOutlet's from my ViewController.h aren't coming over.
I don't have a reputation of 10 or above, so here is a screenshot of my File's Owner not showing my IBOutlets.
Here is my ViewController.h code:
#import <UIKit/UIKit.h>
#interface ViewController : UIViewController {
IBOutlet UITextField *txtName;
IBOutlet UILabel *lblMessage;
}
#property (nonatomic, retain) IBOutlet UITextField *txtName;
#property (nonatomic, retain) IBOutlet UILabel *lblMessage;
- (IBAction)doSomething;
#end
Here is my ViewController.m code:
#import "ViewController.h"
#implementation ViewController
#synthesize txtName;
#synthesize lblMessage;
- (IBAction) doSomething
{
NSString *msg = [[NSString alloc] initWithFormat:#"Hello, %#",txtName.text];
[lblMessage setText:msg];
}
#end
I am new to Objective-C and Xcode, so I could have made a mistake, but I've followed many tutorials and I can never get my IBOutlets to show. I have gone as far as to delete Xcode 4.2 and re-installed to try and fix this issue. Here is a screenshot of my Xcode Version 4.2, Build 4D199 info.
Anyone else run into this issue? Thanks anyone who can point out any mistakes I have made. Please let me know if more information is needed.
When you create your IBAction, in the .h file, there will be a connection indicator to the left of it. When it isn't connected it shows a empty circle.
Press and hold this and drag it to the item you want to connect it to. I usually open up the XIB in a new window by double clicking it.
If it wont connect you must set the File's Owner in the XIB file. Select File's Owner in the Placeholders panel. Move over to the Utilities panel and make sure the Custom class, in Identity Inspector, is set to what ever your viewcontroller is named.
I Hope this will help you.
Cheers!
Try to reassign your file owner class reference in xib file.
Then attach all your IBOutlet connections.
Hope this might be helpful to you.
Check if the Files Owner is set to "ViewController". Check the following link:
http://developer.apple.com/library/ios/#documentation/IDEs/Conceptual/Xcode4TransitionGuide/InterfaceBuilder/InterfaceBuilder.html
Two things need to be added, before Xcode will allow creation of IBOutlet for the text field from the Storyboard:
Assign the underlying ViewController as the delegate to the UITextField
Add the to the #interface declaration in the ViewController.h file:
#interface ViewController : UIViewController<UITextFieldDelegate>
Until both of these are completed, you can Ctrl-click and drag from the Storyboard to the .h file, but no IBOutlet connection will be enabled.
I've finally figured out the issue, hope this helps anyone else currently having the same problem.
It had nothing to do with the xib's file owner setting. What my issue was that I had the xib file in a different directory than the source files, thus it wasn't able to connect the outlets. Once I moved the files to the same directory, everything worked. FYI, I moved everything to the top directory. Not sure sub directories will work...
To move the files, be sure to update xcode to point to the new locations.
i recently updated my IDE to XCode 4.0 and saw a strange change in the Utillity-Application boiler-plate-code:
First, the MainViewController.h-File:
#import <UIKit/UIKit.h>
#class MainViewController;
#interface UtilityAppDelegate : NSObject <UIApplicationDelegate> {
}
#property (nonatomic, retain) IBOutlet UIWindow *window;
#property (nonatomic, retain) IBOutlet MainViewController *mainViewController;
#end
Question 1: Where is "mainViewController" declared in the first place? I didn't find it anywhere.
In the *.m-File there is a
#synthesize mainViewController=_mainViewController;
statement. So my second question: Where is "_mainViewController" hidden? Can't find a declaration anywhere. It comes somehow out of the main *.nib file I guess.
But there is another problem: I did add a UINavigationController to one of my recent projects and have no need for mainViewController anymore. But when I delete #property and #synthesize out of MainViewController.m/.h , I can't run the app anymore because of this exception:
setValue:forUndefinedKey:]: this class is not key value coding-compliant for the key mainViewController.'
occurring at this line
int retVal = UIApplicationMain(argc, argv, nil, nil);
in the main.m.
Thx for your help.
Look at you info.plist it's should be declared there. If you created your app with a template it's configured by the plist. There is some implicit declaration done by this, the mainWindow.xib(in my example) contains more than a window. There are the connections to the appDelegate and the viewController, see second screenshot.
The last line of the screenshot:
Question 1:
When you use a declaration like this, you don't also need to explicitly define the property.
.h
#property (nonatomic, retain) IBOutlet MainViewController *mainViewController;
.m
#synthesize mainViewController=_mainViewController;
Question 2:
_mainViewController is not hidden. It points to mainViewController which is implicitly defined in the #property statement in .h
#synthesize mainViewController=_mainViewController;
This format is used to distinguish between the ivar and other properties. It refers to mainViewController.
Question 3:
You deleted the declarations #property/#synthesize for mainViewController, but it still exists in the nib file (IB). Delete it from IB and you should be good to go.
You're encountering the new ABI for the first time. It is no longer necessary to actually declare variables for properties. If you use #property and #synthesize, a backing ivar will automatically be generated for you.
You're probably getting the KVC error because the NIB still references the old property. You should see a warning about this during compile. In IB, look at your App Delegate; it probably still has an outlet for mainViewController, and you probably are still generating a MainViewController. You need to delete them from the NIB.
I am trying to figure out how to take a screen capture feed and send it to an iOS device (an iPad in this case) and have the images displayed on the screen, updating as each new image is sent while clearing the old one from memory.
I am just starting with the basics, so I am trying to get the simulator to load a screenshot from the desktop and display it on the screen, and then change the image as I take a new screenshot, and either delete the old one so I can rename the new screenshot to carry the same name or to simply overwrite the old one (thus the reference should still point correctly in the programming code).
I tried using a button that reloaded my UIImageView via:
- (IBAction)buttonPressed:(id)sender
{
[UIImageView setImage:ScreenCapture];
}
where ScreenCapture is the name of the UIImageView, with the hope that it would reload the existing referenced image.png file, but clicking the button simply exits that program within the simulator and goes back to the simulator's home screen.
Am I using the wrong object when trying to get this done via UIImageView? Is their an existing program/tutorial on this?
I would try to reverse engineer VNC for the iPhone, but both the copyright issues and the amount of advanced programming features are well beyond me.
Once I can get something working through Xcode, I am also planning on trying to implement the same thing via MonoTouch to see which language is easier to use and more beginner friendly.
Thank you for the help,
~Chris
header:
#import <UIKit/UIKit.h>
#interface Screen_Capture_3ViewController : UIViewController {
IBOutlet UIImageView *ScreenCapture;
IBOutlet UIBarButtonItem *Update;
}
#property (nonatomic, retain) IBOutlet UIImageView *ScreenCapture;
#property (nonatomic, retain) IBOutlet UIBarButtonItem *Update;
- (IBAction)buttonPressed:(id)sender;
#end
.m:
#import "Screen_Capture_3ViewController.h"
#implementation Screen_Capture_3ViewController
#synthesize ScreenCapture;
#synthesize Update;
- (IBAction)buttonPressed:(id)sender
{
[UIImageView setImage:ScreenCapture];
}
Everything else remains at the default when selecting "View-based Application", and I connected the ScreenCapture to the UIImageView in Interface builder, as well as Update and buttonPressed to the UIBarButtonItem in Interface Builder.
setImage is an instance method, not a class method, so you can't send it directly to UIImageView (nor would it really mean much).
Keep your current code from your question for the header (but only the property should be marked as IBOutlet):
#interface Screen_Capture_3ViewController : UIViewController {
UIImageView *ScreenCapture;
UIBarButtonItem *Update;
}
#property (nonatomic, retain) IBOutlet UIImageView *ScreenCapture;
#property (nonatomic, retain) IBOutlet UIBarButtonItem *Update;
- (IBAction)buttonPressed:(id)sender;
#end
In your implementation, your event handler should be something like this:
- (IBAction)buttonPressed:(id)sender {
UIImage* newImage = [UIImage imageWithContentsOfFile:#"pathToImage.png"];
[ScreenCapture setImage:newImage];
}