-
Notifications
You must be signed in to change notification settings - Fork 10
/
Copy pathtools.c
136 lines (114 loc) · 3.95 KB
/
tools.c
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "media.h"
#include "tools.h"
/*
* Some info:
* ----------
* xdg-open uses .desktop files, which can be found in /usr/share/applications/
* Local .desktop files of the user can be found in ~/.local/share/applications/
*
* You can get a file's default open command with:
* xdg-mime query default $(file --mime-type -b filename)
*
* You can set it with:
* xdg-mime default file.desktop mime/type
*
* xdg-open saves these associations of the user in ~/.local/share/applications/mimeapps.list
*/
#define OPEN_COMMAND "DISPLAY=:%d xdg-open "
#define XDG_QUERY_DEFAULT "xdg-mime query default "
static void xdg_open(char *fullpath, int display_number)
{
// Ugly hack to check if it is a .desktop file that contains a URL= entry
// This should be made into a pure C implementation, instead of this shell logic
char checkurl[4096];
snprintf(checkurl, 4096, "filename=%s; if [ $(echo \"$filename\" | tail -c -9) = \".desktop\" ]; then grep URL= \"$filename\" | cut -c 5-; fi", fullpath);
char *url = execute_binary(checkurl);
if (strlen(url)>0)
fullpath = url;
char command[4096];
snprintf(command, 40, OPEN_COMMAND, display_number);
strcat(command, "\"");
strcat(command, fullpath);
strcat(command, "\" &");
printf("Executing command to open file: %s\n", command);
system(command);
}
// When a user points to and clicks on an object, the tool is applied on it
int apply_tool_on_object(struct tree_entry *object, char *currentpath)
{
int toreturn = 0;
// We'll need the full path
char fullpath[4096] = { 0 };
strcat(fullpath, currentpath);
if (strlen(fullpath) > 1)
strcat(fullpath, "/");
strcat(fullpath, object->name);
if (CURRENT_TOOL == TOOL_OPENER) {
// If we have an in-world handler for the file, use it
if (object->regtype == VIDEOFILE || object->regtype == VIDEOSOURCEFILE || object->regtype == AUDIOFILE || object->regtype == PROCESS) {
if (object == TDFSB_MEDIA_FILE) {
toggle_media_pipeline();
} else {
cleanup_media_player(); // Stop all other playing media
play_media(fullpath, object);
}
} else if (object->openwith) {
cleanup_media_player();
play_media(fullpath, object); // Start an X server
xdg_open(fullpath, 1); // Start the program that opens the file
calculate_scale(object);
toreturn = 1;
}
} else if (CURRENT_TOOL == TOOL_EXTERNAL_OPENER) {
xdg_open(fullpath, 0);
} else if (CURRENT_TOOL == TOOL_WEAPON) {
// printf("TODO: Start some animation on the object to show it is being deleted ");
object->tombstone = 1; // Mark the object as deleted
// Refresh (fairly static) GLCallLists with Solids and Blends so that the tool applications will be applied
toreturn = 1;
} else {
printf("ERROR: invalid tool type %d cannot be applied on object %s\n", CURRENT_TOOL, object->name);
}
return toreturn;
}
void init_tools(void)
{
CURRENT_TOOL = TOOL_OPENER; // The tool (or weapon) we are currently holding
tool[TOOL_OPENER] = "Open file/folder in 3D world";
tool[TOOL_EXTERNAL_OPENER] = "Open file/folder in 2D desktop";
tool[TOOL_WEAPON] = "Laser shooter demo (file not really deleted :-)";
}
char *xdg_query_default(const char *mimetype)
{
char *command = malloc(sizeof(char) * 1024);
strcpy(command, XDG_QUERY_DEFAULT);
strcat(command, mimetype);
char *default_program_desktop_file = execute_binary(command);
free(command);
return default_program_desktop_file;
}
char *execute_binary(char *toexec)
{
FILE *fp;
int i;
char path[1035] = { 0 };
char *toreturn = malloc(sizeof(char) * 1024);
// Zero initialize (isn't there a zmalloc in user space?!)
for (i = 0; i < 1024; i++)
toreturn[i] = 0;
// xdg-mime query default $(file --mime-type -b filename)
fp = popen(toexec, "r");
if (fp == NULL) {
printf("ERROR: Failed to run the command\n");
}
/* Read the output a line at a time - output it. */
while (fgets(path, sizeof(path) - 1, fp) != NULL) {
strcat(toreturn, path);
}
/* close */
pclose(fp);
return toreturn;
}