• Прежде, чем задать вопрос, пожалуйста, убедитесь, что такой вопрос не задавался раньше. Старайтесь описать суть вопроса как можно подробней. • Прежде, чем опубликовать ответ на вопрос, пожалуйста, убедитесь, что обладаете необходимыми для этого знаниями. Старайтесь cформулировать суть ответа как можно лаконичней. • При желании ответить в приватном порядке, пожалуйста, воспользуйтесь ЛС. • При желании поблагодарить ответившего, пожалуйста, воспользуйтесь кнопкой "+" полезного сообщения.
Сообщения, не относящиеся к вопросам по скриптам Papyrus, ответам на них или уточнениям, являются оффтопом и могут быть удалены.
Красное солнце Есть вопросы по скриптам Papyrus? Пиши не в ЛС, а в эту тему.
LordVadim, Amiball1992, У призраков 2 параметра: 1. Стоит галка is Ghost. Она отвечает за неуязвимость, стрелы пролетают насквозь. 2. Стоит скрипт, дающий GhostAbility. Это способность, дающая прозрачность. Но, увы, всё это вместе не позволяет сквозь него ходить. Я вообще не уверен, что в игре такое возможно, ведь тогда модель должна проваливаться под пол.
Изменение репутации для пользователя LordVadim
LordVadimOffline
Сообщение №632
написано: 14 декабря 2013, 04:26
| Отредактировано: LordVadim - 14 декабря 2013, 04:29
Но, увы, всё это вместе не позволяет сквозь него ходить. Я вообще не уверен, что в игре такое возможно, ведь тогда модель должна проваливаться под пол.
Но ведь если для игрока применить консольную команду TCL он, фактически, становится призраком. А игрок - это тот же НПС, только управляемый. Значит, технически, такая возможность в игре есть. Или я что то путаю? Ghost, GhostAbility, SetAlpha() - не решают проблему. Только визуальный эффект.
LordVadim, есть такой крик "Бесплотность", в нём сказано, что ни вы, ни вам во время его действия нельзя нанести урон. Попробуй поправить его скрипт в нужную тебе сторону.
есть такой крик "Бесплотность", в нём сказано, что ни вы, ни вам во время его действия нельзя нанести урон. Попробуй поправить его скрипт в нужную тебе сторону.
Этот крик делает ГГ "Ghost", т.е. неуязвимым для оружия и магии, но коллизия всё равно остаётся - ГГ не может пройти сквозь стену или другого НПС. Коллизию НПС можно отключить: убив НПС, глобальной функцией отключающей всю коллизию в игре Debug.ToggleCollisions(), и привязкой НПС к объекту функцией akActor.SetVehicle(akObject).
У всех этих способов есть свои "недостатки". Убивать - не вариант. Глобально отключать ВСЮ коллизию - это имитация TCL, а результат такого вы сами представляете. Привязывать НПС к маркеру/объекту - это только на ГГ хорошо работает, он может ходить сквозь стены и т.д., т.е. коллизия снимается только с ГГ, а все остальные объекты/НПС живут полноценной жизнью. Но если привязать НПС, то он не сможет самостоятельно ходить, а будет всё время находится у этого маркера и впустую перебирать ногами, типа идёт, но с места не сдвинется.
В принципе, можно визуально "обмануть" движок и игрока, но это довольно сложный наворот. Для этого можно использовать TranslateTo()для перемещения НПС, тогда в момент этого перемещения коллизия НПС отключается. Если это связать с анимацией ходьбы/бега, то можно визуально добиться эффекта "НПС идёт сквозь препятствия и его можно тоже пройти насквозь". Понадобится вычислять путь "куда идёт НПС" и вести его данной командой по этому пути. Но это сложно, проще отказаться от идеи бесплотности призраков.
Ни один маг.эффект не позволяет отключать коллизию, поэтому о магии можно забыть.
Но это сложно, проще отказаться от идеи бесплотности призраков.
Похоже - единственно верный вариант. Тогда другой вопрос: На НПС проигрывается анимация, во время этой анимации положение тела меняется, но координаты получаемые функциями GetPosition... не меняются, можно ли как то получить координаты реального положения тела во время проигрывания анимации?
Изменение репутации для пользователя slastik
slastikOffline
Сообщение №637
написано: 15 декабря 2013, 12:06
| Отредактировано: slastik - 15 декабря 2013, 12:07
Доброго времени суток. Возникла проблемка. Составил скрипт для НПС, чтобы при активации диалога с ним сначла выпрыгивало окно с кнопками. Выглядит следующим образом:
Event OnLoad() BlockActivation() EndEvent
EVENT onActivate(objectReference actronaut) Int menu menu = Menu01.Show() If (menu == 0) Activate(player, true) ElseIf (menu == 1) If Player.GetItemCount(Item01) >= 1 Player.RemoveItem(Item01) Spell01.Cast(actronaut) Else Message01.Show() EndIf EndIf endEVENT
Я конечно подозреваю, что многое сделал неправильно, но в таком виде скрипт компилируется и работает. Подскажите, как сделать, чтобы спелл кастовался не на ГГ, а на НПС. Чем нужно заменить actronaut или нужен другой тип эвента?
Как из моего скрипта, висящего на XMarker узнать значение переменной из некоторого квеста? Подробнее так: мне нужно делать предметы видимыми при приобретении игроком дома. Я не хочу портить ванильный скрипт и вставлять свой код туда. Но там (HousePurchaseScript из квеста HousePurchase) есть переменная int Property WhiterunHouseVarAuto conditional, которой при покупке дома присваивают 1. Тогда я могу включать свой маркер при загрузке локации, если эта переменная равна 1. Но для этого мне надо получить к ней доступ в моём скрипте.
Добавлено (16 Декабря 2013, 13:14) --------------------------------------------- Ну вот, нашёл другое решение: после покупки дома меняется стадия в квестах Favor250 - Favor254, а это я уже могу засекать. Но всё равно, интересно, как можно обращаться к переменным из стороннего скрипта (квеста).
Изменение репутации для пользователя Artem13
Artem13Offline
Сообщение №640
написано: 16 декабря 2013, 09:18
| Отредактировано: Artem13 - 16 декабря 2013, 09:19
Myprism, раньше это делалось так: QuestName.VarName. Можно ли так делать в папирусе - хз. Попробуй.
<a class="link" href="http://nick-name.ru/sertificates/278209/" rel="nofollow" target="_blank"> border="0" alt=""/</a> Да, мы бандиты и бродяги, как злословит молва, Мы попадаем в передряги, помня эти слова. Смотри вперед и не сдавайся ты на милость судьбе! Предай их всех, останься верен себе. (Канцлер Ги - Кантри Бреган Д'Эрт)
Как из моего скрипта, висящего на XMarker узнать значение переменной из некоторого квеста? Подробнее так: мне нужно делать предметы видимыми при приобретении игроком дома. Я не хочу портить ванильный скрипт и вставлять свой код туда. Но там (HousePurchaseScript из квеста HousePurchase) есть переменная int Property WhiterunHouseVar Auto conditional, которой при покупке дома присваивают 1. Тогда я могу включать свой маркер при загрузке локации, если эта переменная равна 1. Но для этого мне надо получить к ней доступ в моём скрипте.
В своем скрипте объявляешь свойство Quest:
Quest PropertyHousePurchaseAuto
В СК назначаешь на него квест HousePurchase
Чтобы получить доступ к свойству WhiterunHouseVar в своем скрипте используешь конструкцию:
(HousePurchase as HousePurchaseScript).WhiterunHouseVar
LordVadim, компилятор глотает не поперхнувшись, но правильной работы у меня не получается. Как будто скрипт не видит настоящего значения переменной. Дом Тёплых ветров у меня куплен, а там единицы нет. Буду дальше копать.
Изменение репутации для пользователя DarkVetal
DarkVetal
Сообщение №644
написано: 16 декабря 2013, 16:03
| Отредактировано: DarkVetal - 16 декабря 2013, 16:07
AleksTirex, нащёт скрипта для лифта. Значит у меня есть 2 положения лифта (верх\низ) и 4 кнопки для управления (2 для подъема лифта, 2 для спуска, то есть 2 наружных для вызова лифта (вверх\вниз) и 2 внутренних непосредственно для запуска лифта изнутри (вверх\вниз). Значит мне нужно 2 скрипта навесить на 4 кнопки, по 1 скрипту на каждые 2 кнопки (1-й скрипт - для подъема, 2-й скрипт - для спуска, то есть один скрипт с разными координатами) и как-то потом привязать эти 4 кнопки к лифту.
Ничерта не понимая в скриптах и немного разбираясь в английском и твоих предыдущих скриптах я составил это: (знаю что неправильно) Scriptname LiftUp extends ObjectReference Event OnActivate(ObjectReference akActionRef) if GetLinkedRef(). Прописать условие если лифт внизу GetLinkedRef().TranslateTo(akObject.X, akObject.Y, akObject.Z + fZZ, 0.0, 0.0, 0.0, 200.0) - отправка лифта вверх endif endEvent Я так понимаю нужно еще доцепить условие проверки координат лифта, если он вверху, то надо ехать вниз, если уже стоит внизу, то ничего не делать. Я не знаю как akObject привязать к кнопкам вызова, знаю как через LinkedRef, но опять же не знаю, как указанную тобой команду akObject подправить под LinkedRef. Если не трудно, подскажи пожалуйста.
Изменение репутации для пользователя LordVadim
LordVadimOffline
Сообщение №645
написано: 16 декабря 2013, 16:34
| Отредактировано: LordVadim - 16 декабря 2013, 16:42
LordVadim, Всё отлично! Большое спасибо. Помогла твоя первая подсказка. Не сразу у меня заработало по причине использования грязного сейва. Ну, как говорят электронщики, если схема заработала сразу - добра не жди
А вариант с ключом покрасивше будет. Тут я смогу использовать один лаконичный скрипт для всех домов. Пойду переделаю на него.
ГГ бежит, идёт или прыгает. Мне надо его остановить так чтобы он встал(тогда ГГ перестает поворачиваться вслед за камерой!!!) При этом нельзя в Game.DisablePlayerControls надолго ставить abMovement =true так как отключается показ состояния здоровья тд.
Изменение репутации для пользователя LordVadim
LordVadimOffline
Сообщение №648
написано: 16 декабря 2013, 17:01
| Отредактировано: LordVadim - 16 декабря 2013, 17:08
Я так понимаю нужно еще доцепить условие проверки координат лифта, если он вверху, то надо ехать вниз, если уже стоит внизу, то ничего не делать. Я не знаю как akObject привязать к кнопкам вызова, знаю как через LinkedRef, но опять же не знаю, как указанную тобой команду akObject подправить под LinkedRef. Если не трудно, подскажи пожалуйста.
Scriptname LiftUp extends ObjectReference
Event OnActivate(ObjectReference akActionRef) if GetLinkedRef().Z == координата; лифт внизу (координату по оси Z взять из СК) GetLinkedRef().TranslateTo(GetLinkedRef().X,GetLinkedRef().Y,GetLinkedRef().Z + fZZ, 0.0, 0.0, 0.0, 200.0); отправка лифта вверх endif endEvent
Переменной fZZ надо или присвоить значение или заменить ее числом (координаты верхнего положения лифта должны быть известны). Нужны будут два скрипта - один для кнопок вверх, другой для кнопок вниз.
*********************************************** Если выйти из этого помещения с лифтом, то сам лифт опустится на исходную позицию (вниз). Если лифт изначально стоит на верху, то поменяй местами "+" и "-" в команде перемещения. При неудачном движении лифта есть "авариный сброс" и лифт со скриптом придут в исходное положение. Пока лифт движется активировать его невозможно, надо подождать до полной остановки. Все рычаги работают однотипно, нет рычагов "вниз" и "наверх". Если лифт внизу, то при нажатии на любой рычаг он поедет вверх, а если на верху, то поедет вниз.
Добавлено (16 Декабря 2013, 21:51) ---------------------------------------------
Цитата LordVadim
Scriptname LiftUp extends ObjectReference Event OnActivate(ObjectReference akActionRef) if GetLinkedRef().Z == координата ; лифт внизу (координату по оси Z взять из СК) GetLinkedRef().TranslateTo(GetLinkedRef().X, GetLinkedRef().Y, GetLinkedRef().Z + fZZ, 0.0, 0.0, 0.0, 200.0) ; отправка лифта вверх endif endEvent
Так делать нельзя. Если в скрипте присутствует "добавляющее число" (fZZ) и нет жёсткой привязки (координата, параметр и прочее), то при повторной активации команды это "добавленное число" добавится и получится уже двойное значение. Чтобы этого избежать необходимо блокировать повторный/внеочередной вызов команды. Можно доп. переменными или статусами.
Это касается любых скриптов с подобными переменными типа fZZ.
Изменение репутации для пользователя LordVadim
LordVadimOffline
Сообщение №650
написано: 16 декабря 2013, 20:54
| Отредактировано: LordVadim - 16 декабря 2013, 19:18
if GetLinkedRef().Z == координата ; лифт внизу (координату по оси Z взять из СК)
Добавлено (16 Декабря 2013, 23:06) --------------------------------------------- .
DarkVetal, Можно в СК поставить два XMarkerHeading в точки координат нижнего положения лифта и верхнего положения и вместо функции TranslateTo() использовать TranslateToRef().
Скрипт для кнопки вверх:
Scriptname LiftUp extends ObjectReference
ObjectReference Property xmUp Auto ; назначить в СК верхний XMarkerHeading
Ни каких проверок не нужно. Даже если в движущемся лифте нажать кнопку, то лифт или продолжит движение или начнет двигаться в обратном направлении в зависимости от кнопки. Кнопки через вкладку LinkedRef связать с лифтом. Если нужно отслеживать положение лифта при загрузке локации, то нужно будет добавить обработку событий: OnCellLoad() и OnTranslationComplete().
Добавлено (17 Декабря 2013, 00:54) --------------------------------------------- А лучше для кнопок использовать один скрипт:
Scriptname LiftUpDown extends ObjectReference
ObjectReference Property xmTarget Auto ; для кнопки вверх назначить в СК верхний XMarkerHeading, для кнопки вниз назначить в СК нижний XMarkerHeading
Сообщение №651
написано: 17 декабря 2013, 15:41
| Отредактировано: DarkVetal - 17 декабря 2013, 16:00
Способ LordVadim работает (при первом запуске лифт поворачивается вокруг своей оси + при движении вниз ГГ подвисает в воздухе и падает на уехавший лифт), а вот при компиляции скрипта AleksTirex выдает это:
C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,16): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,25): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,28): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,37): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,40): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,49): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,51): cannot subtract a none from a float (cast missing or types unrelated) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,4): type mismatch on parameter 1 (did you forget a cast?) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,4): type mismatch on parameter 2 (did you forget a cast?) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(9,4): type mismatch on parameter 3 (did you forget a cast?) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,16): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,25): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,28): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,37): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,40): variable akObject is undefined C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,49): none is not a known user-defined type C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,51): cannot add a none to a float (cast missing or types unrelated) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,4): type mismatch on parameter 1 (did you forget a cast?) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,4): type mismatch on parameter 2 (did you forget a cast?) C:\Games\Skyrim\Data\Scripts\Source\temp\aaLift2.psc(12,4): type mismatch on parameter 3 (did you forget a cast?) No output generated for aaLift2, compilation failed.
Лифт разворачивается потому, что проставлены не "циферки координат", а углы вращения по осям X, Y, Z. В функции TranslateTo() первые три значения задают координаты X, Y, Z, следующие три значения - углы вращения по осям X, Y, Z, седьмое значение - скорость перемещения, восьмое значение - скорость вращения.
Но это скрипт Алекса, который не компилируется, а я говорю о твоем (от маркера к маркеру, при первом запуске платформа поворачивается по часовой стрелке где-то на 3\4)
Изменение репутации для пользователя LordVadim
LordVadimOffline
Сообщение №654
написано: 18 декабря 2013, 06:42
| Отредактировано: LordVadim - 18 декабря 2013, 05:55
Но это скрипт Алекса, который не компилируется, а я говорю о твоем (от маркера к маркеру, при первом запуске платформа поворачивается по часовой стрелке где-то на 3\4)
Значит надо тот маркер, к которому едет платформа повернуть в противоположную сторону на 3/4. Проверь в СК углы поворота маркеров должны совпадать с углами поворота лифта.
Для точного позиционирования в СК порядок действий такой: Отодвинь маркеры в сторону, что бы не мешали. Поставь лифт в верхнее положение и открой свойства 3D Data. Открой свойства 3D Data для верхнего маркера. Все значения Position и Rotation из свойств лифта скопируй в свойства маркера. Тоже самое для нижнего положения лифта и нижнего маркера. Теперь лифт будет двигаться точно между заданными координатами не поворачиваясь.
Добавлено (18 Декабря 2013, 10:42) --------------------------------------------- На счет подвисающего ГГ - попроси помощи у Алекса. Он как то упоминал функцию SetVehicle() - привязки к объектам, я с ней не разбирался, а Алекс наверняка знает как она работает.
подскажите наиболее правильный способ подсчитать кол-во видов предметов в инвентаре определенной категории. например у меня в инвентаре 2 вина, 3 эля и 10 меда. мне нужно что бы скрипт выдал = 3 вида алкоголя или у меня есть 5 кусков мяса коровы. 2 куска лошади и 8 лося(оленя) тоже самое. нужно что бы был выдан результат = 3 вида мяса.
у меня что то очень уж громоздкое и глючное выходит.
подскажите наиболее правильный способ подсчитать кол-во видов предметов в инвентаре определенной категории.
int iFormIndex = akActor.GetNumItems() - количество категорий/типов/базовых предметов
Определить конкретный тип объекта, типа "мясо", стандартыми методами нельзя, т.к. мясо лося и мясо крысы ничем не отличается вообще, только ID. (разрабы не простовляли кейворды на типы предметов)
Можно проверить по основному типу объекта: яд, пища, зелье (по кейвордам). Но выделить "это == мясо" не получится.
int iPotion int iPoison int Food
Function ChengInventory() int iFormIndex = akActor.GetNumItems() iPotion = 0 iPoison = 0 Food = 0 While iFormIndex > 0 iFormIndex -= 1 Form kForm = akActor.GetNthForm(iFormIndex) if kForm.GetType() == 46 ; Potion if kForm.HasKeywordString("vendoritempotion") ; зелье iPotion += 1 elseif kForm.HasKeywordString("vendoritempoison") ; яд iPoison += 1 elseif kForm.HasKeywordString("vendoritemfood") ; пища/вино Food += 1 endif endif endWhile endFunction
Можно конкретизировать поиск, тогда надо сделать форм-лист со своими проверяемыми предметами. Например, в лист сперва вносите всё вино, потом добавляете всё мясо, потом всё ... и т.д. Получится список, в котором отсортированы предметы Potion. Можно сделать отдельными списками на каждый тип продукта, это как будет удобнее автору. Далее проверка очень простая:
FormList Property ListItemPotion Auto
Function ChengInventory() int iFormIndex = akActor.GetNumItems() While iFormIndex > 0 iFormIndex -= 1 Form kForm = akActor.GetNthForm(iFormIndex) int iIndex = ListItemPotion.Find(kForm) if iIndex != -1 if iIndex <= 12 ; это вино, т.к. в листе первые 12 объектов == вино ; считаем кол-во вина elseif iIndex > 12 && iIndex <= 25 ; это мясо, т.к. в листе с 13 по 25 объект == мясо ; считаем кол-во мяса elseif iIndex > 25 ; это продукты питания типа сыра и лука, т.к. ... ; считаем кол-во endif endif endWhile endFunction
*********************************************
На этом принципе построения можно создать много разных вариантов скрипта. (необходимые переменные добавь сам, и не забудь назначить/обозначить akActor)
Изменение репутации для пользователя Greez
GreezOffline
Сообщение №657
написано: 18 декабря 2013, 15:19
| Отредактировано: Greez - 18 декабря 2013, 15:20
AleksTirex, не знаеш случайно, а можна ли во время движения лифта сделать так, чтобы ГГ или напарник стояли жёстко на платформе. А то лифт едет вверх - ноги встряют в модель, едет вниз - персонаж зависает в воздухе, а потом падает вдогонку на лифт. Всё бы ничего, но кроме двухэтажного дома планирую ещё и небоскрёб, а там уже падение критично (шутка ли, 100 этажей, вровень с Высоким Хротгаром)
AleksTirex, не знаеш случайно, а можна ли во время движения лифта сделать так, чтобы ГГ или напарник стояли жёстко на платформе. А то лифт едет вверх - ноги встряют в модель, едет вниз - персонаж зависает в воздухе, а потом падает вдогонку на лифт. Всё бы ничего, но кроме двухэтажного дома планирую ещё и небоскрёб, а там уже падение критично (шутка ли, 100 этажей, вровень с Высоким Хротгаром)
Скинь ниф лифта и заодно положи в архив все исходники скриптов, связанные с этим лифтом. Есть разные варианты решения, я посмотрю, какой лучше подойдёт.
Форум » TES V: Skyrim » Мастерская » Вопросы по скриптам Papyrus (О скриптах Papyrus (Skyrim). Скриптеры не проходите мимо!)