Delphi Indy 10 UDP客户端和开放式声音控制

Delphi Indy 10 UDP客户端和开放式声音控制,delphi,indy,indy10,osc,delphi-10.3-rio,Delphi,Indy,Indy10,Osc,Delphi 10.3 Rio,要控制贝林格X32混音器,我必须发送一条OSC消息,如/ch/01/mix/fader,f.3,将音量控制器移动到30%。根据OSC协议,混音器希望.3以4个字符的字符串形式输入-十六进制3E 99 99 9A。因此,涉及到特殊角色 TIdUDPClient被赋予3E 99 99 9A的字符,但它发出3E 3F 3F 3F。同样地,.4希望成为3E CC CD但3E 3F 3F 3F已发送 当您达到.5或更高版本时,当字符位于3F以下时,情况会再次出现。例如,.6应该是3F 19 99 9A并作

要控制贝林格X32混音器,我必须发送一条OSC消息,如
/ch/01/mix/fader,f.3
,将音量控制器移动到
30%
。根据OSC协议,混音器希望
.3
以4个字符的字符串形式输入-十六进制
3E 99 99 9A
。因此,涉及到特殊角色

TIdUDPClient
被赋予
3E 99 99 9A
的字符,但它发出
3E 3F 3F 3F
。同样地,
.4
希望成为
3E CC CD
3E 3F 3F 3F
已发送

当您达到
.5
或更高版本时,当字符位于
3F
以下时,情况会再次出现。例如,
.6
应该是
3F 19 99 9A
并作为
3F 19 3F 3F
输出

显然,贝林格只是在看那里的前两个角色

我使用的是Delphi RioIndy 10版本。我可以使用LnetLazarus中创建一个工作正常的模块。但我的主要应用程序是Delphi,我需要这种能力。正如你所看到的,我尝试了几种不同的方法,但都没有效果

如何发送正确的字符

procedure TCPForm1.OSCSendMsg;
var
  OutValueStr: String;
  I: Integer;
  J: Tbytes;
  B1: TIdbytes;
begin
  If Length(CommandStr) > 0 then begin
    OscCommandStr := PadStr(CommandStr);        //convert CommandStr to OSC string
    If TypeStr='' then OscCommandStr := OscCommandStr+','+#0+#0+#0;
    If Length(TypeStr) = 1 then begin
      If TypeStr='i' then Begin     // Parameter is an integer
              I := swapendian(IValue);              //change to big endian
              OscCommandStr := OscCommandStr+','+TypeStr+#0+#0+IntToCharStr(I);
              OutValueStr   := IntToStr(IValue);
            end;
      If TypeStr='f' then Begin     // Parameter is a float (real)
              I := swapendian(PInteger(@FValue)^);   //typecast & change to big endian
              //I := htonl(PInteger(@FValue)^);   //typecast & change to big endian
              //J := MakeOSCFloat(FValue);
              OscCommandStr := OscCommandStr+','+TypeStr+#0+#0+IntToCharStr(I);
              //OscCommandStr := OscCommandStr+','+TypeStr+#0+#0+char(J[0])+char(J[1])+char(J[2])+char(J[3]);
              OutValueStr   := FloatToStr(FValue);
            end;
    end;
  //IdUDPClient2.Send(OSCCommandStr,IndyTextEncoding_UTF8);
  //IdUDPClient2.Send(OSCCommandStr);
  B1 := toBytes(OSCCommandStr);
  IdUDPClient2.SendBuffer(B1);
   if loglevel>0 then logwrite('OSC= '+ hexstr(OSCCommandStr));
   Wait(UDPtime);
//   if loglevel>0 then logwrite('OSC '+ OSCCommandStr);
  end;
end;

function  TCPForm1.IntToCharStr(I : Integer) : String;
var
  CharStr : String;
  MyArray: array [0..3] of Byte;
  J: Integer;
begin
  For J :=0 to 3 do MyArray[J] := 0;
  Move(I, MyArray, 4);  //typeset conversion from integer to array of byte
  CharStr := '';
  For J :=0 to 3 do     //convert array of byte to string
    CharStr := CharStr+char(MyArray[J]);
  IntToCharStr := CharStr;
end;
更新

系统不允许我添加此作为答案,所以

谢谢你,雷米。至少就X32软件模拟器而言,添加8位文本编码会给出正确的响应。我得等到明天才能在剧院里测试真正的混音器。如果我们能够控制通信的两端,字节数组可能会更好。事实上,我无法更改X32,它希望为文本字符串“/ch/01/mix/fader,f.4”获得一个填充字符串(十六进制:2F 63 68 2F 30 31 2F 6D 69 78 2F 66 61 64 65 72 00 00 00 00 00 2C 66 00 00 3E CC CD)。X32响应的消息文档是一个具有不同参数的类似消息的长表。e、 g.“/ch/01/mix/mute on”(混音/静音开启)、“/bus/1/dyn/比率,i 2”等。这一切都符合开放式声音控制协议

一如既往,你是印地智慧的最终源泉,所以,谢谢你。我将在使用实际设备获得结果后编辑此注释

更新

确认将8位文本编码添加到Send命令可用于X32。干杯由此产生了几个问题:

  • 一个发送构造是否优于另一个

  • 我应该在哪里阅读/了解更多关于印地的这些细节


  • 3F
    是ASCII
    “?”
    字符。当Unicode字符被编码为不支持该Unicode字符的字节编码时,您将看到该字符被发送。例如,Indy的默认文本编码为US-ASCII,除非您另有指定(通过
    IdGlobal.pas
    单元中的
    GIdDefaultTextEncoding
    变量,或通过各种类属性或方法参数),并且US-ASCII不支持Unicode字符>U+007F

    看起来您处理的是二进制协议,而不是文本协议,那么为什么要使用字符串来创建其消息呢?我认为字节数组更有意义

    至少,尝试使用Indy的8位文本编码(通过
    IdGlobal.pas
    单元中的
    IndyTextEncoding_8Bit()
    函数)将Unicode字符U+0000..U+00FF转换为字节0x00..0xFF,而不丢失数据,例如:

    B1:=ToBytes(OSCCommandStr,indytextencode8bit);//不是ASCII或UTF8!
    IdUDPClient2.SendBuffer(B1);
    
    IdUDPClient2.Send(osccomandstr,indytextencode8bit);//不是ASCII或UTF8!
    
    此消息不能使用ansi字符(ansistring)发送,还是需要特定的二进制格式?OSC协议在字符、填充和尾端使用方面是特定的。看一看我的答案。你删除了答案:这不是冒犯任何人的问题,只是答案是为了答案,而不是评论。如果你认为@ ReMe的回答已经回答了你要问的问题,你只需要点击它的LHS上的嘀嗒图标。这对读者很有用,因为它告诉他们答案值得一看(雷米的答案总是值得一看),也就是说,它有助于提高信噪比。@Dgbaxter UDP只对字节而不是字符串进行操作。字符串以字节形式传输。您无需更改X32上的任何内容即可在自己的代码中使用字节数组(例如,您的
    ToBytes()
    示例)。我认为您需要仔细阅读8位字符串和8位字节之间的相关性。它们是相同的数据。您可以使用字节数组来构建OSC消息,特别是对于不涉及人类可读字符的部分。只是考虑一下…