'From Cuis 1.0 of 31 July 2009 [latest update: #250] on 4 August 2009 at 5:48:02 pm'!
!classDefinition: #BitBlt category: #'Graphics-Primitives'!
Object subclass: #BitBlt
	instanceVariableNames: 'destForm sourceForm halftoneForm combinationRule destX destY width height sourceX sourceY clipX clipY clipWidth clipHeight colorMap secondPassColorMap secondPassRule '
	classVariableNames: 'CachedFontColorMaps ColorConvertingMaps '
	poolDictionaries: ''
	category: 'Graphics-Primitives'!

!BitBlt methodsFor: 'accessing' stamp: 'jmv 8/4/2009 17:30'!
secondPassRule: rule2 secondPassColorMap: colorMap2
	"If these variables are not nil, #displayString:from:to:at:strikeFont:kern: will do two passes.
	The first will be with parameters as provided. The second one will use these new variables.
	
	This is useful for composing complex BitBlt rules from simple ones"
	
	secondPassRule _ rule2.
	secondPassColorMap _ colorMap2! !

!BitBlt methodsFor: 'copying' stamp: 'jmv 8/4/2009 16:37'!
displayString: aString from: startIndex to: stopIndex at: aPoint strikeFont: font kern: kernDelta
	"If required, do a second pass with new rule and colorMap"

	| answer prevRule prevMap |
	answer := self basicDisplayString: aString from: startIndex to: stopIndex at: aPoint strikeFont: font kern: kernDelta.
	secondPassRule ifNotNil: [
		prevRule := combinationRule.
		combinationRule := secondPassRule.
		prevMap := colorMap.
		colorMap := secondPassColorMap.
		self basicDisplayString: aString from: startIndex to: stopIndex at: aPoint strikeFont: font kern: kernDelta.
		combinationRule := prevRule.
		colorMap := prevMap ].
	^answer! !

!BitBlt methodsFor: 'private' stamp: 'jmv 8/4/2009 17:47'!
installStrikeFont: aStrikeFont foregroundColor: foregroundColor

	| lastSourceDepth targetColor |
	sourceForm notNil ifTrue: [ lastSourceDepth _ sourceForm depth ].
	sourceForm _ aStrikeFont glyphs.
	"Ignore any halftone pattern since we use a color map approach here"
	halftoneForm _ nil.
	sourceY _ 0.
	height _ aStrikeFont height.
	"Set later if needed"
	self secondPassRule: nil secondPassColorMap: nil.

	sourceForm depth = 1 ifTrue: [
		self combinationRule: Form paint.
		(colorMap isNil or: [ lastSourceDepth ~= sourceForm depth ]) ifTrue: [
			"Set up color map for a different source depth (color font)"
			"Uses caching for reasonable efficiency"
			colorMap _ self cachedFontColormapFrom: sourceForm depth to: destForm depth.
			colorMap at: 1 put: (destForm pixelValueFor: Color transparent)].
		colorMap at: 2 put: (destForm pixelValueFor: foregroundColor) ]
	
	ifFalse: [
		(Preferences subPixelRenderFonts and: [ foregroundColor = Color black or: [ Preferences subPixelRenderColorFonts ]]) ifTrue: [
			destForm depth > 8 ifTrue: [
				"rgbMul is equivalent to component alpha blend if text is black (only faster, hehe)"
				self combinationRule: 37.		"rgbMul"
				colorMap _ sourceForm depth ~= destForm depth
					ifTrue: [ self cachedFontColormapFrom: sourceForm depth to: destForm depth ].
				(Preferences properAlphaForBlackText or: [ (foregroundColor = Color black) not ]) ifTrue: [
					"rgbMul / rgbAdd IS component alpha blend for any color of text (neat trick, eh!!)"
					self secondPassRule: 20 "rgbAdd" secondPassColorMap: 
						(self colorConvertingMap: foregroundColor from: sourceForm depth to: destForm depth keepSubPixelAA: true)]]
			ifFalse: [
				self combinationRule: 25.		"Paint"
				targetColor _ foregroundColor = Color black ifFalse: [ foregroundColor ].
				colorMap _ self colorConvertingMap: targetColor from: sourceForm depth to: destForm depth keepSubPixelAA: true]]
		ifFalse: [
			"Do not use rule 34 for 16bpp display. TTCFont uses it, but it builds a glyphs cache for each color used!!"
			self combinationRule: (destForm depth = 32 ifTrue: [34 "alphaBlendScaled"] ifFalse: [25 "Paint"]).
			colorMap _ self colorConvertingMap: foregroundColor from: sourceForm depth to: destForm depth keepSubPixelAA: false]].! !

!classDefinition: #BitBlt category: #'Graphics-Primitives'!
Object subclass: #BitBlt
	instanceVariableNames: 'destForm sourceForm halftoneForm combinationRule destX destY width height sourceX sourceY clipX clipY clipWidth clipHeight colorMap secondPassColorMap secondPassRule'
	classVariableNames: 'CachedFontColorMaps ColorConvertingMaps'
	poolDictionaries: ''
	category: 'Graphics-Primitives'!
