home *** CD-ROM | disk | FTP | other *** search
/ Chip 2002 October / Chip_2002-10_cd1.bin / zkuste / delphi / kolekce / d56 / FLEXCEL.ZIP / XLSAdapter / UXlsStrings.pas < prev    next >
Pascal/Delphi Source File  |  2002-06-15  |  6KB  |  228 lines

  1. unit UXlsStrings;
  2.  
  3. interface
  4. uses XlsMessages, SysUtils,classes, UXlsBaseRecords;
  5. type
  6.   TStrLenLength= 1..2;
  7.   TCharSize=1..2;
  8.  
  9.   TExcelString= class
  10.   private
  11.     // Common data
  12.     StrLenLength: TStrLenLength;  //this stores if it's a one or two bytes length
  13.     StrLen: word;
  14.     OptionFlags: byte;
  15.     WideData: WideString;
  16.     ShortData: string;
  17.  
  18.     //Rich text
  19.     NumberRichTextFormats: word;
  20.     RichTextFormats: PArrayOfByte;
  21.  
  22.     //FarEast
  23.     FarEastDataSize: Cardinal;
  24.     FarEastData: PArrayOfByte;
  25.     function GetValue: WideString;
  26.  
  27.   public
  28.     constructor Create(const aStrLenLength: TStrLenLength; var aRecord: TBaseRecord; var Ofs: integer);overload;
  29.     constructor Create(const aStrLenLength: TStrLenLength;const s: wideString); overload;
  30.  
  31.     destructor Destroy;override;
  32.  
  33.     procedure SaveToStream(const DataStream: TStream);
  34.  
  35.     function GetCharSize: TCharSize;
  36.     function HasRichText: boolean;
  37.     function HasFarInfo: boolean;
  38.  
  39.     function Compare(const Str2: TExcelString): integer; //-1 if less, 0 if equal, 1 if more
  40.     function TotalSize: int64;
  41.  
  42.     procedure CopyToPtr(const Ptr: PArrayOfByte; const aPos: integer);
  43.     property Value: WideString read GetValue;
  44.   end;
  45.  
  46. implementation
  47.  
  48. { TExcelString }
  49.  
  50. function MyWideCompareStr(const S1, S2: WideString): Integer;
  51. var
  52.   i:integer;
  53. begin
  54.   Result:=0;
  55.   if Length(S1)<Length(S2) then Result:=-1 else if Length(S1)>Length(S2) then Result:=1
  56.   else
  57.   for i:=1 to Length(S1) do
  58.   begin
  59.     if S1[i]=S2[i] then continue
  60.     else if S1[i]<S2[i] then Result:=-1 else Result:=1;
  61.     exit;
  62.   end;
  63. end;
  64.  
  65.  
  66. constructor TExcelString.Create(const aStrLenLength: TStrLenLength; var aRecord: TBaseRecord; var Ofs: integer);
  67. var
  68.   StrLenByte: byte;
  69.   DestPos: integer;
  70. begin
  71.   inherited Create;
  72.   StrLenLength:=aStrLenLength;
  73.   if StrLenLength=1 then
  74.   begin
  75.     ReadMem(aRecord, Ofs, StrLenLength, @StrLenByte);
  76.     StrLen:=StrLenByte;
  77.   end
  78.   else ReadMem(aRecord, Ofs, StrLenLength, @StrLen);
  79.  
  80.   ReadMem(aRecord, Ofs, SizeOf(OptionFlags), @OptionFlags);
  81.  
  82.   if HasRichText then ReadMem(aRecord, Ofs, SizeOf(NumberRichTextFormats), @NumberRichTextFormats)
  83.   else NumberRichTextFormats:=0;
  84.  
  85.   if HasFarInfo then ReadMem(aRecord, Ofs, SizeOf(FarEastDataSize), @FarEastDataSize)
  86.   else FarEastDataSize:=0;
  87.  
  88.   DestPos:=0;
  89.   SetLength( ShortData, StrLen);
  90.   SetLength( WideData, StrLen);
  91.   ReadStr(aRecord, Ofs, ShortData, WideData, OptionFlags, DestPos, StrLen);
  92.   if GetCharSize=1 then WideData:='' else ShortData:='';
  93.  
  94.   if NumberRichTextFormats>0 then
  95.   begin
  96.     GetMem(RichTextFormats, 4* NumberRichTextFormats);
  97.     ReadMem(aRecord, Ofs, 4* NumberRichTextFormats, RichTextFormats)
  98.   end;
  99.  
  100.   if FarEastDataSize>0 then
  101.   begin
  102.     GetMem(FarEastData, FarEastDataSize);
  103.     ReadMem(aRecord, Ofs, FarEastDataSize, FarEastData)
  104.   end;
  105.  
  106. end;
  107.  
  108. function TExcelString.Compare(const Str2: TExcelString): integer;
  109. begin
  110.   if StrLenLength< Str2.StrLenLength then begin;Result:=-1;exit; end
  111.   else if StrLenLength> Str2.StrLenLength then begin;Result:=1;exit; end;
  112.  
  113.   if OptionFlags< Str2.OptionFlags then begin; Result:=-1; exit; end
  114.   else if OptionFlags> Str2.OptionFlags then begin; Result:=1; exit; end;
  115.  
  116.   if GetCharSize=1 then Result:=CompareStr(ShortData, Str2.ShortData) else
  117.   Result:= MyWideCompareStr(WideData, Str2.WideData);
  118. end;
  119.  
  120. constructor TExcelString.Create(const aStrLenLength: TStrLenLength;
  121.   const s: wideString);
  122. begin
  123.   inherited Create;
  124.   StrLenLength:=aStrLenLength;
  125.   case StrLenLength of
  126.     1: if Length(s)> $FF then raise Exception.Create(ErrInvalidStringRecord);
  127.   end; //case
  128.   StrLen:=Length(s);
  129.  
  130.   OptionFlags:=0;
  131.   if IsWide(s) then OptionFlags:=1;
  132.   NumberRichTextFormats:=0;
  133.   FarEastDataSize:=0;
  134.  
  135.   if GetCharSize= 1 then ShortData:=s else WideData:=s;
  136. end;
  137.  
  138. destructor TExcelString.Destroy;
  139. begin
  140.   FreeMem(FarEastData);
  141.   FreeMem(RichTextFormats);
  142.   inherited;
  143. end;
  144.  
  145. function TExcelString.GetCharSize: TCharSize;
  146. begin
  147.   if OptionFlags and $1 = 0 then Result:=1 else Result:=2;
  148. end;
  149.  
  150. function TExcelString.HasFarInfo: boolean;
  151. begin
  152.   Result:= OptionFlags and $4 = $4;
  153. end;
  154.  
  155. function TExcelString.HasRichText: boolean;
  156. begin
  157.   Result:= OptionFlags and $8 = $8;
  158. end;
  159.  
  160. function TExcelString.TotalSize: int64;
  161. begin
  162.   Result:=
  163.     StrLenLength+
  164.     SizeOf(OptionFlags)+
  165.     StrLen* GetCharSize;
  166.  
  167.     //Rich text
  168.     if HasRichText then
  169.       Result:=Result + SizeOf(NumberRichTextFormats)+ 4* NumberRichTextFormats;
  170.  
  171.     //FarEast
  172.     if HasFarInfo then
  173.       Result:=Result+ SizeOf(FarEastDataSize) + FarEastDataSize;
  174. end;
  175.  
  176. procedure TExcelString.SaveToStream(const DataStream: TStream);
  177.  
  178. begin
  179.   case StrLenLength of
  180.     1: DataStream.Write(StrLen, SizeOf(Byte));
  181.     2: DataStream.Write(StrLen, SizeOf(Word));
  182.     else raise Exception.Create(ErrInvalidStrLenLength);
  183.   end; //case
  184.  
  185.   DataStream.Write(OptionFlags, SizeOf(OptionFlags));
  186.  
  187.   if HasRichText then
  188.     DataStream.Write(NumberRichTextFormats, SizeOf(NumberRichTextFormats));
  189.  
  190.   if HasFarInfo then
  191.     DataStream.Write(FarEastDataSize, SizeOf(FarEastDataSize));
  192.  
  193.   if GetCharSize= 1 then
  194.     if StrLen>0 then DataStream.Write(ShortData[1], Length(ShortData)) else //nothing
  195.   else
  196.     if StrLen>0 then DataStream.Write(WideData[1], Length(WideData)* SizeOf(WideChar));
  197.  
  198.   if NumberRichTextFormats>0 then
  199.     DataStream.Write(RichTextFormats^, 4*NumberRichTextFormats);
  200.  
  201.   if FarEastDataSize>0 then
  202.     DataStream.Write(FarEastData^, FarEastDataSize);
  203.  
  204. end;
  205.  
  206. procedure TExcelString.CopyToPtr(const Ptr: PArrayOfByte;
  207.   const aPos: integer);
  208. var
  209.   Ms: TMemoryStream;
  210. begin
  211.   //Not the most efficient... but this way we avoid duplicating code 
  212.   Ms:= TMemoryStream.Create;
  213.   try
  214.     SaveToStream(Ms);
  215.     Ms.Position:=0;
  216.     Ms.Read(Ptr[aPos], Ms.Size);
  217.   finally
  218.     FreeAndNil(Ms);
  219.   end;
  220. end;
  221.  
  222. function TExcelString.GetValue: WideString;
  223. begin
  224.   if GetCharSize=1 then Result:= ShortData else Result:= WideData;
  225. end;
  226.  
  227. end.
  228.