[ Новые сообщения · Участники · Правила форума · Поиск · RSS ]
Страница 1 из 212»
Форум Panda3D - по русски » Panda3D » Общие вопросы » Pick Model , struct вопросы (?)
Pick Model , struct вопросы (?)
FertoVordalastrДата: Суббота, 28.03.2009, 17:26 | Сообщение # 1
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
задача такая - нужно написать небольшую прогу, где есть массив объектов, состояние которых меняется постоянно (несколько переменных приращиваются с каждым шагом главного цикла) и есть игрок, который должен нажать на объект мышой и выбрать из выпадающего окошечка вариант действия... на Сях реализовать было просто, но после стольких лет наСилования никак не могу вкурить в py
вопросы:
1) Как в питоне можно реализовать аналог двумерного массива структур?
2) Как собственно реализовать Pick мышой... пытался глянуть пример Chessboard, но нифига не могу вкурить...
3) Как реализовать выпадающие кнопочки? есть идея сделать это с помощью встроенных GUI как картинки, выпадающие под координатами мыши в 2D но тоже пока не до конца разобрался как...

КТО МОЖЕТ, ПОМОГИТЕ!!!!!! УМОЛЯЮ!!!!! ДИПЛОМ ГОРИТ!!!!

 
ninthДата: Воскресенье, 29.03.2009, 12:57 | Сообщение # 2
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
1.
в питоне массив может содержать любые данные, в т.ч. другой массив, кортеж или справочник. Т.е. в зависимости от задачи для многомерного массива ты можешь использовать либо вложенные массивы, либо массив кортежей или справочников.
Вот пример работы со всеми тремя вариантами
Code
myarray1=[]
myarray2=[]
myarray3=[]
for i in xrange(5):
     myarray1.append([i+1,i+2,i+3])
     myarray2.append((i+4,i+5,i+6))
     myarray3.append({'f1':i+7,'f2':i+8,'f3':i+9})

for a in myarray1:
     summ=a[0]+a[1]+a[2]
     print a
     print 'a1:'+str(summ)

for x,y,z in myarray2:
     summ=x+y+z
     print x,y,z
     print 'a2:'+str(summ)

for a in myarray3:
     print a
     summ=a['f1']+a['f2']+a['f3']
     print 'a3:'+str(summ)

А вообще, загляни в раздел файлов, там лежит учебник по питону - всё довольно просто, нужно только понять логику питона.

2.
Более конкретно скажи что непонятно? Общий принцип - создаём систему коллизий - с одной стороны объекты которые надо пикать, с другой - луч, идущий от камеры с учётом экранных координат, и пикаем этим лучём. Для упрощения узнавания по какому объекту попали - чтоб не перебирать массив, объект определяем по присвоенному ранее тегу.

3.
Ну, собственно, да - так обычно и делается, либо использовать виджеты, но виджеты в данном случае не очень хорошо смотреться будут

З.Ы. Я эту тему чуть позже перенесу в вопросы для начинающих... так что если что, ищи там.

 
FertoVordalastrДата: Воскресенье, 29.03.2009, 18:32 | Сообщение # 3
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
Спасибо огромное ))))) куча всего стала понятна )))
на тему учебника - читаю Россума, проблемма в сжатости сроков на реализацию. не хватает времени до конца разобраться... а можете представить, какое состояние принимает мозг, когда наСильник за 2 дня читает учебник по py и пытается написать что-то дельное... не могу никак начать мыслить по питоновскому... а отсутствие необходимости задавать тип всему что я объявляю меня просто из седла вырубает.

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

2) спасибо )))) нашел другую статью на форуме про коллизии. тока не сильно понял - как мне создать объект луча?

3) опять же не ориентируюсь пока что в классах ) можно узнать, в каком классе лежит DXGUI или что нить подобное?

еще раз спасибо за помощь.

Сообщение отредактировал FertoVordalastr - Воскресенье, 29.03.2009, 18:33
 
ninthДата: Среда, 01.04.2009, 23:21 | Сообщение # 4
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
Да, действительно в питоне типы переменных определяются по содержимому и могут быть переопределены на лету просто присвоением переменной другого типа. Птон интерпретируемый язык, что даёт свои особенности - плюсы и минусы )

1. У питона довольно оригинальный подход к синтаксису, заставляющий сразу правильно оформлять код. Вместо begin end в Delphi или {} в С используются отступы - т.е. инструкции одного составного оператора должны иметь одинаковый отступ (пробел и табуляция различаются).
Да, ты правильно понял. В массив можно так же загнать например класс, написанный тобой. Т.е. если ты работаешь со сложными структурами, то возможно будет удобнее, если твоя переменная будет иметь собственные методы (впрочем, это стандарт для ООП). Так же один массив может содержать одновременно переменные разных типов (ещё одно непривычное отличие от компилируемых языков).
Да, в питоне несколько непривычно реализованы циклы со счётчиками, здесь нет обычного указания от-до-приращение for(i=0;i<5;i++). В питоновском цикле по очереди берутся значения из предложенного списка, пока не будет достигнут конец. Например, функция xrange(5) приведённая в предыдущем посте возвращает массив от 0 до 4. Непривычно, но это позволяет упростить операции с перебором элементов массивов.

