Подтвердить что ты не робот

Должен ли я подкласс CCSprite, CCNode или NSObject?

Я вижу, что некоторые тексты всегда кажутся подклассами CCSprite. Я где-то читал, что это нехорошо делать, и что лучше начать с чего-то основного. Я хотел узнать, что делают разработчики pro игр с точки зрения структуры игры. Это подкласс CCSprite или добавить CCSprite в класс NSObject ETC.

Надеюсь, мой вопрос имеет смысл.

4b9b3361

Ответ 1

Ваш вопрос определенно имеет смысл.

Это фундаментальный вопрос архитектуры. Если ваша игра в основном основана на "анимации", я бы пошел на подкласс CCSprite. Если ваша игра в основном основана на некоторой логике, возможно, RPG или что-то еще, тогда представление экрана на самом деле является лишь одним из возможных видов состояния игры. Следовательно, это должно быть, на мой взгляд, частью объекта в дереве объектов, представляющих ваше состояние игры.

Другими словами: если ваше состояние игры по существу является сценой, то подкласс CCSprite, потому что Cocos2D, вероятно, лучше, чем вы, при управлении сценами. Если ваше состояние игры "что-то еще", вам, вероятно, стоит подумать о создании собственного представления этого состояния и сделать свою часть спрайта в игровом объекте. Это также позволит вам "переключать" графические движки, если вы решите изменить рендеринг. Например, вы можете сделать RPG с 2D-представлением в Cocos2D. Через некоторое время вы показываете свою демоверсию Ubisoft, и они в нее влюбляются и дают вам 20 миллионов долларов, чтобы закончить ее, но они запросят 3D-рендеринг. Если вы пошли на подкласс CCSprite, вам придется переделать всю игру. Если вы пошли на интеграцию CCSprite/CCNode в класс, основанный на NSObject, вам хорошо идти.

Конечно, этот пример немного преувеличен с целью... example: D

Ответ 2

Я предпочитаю подкласс CCNode почти исключительно.

Я бы только подклассы CCSprite, CCLabel и другие внутренние классы Cocos2D, если мне нужен спрайт, ярлык или что-то другое, чтобы вести себя несколько иначе, чем базовая реализация. И подклассификация была бы последней мерой, если категория недостаточна. Большинство разработчиков Cocos2D, по-видимому, не понимают, что CCSprite сам по себе является полным классом, который не нужно расширять (подклассы) для представления игровых объектов. Но слишком легко попасть в эту привычку, потому что, создав подкласс CCSprite, вы получаете визуальные эффекты, и у вас есть контейнер для вашего логического кода игры. Это просто не очень OOP для этого.

Если вы подумаете об этом, как только вы добавите какой-то код логической игры в CCSprite, это не просто CCSprite, или не так ли? Один хороший способ подумать об этом заключается в следующем: если вы подклассифицируете класс (назовите его MyClass) и добавите в него свой собственный код, будет ли это иметь смысл для подкласса MyClass для других целей? Если нет, то вы не должны подклассы.

Чтобы пойти с широко используемой аналогией ООП класса "Автомобиль": вы подклассифицируете "Автомобиль", чтобы создавать более специализированные, но все же общие классы, такие как "SportsCar", "Грузовик", "Ван", но вы не подклассы "Автомобиль", чтобы создать "Porsche 911 V-Turbo Model 6" . Почему нет? Поскольку класс "SportsCar" имеет все аспекты создания экземпляра SportsCar, который затем становится "Porsche 911 V-Turbo Model 6".

Другое дело, что вам стоит подумать, что "Porsche 911 V-Turbo Model 6" будет высокоспециализированным классом, который не имеет какой-либо другой цели, кроме определения того, что такое конкретный автомобиль. Не было бы никакого смысла подклассифицировать класс Porsche 911, потому что он по существу потерял свои общие атрибуты и заменил их очень конкретными деталями реализации. Если у вас есть класс, который вы не можете обосновать подклассом, вы создали тупик в своей иерархии классов и, по сути, написали функциональный код, а не объектно-ориентированный код. Тем не менее, это нормально для простых игр, но оно вернется, чтобы преследовать вас, если вы осмелитесь сделать больше.

