How can i fix this kind of problems
here is some code
BOOL missed = NO;
if (elem.lastCall.lastMissedEvent) {
if ([elem.status intValue] == 3 && [elem.timeStamp compare:elem.lastCall.lastMissedEvent] != NSOrderedAscending) {
missed = YES;
}
}
SCBubbleViewOut *bubble = nil;
if ([cell.bubbleView isKindOfClass:[SCBubbleViewOut class]]) {
bubble = (SCBubbleViewOut *) cell.bubbleView;
}
or here is some more code snipet
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath
{
NSString *userid = [members objectAtIndex:indexPath.row];
BOOL itsMe = NO;
if ([userid isEqualToString:[SCUserProfile currentUser].userid]) {
itsMe = YES;
[self performSegueWithIdentifier:#"SCUserProfileControllerSegue" sender:self];
}
else
{
[self showFriendDetailForUserid:userid];
}
}
from these cases i get
Value stored to "BOOL" is never read;
BOOL = itsMe , missed and bubble.
Any help is highly appreciated
Thanks in Advance.
Well, you are storing some value into a variable "missed", and you are never using the value stored. So the compiler is wondering why you are doing this, because it is pointless, and the compiler assumes that maybe you wanted to do something else.
If you stored the variable for example so that you can view it in the debugger, add a line
(void) missed;
That tells the compiler "yes, I know I store a value and I'm not using it, leave me alone". On the other hand, if that's not the case then you need to figure out what you actually wanted to do. The compiler doesn't know, and we don't know. The compiler just says "this doesn't look right", and I can only agree with it.
Related
Please can anyone tell me why this piece of code isn't working? I've got a dictionary which contains UIViews with tables inside associated with the keys which are the names of the corresponding buttons (there are a lot of them). So what I actually want to do is to change the view visibility on the corresponding button click. But the issue is that the expression to do that is not accepted by Xcode and I get the Expected Identifier error.
- (IBAction)choosingButtonClicked:(id)sender {
if ([sender currentTitle]) {
[(UIView *)[self.selectionTables objectForKey:[sender currentTitle]]].hidden = ![(UIView *)[self.selectionTables objectForKey:[sender currentTitle]]].isHidden;
}
}
First of all, with all due respect, I agree with trojanfoe comments. Its not working because its not properly written.
Now, lets try to streamline it with below code:
- (IBAction)choosingButtonClicked:(id)sender {
NSString *title = [sender currentTitle];
if (title) {
UIView *selectionView = (UIView *)self.selectionTables[title];
selectionView.hidden = !selectionView.isHidden;
}
}
Your code is too complex, because of that even the author can't understand it. If we re-write your code using local variables, it will look like:
- (IBAction)choosingButtonClicked:(id)sender
{
NSString *title = [sender currentTitle];
if (title)
{
UIView *tempView = (UIView *)[self.selectionTables objectForKey:title];
[tempView].hidden = ![tempView].isHidden;
}
}
If you check the code now, you can see that the following code is causing the issues:
[tempView].hidden = ![tempView].isHidden;
Change your method like:
- (IBAction)choosingButtonClicked:(id)sender
{
NSString *title = [sender currentTitle];
if (title)
{
UIView *tempView = (UIView *)[self.selectionTables objectForKey:title];
tempView.hidden = !(tempView.isHidden);
}
}
I'm just learning all this stuff, so excuse me if I'm making a glaring error.
I have an array of levels of expertise: #[#"NOVICE", #"INTERMEDIATE", #"PRO", #"ALL LEVELS"];.
The user can select up to two, but if ALL LEVELS is selected, the segue is performed and the setting saved.
What I'm trying to avoid is a user selecting NOVICE and PRO. If NOVICE is selected, I want PRO to be deselected and unhighlighted. And vice versa.
Here's what I have, but I get the error:
- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
NSString *organizeLevelOfPlay = self.organizeDifficultyArray[indexPath.row];
if ([organizeLevelOfPlay isEqualToString:#"ALL LEVELS"]){
[self performSegueWithIdentifier:#"MinimumNumberOfPlayers" sender:self];
} else if ([organizeLevelOfPlay isEqualToString:#"NOVICE"]){
[self.organizeDifficultyArray[2] setHighlighted:NO animated:YES]; //I get an error here.
[self.selectionArray removeObject:self.organizeDifficultyArray[2]];
[self.selectionArray addObject:organizeLevelOfPlay];
self.result = [[self.selectionArray valueForKey:#"description"] componentsJoinedByString:#"/"];
NSLog(#"%#", self.selectionArray);
} else if ([organizeLevelOfPlay isEqualToString:#"INTERMEDIATE"]) {
[self.selectionArray addObject:organizeLevelOfPlay];
self.result = [[self.selectionArray valueForKey:#"description"] componentsJoinedByString:#"/"];
NSLog(#"%#", self.selectionArray);
} else if ([organizeLevelOfPlay isEqualToString:#"PRO"]){
[self.organizeDifficultyArray[0] setHighlighted:NO animated:YES]; //I get an error here.
[self.selectionArray removeObject:self.organizeDifficultyArray[0]];
[self.selectionArray addObject:organizeLevelOfPlay];
self.result = [[self.selectionArray valueForKey:#"description"] componentsJoinedByString:#"/"];
NSLog(#"%#", self.selectionArray);
}}
try to use
-[tableView: deselectRowAtIndexPath:] function to replace the -[setHighlighted:NO animated:YES] one. #"NOVICE" and #"PRO" may be is indexpath{0,1} , indexpath{0,2}.
I'm expecting to get a little help with a UIButtons staying .hidden. I'm new to this site so please give me a min to best describe this problem I face.
Below is a picture of 2 UIButtons, in the middle of these UIButtons there is another one called OnRoute. Once the Acknowledged button is pressed it is hidden to which sends a status and reveals the OnRoute UIButton. Now the Acknowledged button is hidden you will only see on screen under the Runsheet button the OnRoute button to which you also press that sends a status and then hides it self.
Once these buttons are pressed you are sent to a UITableView and at this point all is well, but when you go back to the menu screen the buttons are reappear as if the buttons have not been pressed. And you can repeat over and over sending status.
The idea of this is to send a job status once the buttons are pressed which in turn shows on software on a server. Once these have been sent and the UIButtons hide for that job number, I would like to keep them hides until job has gone from hand set.
This is complex problem but if anyone has any ideas of this, I would really be thankful.
//This is in ViewDidLoad
self.onroute.hidden = YES;
NSNumber *num = [NSNumber numberWithInt:10.00];
self.acknow.hidden = YES;
if((self.consignment.cur_status_no < num) || [self.consignment.newjob isEqual:#(YES)]){
self.acknow.hidden = NO;
//This is in IBAction
- (IBAction)acknowledgebtn:(id)sender {
if (self.onroute.hidden == YES){
self.acknow.hidden = NO;
self.onroute.hidden = NO;
self.acknow.hidden = YES;
//and this is for the other IBAction
if (self.acknow.hidden == YES){
self.onroute.hidden = YES;
As I'm new to the site it will not let me post picture of UIButton sorry for this.
My suggestion would be to use some booleans instead of relying on the buttons hidden property. Then save the booleans when transferring to a new view. Then when you return to the main menu check the booleans and see what should be hidden and what should not be.
Also when I name variables I like to pretend that someone else will be looking at my code. So instead of just onroute as the button name, I would make it onrouteBut. This makes it a lot easier when I go back through my code as well so I know exactly what each variable is just by looking at the name.
As for the code I don't know how you are presenting views, so I can't really give a full answer. But I think this will help.
in your .h
#property (nonatomic) BOOL onrouteBool;
#property (nonatomic) BOOL acknowBool;
//whatever other bools you need instead of using button.hidden == YES/NO
in your .m
#synthesize onrouteBool, acknowBool;
-(void)viewDidLoad {
onrouteBut.hidden = YES;
onrouteBool = YES;
NSNumber *num = [NSNumber numberWithInt:10.00];
acknowBut.hidden = YES;
acknowBool = YES;
if((self.consignment.cur_status_no < num) || [self.consignment.newjob isEqual:#(YES)]) {
acknowBut.hidden = NO;
acknowBool = NO;
}
}
-(IBAction)acknowledgeBtn:(id)sender {
if (onrouteBool == YES) {
acknowBut.hidden = NO;
onrouteBut.hidden = NO;
acknowBool = NO;
onrouteBool = NO;
//this part doesn't make sense you set the button to visible and then hidden right after
acknowBut.hidden = YES;
acknowBool = YES;
}
}
-(IBAction)onrouteBtn:(id)sender {
if (acknowBool == YES) {
onrouteBut.hidden = YES;
onrouteBool = YES;
}
}
So now before you transition to your next view call this method to save the bools
-(void)saveTheBools {
//save the bools however you want before you transition the view
//one way is nsuserdefaults
[[NSUserDefaults standardUserDefaults]setBool:onrouteBool forKey:#"onrouteBool"];
[[NSUserDefaults standardUserDefaults]setBool:acknowBool forKey:#"acknowBool"];
[[NSUserDefaults standardUserDefaults]synchronize];
//how you save them
}
then when you transition back to the main menu check the bools to see if the buttons should be hidden
-(void)checkTheBools {
onrouteBool = [[NSUserDefaults standardUserDefaults] boolForKey:#"onrouteBool"];
acknowBool = [[NSUserDefaults standardUserDefaults] boolForKey:#"acknowBool"];
if (onrouteBool == YES) {
onrouteBut.hidden = YES;
}
else {
onrouteBut.hidden = NO;
}
if (acknowBool == YES) {
acknowBut.hidden = YES;
}
else {
acknowBut.hidden = NO;
}
//whatever else you need to hidden or make visible
}
This is all just to give you some ideas of what to do. Use what you need to make it work. This is how I would do it, I don't know if this is best way to do it but it's a starting point. I can't really give a specific answer without seeing all of your code, since I don't know how you're transitioning views, what you are initializing, retaining, etc.
Hope this helps you out, if not my bad. Just keep working at it and you'll find something that works for you eventually.
edit:
As for the status problem you are having I can't really help because I don't have the code to look at. I think it probably has to do with saving your variables so you can access them across classes. So like I showed you how to save the booleans and use them you probably will have to do something similar to check if the status has sent or not.
I suggested using nsuserdefaults because that is the easiest thing to do, however it is not the best to rely on that for saving all of your variables. You can also look into singletons, core data, or anything that will allow you to save the variables that you need across classes. You just have to find the way that works best for what you are trying to do.
The only way you are going to learn is to struggle at times, do some research, and try different things until you find a solution. Also take advantage of the resources apple provides you with as a developer. I think you will be able to figure this one out. Good luck
Just wanted to update anyone having this problem, I managed to fix this using doubleValue.
onroute.hidden = YES;
onrouteBool = YES;
NSNumber *num1 = [NSNumber numberWithDouble:10.00];
if(([self.consignment.cur_status_no doubleValue] < [num1 doubleValue] ) ) {
if([self.consignment.newjob isEqual:#(NO)]) {
onroute.hidden = NO;
onrouteBool = NO;
}
}
acknow.hidden = YES;
acknowBool = YES;
if([self.consignment.newjob isEqual:#(YES)]) {
acknow.hidden = NO;
acknowBool = NO;
}
Thanks again for all your help.
I've written a category on UIView that allows me to walk the view hierarchy:
UIView+Capture.h
typedef void(^MSViewInspectionBlock)(UIView *view, BOOL *stop);
#interface UIView (Capture)
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block;
#end
UIView+Capture.m
#implementation UIView (Capture)
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block
{
BOOL stop = NO;
[self inspectViewHeirarchy:block stop:stop];
}
#pragma - Private
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block stop:(BOOL)stop
{
if (!block || stop) {
return;
}
block(self, &stop);
for (UIView *view in self.subviews) {
[view inspectViewHeirarchy:block stop:stop];
if (stop) {
break;
}
}
}
#end
Which you can use like so:
[[[UIApplication sharedApplication] keyWindow] inspectViewHeirarchy:^(UIView *view, BOOL *stop) {
if ([view isMemberOfClass:[UIScrollView class]]) {
NSLog(#"Found scroll view!");
*stop = YES;
}
}];
Everything works fine, except setting stop to YES. This appears to have absolutely no effect whatsoever. Ideally, I'd like this to halt the recursion, so when I've found the view I want to take some action on I don't have to continue to traverse the rest of the view hierarchy.
I'm pretty dense when it comes to using blocks, so it may be something completely obvious. Any help will be greatly appreciated.
The way you're using a block is exactly the same as using a C function. So there's nothing special you really need to know about blocks. Your code should work but note the difference between passing stop as a BOOL * to your block and to create a new local when you recurse.
It looks like you're expecting calls down to inspectViewHierarchy:stop: to affect the outer stop variable. That won't happen unless you pass it as a reference. So I think what you want is:
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block stop:(BOOL *)stop
...and appropriate other changes.
I assume you want to return all the way out from the top-level inspectViewHierarchy when the user sets stop to YES.
(Incidentally, you spelled “hierarchy” wrong and you should use a prefix on methods you add to standard classes.)
#implementation UIView (Capture)
- (void)micpringle_visitSubviewsRecursivelyWithBlock:(MSViewInspectionBlock)block
{
BOOL stop = NO;
[self inspectViewHierarchy:block stop:&stop];
}
#pragma - Private
- (void)micpringle_visitSubviewsRecursivelyWithBlock:(MSViewInspectionBlock)block stop:(BOOL *)stop
{
block(self, stop);
if (*stop)
return;
for (UIView *view in self.subviews) {
[view micpringle_visitSubviewsRecursivelyWithBlock:block stop:stop];
if (*stop)
break;
}
}
#end
- (BOOL) inspectViewHeirarchy:(MSViewInspectionBlock)block
{
BOOL stop = NO;
block(self, &stop);
if (stop)
return YES;
for (UIView *view in self.subviews) {
if ([view inspectViewHeirarchy:block])
return YES;
}
return NO;
}
Try this:
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block
{
__block BOOL stop = NO;
[self inspectViewHeirarchy:block stop:stop];
}
Blocks, by nature, copy the variables and context in which they are declared.
Even though you are passing the boolean as a reference, it's possible that it's using a copy of the context and not the true stop.
This is just a wild guess but, inside inspectViewHierarchy:stop: do something like:
- (void)inspectViewHeirarchy:(MSViewInspectionBlock)block stop:(BOOL)stop
{
if (!block || stop) {
return;
}
// Add these changes
__block BOOL blockStop = stop;
block(self, &blockStop);
for (UIView *view in self.subviews) {
[view inspectViewHeirarchy:block stop:stop];
if (stop) {
break;
}
}
}
This may be a long shot and I'm not 100% sure it will work without having your project, but it's worth a shot.
Also, refactor your method so "heirarchy" is actually spelled "hierarchy" :] It's good for reusability and for keeping a good code base ;)
wouldn't you want to check the status of 'stop' directly after you invoke the block? It doesn't help to invoke it after you call inspectViewHierarchy:stop: because you are passing a copy of 'stop' to that method instead of the reference.
With the following setup
....
MyUIMenuItem *someAction = [[MyUIMenuItem alloc]initWithTitle : #"Something" action : #selector(menuItemSelected:)];
MyUIMenuItem *someAction2 = [[MyUIMenuItem alloc]initWithTitle : #"Something2" action : #selector(menuItemSelected:)];
....
- (IBAction) menuItemSelected : (id) sender
{
UIMenuController *mmi = (UIMenuController*) sender;
}
How to figure out which menu item was selected.
And don't say that you need to have two methods... Thanks in advance.
Okay, I've solved this one. The solution isn't pretty, and the better option is "Apple fixes the problem", but this at least works.
First of all, prefix your UIMenuItem action selectors with "magic_". And don't make corresponding methods. (If you can do that, then you don't need this solution anyway).
I'm building my UIMenuItems thus:
NSArray *buttons = [NSArray arrayWithObjects:#"some", #"random", #"stuff", nil];
NSMutableArray *menuItems = [NSMutableArray array];
for (NSString *buttonText in buttons) {
NSString *sel = [NSString stringWithFormat:#"magic_%#", buttonText];
[menuItems addObject:[[UIMenuItem alloc]
initWithTitle:buttonText
action:NSSelectorFromString(sel)]];
}
[UIMenuController sharedMenuController].menuItems = menuItems;
Now your class that catches the button tap messages needs a few additions. (In my case the class is a subclass of UITextField. Yours might be something else.)
First up, the method that we've all been wanting to have but that didn't exist:
- (void)tappedMenuItem:(NSString *)buttonText {
NSLog(#"They tapped '%#'", buttonText);
}
Then the methods that make it possible:
- (BOOL)canPerformAction:(SEL)action withSender:(id)sender {
NSString *sel = NSStringFromSelector(action);
NSRange match = [sel rangeOfString:#"magic_"];
if (match.location == 0) {
return YES;
}
return NO;
}
- (NSMethodSignature *)methodSignatureForSelector:(SEL)sel {
if ([super methodSignatureForSelector:sel]) {
return [super methodSignatureForSelector:sel];
}
return [super methodSignatureForSelector:#selector(tappedMenuItem:)];
}
- (void)forwardInvocation:(NSInvocation *)invocation {
NSString *sel = NSStringFromSelector([invocation selector]);
NSRange match = [sel rangeOfString:#"magic_"];
if (match.location == 0) {
[self tappedMenuItem:[sel substringFromIndex:6]];
} else {
[super forwardInvocation:invocation];
}
}
One would expect that the action associated with a given menu item would include a sender parameter that should point to the chosen menu item. Then you could simply examine the title of the item, or do as kforkarim suggests and subclass UIMenuItem to include a proeprty that you can use to identify the item. Unfortunately, according to this SO question, the sender parameter is always nil. That question is over a year old, so things may have changed -- take a look at what you get in that parameter.
Alternately, it looks like you'll need to a different action for each menu item. Of course, you could set it up so that all your actions call a common method, and if they all do something very similar that might make sense.
Turns out it's possible to obtain the UIButton object (which is actually UICalloutBarButton) that represents UIMenuItem if you subclass UIApplication and reimplement -sendAction:to:from:forEvent:. Although only -flash selector goes through UIApplication, it's enough.
#interface MyApplication : UIApplication
#end
#implementation MyApplication
- (BOOL)sendAction:(SEL)action to:(id)target from:(id)sender forEvent:(UIEvent *)event
{
// target == sender condition is just an additional one
if (action == #selector(flash) && target == sender && [target isKindOfClass:NSClassFromString(#"UICalloutBarButton")]) {
NSLog(#"pressed menu item title: %#", [(UIButton *)target titleLabel].text);
}
return [super sendAction:action to:target from:sender forEvent:event];
}
#end
You can save target (or any data you need from it) in e.g. property and access it later from your UIMenuItem's action.
And to make your UIApplication subclass work, you must pass its name as a third parameter to UIApplicationMain():
int main(int argc, char *argv[])
{
#autoreleasepool {
return UIApplicationMain(argc, argv, NSStringFromClass([MyApplication class]), NSStringFromClass([YOUR_APP_DELEGATE class]));
}
}
This solution works on iOS 5.x-7.0 as of post date (didn't test on older versions).
ort11, you might want to create a property of myuimenuitem and set some sort of Tag. Thay way the object of sender could be recognized by its tag it. In Ibaction then you can set a switch statement that can correspond to each sender.tag and work throught that logic. I guess thats the simplest way to go.