Line data Source code
1 :
2 : /* Copyright (c) 2007-2012, Stefan Eilemann <eile@equalizergraphics.com>
3 : * 2011, Daniel Nachbaur <danielnachbaur@gmail.com>
4 : *
5 : * This library is free software; you can redistribute it and/or modify it under
6 : * the terms of the GNU Lesser General Public License version 2.1 as published
7 : * by the Free Software Foundation.
8 : *
9 : * This library is distributed in the hope that it will be useful, but WITHOUT
10 : * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
11 : * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
12 : * details.
13 : *
14 : * You should have received a copy of the GNU Lesser General Public License
15 : * along with this library; if not, write to the Free Software Foundation, Inc.,
16 : * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
17 : */
18 :
19 : #include "compoundUpdateInputVisitor.h"
20 :
21 : #include "frame.h"
22 : #include "frameData.h"
23 : #include "tileQueue.h"
24 : #include "server.h"
25 :
26 : #include <eq/client/log.h>
27 : #include <eq/fabric/iAttribute.h>
28 :
29 : namespace eq
30 : {
31 : namespace server
32 : {
33 72 : CompoundUpdateInputVisitor::CompoundUpdateInputVisitor(
34 : const Compound::FrameMap& outputFrames,
35 : const Compound::TileQueueMap& outputQueues )
36 : : _outputFrames( outputFrames )
37 72 : , _outputQueues( outputQueues )
38 72 : {}
39 :
40 171 : VisitorResult CompoundUpdateInputVisitor::visit( Compound* compound )
41 : {
42 171 : if( !compound->isActive( ))
43 68 : return TRAVERSE_PRUNE;
44 :
45 103 : _updateQueues( compound );
46 103 : _updateFrames( compound );
47 103 : return TRAVERSE_CONTINUE;
48 : }
49 :
50 103 : void CompoundUpdateInputVisitor::_updateQueues( const Compound* compound )
51 : {
52 103 : const TileQueues& inputQueues = compound->getInputTileQueues();
53 103 : for( TileQueuesCIter i = inputQueues.begin(); i != inputQueues.end(); ++i )
54 : {
55 : //----- Find corresponding output queue
56 0 : TileQueue* queue = *i;
57 0 : const std::string& name = queue->getName();
58 :
59 0 : Compound::TileQueueMap::const_iterator j = _outputQueues.find( name );
60 :
61 0 : if( j == _outputQueues.end( ))
62 : {
63 0 : LBVERB << "Can't find matching output queue, ignoring input queue "
64 0 : << name << std::endl;
65 0 : queue->unsetData();
66 0 : continue;
67 : }
68 :
69 0 : LBASSERT( queue->isAttached( ));
70 :
71 0 : TileQueue* outputQueue = j->second;
72 0 : queue->setOutputQueue( outputQueue, compound );
73 : }
74 103 : }
75 :
76 103 : void CompoundUpdateInputVisitor::_updateFrames( Compound* compound )
77 : {
78 103 : const Channel* channel = compound->getChannel();
79 103 : if( !compound->testInheritTask( fabric::TASK_ASSEMBLE ) || !channel )
80 72 : return;
81 :
82 31 : const Frames& inputFrames = compound->getInputFrames();
83 31 : if( inputFrames.empty( ))
84 : {
85 22 : compound->unsetInheritTask( fabric::TASK_ASSEMBLE );
86 22 : return;
87 : }
88 :
89 18 : for( FramesCIter i = inputFrames.begin(); i != inputFrames.end(); ++i )
90 : {
91 : //----- Find corresponding output frame
92 9 : Frame* frame = *i;
93 9 : const std::string& name = frame->getName();
94 :
95 9 : Compound::FrameMap::const_iterator j = _outputFrames.find( name );
96 :
97 9 : if( j == _outputFrames.end( ))
98 : {
99 0 : LBVERB << "Can't find matching output frame, ignoring input frame "
100 0 : << name << std::endl;
101 0 : frame->unsetData();
102 0 : continue;
103 : }
104 :
105 : //----- Set frame parameters:
106 : // 1) Frame offset
107 9 : Frame* outputFrame = j->second;
108 9 : const Channel* iChannel = compound->getInheritChannel();
109 9 : Vector2i frameOffset = outputFrame->getMasterData()->getOffset() +
110 18 : frame->getNativeOffset();
111 :
112 9 : if( outputFrame->getCompound()->getInheritChannel() != iChannel )
113 0 : frameOffset = frame->getNativeOffset();
114 9 : else if( channel != iChannel )
115 : {
116 : // compute delta offset between source and destination, since the
117 : // channel's native origin (as opposed to destination) is used.
118 0 : const Viewport& frameVP = frame->getViewport();
119 0 : const PixelViewport& inheritPVP=compound->getInheritPixelViewport();
120 0 : PixelViewport framePVP( inheritPVP );
121 :
122 0 : framePVP.apply( frameVP );
123 0 : frameOffset.x() -= framePVP.x;
124 0 : frameOffset.y() -= framePVP.y;
125 :
126 0 : const PixelViewport& iChannelPVP = iChannel->getPixelViewport();
127 0 : frameOffset.x() -= iChannelPVP.x;
128 0 : frameOffset.y() -= iChannelPVP.y;
129 : }
130 9 : frame->setOffset( frameOffset );
131 :
132 : // 2) zoom
133 9 : _updateZoom( compound, frame, outputFrame );
134 :
135 : // 3) TODO input frames are moved using the offset. The pvp signifies
136 : // the pixels to be used from the frame data.
137 : //framePVP.x = static_cast< int32_t >( frameVP.x * inheritPVP.w );
138 : //framePVP.y = static_cast< int32_t >( frameVP.y * inheritPVP.h );
139 : //frame->setInheritPixelViewport( framePVP );
140 : //----- Link input frame to output frame (connects frame data)
141 9 : outputFrame->addInputFrame( frame, compound );
142 :
143 9 : for( unsigned k = 0; k < NUM_EYES; ++k )
144 : {
145 9 : const Eye eye = Eye( 1<<k );
146 18 : if( compound->isInheritActive( eye ) && // eye pass used
147 9 : outputFrame->hasData( eye )) // output data for eye pass
148 : {
149 9 : frame->commit();
150 9 : LBLOG( LOG_ASSEMBLY )
151 0 : << "Input frame \"" << name << "\" on channel \""
152 0 : << channel->getName() << "\" id " << frame->getID() << " v"
153 9 : << frame->getVersion() << "\" tile pos "
154 0 : << frame->getOffset() << ' ' << frame->getZoom()
155 27 : << std::endl;
156 9 : break;
157 : }
158 : }
159 : }
160 : }
161 :
162 9 : void CompoundUpdateInputVisitor::_updateZoom( const Compound* compound,
163 : Frame* frame,
164 : const Frame* outputFrame )
165 : {
166 9 : Zoom zoom = frame->getNativeZoom();
167 9 : if( !zoom.isValid( )) // if zoom is not set, inherit from parent
168 9 : zoom = compound->getInheritZoom();
169 :
170 : // Zoom difference between output and input
171 9 : const FrameData* frameData = outputFrame->getMasterData();
172 9 : zoom /= frameData->getZoom();
173 :
174 9 : frame->setZoom( zoom );
175 9 : }
176 :
177 : }
178 27 : }
|