1/* 2 This file is part of HelpViewer (http://www.roard.com/helpviewer) 3 Copyright (C) 2003 Nicolas Roard (nicolas@roard.com) 4 5 This program is free software; you can redistribute it and/or modify 6 it under the terms of the GNU General Public License as published by 7 the Free Software Foundation; either version 2 of the License, or 8 (at your option) any later version. 9 10 This program is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 GNU General Public License for more details. 14 15 You should have received a copy of the GNU General Public License 16 along with this program; if not, write to the Free Software 17 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. 18*/ 19 20#include "FigureCell.h" 21 22@implementation FigureCell 23 24- (id) initWithSize: (NSSize) size 25{ 26 [super init]; 27 _size = size; 28 _image = nil; 29 _legends = nil; 30 return self; 31} 32 33- (void) setLegends: (NSArray*) legends 34{ 35 ASSIGN (_legends, legends); 36} 37 38- (void) setImage: (NSImage*) img 39{ 40 ASSIGN (_image, img); 41} 42 43- (NSSize) cellSize 44{ 45 return _size; 46} 47 48- (void) resize: (id) sender 49{ 50 [self resizeWithTextView: [sender object]]; 51} 52 53- (void) resizeWithTextView: (NSTextView*) textView 54{ 55 float minimalHeight; 56 float imageWidth = [_image size].width; 57 float imageHeight = [_image size].height; 58 59 if (_legends) 60 { 61 int i; 62 float interspace = 20; 63 float spaceMargin = 20; 64 float border = 12; 65 float Margin = ([textView bounds].size.width - imageWidth - 2*spaceMargin - 2*border)/2; 66 67 NSMutableParagraphStyle* paragraph = [NSMutableParagraphStyle new]; 68 [paragraph setAlignment: NSLeftTextAlignment]; 69 [paragraph setTailIndent: Margin]; 70 [paragraph setHeadIndent: 0.0]; 71 [paragraph setFirstLineHeadIndent: 0.0]; 72 73 NSDictionary* attributes = [NSDictionary dictionaryWithObject: paragraph 74 forKey: NSParagraphStyleAttributeName]; 75 76 NSMutableArray* preLeftLegends = [NSMutableArray array]; 77 NSMutableArray* preRightLegends = [NSMutableArray array]; 78 79 for (i=0; i<[_legends count]; i++) 80 { 81 Legend* current = [_legends objectAtIndex: i]; 82 [[current legend] addAttributes: attributes 83 range: NSMakeRange (0, [[current legend] length])]; 84 NSSize s = [[current legend] size]; 85 86 [current setHeight: s.height]; 87 if ([current point].x > (imageWidth/2)) 88 { 89 [current setRightPos]; // on range � droite 90 [preRightLegends addObject: current]; 91 } 92 else 93 { 94 [preLeftLegends addObject: current]; 95 } 96 } 97 98 NSArray* LeftLegends = [preLeftLegends sortedArrayUsingSelector: @selector (compareLegends:)]; 99 NSArray* RightLegends = [preRightLegends sortedArrayUsingSelector: @selector (compareLegends:)]; 100 101 float LeftLegendsHeight = 0; 102 float RightLegendsHeight = 0; 103 104 for (i=0; i < [LeftLegends count]; i++) 105 { 106 LeftLegendsHeight += [[LeftLegends objectAtIndex: i] height]; 107 } 108 109 for (i=0; i < [RightLegends count]; i++) 110 { 111 RightLegendsHeight += [[RightLegends objectAtIndex: i] height]; 112 } 113 114 float minimalInterspace = 8; 115 116 minimalHeight = LeftLegendsHeight+([LeftLegends count]+1)*minimalInterspace; 117 118 if (imageHeight < minimalHeight) imageHeight = minimalHeight; 119 } 120 121 _size = NSMakeSize ([textView bounds].size.width, imageHeight); 122} 123 124- (void) drawLegends: (NSArray*) legends onRight: (BOOL) right 125 withInterspace: (float) interspace withAttributes: (NSDictionary*) attributes 126 withFrame: (NSRect) cellFrame withBorder: (float) border withMargin: (float) Margin 127 withSpaceMargin: (float) spaceMargin withImageWidth: (float) imageWidth withPosImage: (float) posImage 128{ 129 float posY = interspace; 130 int i; 131 for (i=0; i < [legends count]; i++) 132 { 133 NSRect r; 134 NSPoint t, tp, p; 135 Legend* current = [legends objectAtIndex: i]; 136 [[current legend] addAttributes: attributes 137 range: NSMakeRange (0, [[current legend] length])]; 138 NSSize s = [[current legend] size]; 139// NSSize s = [[current legend] sizeWithAttributes: attributes]; 140 141 if (!right) 142 { 143 r = NSMakeRect (cellFrame.origin.x + border + (Margin-s.width) - 2, cellFrame.origin.y + posY - 2, s.width + 4, s.height + 4); 144 t = NSMakePoint (cellFrame.origin.x + border + (Margin-s.width), cellFrame.origin.y + posY); 145 tp = NSMakePoint (cellFrame.origin.x + border + Margin + 2, cellFrame.origin.y + posY + s.height/2); 146 } 147 else 148 { 149 r = NSMakeRect (cellFrame.origin.x + border + Margin + (2*spaceMargin) + imageWidth - 2, 150 cellFrame.origin.y + posY - 2, s.width + 4, s.height + 4); 151 t = NSMakePoint (cellFrame.origin.x + border + Margin + (2*spaceMargin) + imageWidth, 152 cellFrame.origin.y + posY); 153 tp = NSMakePoint (cellFrame.origin.x + border + Margin + (2*spaceMargin) + imageWidth - 2, 154 cellFrame.origin.y + posY + s.height/2); 155 } 156 157 p = NSMakePoint (cellFrame.origin.x + border + Margin + spaceMargin + [current point].x, 158 cellFrame.origin.y + [current point].y + posImage); 159 160 // [[NSBezierPath bezierPathWithRect: r] stroke]; 161 [[NSColor colorWithCalibratedRed: 0.81 green: 0.84 blue: 0.88 alpha:1.0] set]; 162 NSBezierPath* path = [[NSBezierPath alloc] init]; 163 164 float radius = 8; 165 166 NSPoint p1 = NSMakePoint (r.origin.x, r.origin.y + radius); 167 NSPoint p2 = NSMakePoint (r.origin.x, r.origin.y + r.size.height - radius); 168 NSPoint p3 = NSMakePoint (r.origin.x + radius, r.origin.y + r.size.height); 169 NSPoint p4 = NSMakePoint (r.origin.x + r.size.width - radius, r.origin.y + r.size.height); 170 NSPoint p5 = NSMakePoint (r.origin.x + r.size.width, r.origin.y + r.size.height - radius); 171 NSPoint p6 = NSMakePoint (r.origin.x + r.size.width, r.origin.y + radius); 172 NSPoint p7 = NSMakePoint (r.origin.x + r.size.width - radius, r.origin.y); 173 NSPoint p8 = NSMakePoint (r.origin.x + radius, r.origin.y); 174 175 NSPoint pr1 = NSMakePoint (r.origin.x + radius, r.origin.y + r.size.height - radius); 176 NSPoint pr2 = NSMakePoint (r.origin.x + r.size.width - radius, r.origin.y + r.size.height - radius); 177 NSPoint pr3 = NSMakePoint (r.origin.x + r.size.width - radius, r.origin.y + radius); 178 NSPoint pr4 = NSMakePoint (r.origin.x + radius, r.origin.y + radius); 179 180 [path moveToPoint: p1]; 181 [path lineToPoint: p2]; 182 //[path appendBezierPathWithArcFromPoint: p2 toPoint: p3 radius: radius]; 183 [path appendBezierPathWithArcWithCenter: pr1 radius: radius startAngle: 180 endAngle: 90 clockwise: YES]; 184 //[path moveToPoint: p3]; 185 [path lineToPoint: p4]; 186 //[path appendBezierPathWithArcFromPoint: p4 toPoint: p5 radius: radius]; 187 [path appendBezierPathWithArcWithCenter: pr2 radius: radius startAngle: 90 endAngle: 0 clockwise: YES]; 188 //[path moveToPoint: p5]; 189 [path lineToPoint: p6]; 190 //[path appendBezierPathWithArcFromPoint: p6 toPoint: p7 radius: radius]; 191 [path appendBezierPathWithArcWithCenter: pr3 radius: radius startAngle: 0 endAngle: 270 clockwise: YES]; 192 //[path moveToPoint: p7]; 193 [path lineToPoint: p8]; 194 //[path appendBezierPathWithArcFromPoint: p8 toPoint: p1 radius: radius]; 195 [path appendBezierPathWithArcWithCenter: pr4 radius: radius startAngle: 270 endAngle: 180 clockwise: YES]; 196 [path fill]; 197// [[current legend] drawAtPoint: t withAttributes: attributes]; 198 [[current legend] drawAtPoint: t]; 199 NSBezierPath* path2 = [NSBezierPath bezierPath]; 200 201 [path2 moveToPoint: tp]; 202 [path2 lineToPoint: p]; 203 [path2 stroke]; 204 205 posY += s.height + interspace; 206 } 207} 208 209 210- (void) drawWithFrame: (NSRect) cellFrame 211 inView: (NSView*) controlView 212{ 213 if (![controlView window]) return; 214 215 [controlView lockFocus]; 216 217 [[NSColor whiteColor] set]; 218 NSRectFill (cellFrame); 219 220 //NSLog (@"drawInteriorWithFrame de FigureCell ... "); 221 //NSLog (@"image : %@", _image); 222 //NSLog (@"cellframe origin x : %.2f origin y : %.2f", cellFrame.origin.x, cellFrame.origin.y); 223 NSLog (@"cellFrame height : %.2f", cellFrame.size.height); 224 225 if (_legends) 226 { 227 228 int i; 229 float interspace = 20; 230 float imageWidth = [_image size].width; 231 float imageHeight = [_image size].height; 232 float spaceMargin = 20; 233 float border = 12; 234 float Margin = (cellFrame.size.width - imageWidth - 2*spaceMargin - 2*border)/2; 235 236 float posImage = 0; 237 if (imageHeight < cellFrame.size.height) 238 { 239 posImage = (cellFrame.size.height - imageHeight)/2; 240 } 241 NSPoint imageOrigin = NSMakePoint (cellFrame.origin.x + border + Margin + spaceMargin, 242 cellFrame.origin.y + imageHeight + posImage); 243 [_image compositeToPoint: imageOrigin operation: NSCompositeSourceAtop]; 244 245 NSMutableParagraphStyle* paragraph = [NSMutableParagraphStyle new]; 246 [paragraph setAlignment: NSLeftTextAlignment]; 247 [paragraph setTailIndent: Margin]; 248 [paragraph setHeadIndent: 0.0]; 249 [paragraph setFirstLineHeadIndent: 0.0]; 250 251 NSDictionary* attributes = [NSDictionary dictionaryWithObject: paragraph 252 forKey: NSParagraphStyleAttributeName]; 253 254 NSMutableArray* preLeftLegends = [NSMutableArray array]; 255 NSMutableArray* preRightLegends = [NSMutableArray array]; 256 257 for (i=0; i<[_legends count]; i++) 258 { 259 Legend* current = [_legends objectAtIndex: i]; 260 [[current legend] addAttributes: attributes 261 range: NSMakeRange (0, [[current legend] length])]; 262 NSSize s = [[current legend] size]; 263 264 [current setHeight: s.height]; 265 if ([current point].x > (imageWidth/2)) 266 { 267 [current setRightPos]; // on range � droite 268 [preRightLegends addObject: current]; 269 } 270 else 271 { 272 [preLeftLegends addObject: current]; 273 } 274 } 275 276 NSArray* LeftLegends = [preLeftLegends sortedArrayUsingSelector: @selector (compareLegends:)]; 277 NSArray* RightLegends = [preRightLegends sortedArrayUsingSelector: @selector (compareLegends:)]; 278 279 //NSLog (@"preLL : %d LL : %d", [preLeftLegends count], [LeftLegends count]); 280 //NSLog (@"preRL : %d RL : %d", [preRightLegends count], [RightLegends count]); 281 282 float LeftLegendsHeight = 0; 283 float RightLegendsHeight = 0; 284 285 for (i=0; i < [LeftLegends count]; i++) 286 { 287 LeftLegendsHeight += [[LeftLegends objectAtIndex: i] height]; 288 } 289 290 for (i=0; i < [RightLegends count]; i++) 291 { 292 RightLegendsHeight += [[RightLegends objectAtIndex: i] height]; 293 } 294 295 interspace = (cellFrame.size.height - LeftLegendsHeight)/ ([LeftLegends count]+1); 296 297 [self drawLegends: LeftLegends onRight: NO withInterspace: interspace 298 withAttributes: attributes withFrame: cellFrame withBorder: border 299 withMargin: Margin withSpaceMargin: spaceMargin withImageWidth: imageWidth 300 withPosImage: posImage]; 301 302 interspace = (cellFrame.size.height - RightLegendsHeight)/ ([RightLegends count]+1); 303 [self drawLegends: RightLegends onRight: YES withInterspace: interspace 304 withAttributes: attributes withFrame: cellFrame withBorder: border 305 withMargin: Margin withSpaceMargin: spaceMargin withImageWidth: imageWidth 306 withPosImage: posImage]; 307 308 } 309 [controlView unlockFocus]; 310} 311 312@end 313