
私は、ラズベリーパイ上のオープンソースプログラムを使用して、C でテキストと PDF ドキュメントを読み取るのに役立つプログラムを作成しようとしています。
プログラムはシンプルで、何も複雑なことはありません。
ラップトップから ssh 経由で Raspberry Pi に接続しています...コマンド ラインから X アプリケーションを問題なく起動できるため、X 転送は正常に動作しています。
私はラズベリーパイで apache2 を使用しており、テキストを貼り付けたり、テキストファイルや PDF ファイルをアップロードしたりできるこのプログラム用のユーザー インターフェイスを作成しました。
テキストは espeak によって音声に変換され、出力は wave ファイルに保存されます。
ここで問題となるのは、私が使用しているもの:
system("xmms2 play file.wav &")
Cコードでは……簡単な説明です
コンパイルはできますが、Web ページから試してみるとエラーが表示されます。
Gtk-WARNING **: cannot open display: localhost:10.0
cannot start xmms2d.....failed to start xmms2 server
アクアラングという別のオーディオ プレーヤーも試してみましたが、一度は動作しましたが、翌日コンピューターを再起動すると動作しなくなりました。
グーグルで調べて、export DISPLAY=:0.0
クライアントとホストのホスト名がlocalhostではないことを確認するなど、あらゆることを試しましたが、成功しませんでした
したがって、C プログラムに追加していない何か、追加する必要があるヘッダー ファイルなどがあるのではないかと思います。Gtk+ はラズベリーにインストールされています。
あるいは、C プログラムとして実行するのではなく、すべてを bash または php で実行する必要があるかもしれません...
aplay を使用して wav ファイルを再生すると、サウンド出力が得られます。唯一の違いは、コマンド ラインとユーザー インターフェイスを備えたものが必要になることです。これにより、プログラムからコマンドを送信でき、ユーザーはいつでもファイルを一時停止および再生できます。
アドバイスが必要です....ここにコードがあります
#include <fcntl.h>
#include <stdlib.h>
#include <unistd.h>
#include <stdio.h>
#include <wiringPi.h>
char readcmd(void) //reading from text file /home/pi/cmdrdy.txt first character is read
{ //whenever text is received a 1 is written to this file, 2 for file received
FILE *stream;
int ch;
if( (stream = fopen("/home/pi/txtrdy.txt", "r")) == NULL )
return 0;
ch = fgetc( stream );
fclose( stream );
return (ch-'0');
}
void reset()
{
FILE *ft;
char ch;
ft = fopen( "/home/pi/cmdrdy.txt", "w" );
ch = '0';
fprintf(ft, "%c", ch );
fclose(ft);
}
void checktxt(){
if(readcmd() == 1)
{
system("espeak -v en -f /home/pi/book.txt -w /home/pi/text.wav &");
reset(); //to reset the text received flag to 0
system("xmms2 play /home/pi/text.wav &");
}
if(readcmd2() == 2)
{
system("pdftotext -layout /home/pi/upload/*.pdf /home/pi/converted.txt &");
delay(300);
system("espeak -v en -f /home/pi/converted.txt -w /home/pi/book.wav &");
delay(500);
system("sudo rm /home/pi/converted.txt");
system("sudo rm /home/pi/upload/*.pdf");
system("xmm2 play /home/pi/book.wav &");
}
}
void main(){
while(1){
checktxt();
}
}
答え1
私自身はこの問題に遭遇したことはありませんが、なぜこのようなことが起こるのか推測することはできます。見たところ、xauth は子プロセスには適用されないようです。実際、次の出力で XAUTHORITY を見つけることができませんでした。
export -p
Raspian を実行している Raspberry 上。
Google で調べても、他の OS でも同じことが当てはまるかどうかはわかりませんでしたが、この問題を解決するのは非常に簡単なので、試してみる価値はあります。コマンドを実行可能スクリプトに置き換えることをお勧めします。スクリプト名は /home/my_name/bin/my_script で、もちろん、chmod 755
次の 3 行のコードを配置して実行可能にします。
#!/bin/bash
export XAUTHORITY=/home/my_name/.Xauthority
xmms2 play file.wav &
system
呼び出しは最初に分岐し、次に呼び出し元の環境変数を使用してシェルのインスタンスを開始するため、プログラムはディスプレイが であることを認識します (そしてそれを認識していることを証明します) 10.0
。ただし、ディスプレイへのアクセスは、コマンドが実行されるサブシェル内で許可される必要がありますxmms2
。この変更により、これが保証されます。
答え2
上記のコードを少し修正し、アドバイスを追加しました
含む
含む
含む
含む
typedef enum {WAIT、TEXT、PDF、DOC}STATES; typedef char STATE; STATE current_state;
char readcmd() //テキスト ファイル /home/pi/cmdrdy.txt から最初の文字を読み取ります { FILE *stream; int ch; if( (stream = fopen("/home/pi/cmdrdy.txt", "r")) == NULL ) return 0; ch =fgetc( stream ); fclose( stream ); return (ch-'0'); }
void reset()
{ ファイル *ft; char ch; ft = fopen( "/home/pi/cmdrdy.txt", "w" ); ch = '0'; fprintf(ft, "%c", ch ); fclose(ft); }
char convtts() { //convert text to speech
system("espeak -v en -f /home/pi/book.txt -w /home/pi/text.wav &");
return (0);
}
char pdf2txt(){ //convert pdf to text
system("pdftotext -layout /usr/lib/cgi-bin/upload/*.pdf /home/pi/converted.txt");
return (0);
}
char pdftts(){ //convert converted text to speech
system("espeak -v en -f /home/pi/converted.txt -w /home/pi/book.wav &");
return(0);
}
void state_machine(void){ //creating a state machine
switch(current_state){
case WAIT:
if(readcmd() == 1)
{
reset();
current_state = TEXT;
}
if(readcmd() == 2)
{
reset();
current_state = PDF;
}
break;
case TEXT:
convtts();
while(convtts()==1);
system("/home/pi/bin/text_script");
current_state = WAIT;
break;
case PDF:
pdf2txt();
while(pdf2txt()==1);
pdftts();
while(pdftts()==1);
system("/home/pi/bin/book_script");
system("sudo rm /usr/lib/cgi-bin/upload/*.pdf");
current_state = WAIT;
break;
} }
void main(){
while(1){
state_machine();
} }
そして、それは魔法のように機能します......本当にありがとう