Пікірлер
@nikitasuyazov2060
@nikitasuyazov2060 29 күн бұрын
Не бомбит у меня, не бомбит! В принципе логика с дамагом по противникам будет такая же. Единственное, что может вызвать вопрос - это их движение по свободным клеткам. Пока что в голову не приходит, как это делать. Не через трейсы точно и не через AI_MoveTo, наверное. Как-то проще нужно. А ещё танчики не доделаны. Там искусственный интеллект сложнее был бы. Танки стреляют в ответ и прячутся.
@Narazves_gamedev
@Narazves_gamedev 28 күн бұрын
Если логика передвижения как в оригинале- враги бездумно тыкаются в стены. И при каждом прикосновении просто меняют направление движения случайным образом. Такое можно и на ивент тик повесить, сложной логики там нет. Хотя есть враги, которые целенаправленно на игрока бегут. Там просто направление нужное задавать. В танчиках делал передвижение через AI_MoveTo, но сам урок не записал, так как времени не было.
@nikitasuyazov2060
@nikitasuyazov2060 29 күн бұрын
Офигеть! Это гениально! Очень крутые уроки.
@nikitasuyazov2060
@nikitasuyazov2060 29 күн бұрын
Да, это идеальная длина видео, когда не длиннее 30 минут.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
А мне музыка не мешала.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Ваще круто! На Анриле действительно можно сделать любую игру. Хоть классическую ЖРПГ, хоть платформер Марио 1, хоть Змейку. И представляю себе лицо того, кто при запуске игры видит надпись Unreal Engine 5😄
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Timestamps (Powered by Merlin AI) 00:03 - Introduction to Bomberman game mechanics and history. 00:55 - Overview of creating a BomberMan project in Unreal Engine. 02:02 - Setting up game levels and adding sprites in Unreal Engine. 03:15 - Guide on adding and extracting sprites for 2D project in Unreal Engine. 04:36 - Organizing sprites into project folders for BomberMan. 06:59 - Creating player sprites for animations in Unreal Engine. 09:58 - Creating death animation in Unreal Engine with sprite selection. 11:34 - Completed character animation setup in Unreal Engine tutorial.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Ни одного урока не видел до этого дня, где бы показывали, как в Анриале делать спрайтовые игры. Думал, что это не возможно. А оказывается, что даже это продумано.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Работает. Правда залогинился не с первой попытки, а без этого выдаёт ошибку, отказывается работать.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Ждём продолжение. Но там ещё очень много делать. Разрушаемость кубов, противников, простейшую логику для них, стрельбу и попадания.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Можно было следам в фотошопе добавить альфа-канал и тогда сгенерировать normal map. И выставить в материалах Blend Mode - Masked, а альфа-канал подключить в Opacity mask. Этот режим прозрачности дешевле. Надо будет понизить светлоту трейсов через multiply на base color, наверное. И cast shadows для мэша следов я отключил в блюпринте.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Крутые уроки! Всё нравится! Делай ещё, не останавливайся.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Смысл делать что-то большее в Ниагаре только если захочется весь проект дорабатывать. А для урока нормально. Тогда можно было бы сделать кораблик с соплами, которые отклоняются против движения и из них вылетает струя пламени. Но это уже навороты.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Очень круто! Отличные уроки, почти догнал выпуск новых.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
В 5.5 у меня уже была прописана "EnhancedInput" в Invaders.Build.cs
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Можно спокойно проходить на UE5.5. Всё тоже самое.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Очень круто, не ожидал, что есть такой замечательный канал и ещё более замечательный его автор.
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Огромная благодарность. Я несколько раз пытался войти в C++ на UE и каждый раз ничего не получалось на этапе подружить VS и UE. Например, про кнопку внизу UE5 "Recompiles and Reload" я в англоязычных курсах не видел. Запускал, как они, у меня открывалось новое окно редактора, простейший код никак не отображался в Анриле. Этот канал - была последняя ниточка, хотел забить и оставаться на блюпринтах. Интересный курс. Была одна загвоздка под конец, эта строка "ScoreText->SetText(FText::AsNumber(Score));" выдавала Null. И в блюпринте было пустое окно Details. А так как я новичок в коде, базовые учебники мне тут абсолютно ничего не говорят, половина слов из внутренней библиотеки Анрила, то стал проверять код, сверил каждую букву. Оказалось, что в BP_Pawn в настройках Class Defaults слетел ScoreText = Text Render Component. Возможно потому, что я удалил в настройках Score Text в графе Text текст Text. А надо было заменить на Score, не удалять совсем. Возможно можно было в коде законспектировать ScoreText, скомпилить, а потом снова добавить, тогда настройки сбросились бы. Или закодить дефолтное значение.
@himaltrex
@himaltrex Ай бұрын
Спасибо за очередной урок! Блин, не представляю, как такую. игру писали 40 лет назад, если даже сейчас все равно так сложно
@himaltrex
@himaltrex Ай бұрын
Простите, музыка громкая и очень сбивает. Урок хороший
@AbraKadabra000
@AbraKadabra000 Ай бұрын
купи норм клаву без чавкающих звуков a4tech fstyler топ. или в фикспрайсе за 200ркблей беспроводные есть с подсветкой букв
@user_drew25
@user_drew25 Ай бұрын
Уважаемый автор, в следующих видео убери пожалуйста фоновый звук. Отвлекает довольно сильно. Спасибо за труд.
@Игорь-б6г7ь
@Игорь-б6г7ь Ай бұрын
Как название обоев раб стола ? ))
@Narazves_gamedev
@Narazves_gamedev Ай бұрын
Это приложение Win dynamic desktop. Время суток на картинке динамически меняется от времени суток на часах. Сама тема называется Big sur
@quadrogod
@quadrogod Ай бұрын
А вот здесь уже поинтересней
@quadrogod
@quadrogod Ай бұрын
Один я не понимаю, зачем делать бомбермена в спрайтах на ue5? Даже если просто в целях обучения основ движка?
@Бумбарашка
@Бумбарашка Ай бұрын
Да!
@Narazves_gamedev
@Narazves_gamedev Ай бұрын
Играл только в эту часть. Ну и на нее есть полный пак спрайтов в открытом доступе)
@quadrogod
@quadrogod Ай бұрын
@@Narazves_gamedev да, это я понимаю. Я к тому, что ядро анрила слишком мощное для подобных игр. Или просто я давно не в теме по движку. Но он будет необоснованно много ресурсов жрать в не зависимости, спрайтовая ли это 2d адвенчура или серьезный 3d рендеринг
@Narazves_gamedev
@Narazves_gamedev Ай бұрын
Вообще, я бы мог сделать ее и на чистом С++, но канал посвящен изучению Анрила. Да и ребятам будет интересно посмотреть, как работать со спрайтами, чтобы потом применять это в более сложных проектах.
@Бумбарашка
@Бумбарашка Ай бұрын
@@quadrogod у меня не скромный вопрос! А за какие ресурсы вы переживаете ? Движок анрил разносторонний и каждый использует его по своему! Начинать с чего то надо! В любой среде есть свой hello world! Ни все продвинутые кодеры да и не всем 3д нужно так же как и вам 2д
@НиколайЧернов-ь9у
@НиколайЧернов-ь9у 7 ай бұрын
продолжение! требуем)
@Narazves_gamedev
@Narazves_gamedev 6 ай бұрын
Ближайшее время пока под вопросом, так как очень много работы
@Kota-Kombo-876
@Kota-Kombo-876 10 ай бұрын
А есть такое только что бы блюпринты рисовал?
@Narazves_gamedev
@Narazves_gamedev 6 ай бұрын
Такого не знаю. Но суть не меняется. Просто переводишь С++ код в БП, он будет работать точно так же. Название методов (функций) в БП и С++ часто похожи.
@moondi4368
@moondi4368 10 ай бұрын
Ну чата гпт хватает. Я считаю плохая идея взять и сгенерировать весь класс целиком, вам придется весь код перечитатт и исправлять возможные косяки, или вообще генерится не то что надо из-за неудачного промпта, лучше генерируйте функции с определенными входами и выходами, просто опишите условия функции и то что она должна возвращать, это точно сэкономит время
@moondi4368
@moondi4368 10 ай бұрын
Да, это требует опыт в программировании
@moondi4368
@moondi4368 10 ай бұрын
Копируешь хаудихо
@alexandershevchenko8683
@alexandershevchenko8683 10 ай бұрын
Все дело в том, что компилятор просто оптимизировал твою функцию, сделал return 1000000. Попробуй каждую итерацию выводить значение, тогда уже более реальное значение получится
@doctor_livsi_pod_phonk
@doctor_livsi_pod_phonk 10 ай бұрын
А вот и нет, тогда бы скорость не различалась... он реально прошелся в цикле столько раз и вернул значение.
@robingad7666
@robingad7666 10 ай бұрын
Ну конечно блюпринты не может выполнить 1кк лопов так как памяти не хватит. Ты сам понимаешь что сморозил. Заходим в настройки и параметр Maximum Loop Iteration Count ставим >1кк. Ой почему то памяти стало хватать. Внимание правильный ответ. Разработчики поставили защиту, чтоб код не уходил в бесконечный цикл, от таких программисто)) А в реальных задачах редко когда приходится делать цикл больше 200 раз. И все ваши искуственные тесты на миллиард тестов не имеет не какого смысла. Ну и не забивыем что в билде все немного иначе. А на разработке можно и подождать 0.01 сек. Честно, не заметно. А экстремально много лупов задач просто нет. Ну а если появится, не кто такое на БП писать не будет, так как там какая то генерация мира. Это не задача для БП. Давай не будем забивать гвозди ноутбуком
@fierybird1371
@fierybird1371 10 ай бұрын
6 лет прошло, а гении думающие что блюпринт работает медленнее делая тесты в среде разработки никуда не делись kzbin.info/www/bejne/jGiTaKVql9B9hbs, при этом оправдываются потом в комментах что хотели показать что это только в среде разработки они медленнее, при этом ни в названии видео ни в описании ничего подобного не указано
@flexight9334
@flexight9334 7 ай бұрын
хорошо , а на это что скажите kzbin.info/www/bejne/r5yVe2SpmbZga6ssi=808c4jpFpPO7uy8Q
@moondi4368
@moondi4368 10 ай бұрын
Почему i++, а не ++i? Зачем делать лишние операции?
@Rowolfs
@Rowolfs 10 ай бұрын
А в чем разница как помню называется инкремент и декремент а в чем их разница не помню?
@moondi4368
@moondi4368 10 ай бұрын
@@Rowolfs ++i - просто прибавляет переменной единицу и возвращает её. i++ - кеширует изначальное значение, прибавляет к переменной единицу но возвращет изначальное значение.
@alexandershevchenko8683
@alexandershevchenko8683 10 ай бұрын
Для обычных стандартных типов разницы нет, компилятор все равно соптимизирует в одни и те же инструкции
@androwinwatch
@androwinwatch 11 ай бұрын
Когда ж вы поймёте, зумеры, что суть в 90% не в скорости кода... Даже ААА игру можно на блюпринтах написать с той же скоростью работы. +- Дело в механиках и гибкости кода. Ноды это и есть код из библиотек эпиков. Просто появляются моменты, когда нужной НОДЫ просто нет. Либо когда-нужно очень красиво все организовать с удобством и т.п.
@peace__duke
@peace__duke 11 ай бұрын
Полная неправда, сорость в 90% случаев не важна в веб или где то в десктоп приложениях на UI, а для игр, тем более на UE5 критически важна скорость, если игра будет работать в 15 ФПС на средних видеокартах то хоть какие механики будут - она провалится. Ну и чертёжики эти сделаны чтобы гей дизайнеры могли набросать что кого или архитекторы, тек то кодить не умеют и не должны по ходу должностных обязанностей. Если на UE5 делать не пререндер рекламного ролика или анимационный фильм а игру то точно надо оптимизировать по скорости ибо UE всё дальше уходит в ту нишу где скорость не главное, а потому те кто всё ещё делает на этом движке игры обязан заботится о том чтобы игра работала как можно быстрее. Ну а механики всякие и прочее это забота не того кто код пишет а дизайнера и прочего обслуживающего персонала.
@androwinwatch
@androwinwatch 11 ай бұрын
@@peace__duke как скажешь, куда нам людям которые уже более 7 лет в Ue работают... Мне просто интересно каким образом у тебя скорость теряется... Сразу видно, что в реальных задачах не участвовал.
@peace__duke
@peace__duke 11 ай бұрын
@@androwinwatch а причём тут опыт?! Я про то что движок постепенно требования к железу повышает с каждой крупной версией, для этого не надо обладать опытом чтобы видеть это. Переход на личности и апелляция к авторитету это классические способы манипуляции. Ни то не другое не имеет к истине никакого отношения. Моя основная идея была что UE это движок который заточен на графоний в ущерб скорости работы, да можно принебречь графонием. но тогда какой смысл делать такое на UE?!
@androwinwatch
@androwinwatch 11 ай бұрын
@@peace__duke ​полностью согласен. Если что не хотел как-либо обидеть, но твой последний комментарий лишён изъянов. Но вообще мы про скорость работы говорили. В примере автора ролика в билде разницы никакой нет. Я еще когда начинал этим заниматься часто сравнивал скорость работы и т.п. Разница была даже не на уровне погрешности, её совсем не было. Но здесь речь не идёт о многомиллионных массивах и т.п. В корпоративном сегменте, вообще без разницы на чем пишешь, лишь бы работало стабильно. Под капот никто не лезет.
@dead7643
@dead7643 10 ай бұрын
@@peace__duke а как связаны графоний и написание игровой логики? У вас графика работает на процессоре или игровая логика на видюхе? При чём тут код и графика?
@Юрий-л3у2и
@Юрий-л3у2и 11 ай бұрын
Отличный туториал
@firegrim
@firegrim 11 ай бұрын
Ух ты как быстро. Вот только для работы плюсовой функции требуется собрать код, а бп работают в рантайме в pie. Теперь соберите проект в финальный билд(shipping) и покажите ещё раз. Не думаю что там будет разница в 25к раз.
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
Вы правы, потому что в финальном билде будет работать машинный код, а не плюсы или бп. И тут быстродействие больше будет зависеть от оптимизации кода. Но это видос скорее про быстродействие на этапе разработки, где скорость кода различается и тяжелые функции лучше убирать в плюсы, чтобы проект быстрее работал и проще было запускать отладку.
@Юрий-л3у2и
@Юрий-л3у2и 11 ай бұрын
Объясните про новую систему управления
@atomfn5336
@atomfn5336 11 ай бұрын
я сам старую через инпуты использую и нежалуюсь
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
Не планирую, так как на ютубе полно подобных видосов. В предыдущих уроках, про танк и вертолет, я поверхностно объяснял, как настраивать управление по новой системе. Для большинства случаев этого будет достаточно.
@Юрий-л3у2и
@Юрий-л3у2и 11 ай бұрын
Отличная подача информации я новичок для меня это важно
@BlackEliteGroup
@BlackEliteGroup 11 ай бұрын
По-моему проще код написать)
@sayz1x175
@sayz1x175 11 ай бұрын
а потом с пеной у рта доказывают что для нормальной игры даже плюсы знать не надо, хватит и блюпринтов =)
@whoknows4728
@whoknows4728 11 ай бұрын
Блю принты как правило для прототипирования, для какого-то гейм дизайнера механику накаидать, а люди на серьезе челые проеты лепят на этом
@maryjane-jq1cw
@maryjane-jq1cw 11 ай бұрын
вот и диванный эксперт со своим важным мнением @@whoknows4728 😂
@atomfn5336
@atomfn5336 11 ай бұрын
atomic heart практически на половину из блупринтов сделан...@@whoknows4728
@FeeNik546
@FeeNik546 11 ай бұрын
@@whoknows4728 пабг изначально чисто на принтах был, фортнайт на 70-80 % на принтах, много есть играбельных игр чисто на принтах
@evl1536
@evl1536 7 ай бұрын
@@whoknows4728 к примеру такие проекты как PUBG: Battlegrounds
@Сма_йлик
@Сма_йлик 11 ай бұрын
😁🤔🤔🙃😎👍👍
@ЗамаскировщикНежданИваныч
@ЗамаскировщикНежданИваныч 11 ай бұрын
Вопрос: почему во всех твоих видео, в качестве шаблона, идут игры из 80-х, 90-х годов прошлого века?
@nikitasuyazov2060
@nikitasuyazov2060 Ай бұрын
Странно, согласен. Где Понг?
@console.g
@console.g 11 ай бұрын
Классные уроки, жаль что не обучающий урок по блюпринты
@Alejandro-iq4ue
@Alejandro-iq4ue 11 ай бұрын
Интересная тема! спасибо за видео, жду продолжения.
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersWall.cpp #include "InvadersWall.h" #include "InvadersProjectile.h" #include "InvadersProjectileEnemy.h" void AInvadersWall::BeginPlay() { Super::BeginPlay(); ConstructWall(); } void AInvadersWall::ConstructWall() { const int32 Count = 20; const double Spacing = 10.0; for (int32 j = 0; j < Count; j++) { for (int32 i = 0; i < Count; i++) { UStaticMeshComponent* WallComponent = NewObject<UStaticMeshComponent>(this, UStaticMeshComponent::StaticClass()); if (WallComponent) { UStaticMesh* WallMesh = LoadObject<UStaticMesh>(nullptr, TEXT("StaticMesh'/Game/Resources/SM_Cube.SM_Cube'")); if (WallMesh) { WallComponent->SetStaticMesh(WallMesh); WallComponent->SetupAttachment(RootComponent); WallComponent->SetRelativeTransform(FTransform(FRotator::ZeroRotator, FVector(0, i * Spacing, j * Spacing), FVector(0.1, 0.1, 0.1))); WallComponent->RegisterComponent(); WallComponent->OnComponentBeginOverlap.AddDynamic(this, &ThisClass::WallOverlap); } } } } } void AInvadersWall::WallOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) { if (Cast<AInvadersProjectile>(OtherActor) || (Cast<AInvadersProjectileEnemy>(OtherActor))) { if (OverlappedComponent) { OverlappedComponent->DestroyComponent(); } } }
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersSwarm.cpp void AInvadersSwarm::SpawnEnemies() const { const FVector SpawnLocation = GetActorLocation(); double Spacing = 120.0; const int32 CountY = 20; const int32 CountZ = 5; for (int32 j = 0; j < CountZ; j++) { for (int32 i = 0; i < CountY; i++) { if (UWorld* World = GetWorld()) { World->SpawnActor<AActor>(ActorToSpawn, (SpawnLocation + FVector(0.0, i * Spacing, j * Spacing)), FRotator::ZeroRotator); } } } } void AInvadersSwarm::CheckEnemies() { TArray<AActor*> OutActors; UGameplayStatics::GetAllActorsOfClass(GetWorld(), AInvadersEnemy::StaticClass(), OutActors); TArray<AInvadersEnemy*> EnemyArray; for (AActor* Actor : OutActors) { if (AInvadersEnemy* Enemy = Cast<AInvadersEnemy>(Actor)) { EnemyArray.Add(Enemy); } } EnemyCount = EnemyArray.Num(); UE_LOG(LogTemp, Warning, TEXT("actors: %d"), EnemyCount); if (EnemyCount <= 0) { UGameplayStatics::OpenLevel(this, FName(*GetWorld()->GetName()), false); } }
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersEnemy.cpp void AInvadersEnemy::BeginFire() { const float FireDelay = FMath::RandRange(2.0, 5.0); if (!ReloadTimerHandle.IsValid()) { GetWorldTimerManager().SetTimer(ReloadTimerHandle, this, &AInvadersEnemy::SpawnProjectile, FireDelay, false); } } void AInvadersEnemy::SpawnProjectile() { ProjectileCheck(); if (ProjectilesCount < ProjectilesMax) { const FVector SpawnLoc = GetActorLocation() + FVector(0.0, 0.0, -100.0); if (UWorld* World = GetWorld()) { World->SpawnActor<AActor>(ActorToSpawn, SpawnLoc, FRotator::ZeroRotator); GetWorldTimerManager().ClearTimer(ReloadTimerHandle); BeginFire(); } } } void AInvadersEnemy::ProjectileCheck() { TArray<AActor*> OutActors; UGameplayStatics::GetAllActorsOfClass(GetWorld(), AInvadersProjectileEnemy::StaticClass(), OutActors); TArray<AInvadersProjectileEnemy*> ProjectilesArray; for (AActor* Actor : OutActors) { if (AInvadersProjectileEnemy* Projectile = Cast <AInvadersProjectileEnemy>(Actor)) { ProjectilesArray.Add(Projectile); } } ProjectilesCount = ProjectilesArray.Num(); UE_LOG(LogTemp, Warning, TEXT("actors: %d"), ProjectilesCount); }
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersEnemy.cpp #include "Components/BrushComponent.h" void AInvadersEnemy::BeginPlay() { Super::BeginPlay(); if (FTimerHandle MoveTimer; !MoveTimer.IsValid()) { GetWorldTimerManager().SetTimer(MoveTimer, this, &ThisClass::Move, 0.05, true); } } void AInvadersEnemy::EnemyOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) { if (Cast<AInvadersProjectile>(OtherActor)) { SpawnExplosionFX(); SpawnSound(); Destroy(); } else if (Cast<UBrushComponent>(OtherComp)) { ChangeDirection(); } } void AInvadersEnemy::Move() { const FVector NewLocation = GetActorLocation() + FVector(0.0, MoveDirection, 0.0); SetActorLocation(NewLocation); } void AInvadersEnemy::ChangeDirection() { TArray <AActor*> OutActors; UGameplayStatics::GetAllActorsOfClass(GetWorld(), StaticClass(), OutActors); for (AActor* EnemyActor : OutActors) { if (AInvadersEnemy* Enemy = Cast<AInvadersEnemy>(EnemyActor)) { Enemy->MoveDirection *= -1.0; } } }
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
// InvadersEnemy.h UCLASS() class INVADERS_API AInvadersEnemy : public AActor { GENERATED_BODY() protected: double MoveDirection = -1.0; void Move(); void ChangeDirection(); };
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersEnemy.cpp #include "NiagaraFunctionLibrary.h" #include "Kismet/GameplayStatics.h" AInvadersEnemy::AInvadersEnemy() { NiagaraSystem = LoadObject<UNiagaraSystem>(nullptr, TEXT("/Game/Resources/NS_Burst")); BlastSound = LoadObject<USoundBase>(nullptr, TEXT("/Game/Resources/SW_Blast")); } void AInvadersEnemy::EnemyOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) { if (Cast<AInvadersProjectile>(OtherActor)) { SpawnExplosionFX(); SpawnSound(); Destroy(); } } void AInvadersEnemy::SpawnExplosionFX() const { if (NiagaraSystem) { UNiagaraFunctionLibrary::SpawnSystemAtLocation(GetWorld(), NiagaraSystem, GetActorLocation()); } } void AInvadersEnemy::SpawnSound() const { if (BlastSound) { UGameplayStatics::PlaySound2D(this, BlastSound); } }
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersEnemy.h class UNiagaraSystem; UCLASS() class INVADERS_API AInvadersEnemy : public AActor { GENERATED_BODY() protected: UPROPERTY(EditDefaultsOnly) TObjectPtr <UNiagaraSystem> NiagaraSystem; UPROPERTY(EditDefaultsOnly) TObjectPtr <USoundBase> BlastSound; UFUNCTION() void SpawnExplosionFX() const; UFUNCTION() void SpawnSound() const; };
@Narazves_gamedev
@Narazves_gamedev 11 ай бұрын
//InvadersEnemy.cpp #include "InvadersEnemy.h" #include "Components/BoxComponent.h" #include "InvadersProjectile.h" AInvadersEnemy::AInvadersEnemy() { EnemyCollision = CreateDefaultSubobject<UBoxComponent>(TEXT("EnemyCollision")); EnemyMesh = CreateDefaultSubobject<UStaticMeshComponent>(TEXT("EnemyMesh")); check(EnemyCollision); check(EnemyMesh); SetRootComponent(EnemyCollision); EnemyMesh->SetupAttachment(EnemyCollision); EnemyCollision->SetBoxExtent(FVector(51.0, 51.0, 51.0)); EnemyCollision->OnComponentBeginOverlap.AddDynamic(this, &ThisClass::EnemyOverlap); } void AInvadersEnemy::EnemyOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) { if (Cast<AInvadersProjectile>(OtherActor)) { Destroy(); } }