在 C 中使用 ueberzug 在终端中覆盖图像
Overlay image in terminal using ueberzug within C
使用 ueberzug 库,可以在 X11 下的终端 windows 中叠加图像。
该库是用 python 编写的 - 为 bash 和 python.
提供了有关如何使用该库的示例
要在终端中叠加图像,只需 运行 ueberzug layer
然后输入 json 格式的字符串,如 {"action": "add", "x": 0, "y": 0, "identifier": "test", "path": "/tmp/image.jpg"}
。这完美无缺。
我想在 C 中调用这个过程。
如果我理解正确,我只需生成一个新进程,然后写入其标准输入,这通常是一项简单的任务。
但是,在我的例子中,我可以看到图像在应用程序终止前闪烁了几分之一秒。这是我的代码:
#include <stdio.h>
#include <stdlib.h>
void run_ueberzug()
{
FILE *output;
output = popen("ueberzug layer", "w");
if (!output)
{
fprintf(stderr, "Incorrect parameters or too many files.\n");
exit(EXIT_FAILURE);
}
fprintf(output, "{\"action\": \"add\", \"x\": 0, \"y\": 0, \"identifier\": \"test\", \"path\": \"/tmp/image.jpg\"}\n");
if (ferror(output))
{
fprintf(stderr, "Output to stream failed.\n");
exit(EXIT_FAILURE);
}
if (pclose(output) != 0)
{
fprintf(stderr, "Could not run more or other error.\n");
exit(EXIT_FAILURE);
}
}
int main(void)
{
run_ueberzug();
return 0;
}
如何解决图片显示不正确的问题? (不只是几分之一秒)
此外,我应该 运行 在单独的线程中吗?目标是能够正确控制 ueberzug 的行为,也就是以编程方式显示图像或 unshow/remove 图像,而不阻塞主应用程序。
为了总结评论,以下解决方案基于您的作品:
- 通过
popen
你fork一个进程,创建一个双向管道并在子shell 中启动命令
- 随后,写入管道,向 ueberzug 发出命令
- 管道必须
fflush
ed,否则只有在进程退出时才会传输
- 如果子 shell 是 killed/quits
,则信号处理程序会捕获 ueberzug 子进程
同时,main
可以继续 运行 您的代码。下面的代码循环显示 3 张图片。
#include <errno.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#define ERROR(text,error) do { fprintf(stderr, "ERROR:%s error:%d\n", (text), error); exit(error); } while(0)
static FILE *output = NULL;
void run_ueberzug()
{
output = popen("/home/hpcraink/.local/bin/ueberzug layer --parser json ", "w");
if (!output)
ERROR("Incorrect parameters or too many files", errno);
}
void mysighandler(int signal) {
int wstatus;
wait(&wstatus);
if (pclose(output) != 0)
ERROR("Could not run more or other error", errno);
}
int main(void)
{
int i = 0;
const char * files[] = {
"img0.jpg",
"img1.jpg",
"img2.jpg",
};
run_ueberzug();
signal(SIGCHLD, &mysighandler);
while (1) {
fprintf(output, "{\"action\": \"remove\", \"identifier\": \"img\"}\n");
fprintf(output, "{\"action\": \"add\", \"x\": 0, \"y\": 0, \"identifier\": \"img\", \"path\": \"%s\"}\n", files[i]);
fflush(output);
i = (i + 1) % (sizeof(files)/sizeof(files[0]));
sleep(1);
}
return EXIT_SUCCESS;
}
使用 ueberzug 库,可以在 X11 下的终端 windows 中叠加图像。 该库是用 python 编写的 - 为 bash 和 python.
提供了有关如何使用该库的示例要在终端中叠加图像,只需 运行 ueberzug layer
然后输入 json 格式的字符串,如 {"action": "add", "x": 0, "y": 0, "identifier": "test", "path": "/tmp/image.jpg"}
。这完美无缺。
我想在 C 中调用这个过程。 如果我理解正确,我只需生成一个新进程,然后写入其标准输入,这通常是一项简单的任务。
但是,在我的例子中,我可以看到图像在应用程序终止前闪烁了几分之一秒。这是我的代码:
#include <stdio.h>
#include <stdlib.h>
void run_ueberzug()
{
FILE *output;
output = popen("ueberzug layer", "w");
if (!output)
{
fprintf(stderr, "Incorrect parameters or too many files.\n");
exit(EXIT_FAILURE);
}
fprintf(output, "{\"action\": \"add\", \"x\": 0, \"y\": 0, \"identifier\": \"test\", \"path\": \"/tmp/image.jpg\"}\n");
if (ferror(output))
{
fprintf(stderr, "Output to stream failed.\n");
exit(EXIT_FAILURE);
}
if (pclose(output) != 0)
{
fprintf(stderr, "Could not run more or other error.\n");
exit(EXIT_FAILURE);
}
}
int main(void)
{
run_ueberzug();
return 0;
}
如何解决图片显示不正确的问题? (不只是几分之一秒)
此外,我应该 运行 在单独的线程中吗?目标是能够正确控制 ueberzug 的行为,也就是以编程方式显示图像或 unshow/remove 图像,而不阻塞主应用程序。
为了总结评论,以下解决方案基于您的作品:
- 通过
popen
你fork一个进程,创建一个双向管道并在子shell 中启动命令
- 随后,写入管道,向 ueberzug 发出命令
- 管道必须
fflush
ed,否则只有在进程退出时才会传输 - 如果子 shell 是 killed/quits ,则信号处理程序会捕获 ueberzug 子进程
同时,main
可以继续 运行 您的代码。下面的代码循环显示 3 张图片。
#include <errno.h>
#include <signal.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#define ERROR(text,error) do { fprintf(stderr, "ERROR:%s error:%d\n", (text), error); exit(error); } while(0)
static FILE *output = NULL;
void run_ueberzug()
{
output = popen("/home/hpcraink/.local/bin/ueberzug layer --parser json ", "w");
if (!output)
ERROR("Incorrect parameters or too many files", errno);
}
void mysighandler(int signal) {
int wstatus;
wait(&wstatus);
if (pclose(output) != 0)
ERROR("Could not run more or other error", errno);
}
int main(void)
{
int i = 0;
const char * files[] = {
"img0.jpg",
"img1.jpg",
"img2.jpg",
};
run_ueberzug();
signal(SIGCHLD, &mysighandler);
while (1) {
fprintf(output, "{\"action\": \"remove\", \"identifier\": \"img\"}\n");
fprintf(output, "{\"action\": \"add\", \"x\": 0, \"y\": 0, \"identifier\": \"img\", \"path\": \"%s\"}\n", files[i]);
fflush(output);
i = (i + 1) % (sizeof(files)/sizeof(files[0]));
sleep(1);
}
return EXIT_SUCCESS;
}