Club Delphi  
    FTP   CCD     Buscar   Trucos   Trabajo   Foros

Retroceder   Foros Club Delphi > Otros entornos y lenguajes > Lazarus, FreePascal, Kylix, etc.
Registrarse FAQ Miembros Calendario Guía de estilo Buscar Temas de Hoy Marcar Foros Como Leídos

Respuesta
 
Herramientas Buscar en Tema Desplegado
  #1  
Antiguo 24-02-2012
NPIdea NPIdea is offline
Miembro
 
Registrado: feb 2005
Posts: 121
Poder: 20
NPIdea Va por buen camino
Problema compilación Bluetoothlaz

Hola a todos.

He instalado Debian en una maquina virtual con VirtualBox y por supuesto Lazarus. Funciona muy bien, hay que decirlo.

Mi proposito erá encontrar librerias bluetooth para hacer alguna aplicación y encontré BluettothLaz 0.1 en la http://wiki.lazarus.freepascal.org/Bluetooth/es.

He instalado la libreria libbluetooth-dev y luego he ido a instalar el paquete. Me da un error de compilación en una unit llamada wiimotetools.

Como no tengo ninguna esperiencia en realizar componentes os pido a ver si le podeis echar un ojo y decirme la solución: (Quito el chorizo variables, sino el mensaje es muy largo y no me deja publicarlo)
Código Delphi [-]

unit WiiMoteTools;

{$mode objfpc}{$H+}

{$linklib bluetooth}

interface

uses
  Classes, SysUtils, Bluetooth, ctypes, Sockets;

//------------------------------------------------------------------------------
// mini libc
type
   __time_t = longint;
   __suseconds_t = longint;
   Ptimeval = ^timeval;
   timeval = record
        tv_sec : __time_t;
        tv_usec : __suseconds_t;
     end;
   __fd_mask = dWord;

const
  __FD_SETSIZE = 1024;
  __NFDBITS       = 8 * sizeof(__fd_mask);

type
  __fd_set = record
     fds_bits: packed array[0..(__FD_SETSIZE div __NFDBITS)-1] of __fd_mask;
  end;
  TFdSet = __fd_set;
  PFdSet = ^TFdSet;
Type
  Pfd_set = ^_fd_set;
  _fd_set = __fd_set;

const
  FD_SETSIZE = __FD_SETSIZE;

Type
  Pfd_mask = ^fd_mask;
  fd_mask = __fd_mask;

const
  NFDBITS = __NFDBITS;

