Oolite 1.91.0.7708-250910-30bbc4c
Loading...
Searching...
No Matches
GuiDisplayGen.m
Go to the documentation of this file.
1/*
2
3GuiDisplayGen.m
4
5Oolite
6Copyright (C) 2004-2013 Giles C Williams and contributors
7
8This program is free software; you can redistribute it and/or
9modify it under the terms of the GNU General Public License
10as published by the Free Software Foundation; either version 2
11of the License, or (at your option) any later version.
12
13This program is distributed in the hope that it will be useful,
14but WITHOUT ANY WARRANTY; without even the implied warranty of
15MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16GNU General Public License for more details.
17
18You should have received a copy of the GNU General Public License
19along with this program; if not, write to the Free Software
20Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
21MA 02110-1301, USA.
22
23*/
24
25#import "GuiDisplayGen.h"
26#import "Universe.h"
27#import "GameController.h"
28#import "PlayerEntity.h"
30#import "OOTextureSprite.h"
31#import "ResourceManager.h"
32#import "OOSound.h"
33#import "OOStringExpander.h"
34#import "OOStringParsing.h"
35#import "HeadUpDisplay.h"
37#import "OOTexture.h"
41
42OOINLINE BOOL RowInRange(OOGUIRow row, NSRange range)
43{
44 return ((int)range.location <= row && row < (int)(range.location + range.length));
45}
46
47@interface GuiDisplayGen (Internal)
48
49- (void) drawGLDisplay:(GLfloat)x :(GLfloat)y :(GLfloat)z :(GLfloat) alpha;
50
51- (void) drawCrossHairsWithSize:(GLfloat) size x:(GLfloat)x y:(GLfloat)y z:(GLfloat)z;
52- (void) drawStarChart:(GLfloat)x :(GLfloat)y :(GLfloat)z :(GLfloat) alpha :(BOOL) compact;
53- (void) drawSystemMarkers:(NSArray *)marker atX:(GLfloat)x andY:(GLfloat)y andZ:(GLfloat)z withAlpha:(GLfloat)alpha andScale:(GLfloat)scale;
54- (void) drawSystemMarker:(NSDictionary *)marker atX:(GLfloat)x andY:(GLfloat)y andZ:(GLfloat)z withAlpha:(GLfloat)alpha andScale:(GLfloat)scale;
55
56- (void) drawEquipmentList:(NSArray *)eqptList z:(GLfloat)z;
57- (void) drawAdvancedNavArrayAtX:(float)x y:(float)y z:(float)z alpha:(float)alpha usingRoute:(NSDictionary *) route optimizedBy:(OORouteType) optimizeBy zoom: (OOScalar) zoom;
58
59@end
60
61
62@implementation GuiDisplayGen
63
64static BOOL _refreshStarChart = NO;
65
66- (id) init
67{
68 if ((self = [super init]))
69 {
75 pixel_row_start = MAIN_GUI_PIXEL_ROW_START; // first position down the page...
76 max_alpha = 1.0;
77
78 pixel_text_size = NSMakeSize(0.9f * pixel_row_height, pixel_row_height); // main gui has 18x20 characters
79
80 pixel_title_size = NSMakeSize(pixel_row_height * 1.75f, pixel_row_height * 1.5f);
81
82 int stops[6] = {0, 192, 256, 320, 384, 448};
83 unsigned i;
84
85 rowRange = NSMakeRange(0,n_rows);
86
87 rowText = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
88 rowKey = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
89 rowColor = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
90
91 for (i = 0; i < n_rows; i++)
92 {
93 [rowText addObject:@"."];
94 [rowKey addObject:[NSString stringWithFormat:@"%d",i]];
95 [rowColor addObject:[OOColor yellowColor]];
96 rowPosition[i].x = 0.0f;
99 }
100
101 for (i = 0; i < n_columns; i++)
102 {
103 tabStops[i] = stops[i];
104 }
105
106 title = @"";
107
108 textColor = [[OOColor yellowColor] retain];
109
110 drawPosition = make_vector(0.0f, 0.0f, 640.0f);
111
113
114 guiUserSettings = [[ResourceManager dictionaryFromFilesNamed:@"gui-settings.plist" inFolder:@"Config" andMerge:YES] retain];
115 }
116 return self;
117}
118
119
120- (id) initWithPixelSize:(NSSize)gui_size
121 columns:(int)gui_cols
122 rows:(int)gui_rows
123 rowHeight:(int)gui_row_height
124 rowStart:(int)gui_row_start
125 title:(NSString*)gui_title
126{
127 self = [super init];
128
129 size_in_pixels = gui_size;
130 n_columns = gui_cols;
131 n_rows = gui_rows;
133 pixel_row_height = gui_row_height;
134 pixel_row_start = gui_row_start; // first position down the page...
135 max_alpha = 1.0;
136
138
139 pixel_title_size = NSMakeSize(pixel_row_height * 1.75f, pixel_row_height * 1.5f);
140
141 unsigned i;
142
143 rowRange = NSMakeRange(0,n_rows);
144
145 rowText = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
146 rowKey = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
147 rowColor = [[NSMutableArray alloc] initWithCapacity:n_rows]; // alloc retains
148
149 for (i = 0; i < n_rows; i++)
150 {
151 [rowText addObject:@""];
152 [rowKey addObject:@""];
153 [rowColor addObject:[OOColor greenColor]];
154 rowPosition[i].x = 0.0f;
157 }
158
159 title = [gui_title retain];
160
161 textColor = [[OOColor yellowColor] retain];
162
163 return self;
164}
165
166
167- (void) dealloc
168{
169 [backgroundSprite release];
170 [foregroundSprite release];
171 [backgroundColor release];
172 [textColor release];
173 [title release];
174 [rowText release];
175 [rowKey release];
176 [rowColor release];
177 [guiUserSettings release];
178
179 [super dealloc];
180}
181
182
183- (void) resizeWithPixelSize:(NSSize)gui_size
184 columns:(int)gui_cols
185 rows:(int)gui_rows
186 rowHeight:(int)gui_row_height
187 rowStart:(int)gui_row_start
188 title:(NSString*) gui_title
189{
190 [self clear];
191 //
192 size_in_pixels = gui_size;
193 n_columns = gui_cols;
194 n_rows = gui_rows;
196 pixel_row_height = gui_row_height;
197 pixel_row_start = gui_row_start; // first position down the page...
198
200 pixel_title_size = NSMakeSize(pixel_row_height * 1.75f, pixel_row_height * 1.5f);
201
202 rowRange = NSMakeRange(0,n_rows);
203 [self clear];
204 //
205 [self setTitle: gui_title];
206}
207
208
209- (void) resizeTo:(NSSize)gui_size
210 characterHeight:(int)csize
211 title:(NSString*)gui_title
212{
213 [self clear];
214 //
215 size_in_pixels = gui_size;
216 n_columns = gui_size.width / csize;
217 n_rows = (int)gui_size.height / csize;
218
219 [self setTitle: gui_title];
220
221 pixel_row_center = gui_size.width / 2;
222 pixel_row_height = csize;
223 currentRow = n_rows - 1; // first position down the page...
224
225 if (title != nil)
226 pixel_row_start = 2.75f * csize + 0.5f * (gui_size.height - n_rows * csize);
227 else
228 pixel_row_start = csize + 0.5f * (gui_size.height - n_rows * csize);
229
230 [rowText removeAllObjects];
231 [rowKey removeAllObjects];
232 [rowColor removeAllObjects];
233
234 unsigned i;
235 for (i = 0; i < n_rows; i++)
236 {
237 [rowText addObject:@""];
238 [rowKey addObject:@""];
239 [rowColor addObject:[OOColor greenColor]];
240 rowPosition[i].x = 0.0f;
243 }
244
245 pixel_text_size = NSMakeSize(csize, csize);
246 pixel_title_size = NSMakeSize(csize * 1.75f, csize * 1.5f);
247
248 OOLog(@"gui.reset", @"gui %@ reset to rows:%d columns:%d start:%d", self, n_rows, n_columns, pixel_row_start);
249
250 rowRange = NSMakeRange(0,n_rows);
251 [self clear];
252}
253
254
255- (NSSize)size
256{
257 return size_in_pixels;
258}
259
260
261- (unsigned)columns
262{
263 return n_columns;
264}
265
266
267- (unsigned)rows
268{
269 return n_rows;
270}
271
272
273- (unsigned)rowHeight
274{
275 return pixel_row_height;
276}
277
278
280{
281 return pixel_row_start;
282}
283
284
285- (NSString *)title
286{
287 return title;
288}
289
290
291- (void) setTitle:(NSString *)str
292{
293 if (str != title)
294 {
295 [title release];
296 if ([str length] == 0) str = nil;
297 title = [str copy];
298 }
299}
300
301
302- (void) setDrawPosition:(Vector) vector
303{
304 drawPosition = vector;
305}
306
307
308- (Vector) drawPosition
309{
310 return drawPosition;
311}
312
313
314- (NSDictionary *) userSettings
315{
316 return guiUserSettings;
317}
318
319
320- (void) fadeOutFromTime:(OOTimeAbsolute) now_time overDuration:(OOTimeDelta) duration
321{
322 if (fade_alpha <= 0.0f)
323 {
324 return;
325 }
326 if (duration == 0.0)
327 fade_sign = -1000.0f;
328 else
329 fade_sign = (float)(-fade_alpha / duration);
330}
331
332
334{
335 fade_sign = 0.0f;
336}
337
338
339- (GLfloat) alpha
340{
341 return fade_alpha;
342}
343
344
345- (void) setAlpha:(GLfloat) an_alpha
346{
347 fade_alpha = an_alpha * max_alpha;
348}
349
350
351- (void) setMaxAlpha:(GLfloat) an_alpha
352{
353 max_alpha = an_alpha;
354}
355
356
357- (void) setBackgroundColor:(OOColor*) color
358{
359 [backgroundColor release];
360 backgroundColor = [color retain];
361}
362
363
365{
366 return textColor;
367}
368
369
370// default text colour for rows
371- (void) setTextColor:(OOColor*) color
372{
373 [textColor release];
374 if (color == nil) color = [[OOColor yellowColor] retain];
375 textColor = [color retain];
376}
377
378
380{
381 return textCommsColor;
382}
383
384
385- (void) setTextCommsColor:(OOColor*) color
386{
387 [textCommsColor release];
388 if (color == nil) color = [[OOColor yellowColor] retain];
389 textCommsColor = [color retain];
390}
391
392
393- (OOColor *) colorFromSetting:(NSString *)setting defaultValue:(OOColor *)def
394{
395
396 OOColor *col = nil;
397 if (setting != nil) {
398 col = [OOColor colorWithDescription:[guiUserSettings objectForKey:setting]];
399 }
400 if (col == nil) {
401 if (def != nil) {
402 col = def;
403 // def = nil => use default_text_color
404 } else {
405 col = textColor;
406 }
407 }
408 return [[col copy] autorelease];
409}
410
411
412- (void) setGLColorFromSetting:(NSString *)setting defaultValue:(OOColor *)def alpha:(GLfloat)alpha
413{
414 GLfloat r,g,b,a;
415 OOColor *col = [self colorFromSetting:setting defaultValue:def];
416 [col getRed:&r green:&g blue:&b alpha:&a];
417
418 OOGL(glColor4f(r, g, b, a*alpha));
419}
420
421
422- (void) setGuiColorSettingFromKey:(NSString *)key color:(OOColor *)col
423{
424 NSMutableDictionary *guiCopy = [guiUserSettings mutableCopy];
425 if (col == nil)
426 {
427 [guiCopy removeObjectForKey:key];
428 }
429 else
430 {
431 [guiCopy setObject:col forKey:key];
432 }
433 [guiUserSettings release];
434 guiUserSettings = [guiCopy copy];
435 [guiCopy release];
436}
437
438
439- (void) setCharacterSize:(NSSize) character_size
440{
441 pixel_text_size = character_size;
442}
443
444
445- (void)setShowAdvancedNavArray:(BOOL)inFlag
446{
447 showAdvancedNavArray = inFlag;
448}
449
450
451- (void) setColor:(OOColor *) color forRow:(OOGUIRow)row
452{
453 if (RowInRange(row, rowRange))
454 [rowColor replaceObjectAtIndex:row withObject:color];
455}
456
457
458- (id) objectForRow:(OOGUIRow)row
459{
460 if (RowInRange(row, rowRange))
461 return [rowText objectAtIndex:row];
462 else
463 return NULL;
464}
465
466
467- (OOGUIRow) rowForKey:(NSString*)key
468{
469 for (unsigned i=0;i<[rowKey count];i++)
470 {
471 if ([key isEqualToString:[rowKey objectAtIndex:i]])
472 {
473 return (OOGUIRow)i;
474 }
475 }
476 return -1;
477}
478
479
480- (NSString*) keyForRow:(OOGUIRow)row
481{
482 if (RowInRange(row, rowRange))
483 return [rowKey objectAtIndex:row];
484 else
485 return NULL;
486}
487
488
490{
492 return selectedRow;
493 else
494 return -1;
495}
496
497
498- (BOOL) setSelectedRow:(OOGUIRow)row
499{
500 if ((row == selectedRow) && RowInRange(row, selectableRange))
501 {
502 return YES;
503 }
504 if (RowInRange(row, selectableRange))
505 {
506 if (![[rowKey objectAtIndex:row] isEqual:GUI_KEY_SKIP])
507 {
508 selectedRow = row;
509 [self reportSelectedRow:row];
510 return YES;
511 }
512 }
513 return NO;
514}
515
516
517- (BOOL) setNextRow:(int) direction
518{
519 OOGUIRow row = selectedRow + direction;
520 while (RowInRange(row, selectableRange))
521 {
522 if (![[rowKey objectAtIndex:row] isEqual:GUI_KEY_SKIP])
523 {
524 selectedRow = row;
525 [self reportSelectedRow:row];
526 return YES;
527 }
528 row += direction;
529 }
530 return NO;
531}
532
533
535{
536 NSUInteger row = selectableRange.location;
537 while (RowInRange(row, selectableRange))
538 {
539 if (![[rowKey objectAtIndex:row] isEqual:GUI_KEY_SKIP])
540 {
541 selectedRow = row;
542 [self reportSelectedRow:row];
543 return YES;
544 }
545 row++;
546 }
547 selectedRow = -1;
548 return NO;
549}
550
551
553{
554 NSUInteger row = selectableRange.location + selectableRange.length - 1;
555 while (RowInRange(row, selectableRange))
556 {
557 if (![[rowKey objectAtIndex:row] isEqual:GUI_KEY_SKIP])
558 {
559 selectedRow = row;
560 [self reportSelectedRow:row];
561 return YES;
562 }
563 row--;
564 }
565 selectedRow = -1;
566 return NO;
567}
568
569
570- (void) reportSelectedRow:(int) row
571{
572 [PLAYER doScriptEvent:OOJSID("guiSelectedRowChanged") withArguments:[NSArray arrayWithObjects:[self keyForRow:row], [NSNumber numberWithInt:row], [self selectedRowText], nil]];
573}
574
575
577{
578 selectedRow = -1;
579}
580
581
582- (NSString *) selectedRowText
583{
584 if ([[rowText objectAtIndex:selectedRow] isKindOfClass:[NSString class]])
585 return (NSString *)[rowText objectAtIndex:selectedRow];
586 if ([[rowText objectAtIndex:selectedRow] isKindOfClass:[NSArray class]])
587 return (NSString *)[[rowText objectAtIndex:selectedRow] objectAtIndex:0];
588 return NULL;
589}
590
591
592- (NSString *) selectedRowKey
593{
594 if ((selectedRow < 0)||((unsigned)selectedRow > [rowKey count]))
595 return nil;
596 else
597 return (NSString *)[rowKey objectAtIndex:selectedRow];
598}
599
600
601- (void) setShowTextCursor:(BOOL) yesno
602{
603 showTextCursor = yesno;
604}
605
606
607- (void) setCurrentRow:(OOGUIRow) value
608{
609 if ((value < 0)||((unsigned)value >= n_rows))
610 {
611 showTextCursor = NO;
612 currentRow = -1;
613 }
614 else
615 {
616 currentRow = value;
617 }
618}
619
620
622{
623 return selectableRange;
624}
625
626
627- (void) setSelectableRange:(NSRange) range
628{
629 selectableRange = range;
630}
631
632
633- (void) setTabStops:(OOGUITabSettings)stops
634{
635 if (stops != NULL) memmove(tabStops, stops, sizeof tabStops);
636}
637
638- (void) overrideTabs:(OOGUITabSettings)stops from:(NSString *)setting length:(NSUInteger)len
639{
640 NSArray *override = [guiUserSettings oo_arrayForKey:setting defaultValue:nil];
641 NSUInteger i;
642 if (stops != NULL && override != nil)
643 {
644 if (len > GUI_MAX_COLUMNS)
645 {
646 len = GUI_MAX_COLUMNS;
647 }
648 for (i=0;i<len;i++)
649 {
650 stops[i] = [override oo_unsignedIntegerAtIndex:i defaultValue:stops[i]];
651 }
652 }
653}
654
655
656- (void) clear
657{
658 [self clearAndKeepBackground:NO];
659}
660
661
662- (void) clearAndKeepBackground:(BOOL)keepBackground
663{
664 unsigned i;
665 [self setTitle: nil];
666 for (i = 0; i < n_rows; i++)
667 {
668 [self setText:@"" forRow:i align:GUI_ALIGN_LEFT];
669 [self setColor:textColor forRow:i];
670 //
671 [self setKey:GUI_KEY_SKIP forRow:i];
672 //
673 rowFadeTime[i] = 0.0f;
674 }
675 [self setShowTextCursor:NO];
676 [self setSelectableRange:NSMakeRange(0,0)];
677 if (!keepBackground) [self clearBackground];
678}
679
680
681- (void) setKey:(NSString *)str forRow:(OOGUIRow)row
682{
683 if (RowInRange(row, rowRange))
684 [rowKey replaceObjectAtIndex:row withObject:str];
685}
686
687
688- (void) setText:(NSString *)str forRow:(OOGUIRow)row
689{
690 if (RowInRange(row, rowRange))
691 {
692 [rowText replaceObjectAtIndex:row withObject:str];
693 }
694}
695
696
697- (void) setText:(NSString *)str forRow:(OOGUIRow)row align:(OOGUIAlignment)alignment
698{
699 if (str != nil && RowInRange(row, rowRange))
700 {
701 [rowText replaceObjectAtIndex:row withObject:str];
702 rowAlignment[row] = alignment;
703 }
704}
705
706
707- (OOGUIRow) addLongText:(NSString *)str
708 startingAtRow:(OOGUIRow)row
709 align:(OOGUIAlignment)alignment
710{
711
712 if ([str rangeOfString:@"\n"].location != NSNotFound)
713 {
714 NSArray *lines = [str componentsSeparatedByString:@"\n"];
715 unsigned i;
716 for (i = 0; i < [lines count]; i++)
717 {
718 row = [self addLongText:[lines oo_stringAtIndex:i] startingAtRow:row align:alignment];
719 }
720 return row;
721 }
722
723 NSSize chSize = pixel_text_size;
724 NSSize strsize = OORectFromString(str, 0.0f, 0.0f, chSize).size;
725 if (strsize.width < size_in_pixels.width)
726 {
727 [self setText:str forRow:row align:alignment];
728 return row + 1;
729 }
730 else
731 {
732 NSMutableArray *words = ScanTokensFromString(str);
733 NSMutableString *string1 = [NSMutableString stringWithCapacity:256];
734 NSMutableString *string2 = [NSMutableString stringWithCapacity:256];
735 strsize.width = 0.0f;
736 while ((strsize.width < size_in_pixels.width)&&([words count] > 0))
737 {
738 [string1 appendString:(NSString *)[words objectAtIndex:0]];
739 [string1 appendString:@" "];
740 [words removeObjectAtIndex:0];
741 strsize = OORectFromString(string1, 0.0f, 0.0f, chSize).size;
742 if ([words count] > 0)
743 strsize.width += OORectFromString((NSString *)[words objectAtIndex:0], 0.0f, 0.0f, chSize).size.width;
744 }
745 [string2 appendString:[words componentsJoinedByString:@" "]];
746 [self setText:string1 forRow:row align:alignment];
747 return [self addLongText:string2 startingAtRow:row+1 align:alignment];
748 }
749}
750
751
752- (NSString *) reflowTextForMFD:(NSString *)input
753{
754 NSMutableString *output = [[NSMutableString alloc] initWithCapacity:512];
755 NSArray *lines = [input componentsSeparatedByString:@"\n"];
756 NSSize chSize = pixel_text_size;
757 NSUInteger limit = chSize.width * 15;
758 NSString *line = nil;
759 foreach (line, lines)
760 {
761 NSMutableArray *words = ScanTokensFromString(line);
762 NSMutableString *accum = [NSMutableString stringWithCapacity:64];
763 if ([words count] > 0)
764 {
765 while ([words count] > 1)
766 {
767 [accum appendString:[words oo_stringAtIndex:0]];
768 [accum appendString:@" "];
769 if (OORectFromString(accum, 0.0f, 0.0f,chSize).size.width + OORectFromString([words oo_stringAtIndex:1], 0.0f, 0.0f,chSize).size.width > limit)
770 {
771 // can't fit next word on this line
772 [output appendString:[accum stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]]];
773 [output appendString:@"\n"];
774 [accum setString:@""];
775 }
776 [words removeObjectAtIndex:0];
777 }
778 [output appendString:accum];
779 [output appendString:[words oo_stringAtIndex:0]];
780 }
781 [output appendString:@"\n"];
782 }
783
784 return [output autorelease];
785}
786
787
789{
790 unsigned i;
791 for (i=0; i < n_rows-1; i++)
792 {
793 [rowText replaceObjectAtIndex:i withObject:@""];
794 [rowColor replaceObjectAtIndex:i withObject:textColor];
795 [rowKey replaceObjectAtIndex:i withObject:@""];
797 rowFadeTime[i] = 0.0f;
798 }
799 rowFadeTime[i] = 0.4f; // fade the last line...
800}
801
802
803- (NSArray *) getLastLines // text, colour, fade time - text, colour, fade time
804{
805 if (n_rows <1) return nil;
806
807 // we have at least 1 row!
808
809 unsigned i = n_rows-1;
810 OORGBAComponents col = [(OOColor *)[rowColor objectAtIndex:i] rgbaComponents];
811
812 if (i>0)
813 {
814 // we have at least 2 rows!
815 OORGBAComponents col0 = [(OOColor *)[rowColor objectAtIndex:i-1] rgbaComponents];
816 return [NSArray arrayWithObjects:[rowText oo_stringAtIndex:i-1],
817 [NSString stringWithFormat:@"%.3g %.3g %.3g %.3g", col0.r, col0.g, col0.b, col0.a],
818 [NSNumber numberWithFloat:rowFadeTime[i-1]],
819 [rowText oo_stringAtIndex:i],
820 [NSString stringWithFormat:@"%.3g %.3g %.3g %.3g", col.r, col.g, col.b, col.a],
821 [NSNumber numberWithFloat:rowFadeTime[i]], nil];
822 }
823 else
824 {
825 return [NSArray arrayWithObjects:[rowText oo_stringAtIndex:i],
826 [NSString stringWithFormat:@"%.3g %.3g %.3g %.3g", col.r, col.g, col.b, col.a],
827 [NSNumber numberWithFloat:rowFadeTime[i]], nil];
828 }
829}
830
831
832- (void) printLongText:(NSString *)str
833 align:(OOGUIAlignment) alignment
834 color:(OOColor *)text_color
835 fadeTime:(float)text_fade
836 key:(NSString *)text_key
837 addToArray:(NSMutableArray *)text_array
838{
839 // print a multi-line message
840 //
841 if ([str rangeOfString:@"\n"].location != NSNotFound)
842 {
843 NSArray *lines = [str componentsSeparatedByString:@"\n"];
844 unsigned i;
845 for (i = 0; i < [lines count]; i++)
846 [self printLongText:[lines oo_stringAtIndex:i] align:alignment color:text_color fadeTime:text_fade key:text_key addToArray:text_array];
847 return;
848 }
849
850 OOGUIRow row = currentRow;
851 if (row == (OOGUIRow)n_rows - 1)
852 [self scrollUp:1];
853 NSSize chSize = pixel_text_size;
854 NSSize strsize = OORectFromString(str, 0.0f, 0.0f, chSize).size;
855 if (strsize.width < size_in_pixels.width)
856 {
857 [self setText:str forRow:row align:alignment];
858 if (text_color)
859 [self setColor:text_color forRow:row];
860 if (text_key)
861 [self setKey:text_key forRow:row];
862 rowFadeTime[row] = text_fade;
863 if (currentRow < (OOGUIRow)n_rows - 1)
864 currentRow++;
865 if (text_array)
866 [text_array addObject:str];
867 }
868 else
869 {
870 NSMutableArray *words = ScanTokensFromString(str);
871 NSMutableString *string1 = [NSMutableString stringWithCapacity:256];
872 NSMutableString *string2 = [NSMutableString stringWithCapacity:256];
873 strsize.width = 0.0f;
874 while ((strsize.width < size_in_pixels.width)&&([words count] > 0))
875 {
876 [string1 appendString:(NSString *)[words objectAtIndex:0]];
877 [string1 appendString:@" "];
878 [words removeObjectAtIndex:0];
879 strsize = OORectFromString(string1, 0.0f, 0.0f, chSize).size;
880 if ([words count] > 0)
881 strsize.width += OORectFromString([words oo_stringAtIndex:0], 0.0f, 0.0f, chSize).size.width;
882 }
883
884 [self setText:string1 forRow:row align:alignment];
885
886 [string2 appendString:[words componentsJoinedByString:@" "]];
887 if (text_color)
888 [self setColor:text_color forRow:row];
889 if (text_key)
890 [self setKey:text_key forRow:row];
891 if (text_array)
892 [text_array addObject:string1];
893 rowFadeTime[row] = text_fade;
894 [self printLongText:string2 align:alignment color:text_color fadeTime:text_fade key:text_key addToArray:text_array];
895 }
896}
897
898
899- (void) printLineNoScroll:(NSString *)str
900 align:(OOGUIAlignment)alignment
901 color:(OOColor *)text_color
902 fadeTime:(float)text_fade
903 key:(NSString *)text_key
904 addToArray:(NSMutableArray *)text_array
905{
906 [self setText:str forRow:currentRow align:alignment];
907 if (text_color)
908 [self setColor:text_color forRow:currentRow];
909 if (text_key)
910 [self setKey:text_key forRow:currentRow];
911 if (text_array)
912 [text_array addObject:str];
913 rowFadeTime[currentRow] = text_fade;
914}
915
916
917- (void) setArray:(NSArray *)arr forRow:(OOGUIRow)row
918{
919 if (RowInRange(row, rowRange))
920 [rowText replaceObjectAtIndex:row withObject:arr];
921}
922
923
924- (void) insertItemsFromArray:(NSArray *)items
925 withKeys:(NSArray *)item_keys
926 intoRow:(OOGUIRow)row
927 color:(OOColor *)text_color
928{
929 if (!items)
930 return;
931 if([items count] == 0)
932 return;
933
934 NSUInteger n_items = [items count];
935 if ((item_keys)&&([item_keys count] != n_items))
936 {
937 // throw exception
938 [NSException raise:@"ArrayLengthMismatchException"
939 format:@"The NSArray sent as 'item_keys' to insertItemsFromArray::: must contain the same number of objects as the NSArray 'items'"];
940 }
941
942 unsigned i;
943 for (i = n_rows; i >= row + n_items ; i--)
944 {
945 [self setKey:[self keyForRow:i - n_items] forRow:i];
946 id old_row_info = [self objectForRow:i - n_items];
947 if ([old_row_info isKindOfClass:[NSArray class]])
948 [self setArray:old_row_info forRow:i];
949 if ([old_row_info isKindOfClass:[NSString class]])
950 [self setText:(NSString *)old_row_info forRow:i];
951 }
952 for (i = 0; i < n_items; i++)
953 {
954 id new_row_info = [items objectAtIndex:i];
955 if (text_color)
956 [self setColor:text_color forRow: row + i];
957 else
958 [self setColor:textColor forRow: row + i];
959 if ([new_row_info isKindOfClass:[NSArray class]])
960 [self setArray:new_row_info forRow: row + i];
961 if ([new_row_info isKindOfClass:[NSString class]])
962 [self setText:(NSString *)new_row_info forRow: row + i];
963 if (item_keys)
964 [self setKey:[item_keys objectAtIndex:i] forRow: row + i];
965 else
966 [self setKey:@"" forRow: row + i];
967 }
968}
969
970
971- (void) scrollUp:(int) how_much
972{
973 unsigned i;
974 for (i = 0; i + how_much < n_rows; i++)
975 {
976 [rowText replaceObjectAtIndex:i withObject:[rowText objectAtIndex: i + how_much]];
977 [rowColor replaceObjectAtIndex:i withObject:[rowColor objectAtIndex: i + how_much]];
978 [rowKey replaceObjectAtIndex:i withObject:[rowKey objectAtIndex: i + how_much]];
979 rowAlignment[i] = rowAlignment[i + how_much];
980 rowFadeTime[i] = rowFadeTime[i + how_much];
981 }
982 for (; i < n_rows; i++)
983 {
984 [rowText replaceObjectAtIndex:i withObject:@""];
985 [rowColor replaceObjectAtIndex:i withObject:textColor];
986 [rowKey replaceObjectAtIndex:i withObject:@""];
988 rowFadeTime[i] = 0.0f;
989 }
990}
991
992
994{
997}
998
999
1000static OOTexture *TextureForGUITexture(NSDictionary *descriptor)
1001{
1002 /*
1003 GUI textures like backgrounds, foregrounds etc. are not processed in any way after loading. However, they are
1004 subject to tone nmapping and gamma correction at the end of the render pass. So we need to declare them as
1005 SRGBA textures here so that OpenGL will automatically convert them to linear space upon loading and the
1006 subsequent tone mapping and gamma correction shader operations will not result in heavy distortion of their
1007 colors.
1008
1009 Also, remember that if no shaders are in use (as in lower detail levels), then we don't need to declare anything.
1010 */
1011 uint32_t srgbaOption = 0UL;
1012 if ([UNIVERSE useShaders]) srgbaOption = kOOTextureSRGBA;
1013 return [OOTexture textureWithName:[descriptor oo_stringForKey:@"name"]
1014 inFolder:@"Images"
1015 options:kOOTextureDefaultOptions | kOOTextureNoShrink | srgbaOption
1016 anisotropy:kOOTextureDefaultAnisotropy
1017 lodBias:kOOTextureDefaultLODBias];
1018}
1019
1020
1021/*
1022 Load a texture sprite given a descriptor. The caller owns a reference to
1023 the result.
1024*/
1025static OOTextureSprite *NewTextureSpriteWithDescriptor(NSDictionary *descriptor)
1026{
1027 OOTexture *texture = nil;
1028 NSSize size;
1029
1030 texture = TextureForGUITexture(descriptor);
1031 if (texture == nil) return nil;
1032
1033 double specifiedWidth = [descriptor oo_doubleForKey:@"width" defaultValue:-INFINITY];
1034 double specifiedHeight = [descriptor oo_doubleForKey:@"height" defaultValue:-INFINITY];
1035 BOOL haveWidth = isfinite(specifiedWidth);
1036 BOOL haveHeight = isfinite(specifiedHeight);
1037
1038 if (haveWidth && haveHeight)
1039 {
1040 // Both specified, use directly without calling -originalDimensions (which may block).
1041 size.width = specifiedWidth;
1042 size.height = specifiedHeight;
1043 }
1044 else
1045 {
1046 NSSize originalDimensions = [texture originalDimensions];
1047
1048 if (haveWidth)
1049 {
1050 // Width specified, but not height; preserve aspect ratio.
1051 CGFloat ratio = originalDimensions.height / originalDimensions.width;
1052 size.width = specifiedWidth;
1053 size.height = ratio * size.width;
1054 }
1055 else if (haveHeight)
1056 {
1057 // Height specified, but not width; preserve aspect ratio.
1058 CGFloat ratio = originalDimensions.width / originalDimensions.height;
1059 size.height = specifiedHeight;
1060 size.width = ratio * size.height;
1061 }
1062 else
1063 {
1064 // Neither specified; use backwards-compatible behaviour.
1065 size = originalDimensions;
1066 }
1067 }
1068
1069 return [[OOTextureSprite alloc] initWithTexture:texture size:size];
1070}
1071
1072
1073- (void) setBackgroundTextureSpecial:(OOGUIBackgroundSpecial)spec withBackground:(BOOL)withBackground
1074{
1075 if (withBackground)
1076 {
1077 NSDictionary *bgDescriptor = nil;
1078 OOGalaxyID galaxy_number = [PLAYER galaxyNumber];
1079
1080 switch (spec)
1081 {
1085 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"custom_chart_mission"];
1086 if (bgDescriptor == nil)
1087 {
1088 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"short_range_chart_mission"];
1089 if (bgDescriptor == nil)
1090 {
1091 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"short_range_chart"];
1092 }
1093 }
1094 break;
1098 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"short_range_chart_mission"];
1099 if (bgDescriptor == nil)
1100 {
1101 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"short_range_chart"];
1102 }
1103 break;
1107 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:[NSString stringWithFormat:@"long_range_chart%d_mission", galaxy_number+1]];
1108 if (bgDescriptor == nil)
1109 {
1110 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"long_range_chart_mission"];
1111 if (bgDescriptor == nil)
1112 {
1113 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:[NSString stringWithFormat:@"long_range_chart%d", galaxy_number+1]];
1114 if (bgDescriptor == nil)
1115 {
1116 bgDescriptor = [UNIVERSE screenTextureDescriptorForKey:@"long_range_chart"];
1117
1118 }
1119 }
1120 }
1121 break;
1123 break;
1124 }
1125 if (bgDescriptor != nil)
1126 {
1127 [self setBackgroundTextureDescriptor:bgDescriptor];
1128 }
1129 }
1130 backgroundSpecial = spec;
1131 [self refreshStarChart];
1132}
1133
1134
1135- (BOOL) setBackgroundTextureDescriptor:(NSDictionary *)descriptor
1136{
1137 [backgroundSprite autorelease];
1140 return backgroundSprite != nil;
1141}
1142
1143
1144- (BOOL) setForegroundTextureDescriptor:(NSDictionary *)descriptor
1145{
1146 [foregroundSprite autorelease];
1148 return foregroundSprite != nil;
1149}
1150
1151
1152- (BOOL) setBackgroundTextureKey:(NSString *)key
1153{
1154 return [self setBackgroundTextureDescriptor:[UNIVERSE screenTextureDescriptorForKey:key]];
1155}
1156
1157
1158- (BOOL) setForegroundTextureKey:(NSString *)key
1159{
1160 return [self setForegroundTextureDescriptor:[UNIVERSE screenTextureDescriptorForKey:key]];
1161}
1162
1163
1164- (BOOL) preloadGUITexture:(NSDictionary *)descriptor
1165{
1166 return TextureForGUITexture(descriptor) != nil;
1167}
1168
1169
1170- (NSDictionary *) textureDescriptorFromJSValue:(jsval)value
1171 inContext:(JSContext *)context
1172 callerDescription:(NSString *)callerDescription
1173{
1175
1176 NSDictionary *result = nil;
1177
1178 if (JSVAL_IS_OBJECT(value))
1179 {
1180 // Null may be used to indicate no texture.
1181 if (JSVAL_IS_NULL(value)) return [NSDictionary dictionary];
1182
1183 JSObject *objValue = JSVAL_TO_OBJECT(value);
1184
1185 if (OOJSGetClass(context, objValue) != [[OOJavaScriptEngine sharedEngine] stringClass])
1186 {
1187 result = OOJSDictionaryFromJSObject(context, objValue);
1188 }
1189 }
1190
1191 if (result == nil)
1192 {
1193 NSString *name = OOStringFromJSValue(context, value);
1194
1195 if (name != nil)
1196 {
1197 result = [NSDictionary dictionaryWithObject:name forKey:@"name"];
1198 if ([name length] == 0) return result; // Explicit empty string may be used to indicate no texture.
1199 }
1200 }
1201
1202 // Start loading the texture, and return nil if it doesn't exist.
1203 if (result != nil && ![self preloadGUITexture:result])
1204 {
1205 OOJSReportWarning(context, @"%@: texture \"%@\" could not be found.", callerDescription, [result oo_stringForKey:@"name"]);
1206 result = nil;
1207 }
1208
1209 return result;
1210
1212}
1213
1214
1215- (void) setStatusPage:(NSInteger)pageNum
1216{
1217 if (pageNum == 0 || (pageNum < 0 && ((NSUInteger)-pageNum) >= statusPage))
1218 {
1219 statusPage = 1;
1220 }
1221 else
1222 {
1223 statusPage += pageNum;
1224 }
1225}
1226
1227
1228- (NSUInteger) statusPage
1229{
1230 return statusPage;
1231}
1232
1233
1234- (void) drawEquipmentList:(NSArray *)eqptList z:(GLfloat)z
1235{
1236 if ([eqptList count] == 0) return;
1237
1239 NSUInteger maxRows = STATUS_EQUIPMENT_MAX_ROWS;
1240 if ([[PLAYER hud] allowBigGui])
1241 {
1243 }
1244 NSUInteger itemsPerColumn = maxRows;
1245
1246
1247 NSInteger firstY = 40; // firstRow =10 :-> 40 - firstRow=11 -> 24 etc...
1248 NSUInteger eqptCount = [eqptList count];
1249 NSUInteger pageCount = 1;
1250 NSUInteger i;
1251 NSInteger start;
1252 NSArray *info = nil;
1253 NSString *name = nil;
1254 BOOL damaged;
1255
1256 // Paging calculations. Assuming 10 lines we get - one page:20 items per page (ipp)
1257 // two pages: 18 ipp - three+ pages: 1st & last 18pp, middle pages 16ipp
1258
1259 i = itemsPerColumn * 2 + 2;
1260 if (eqptCount > i) // don't fit in one page?
1261 {
1262 [[UNIVERSE gameController] setMouseInteractionModeForUIWithMouseInteraction:YES];
1263
1264 i = itemsPerColumn * 4; // total items in the first and last pages
1265 itemsPerColumn--; // for all the middle pages.
1266 if (eqptCount <= i) // two pages
1267 {
1268 pageCount++;
1269 if (statusPage == 1)
1270 {
1271 start = 0;
1272 }
1273 else
1274 {
1275 statusPage = 2;
1276 start = i/statusPage; // for the for loop
1277 }
1278 }
1279 else // three or more
1280 {
1281 pageCount = ceil((float)(eqptCount-i)/(itemsPerColumn*2)) + 2;
1282 statusPage = (NSInteger)OOClampInteger(statusPage, 1, pageCount);
1283 start = (statusPage == 1) ? 0 : (statusPage-1) * itemsPerColumn * 2 + 2;
1284 }
1285 }
1286 else
1287 {
1288 statusPage = pageCount; // one page
1289 start = 0;
1290 // if we have mouse interaction active, it means that we had more than one
1291 // pages earlier, but only one now, as e.g. in the case of a hud that wss
1292 // subsequently hidden, resulting in the equip list fitting in one page,
1293 // so we need to deactivate it
1294 if (OOMouseInteractionModeIsUIScreen([[UNIVERSE gameController] mouseInteractionMode]))
1295 {
1296 // clear the gui-more and gui-back key rows first
1297 [self setText:@"" forRow:firstRow];
1298 [self setKey:GUI_KEY_SKIP forRow:firstRow];
1299 [self setText:@"" forRow:firstRow + STATUS_EQUIPMENT_MAX_ROWS];
1300 [self setKey:GUI_KEY_SKIP forRow:firstRow + STATUS_EQUIPMENT_MAX_ROWS];
1301 [self setSelectableRange:NSMakeRange(0,0)];
1302
1303 [[UNIVERSE gameController] setMouseInteractionModeForUIWithMouseInteraction:NO];
1304 }
1305 }
1306
1307 if (statusPage > 1)
1308 {
1309 [self setColor:[self colorFromSetting:kGuiStatusEquipmentScrollColor defaultValue:[OOColor greenColor]] forRow:firstRow];
1310 [self setArray:[NSArray arrayWithObjects:DESC(@"gui-back"), @"", @" <-- ",nil] forRow:firstRow];
1311 [self setKey:GUI_KEY_OK forRow:firstRow];
1312 firstY -= 16; // start 1 row down!
1313 if (statusPage == pageCount)
1314 {
1315 [self setSelectableRange:NSMakeRange(firstRow, 1)];
1316 [self setSelectedRow:firstRow];
1317 }
1318 }
1319 if (statusPage < pageCount)
1320 {
1321 [self setColor:[self colorFromSetting:kGuiStatusEquipmentScrollColor defaultValue:[OOColor greenColor]] forRow:firstRow + maxRows];
1322 [self setArray:[NSArray arrayWithObjects:DESC(@"gui-more"), @"", @" --> ",nil] forRow:firstRow + maxRows];
1323 [self setKey:GUI_KEY_OK forRow:firstRow + maxRows];
1324 if (statusPage == 1)
1325 {
1326 [self setSelectableRange:NSMakeRange(firstRow + maxRows, 1)];
1327 [self setSelectedRow:firstRow + maxRows];
1328 }
1329 }
1330 if (statusPage > 1 && statusPage < pageCount)
1331 {
1332 [self setSelectableRange:NSMakeRange(firstRow, MIN(firstRow + maxRows, GUI_DEFAULT_ROWS - firstRow))];
1333 // default selected row to 'More -->' if we are looking at one of the middle pages
1334 if ([self selectedRow] == -1) [self setSelectedRow:firstRow + maxRows];
1335 }
1336
1337 if (statusPage == 1 || statusPage == pageCount) itemsPerColumn++;
1338 eqptCount = (NSInteger)OOClampInteger(eqptCount, 1, start + itemsPerColumn * 2);
1339 for (i = start; i < eqptCount; i++)
1340 {
1341 info = [eqptList oo_arrayAtIndex:i];
1342 name = [info oo_stringAtIndex:0];
1343 if([name length] > 42) name = [[name substringToIndex:40] stringByAppendingString:@"..."];
1344
1345 damaged = ![info oo_boolAtIndex:1];
1346 if (damaged)
1347 {
1348 // Damaged items show up orange.
1349 [self setGLColorFromSetting:@"status_equipment_damaged_color" defaultValue:[OOColor orangeColor] alpha:1.0];
1350 }
1351 else
1352 {
1353 OOColor *dispCol = [info oo_objectAtIndex:2];
1354 // Normal items in default colour
1355 [self setGLColorFromSetting:@"status_equipment_ok_color" defaultValue:dispCol alpha:1.0];
1356 }
1357
1358 if (i - start < itemsPerColumn)
1359 {
1360 OODrawString(name, -220, firstY - 16 * (NSInteger)(i - start), z, NSMakeSize(15, 15));
1361 }
1362 else
1363 {
1364 OODrawString(name, 50, firstY - 16 * (NSInteger)(i - itemsPerColumn - start), z, NSMakeSize(15, 15));
1365 }
1366 }
1367}
1368
1369
1371{
1372 GLfloat x = drawPosition.x;
1373 GLfloat y = drawPosition.y;
1374 GLfloat z = [[UNIVERSE gameView] display_z];
1375
1376 if (backgroundSprite!=nil)
1377 {
1379 }
1380
1381}
1382
1383
1385{
1386 _refreshStarChart = YES;
1387}
1388
1389
1390- (int) drawGUI:(GLfloat) alpha drawCursor:(BOOL) drawCursor
1391{
1392 GLfloat x = drawPosition.x;
1393 GLfloat y = drawPosition.y;
1394 GLfloat z = [[UNIVERSE gameView] display_z];
1395
1396 if (alpha > 0.05f)
1397 {
1398 PlayerEntity* player = PLAYER;
1399
1400 [self drawGLDisplay:x - 0.5f * size_in_pixels.width :y - 0.5f * size_in_pixels.height :z :alpha];
1401
1402 if (self == [UNIVERSE gui])
1403 {
1404 if ([player guiScreen] == GUI_SCREEN_SHORT_RANGE_CHART || [player guiScreen] == GUI_SCREEN_LONG_RANGE_CHART ||
1411 {
1412 [self drawStarChart:x - 0.5f * size_in_pixels.width :y - 0.5f * size_in_pixels.height :z :alpha :NO];
1413 }
1417 {
1418 [self drawStarChart:x - 0.5f * size_in_pixels.width :y - 0.5f * size_in_pixels.height :z :alpha :YES];
1419 }
1420 if ([player guiScreen] == GUI_SCREEN_STATUS)
1421 {
1423 }
1424 if ([player guiScreen] == GUI_SCREEN_STICKPROFILE)
1425 {
1426 [player stickProfileGraphAxisProfile: alpha screenAt: make_vector(x,y,z) screenSize: size_in_pixels];
1427 }
1428 }
1429
1430 if (fade_sign)
1431 {
1432 fade_alpha += (float)(fade_sign * [UNIVERSE getTimeDelta]);
1433 if (fade_alpha < 0.05f) // done fading out
1434 {
1435 fade_alpha = 0.0f;
1436 fade_sign = 0.0f;
1437 }
1438 if (fade_alpha >= max_alpha) // done fading in
1439 {
1441 fade_sign = 0.0f;
1442 }
1443 }
1444 }
1445
1446 int cursor_row = 0;
1447
1448 if (drawCursor)
1449 {
1450 NSPoint vjpos = [[UNIVERSE gameView] virtualJoystickPosition];
1451 double cursor_x = size_in_pixels.width * vjpos.x;
1452 if (cursor_x < -size_in_pixels.width * 0.5) cursor_x = -size_in_pixels.width * 0.5f;
1453 if (cursor_x > size_in_pixels.width * 0.5) cursor_x = size_in_pixels.width * 0.5f;
1454 double cursor_y = -size_in_pixels.height * vjpos.y;
1455 if (cursor_y < -size_in_pixels.height * 0.5) cursor_y = -size_in_pixels.height * 0.5f;
1456 if (cursor_y > size_in_pixels.height * 0.5) cursor_y = size_in_pixels.height * 0.5f;
1457
1458 cursor_row = 1 + (float)floor((0.5f * size_in_pixels.height - pixel_row_start - cursor_y) / pixel_row_height);
1459
1460 GLfloat h1 = 3.0f;
1461 GLfloat h3 = 9.0f;
1462 OOGL(glColor4f(0.6f, 0.6f, 1.0f, 1.0f)); // original value of (0.2f, 0.2f, 1.0f, 0.5f) too dark - Nikos 20130616
1463 OOGL(GLScaledLineWidth(2.0f));
1464
1465 cursor_x += x;
1466 cursor_y += y;
1467 [[UNIVERSE gameView] setVirtualJoystick:cursor_x/size_in_pixels.width :-cursor_y/size_in_pixels.height];
1468
1469 OOGLBEGIN(GL_LINES);
1470 glVertex3f((float)cursor_x - h1, (float)cursor_y, z); glVertex3f((float)cursor_x - h3, (float)cursor_y, z);
1471 glVertex3f((float)cursor_x + h1, (float)cursor_y, z); glVertex3f((float)cursor_x + h3, (float)cursor_y, z);
1472 glVertex3f((float)cursor_x, (float)cursor_y - h1, z); glVertex3f((float)cursor_x, (float)cursor_y - h3, z);
1473 glVertex3f((float)cursor_x, (float)cursor_y + h1, z); glVertex3f((float)cursor_x, (float)cursor_y + h3, z);
1474 OOGLEND();
1475 OOGL(GLScaledLineWidth(1.0f));
1476
1477 }
1478
1479 return cursor_row;
1480}
1481
1482
1483- (void) drawGLDisplay:(GLfloat)x :(GLfloat)y :(GLfloat)z :(GLfloat) alpha
1484{
1485 NSSize strsize;
1486 unsigned i;
1487 OOTimeDelta delta_t = [UNIVERSE getTimeDelta];
1488 NSSize characterSize = pixel_text_size;
1489 NSSize titleCharacterSize = pixel_title_size;
1490 float backgroundAlpha = self == [UNIVERSE messageGUI] && ![UNIVERSE permanentMessageLog] ? 0.0f : alpha;
1491 float row_alpha[n_rows];
1492
1493 // calculate fade out time and alpha for each row. Do it before
1494 // applying a potential background because we need the maximum alpha
1495 // of all rows to be the alpha applied to the background color
1496 for (i = 0; i < n_rows; i++)
1497 {
1498 row_alpha[i] = alpha;
1499
1500 if(![UNIVERSE autoMessageLogBg] && [PLAYER guiScreen] == GUI_SCREEN_MAIN) backgroundAlpha = alpha;
1501
1502 if (rowFadeTime[i] > 0.0f && ![UNIVERSE permanentMessageLog])
1503 {
1504 rowFadeTime[i] -= (float)delta_t;
1505 if (rowFadeTime[i] <= 0.0f)
1506 {
1507 [rowText replaceObjectAtIndex:i withObject:@""];
1508 rowFadeTime[i] = 0.0f;
1509 continue;
1510 }
1511 if ((rowFadeTime[i] > 0.0f)&&(rowFadeTime[i] < 1.0))
1512 {
1513 row_alpha[i] *= rowFadeTime[i];
1514 if (backgroundAlpha < row_alpha[i]) backgroundAlpha = row_alpha[i];
1515 }
1516 else
1517 {
1518 backgroundAlpha = alpha;
1519 }
1520 }
1521 }
1522
1523 // do backdrop
1524 // don't draw it if docked, unless message_gui is permanent
1525 // don't draw it on the intro screens
1526 if (backgroundColor)
1527 {
1528 int playerStatus = [PLAYER status];
1529 if (playerStatus != STATUS_START_GAME && playerStatus != STATUS_DEAD)
1530 {
1531 OOGL(glColor4f([backgroundColor redComponent], [backgroundColor greenComponent], [backgroundColor blueComponent], backgroundAlpha * [backgroundColor alphaComponent]));
1532 OOGLBEGIN(GL_QUADS);
1533 glVertex3f(x + 0.0f, y + 0.0f, z);
1534 glVertex3f(x + size_in_pixels.width, y + 0.0f, z);
1535 glVertex3f(x + size_in_pixels.width, y + size_in_pixels.height, z);
1536 glVertex3f(x + 0.0f, y + size_in_pixels.height, z);
1537 OOGLEND();
1538 }
1539 }
1540
1541 // show the 'foreground', aka overlay!
1542
1543 if (foregroundSprite != nil)
1544 {
1545 [foregroundSprite blitCentredToX:x + 0.5f * size_in_pixels.width Y:y + 0.5f * size_in_pixels.height Z:z alpha:alpha];
1546 }
1547
1548 if (!RowInRange(selectedRow, selectableRange))
1549 selectedRow = -1; // out of Range;
1550
1552 // drawing operations here
1553
1554 if (title != nil)
1555 {
1556 //
1557 // draw the title
1558 //
1559 strsize = OORectFromString(title, 0.0f, 0.0f, titleCharacterSize).size;
1560 [self setGLColorFromSetting:kGuiScreenTitleColor defaultValue:[OOColor redColor] alpha:alpha];
1561
1562 OODrawString(title, x + pixel_row_center - strsize.width/2.0, y + size_in_pixels.height - pixel_title_size.height, z, titleCharacterSize);
1563
1564 // draw a horizontal divider
1565 //
1566 [self setGLColorFromSetting:kGuiScreenDividerColor defaultValue:[OOColor colorWithWhite:0.75 alpha:1.0] alpha:alpha];
1567
1568 OOGLBEGIN(GL_QUADS);
1569 glVertex3f(x + 0, y + size_in_pixels.height - pixel_title_size.height + 4, z);
1570 glVertex3f(x + size_in_pixels.width, y + size_in_pixels.height - pixel_title_size.height + 4, z);
1571 glVertex3f(x + size_in_pixels.width, y + size_in_pixels.height - pixel_title_size.height + 2, z);
1572 glVertex3f(x + 0, y + size_in_pixels.height - pixel_title_size.height + 2, z);
1573 OOGLEND();
1574 }
1575
1576 // draw each row of text
1577 //
1579 for (i = 0; i < n_rows; i++)
1580 {
1581 OOColor* row_color = (OOColor *)[rowColor objectAtIndex:i];
1582 glColor4f([row_color redComponent], [row_color greenComponent], [row_color blueComponent], row_alpha[i]);
1583
1584 if ([[rowText objectAtIndex:i] isKindOfClass:[NSString class]])
1585 {
1586 NSString* text = (NSString *)[rowText objectAtIndex:i];
1587 if (![text isEqual:@""])
1588 {
1589 strsize = OORectFromString(text, 0.0f, 0.0f, characterSize).size;
1590 switch (rowAlignment[i])
1591 {
1592 case GUI_ALIGN_LEFT :
1593 rowPosition[i].x = 0.0f;
1594 break;
1595 case GUI_ALIGN_RIGHT :
1596 rowPosition[i].x = size_in_pixels.width - strsize.width;
1597 break;
1598 case GUI_ALIGN_CENTER :
1599 rowPosition[i].x = (size_in_pixels.width - strsize.width)/2.0f;
1600 break;
1601 }
1602 if (i == (unsigned)selectedRow)
1603 {
1604 NSRect block = OORectFromString(text, x + rowPosition[i].x + 2, y + rowPosition[i].y + 2, characterSize);
1606 [self setGLColorFromSetting:kGuiSelectedRowBackgroundColor defaultValue:[OOColor redColor] alpha:alpha];
1607 OOGLBEGIN(GL_QUADS);
1608 glVertex3f(block.origin.x, block.origin.y, z);
1609 glVertex3f(block.origin.x + block.size.width, block.origin.y, z);
1610 glVertex3f(block.origin.x + block.size.width, block.origin.y + block.size.height, z);
1611 glVertex3f(block.origin.x, block.origin.y + block.size.height, z);
1612 OOGLEND();
1613 [self setGLColorFromSetting:kGuiSelectedRowColor defaultValue:[OOColor blackColor] alpha:alpha];
1615 }
1616 OODrawStringQuadsAligned(text, x + rowPosition[i].x, y + rowPosition[i].y, z, characterSize, NO);
1617
1618 // draw cursor at end of current Row
1619 //
1620 if ((showTextCursor)&&(i == (unsigned)currentRow))
1621 {
1622 NSRect tr = OORectFromString(text, 0.0f, 0.0f, characterSize);
1623 NSPoint cu = NSMakePoint(x + rowPosition[i].x + tr.size.width + 0.2f * characterSize.width, y + rowPosition[i].y);
1624 tr.origin = cu;
1625 tr.size.width = 0.5f * characterSize.width;
1626 GLfloat g_alpha = 0.5f * (1.0f + (float)sin(6 * [UNIVERSE getTime]));
1628 [self setGLColorFromSetting:kGuiTextInputCursorColor defaultValue:[OOColor redColor] alpha:row_alpha[i]*g_alpha];
1629 OOGLBEGIN(GL_QUADS);
1630 glVertex3f(tr.origin.x, tr.origin.y, z);
1631 glVertex3f(tr.origin.x + tr.size.width, tr.origin.y, z);
1632 glVertex3f(tr.origin.x + tr.size.width, tr.origin.y + tr.size.height, z);
1633 glVertex3f(tr.origin.x, tr.origin.y + tr.size.height, z);
1634 OOGLEND();
1636 }
1637 }
1638 }
1639 if ([[rowText objectAtIndex:i] isKindOfClass:[NSArray class]])
1640 {
1641 NSArray *array = [rowText oo_arrayAtIndex:i];
1642 NSUInteger j, max_columns = MIN([array count], n_columns);
1643 BOOL isLeftAligned;
1644
1645 for (j = 0; j < max_columns; j++)
1646 {
1647 NSString* text = [array oo_stringAtIndex:j];
1648 if ([text length] != 0)
1649 {
1650 isLeftAligned = tabStops[j] >= 0;
1651 rowPosition[i].x = labs(tabStops[j]);
1652
1653 // we don't want to highlight leading space(s) or narrow spaces (\037s)
1654 NSString *hilitedText = [text stringByTrimmingCharactersInSet:[NSCharacterSet characterSetWithCharactersInString:@" \037"]];
1655 NSRange txtRange = [text rangeOfString:hilitedText];
1656 unsigned leadingSpaces = 0;
1657
1658 if (EXPECT_NOT(txtRange.location == NSNotFound))
1659 {
1660 // This never happens!
1661 hilitedText = text;
1662 }
1663 else if (txtRange.location > 0)
1664 {
1665 // padded string!
1666 NSRange padRange;
1667 padRange.location = 0;
1668 padRange.length = txtRange.location;
1669 NSRect charBlock = OORectFromString([text substringWithRange:padRange], 0, 0, characterSize);
1670 leadingSpaces = (unsigned)charBlock.size.width;
1671
1672/* // if we're displaying commodity-quantity-none, let's try and be pixel perfect!
1673 NSString *qtyNone = DESC(@"commodity-quantity-none");
1674 txtRange = [hilitedText rangeOfString:qtyNone];
1675
1676 if (txtRange.location == 0) // bingo!
1677 {
1678 rowPosition[i].x += OORectFromString(@"0", 0, 0, characterSize).size.width - OORectFromString(qtyNone, 0, 0, characterSize).size.width;
1679 } */
1680 }
1681
1682 // baseline text rect, needed for correct highlight positioning.
1683 NSRect block = OORectFromString(text, x + rowPosition[i].x + 2, y + rowPosition[i].y + 2, characterSize);
1684
1685 if(!isLeftAligned)
1686 {
1687 rowPosition[i].x -= block.size.width + 3;
1688 }
1689 block = OORectFromString(hilitedText, x + rowPosition[i].x + 1 + leadingSpaces, y + rowPosition[i].y + 2, characterSize);
1690 block.size.width += 3;
1691
1692
1693 if (i == (unsigned)selectedRow)
1694 {
1696 [self setGLColorFromSetting:kGuiSelectedRowBackgroundColor defaultValue:[OOColor redColor] alpha:alpha];
1697 OOGLBEGIN(GL_QUADS);
1698 glVertex3f(block.origin.x, block.origin.y, z);
1699 glVertex3f(block.origin.x + block.size.width, block.origin.y, z);
1700 glVertex3f(block.origin.x + block.size.width, block.origin.y + block.size.height, z);
1701 glVertex3f(block.origin.x, block.origin.y + block.size.height, z);
1702 OOGLEND();
1703 [self setGLColorFromSetting:kGuiSelectedRowColor defaultValue:[OOColor blackColor] alpha:alpha];
1705 }
1706 OODrawStringQuadsAligned(text, x + rowPosition[i].x, y + rowPosition[i].y, z, characterSize,NO);
1707 }
1708 }
1709 }
1710 }
1713}
1714
1715
1716- (void) drawCrossHairsWithSize:(GLfloat) size x:(GLfloat)x y:(GLfloat)y z:(GLfloat)z
1717{
1718 OOGLBEGIN(GL_QUADS);
1719 glVertex3f(x - 1, y - size, z);
1720 glVertex3f(x + 1, y - size, z);
1721 glVertex3f(x + 1, y + size, z);
1722 glVertex3f(x - 1, y + size, z);
1723 glVertex3f(x - size, y - 1, z);
1724 glVertex3f(x + size, y - 1, z);
1725 glVertex3f(x + size, y + 1, z);
1726 glVertex3f(x - size, y + 1, z);
1727 OOGLEND();
1728}
1729
1730
1732{
1733 PlayerEntity *player = PLAYER;
1734 OOGalaxyID galaxy_number = [player galaxyNumber];
1735 NSInteger system_id = [UNIVERSE findSystemNumberAtCoords:[player cursor_coordinates] withGalaxy:[player galaxyNumber] includingHidden:NO];
1736
1737 NSString *location_key = [NSString stringWithFormat:@"long-range-chart-title-%d-%ld", galaxy_number, (long)system_id];
1738 if ([[UNIVERSE descriptions] valueForKey:location_key] == nil)
1739 {
1740 NSString *gal_key = [NSString stringWithFormat:@"long-range-chart-title-%d", galaxy_number];
1741 if ([[UNIVERSE descriptions] valueForKey:gal_key] == nil)
1742 {
1743 [self setTitle:[NSString stringWithFormat:DESC(@"long-range-chart-title-d"), galaxy_number+1]];
1744 }
1745 else
1746 {
1747 [self setTitle:[UNIVERSE descriptionForKey:gal_key]];
1748 }
1749 }
1750 else
1751 {
1752 [self setTitle:[UNIVERSE descriptionForKey:location_key]];
1753 }
1754}
1755
1756
1757- (void) drawStarChart:(GLfloat)x :(GLfloat)y :(GLfloat)z :(GLfloat) alpha :(BOOL)compact
1758{
1759 PlayerEntity* player = PLAYER;
1760
1761 if (!player)
1762 return;
1763
1764 OOSystemDescriptionManager *systemManager = [UNIVERSE systemManager];
1765
1766 OOScalar zoom = [player chart_zoom];
1767 NSPoint chart_centre_coordinates = [player adjusted_chart_centre];
1768 NSPoint galaxy_coordinates = [player galaxy_coordinates];
1769 NSPoint cursor_coordinates = [player cursor_coordinates];
1770 NSPoint info_system_coordinates = [[UNIVERSE systemManager] getCoordinatesForSystem: [player infoSystemID] inGalaxy: [player galaxyNumber]];
1772 OOGalaxyID galaxy_id = [player galaxyNumber];
1773 GLfloat r = 1.0, g = 1.0, b = 1.0;
1774 BOOL noNova;
1775 NSPoint cu;
1776 NSUInteger systemParameter;
1777
1778 double fuel = 35.0 * [player dialFuel];
1779
1780 double hcenter = size_in_pixels.width/2.0;
1781 double hscale = size_in_pixels.width / (CHART_WIDTH_AT_MAX_ZOOM*zoom);
1782 double vscale = -size_in_pixels.height / (2*CHART_HEIGHT_AT_MAX_ZOOM*zoom);
1783 double vcenter = CHART_SCREEN_VERTICAL_CENTRE;
1784 double hoffset = hcenter - chart_centre_coordinates.x*hscale;
1785 double voffset = size_in_pixels.height - vcenter - chart_centre_coordinates.y*vscale;
1786
1787 if (compact)
1788 {
1789 hscale = size_in_pixels.width / 256.0;
1790 vscale = -1.0 * size_in_pixels.height / 512.0;
1791 hoffset = 0.0f;
1792 voffset = size_in_pixels.height - pixel_title_size.height - 5;
1794 chart_centre_coordinates.x = 128.0;
1795 chart_centre_coordinates.y = 128.0;
1796 zoom = CHART_MAX_ZOOM;
1797 }
1798
1799 int i;
1800 double d, distance = 0.0, time = 0.0;
1801 int jumps = 0;
1802 NSPoint star;
1803 OOScalar pixelRatio;
1804 NSRect clipRect;
1805
1806 OORouteType advancedNavArrayMode = [player ANAMode];
1807 BOOL routeExists = NO;
1808
1809 NSInteger concealment[256];
1810 for (i=0;i<256;i++) {
1811 NSDictionary *systemInfo = [systemManager getPropertiesForSystem:i inGalaxy:galaxy_id];
1812 concealment[i] = [systemInfo oo_intForKey:@"concealment" defaultValue:OO_SYSTEMCONCEALMENT_NONE];
1813 }
1814
1815 BOOL *systemsFound = [UNIVERSE systemsFound];
1816 NSSize viewSize = [[UNIVERSE gameView] backingViewSize];
1817 double aspect_ratio = viewSize.width / viewSize.height;
1818
1819 // default colours - match those in HeadUpDisplay:OODrawPlanetInfo
1820 GLfloat govcol[] = { 0.5, 0.0, 0.7,
1821 0.7, 0.5, 0.3,
1822 0.0, 1.0, 0.3,
1823 1.0, 0.8, 0.1,
1824 1.0, 0.0, 0.0,
1825 0.1, 0.5, 1.0,
1826 0.7, 0.7, 0.7,
1827 0.7, 1.0, 1.0};
1828
1829 if (aspect_ratio > 4.0/3.0)
1830 {
1831 pixelRatio = viewSize.height / 480.0;
1832 }
1833 else
1834 {
1835 pixelRatio = viewSize.width / 640.0;
1836 }
1837
1838 NSInteger textRow = compact ? GUI_ROW_CHART_SYSTEM_COMPACT : GUI_ROW_CHART_SYSTEM;
1839
1840 clipRect = NSMakeRect((viewSize.width - size_in_pixels.width*pixelRatio)/2.0,
1841 (viewSize.height + size_in_pixels.height*pixelRatio)/2.0 - (pixel_title_size.height + 15 + (textRow-2)*MAIN_GUI_ROW_HEIGHT) * pixelRatio,
1842 size_in_pixels.width * pixelRatio,
1843 (textRow-1) * MAIN_GUI_ROW_HEIGHT * pixelRatio);
1844
1845 OOSystemID target = [PLAYER targetSystemID];
1846 double dx, dy;
1847
1848 // get a list of systems marked as contract destinations
1849 NSDictionary* markedDestinations = [player markedDestinations];
1850
1851 // get present location
1852 cu = NSMakePoint((float)(hscale*galaxy_coordinates.x+hoffset),(float)(vscale*galaxy_coordinates.y+voffset));
1853
1854 // enable draw clipping; limit drawing area within the chart area
1855 OOGL(glEnable(GL_SCISSOR_TEST));
1856 OOGL(glScissor(clipRect.origin.x, clipRect.origin.y, clipRect.size.width, clipRect.size.height));
1857
1858 // Cache nearby systems so that [UNIVERSE generateSystemData:] does not get called on every frame
1859 // Caching code submitted by Y A J, 20091022
1860
1861 static OOGalaxyID saved_galaxy_id;
1862 static struct saved_system
1863 {
1864 OOSystemID sysid;
1865 int tec, eco, gov;
1866 NSString* p_name;
1867 BOOL nova;
1868 } nearby_systems[ 256 ];
1869 static int num_nearby_systems = 0;
1870
1871 if ( _refreshStarChart || galaxy_id != saved_galaxy_id)
1872 {
1873 // saved systems are stale; recompute
1874 _refreshStarChart = NO;
1875 for (i = 0; i < num_nearby_systems; i++)
1876 [nearby_systems[ i ].p_name release];
1877
1878 num_nearby_systems = 0;
1879 for (i = 0; i < 256; i++)
1880 {
1881
1882 NSDictionary* sys_info = [UNIVERSE generateSystemData:i];
1883 if (EXPECT_NOT([sys_info oo_boolForKey:@"sun_gone_nova"]))
1884 {
1885 nearby_systems[ num_nearby_systems ].gov = -1; // Flag up nova systems!
1886 }
1887 else
1888 {
1889 nearby_systems[ num_nearby_systems ].tec = [sys_info oo_intForKey:KEY_TECHLEVEL];
1890 nearby_systems[ num_nearby_systems ].eco = [sys_info oo_intForKey:KEY_ECONOMY];
1891 nearby_systems[ num_nearby_systems ].gov = [sys_info oo_intForKey:KEY_GOVERNMENT];
1892 }
1893 nearby_systems[ num_nearby_systems ].sysid = i;
1894 nearby_systems[ num_nearby_systems ].p_name = [[sys_info oo_stringForKey:KEY_NAME] retain];
1895 nearby_systems[ num_nearby_systems ].nova = [[UNIVERSE generateSystemData:i] oo_boolForKey:@"sun_gone_nova"];
1896 num_nearby_systems++;
1897 }
1898 saved_galaxy_id = [player galaxyNumber];
1899 }
1900
1901 static OOSystemID savedPlanetNumber = 0;
1902 static OOSystemID savedDestNumber = 0;
1903 static OORouteType savedArrayMode = OPTIMIZED_BY_NONE;
1904 static NSDictionary *routeInfo = nil;
1905
1906 /* May override current mode for mission screens */
1907 if (backgroundSpecial == GUI_BACKGROUND_SPECIAL_LONG_ANA_SHORTEST ||
1908 backgroundSpecial == GUI_BACKGROUND_SPECIAL_SHORT_ANA_SHORTEST ||
1909 backgroundSpecial == GUI_BACKGROUND_SPECIAL_CUSTOM_ANA_SHORTEST)
1910 {
1911 advancedNavArrayMode = OPTIMIZED_BY_JUMPS;
1912 }
1913 else if (backgroundSpecial == GUI_BACKGROUND_SPECIAL_LONG_ANA_QUICKEST ||
1914 backgroundSpecial == GUI_BACKGROUND_SPECIAL_SHORT_ANA_QUICKEST ||
1915 backgroundSpecial == GUI_BACKGROUND_SPECIAL_CUSTOM_ANA_QUICKEST)
1916 {
1917 advancedNavArrayMode = OPTIMIZED_BY_TIME;
1918 }
1919
1920 if (advancedNavArrayMode != OPTIMIZED_BY_NONE && [player hasEquipmentItemProviding:@"EQ_ADVANCED_NAVIGATIONAL_ARRAY"])
1921 {
1922 OOSystemID planetNumber = [PLAYER systemID];
1923 OOSystemID destNumber = [PLAYER targetSystemID];
1924 if (routeInfo == nil || planetNumber != savedPlanetNumber || destNumber != savedDestNumber || advancedNavArrayMode != savedArrayMode)
1925 {
1926 [routeInfo release];
1927 routeInfo = [[UNIVERSE routeFromSystem:planetNumber toSystem:destNumber optimizedBy:advancedNavArrayMode] retain];
1928 savedPlanetNumber = planetNumber;
1929 savedDestNumber = destNumber;
1930 savedArrayMode = advancedNavArrayMode;
1931 }
1932 target = destNumber;
1933
1934 // if the ANA has been activated and we are in string input mode (i.e. planet search),
1935 // get out of it so that distance and time data can be displayed
1936 //if ([[[UNIVERSE gameView] typedString] length] > 0) [player clearPlanetSearchString];
1937
1938 if (routeInfo) routeExists = YES;
1939
1940 [self drawAdvancedNavArrayAtX:x+hoffset y:y+voffset z:z alpha:alpha usingRoute: (planetNumber != destNumber ? (id)routeInfo : nil) optimizedBy:advancedNavArrayMode zoom: zoom];
1941
1942 if (routeExists)
1943 {
1944 distance = [routeInfo oo_doubleForKey:@"distance"];
1945 time = [routeInfo oo_doubleForKey:@"time"];
1946 jumps = [routeInfo oo_intForKey:@"jumps"];
1947
1948 if (distance == 0.0 && planetNumber != destNumber)
1949 {
1950 // zero-distance double fix
1951 distance = 0.1;
1952 time = 0.01;
1953 }
1954 }
1955 }
1956 else
1957 {
1958 [self drawAdvancedNavArrayAtX:x+hoffset y:y+voffset z:z alpha:alpha usingRoute:nil optimizedBy:OPTIMIZED_BY_NONE zoom: zoom];
1959 }
1960 if (!routeExists)
1961 {
1962 NSPoint targetCoordinates = [systemManager getCoordinatesForSystem:target inGalaxy:galaxy_id];
1963
1964 distance = distanceBetweenPlanetPositions(targetCoordinates.x,targetCoordinates.y,galaxy_coordinates.x,galaxy_coordinates.y);
1965 if (distance == 0.0)
1966 {
1967 if (target != [PLAYER systemID])
1968 {
1969 // looking at the other half of a zero-distance double
1970 // distance is treated as 0.1 LY
1971 distance = 0.1;
1972 }
1973 }
1974 if ([player hasHyperspaceMotor] && distance <= [player fuel]/10.0)
1975 {
1976 time = distance * distance;
1977 }
1978 else
1979 {
1980 time = 0.0;
1981 }
1982 }
1983
1984 if ([player hasHyperspaceMotor])
1985 {
1986 // draw fuel range circle
1987 OOGL(GLScaledLineWidth(2.0f));
1988 [self setGLColorFromSetting:kGuiChartRangeColor defaultValue:[OOColor greenColor] alpha:alpha];
1989
1990 GLDrawOval(x + cu.x, y + cu.y, z, NSMakeSize((float)(fuel*hscale), 2*(float)(fuel*vscale)), 5);
1991 }
1992
1993
1994 // draw crosshairs over current location
1995 //
1996 [self setGLColorFromSetting:kGuiChartCrosshairColor defaultValue:[OOColor greenColor] alpha:alpha];
1997
1998 [self drawCrossHairsWithSize:12/zoom+2 x:x + cu.x y:y + cu.y z:z];
1999
2000
2001 // draw crosshairs over cursor
2002 //
2003 [self setGLColorFromSetting:kGuiChartCursorColor defaultValue:[OOColor redColor] alpha:alpha];
2004 cu = NSMakePoint((float)(hscale*cursor_coordinates.x+hoffset),(float)(vscale*cursor_coordinates.y+voffset));
2005 [self drawCrossHairsWithSize:7/zoom+2 x:x + cu.x y:y + cu.y z:z];
2006
2007 // draw marks and stars
2008 //
2009 OOGL(GLScaledLineWidth(1.5f));
2010 OOGL(glColor4f(1.0f, 1.0f, 0.75f, alpha)); // pale yellow
2011
2012 for (i = 0; i < num_nearby_systems; i++)
2013 {
2014 NSPoint sys_coordinates = [systemManager getCoordinatesForSystem:i inGalaxy:galaxy_id];
2015
2016 dx = fabs(chart_centre_coordinates.x - sys_coordinates.x);
2017 dy = fabs(chart_centre_coordinates.y - sys_coordinates.y);
2018
2020 continue;
2021
2022
2023 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NOTHING) {
2024 // system is not known
2025 continue;
2026 }
2027
2028 NSDictionary *systemInfo = [systemManager getPropertiesForSystem:i inGalaxy:galaxy_id];
2029 float blob_factor = [guiUserSettings oo_floatForKey:kGuiChartCircleScale defaultValue:0.0017];
2030 float blob_size = (1.0f + blob_factor * [systemInfo oo_floatForKey:@"radius"])/zoom;
2031 if (blob_size < 0.5) blob_size = 0.5;
2032
2033 star.x = (float)(sys_coordinates.x * hscale + hoffset);
2034 star.y = (float)(sys_coordinates.y * vscale + voffset);
2035
2036 noNova = !nearby_systems[i].nova;
2037 NSAssert1(chart_mode <= OOLRC_MODE_TECHLEVEL, @"Long range chart mode %i out of range", (int)chart_mode);
2038
2039 NSArray *markers = [markedDestinations objectForKey:[NSNumber numberWithInt:i]];
2040 if (markers != nil) // is marked
2041 {
2042 GLfloat base_size = 0.5f * blob_size + 2.5f;
2043 [self drawSystemMarkers:markers atX:x+star.x andY:y+star.y andZ:z withAlpha:alpha andScale:base_size];
2044 }
2045
2046 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NODATA) {
2047 // no system data available
2048 r = g = b = 0.7;
2049 OOGL(glColor4f(r, g, b, alpha));
2050 } else {
2051 switch (chart_mode)
2052 {
2053 case OOLRC_MODE_ECONOMY:
2054 if (EXPECT(noNova))
2055 {
2056 systemParameter = nearby_systems[i].eco;
2057 GLfloat ce1 = 1.0f - 0.125f * systemParameter;
2058 [self setGLColorFromSetting:[NSString stringWithFormat:kGuiChartEconomyUColor, (unsigned long)systemParameter]
2059 defaultValue:[OOColor colorWithRed:ce1 green:1.0f blue:0.0f alpha:1.0f]
2060 alpha:1.0];
2061 }
2062 else
2063 {
2064 r = g = b = 0.3;
2065 OOGL(glColor4f(r, g, b, alpha));
2066 }
2067 break;
2068 case OOLRC_MODE_GOVERNMENT:
2069 if (EXPECT(noNova))
2070 {
2071 systemParameter = nearby_systems[i].gov;
2072 [self setGLColorFromSetting:[NSString stringWithFormat:kGuiChartGovernmentUColor, (unsigned long)systemParameter]
2073 defaultValue:[OOColor colorWithRed:govcol[systemParameter*3] green:govcol[1+(systemParameter*3)] blue:govcol[2+(systemParameter*3)] alpha:1.0f]
2074 alpha:1.0];
2075 }
2076 else
2077 {
2078 r = g = b = 0.3;
2079 OOGL(glColor4f(r, g, b, alpha));
2080 }
2081 break;
2082 case OOLRC_MODE_TECHLEVEL:
2083 if (EXPECT(noNova))
2084 {
2085 systemParameter = nearby_systems[i].tec;
2086 r = 0.6;
2087 g = b = 0.20 + (0.05 * (GLfloat)systemParameter);
2088 }
2089 else
2090 {
2091 r = g = b = 0.3;
2092 }
2093 OOGL(glColor4f(r, g, b, alpha));
2094 break;
2095 case OOLRC_MODE_UNKNOWN:
2096 case OOLRC_MODE_SUNCOLOR:
2097 if (EXPECT(noNova))
2098 {
2099 r = g = b = 1.0;
2100 OOColor *sunColor = [OOColor colorWithDescription:[[UNIVERSE systemManager] getProperty:@"sun_color" forSystem:i inGalaxy:galaxy_id]];
2101 if (sunColor != nil) {
2102 [sunColor getRed:&r green:&g blue:&b alpha:&alpha];
2103 alpha = 1.0; // reset
2104 }
2105 }
2106 else
2107 {
2108 r = 1.0;
2109 g = 0.2;
2110 b = 0.0;
2111 }
2112 OOGL(glColor4f(r, g, b, alpha));
2113 break;
2114 }
2115 }
2116
2117 GLDrawFilledOval(x + star.x, y + star.y, z, NSMakeSize(blob_size,blob_size), 15);
2118 }
2119
2120 // draw found stars and captions
2121 //
2122 GLfloat systemNameScale = [guiUserSettings oo_floatForKey:kGuiChartLabelScale defaultValue:1.0];
2123
2124 OOGL(GLScaledLineWidth(1.5f));
2125 [self setGLColorFromSetting:kGuiChartMatchBoxColor defaultValue:[OOColor greenColor] alpha:alpha];
2126
2127 int n_matches = 0, foundIndex = -1;
2128
2129 for (i = 0; i < 256; i++) if (systemsFound[i])
2130 {
2131 if(foundSystem == n_matches) foundIndex = i;
2132 n_matches++;
2133 }
2134
2135 if (n_matches == 0)
2136 {
2137 foundSystem = 0;
2138 }
2139 else if (backgroundSpecial == GUI_BACKGROUND_SPECIAL_LONG_ANA_SHORTEST || backgroundSpecial == GUI_BACKGROUND_SPECIAL_LONG_ANA_QUICKEST || backgroundSpecial == GUI_BACKGROUND_SPECIAL_LONG)
2140 {
2141 // do nothing at this stage
2142 }
2143 else
2144 {
2145 for (i = 0; i < 256; i++)
2146 {
2147 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NONAME)
2148 {
2149 continue;
2150 }
2151
2152 BOOL mark = systemsFound[i];
2153 float marker_size = 8.0/zoom;
2154 NSPoint sys_coordinates = [systemManager getCoordinatesForSystem:i inGalaxy:galaxy_id];
2155
2156 dx = fabs(chart_centre_coordinates.x - sys_coordinates.x);
2157 dy = fabs(chart_centre_coordinates.y - sys_coordinates.y);
2158
2159 if (mark && (dx <= zoom*(CHART_WIDTH_AT_MAX_ZOOM/2.0+CHART_CLIP_BORDER))&&(dy <= zoom*(CHART_HEIGHT_AT_MAX_ZOOM+CHART_CLIP_BORDER)))
2160 {
2161 star.x = (float)(sys_coordinates.x * hscale + hoffset);
2162 star.y = (float)(sys_coordinates.y * vscale + voffset);
2163 OOGLBEGIN(GL_LINE_LOOP);
2164 glVertex3f(x + star.x - marker_size, y + star.y - marker_size, z);
2165 glVertex3f(x + star.x + marker_size, y + star.y - marker_size, z);
2166 glVertex3f(x + star.x + marker_size, y + star.y + marker_size, z);
2167 glVertex3f(x + star.x - marker_size, y + star.y + marker_size, z);
2168 OOGLEND();
2169 if (i == foundIndex || n_matches == 1)
2170 {
2171 if (n_matches == 1) foundSystem = 0;
2172 if (zoom > CHART_ZOOM_SHOW_LABELS && advancedNavArrayMode == OPTIMIZED_BY_NONE)
2173 {
2174 [self setGLColorFromSetting:kGuiChartMatchLabelColor defaultValue:[OOColor cyanColor] alpha:alpha];
2175 OODrawString([UNIVERSE systemNameIndex:i] , x + star.x + 2.0, y + star.y - 10.0f, z, NSMakeSize(10*systemNameScale,10*systemNameScale));
2176 [self setGLColorFromSetting:kGuiChartMatchBoxColor defaultValue:[OOColor greenColor] alpha:alpha];
2177 }
2178 }
2179 else if (zoom > CHART_ZOOM_SHOW_LABELS)
2180 {
2181 OODrawString([UNIVERSE systemNameIndex:i] , x + star.x + 2.0, y + star.y - 10.0f, z, NSMakeSize(10*systemNameScale,10*systemNameScale));
2182 }
2183 }
2184 }
2185 }
2186
2187 // draw names
2188 //
2189// OOGL(glColor4f(1.0f, 1.0f, 0.0f, alpha)); // yellow
2190
2191 int targetIdx = -1;
2192 struct saved_system *sys;
2193 NSSize chSize = NSMakeSize(pixel_row_height*systemNameScale/zoom,pixel_row_height*systemNameScale/zoom);
2194
2195 double jumpRange = MAX_JUMP_RANGE * [PLAYER dialFuel];
2196 for (i = 0; i < num_nearby_systems; i++)
2197 {
2198 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NONAME)
2199 {
2200 continue;
2201 }
2202
2203 sys = nearby_systems + i;
2204 NSPoint sys_coordinates = [systemManager getCoordinatesForSystem:sys->sysid inGalaxy:galaxy_id];
2205
2206 dx = fabs(chart_centre_coordinates.x - sys_coordinates.x);
2207 dy = fabs(chart_centre_coordinates.y - sys_coordinates.y);
2208
2210 continue;
2211 star.x = (float)(sys_coordinates.x * hscale + hoffset);
2212 star.y = (float)(sys_coordinates.y * vscale + voffset);
2213 if (sys->sysid == target) // not overlapping twin? (example: Divees & Tezabi in galaxy 5)
2214 {
2215 targetIdx = i; // we have a winner!
2216 }
2217
2218
2219
2220 if (zoom < CHART_ZOOM_SHOW_LABELS)
2221 {
2222 if (![player showInfoFlag]) // System's name
2223 {
2224
2225 d = distanceBetweenPlanetPositions(galaxy_coordinates.x, galaxy_coordinates.y, sys_coordinates.x, sys_coordinates.y);
2226 if (d <= jumpRange)
2227 {
2228 [self setGLColorFromSetting:kGuiChartLabelReachableColor defaultValue:[OOColor yellowColor] alpha:alpha];
2229 }
2230 else
2231 {
2232 [self setGLColorFromSetting:kGuiChartLabelColor defaultValue:[OOColor yellowColor] alpha:alpha];
2233
2234 }
2235
2236 OODrawString(sys->p_name, x + star.x + 2.0, y + star.y, z, chSize);
2237 }
2238 else if (EXPECT(sys->gov >= 0)) // Not a nova? Show the info.
2239 {
2240 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NODATA)
2241 {
2242 [self setGLColorFromSetting:kGuiChartLabelColor defaultValue:[OOColor yellowColor] alpha:alpha];
2243 OODrawHilightedString(@"???", x + star.x + 2.0, y + star.y, z, chSize);
2244 }
2245 else
2246 {
2247 OODrawPlanetInfo(sys->gov, sys->eco, sys->tec, x + star.x + 2.0, y + star.y + 2.0, z, chSize);
2248 }
2249 }
2250 }
2251 }
2252
2253 // highlight the name of the currently selected system
2254 // (needed to get things right in closely-overlapping systems)
2255 if( targetIdx != -1 && zoom <= CHART_ZOOM_SHOW_LABELS)
2256 {
2257 if (concealment[targetIdx] < OO_SYSTEMCONCEALMENT_NONAME)
2258 {
2259 sys = nearby_systems + targetIdx;
2260 NSPoint sys_coordinates = [systemManager getCoordinatesForSystem:sys->sysid inGalaxy:galaxy_id];
2261
2262 star.x = (float)(sys_coordinates.x * hscale + hoffset);
2263 star.y = (float)(sys_coordinates.y * vscale + voffset);
2264
2265 if (![player showInfoFlag])
2266 {
2267 d = distanceBetweenPlanetPositions(galaxy_coordinates.x, galaxy_coordinates.y, sys_coordinates.x, sys_coordinates.y);
2268 if (d <= jumpRange)
2269 {
2270 [self setGLColorFromSetting:kGuiChartLabelReachableColor defaultValue:[OOColor yellowColor] alpha:alpha];
2271 }
2272 else
2273 {
2274 [self setGLColorFromSetting:kGuiChartLabelColor defaultValue:[OOColor yellowColor] alpha:alpha];
2275
2276 }
2277
2278 OODrawHilightedString(sys->p_name, x + star.x + 2.0, y + star.y, z, chSize);
2279 }
2280 else if (sys->gov >= 0) // Not a nova? Show the info.
2281 {
2282 if (concealment[targetIdx] >= OO_SYSTEMCONCEALMENT_NODATA)
2283 {
2284 [self setGLColorFromSetting:kGuiChartLabelColor defaultValue:[OOColor yellowColor] alpha:alpha];
2285 OODrawHilightedString(@"???", x + star.x + 2.0, y + star.y, z, chSize);
2286 }
2287 else
2288 {
2289 OODrawHilightedPlanetInfo(sys->gov, sys->eco, sys->tec, x + star.x + 2.0, y + star.y + 2.0, z, chSize);
2290 }
2291 }
2292 }
2293 }
2294
2295 OOGUITabSettings tab_stops;
2296 tab_stops[0] = 0;
2297 tab_stops[1] = 96;
2298 tab_stops[2] = 288;
2299 [self overrideTabs:tab_stops from:kGuiChartTraveltimeTabs length:3];
2300 [self setTabStops:tab_stops];
2301 NSString *targetName = [[UNIVERSE getSystemName:target] retain];
2302
2303 // distance-f & est-travel-time-f are identical between short & long range charts in standard Oolite, however can be alterered separately via OXPs
2304 NSString *travelDistLine = @"";
2305 if (distance > 0)
2306 {
2307 travelDistLine = OOExpandKey(@"long-range-chart-distance", distance);
2308 }
2309 NSString *travelTimeLine = @"";
2310 if (time > 0)
2311 {
2312 travelTimeLine = OOExpandKey(@"long-range-chart-est-travel-time", time);
2313 }
2314
2315 if(concealment[target] < OO_SYSTEMCONCEALMENT_NONAME)
2316 {
2317 [self setArray:[NSArray arrayWithObjects:targetName, travelDistLine,travelTimeLine,nil] forRow:textRow];
2318 }
2319 else
2320 {
2321 [self setArray:[NSArray arrayWithObjects:@"", travelDistLine,travelTimeLine,nil] forRow:textRow];
2322 }
2323 if ([PLAYER guiScreen] == GUI_SCREEN_SHORT_RANGE_CHART)
2324 {
2325 if (jumps > 0)
2326 {
2327 [self setArray:[NSArray arrayWithObjects: @"", OOExpandKey(@"short-range-chart-jumps", jumps), nil] forRow: textRow + 1];
2328 }
2329 else
2330 {
2331 [self setArray:[NSArray array] forRow: textRow + 1];
2332 }
2333 }
2334 [targetName release];
2335
2336 // draw planet info circle
2337 OOGL(GLScaledLineWidth(2.0f));
2338 [self setGLColorFromSetting: kGuiChartInfoMarkerColor defaultValue:[OOColor blueColor] alpha:alpha];
2339 cu = NSMakePoint((float)(hscale*info_system_coordinates.x+hoffset),(float)(vscale*info_system_coordinates.y+voffset));
2340 GLDrawOval(x + cu.x, y + cu.y, z, NSMakeSize(6.0f/zoom+2.0f, 6.0f/zoom+2.0f), 5);
2341
2342 // disable draw clipping
2343 OOGL(glDisable(GL_SCISSOR_TEST));
2344
2345 // Draw bottom divider
2346 [self setGLColorFromSetting:kGuiScreenDividerColor defaultValue:[OOColor colorWithWhite:0.75 alpha:1.0] alpha:alpha];
2347 OOGLBEGIN(GL_QUADS);
2348 glVertex3f(x + 0, (float)(y + size_in_pixels.height - (textRow-1)*MAIN_GUI_ROW_HEIGHT - pixel_title_size.height), z);
2349 glVertex3f(x + size_in_pixels.width, (GLfloat)(y + size_in_pixels.height - (textRow-1)*MAIN_GUI_ROW_HEIGHT - pixel_title_size.height), z);
2350 glVertex3f(x + size_in_pixels.width, (GLfloat)(y + size_in_pixels.height - (textRow-1)*MAIN_GUI_ROW_HEIGHT - pixel_title_size.height - 2), z);
2351 glVertex3f(x + 0, (GLfloat)(y + size_in_pixels.height - (textRow-1)*MAIN_GUI_ROW_HEIGHT - pixel_title_size.height - 2), z);
2352 OOGLEND();
2353}
2354
2355
2356- (void) drawSystemMarkers:(NSArray *)markers atX:(GLfloat)x andY:(GLfloat)y andZ:(GLfloat)z withAlpha:(GLfloat)alpha andScale:(GLfloat)scale
2357{
2358 NSEnumerator *mEnum;
2359 NSDictionary *marker;
2360 for (mEnum = [markers objectEnumerator]; (marker = [mEnum nextObject]); )
2361 {
2362 [self drawSystemMarker:marker atX:x andY:y andZ:z withAlpha:alpha andScale:scale];
2363 }
2364}
2365
2366
2367- (void) drawSystemMarker:(NSDictionary *)marker atX:(GLfloat)x andY:(GLfloat)y andZ:(GLfloat)z withAlpha:(GLfloat)alpha andScale:(GLfloat)scale
2368{
2369 NSString *colorDesc = [marker oo_stringForKey:@"markerColor" defaultValue:@"redColor"];
2371
2372 OOGL(glColor4f(color.r, color.g, color.b, alpha)); // red
2373 GLfloat mark_size = [marker oo_floatForKey:@"markerScale" defaultValue:1.0];
2374 if (mark_size > 2.0)
2375 {
2376 mark_size = 2.0;
2377 }
2378 else if (mark_size < 0.5)
2379 {
2380 mark_size = 0.5;
2381 }
2382 mark_size *= scale;
2383
2384 NSString *shape = [marker oo_stringForKey:@"markerShape" defaultValue:@"MARKER_X"];
2385
2386 OOGLBEGIN(GL_LINES);
2387 if ([shape isEqualToString:@"MARKER_X"])
2388 {
2389 glVertex3f(x - mark_size, y - mark_size, z);
2390 glVertex3f(x + mark_size, y + mark_size, z);
2391 glVertex3f(x - mark_size, y + mark_size, z);
2392 glVertex3f(x + mark_size, y - mark_size, z);
2393 }
2394 else if ([shape isEqualToString:@"MARKER_PLUS"])
2395 {
2396 mark_size *= 1.4; // match volumes
2397 glVertex3f(x, y - mark_size, z);
2398 glVertex3f(x, y + mark_size, z);
2399 glVertex3f(x - mark_size, y, z);
2400 glVertex3f(x + mark_size, y, z);
2401 }
2402 else if ([shape isEqualToString:@"MARKER_SQUARE"])
2403 {
2404 glVertex3f(x - mark_size, y - mark_size, z);
2405 glVertex3f(x - mark_size, y + mark_size, z);
2406 glVertex3f(x - mark_size, y + mark_size, z);
2407 glVertex3f(x + mark_size, y + mark_size, z);
2408 glVertex3f(x + mark_size, y + mark_size, z);
2409 glVertex3f(x + mark_size, y - mark_size, z);
2410 glVertex3f(x + mark_size, y - mark_size, z);
2411 glVertex3f(x - mark_size, y - mark_size, z);
2412 }
2413 else if ([shape isEqualToString:@"MARKER_DIAMOND"])
2414 {
2415 mark_size *= 1.4; // match volumes
2416 glVertex3f(x, y - mark_size, z);
2417 glVertex3f(x - mark_size, y, z);
2418 glVertex3f(x - mark_size, y, z);
2419 glVertex3f(x, y + mark_size, z);
2420 glVertex3f(x, y + mark_size, z);
2421 glVertex3f(x + mark_size, y, z);
2422 glVertex3f(x + mark_size, y, z);
2423 glVertex3f(x, y - mark_size, z);
2424 }
2425 OOGLEND();
2426}
2427
2428
2429- (OOSystemID) targetNextFoundSystem:(int)direction // +1 , 0 , -1
2430{
2431 OOSystemID sys = [PLAYER targetSystemID];
2432 if ([PLAYER guiScreen] != GUI_SCREEN_SHORT_RANGE_CHART && [PLAYER guiScreen] != GUI_SCREEN_LONG_RANGE_CHART) return sys;
2433
2434 BOOL *systemsFound = [UNIVERSE systemsFound];
2435 unsigned i, first = 0, last = 0, count = 0;
2436 int systemIndex = foundSystem + direction;
2437
2438 if (direction == 0) systemIndex = 0;
2439
2440 for (i = 0; i <= kOOMaximumSystemID; i++)
2441 {
2442 if (systemsFound[i])
2443 {
2444 if (count == 0)
2445 {
2446 first = last = i;
2447 }
2448 else
2449 {
2450 last = i;
2451 }
2452 if (systemIndex == (int)count)
2453 {
2454 sys = i;
2455 }
2456 count++;
2457 }
2458 }
2459
2460 if (count == 0) return sys; // empty systemFound list.
2461
2462 // loop back if needed.
2463 if (systemIndex < 0)
2464 {
2465 systemIndex = count - 1;
2466 sys = last;
2467 }
2468 if (systemIndex >= (int)count)
2469 {
2470 systemIndex = 0;
2471 sys = first;
2472 }
2473
2474 foundSystem = systemIndex;
2475 return sys;
2476}
2477
2478
2479// Advanced Navigation Array -- galactic chart route mapping - contributed by Nikos Barkas (another_commander).
2480- (void) drawAdvancedNavArrayAtX:(float)x y:(float)y z:(float)z alpha:(float)alpha usingRoute:(NSDictionary *) routeInfo optimizedBy:(OORouteType) optimizeBy zoom: (OOScalar) zoom
2481{
2482 GLfloat lr,lg,lb,la,lr2,lg2,lb2,la2;
2483 double hscale = size_in_pixels.width / (CHART_WIDTH_AT_MAX_ZOOM*zoom);
2484 double vscale = -1.0 * size_in_pixels.height / (2*CHART_HEIGHT_AT_MAX_ZOOM*zoom);
2485 NSPoint star = NSZeroPoint,
2486 star2 = NSZeroPoint,
2487 starabs = NSZeroPoint,
2488 star2abs = NSZeroPoint;
2489 OOSystemDescriptionManager *systemManager = [UNIVERSE systemManager];
2490 OOGalaxyID g = [PLAYER galaxyNumber];
2491 OOSystemID planetNumber = [PLAYER systemID];
2492
2493 OOColor *defaultConnectionColor = [self colorFromSetting:kGuiChartConnectionColor defaultValue:[OOColor colorWithWhite:0.25 alpha:1.0]];
2494 OOColor *currentJumpColorStart = [self colorFromSetting:kGuiChartCurrentJumpStartColor defaultValue:[OOColor colorWithWhite:0.25 alpha:0.0]];
2495 OOColor *currentJumpColorEnd = [self colorFromSetting:kGuiChartCurrentJumpEndColor defaultValue:[OOColor colorWithWhite:0.25 alpha:0.0]];
2496
2497 OOColor *thisConnectionColor = nil;
2498 OOColor *thatConnectionColor = nil;
2499
2500 float jumpRange = MAX_JUMP_RANGE * ((optimizeBy == OPTIMIZED_BY_NONE) ? [PLAYER dialFuel] : 1.0);
2501
2502 NSInteger concealment[256];
2503 for (NSUInteger i=0;i<256;i++) {
2504 NSDictionary *systemInfo = [systemManager getPropertiesForSystem:i inGalaxy:g];
2505 concealment[i] = [systemInfo oo_intForKey:@"concealment" defaultValue:OO_SYSTEMCONCEALMENT_NONE];
2506 }
2507
2508
2509 OOGLBEGIN(GL_LINES);
2510 for (OOSystemID i = 0; i < 256; i++)
2511 {
2512
2513 if (concealment[i] >= OO_SYSTEMCONCEALMENT_NOTHING) {
2514 // system is not known
2515 continue;
2516 }
2517
2518 /* Concealment */
2519 if (optimizeBy == OPTIMIZED_BY_NONE && i != planetNumber)
2520 {
2521 continue;
2522 }
2523
2525
2526 star.x = (float)(starabs.x * hscale);
2527 star.y = (float)(starabs.y * vscale);
2528
2529 // if in non-route mode, we're always starting from i, so need
2530 // to do <i here too.
2531 OOSystemID loopstart = (optimizeBy == OPTIMIZED_BY_NONE) ? 0 : (i+1);
2532
2533 for (OOSystemID j = loopstart; j < 256; j++)
2534 {
2535 if (i == j)
2536 {
2537 continue; // for OPTIMIZED_BY_NONE case
2538 }
2539
2540 if (concealment[j] >= OO_SYSTEMCONCEALMENT_NOTHING) {
2541 // system is not known
2542 continue;
2543 }
2544
2546 double d = distanceBetweenPlanetPositions(starabs.x, starabs.y, star2abs.x, star2abs.y);
2547
2548 if (d <= jumpRange) // another_commander - Default to 7.0 LY.
2549 {
2550 star2.x = (float)(star2abs.x * hscale);
2551 star2.y = (float)(star2abs.y * vscale);
2552 if (optimizeBy == OPTIMIZED_BY_NONE)
2553 {
2554 [currentJumpColorStart getRed:&lr green:&lg blue:&lb alpha:&la];
2555 [currentJumpColorEnd getRed:&lr2 green:&lg2 blue:&lb2 alpha:&la2];
2556 OOGL(glColor4f(lr, lg, lb, la*alpha));
2557 glVertex3f(x+star.x, y+star.y, z);
2558
2559 float frac = (d/jumpRange);
2560 OOGL(glColor4f(
2561 OOLerp(lr,lr2,frac),
2562 OOLerp(lg,lg2,frac),
2563 OOLerp(lb,lb2,frac),
2564 OOLerp(la,la2,frac)
2565 ));
2566 glVertex3f(x+star2.x, y+star2.y, z);
2567
2568 }
2569 else
2570 {
2571 thisConnectionColor = [OOColor colorWithDescription:[systemManager getProperty:@"link_color" forSystemKey:[NSString stringWithFormat:@"interstellar: %d %ld %ld", g, (long)i, (long)j]]];
2572
2573 if (thisConnectionColor == nil)
2574 {
2575 thisConnectionColor = defaultConnectionColor;
2576 }
2577 [thisConnectionColor getRed:&lr green:&lg blue:&lb alpha:&la];
2578 OOGL(glColor4f(lr, lg, lb, la*alpha));
2579
2580 glVertex3f(x+star.x, y+star.y, z);
2581
2582 // and the other colour for the other end
2583 thatConnectionColor = [OOColor colorWithDescription:[systemManager getProperty:@"link_color" forSystemKey:[NSString stringWithFormat:@"interstellar: %d %ld %ld", g, (long)j, (long)i]]];
2584
2585 if (thatConnectionColor == nil)
2586 {
2587 thatConnectionColor = thisConnectionColor;
2588 }
2589 [thatConnectionColor getRed:&lr green:&lg blue:&lb alpha:&la];
2590 OOGL(glColor4f(lr, lg, lb, la*alpha));
2591
2592 glVertex3f(x+star2.x, y+star2.y, z);
2593 }
2594 }
2595 }
2596 }
2597 OOGLEND();
2598
2599 if (optimizeBy == OPTIMIZED_BY_NONE)
2600 {
2601 return;
2602 }
2603
2604 if (routeInfo)
2605 {
2606 NSUInteger i, route_hops = [[routeInfo oo_arrayForKey:@"route"] count] - 1;
2607
2608 if (optimizeBy == OPTIMIZED_BY_JUMPS)
2609 {
2610 // route optimised by distance
2611 [self setGLColorFromSetting:kGuiChartRouteShortColor defaultValue:[OOColor yellowColor] alpha:alpha];
2612 }
2613 else
2614 {
2615 // route optimised by time
2616 [self setGLColorFromSetting:kGuiChartRouteQuickColor defaultValue:[OOColor cyanColor] alpha:alpha];
2617 }
2618 OOSystemID loc;
2619 for (i = 0; i < route_hops; i++)
2620 {
2621 loc = [[routeInfo objectForKey:@"route"] oo_intAtIndex:i];
2623 star2abs = [systemManager getCoordinatesForSystem:[[routeInfo objectForKey:@"route"] oo_intAtIndex:i+1] inGalaxy:g];
2624
2625 star.x = (float)(starabs.x * hscale);
2626 star.y = (float)(starabs.y * vscale);
2627
2628 star2.x = (float)(star2abs.x * hscale);
2629 star2.y = (float)(star2abs.y * vscale);
2630
2631
2632 OOGLBEGIN(GL_LINES);
2633 glVertex3f(x+star.x, y+star.y, z);
2634 glVertex3f(x+star2.x, y+star2.y, z);
2635 OOGLEND();
2636
2637 // Label the route, if not already labelled
2638 if (zoom > CHART_ZOOM_SHOW_LABELS && concealment[loc] < OO_SYSTEMCONCEALMENT_NONAME)
2639 {
2640 OODrawString([UNIVERSE systemNameIndex:loc], x + star.x + 2.0, y + star.y, z, NSMakeSize(8,8));
2641 }
2642 }
2643 // Label the destination, which was not included in the above loop.
2644 if (zoom > CHART_ZOOM_SHOW_LABELS)
2645 {
2646 loc = [[routeInfo objectForKey:@"route"] oo_intAtIndex:i];
2647 if(concealment[loc] < OO_SYSTEMCONCEALMENT_NONAME)
2648 {
2649 OODrawString([UNIVERSE systemNameIndex:loc], x + star2.x + 2.0, y + star2.y, z, NSMakeSize(10,10));
2650 }
2651 }
2652 }
2653}
2654
2655@end
#define MAIN_GUI_PIXEL_ROW_START
#define GUI_KEY_SKIP
#define GUI_MAX_COLUMNS
OOGUIBackgroundSpecial
@ GUI_BACKGROUND_SPECIAL_CUSTOM_ANA_QUICKEST
@ GUI_BACKGROUND_SPECIAL_SHORT_ANA_SHORTEST
@ GUI_BACKGROUND_SPECIAL_LONG
@ GUI_BACKGROUND_SPECIAL_LONG_ANA_SHORTEST
@ GUI_BACKGROUND_SPECIAL_SHORT
@ GUI_BACKGROUND_SPECIAL_NONE
@ GUI_BACKGROUND_SPECIAL_SHORT_ANA_QUICKEST
@ GUI_BACKGROUND_SPECIAL_LONG_ANA_QUICKEST
@ GUI_BACKGROUND_SPECIAL_CUSTOM
@ GUI_BACKGROUND_SPECIAL_CUSTOM_ANA_SHORTEST
OOGUITabStop OOGUITabSettings[GUI_MAX_COLUMNS]
#define MAIN_GUI_PIXEL_WIDTH
#define MAIN_GUI_PIXEL_HEIGHT
#define GUI_DEFAULT_ROWS
#define MAIN_GUI_ROW_HEIGHT
NSInteger OOGUIRow
OOGUIAlignment
@ GUI_ALIGN_RIGHT
@ GUI_ALIGN_LEFT
@ GUI_ALIGN_CENTER
#define GUI_DEFAULT_COLUMNS
static BOOL _refreshStarChart
OOINLINE BOOL RowInRange(OOGUIRow row, NSRange range)
void OODrawHilightedString(NSString *text, GLfloat x, GLfloat y, GLfloat z, NSSize siz)
void OODrawStringQuadsAligned(NSString *text, GLfloat x, GLfloat y, GLfloat z, NSSize siz, BOOL rightAlign)
void OOStartDrawingStrings(void)
NSRect OORectFromString(NSString *text, GLfloat x, GLfloat y, NSSize siz)
void OODrawHilightedPlanetInfo(int gov, int eco, int tec, GLfloat x, GLfloat y, GLfloat z, NSSize siz)
void OODrawString(NSString *text, GLfloat x, GLfloat y, GLfloat z, NSSize siz)
void OODrawPlanetInfo(int gov, int eco, int tec, GLfloat x, GLfloat y, GLfloat z, NSSize siz)
void OOStopDrawingStrings(void)
OOINLINE long long OOClampInteger(long long value, long long minValue, long long maxValue) ALWAYS_INLINE_FUNC
#define EXPECT_NOT(x)
#define OOINLINE
#define EXPECT(x)
#define OOJS_PROFILE_EXIT
#define OOJS_PROFILE_ENTER
void OOJSReportWarning(JSContext *context, NSString *format,...)
NSDictionary * OOJSDictionaryFromJSObject(JSContext *context, JSObject *object)
NSString * OOStringFromJSValue(JSContext *context, jsval value)
OOINLINE JSClass * OOJSGetClass(JSContext *cx, JSObject *obj) ALWAYS_INLINE_FUNC
#define OOLog(class, format,...)
Definition OOLogging.h:88
#define MIN(A, B)
Definition OOMaths.h:111
GLfloat OOScalar
Definition OOMaths.h:64
BOOL OOMouseInteractionModeIsUIScreen(OOMouseInteractionMode mode)
#define OOGLBEGIN
Definition OOOpenGL.h:253
void GLDrawFilledOval(GLfloat x, GLfloat y, GLfloat z, NSSize siz, GLfloat step)
Definition OOOpenGL.m:165
void GLScaledLineWidth(GLfloat width)
Definition OOOpenGL.m:218
void GLDrawOval(GLfloat x, GLfloat y, GLfloat z, NSSize siz, GLfloat step)
Definition OOOpenGL.m:155
#define OOGL(statement)
Definition OOOpenGL.h:251
#define OOGLEND
Definition OOOpenGL.h:254
unsigned count
return nil
float y
float x
#define OOExpandKey(key,...)
NSMutableArray * ScanTokensFromString(NSString *values)
@ OO_SYSTEMCONCEALMENT_NODATA
@ OO_SYSTEMCONCEALMENT_NOTHING
@ OO_SYSTEMCONCEALMENT_NONAME
@ kOOTextureSRGBA
Definition OOTexture.h:63
OOLongRangeChartMode
Definition OOTypes.h:50
@ kOOMaximumSystemID
Definition OOTypes.h:217
OORouteType
Definition OOTypes.h:33
@ OPTIMIZED_BY_NONE
Definition OOTypes.h:34
@ OPTIMIZED_BY_JUMPS
Definition OOTypes.h:35
@ OPTIMIZED_BY_TIME
Definition OOTypes.h:36
int16_t OOSystemID
Definition OOTypes.h:211
uint8_t OOGalaxyID
Definition OOTypes.h:210
double OOTimeDelta
Definition OOTypes.h:224
double OOTimeAbsolute
Definition OOTypes.h:223
#define CHART_SCREEN_VERTICAL_CENTRE
#define CHART_SCREEN_VERTICAL_CENTRE_COMPACT
#define CHART_WIDTH_AT_MAX_ZOOM
#define CHART_ZOOM_SHOW_LABELS
#define CHART_MAX_ZOOM
#define CHART_HEIGHT_AT_MAX_ZOOM
@ STATUS_EQUIPMENT_FIRST_ROW
@ GUI_ROW_CHART_SYSTEM_COMPACT
@ STATUS_EQUIPMENT_MAX_ROWS
@ GUI_ROW_CHART_SYSTEM
@ STATUS_EQUIPMENT_BIGGUI_EXTRA_ROWS
#define PLAYER
#define CHART_CLIP_BORDER
#define MAX_JUMP_RANGE
Definition ShipEntity.h:107
#define UNIVERSE
Definition Universe.h:840
OOTextureSprite * foregroundSprite
unsigned n_columns
NSRange selectableRange
void scrollUp:(int how_much)
OOColor * colorFromSetting:defaultValue:(NSString *setting,[defaultValue] OOColor *def)
BOOL setSelectedRow:(OOGUIRow row)
NSMutableArray * rowColor
float rowFadeTime[GUI_MAX_ROWS]
OOTextureSprite * backgroundSprite
OOGUIRow addLongText:startingAtRow:align:(NSString *str,[startingAtRow] OOGUIRow row,[align] OOGUIAlignment alignment)
void drawSystemMarker:atX:andY:andZ:withAlpha:andScale:(NSDictionary *marker, [atX] GLfloat x, [andY] GLfloat y, [andZ] GLfloat z, [withAlpha] GLfloat alpha, [andScale] GLfloat scale)
static OOTextureSprite * NewTextureSpriteWithDescriptor(NSDictionary *descriptor)
NSString * selectedRowText()
OOSystemID foundSystem
void setText:forRow:(NSString *str,[forRow] OOGUIRow row)
void setText:forRow:align:(NSString *str,[forRow] OOGUIRow row,[align] OOGUIAlignment alignment)
void drawSystemMarkers:atX:andY:andZ:withAlpha:andScale:(NSArray *markers, [atX] GLfloat x, [andY] GLfloat y, [andZ] GLfloat z, [withAlpha] GLfloat alpha, [andScale] GLfloat scale)
OOColor * textColor
OOGUIBackgroundSpecial backgroundSpecial
void clearAndKeepBackground:(BOOL keepBackground)
NSSize pixel_text_size
void drawEquipmentList:z:(NSArray *eqptList, [z] GLfloat z)
NSArray * getLastLines()
BOOL setForegroundTextureDescriptor:(NSDictionary *descriptor)
OOGUIRow selectedRow
void overrideTabs:from:length:(OOGUITabSettings stops,[from] NSString *setting,[length] NSUInteger len)
NSDictionary * userSettings()
NSMutableArray * rowText
void setSelectableRange:(NSRange range)
OOGUIAlignment rowAlignment[GUI_MAX_ROWS]
void setColor:forRow:(OOColor *color,[forRow] OOGUIRow row)
NSString * selectedRowKey()
NSSize size_in_pixels
NSString * title
static OOTexture * TextureForGUITexture(NSDictionary *descriptor)
id objectForRow:(OOGUIRow row)
NSSize pixel_title_size
void drawCrossHairsWithSize:x:y:z:(GLfloat size, [x] GLfloat x, [y] GLfloat y, [z] GLfloat z)
OOGUIRow currentRow
void setGLColorFromSetting:defaultValue:alpha:(NSString *setting,[defaultValue] OOColor *def,[alpha] GLfloat alpha)
void reportSelectedRow:(int row)
void printLongText:align:color:fadeTime:key:addToArray:(NSString *str,[align] OOGUIAlignment alignment,[color] OOColor *text_color,[fadeTime] float text_fade,[key] NSString *text_key,[addToArray] NSMutableArray *text_array)
unsigned columns()
OOGUITabSettings tabStops
void setTitle:(NSString *str)
void setTabStops:(OOGUITabSettings stops)
BOOL setLastSelectableRow()
NSString * keyForRow:(OOGUIRow row)
NSUInteger statusPage
unsigned pixel_row_height
void drawAdvancedNavArrayAtX:y:z:alpha:usingRoute:optimizedBy:zoom:(float x, [y] float y, [z] float z, [alpha] float alpha, [usingRoute] NSDictionary *routeInfo, [optimizedBy] OORouteType optimizeBy, [zoom] OOScalar zoom)
void setShowTextCursor:(BOOL yesno)
BOOL setFirstSelectableRow()
NSMutableArray * rowKey
NSDictionary * guiUserSettings
BOOL setBackgroundTextureDescriptor:(NSDictionary *descriptor)
BOOL showAdvancedNavArray
NSPoint rowPosition[GUI_MAX_ROWS]
OOColor * backgroundColor
OOColor * textCommsColor
void setArray:forRow:(NSArray *arr,[forRow] OOGUIRow row)
unsigned rowHeight()
void setKey:forRow:(NSString *str,[forRow] OOGUIRow row)
OOColor * cyanColor()
Definition OOColor.m:286
OOColor * colorWithRed:green:blue:alpha:(float red,[green] float green,[blue] float blue,[alpha] float alpha)
Definition OOColor.m:95
OOColor * colorWithWhite:alpha:(float white,[alpha] float alpha)
Definition OOColor.m:103
OOColor * orangeColor()
Definition OOColor.m:304
OOColor * colorWithDescription:(id description)
Definition OOColor.m:127
OOColor * redColor()
Definition OOColor.m:268
OOColor * greenColor()
Definition OOColor.m:274
void getRed:green:blue:alpha:(float *red,[green] float *green,[blue] float *blue,[alpha] float *alpha)
Definition OOColor.m:368
OOColor * blueColor()
Definition OOColor.m:280
OOColor * yellowColor()
Definition OOColor.m:292
OOColor * blackColor()
Definition OOColor.m:238
OORGBAComponents rgbaComponents()
Definition OOColor.m:379
NSPoint getCoordinatesForSystem:inGalaxy:(OOSystemID s,[inGalaxy] OOGalaxyID g)
NSDictionary * getPropertiesForSystem:inGalaxy:(OOSystemID s,[inGalaxy] OOGalaxyID g)
id getProperty:forSystemKey:(NSString *property,[forSystemKey] NSString *key)
void blitBackgroundCentredToX:Y:Z:alpha:(float x,[Y] float y,[Z] float z,[alpha] float a)
NSSize originalDimensions()
Definition OOTexture.m:313
void applyNone()
Definition OOTexture.m:275
id textureWithName:inFolder:options:anisotropy:lodBias:(NSString *name,[inFolder] NSString *directory,[options] OOTextureFlags options,[anisotropy] GLfloat anisotropy,[lodBias] GLfloat lodBias)
Definition OOTexture.m:134
OOLongRangeChartMode longRangeChartMode
OOGalaxyID galaxyNumber()
NSArray * equipmentList()
OORouteType ANAMode()
NSPoint galaxy_coordinates
void stickProfileGraphAxisProfile:screenAt:screenSize:(GLfloat alpha,[screenAt] Vector screenAt,[screenSize] NSSize screenSize)
NSPoint cursor_coordinates
OOScalar chart_zoom
OOSystemID infoSystemID()
NSPoint adjusted_chart_centre()
NSDictionary * markedDestinations()
GLfloat dialFuel()
NSDictionary * dictionaryFromFilesNamed:inFolder:andMerge:(NSString *fileName,[inFolder] NSString *folderName,[andMerge] BOOL mergeFiles)
voidpf void uLong size
Definition ioapi.h:134
typedef int(ZCALLBACK *close_file_func) OF((voidpf opaque
OOINLINE double distanceBetweenPlanetPositions(int x1, int y1, int x2, int y2) INLINE_CONST_FUNC