[Bf-blender-cvs] [4c56a47] soc-2014-shapekey: Fixed yesterday's shape key compression

Grigory Revzin noreply at git.blender.org
Sat Jun 14 19:35:21 CEST 2014


Commit: 4c56a47730b93f47c356fe5c36e1fa513a78cb37
Author: Grigory Revzin
Date:   Sat Jun 14 19:24:36 2014 +0400
https://developer.blender.org/rB4c56a47730b93f47c356fe5c36e1fa513a78cb37

Fixed yesterday's shape key compression

1) Shape key data would fail to link on file read, fixed now.

2) Endianess flipping now supports compressed shape keys, just have to
test (thanks ideasman42 for ideas)

3) Also removed some debug printfs

===================================================================

M	release/datafiles/locale
M	release/scripts/addons
M	release/scripts/addons_contrib
M	scons
M	source/blender/blenloader/intern/readfile.c
M	source/blender/blenloader/intern/writefile.c
M	source/blender/makesdna/DNA_key_types.h

===================================================================

diff --git a/release/datafiles/locale b/release/datafiles/locale
index cb1967c..f56a042 160000
--- a/release/datafiles/locale
+++ b/release/datafiles/locale
@@ -1 +1 @@
-Subproject commit cb1967cc63a6d2d75d2b59cdf91c5f5645285aea
+Subproject commit f56a042595d86bc3e899ae73276a2709d48b1964
diff --git a/release/scripts/addons b/release/scripts/addons
index c50944e..90ba26f 160000
--- a/release/scripts/addons
+++ b/release/scripts/addons
@@ -1 +1 @@
-Subproject commit c50944e808d6c74148237e85866e893628f0fee6
+Subproject commit 90ba26f45feab4f02e9652c274890a986797d446
diff --git a/release/scripts/addons_contrib b/release/scripts/addons_contrib
index 31545d2..e253e7e 160000
--- a/release/scripts/addons_contrib
+++ b/release/scripts/addons_contrib
@@ -1 +1 @@
-Subproject commit 31545d25c9cb41d271a3f3ef84d327708572290e
+Subproject commit e253e7e3963eaca55902500768ea7a116163f819
diff --git a/scons b/scons
index 2d6ebcb..59512aa 160000
--- a/scons
+++ b/scons
@@ -1 +1 @@
-Subproject commit 2d6ebcb23909058b846aa232ecb2fee497924cf8
+Subproject commit 59512aadd1d16d7b9327f0eefafb23513b4f2137
diff --git a/source/blender/blenloader/intern/readfile.c b/source/blender/blenloader/intern/readfile.c
index e2aca7c..7fe68f3 100644
--- a/source/blender/blenloader/intern/readfile.c
+++ b/source/blender/blenloader/intern/readfile.c
@@ -3060,35 +3060,47 @@ void uncompress_kb(Key * key, KeyBlock *kb)
 	kb->totelem = rk->totelem;
 
 	/* free compressed data */