Function __FDELT(d: longint): Integer;
Function __FDMASK(d: longint): __fd_mask;
procedure FD_ZERO(out fdset: _fd_set);
procedure FD_SET(fd: longint; var fdset: _fd_Set);
type
  TAccelVector = record
    x,y,z: integer;
  end;
  
  TAccelCalibration = record
    cal_zero: TAccelVector;
    cal_g: TAccelVector;
  end;
  
  TWiiMoteReadRequest = class;

  TWiiMoteReadCallback = procedure(Request: TWiiMoteReadRequest) of object;

  { TWiiMoteReadRequest }

  TWiiMoteReadRequest = class
  public
    Callback: TWiiMoteReadCallback;
    Addr: cardinal;
    BufSize: word;
    Buf: PByte;
    Received: word;
    constructor Create(const TheCallback: TWiiMoteReadCallback;
                       TheAddr: cardinal; TheBufSize: word);
    destructor Destroy; override;
  end;

  TWiiMoteDot = record
    X: word;
    Y: word;
    Size: word;
    Visible: boolean;
  end;

  TWiimotes = class;

  { TWiiMote }

  TWiimote = class
  private
    FLEDS: integer;
    FRealizedIR: boolean;
    FReadRequests: TFPList;// list of TWiiMoteReadRequest
    function SendCmd(ReportType: byte; Msg: PByte; Count: integer): PtrInt;
    function SendData(Addr: cuint; Data: Pointer; Count: byte): PtrInt;
    function RequestRead(const Callback: TWiiMoteReadCallback;
                          Addr: cuint; BufSize: cushort): TWiiMoteReadRequest;
    procedure SendNextReadRequest;
    procedure OnHandShake(Request: TWiiMoteReadRequest);
    procedure HandleEvents;
    procedure HandleRead;
  public
    constructor Create;
    destructor Destroy; override;
    procedure SetLEDs(const AValue: integer);
    function Connect: boolean;
    procedure Disconnect;
    procedure EnableHandshake;
    function RealizeReportType: boolean;
    procedure RealizeIR;
    
    WiiMotes: TWiiMotes;
    ID: integer;
    Name: string;
    bdaddr: bdaddr_t;
    Found: boolean;
    Connected: boolean;
    OutSocket: cint;
    InSocket: cint;
    Handshaking: boolean;
    HandshakeComplete: boolean;
    Event: TWiimoteEventType;
    EventBuf: array[0..31] of byte;
    
    // properties
    LEDs: integer;
    Rumble: boolean;
    Continuous: boolean;
    ReportMotion: boolean;
    ReportIR: boolean;
    ReportExpansion: boolean;
    Buttons: word; // current button state
    Accel: TAccelVector; // current accelerator state
    AccelCalibration: TAccelCalibration;
    Dots: array[0..3] of TWiiMoteDot;
  end;
  
  { TWiiMotes }

  TWiimotes = class
  private
    FItems: TFPList;
    function GetItems(Index: integer): TWiimote;
  public
    constructor Create;
    destructor Destroy; override;
    function Add(Item: TWiimote): integer;
    function Count: integer;
    property Items[Index: integer]: TWiimote read GetItems; default;
    procedure FindWiiMotes(timeout: integer);
    function Connect: integer;
    procedure Disconnect;
    function HandleEvents: boolean;
  end;


function c_close(fd: cint): cint; external name 'close';


implementation

function __FDELT(d: longint): Integer;
begin
  Result:=d div __NFDBITS;
end;

function __FDMASK(d: longint): __fd_mask;
begin
  Result:=1 shl (d mod __NFDBITS);
end;

procedure FD_ZERO(out fdset: _fd_set);
var
  I: Integer;
begin
  with fdset do
    for I:=Low(fds_bits) to High(fds_bits) do
      fds_bits[i]:=0;
end;

procedure FD_SET(fd: longint; var fdset: _fd_Set);
begin
  fdset.fds_bits[__FDELT(fd)]:=fdset.fds_bits[__FDELT(fd)] or __FDMASK(fd);
end;

procedure FD_CLR(fd: longint; var fdset: _fd_set);
begin
  fdset.fds_bits[__FDELT(fd)]:=fdset.fds_bits[__FDELT(fd)] and (not __FDMASK(fd));
end;

function FD_ISSET(fd: longint; const fdset: _fd_set): Boolean;
begin
  Result:=(fdset.fds_bits[__FDELT(fd)] and __FDMASK(fd))<>0;
end;


procedure TWiimotes.FindWiiMotes(timeout: integer);
var
  device_id, device_sock: cint;
  scan_info: array[0..127] of inquiry_info;
  scan_info_ptr: Pinquiry_info;
  found_devices: cint;
  DevName: PCChar;
  CurWiiMote: TWiimote;
  i: Integer;
begin
  // get the id of the first bluetooth device.
  device_id := hci_get_route(nil);
  if (device_id < 0) then
    raise Exception.Create('FindWiiMotes: hci_get_route');

  // create a socket to the device
  device_sock := hci_open_dev(device_id);
  if (device_sock < 0) then
    raise Exception.Create('hci_open_dev');

  // scan for bluetooth devices for 'timeout' seconds
  scan_info_ptr:=@scan_info[0];
  FillByte(scan_info[0],SizeOf(inquiry_info)*128,0);
  found_devices := hci_inquiry_1(device_id, timeout, 128, nil,
                                 @scan_info_ptr, IREQ_CACHE_FLUSH);
  if (found_devices < 0) then
    raise Exception.Create('hci_inquiry');
  writeln('found_devices=',found_devices);
  
  // display discovered devices
  DevName:=nil;
  GetMem(DevName,20);
  for i:=0 to found_devices-1 do begin
    if ((scan_info[i].dev_class[0] = WM_DEV_CLASS_0) and
        (scan_info[i].dev_class[1] = WM_DEV_CLASS_1) and
        (scan_info[i].dev_class[2] = WM_DEV_CLASS_2)) then
    begin
      CurWiiMote:=TWiimote.Create;
      Add(CurWiiMote);
      // found a device
      ba2str(@scan_info[i].bdaddr, DevName);
      CurWiiMote.Name:=PChar(DevName);
      CurWiiMote.bdaddr:=scan_info[i].bdaddr;
      CurWiiMote.Found:=true;

      writeln(i,' Device=',CurWiiMote.Name);
    end;
  end;
  FreeMem(DevName);

  c_close(device_sock);
end;

function TWiimotes.Connect: integer;
var
  CurWiiMote: TWiimote;
  i: Integer;
begin
  Result:=0;
  for i:=0 to Count-1 do begin
    CurWiiMote:=Items[i];
    if not CurWiiMote.Found then
      // if the device address is not set, skip it
      continue;

    if CurWiiMote.Connect then
      inc(Result);
  end;
end;

procedure TWiimotes.Disconnect;
var
  i: Integer;
begin
  for i:=0 to Count-1 do Items[i].Disconnect;
end;

function TWiimotes.HandleEvents: boolean;
var
  fds: _fd_set;
  highest_fd: integer;
  tv: timeval;
  i: integer;
  r: PtrInt;
begin
  highest_fd:=0;
  Result:=false;

  // block select() for 1/2000th of a second
  tv.tv_sec := 0;
  tv.tv_usec := 500;

  FD_ZERO(fds);

  for i:=0 to Count-1 do begin
    // only poll it if it is connected
    if Items[i].Connected then begin
      FD_SET(Items[i].InSocket, fds);

      // find the highest fd of the connected wiimotes
      if (Items[i].InSocket > highest_fd) then
        highest_fd := Items[i].InSocket;
    end;

    Items[i].Event:= WiiMote_NONE;
  end;

  if (select(highest_fd + 1, @fds, nil, nil, @tv) = -1) then
    raise Exception.Create('Unable to select() the wiimote interrupt socket(s)');

  // check each socket for an event
  for i:=0 to Count-1 do begin
    // if this wiimote is not connected, skip it
    if not Items[i].Connected then
      continue;

    if (FD_ISSET(Items[i].InSocket, fds)) then begin
      // clear out the event buffer
      FillByte(Items[i].EventBuf[0],32,0);

      // read the pending message into the buffer
      r := fprecv(Items[i].InSocket,@Items[i].EventBuf[0], 32,0);
      if (r = -1) then begin
        // error reading data
        writeln('Receiving wiimote data '+IntToStr(Items[i].ID));
        // remote disconnect
        Items[i].Disconnect;
        Result:=true;
        continue;
      end;

      // propagate the event
      if Items[i].EventBuf[1]<>0 then begin
        Items[i].HandleEvents;
        Result:=true;
      end;
    end else begin
      //idle_cycle(wm[i]);
    end;
  end;
end;

{ TWiimotes }

function TWiimotes.GetItems(Index: integer): TWiimote;
begin
  Result:=TWiimote(FItems[Index]);
end;

constructor TWiimotes.Create;
begin
  FItems:=TFPList.Create;
end;

destructor TWiimotes.Destroy;
var
  i: Integer;
begin
  for i:=0 to FItems.Count-1 do TObject(FItems[i]).Free;
  FreeAndNil(FItems);
  inherited Destroy;
