1 /* 2 * Copyright 2001-2005, Haiku. 3 * Distributed under the terms of the MIT License. 4 * 5 * Authors: 6 * Pahtz <pahtz@yahoo.com.au> 7 * Axel Dörfler, axeld@pinc-software.de 8 */ 9 10 /** Class for low-overhead port-based messaging */ 11 12 #include <stdlib.h> 13 #include <string.h> 14 #include <new> 15 #include <Gradient.h> 16 #include <GradientLinear.h> 17 #include <GradientRadial.h> 18 #include <GradientRadialFocus.h> 19 #include <GradientDiamond.h> 20 #include <GradientConic.h> 21 #include <Region.h> 22 #include <Shape.h> 23 24 #include <ServerLink.h> 25 #include <ServerProtocol.h> 26 27 //#define TRACE_SERVER_LINK_GRADIENTS 28 #ifdef TRACE_SERVER_LINK_GRADIENTS 29 # include <OS.h> 30 # define GTRACE(x) debug_printf x 31 #else 32 # define GTRACE(x) ; 33 #endif 34 35 36 namespace BPrivate { 37 38 ServerLink::ServerLink() 39 { 40 } 41 42 43 ServerLink::~ServerLink() 44 { 45 } 46 47 48 status_t 49 ServerLink::ReadRegion(BRegion *region) 50 { 51 fReceiver->Read(®ion->fCount, sizeof(long)); 52 if (region->fCount > 0) { 53 fReceiver->Read(®ion->fBounds, sizeof(clipping_rect)); 54 if (!region->_SetSize(region->fCount)) 55 return B_NO_MEMORY; 56 return fReceiver->Read(region->fData, 57 region->fCount * sizeof(clipping_rect)); 58 } else { 59 return fReceiver->Read(®ion->fBounds, sizeof(clipping_rect)); 60 } 61 } 62 63 64 status_t 65 ServerLink::AttachRegion(const BRegion ®ion) 66 { 67 fSender->Attach(®ion.fCount, sizeof(long)); 68 if (region.fCount > 0) { 69 fSender->Attach(®ion.fBounds, sizeof(clipping_rect)); 70 return fSender->Attach(region.fData, 71 region.fCount * sizeof(clipping_rect)); 72 } else { 73 return fSender->Attach(®ion.fBounds, sizeof(clipping_rect)); 74 } 75 } 76 77 78 status_t 79 ServerLink::ReadShape(BShape *shape) 80 { 81 int32 opCount, ptCount; 82 fReceiver->Read(&opCount, sizeof(int32)); 83 fReceiver->Read(&ptCount, sizeof(int32)); 84 85 uint32 opList[opCount]; 86 if (opCount > 0) 87 fReceiver->Read(opList, opCount * sizeof(uint32)); 88 89 BPoint ptList[ptCount]; 90 if (ptCount > 0) 91 fReceiver->Read(ptList, ptCount * sizeof(BPoint)); 92 93 shape->SetData(opCount, ptCount, opList, ptList); 94 return B_OK; 95 } 96 97 98 status_t 99 ServerLink::AttachShape(BShape &shape) 100 { 101 int32 opCount, ptCount; 102 uint32 *opList; 103 BPoint *ptList; 104 105 shape.GetData(&opCount, &ptCount, &opList, &ptList); 106 107 fSender->Attach(&opCount, sizeof(int32)); 108 fSender->Attach(&ptCount, sizeof(int32)); 109 if (opCount > 0) 110 fSender->Attach(opList, opCount * sizeof(uint32)); 111 if (ptCount > 0) 112 fSender->Attach(ptList, ptCount * sizeof(BPoint)); 113 return B_OK; 114 } 115 116 117 status_t 118 ServerLink::ReadGradient(BGradient **gradient) 119 { 120 GTRACE(("ServerLink::ReadGradient\n")); 121 return fReceiver->ReadGradient(gradient); 122 } 123 124 125 status_t 126 ServerLink::AttachGradient(const BGradient &gradient) 127 { 128 GTRACE(("ServerLink::AttachGradient\n")); 129 BGradient::Type gradientType = gradient.GetType(); 130 int32 stopCount = gradient.CountColorStops(); 131 GTRACE(("ServerLink::AttachGradient> color stop count == %d\n", 132 (int)stopCount)); 133 fSender->Attach(&gradientType, sizeof(BGradient::Type)); 134 fSender->Attach(&stopCount, sizeof(int32)); 135 if (stopCount > 0) { 136 for (int i = 0; i < stopCount; i++) { 137 fSender->Attach(gradient.ColorStopAtFast(i), 138 sizeof(BGradient::ColorStop)); 139 } 140 } 141 142 switch(gradientType) { 143 case BGradient::TYPE_LINEAR: { 144 GTRACE(("ServerLink::AttachGradient> type == TYPE_LINEAR\n")); 145 const BGradientLinear* linear = (BGradientLinear*) &gradient; 146 BPoint start = linear->Start(); 147 BPoint end = linear->End(); 148 fSender->Attach(&start, sizeof(BPoint)); 149 fSender->Attach(&end, sizeof(BPoint)); 150 break; 151 } 152 case BGradient::TYPE_RADIAL: { 153 GTRACE(("ServerLink::AttachGradient> type == TYPE_RADIAL\n")); 154 const BGradientRadial* radial = (BGradientRadial*) &gradient; 155 BPoint center = radial->Center(); 156 float radius = radial->Radius(); 157 fSender->Attach(¢er, sizeof(BPoint)); 158 fSender->Attach(&radius, sizeof(float)); 159 break; 160 } 161 case BGradient::TYPE_RADIAL_FOCUS: { 162 GTRACE(("ServerLink::AttachGradient> type == TYPE_RADIAL_FOCUS\n")); 163 const BGradientRadialFocus* radialFocus = 164 (BGradientRadialFocus*) &gradient; 165 BPoint center = radialFocus->Center(); 166 BPoint focal = radialFocus->Focal(); 167 float radius = radialFocus->Radius(); 168 fSender->Attach(¢er, sizeof(BPoint)); 169 fSender->Attach(&focal, sizeof(BPoint)); 170 fSender->Attach(&radius, sizeof(float)); 171 break; 172 } 173 case BGradient::TYPE_DIAMOND: { 174 GTRACE(("ServerLink::AttachGradient> type == TYPE_DIAMOND\n")); 175 const BGradientDiamond* diamond = (BGradientDiamond*) &gradient; 176 BPoint center = diamond->Center(); 177 fSender->Attach(¢er, sizeof(BPoint)); 178 break; 179 } 180 case BGradient::TYPE_CONIC: { 181 GTRACE(("ServerLink::AttachGradient> type == TYPE_CONIC\n")); 182 const BGradientConic* conic = (BGradientConic*) &gradient; 183 BPoint center = conic->Center(); 184 float angle = conic->Angle(); 185 fSender->Attach(¢er, sizeof(BPoint)); 186 fSender->Attach(&angle, sizeof(float)); 187 break; 188 } 189 case BGradient::TYPE_NONE: { 190 GTRACE(("ServerLink::AttachGradient> type == TYPE_NONE\n")); 191 break; 192 } 193 } 194 return B_OK; 195 } 196 197 198 status_t 199 ServerLink::FlushWithReply(int32 &code) 200 { 201 status_t status = Flush(B_INFINITE_TIMEOUT, true); 202 if (status < B_OK) 203 return status; 204 205 return GetNextMessage(code); 206 } 207 208 } // namespace BPrivate 209