Подводя итог: вы должны подклассифицировать CCSprite только в том случае, если вы намерены сделать более специализированный, но все же общедоступный тип CCSprite. Одним из примеров этого может быть CCLabelTTF, который подклассы из CCSprite. Это добавляет возможность создавать текстуру CCSprite во время выполнения из шрифта и строки. Другим примером для подкласса CCSprite было бы, если бы вам нужен CCSprite, который обновил бы свою текстуру с Карт Google, чтобы он напоминал плиту карт, основанную на координатах долготы и широты и уровне масштабирования. Это по существу было бы немым объектом, единственной целью которого является отображение прямоугольного изображения в определенном положении. Это CCSprite. Тупой объект, который отображает текстуру в определенном месте.

Вопрос действительно в этом: есть ( "is a" ) ваш игровой объект - спрайт, или он имеет ( "имеет" ) спрайт для его визуальное представление? Ответ всегда должен быть последним. Общим правилом для подклассификации является отношение "есть" , в случае "имеет" время для композитного шаблона . Если вы сомневаетесь, и оба кажутся применимыми, всегда ошибайтесь на стороне "есть" , потому что это всегда работает.

Почему я должен сказать, что игровой объект не спрайт, но имеет спрайт? Ясно, что оба применимы. Ответ: игровой объект "является" спрайтом только до тех пор, пока он может быть представлен одним спрайтом и ничем иным. Но на самом деле ваш игровой объект может быть представлен несколькими спрайтами или спрайтом, меткой и некоторыми эффектами частиц. Это означает, что отношения "есть" гораздо более вероятно разорваны по мере того, как приложение разрабатывается, а это означает, что нужно выполнить дополнительную рефакторинг.

Используя CCNode в качестве базового класса для ваших игровых объектов и добавляя визуальные узлы на эту базу node, вы также можете использовать базовый node в качестве объекта контроллера для представления (-ов) игрового объекта. Это означает, что он лучше соответствует шаблону Model-View-Controller (MVC).

Наконец, я бы не подклассифицировал NSObject для чего-либо, что должно быть в иерархии представления cocos2d, или сохраняет ссылку на то, что находится в иерархии представления cocos2d. По той простой причине, что подклассы NSObject не предлагают каких-либо стандартных функций CCNode (планирование, добавление дочерних узлов, относительное позиционирование дочерних узлов) и, самое главное, трудно использовать подклассы NSObject вместе с Cocos2D, а не автоматическое управление памятью node.

Не вдаваясь в подробности, простое правило заключается в том, что если подкласс имеет переменную экземпляра, которая является Cocos2D node, она сама должна быть Cocos2D node, так что управление памятью и все остальные аспекты просты и надежны. Что касается Cocos2D, класс CCNode является корневым классом для иерархии представлений, поэтому он похож на класс UIResponder с возможностью возьмите на себя роль классов UIView и/или UIViewController (оба подкласса от UIResponder кстати) на случайных событиях.

Короче: подкласс CCNode, затем используйте шаблон состава/агрегации для визуальных аспектов класса.

Ответ 3

Если у вас есть этот вопрос на этом предприятии вашего путешествия Cocos2D, подкласс CCSprite и покончить с этим. Вы не будете создавать ничего прямо сейчас, что потребует передовых методов тонко настроенных классов. Я говорю это не как оскорбление ваших способностей, а как человек, у которого когда-то был этот вопрос.

Когда вы начинаете задаваться вопросом, нужно ли переписывать вызовы метода OpenGL для CCNode, тогда вы будете в такой ситуации, когда вам нужно будет тщательно изучить свои параметры подкласса. Подкласс CCSprite предоставляет вам все методы и свойства всего ниже, что дает вам возможность открывать, учиться и двигаться вперед.

Короче: подкласс CCSprite.

Ответ 4

По-моему, объект в игре не спрайт. Sprite - это представление для объекта, это означает, что вам нужно создать подкласс класса GameObject NSObject (возможно, CCNode).

Подводя итог: подкласс NSObject или CCSprite - это структура класса, вам нужно использовать свой стиль кода.