当前位置:  编程技术>综合
本页文章导读:
    ▪如何制作一个基于Tile的游戏 Cocos2d-x 2.0.4            本文实践自 Ray Wenderlich 的文章《How To Make a Tile-Based Game with Cocos2D》,文中使用Cocos2D,我在这里使用Cocos2D-x 2.0.4进行学习和移植。这个游戏是关于一个忍者在沙漠中寻找.........
    ▪[Magento] Change store's language and currency according to customer's GeoIP?      It is brilliant that your online store or shop can show customers' native language and currency when they access your stores.This is dynamic and charming feature we want to achieve in Magento. Luckily, Magento supports multiple-language and currency in.........
    ▪struts1源码阅读(2)          在第一章中,我们讲到在ActionServlet初始化时,不同的模块会初始化不同的ModuleConfig对象。但struts1到底是如何初始化ModuleConfig对象的,当时并没有详细叙述。这些内容将是本章的.........

[1]如何制作一个基于Tile的游戏 Cocos2d-x 2.0.4
    来源: 互联网  发布时间: 2013-11-07

      本文实践自 Ray Wenderlich 的文章《How To Make a Tile-Based Game with Cocos2D》,文中使用Cocos2D,我在这里使用Cocos2D-x 2.0.4进行学习和移植。这个游戏是关于一个忍者在沙漠中寻找西瓜的故事。
      在这部分内容,将会学习到如何用Tile创建一个地图,如何加载地图到游戏,如何让地图跟随玩家滚动,以及如何使用对象层。下一部分内容,将介绍如何在地图中创建可碰撞的区域,如何使用Tile属性,如何创建可拾取的物品和动态修改地图,以及如何确保忍者不会吃撑掉。
 
步骤如下:
1.新建Cocos2d-win32工程,工程名为"TileGame",去除"Box2D"选项,勾选"Simple Audio Engine in Cocos Denshion"选项;
2.下载本游戏所需的资源,将资源放置"Resources"目录下;

3.使用Tiled工具制作地图。首先,下载开源的Tiled Map Editor工具,当前版本为0.8.1,建议使用QT版本。在Tiled工具,点击菜单栏→"文件"→"新文件",在弹出的对话框中,填入如下内容:

地图方向分为:正常、45度。地图大小填入的是tile单位。块大小是资源每个tile的实际像素大小,在本篇中,使用32x32大小。点击"确定"。
4.接着,把所需要的tile集合加入到工具中。菜单栏→"地图"→"新图块",填入如下内容:

点击"浏览",选择"Resources"目录下的tmw_desert_spacing.png文件,会自动填充"名称"内容。块的宽高都为32像素。边距就是当前tile块开始计算实际像素时,应该跳过多少像素,宽高一样。间距就是两个tile块之间的像素距离,宽高一样。看看tmw_desert_spacing.png文件,可以看到每个tile块都1像素的黑色边框,这就是为什么要设置边距和间距为1像素。

点击"确定"。
5.可以看到tile块出现在"图块"窗口中。现在可以开始画地图。点击菜单栏→"视图"→"显示网格",可以开启网格参照线。点击工具栏"图章刷",然后在"图块"窗口点选一个tile块,接着在地图中,点击放入你所想要的位置。

用工具栏"填充",把地图背景填充成同一个tile块,这里为沙漠背景。可以从"图块"窗口点选多个tile块,可按Ctrl键多选,这样可以一次性将多个tile块放入地图中。进行制作地图,确保至少有一对建筑在地图上,因为后面需要一些东西来做碰撞。一旦完成了地图的制作,双击"图层"窗口中的当前层"块层 1",重命名为"Background"。然后点击工具栏"保存",命名为"TileMap.tmx",保存在"Resources"目录下。

6.将Tile地图加入到场景中。在HelloWorldScene.h文件中,添加如下代码:

1
2
CC_SYNTHESIZE_RETAIN(cocos2d::CCTMXTiledMap*, _tileMap, TileMap);
CC_SYNTHESIZE_RETAIN(cocos2d::CCTMXLayer*, _background, Background);
在HelloWorldScene.cpp文件中,构造函数添加如下:
1
2
3
4
5
HelloWorld::HelloWorld()
{
    _tileMap = NULL;
    _background = NULL;
}
初始化init函数,修改如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
bool HelloWorld::init()
{
    bool bRet = false;
    do 
    {    
        CC_BREAK_IF(! CCLayer::init());

        this->setTileMap(CCTMXTiledMap::create("TileMap.tmx"));
        this->setBackground(_tileMap->layerNamed("Background"));
        this->addChild(_tileMap, -1);
        bRet = true;
    } while (0);

    return bRet;
}

7.编译运行,可以看到整个地图的左下角,如下图所示:

要让它成为一个游戏,还需要三件事:玩家、玩家初始点、移动视图以便能够看到玩家。
8.Tiled支持两种类型层:tile层和对象层。对象层允许你在地图上可能发生事件的区域绘制矩形。比如:你可能需要一个怪物出生区域,或者一个一进入就会挂掉的区域。在这里,我们给玩家创建一个出生地。菜单栏→"图层"→"添加对象层",命名为"Objects",点击工具栏"插入对象",在地图上选择一个位置并点击它,这时会出现一个灰色的矩形框,右键选择"对象属性",名称填入"SpawnPoint&quo

    
[2][Magento] Change store's language and currency according to customer's GeoIP?
    来源: 互联网  发布时间: 2013-11-07

It is brilliant that your online store or shop can show customers' native language and currency when they access your stores.This is dynamic and charming feature we want to achieve in Magento. Luckily, Magento supports multiple-language and currency in one installation. I will try to use GeoIP database data to integrate with Magento.

When you run Magento store, there is one step called store initialization. From code's viewpoint, it is that index.php calls the methods in Mage class and Mage class calls the methods in Mage_Core_Model_App class. In  Mage_Core_Model_App class, the store you run is initialized as below:

    protected function _initCurrentStore($scopeCode, $scopeType)
    {
        Varien_Profiler::start('mage::app::init::stores');
        $this->_initStores();
        Varien_Profiler::stop('mage::app::init::stores');

        if (empty($scopeCode) && !is_null($this->_website)) {
            $scopeCode = $this->_website->getCode();
            $scopeType = 'website';
        }
        switch ($scopeType) {
            case 'store':
                $this->_currentStore = $scopeCode;
                break;
            case 'group':
                $this->_currentStore = $this->_getStoreByGroup($scopeCode);
                break;
            case 'website':
                $this->_currentStore = $this->_getStoreByWebsite($scopeCode);
                break;
            default:
                $this->throwStoreException();
        }

        if (!empty($this->_currentStore)) {
            $this->_checkCookieStore($scopeType);
            $this->_checkGetStore($scopeType);
        }
        $this->_useSessionInUrl = $this->getStore()->getConfig(
            Mage_Core_Model_Session_Abstract::XML_PATH_USE_FRONTEND_SID);
        return $this;
    }
In regard to stores, It has default currency and language, but we can also use class Mage_Core_Model_Store's method to change the currency the store is using.

    public function setCurrentCurrencyCode($code)
    {
        $code = strtoupper($code);
        if (in_array($code, $this->getAvailableCurrencyCodes())) {
            $this->_getSession()->setCurrencyCode($code);
            if ($code == $this->getDefaultCurrency()) {
                Mage::app()->getCookie()->delete(self::COOKIE_CURRENCY, $code);
            } else {
                Mage::app()->getCookie()->set(self::COOKIE_CURRENCY, $code);
            }
        }
        return $this;
    }
Since we know how to change the currency, the left question is how we get the customer's country and currency information when they visit your site. GeoIP data gives us the answer.First of all, we can get the customer's IP when he comes to your stores.

$ip = $_SERVER['REMOTE_ADDR'];
The next step is to find the country and currency based on the GeoIP database.

class Wonder_GeoIP_Model_Wrapper
{
    private $flags;
    private $filehandle;
    private $memory_buffer;
    private $databaseType;
    private $databaseSegments;
    private $record_length;
    private $shmid;
    private $GEOIP_COUNTRY_CODE_TO_NUMBER = array(
        "" => 0, "AP" => 1, "EU" => 2, "AD" => 3, "AE" => 4, "AF" => 5,
        "AG" => 6, "AI" => 7, "AL" => 8, "AM" => 9, "CW" => 10, "AO" => 11,
        "AQ" => 12, "AR" => 13, "AS" => 14, "AT" => 15, "AU" => 16, "AW" => 17,
        "AZ" => 18, "BA" => 19, "BB" => 20, "BD" => 21, "BE" => 22, "BF" => 23,
        "BG" => 24, "BH" => 25, "BI" => 26, "BJ" => 27, "BM" => 28, "BN" => 29,
        "BO" => 30, "BR" => 31, "BS" => 32, "BT" => 33, "BV" => 34, "BW" => 35,
        "BY" => 36, "BZ" => 37, "CA" => 38, "CC" => 39, "CD" => 40, "CF" => 41,
        "CG" => 42, "CH" => 43, "CI" => 44, "CK" => 45, "CL" => 46, "CM" => 47,
        "CN" => 48, "CO" => 49, "CR" => 50, "CU" => 51, "CV" => 52, "CX" => 53,
        "CY" => 54, "CZ" => 55, "DE" => 56, "DJ" => 57, "DK" => 58, "DM" => 59,
        "DO" => 60, "DZ" => 61, "EC" => 62, "EE" => 63, "EG" => 64, "EH" => 65,
        "ER" => 66, "ES" => 67, "ET" => 68, "FI" => 69, "FJ" => 70, "FK" => 71,
        "FM" => 72, "FO" => 73, "FR" => 74, "SX" => 75, "GA" => 76, "GB" => 77,
        "GD" => 78, "GE" => 79, "GF" => 80, "GH" => 81, "GI" => 82, "GL" => 83,
        "GM" => 84, "GN" => 85, "GP" => 86, "GQ" => 87, "GR" => 88, "GS" => 89,
        "GT" => 90, "GU" => 91, "GW" => 92, "GY" => 93, "HK" => 94, "HM" => 95,
        "HN" => 96, "HR" => 97, "HT" => 98, "HU" => 99, "ID" => 100, "IE" => 101,
        "IL" => 102, "IN" => 103, "IO" => 104, "IQ" => 105, "IR" => 106, "IS" => 107,
        "IT" => 108, "JM" => 109, "JO" => 110, "JP" => 111, "KE" => 112, "KG" => 113,
        "KH" => 114, "KI" => 115, "KM" => 116, "KN" => 117, "KP" => 118, "KR" => 119,
        "KW" => 120, "KY" => 121, "KZ" => 122, "LA" => 123, "LB" => 124, "LC" => 125,
        "LI" => 126, "LK" => 127, "LR" => 128, "LS" => 129, "LT" => 130, "LU" => 131,
        "LV" => 132, "LY" => 133, "MA" => 134, "MC" => 135, "MD" => 136, "MG" => 137,
        "MH" => 138, "MK" => 139, "ML" => 140, "MM" => 141, "MN" => 142, "MO" => 143,
        "MP" => 144, "MQ" => 145, "MR" => 146, "MS" => 147, "MT" => 148, "MU" => 149,
        "MV" => 150, "MW" => 151, "MX" => 152, "MY" => 153, "MZ" => 154, "NA" => 155,
        "NC" => 156, "NE" => 157, "NF" => 158, "NG" => 159, "NI" => 160, "NL" => 161,
        "NO" => 162, "NP" => 163, "NR" => 164, "NU" => 165, "NZ" => 166, "OM" => 167,
        "PA" => 168, "PE" => 169, "PF" => 170, "PG" => 171, "PH" => 172, "PK" => 173,
        "PL" => 174, "PM" => 175, "PN" => 176, "PR" => 177, "PS" => 178, "PT" => 179,
        "PW" => 180, "PY" => 181, "QA" => 182, "RE" => 183, "RO" => 184, "RU" => 185,
        "RW" => 186, "SA" => 187, "SB" => 188, "SC" => 189, "SD" => 190, "SE" => 191,
        "SG" => 192, "SH" => 193, "SI" => 194, "SJ" => 195, "SK" => 196, "SL" => 197,
        "SM" => 198, "SN" => 199, "SO" => 200, "SR" => 201, "ST" => 202, "SV" => 203,
        "SY" => 204, "SZ" => 205, "TC" => 206, "TD" => 207, "TF" => 208, "TG" => 209,
        "TH" => 210, "TJ" => 211, "TK" => 212, "TM" => 213, "TN" => 214, "TO" => 215,
        "TL" => 216, "TR" => 217, "TT" => 218, "TV" => 219, "TW" => 220, "TZ" => 221,
        "UA" => 222, "UG" => 223, "UM" => 224, "US" => 225, "UY" => 226, "UZ" => 227,
        "VA" => 228, "VC" => 229, "VE" => 230, "VG" => 231, "VI" => 232, "VN" => 233,
        "VU" => 234, "WF" => 235, "WS" => 236, "YE" => 237, "YT" => 238, "RS" => 239,
        "ZA" => 240, "ZM" => 241, "ME" => 242, "ZW" => 243, "A1" => 244, "A2" => 245,
        "O1&      
    
[3]struts1源码阅读(2)
    来源: 互联网  发布时间: 2013-11-07

    在第一章中,我们讲到在ActionServlet初始化时,不同的模块会初始化不同的ModuleConfig对象。但struts1到底是如何初始化ModuleConfig对象的,当时并没有详细叙述。这些内容将是本章的重点。

    struts1会根据web.xml中的配置,对每个模块都创建一个ModuleConfig对象,而每个模块可能会有多个struts的配置文件。在调用initModuleConfig()方法进行初始化时,会创建一个Digester对象,解析struts配置文件的工作就完全交由Digester负责了。

    Digester也是Apache下的一个开源框架,主要功能就是将XML解析成java对象,它对SAX进行封装。Digester具体的使用就不赘述了,这里列出我觉得struts1中用到的几个比较重要的类:

    1、Rule:在解析某个元素时执行的动作。

    2、RuleSet:配置一系列完整的相关Rule定义。Struts1对struts的配置文件中所有的元素均由ConfigRuleSet来处理。

    3、Rules:Rule实例的集合,可以通过制定元素对应的规则。

    4、Digester:解析XML的主要类。

    创建Digester对象的方法为:

protected Digester initConfigDigester() throws ServletException {

        // :FIXME: Where can ServletException be thrown?

        // Do we have an existing instance?
        if (configDigester != null) {
            return (configDigester);
        }

        // Create a new Digester instance with standard capabilities
        configDigester = new Digester();
        configDigester.setNamespaceAware(true);
        configDigester.setValidating(this.isValidating());
        configDigester.setUseContextClassLoader(true);
        configDigester.addRuleSet(new ConfigRuleSet());
        for (int i = 0; i < registrations.length; i += 2) {
            URL url = this.getClass().getResource(registrations[i+1]);
            if (url != null) {
                configDigester.register(registrations[i], url.toString());
            }
        }

        this.addRuleSets();

        // Return the completely configured Digester instance
        return (configDigester);
    }

    configDigester.addRuleSet(new ConfigRuleSet())最主要的目的就是调用RuleSet.addRuleInstances(),将struts配置文件的元素和规则进行对应。在ConfigRuleSet()方法中,将struts配置文件的所有元素都进行了标识,这里摘出部分:

digester.addFactoryCreate
            ("struts-config/action-mappings/action",
             new ActionMappingFactory());
        digester.addSetProperties
            ("struts-config/action-mappings/action");
        digester.addSetNext
            ("struts-config/action-mappings/action",
             "addActionConfig",
             "org.apache.struts.config.ActionConfig");

        digester.addSetProperty
            ("struts-config/action-mappings/action/set-property",
             "property", "value");

    这里的代码片段实际上是在创建一些Rule,并将这rule放到Rules。如果从面向对象的角度来看,实际上是分成两部分。将当前要处理的元素看成是一个对象,第一部分就是创建一个对象(此处是生成对象的工厂),第二部分就是为这个对象设置属性。不知道这么说是不是好理解一些,当然,前提是要对Digester有一定的了解,我在看这些代码时,也花了一些时间去看Digester的文档和源码。

    在创建Digester对象时,将元素与规则进行了映射。Digester对象在解析XML文档时,当开始解析标签时,会对碰到的各个标签用“/”拼接起来。当处理完某个元素时,会将该字符串最后“/”及之后的字符剔除,形成新的字符串。根据拼接的字符串,找到对应的Rule对象进行处理。之前也提到,对于每个标签,会生成一个对象,该对象在标签进行解析时会放入到Digester的栈中,解析完该标签后,会从栈处弹出。

    拿解析action的代码片段为例,ActionMappingFactory工厂对象会被封装到FactoryCreateRule对象(Rule)中。在开始对action标签进行解析时,会将生成的ActionMapping对象放入到栈中,并对action标签元素属性进行解析,取栈顶元素进行赋值。同时对标签<set-property>进行解析时,也会对栈顶元素进行赋值。有一个特殊的地方需要说明,digester.addSetNext()是创建一个SetNextRule对象,在对标签<action>解析结束时,调用栈顶倒数第二个对象的addActionConfig方法,该方法的参数即为栈顶第一个元素。

    以上只是对部分代码进行了描述,实际上Digester在进行解析时,会将每个标签看成一个对象(实际上依据你生成的Rule可能会有例外,比如:<set-property>),然后利用栈对这些对象进行深度遍历,每次解析完一个标签,就将该标签对应的对象从栈中弹出。下面用一个图来描述:

    在解析之前,会将生成的ModuleConfig对象放入栈。

    在解析<action>标签时,将创建的ActionMapping对象放入栈中,在解析<action>标签的子节点<exception>时,会将ExceptionConfig对象放入栈中。一直到最后一个子节点。当解析完一个标签时,就将其从栈顶弹出。

    实际上,struts配置文件中的标签对应的类,基本上都是在org.apache.struts.config包中,并且以Config结尾。如<action>对应的ActionMappping,它的父类是ActionConfig。

    在解析配置文件时,有四个是用工厂类来实现的。分别是<action>、<action/forward>、<form-bean>、<global-forwards/forward>。这些标签有个className属性,其负责设置标签对应的设置类。如果没有设置,则取ModuleConfig对象的默认值,分别为:

/**
     * The default class name to be used when creating action form bean
     * instances.
     */
    protected String actionFormBeanClass = "org.apache.struts.action.ActionFormBean";
    
    /**
     * The default class name to be used when creating action mapping instances.
     */
    protected String actionMappingClass = "org.apache.struts.action.ActionMapping";
    
    /**
     * The default class name to be used when creating action forward instances.
     */
    protected String actionForwardClass = "org.apache.struts.action.ActionForward";

    实际上,ibatis在解析配置文件时,也用的这种思想。每个标签都有一个config对象与之对应,这应该就是传说中的面向对象思想吧。

作者:duwenchao1986 发表于2013-1-6 18:39:14 原文链接
阅读:19 评论:0 查看评论

    
最新技术文章:
▪error while loading shared libraries的解決方法    ▪版本控制的极佳实践    ▪安装多个jdk,多个tomcat版本的冲突问题
▪简单选择排序算法    ▪国外 Android资源大集合 和个人学习android收藏    ▪.NET MVC 给loading数据加 ajax 等待loading效果
▪http代理工作原理(3)    ▪关注细节-TWaver Android    ▪Spring怎样把Bean实例暴露出来?
▪java写入excel2007的操作    ▪http代理工作原理(1)    ▪浅谈三层架构
▪http代理工作原理(2)    ▪解析三层架构……如何分层?    ▪linux PS命令
▪secureMRT Linux命令汉字出现乱码    ▪把C++类成员方法直接作为线程回调函数    ▪weak-and算法原理演示(wand)
▪53个要点提高PHP编程效率    ▪linux僵尸进程    ▪java 序列化到mysql数据库中
▪利用ndk编译ffmpeg    ▪活用CSS巧妙解决超长文本内容显示问题    ▪通过DBMS_RANDOM得到随机
▪CodeSmith 使用教程(8): CodeTemplate对象    ▪android4.0 进程回收机制    ▪仿天猫首页-产品分类
▪从Samples中入门IOS开发(四)------ 基于socket的...    ▪工作趣事 之 重装服务器后的网站不能正常访...    ▪java序列化学习笔记
▪Office 2010下VBA Addressof的应用    ▪一起来学ASP.NET Ajax(二)之初识ASP.NET Ajax    ▪更改CentOS yum 源为163的源
▪ORACLE 常用表达式    ▪记录一下,AS3反射功能的实现方法    ▪u盘文件系统问题
▪java设计模式-观察者模式初探    ▪MANIFEST.MF格式总结    ▪Android 4.2 Wifi Display核心分析 (一)
▪Perl 正则表达式 记忆方法    ▪.NET MVC 给loading数据加 ajax 等待laoding效果    ▪java 类之访问权限
▪extjs在myeclipse提示    ▪xml不提示问题    ▪Android应用程序运行的性能设计
▪sharepoint 2010 自定义列表启用版本记录控制 如...    ▪解决UIScrollView截获touch事件的一个极其简单有...    ▪Chain of Responsibility -- 责任链模式
▪运行skyeye缺少libbfd-2.18.50.0.2.20071001.so问题    ▪sharepoint 2010 使用sharepoint脚本STSNavigate方法实...    ▪让javascript显原型!
▪kohana基本安装配置    ▪MVVM开发模式实例解析    ▪sharepoint 2010 设置pdf文件在浏览器中访问
▪spring+hibernate+事务    ▪MyEclipse中文乱码,编码格式设置,文件编码格...    ▪struts+spring+hibernate用jquery实现数据分页异步加...
▪windows平台c++开发"麻烦"总结    ▪Android Wifi几点    ▪Myeclipse中JDBC连接池的配置
▪优化后的冒泡排序算法    ▪elasticsearch RESTful搜索引擎-(java jest 使用[入门])...    ▪MyEclipse下安装SVN插件SubEclipse的方法
▪100个windows平台C++开发错误之七编程    ▪串口转以太网模块WIZ140SR/WIZ145SR 数据手册(版...    ▪初识XML(三)Schema
▪Deep Copy VS Shallow Copy    ▪iphone游戏开发之cocos2d (七) 自定义精灵类,实...    ▪100个windows平台C++开发错误之八编程
▪C++程序的内存布局    ▪将不确定变为确定系列~Linq的批量操作靠的住...    ▪DIV始终保持在浏览器中央,兼容各浏览器版本
互联网 iis7站长之家
▪android Content Provider详解九    ▪简单的图片无缝滚动效果    ▪required artifact is missing.
▪c++编程风格----读书笔记(1)    ▪codeforces round 160    ▪【Visual C++】游戏开发笔记四十 浅墨DirectX教程...
▪【D3D11游戏编程】学习笔记十八:模板缓冲区...    ▪codeforces 70D 动态凸包    ▪c++编程风格----读书笔记(2)
▪Android窗口管理服务WindowManagerService计算Activity...    ▪keytool 错误: java.io.FileNotFoundException: MyAndroidKey....    ▪《HTTP权威指南》读书笔记---缓存
▪markdown    ▪[设计模式]总结    ▪网站用户行为分析在用户市场领域的应用
 


站内导航:


特别声明:169IT网站部分信息来自互联网,如果侵犯您的权利,请及时告知,本站将立即删除!

©2012-2021,,E-mail:www_#163.com(请将#改为@)

浙ICP备11055608号-3