2. Посмотри демку №2 по ODE в файлах на этом сайте. Там есть модуль MousePicker - достаточно подробно откомментирован.

3. Посмотри каталоге статью по DirectGUI панды и демку из поставляемых с пандой - Music-Box - там используется пандовский GUI.

 
FertoVordalastrДата: Пятница, 22.05.2009, 19:17 | Сообщение # 5
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
АААААА!!!!!! Господа!!!! умоляю, спасите!
неделя осталась я все диплом доделать не могу.... со структурой данных определился, гуев наделал, даже по модульному все сделал
(спасибо нашему админу )))) огромное спасибо за уроки в детсаду)

только вот никак не получается реализовать основное

Задача:
Имеется куча моделей, состояние которых отображается цветом. Состояние пересчитывается каждые n миллисекунд по жутко хитрой формуле, после чего обновляется свет.

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

были подозрения на неправильность формулы, но я ее уже проверил и отладил. еще может быть с точностью питонвского флоата, но тут тогда не знаю как решить.

В общем - выручите!!!! УМОЛЯЮ!!!! не хочу диплом провалить.

 
3dmaxДата: Пятница, 22.05.2009, 22:01 | Сообщение # 6
Генерал-майор
Группа: Проверенные
Сообщений: 334
Награды: 0
Репутация: 1
Статус: Offline
выкладуй исходник, я сам не особо шарю но вот может ninth, поможет или еще кто знающий.
 
ninthДата: Суббота, 23.05.2009, 17:02 | Сообщение # 7
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
У меня подозрение, что ты используешь taskMgr.add(...) и Task.cont а тебе требуется taskMgr.doMethodLater(...) и Task.again. А вообще, Макс прав - лучше всего давай код, если по каким-то причинам не хочешь на форуме выкладывать - отправляй на rupanda3d (с_А_б_а_к_а) gmail.com
 
FertoVordalastrДата: Суббота, 23.05.2009, 18:56 | Сообщение # 8
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
Code

//Куча инициализации и организации структуры данных, которая заканчивается так:
for x in students:
     for y in x:
         y['model'].setColor(y['r'],0,y['b'])
classRoom = loader.loadModel("models/class.egg")
classRoom.reparentTo(render)

base.disableMouse()
base.camera.setPos(-40,-40,40)
base.camera.lookAt(mStd32)

lght= DirectionalLight('my_lght')
alight = AmbientLight('my_alight')
lght.setColor(VBase4(0.25,0.75,1,0.8))

lg= render.attachNewNode(lght)
al=render.attachNewNode(alight)
lg.setHpr(30,-20,0)

render.setLight(lg)
render.setLight(al)

def msTask(task):
     k=0
     p=0
     for i in range(6):
         for j in range(4):
             p=students[i][j]['b']
             if(students[i][j]['b']<0.5) and (students[i][j]['b']>=0):
                 if(students[i][j]['r']<math.floor((1-p*0.000005))):
                     students[i][j]['r']+=math.floor((0.5-p)*0.000005)
                 else:
                     students[i][j]['r']=1
             if(students[i][j]['b']>0.5) and (students[i][j]['b']<=1):
                 if(students[i][j]['r']>math.floor((p*0.000005))):
                     students[i][j]['r']-=math.floor((0.5-p)*0.000005)
                 else:
                     students[i][j]['r']=0
     for i in range(4):
         reserve[2][i]=math.ceil((students[1][i]['b']+students[2][i]['b'])/2)
         reserve[5][i]=math.ceil((students[3][i]['b']+students[4][i]['b'])/2)
     for i in range(2):
         for j in range(4):
             reserve[i][j] = students[i][j]['b']
             reserve[i+3][j] = students[i+2][j]['b']
             reserve[i+6][j] = students[i+4][j]['b']
     for i in range(8):
         for j in range(4):
             k=0
             if(i!=2) or (i!=5):
                 if(i>=1):
                     if(i==1) or (i==4) or(i==7):
                         temp[i][j]+=2*reserve[i-1][j]
                     else:
                         temp[i][j]+=reserve[i-1][j]
                         k+=1
                 if(j>=1) and (i>=1):
                     temp[i][j]+=reserve[i-1][j-1]
                     k+=1
                 if(j>=1):
                     temp[i][j]+=reserve[i][j-1]
                     k+=1
                 if(j>=1) and (i<=6):
                     temp[i][j]+=reserve[i+1][j-1]
                     k+=1
                 if(i<=6):
                     if(i==0) or (i==3) or (i==6):
                         temp[i][j]+=2*reserve[i+1][j]
                     else:
                         temp[i][j]+=reserve[i+1][j]
                         k+=1
                 if(j<=2) and (i<=6):
                     temp[i][j]+=reserve[i+1][j+1]
                     k+=1
                 if(j<=2):
                     temp[i][j]+=reserve[i][j+1]
                     k+=1
                 if(i>=1) and (j<=2):
                     temp[i][j]+=reserve[i-1][j+1]
                     k+=1
                      
                 p=math.ceil(0.00005*((k+1)-temp[i][j]))
                 if (i<2):
                     if(students[i][j]['b']>p):
                         students[i][j]['b']-=p
                     else:
                         students[i][j]['b']=0
                 if(i<4):
                     if(students[i-1][j]['b']>p):
                         students[i][j]['b']-=p
                     else:
                         students[i-1][j]['b']=0
                 if(i<6):
                     if(students[i-2][j]['b']>p):
                         students[i][j]['b']-=p
                     else:
                         students[i-2][j]['b']=0
     for x in range(6):
         for y in range(4):
             students[x][y]['model'].setColor(students[x][y]['r'],0,students[x][y]['b'])
     return Task.again

