⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 maptilecacher.perl

📁 google maps 下载程序,mgmaps手机软件本地可用
💻 PERL
字号:
#!/usr/bin/perl# version 1.21# created by MichaelAtUVa# updated by Cristian Streng based on suggestions by n95_rit, Kozawa, denilsonsa, CrazyTerabyte and others#Externalsuse Math::Trig;use POSIX;#Caching Variables$numZoomLevels = 17;$dir_TopLevel = "MGMapsCache";$file_CacheConf = "cache.conf";$cache_Version = 3;$tiles_per_file = 1;$hashSize = 97;# Sleep$sleepTime = 0;$sleepEvery = 10000;print <<EOF;*** MGMaps Tile Cacher ***EOF#OS Specific Variables $wget = "wget -Y off -nv -O TempTile ";$linuxDirDivider = "\/"; $linuxMoveCommand = "mv"; $linuxDeleteCommand = "rm";$windowsDirDivider = "\\"; $windowsMoveCommand = "move"; $windowsDeleteCommand = "del";print "Detected OS: $^O\n";if($^O ge "linux" || $^O ge "cygwin" ) {	$systemDirDivider = $linuxDirDivider;	$systemMoveCommand = $linuxMoveCommand;	$systemDeleteCommand = $linuxDeleteCommand;	$systemRefererParam = "--referer=http://maps.google.com/ ";}elsif($^O ge "MSWin"){	$systemDirDivider = $windowsDirDivider;	$systemMoveCommand = $windowsMoveCommand;	$systemDeleteCommand = $windowsDeleteCommand;	$systemRefererParam = "--referer=http://maps.google.com/ ";}if($^O eq "darwin"){	$systemDirDivider = $linuxDirDivider;	$systemMoveCommand = $linuxMoveCommand;	$systemDeleteCommand = $linuxDeleteCommand;	$wget = "curl -# -o TempTile ";	$systemRefererParam = "-e http://maps.google.com/ "; }$file_CacheConf = $dir_TopLevel.$systemDirDivider.$file_CacheConf;# Main# Read and/or write configurationif (-d $dir_TopLevel == FALSE) {  system("mkdir $dir_TopLevel");}# Search for version number$configured = 0;if (-f $file_CacheConf != FALSE) {  open(F, "<".$file_CacheConf) or die("Cannot read cache config file");  $line = <F>;  @splits = split('=', $line);  if (int($splits[1]) > 2) {    $line = <F>;    @splits = split('=', $line);    $tiles_per_file = int($splits[1]);    $configured = 1;  }  else {    print "Older version of MGMapsCache found, please (re)move it.\n";    exit;  }  close(F);}# Ask for configurationif ($configured == 0) {  # read configuration  print "Cache configuration file does not exist, configuring...\n\n";  do {    print "Map tiles per file (a power of two, 1-4096, default $tiles_per_file): ";    chomp($tpf = <>);    if ($tpf eq "") {      $tpf = $tiles_per_file;      break;    }    $tpf = int($tpf);    if ($tpf == 0) {      $tpf = $tiles_per_file;    }    # power of two  } while (($tpf & -$tpf) != $tpf);    $tiles_per_file = $tpf;    open(F, ">".$file_CacheConf) or die("Cannot write cache config file");  print F "version=".$cache_Version."\n";  print F "tiles_per_file=".$tiles_per_file."\n";  close(F);}else {  print "Storing $tiles_per_file tiles per file.\n\n";}$tiles_per_file_log = 0;$tpf = $tiles_per_file;while ($tpf > 1) {  $tiles_per_file_log++;  $tpf>>=1;}$tpfy = $tiles_per_file_log>>1;$tpfx = 1<<($tpfy + ($tiles_per_file_log&1));$tpfy = 1<<$tpfy;print <<EOF;Please choose map type by entering the associated keyword (case sensitive)...GoogleMap - Google Road MapsGoogleSat - Google Satellite ImagesGoogleHybrid - Google Satellite Images with Road Maps OverlayedGoogleChina - Google Road Maps (China)YahooMap - Yahoo Rood MapsYahooSat - Yahoo Satellite ImagesYahooHybrid - Yahoo Satellite Images with Road Maps OverlayedAskDotComMap - Ask.com Road MapsAskDotComSat - Ask.com Aerial ImagesAskDotComHybrid - Ask.com Aerial Images with LabelsMicrosoftMap - Microsoft Road MapsMicrosoftSat - Microsoft Aerial ImagesMicrosoftHybrid - Microsoft Aerial Images with Road Maps OverlayedOpenStreetMap - OpenStreetMap.org MapsEOFprint "Choice: ";do {	$MapType = <>;	$MapType =~ s/^\s+//;	$MapType =~ s/\s+$//;} while ($MapType eq "");# TODO make it case insensitiveprint "Enter Zoom Level (0-23): ";chomp($zoomLevel = <>);$zoomLevel = $numZoomLevels-$zoomLevel;print "\nEnter coordinates in decimal degrees format... 38.031078, -78.481529 \n";print "Top left (latitude, longitude):  ";($topLeftTileX, $topLeftTileY) = convertCoordindates2Tiles(split(/,/,<>,2), $zoomLevel);print "Bottom right (latitude, longitude):  ";($bottomRightTileX, $bottomRightTileY) = convertCoordindates2Tiles(split(/,/,<>,2), $zoomLevel);my $bound = 1<<($numZoomLevels-$zoomLevel);# swap coords if not in correct orderif ($topLeftTileX > $bottomRightTileX) { $t = $topLeftTileX; $topLeftTileX = $bottomRightTileX; $bottomRightTileX = $t; }if ($topLeftTileY > $bottomRightTileY) { $t = $topLeftTileY; $topLeftTileY = $bottomRightTileY; $bottomRightTileY = $t; }# out of map?if ($topLeftTileX < 0) { $topLeftTileX = 0; }if ($bottomRightTileX >= $bound) { $bottomRightTileX = $bound-1; }if ($topLeftTileY < 0) { $topLeftTileY = 0; }if ($bottomRightTileY >= $bound) { $bottomRightTileY = $bound-1; }# still swapped coords? (we're entirely out of the map)if ($topLeftTileX > $bottomRightTileX or $topLeftTileY > $bottomRightTileY) {  print "\n*** No map tiles to download ***\n";  exit;}$numTiles = (abs($topLeftTileX-$bottomRightTileX)+1)*(abs($topLeftTileY-$bottomRightTileY)+1);$numTiles *= (index($MapType,"Hybrid") != -1) ? 2 : 1;$zl = $numZoomLevels-$zoomLevel;print <<EOF;Ready to cache $numTiles tiles...Type: $MapTypeZoom: $zlPress enter to continue.EOF$_ = <>;print "*** Caching Started ***\n\n";my $tileCount = 0;my $actualTileCount = 0;downloadTiles($MapType, $topLeftTileX, $topLeftTileY, $bottomRightTileX, $bottomRightTileY);print "\n*** Caching Complete ***\n";exit;#MapTileCacher Subroutinessub convertCoordindates2Tiles {    my $lat = shift;    my $long = shift;    my $z = shift;     my $pixelsPerTile = 256;        my $mapsize = 2**(($numZoomLevels + (log($pixelsPerTile)/log(2)))-$z);    my $origin = $mapsize / 2;    my $longdeg = abs(-180 - $long);    my $longppd = $mapsize / 360;    my $longppdrad = $mapsize/(2*pi);    my $pixelx = $longdeg * $longppd;    my $longtiles = $pixelx  / $pixelsPerTile;        my $tilex = cast2Integer($longtiles);        my $e = sin($lat*(1/180.*pi));    if ($e>0.9999) { $e=0.9999; }    if ($e<-0.9999) { $e=-0.9999; }        my $pixely = $origin + 0.5*log((1+$e)/(1-$e)) * (-$longppdrad);     my $tiley = cast2Integer($pixely / $pixelsPerTile);    return ($tilex, $tiley);}sub downloadTiles{	my $MapType = shift; 	my $topLeftTileX = shift;	my $topLeftTileY = shift;	my $bottomRightTileX = shift;	my $bottomRightTileY = shift;  		if(index($MapType,"Hybrid") != -1)	{	    my $MapSource = substr($MapType,0,index($MapType,"Hybrid"));	    downloadTiles($MapSource . "Sat", $topLeftTileX, $topLeftTileY, $bottomRightTileX, $bottomRightTileY);	    downloadTiles($MapSource . "Hyb", $topLeftTileX, $topLeftTileY, $bottomRightTileX, $bottomRightTileY);	}	else	{		for ($y = $topLeftTileY; $y <= $bottomRightTileY; $y++) 		{			for ($x = $topLeftTileX; $x <= $bottomRightTileX; $x++) 			{				$tileCount++;				# avoid sleeping for #0				if ((($actualTileCount+1) % $sleepEvery) == 0)				{					print "* Sleeping $sleepTime seconds\n";					sleep($sleepTime);				}								my $localFileName = $dir_TopLevel . $systemDirDivider . $MapType . "_" .($numZoomLevels-$zoomLevel);				if ($tiles_per_file == 1) {				  $localFileName .= $systemDirDivider . (($x*256+$y)%$hashSize) . $systemDirDivider . "$x\_$y";				}				else {				  $localFileName .= $systemDirDivider . int($x/$tpfx) . "_" . int($y/$tpfy);				}				$localFileName .= ".mgm";				$dx = $x % $tpfx;				$dy = $y % $tpfy;								my $url = getTileURL($MapType,$x,$y);				$found = checkCached($localFileName,$dx,$dy);								if($found == 0)				{					my $referer = (index($MapType,"Google") != -1) ? $systemRefererParam : "";					$wgetFileCommand = $wget . $referer. "\"" . $url . "\"" ;					print "* Downloading tile $tileCount of $numTiles from $url\n";					if (index($MapType,"Sat") != -1) {$actualTileCount++;}					system($wgetFileCommand);					cacheDownloadedTile("TempTile",$localFileName,$dx,$dy); 				} 								else {print "* Skipping tile $tileCount of $numTiles from $url (already cached).\n";}			}		}	}}# check if the map tile is already cached in $localFilename as ($dx,$dy)sub checkCached{	my $localFileName = shift;	my $dx = shift;	my $dy = shift;	local $buf = '';		if (-f $localFileName == FALSE) {	  return 0;	}		# if the file exists and we have 1 tile/file, don't verify anything else	elsif ($tiles_per_file == 1) {	  return 1;	}		sysopen(FD, $localFileName, O_RDONLY);	binmode(FD);	sysread(FD, $buf, 6*$tiles_per_file+2);	$num = (ord(substr($buf,0,1))<<8)+ord(substr($buf,1,1));	for (my $i=0; $i<$num; $i++) {	  if (ord(substr($buf,2+$i*6,1)) == $dx && ord(substr($buf,2+$i*6+1,1)) == $dy) {	    close(FD);	    return 1;	  }	}	close(FD);	return 0;}sub cacheDownloadedTile{	my $tempTile = shift;	my $localFileName = shift; 	my $dx = shift;	my $dy = shift;	local $buf = '';		if(-s $tempTile)	{		my $dir_TopLevel;		my $dir_TypeZoomLevel;		my $dir_HashLevel;		if ($tiles_per_file == 1) {		  ($dir_TopLevel, $dir_TypeZoomLevel, $dir_HashLevel) 			= split(($systemDirDivider eq "\\") ? "$systemDirDivider$systemDirDivider" : "$systemDirDivider",$localFileName);		}				else {		  ($dir_TopLevel, $dir_TypeZoomLevel) 			= split(($systemDirDivider eq "\\") ? "$systemDirDivider$systemDirDivider" : "$systemDirDivider",$localFileName);		}				$dir_TypeZoomLevel = $dir_TopLevel . $systemDirDivider . $dir_TypeZoomLevel;		if(-d $dir_TypeZoomLevel == FALSE){system("mkdir $dir_TypeZoomLevel");}				if ($tiles_per_file == 1) {		  $dir_HashLevel = $dir_TypeZoomLevel . $systemDirDivider . $dir_HashLevel;		  if(-d $dir_HashLevel == FALSE){system("mkdir $dir_HashLevel");}		  system("$systemMoveCommand $tempTile $localFileName");		  print "\tTile cached at $localFileName\n";		  return;		}				# append to the file, write info and offset to header		my $num = 0;		my $ofs = $tiles_per_file*6+2;		$existed = ((-f $localFileName != FALSE) ? 1 : 0);		sysopen($fh, $localFileName, O_RDWR|O_CREAT);		binmode($fh);		if ($existed == 1) {		  sysread($fh, $buf, $ofs);		  $num = (ord(substr($buf,0,1))<<8)+ord(substr($buf,1,1));		  $ofs = (ord(substr($buf,2+$num*6-6+2,1))<<24)+		         (ord(substr($buf,2+$num*6-6+3,1))<<16)+		         (ord(substr($buf,2+$num*6-6+4,1))<<8)+		         ord(substr($buf,2+$num*6-6+5,1));		}		else {		  $buf = chr(0) x $ofs;		  syswrite($fh, $buf, $ofs);		}		my $totalsize = 0;		sysseek($fh, $ofs, 0);		sysopen(F2, $tempTile, O_RDONLY);		binmode(F2);		while ((my $read = sysread(F2, $buf, 4096)) > 0) {		  $totalsize += $read;		  syswrite($fh, $buf, $read);		}		close(F2);		# new offset		$totalsize += $ofs;				# update header - number of tiles		$buf = "" . chr(($num+1)>>8) . chr(($num+1)&255);		sysseek($fh, 0, 0);		syswrite($fh, $buf, 2);				# update header - new tile data		$buf = "" . chr($dx) . chr($dy) . chr($totalsize>>24) . chr(($totalsize>>16)&255) . chr(($totalsize>>8)&255) . chr($totalsize&255);		sysseek($fh, 6*$num+2, 0);		syswrite($fh, $buf, 6);		close($fh);				# delete temp tile		system("$systemDeleteCommand $tempTile");				# system("$systemMoveCommand $tempTile $localFileName");				print "\tTile cached at $localFileName\n"	}	else {system("$systemDeleteCommand $tempTile"); print "\tERROR: Requested tile did not exist.\n"}}sub getTileURL{	my $MapType = shift;	my $x = shift;	my $y = shift;	 	my $url = "";		if($MapType eq "GoogleMap" || $MapType eq "GoogleHyb")	{		$url = "http://mt" . (($x+$y)%4) . ".google.com/mt?n=404&v=";		$url .= ($MapType eq "GoogleMap") ? "w2.56" : "w2t.57";		$url .= "&x=$x&y=$y&zoom=$zoomLevel"; 	}	elsif($MapType eq "GoogleChina")	{		$url = "http://mapgoogle.mapabc.com/googlechina/maptile?v=w2.56";		$url .= "&x=$x&y=$y&zoom=$zoomLevel"; 	}	elsif($MapType eq "GoogleSat")	{ 		my @goolgeSatURLLetters = ("q", "r", "t", "s" );				$url = "http://kh" . (($x+$y)%4) . ".google.com/kh?n=404&v=18&t=t";		for($i=$numZoomLevels-$zoomLevel-1; $i >= 0; $i--)		{ 			$url .= $goolgeSatURLLetters[((($y >> $i) & 1) << 1) + (($x >> $i) & 1)];		}	}  	elsif(index($MapType,"Yahoo") != -1)	{		$url = ($MapType eq "YahooMap") ? "http://png.maps.yimg.com/png?t=m&v=3.52" : 			 ($MapType eq "YahooSat") ? "http://aerial.maps.yimg.com/tile?t=a&v=1.7" : "http://aerial.maps.yimg.com/png?t=h&v=2.2";		$url .= "&x=$x&y=" . (((1 << ($numZoomLevels-$zoomLevel)) >> 1)-1-$y) . "&z=" . ($zoomLevel+1); 	}	elsif(index($MapType,"Microsoft") != -1)	{		$url  = ($MapType eq "MicrosoftMap") ?  "http://r" : ($MapType eq "MicrosoftSat") ?  "http://a" : "http://h";		$url .= ((($y & 1) << 1) + ($x & 1)) . ".ortho.tiles.virtualearth.net/tiles/";		$url .= ($MapType eq "MicrosoftMap") ?  "r" : ($MapType eq "MicrosoftSat") ?  "a" : "h";		for($i=$numZoomLevels-$zoomLevel-1; $i >= 0; $i--)		{        	    $url = $url . ((((($y >> $i) & 1) << 1) + (($x >> $i) & 1)));		} 		$url .= ($MapType eq "MicrosoftMap") ?  ".png?g=72" : ".jpeg?g=72";	}	elsif(index($MapType,"AskDotCom") != -1)	{		$url  = ($zoomLevel > 6) ? "http://mapstatic" : "http://mapcache";		$url .= (($x+$y)%4 + 1) . ".ask.com/";		$url .= ($MapType eq "AskDotComMap") ? "map" : ($MapType eq "AskDotComSat") ? "sat" : "mapt"; 		$url .= "/" . ($zoomLevel+2) . "/";		$url .= ($x-((1<<($numZoomLevels-$zoomLevel))>>1)) . "/" . ($y-((1<<($numZoomLevels-$zoomLevel))>>1));		$url .= "?partner=&tc=28";	}	elsif(index($MapType,"OpenStreetMap") != -1)	{		$url  = "http://tile.openstreetmap.org/" . ($numZoomLevels-$zoomLevel) . "/" . $x . "/" . $y . ".png";	}		return $url}#Utility Subroutinessub cast2Integer {    my $f = shift;    if ($f < 0) {return ceil($f);}    else {return floor($f);}}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -