[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Gzz-commits] gzz doc/Gzz_Memory.rst gzz/mem/MemoryConsumer.j...
From: |
Tuomas J. Lukka |
Subject: |
[Gzz-commits] gzz doc/Gzz_Memory.rst gzz/mem/MemoryConsumer.j... |
Date: |
Wed, 08 Jan 2003 05:35:11 -0500 |
CVSROOT: /cvsroot/gzz
Module name: gzz
Changes by: Tuomas J. Lukka <address@hidden> 03/01/08 05:35:11
Modified files:
doc : Gzz_Memory.rst
gzz/mem : MemoryConsumer.java MemoryPartitioner.java
Log message:
More work on gzz.mem
CVSWeb URLs:
http://savannah.gnu.org/cgi-bin/viewcvs/gzz/gzz/doc/Gzz_Memory.rst.diff?tr1=1.7&tr2=1.8&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/gzz/gzz/gzz/mem/MemoryConsumer.java.diff?tr1=1.3&tr2=1.4&r1=text&r2=text
http://savannah.gnu.org/cgi-bin/viewcvs/gzz/gzz/gzz/mem/MemoryPartitioner.java.diff?tr1=1.1&tr2=1.2&r1=text&r2=text
Patches:
Index: gzz/doc/Gzz_Memory.rst
diff -u gzz/doc/Gzz_Memory.rst:1.7 gzz/doc/Gzz_Memory.rst:1.8
--- gzz/doc/Gzz_Memory.rst:1.7 Wed Jan 8 00:40:35 2003
+++ gzz/doc/Gzz_Memory.rst Wed Jan 8 05:35:09 2003
@@ -149,10 +149,12 @@
bigpackage gzz.mem
- class MemoryPartitioner
+ class MemoryPartitioner "staticAPI"
jlink
methods
void request(MemoryConsumer c, float importance, float quality, Obs
o)
+ void start(Object id)
+ void end(Object id)
assoc multi(*) - multi(1) MemoryConsumer
@@ -185,5 +187,6 @@
Need to be able to handle case of 1 focus-request + 100 low-quality non-focus
requests
IN A SINGLE VOBSCENE.
+
Index: gzz/gzz/mem/MemoryConsumer.java
diff -u gzz/gzz/mem/MemoryConsumer.java:1.3 gzz/gzz/mem/MemoryConsumer.java:1.4
--- gzz/gzz/mem/MemoryConsumer.java:1.3 Wed Jan 8 00:40:35 2003
+++ gzz/gzz/mem/MemoryConsumer.java Wed Jan 8 05:35:10 2003
@@ -5,7 +5,8 @@
/** An object representing an entity which would like
* to consume a significant amount of memory (large image or such).
- * Memoryconsumers <b>must</b> work as hash keys.
+ * Memoryconsumers <b>must</b> work as hash keys; a new consumer with
+ * the same meaning as a previous one must be found in a hash.
* <p>
* Quality is an important variable whose semantics are not defined in this
interface
* beyond that
@@ -20,6 +21,7 @@
public interface MemoryConsumer {
/** Whether this object can make use of byte amounts less
* than getMaxBytes() returns.
+ * For example, images can be scaled down but text cannot.
*/
boolean getScalable();
/** The maximum number of bytes this object would like to consume.
@@ -32,6 +34,8 @@
* setReservation has been called, it is undefined whether
* the previous Obs will be called at all. The size, when the later Obs
* is called, is the new one.
+ * <p>
+ * <b>This method may only be called by address@hidden
MemoryPartitioner}.</b>
* @param bytes The maximum amount of bytes this object should reserve.
* @param quality Maximum quality that should be loaded (if quality is
* adjusted in discrete steps, the class may round
upwards).
@@ -41,5 +45,9 @@
/** Get the number of bytes currently used.
*/
int getReservation();
+
+ /** Get the quality currently used.
+ */
+ float getQuality();
}
Index: gzz/gzz/mem/MemoryPartitioner.java
diff -u gzz/gzz/mem/MemoryPartitioner.java:1.1
gzz/gzz/mem/MemoryPartitioner.java:1.2
--- gzz/gzz/mem/MemoryPartitioner.java:1.1 Wed Jan 8 00:40:35 2003
+++ gzz/gzz/mem/MemoryPartitioner.java Wed Jan 8 05:35:11 2003
@@ -3,6 +3,8 @@
package gzz.mem;
import gzz.Obs;
+import java.util.*;
+
/** A static API which divides the available memory between
* MemoryConsumers.
@@ -13,11 +15,82 @@
*/
public static int memory = 64 * 1024 * 1024;
+
+ static Stack currentScene = new Stack();
+ static {
+ currentScene.push(null);
+ }
+
+ static public void start(Object id) {
+ currentScene.push(id);
+ }
+ static public void end(Object id) {
+ currentScene.pop();
+ }
+
static class ConsumerRecord {
-// float
+ /** The current maximum importance.
+ * May be set to -1 at any time by the background thread.
+ */
+ float maxImportance = -1;
+ float maxQuality = -1;
+
+ /** The filtered importance.
+ */
+ float curImportance = -1;
+ float curQuality = -1;
+
+ /** The number of bytes requested from the consumer.
+ */
+ int setBytes = 0;
+ int setQuality = -1;
+
+ /** The number of bytes the consumer reports using currently.
+ */
+ int gotBytes = 0;
+ int gotQuality = -1;
+
+ Obs o;
+
+ /** Update curImportance and curQuality towards the observed
+ * values.
+ */
+ void bgUpdate() {
+ float i = maxImportance;
+ maxImportance = -1;
+ float q = maxQuality;
+ maxQuality = -1;
+
+ if(i < 0) {
+ curImportance *= .98;
+ } else {
+ if(i >= curImportance)
+ curImportance = i;
+ else {
+ curImportance -= .02 * (curImportance - i);
+ }
+ }
+ // We won't decay: will always remain an interpolate
+ if(q >= 0) {
+ if(q >= curQuality)
+ curQuality = q;
+ else
+ curQuality -= .02 * (curQuality - q);
+ }
+ }
+
+ void update(float importance, float quality, Obs o) {
+ if(importance > maxImportance)
+ maxImportance = importance;
+ if(quality > maxQuality)
+ maxQuality = quality;
+ this.o = o;
+ }
+
}
- // Map consumer2
+ static Map consumer2record = Collections.synchronizedMap(
+ new WeakHashMap());
/** Indicate that a request for the data of the given consumer was made.
* @param consumer The consumer whose data was requested.
@@ -26,6 +99,8 @@
* @param quality An abstract value to be passed to
* address@hidden
MemoryConsumer#setReservation}. For example,
* this could be the DPI resolution of an
image.
+ * 0 = no quality at all, negative values
+ * not allowed.
* @param o An observer to be called (if non-null)
* when the consumer's size is changed the next time.
* Note that the semantics are different from
address@hidden MemoryConsumer.setReservation}'s
@@ -33,13 +108,42 @@
* This difference is up to MemoryPartitioner to handle
internally.
* @see MemoryConsumer
*/
- public void request(MemoryConsumer consumer, float importance, float
quality, Obs o) {
-
+ static public void request(MemoryConsumer consumer, float importance,
float quality, Obs o) {
+ ConsumerRecord rec = (ConsumerRecord)consumer2record.get(consumer);
+ if(rec == null) {
+ rec = new ConsumerRecord();
+ consumer2record.put(consumer, rec);
+ }
+ rec.update(importance, quality, o);
+
}
static Thread repartitioner = new Thread() {
public void run() {
-
+ int sum1 = 0;
+ int sumReduced = 0;
+ for(int round = 0; ; round++) {
+ for(Iterator i = consumer2record.keySet().iterator();
i.hasNext(); ) {
+ MemoryConsumer cons = (MemoryConsumer)i.next();
+ ConsumerRecord rec =
(ConsumerRecord)consumer2record.get(cons);
+ if(round == 0) rec.bgUpdate();
+ float imp = 0;
+ if(rec.curImportance > 0)
+ imp = (float)Math.pow(rec.curImportance, round);
+ else if(round == 0)
+ imp = 1;
+ int byt = cons.getMaxBytes(rec.curQuality);
+ if(rec.curImportance == 1)
+ sum1 += byt;
+ sumReduced += (int)(imp * byt);
+ }
+ if(sum1 > memory) {
+ // Problem! Not enough memory for all 1-importances
+ }
+ if(sumReduced <= memory) {
+ // Hey, now it fits!
+ }
+ }
}
};
}
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Gzz-commits] gzz doc/Gzz_Memory.rst gzz/mem/MemoryConsumer.j...,
Tuomas J. Lukka <=