-	MEM_freeN(kbcde);
+	if (kbcde) {
+		/* compressed data may be NULL when a kb doesn't have any differences from the basis */
+		MEM_freeN(kbcde);
+	}
 }
 
 static void switch_endian_keyblock(Key *key, KeyBlock *kb)
 {
 	int elemsize, a, b;
 	const char *data, *poin, *cp;
-	
-	elemsize = key->elemsize;
 	data = kb->data;
-	
-	for (a = 0; a < kb->totelem; a++) {
-		cp = key->elemstr;
-		poin = data;
-		
-		while (cp[0]) {  /* cp[0] == amount */
-			switch (cp[1]) {  /* cp[1] = type */
+
+	if (kb->compressed) {
+		KB_ComprMeshDataEnt *kbcde = data;
+		for (a = 0; a < kb->totelem; ++a) {
+			BLI_endian_switch_int32(&kbcde[a].vertex_index);
+			BLI_endian_switch_float_array((float *) &kbcde[a].co, 3);
+		}
+	} 
+	else {
+		elemsize = key->elemsize;
+		for (a = 0; a < kb->totelem; a++) {
+			cp = key->elemstr;
+			poin = data;
+
+			while (cp[0]) {  /* cp[0] == amount */
+				switch (cp[1]) {  /* cp[1] = type */
 				case IPO_FLOAT:
 				case IPO_BPOINT:
 				case IPO_BEZTRIPLE:
 					b = cp[0];
 					BLI_endian_switch_float_array((float *)poin, b);
-					poin += sizeof(float) * b;
+					poin += sizeof(float)* b;
 					break;
+				}
+
+				cp += 2;
 			}
-			
-			cp += 2;
+			data += elemsize;
 		}
-		data += elemsize;
+
 	}
 }
 
@@ -3109,17 +3121,15 @@ static void direct_link_key(FileData *fd, Key *key)
 	for (kb = key->block.first; kb; kb = kb->next) {
 		kb->data = newdataadr(fd, kb->data);
 
-		if (kb->compressed && key->refkey != kb) {
-			uncompress_kb(key, kb);
-			printf("Unpacked kb %s\n", kb->name);
-		}
-		
 		if (fd->flags & FD_FLAGS_SWITCH_ENDIAN) {
-			BLI_assert(0); /* not supported with compressing yet */
 			switch_endian_keyblock(key, kb);
 		}
 
+		if (kb->compressed && key->refkey != kb) {
+			uncompress_kb(key, kb);
+		}
 	}
+
 }
 
 /* ************ READ mball ***************** */
diff --git a/source/blender/blenloader/intern/writefile.c b/source/blender/blenloader/intern/writefile.c
index ebd70f2..233a382 100644
--- a/source/blender/blenloader/intern/writefile.c
+++ b/source/blender/blenloader/intern/writefile.c
@@ -1612,7 +1612,10 @@ void compress_kb(KeyBlock *kb, Key *key_owner)
 		MEM_freeN(kb->data);
 		kb->data = kbcde;
 
-		printf("Packed keyblock %s to %d verts\n", kb->name, changed_verts);
+		if (G.debug_value == 1) {
+			printf("Compressed Shape Key %s, %.2f times smaller \n",
+					(rk->totelem * sizeof(float) * 3) / changed_verts * sizeof(KB_ComprMeshDataEnt));
+		}
 	}
 	else {
 		MEM_freeN(kbcde);
@@ -1640,20 +1643,32 @@ static void write_keys(WriteData *wd, ListBase *idbase)
 	key = idbase->first;
 
 	while (key) {
-		if (key->id.us>0 || wd->current) {
-			/* write LibData */
-			writestruct(wd, ID_KE, "Key", 1, key);
-			if (key->id.properties) IDP_WriteProperty(key->id.properties, wd);
-			
-			if (key->adt) write_animdata(wd, key->adt);
-
+		if (key->id.us > 0 || wd->current) {
 			/* direct data */
 			if (GS(key->from->name) == ID_ME && !(U.flag & USER_LEGACY_KEYBLOCKS_FMT)) {
+				ListBase lb = key->block;
+
 				/* if mesh keys, save a compressed copy */
 				Key *dupe = BKE_key_copy_nolib(key);
+
+				/* restore these later - we need to write the current key struct,
+				 * or linkage will fail later on file read */
+				key->block = dupe->block;
+				key->refkey = dupe->refkey;
+
+				/* write LibData */
+				writestruct(wd, ID_KE, "Key", 1, key);
+				if (key->id.properties)
+					IDP_WriteProperty(dupe->id.properties, wd);
+
+				if (key->adt)
+					write_animdata(wd, key->adt);
+
 				compress_keyblocks(dupe);
 
-				kb = dupe->block.first;
+				/* direct */
+				kb = key->block.first;
+
 				while (kb) {
 					writestruct(wd, DATA, "KeyBlock", 1, kb);
 					if (kb->compressed) 
@@ -1663,11 +1678,23 @@ static void write_keys(WriteData *wd, ListBase *idbase)
 					kb = kb->next;
 				}
 
+				/* restore key data */
+				key->block = lb;
+				key->refkey = lb.first; /* reference kb always is basis */
+
 				BKE_key_free_nolib(dupe);
 				MEM_freeN(dupe);
 			}
-			else
-			{
+			else {
+				/* lib */
+				writestruct(wd, ID_KE, "Key", 1, key);
+				if (key->id.properties)
+					IDP_WriteProperty(key->id.properties, wd);
+
+				if (key->adt)
+					write_animdata(wd, key->adt);
+
+				/* direct */
 				kb = key->block.first;
 				while (kb) {
 					writestruct(wd, DATA, "KeyBlock", 1, kb);
diff --git a/source/blender/makesdna/DNA_key_types.h b/source/blender/makesdna/DNA_key_types.h
index 66b1a09..55eaf58 100644
--- a/source/blender/makesdna/DNA_key_types.h
+++ b/source/blender/makesdna/DNA_key_types.h
@@ -58,10 +58,9 @@ typedef struct KeyBlock {
 	float curval;      /* influence (typically [0 - 1] but can be more), (Key->type == KEY_RELATIVE) only.*/
 
 	short type;        /* interpolation type (Key->type == KEY_NORMAL) only. */
-	short compressed;  /* for disk save; if 1, then they key's data is laid out as an array of
+	short compressed;  /* for disk write/read; if 1, then they key's data is laid out as an array of
 					    * KB_ComprMeshDataEnt structs (total totelem).
-						* Mesh only. Does not do anything at 
-						* runtime */
+						* Mesh only. Does not do anything useful at runtime */
 
 	short relative;    /* relative == 0 means first key is reference, otherwise the index of Key->blocks */
 	short flag;




More information about the Bf-blender-cvs mailing list