Я хочу отключить кнопки в листе UIAction и включить их после того, как определенное условие будет истинным. Как мне это достичь? Есть идеи?iPhone Отключение кнопок UIActionSheet
ответ
Есть ли обстоятельства, которые могут измениться, в то время как лист действий открыт, что может привести к включению кнопки? Если нет, я думаю, что лучший подход состоит в том, чтобы изменить кнопки, отображаемые на экране в зависимости от вашего состояния.
В противном случае единственный способ справиться с этим состоит в том, чтобы перебирать подзоны листа, как сказал Крейг, и искать объекты UIButton
. Однако я был бы осторожен в использовании названия кнопки, потому что заголовок мог (и должен!) Быть локализован для разных языков. Таким образом, сравнение с заголовком не так надежно. Поскольку вы не создали кнопку, вы действительно не знаете, что будет tag
или action
каждой кнопки, так что это тоже сложно.
Предположительно, кнопки будут отображаться в subviews
массиве в том порядке, указанных им в UIActionSheet
, но так как это не документировано, нет никакой гарантии, что они будут появляться в таком порядке, или что они будут продолжать появляться в этом порядке в будущих выпусках Cocoa Touch SDK. Из-за этого, я бы не стал беспокоиться в основном о том, чтобы быть отвергнутым из App Store для использования недокументированных функций.
Вы не будете отклонены в App Store для этой процедуры. Всегда есть шанс, что Apple изменит порядок подсмотра, и ваше приложение может начать действовать странно, но это не тип «недокументированной функциональности», которую они запретят в магазине. –
Правда, это не то же самое, что частный API, но он является частным в том смысле, что он основан на эксперименте, а не на документации. Я бы очень рекомендовал против этого. Я не уверен, что Apple не откажется от него - соглашение дает им свободу действий в отказе от приложений по любой причине. – Alex
Если вы добавите представление в лист действий, представление не получит никакого события. Вам нужно просмотреть представление панели действий.
Ниже, как я добавил кнопку с сенсорным до события:
- (void)didPresentActionSheet:(UIActionSheet *)actionSheet{
CGRect rect = CGRectMake(0,0, 320, 480);
UIButton* anImage = [[UIButton alloc] init];
[anImage setTitle:@"GHello worl" forState:UIControlStateNormal];
[anImage setTitle:@"GHello worl dfasd" forState:UIControlStateHighlighted];
[anImage setTitle:@"GHello worl selected" forState:UIControlStateSelected];
//[anImage setBackgroundImage:[UIImage imageNamed:@"photo.png"] forState:UIControlStateNormal];
[anImage addTarget:self action:@selector(buttonClicked:) forControlEvents:UIControlEventTouchUpInside];
rect = CGRectMake(0,0, 320, 220);
anImage.frame =rect;
[actionSheet.superview addSubview:anImage];
[anImage release];
}
Я обнаружил, что ответ Крейга не работает для меня (на OS 3.1). Через некоторое копаться я обнаружил, что подвиды из UIActionSheet
фактически из незарегистрированной классаUIThreePartButton
Во всяком случае, это работает для меня (реализуется в рамках метода UIActionSheetDelegete
)
- (void)willPresentActionSheet:(UIActionSheet *)actionSheet // before animation and showing view
{
for (UIView* view in [actionSheet subviews])
{
if ([[[view class] description] isEqualToString:@"UIThreePartButton"])
{
if ([view respondsToSelector:@selector(title)])
{
NSString* title = [view performSelector:@selector(title)];
if ([title isEqualToString:@"Button 1"] && [view respondsToSelector:@selector(setEnabled:)])
{
[view performSelector:@selector(setEnabled:) withObject:NO];
}
}
}
}
}
Надежда, которая помогает кто-то еще, хотя я бы повторил вопрос Эд Марти о том, лучше ли вам просто убрать эти кнопки из листа действий, а не делать это. Как всегда при использовании недокументированных функций существует риск отклонения магазина приложений, хотя этот код написан неудачно изящно, если Apple снова включит API в будущей версии ОС.
Никогда не используйте 'description' для сравнения классов. Правильный способ - использовать use [[view isKindOfClass: NSClassFromString (@ "UIThreePartButton")]; ' – Kornel
Использование недокументированных классов, подобных этому, является верным способом отклонения при отправке в App Store. – PeyloW
UIActionSheet не предназначен для настройки. Он должен отображать фактический набор доступных опций. Он не должен изменять доступность кнопки во время сверху. Просто удалите неиспользуемые кнопки или воспользуйтесь нестандартным представлением.
У меня возникла аналогичная проблема, когда у меня был лист действий, который изменяется в зависимости от некоторых условий. Я опустил варианты, которые не применимы к файлу действий, но в некоторых случаях я получаю лист действий с одним выбором. Это кажется немного глупым, поскольку я мог бы активировать этот выбор немедленно, не отображая лист вообще.
Однако я также хочу, чтобы пользователи узнали, что нажатие определенной кнопки на экране дает им список вариантов, на которые они могут выбрать. Вот почему я хочу отображать лист действий и в тех случаях, когда у него есть только один выбор.Я думал об отключении неприменимых вариантов вместо того, чтобы опускать их с листа, но это тоже не понравилось.
Мой случай связан имеющий-значок пользователя в пользовательской нижней панели и нажатие на нее представлены следующие варианты:
- , если вход в
- Мой профиль
- Выезд
- если не вошли в
- Вход
Это, вероятно, немного поздно. Но, как я понял, создайте UIButton (s) и добавьте их в подпрограмму UIActionSheet. Убедитесь, что эти кнопки установлены сверху и полностью закрывают кнопку (ы) UIActionSheet по умолчанию для замены. Когда UIButton помещается над кнопкой UIActionSheet по умолчанию, ее UIResponder имеет приоритет над URIsponder кнопки UIActionSheet. Таким образом, вы можете отключить и включить эти кнопки, но вы бы хотели, чтобы в любом месте логики UIViewController. Это может быть альтернативой доступу к частным методам в SDK (например, выше - UIThreePartButton), и Apple может отклонить ваше приложение. Я считаю, что это следует принципам Apple.
i.e Настройка UIButtons для включения/выключения после определенных условий.
// Instantiate once within a method
if (self.actionSheet==nil) {
UIActionSheet *as = [[UIActionSheet alloc]
initWithTitle:@""
delegate:self
cancelButtonTitle:@"Cancel"
destructiveButtonTitle:@"Load Data"
otherButtonTitles:@"Update Data",nil];
//[actionSheet showInView:self.view];
self.loadUIButton.frame = CGRectMake(24.0f,25.0f,275.f,46.0f);
[as addSubview: self.loadUIButton];
self.updateUIButton.frame = CGRectMake(24.0f,78.0f,275.f,46.0f);
[as addSubview: self.updateUIButton];
//[actionSheet addSubview: self.cancelUIButton];
//[as showFromToolbar: self.navigationController.toolbar];
self.actionSheet = as;
[as release];
}
[self.actionSheet showFromToolbar: self.navigationController.toolbar];
ПРИМЕЧАНИЕ: Это отлично сработало в предыдущем приложении, которое я построил.
Вы можете попробовать [actionSheet valueForKey: "кнопки _" @] в вашем UIActionSheetDelegate так:
- (void)willPresentActionSheet:(UIActionSheet *)actionSheet
{
for (UIButton *btn in [actionSheet valueForKey:@"_buttons"])
{
[btn setBackgroundImage:[UIImage imageNamed:@"btnActionSheetUp.png"] forState:UIControlStateNormal];
[btn setBackgroundImage:[UIImage imageNamed:@"btnActionSheetDown.png"] forState:UIControlStateHighlighted];
}
}
Надеемся, что это привычка изменения в будущих версиях SDK.
Будет ли это отклонено? Если у вас много кнопок, UIActionSheet собирается установить свиток с кнопками, и тогда это не работает, вы знаете, как его решить? Спасибо! – Oscar
Я знаю, что трудно изменить чей-то разум, но вы уверены, что действительно хотите сделать это таким образом? Возможно, вместо этого вы хотите просто показать лист действий без отключенных кнопок, а когда какое-то условие истинно, покажите другое (при необходимости спрячьте другое) –
См. Альтернативный ответ, который я собираю из многочисленных источников в этом [SO ответ ] (http://stackoverflow.com/a/9380142/100017) – Reuven