end;

function TWiimotes.Add(Item: TWiimote): integer;
begin
  Item.ID:=Count;
  Item.WiiMotes:=Self;
  Result:=FItems.Add(Item);
end;

function TWiimotes.Count: integer;
begin
  Result:=FItems.Count;
end;

{ TWiimote }

procedure TWiimote.SetLEDs(const AValue: integer);
var
  buf: byte;
begin
  // remove the lower 4 bits because they control rumble
  FLEDs:=AValue and $F0;
  // make sure if the rumble is on that we keep it on
  if Rumble then
    FLEDs := FLEDs or 1;

  if Connected then begin
    buf := FLEDs;
    SendCmd(WM_CMD_LED, @buf, 1);
  end;
end;

function TWiimote.Connect: boolean;
var
  Addr: sockaddr_l2;
begin
  Addr.l2_family:=AF_BLUETOOTH;
  Addr.l2_bdaddr:=bdaddr;

  // OUTPUT CHANNEL
  OutSocket:=fpsocket(AF_BLUETOOTH, SOCK_SEQPACKET, BTPROTO_L2CAP);
  if (OutSocket = -1) then
    exit(false);

  {$IFDEF BIG_ENDIAN}
  {$ERROR ToDo BIG_ENDIAN}
  {$ENDIF}
  Addr.l2_psm := WM_OUTPUT_CHANNEL; // htobs

  // connect to wiimote
  if (fpconnect(OutSocket, psockaddr(@addr), SizeOf(addr)) < 0) then
    raise Exception.Create('fpconnect output');

  // INPUT CHANNEL
  InSocket:=fpsocket(AF_BLUETOOTH, SOCK_SEQPACKET, BTPROTO_L2CAP);
  if (InSocket = -1) then begin
    CloseSocket(OutSocket);
    OutSocket := -1;
    exit(false);
  end;

  Addr.l2_psm := WM_INPUT_CHANNEL; // htobs

  // connect to wiimote
  if (fpconnect(InSocket, psockaddr(@addr), SizeOf(addr)) < 0) then
  begin
    CloseSocket(OutSocket);
    OutSocket := -1;
    raise Exception.Create('fpconnect input');
  end;

  writeln('Connected to wiimote ',ID);

  // do the handshake
  Connected:=true;

  EnableHandshake;
  RealizeReportType;

  Result:=true;
end;

procedure TWiimote.Disconnect;
begin
  if not Connected then exit;

  CloseSocket(OutSocket);
  CloseSocket(InSocket);

  OutSocket:=-1;
  InSocket:=-1;

  Connected:=false;
  Handshaking:=false;
  HandshakeComplete:=false;
  FRealizedIR:=false;
end;

procedure TWiimote.EnableHandshake;
begin
  // send request to wiimote for accelerometer calibration

  Handshaking:=true;
  SetLEDs(WIIMOTE_LED_ALL);
  RequestRead(@OnHandShake,WM_MEM_OFFSET_CALIBRATION, 7);

  //WiiMote_read_data(wm, WiiMote_handshake, buf, WM_MEM_OFFSET_CALIBRATION, 7);
  //inc(WiiMote.Handshake_State);

  //WiiMote_set_leds(wm, WIIMOTE_LED_NONE);
end;

function TWiimote.RealizeReportType: boolean;
var
  buf: array[0..1] of byte;
begin
  if not Connected then exit(false);

  if Continuous then
    buf[0] := 4 // set to 0x04 for continuous reporting
  else
    buf[0] :=0;
  buf[1] := 0;

  // if rumble is enabled, make sure we keep it
  if Rumble then
    buf[0] := buf[0] or 1;

  if ReportMotion    then buf[1] := buf[1] or WM_RPT_BTN_ACC;
  if ReportExpansion then buf[1] := buf[1] or WM_RPT_BTN_EXP;
  if ReportIR        then buf[1] := buf[1] or WM_RPT_BTN_IR;
  writeln('TWiiMote.RealizeReportType ',buf[1]);

  if SendCmd(WM_CMD_REPORT_TYPE,@buf[0],2)<=0 then begin
    writeln('TWiiMote.RealizeReportType FAILED');
    exit(false);
  end;

  Result:=true;
end;

procedure TWiimote.RealizeIR;
var
  buf: byte;
begin
  if not HandshakeComplete then begin
    writeln('TWiiMote.EnableIR still handshaking');
    exit;
  end;
  
  if ReportIR=FRealizedIR then exit;

  writeln('TWiiMote.RealizeIR ReportIR=',ReportIR);
  
  // set camera 1 and 2
  if ReportIR then
    buf:=4
  else
    buf:=0;
  SendCmd(WM_CMD_IR,@buf,1);
  SendCmd(WM_CMD_IR_2,@buf,1);

  if ReportIR then begin
    // enable IR, set sensitivity
    buf:=8;
    SendData(WM_REG_IR,@buf,1);

    // wait for the wiimote to catch up
    Sleep(50);

    // write sensitivity blocks
    SendData(WM_REG_IR_BLOCK1, Pointer(WM_IR_BLOCK1_CLIFF), length(WM_IR_BLOCK1_CLIFF));
    SendData(WM_REG_IR_BLOCK2, Pointer(WM_IR_BLOCK2_CLIFF), length(WM_IR_BLOCK2_CLIFF));

    // set the IR mode
    if ReportExpansion then
      buf := WM_IR_TYPE_BASIC
    else
      buf := WM_IR_TYPE_EXTENDED;
    SendData(WM_REG_IR_MODENUM,@buf,1);

    // wait for the wiimote to catch up
    Sleep(50);

    // set the wiimote report type
    RealizeReportType;
    writeln('TWiiMote.RealizeIR IR enabled');
  end;
end;

procedure TWiimote.HandleEvents;
var
  Data: PByte;
  i: Integer;
begin
  // don't know what WiiMote.EventBuf[0] is
  case EventBuf[1] of

  WM_RPT_CTRL_STATUS:
    begin
      writeln('TWiiMote.HandleEvent WM_RPT_CTRL_STATUS');
    end;

  WM_RPT_READ:
    begin
      writeln('TWiiMote.HandleEvent WM_RPT_READ');
      HandleRead;
    end;

  WM_RPT_WRITE:
    begin
      writeln('TWiiMote.HandleEvent WM_RPT_WRITE');
    end;

  WM_RPT_BTN:
    begin
      Buttons:=PWord(@EventBuf[2])^ and WIIMOTE_BUTTON_ALL;
      writeln('TWiiMote.HandleEvent Button ',Buttons);
    end;

  WM_RPT_BTN_ACC or WM_RPT_BTN_IR:
    begin
      Buttons:=PWord(@EventBuf[2])^ and WIIMOTE_BUTTON_ALL;
      Accel.x:=EventBuf[4];
      Accel.y:=EventBuf[5];
      Accel.z:=EventBuf[6];
      // 7,8,9,10
      Data:=PByte(@EventBuf[7]);
      for i := 0 to 3 do begin
        Dots[i].x := 1023 - (data[3*i] or ((data[(3*i)+2] and $30) shl 4));
        Dots[i].y := data[(3*i)+1] or ((data[(3*i)+2] and $C0) shl 2);

        Dots[i].size := data[(3*i)+2] and $0F;

        // if in range set to visible
        Dots[i].visible := (Dots[i].y <> 1023);
        //if dot[i].visible then write(' ',dot[i].rx,' ',dot[i].ry,' ',dot[i].size,' ',dot[i].visible);
      end;
      //for i:=0 to 20 do write(IntToHex(ord(EventBuf[i]),2),' ');
      //writeln(' TWiiMotes.HandleEvent x=',Accel.x,' y=',Accel.y,' z=',Accel.z);
      //Sleep(300);
    end;

  else
    writeln('TWiiMotes.HandleEvent other decimal=',EventBuf[1],' hex=',IntToHex(EventBuf[1],2));
  end;