taskMgr.add(msTask,'MainTask')
run()

пытался сделать как то doLater но не сильно воткнулся кажись...

 
ninthДата: Суббота, 23.05.2009, 19:19 | Сообщение # 9
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
попробуй taskMgr.doMethodLater(0.1,msTask,'Main task') и поиграй параметром 0.1
 
FertoVordalastrДата: Суббота, 23.05.2009, 19:39 | Сообщение # 10
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
спс большое )))
можешь еще пожалуйста одну вещь объяснить.
спер я модуль mousepick из примера, подогнал его под себя, но не докнца в него воткнулся:
-подключаю модуль
-создаю... ээээмм... наверное, экземпляр класса... другой ассоциации нет
-добавляю все пикаемые модели в список пикаемых моделей...

а как и где вызывается обработка самого пика?

 
ninthДата: Суббота, 23.05.2009, 20:06 | Сообщение # 11
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
Если это из примера с ODE, то там проверка происходит в процедуре pick. Вызывается она по нажатию кнопки мыши.
 
FertoVordalastrДата: Пятница, 29.05.2009, 06:36 | Сообщение # 12
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
ссорь, что снова отвлекаю глупыми вопросами... но чето я не пойму свой mousePick
в примере много лишнего... чувствуется... а я не знаю чего.

моя проблемма в том что пример расчитан на немедленное выполнение действия по пику, а мне нужно всего лишь получить нод по которому я пикнул. пытался сделать в методе pick() в конце return b (нод который определяется), а потом юзать в главной программе типа pick().setPos()
а оно не компилиться даже (
а кода возвращаю все на места, оно вааще не работает.

вопрос в том - как мне получить нод, который я пикаю?

 
ninthДата: Пятница, 29.05.2009, 08:19 | Сообщение # 13
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
Посмотри - в примере с пикабельными кубиками для того чтоб не заморачиваться с поиском того по чему клацнули есть список pickableObjects. При добавлении нового бокса я вызываю addPickableObject, которая назначает боксу маску, назначает тэг и вносит объект в список. При проверке коллизии я получаю обратно тэг, назначенный пикнутому объекту self.pickerQ.getEntry(0).getIntoNode().getTag('obj'), а тэг я назначал равный индексу - obj.find("*").node().setTag('obj', str(len(self.pickableObjects))) объекта в массиве, так что остаётся тэг перегнать в число int() и обратиться по этому индексу к массиву.
 
FertoVordalastrДата: Среда, 03.06.2009, 19:52 | Сообщение # 14
Сержант
Группа: Пользователи
Сообщений: 28
Награды: 0
Репутация: 0
Статус: Offline
кажется, я сам все усложнил своим вопросом...
если я правильно понял, то вместо того, чтобы получать handle нода и передавать его потом во внешнюю функцию (как было мне показано), можно совершить все действия над ним в самом пике без лишних поисков... так будет легче наверное??
 
ninthДата: Четверг, 04.06.2009, 21:28 | Сообщение # 15
Admin
Группа: Администраторы
Сообщений: 1555
Награды: 5
Репутация: 46
Статус: Offline
Можно, но дело в том, что загружаемая модель может состоять из нескольких нодов и лучом ты получаешь только тот, с которым произошло пересечение, так что может выйти, что используя хэндл, полученный таким образом, ты будешь рулить только куском модели. Впрочем, для простого кубика, думаю это не является проблемой.
 
Форум Panda3D - по русски » Panda3D » Общие вопросы » Pick Model , struct вопросы (?)
Страница 1 из 212»
Поиск: