blob: e6adfd0bd1f839bef94af2568d5108d0fd89616c [file] [log] [blame]
yangsu@google.com59870452011-08-02 13:20:22 +00001#import "SkOptionsTableViewController.h"
2#include "SkEvent.h"
caryclark@google.com867cbd82012-09-20 15:45:41 +00003#include "SkTArray.h"
yangsu@google.com59870452011-08-02 13:20:22 +00004
5@implementation SkOptionItem
6@synthesize fCell, fItem;
7- (void)dealloc {
8 [fCell release];
9 [super dealloc];
10}
11@end
12
13@implementation SkOptionListItem
14@synthesize fOptions;
15- (void)dealloc {
16 [fOptions release];
17 [super dealloc];
18}
19@end
20
21@implementation SkOptionsTableViewController
22
23@synthesize fItems, fCurrentList;
24
25- (id)initWithStyle:(UITableViewStyle)style {
26 self = [super initWithStyle:style];
27 if (self) {
28 self.fItems = [NSMutableArray array];
29 }
30 return self;
31}
32
33//SkUIViewOptionsDelegate
34- (void) view:(SkUIView*)view didAddMenu:(const SkOSMenu*)menu {}
caryclark@google.com867cbd82012-09-20 15:45:41 +000035- (void) view:(SkUIView*)view didUpdateMenu:(SkOSMenu*)menu {
yangsu@google.com59870452011-08-02 13:20:22 +000036 [self updateMenu:menu];
37}
38
39- (NSUInteger)convertPathToIndex:(NSIndexPath*)path {
40 NSUInteger index = 0;
41 for (NSInteger i = 0; i < path.section; ++i) {
yangsu@google.comef7bdfa2011-08-12 14:27:47 +000042 index += (*fMenus)[i]->getCount();
yangsu@google.com59870452011-08-02 13:20:22 +000043 }
44 return index + path.row;
45}
46
47- (void)registerMenus:(const SkTDArray<SkOSMenu*>*)menus {
48 fMenus = menus;
49 for (NSUInteger i = 0; i < fMenus->count(); ++i) {
50 [self loadMenu:(*fMenus)[i]];
51 }
52}
53
54- (void)updateMenu:(SkOSMenu*)menu {
55 // the first menu is always assumed to be the static, the second is
56 // repopulated every time over and over again
57 int menuIndex = fMenus->find(menu);
58 if (menuIndex >= 0 && menuIndex < fMenus->count()) {
59 NSUInteger first = 0;
60 for (NSInteger i = 0; i < menuIndex; ++i) {
yangsu@google.comef7bdfa2011-08-12 14:27:47 +000061 first += (*fMenus)[i]->getCount();
yangsu@google.com59870452011-08-02 13:20:22 +000062 }
63 [fItems removeObjectsInRange:NSMakeRange(first, [fItems count] - first)];
64 [self loadMenu:menu];
65 }
66 [self.tableView reloadData];
67}
68
caryclark@google.com867cbd82012-09-20 15:45:41 +000069- (void)loadMenu:(SkOSMenu*)menu {
yangsu@google.comef7bdfa2011-08-12 14:27:47 +000070 const SkOSMenu::Item* menuitems[menu->getCount()];
71 menu->getItems(menuitems);
72 for (int i = 0; i < menu->getCount(); ++i) {
73 const SkOSMenu::Item* item = menuitems[i];
yangsu@google.com59870452011-08-02 13:20:22 +000074 NSString* title = [NSString stringWithUTF8String:item->getLabel()];
75
yangsu@google.com59870452011-08-02 13:20:22 +000076 if (SkOSMenu::kList_Type == item->getType()) {
yangsu@google.comf3493f02011-08-08 15:12:05 +000077 int value = 0;
yangsu@google.com59870452011-08-02 13:20:22 +000078 SkOptionListItem* List = [[SkOptionListItem alloc] init];
yangsu@google.comf3493f02011-08-08 15:12:05 +000079
yangsu@google.com59870452011-08-02 13:20:22 +000080 List.fItem = item;
81 List.fOptions = [[SkOptionListController alloc] initWithStyle:UITableViewStyleGrouped];
82
yangsu@google.comf3493f02011-08-08 15:12:05 +000083 int count = 0;
yangsu@google.comef7bdfa2011-08-12 14:27:47 +000084 SkOSMenu::FindListItemCount(*item->getEvent(), &count);
caryclark@google.com867cbd82012-09-20 15:45:41 +000085 SkTArray<SkString> options;
86 options.resize_back(count);
87 SkOSMenu::FindListItems(*item->getEvent(), &options.front());
yangsu@google.comf3493f02011-08-08 15:12:05 +000088 for (int i = 0; i < count; ++i)
89 [List.fOptions addOption:[NSString stringWithUTF8String:options[i].c_str()]];
yangsu@google.comef7bdfa2011-08-12 14:27:47 +000090 SkOSMenu::FindListIndex(*item->getEvent(), item->getSlotName(), &value);
yangsu@google.comf3493f02011-08-08 15:12:05 +000091
92 List.fOptions.fSelectedIndex = value;
yangsu@google.com59870452011-08-02 13:20:22 +000093 List.fCell = [self createList:title
94 default:[List.fOptions getSelectedOption]];
95 List.fOptions.fParentCell = List.fCell;
96 [fItems addObject:List];
97 [List release];
98 }
99 else {
100 SkOptionItem* option = [[SkOptionItem alloc] init];
101 option.fItem = item;
yangsu@google.comf3493f02011-08-08 15:12:05 +0000102
yangsu@google.com59870452011-08-02 13:20:22 +0000103 bool state = false;
yangsu@google.comf3493f02011-08-08 15:12:05 +0000104 SkString str;
105 SkOSMenu::TriState tristate;
yangsu@google.com59870452011-08-02 13:20:22 +0000106 switch (item->getType()) {
107 case SkOSMenu::kAction_Type:
108 option.fCell = [self createAction:title];
109 break;
110 case SkOSMenu::kSwitch_Type:
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000111 SkOSMenu::FindSwitchState(*item->getEvent(), item->getSlotName(), &state);
yangsu@google.com59870452011-08-02 13:20:22 +0000112 option.fCell = [self createSwitch:title default:(BOOL)state];
113 break;
114 case SkOSMenu::kSlider_Type:
115 SkScalar min, max, value;
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000116 SkOSMenu::FindSliderValue(*item->getEvent(), item->getSlotName(), &value);
117 SkOSMenu::FindSliderMin(*item->getEvent(), &min);
118 SkOSMenu::FindSliderMax(*item->getEvent(), &max);
yangsu@google.com59870452011-08-02 13:20:22 +0000119 option.fCell = [self createSlider:title
120 min:min
121 max:max
122 default:value];
123 break;
124 case SkOSMenu::kTriState_Type:
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000125 SkOSMenu::FindTriState(*item->getEvent(), item->getSlotName(), &tristate);
yangsu@google.comf3493f02011-08-08 15:12:05 +0000126 option.fCell = [self createTriState:title default:(int)tristate];
yangsu@google.com59870452011-08-02 13:20:22 +0000127 break;
128 case SkOSMenu::kTextField_Type:
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000129 SkOSMenu::FindText(*item->getEvent(), item->getSlotName(), &str);
yangsu@google.com59870452011-08-02 13:20:22 +0000130 option.fCell = [self createTextField:title
yangsu@google.comf3493f02011-08-08 15:12:05 +0000131 default:[NSString stringWithUTF8String:str.c_str()]];
yangsu@google.com59870452011-08-02 13:20:22 +0000132 break;
133 default:
134 break;
135 }
136 [fItems addObject:option];
137 [option release];
138 }
139 }
140}
141
142- (void)valueChanged:(id)sender {
143 UITableViewCell* cell = (UITableViewCell*)(((UIView*)sender).superview);
144 NSUInteger index = [self convertPathToIndex:[self.tableView indexPathForCell:cell]];
145 SkOptionItem* item = (SkOptionItem*)[fItems objectAtIndex:index];
146 if ([sender isKindOfClass:[UISlider class]]) {//Slider
147 UISlider* slider = (UISlider *)sender;
148 cell.detailTextLabel.text = [NSString stringWithFormat:@"%1.1f", slider.value];
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000149 item.fItem->setScalar(slider.value);
yangsu@google.com59870452011-08-02 13:20:22 +0000150 }
151 else if ([sender isKindOfClass:[UISwitch class]]) {//Switch
152 UISwitch* switch_ = (UISwitch *)sender;
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000153 item.fItem->setBool(switch_.on);
yangsu@google.com59870452011-08-02 13:20:22 +0000154 }
155 else if ([sender isKindOfClass:[UITextField class]]) { //TextField
156 UITextField* textField = (UITextField *)sender;
157 [textField resignFirstResponder];
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000158 item.fItem->setString([textField.text UTF8String]);
yangsu@google.com59870452011-08-02 13:20:22 +0000159 }
160 else if ([sender isKindOfClass:[UISegmentedControl class]]) { //Action
161 UISegmentedControl* segmented = (UISegmentedControl *)sender;
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000162 SkOSMenu::TriState state;
163 if (2 == segmented.selectedSegmentIndex) {
164 state = SkOSMenu::kMixedState;
165 } else {
166 state = (SkOSMenu::TriState)segmented.selectedSegmentIndex;
167 }
168 item.fItem->setTriState(state);
yangsu@google.com59870452011-08-02 13:20:22 +0000169 }
170 else{
171 NSLog(@"unknown");
172 }
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000173 item.fItem->postEvent();
yangsu@google.com59870452011-08-02 13:20:22 +0000174}
175
176- (UITableViewCell*)createAction:(NSString*)title {
177 UITableViewCell* cell = [[[UITableViewCell alloc]
178 initWithStyle:UITableViewCellStyleValue1
179 reuseIdentifier:nil] autorelease];
180 cell.textLabel.text = title;
181 return cell;
182}
183
184- (UITableViewCell*)createSwitch:(NSString*)title default:(BOOL)state {
185 UITableViewCell* cell = [[[UITableViewCell alloc]
186 initWithStyle:UITableViewCellStyleValue1
187 reuseIdentifier:nil] autorelease];
188 cell.textLabel.text = title;
189 cell.selectionStyle = UITableViewCellSelectionStyleNone;
190 UISwitch* switchView = [[UISwitch alloc] initWithFrame:CGRectZero];
191 [switchView setOn:state animated:NO];
192 [switchView addTarget:self
193 action:@selector(valueChanged:)
194 forControlEvents:UIControlEventValueChanged];
195 cell.accessoryView = switchView;
196 [switchView release];
197 return cell;
198}
199
200- (UITableViewCell*)createSlider:(NSString*)title
201 min:(float)min
202 max:(float)max
203 default:(float)value {
204 UITableViewCell* cell = [[[UITableViewCell alloc]
205 initWithStyle:UITableViewCellStyleValue1
206 reuseIdentifier:nil] autorelease];
207 cell.textLabel.text = title;
208 cell.selectionStyle = UITableViewCellSelectionStyleNone;
209 UISlider* sliderView = [[UISlider alloc] init];
210 sliderView.value = value;
211 sliderView.minimumValue = min;
212 sliderView.maximumValue = max;
213 [sliderView addTarget:self
214 action:@selector(valueChanged:)
215 forControlEvents:UIControlEventValueChanged];
216 cell.detailTextLabel.text = [NSString stringWithFormat:@"%1.1f", value];
217 cell.accessoryView = sliderView;
218 [sliderView release];
219 return cell;
220}
221
222- (UITableViewCell*)createTriState:(NSString*)title default:(int)index {
223 UITableViewCell* cell = [[[UITableViewCell alloc]
224 initWithStyle:UITableViewCellStyleValue1
225 reuseIdentifier:nil] autorelease];
226 cell.textLabel.text = title;
227 cell.selectionStyle = UITableViewCellSelectionStyleNone;
228 NSArray* items = [NSArray arrayWithObjects:@"Off", @"On", @"Mixed", nil];
229 UISegmentedControl* segmented = [[UISegmentedControl alloc] initWithItems:items];
230 segmented.selectedSegmentIndex = (index == -1) ? 2 : index;
231 segmented.segmentedControlStyle = UISegmentedControlStyleBar;
232 [segmented addTarget:self
233 action:@selector(valueChanged:)
234 forControlEvents:UIControlEventValueChanged];
235 cell.accessoryView = segmented;
236 [segmented release];
237 return cell;
238}
239
240- (UITableViewCell*)createTextField:(NSString*)title
yangsu@google.comf3493f02011-08-08 15:12:05 +0000241 default:(NSString*)value {
yangsu@google.com59870452011-08-02 13:20:22 +0000242 UITableViewCell* cell = [[[UITableViewCell alloc]
243 initWithStyle:UITableViewCellStyleValue1
244 reuseIdentifier:nil] autorelease];
245 cell.textLabel.text = title;
246 cell.selectionStyle = UITableViewCellSelectionStyleNone;
247 UITextField* textField = [[UITextField alloc]
248 initWithFrame:CGRectMake(0, 10, 150, 25)];
249 textField.adjustsFontSizeToFitWidth = YES;
robertphillips@google.comc94a9cc2013-03-28 18:03:27 +0000250 textField.textAlignment = NSTextAlignmentRight;
yangsu@google.com59870452011-08-02 13:20:22 +0000251 textField.textColor = cell.detailTextLabel.textColor;
yangsu@google.comf3493f02011-08-08 15:12:05 +0000252 textField.placeholder = value;
yangsu@google.com59870452011-08-02 13:20:22 +0000253 textField.returnKeyType = UIReturnKeyDone;
254 [textField addTarget:self
255 action:@selector(valueChanged:)
256 forControlEvents:UIControlEventEditingDidEndOnExit];
257 cell.accessoryView = textField;
258 [textField release];
259 return cell;
260}
261
262- (UITableViewCell*)createList:(NSString*)title default:(NSString*)value{
263 UITableViewCell* cell = [[[UITableViewCell alloc]
264 initWithStyle:UITableViewCellStyleValue1
265 reuseIdentifier:nil] autorelease];
266 cell.textLabel.text = title;
267 cell.accessoryType = UITableViewCellAccessoryDisclosureIndicator;
268 cell.detailTextLabel.text = value;
269 return cell;
270}
271
272#pragma mark -
273#pragma mark Table view data source
274
275- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView {
276 return fMenus->count();
277}
278
279- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section {
280 return [NSString stringWithUTF8String:(*fMenus)[section]->getTitle()];
281}
282
283- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section {
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000284 return (*fMenus)[section]->getCount();
yangsu@google.com59870452011-08-02 13:20:22 +0000285}
286
287- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath {
288 return ((SkOptionItem*)[fItems objectAtIndex:[self convertPathToIndex:indexPath]]).fCell;
289}
290
291#pragma mark -
292#pragma mark Table view delegate
293
294- (void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath {
295 UITableViewCell* cell = [tableView cellForRowAtIndexPath:indexPath];
yangsu@google.comf3493f02011-08-08 15:12:05 +0000296 id item = [fItems objectAtIndex:[self convertPathToIndex:indexPath]];
yangsu@google.com59870452011-08-02 13:20:22 +0000297
298 if ([item isKindOfClass:[SkOptionListItem class]]) {
299 SkOptionListItem* list = (SkOptionListItem*)item;
300 self.fCurrentList = list;
301 self.navigationController.delegate = self;
302 [self.navigationController pushViewController:list.fOptions animated:YES];
303 }
304 else if ([item isKindOfClass:[SkOptionItem class]]) {
305 if (UITableViewCellSelectionStyleNone != cell.selectionStyle) { //Actions
306 SkOptionItem* action = (SkOptionItem*)item;
307 action.fItem->postEvent();
308 }
309 }
310 else{
311 NSLog(@"unknown");
312 }
313
314 [self.tableView deselectRowAtIndexPath:indexPath animated:YES];
315}
316
317#pragma mark -
318#pragma mark Navigation controller delegate
319
320- (void)navigationController:(UINavigationController *)navigationController
321 willShowViewController:(UIViewController *)viewController
322 animated:(BOOL)animated {
323 if (self == viewController) { //when a List option is popped, trigger event
324 NSString* selectedOption = [fCurrentList.fOptions getSelectedOption];
325 fCurrentList.fCell.detailTextLabel.text = selectedOption;
yangsu@google.comef7bdfa2011-08-12 14:27:47 +0000326 fCurrentList.fItem->setInt(fCurrentList.fOptions.fSelectedIndex);
327 fCurrentList.fItem->postEvent();
yangsu@google.com59870452011-08-02 13:20:22 +0000328 }
329}
330
331#pragma mark -
332#pragma mark Memory management
333
334- (void)dealloc {
335 self.fItems = nil;
336 [super dealloc];
337}
338
339@end