//author: bobef //license: use without restrictions at your own risk import std.stdio; import std.string; import std.path; import std.file; version=t_Windows; version(t_Windows) static const char[1] std_path_sep="\\"; version(t_Linux) static const char[1] std_path_sep="/"; char[] fixPath(char[] s) { version(t_Windows){return replace(s,"/","\\");} version(t_Linux){return replace(s,"\\","/");} } char[] getFullPath(char[] path) { if(!path.length) return null; path=fixPath(path); version(Linux) path=expandTilde(path); version(Windows) if(getDrive(path).length) return _cleanPath(path,0); if(path[0]==std_path_sep[0]) { version(Windows) return cleanPath(getDrive(getcwd())~path); version(Linux) return cleanPath(path); } else return cleanPath(getcwd()~std_path_sep~path); } int getRelativePath(char[] basepath,char[] destpath,out char[] ret) { basepath=fixPath(basepath); destpath=fixPath(destpath); if(!destpath.length) return 0; if(!basepath.length) {ret=destpath;return 1;} if(basepath[basepath.length-1]==std_path_sep[0]) basepath.length=basepath.length-1; if(destpath[destpath.length-1]==std_path_sep[0]) destpath.length=destpath.length-1; version(Windows) { char[] drv1=_getDrive(basepath,0); char[] drv2=_getDrive(destpath,0); int s1=0,s2=0; if(drv1.length && drv2.length && drv1!=drv2) {ret=destpath;return 1;} else { if(drv1.length) s1=drv1.length+1; if(drv2.length) s2=drv2.length+1; } char[][] basedirs = s1=destdirs.length?destdirs.length:basedirs.length; int lastCommonDir=-1; for (int i=0; il1) { destdirs=destdirs[l1..destdirs.length].dup; //do we need dup? if(end>0) ret~=std.path.sep; } else destdirs=null; if(destdirs.length) ret ~= _cleanPath(std.string.join(destdirs,std_path_sep),0); return 1; } char[] getDrive(char[] path) { version(t_Linux) return null; version(t_Windows) return _getDrive(path,1); } private char[] _getDrive(char[] path,int fix) { version(Linux) return null; version(Windows) { if(path.length<2) return null; if(fix) path=fixPath(path); if(path[0..2]=="\\\\") { int r=find(path[2..path.length],std_path_sep); if(r>0) return path[0..r+2]; else return path; } else { int r=find(path,':'); if(r>0) return path[0..r+1]; else return null; } } } char[] cleanPath(char[] path){return _cleanPath(path,1);} private char[] _cleanPath(char[] path,int fix) { if(fix) path=fixPath(path); char[][] as=split(path,std_path_sep); int[] i; version(Windows) int mindir=_getDrive(path,0).length?1:0; if(as.length) { for(int c=0;cmindir) if(i.length) i.length=i.length-1; else {if(as[c].length || (!as[c].length && !c)) i~=c;} //do not skip initial slash } else {if(as[c].length || (!as[c].length && !c)) i~=c;} //do not skip initial slash } char[] ret; version(Linux) ret=std_path_sep; int end=i.length-1; for(int c=0;c