end;

procedure TWiimote.HandleRead;
var
  Error: byte;
  len: byte;
  offset: word;
  Request: TWiiMoteReadRequest;
begin
  // always assume the packet received is from the most recent request

  Buttons:=PWord(@EventBuf[2])^ and WIIMOTE_BUTTON_ALL;

  // if we don't have a request out then we didn't ask for this packet
  if FReadRequests.Count=0 then begin
    writeln('TWiiMote.HandleRead Received data packet whithout request');
    exit;
  end;

  Error := EventBuf[4] and $0F;
....................... y sigue



En la linea en rojo me da el error de compilación:

/home/heppy/Downloads/bluetooth/wiimotetools.pas(311,5) Error: Fields cannot appear after a method or property definition, start a new visibility section first

Por más que lo miro y lo remiro, no encuentro solución.

Gracias y disculpad por el chorizo código.

Última edición por NPIdea fecha: 24-02-2012 a las 13:40:49. Razón: Mal puesto código
Responder Con Cita
  #2  
Antiguo 29-02-2012
Avatar de TiammatMX
TiammatMX TiammatMX is offline
Miembro
 
Registrado: jun 2006
Ubicación: Universo Curvo\Vía Láctea\Sistema Solar\Planeta Tierra\América\México\Puebla\Heróica Puebla de Zaragoza\Jardines de San Manuel\Home
Posts: 746
Poder: 18
TiammatMX Va camino a la fama
Cita:
Empezado por NPIdea Ver Mensaje
... (¡¡uffff!!)
/home/heppy/Downloads/bluetooth/wiimotetools.pas(311,5) Error: Fields cannot appear after a method or property definition, start a new visibility section first

Por más que lo miro y lo remiro, no encuentro solución...
Finalmente, el problema es que quien hizo la librería tiene un error no grave, pero sí escandaloso: Está poniendo los campos inmediatamente después de la definición de un método. Prueba a invertir el orden o en todo caso, contacta al desarrollador de la librería y que te solucione el problema que él creó.
__________________
Felipe Eduardo Ortiz López. Delphi programmers does it recursively...

"Un programador, es un creador de universos en donde sólo él es responsable. Universos de complejidad prácticamente ilimitada que se puede crear en forma de programas de ordenador." - Joseph Weizenbaum.

Témele a los profetas... y a aquellos que están listos para morir por "la verdad", ya que como regla general hacen morir a muchos otros con ellos, frecuentemente antes que ellos, y a veces en lugar de ellos. — Umberto Eco
Responder Con Cita
Respuesta


Herramientas Buscar en Tema
Buscar en Tema:

Búsqueda Avanzada
Desplegado

Normas de Publicación
no Puedes crear nuevos temas
no Puedes responder a temas
no Puedes adjuntar archivos
no Puedes editar tus mensajes

El código vB está habilitado
Las caritas están habilitado
Código [IMG] está habilitado
Código HTML está deshabilitado
Saltar a Foro

Temas Similares
Tema Autor Foro Respuestas Último mensaje
compilacion pascal alaain04 Lazarus, FreePascal, Kylix, etc. 4 19-07-2011 05:05:07
Directivas de compilación Livey Varios 0 21-09-2010 23:03:51
¿Directivas compilacion? drykea Varios 1 03-05-2007 14:51:15
Errores De CompilaciÓn nax Varios 1 20-08-2005 07:54:24
Compilación Delphi7 jatorve Varios 3 08-03-2005 21:38:39


La franja horaria es GMT +2. Ahora son las 12:18:27.


Powered by vBulletin® Version 3.6.8
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
Traducción al castellano por el equipo de moderadores del Club Delphi
Copyright 1996-2007 Club Delphi