aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/linden/indra/llimage/llimageworker.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'linden/indra/llimage/llimageworker.cpp')
-rw-r--r--linden/indra/llimage/llimageworker.cpp184
1 files changed, 184 insertions, 0 deletions
diff --git a/linden/indra/llimage/llimageworker.cpp b/linden/indra/llimage/llimageworker.cpp
new file mode 100644
index 0000000..4550848
--- /dev/null
+++ b/linden/indra/llimage/llimageworker.cpp
@@ -0,0 +1,184 @@
1/**
2 * @file llimage.cpp
3 * @brief Base class for images.
4 *
5 * Copyright (c) 2001-2007, Linden Research, Inc.
6 *
7 * The source code in this file ("Source Code") is provided by Linden Lab
8 * to you under the terms of the GNU General Public License, version 2.0
9 * ("GPL"), unless you have obtained a separate licensing agreement
10 * ("Other License"), formally executed by you and Linden Lab. Terms of
11 * the GPL can be found in doc/GPL-license.txt in this distribution, or
12 * online at http://secondlife.com/developers/opensource/gplv2
13 *
14 * There are special exceptions to the terms and conditions of the GPL as
15 * it is applied to this Source Code. View the full text of the exception
16 * in the file doc/FLOSS-exception.txt in this software distribution, or
17 * online at http://secondlife.com/developers/opensource/flossexception
18 *
19 * By copying, modifying or distributing this software, you acknowledge
20 * that you have read and understood your obligations described above,
21 * and agree to abide by those obligations.
22 *
23 * ALL LINDEN LAB SOURCE CODE IS PROVIDED "AS IS." LINDEN LAB MAKES NO
24 * WARRANTIES, EXPRESS, IMPLIED OR OTHERWISE, REGARDING ITS ACCURACY,
25 * COMPLETENESS OR PERFORMANCE.
26 */
27
28#include "linden_common.h"
29
30#include "llimageworker.h"
31#include "llimagedxt.h"
32
33//----------------------------------------------------------------------------
34
35//static
36LLWorkerThread* LLImageWorker::sWorkerThread = NULL;
37S32 LLImageWorker::sCount = 0;
38
39//static
40void LLImageWorker::initClass(LLWorkerThread* workerthread)
41{
42 sWorkerThread = workerthread;
43}
44
45//static
46void LLImageWorker::cleanupClass()
47{
48}
49
50//----------------------------------------------------------------------------
51
52LLImageWorker::LLImageWorker(LLImageFormatted* image, U32 priority, S32 discard, LLResponder* responder)
53 : LLWorkerClass(sWorkerThread, "Image"),
54 mFormattedImage(image),
55 mDecodedType(-1),
56 mDiscardLevel(discard),
57 mPriority(priority),
58 mResponder(responder)
59{
60 ++sCount;
61}
62
63LLImageWorker::~LLImageWorker()
64{
65 mDecodedImage = NULL;
66 mFormattedImage = NULL;
67 --sCount;
68}
69
70//----------------------------------------------------------------------------
71
72//virtual, main thread
73void LLImageWorker::startWork(S32 param)
74{
75 llassert_always(mDecodedImage.isNull());
76 mDecodedType = -1;
77}
78
79bool LLImageWorker::doWork(S32 param)
80{
81 bool decoded = false;
82 if(mDecodedImage.isNull())
83 {
84 if (!mFormattedImage->updateData())
85 {
86 mDecodedType = -2; // failed
87 return true;
88 }
89 if (mDiscardLevel >= 0)
90 {
91 mFormattedImage->setDiscardLevel(mDiscardLevel);
92 }
93 if (!(mFormattedImage->getWidth() * mFormattedImage->getHeight() * mFormattedImage->getComponents()))
94 {
95 decoded = true; // failed
96 }
97 else
98 {
99 S32 nc = param ? 1 : mFormattedImage->getComponents();
100 mDecodedImage = new LLImageRaw(mFormattedImage->getWidth(),
101 mFormattedImage->getHeight(),
102 nc);
103 }
104 }
105 if (!decoded)
106 {
107 if (param == 0)
108 {
109 // Decode primary channels
110 decoded = mFormattedImage->decode(mDecodedImage, .1f); // 1ms
111 }
112 else
113 {
114 // Decode aux channel
115 decoded = mFormattedImage->decode(mDecodedImage, .1f, param, param); // 1ms
116 }
117 }
118 if (decoded)
119 {
120 // Call the callback immediately; endWork doesn't get called until ckeckWork
121 if (mResponder.notNull())
122 {
123 bool success = (!wasAborted() && mDecodedImage.notNull() && mDecodedImage->getDataSize() != 0);
124 mResponder->completed(success);
125 }
126 }
127 return decoded;
128}
129
130void LLImageWorker::endWork(S32 param, bool aborted)
131{
132 if (mDecodedType != -2)
133 {
134 mDecodedType = aborted ? -2 : param;
135 }
136}
137
138//----------------------------------------------------------------------------
139
140
141BOOL LLImageWorker::requestDecodedAuxData(LLPointer<LLImageRaw>& raw, S32 channel, S32 discard)
142{
143 // For most codecs, only mDiscardLevel data is available.
144 // (see LLImageDXT for exception)
145 if (discard >= 0 && discard != mFormattedImage->getDiscardLevel())
146 {
147 llerrs << "Request for invalid discard level" << llendl;
148 }
149 checkWork();
150 if (mDecodedType == -2)
151 {
152 return TRUE; // aborted, done
153 }
154 if (mDecodedType != channel)
155 {
156 if (!haveWork())
157 {
158 addWork(channel, mPriority);
159 }
160 return FALSE;
161 }
162 else
163 {
164 llassert_always(!haveWork());
165 llassert_always(mDecodedType == channel);
166 raw = mDecodedImage; // smart pointer acquires ownership of data
167 mDecodedImage = NULL;
168 return TRUE;
169 }
170}
171
172BOOL LLImageWorker::requestDecodedData(LLPointer<LLImageRaw>& raw, S32 discard)
173{
174 if (mFormattedImage->getCodec() == IMG_CODEC_DXT)
175 {
176 // special case
177 LLImageDXT* imagedxt = (LLImageDXT*)((LLImageFormatted*)mFormattedImage);
178 return imagedxt->getMipData(raw, discard);
179 }
180 else
181 {
182 return requestDecodedAuxData(raw, 0, discard);
183 }
184}