bool GraphicsElementManager::InitPrimitiveElement( shared_ptr<PrimitiveElement> pElement,
													const SRect& non_scaled_rect,
												    const SFloatRGBAColor& color,
													int layer_index )
{
	bool res = InitElement( pElement, layer_index );
	if( !res )
		return false;

	pElement->SetColor( 0, color );

	AABB2 non_scaled_aabb;
	non_scaled_aabb.vMin.x = (float)non_scaled_rect.left;
	non_scaled_aabb.vMin.y = (float)non_scaled_rect.top;
	non_scaled_aabb.vMax.x = (float)non_scaled_rect.right;
	non_scaled_aabb.vMax.y = (float)non_scaled_rect.bottom;

	// set as local coord
	// the element is owned by a group: local coord
	// the element is not owned by any group: global coord
	pElement->SetLocalTopLeftPos( non_scaled_rect.GetTopLeftCorner() );

	pElement->SetSizeLTRB( non_scaled_aabb.vMin, non_scaled_aabb.vMax );

	return true;
}
shared_ptr<TextElement> GraphicsElementManager::CreateText( int font_id, const std::string& text,
												  const SRect& textbox, int align_h, int align_v,
												  const SFloatRGBAColor& color, int font_w, int font_h, int layer )
{
/*	int index = GetVacantSlotIndex();

	if( !RegisterToLayer( index, layer ) )
		return shared_ptr<TextElement>();
*/
	AABB2 aabb;
	aabb.vMin = Vector2( (float)textbox.left,  (float)textbox.top );
	aabb.vMax = Vector2( (float)textbox.right, (float)textbox.bottom );
	shared_ptr<TextElement> pTextElement( new TextElement( font_id, text, aabb, align_h, align_v, color ) );
	pTextElement->SetFontSize( font_w, font_h );

	bool res = InitElement( pTextElement, layer );
	if( !res )
		return shared_ptr<TextElement>();

	// manager must be set to the element before calling SetLocalTopLeftPos()
	// because it calls UpdateTextAlignment(), which calls GraphicsElementManager::GetFont()
	pTextElement->SetLocalTopLeftPos( textbox.GetTopLeftCorner() );

	pTextElement->UpdateTextAlignment();

	// need to scale text element?

	return pTextElement;
}
void CGM_StdSliderRenderer::Init( CGM_Slider& slider )
{
//	CGM_StdStaticRenderer::Init( CGM_Static *pStatic );

	// slider frame
	const SFloatRGBAColor& normal_color = m_aColor[CGM_Control::STATE_NORMAL];
	const SFloatRGBAColor& bg_color     = SFloatRGBAColor(0.0f,0.0f,0.0f,0.6f);
	m_pRect                  = m_pGraphicsElementManager->CreateRect(      slider.GetLocalRect(), bg_color, normal_color, 2 );
//	m_pFrameRect             = m_pGraphicsElementManager->CreateFrameRect( slider.GetLocalRect(), normal_color, 2 );

	// slider button
	SRect btn_rect = slider.GetButtonRect();
	SRect local_btn_rect = RectLTWH( 0, 0, btn_rect.GetWidth(), btn_rect.GetHeight() );
	m_pSliderButtonRect      = m_pGraphicsElementManager->CreateRect(      local_btn_rect,  bg_color, normal_color, 2 );
//	m_pSliderButtonFrameRect = m_pGraphicsElementManager->CreateFrameRect( local_btn_rect,  normal_color, 2 );

	SRect dot_rect = local_btn_rect;
	dot_rect.Inflate( -dot_rect.GetWidth() / 4, -dot_rect.GetHeight() / 4 );
	m_pSliderButtonDot       = m_pGraphicsElementManager->CreateFillRect( dot_rect, normal_color, 2 );

	const SRect slider_rect = slider.GetBoundingBox();
	const SPoint slider_topleft = slider_rect.GetTopLeftCorner(); // global
	const SPoint btn_local_topleft = slider.GetLocalButtonRectInOwnerDialogCoord().GetTopLeftCorner(); // local coord of owner dialog

	// subgroup for slider button
	vector<boost::shared_ptr<GraphicsElement> > vecpButtonElement;
	vecpButtonElement.push_back( m_pSliderButtonRect );
//	vecpButtonElement.push_back( m_pSliderButtonFrameRect );
	vecpButtonElement.push_back( m_pSliderButtonDot );
	m_pSliderButtonRect->SetLocalTopLeftPos( Vector2(0,0) );
//	m_pSliderButtonFrameRect->SetLocalTopLeftPos( SPoint(0,0) );
	m_pSliderButtonDot->SetLocalTopLeftPos( SPoint(0,0) + dot_rect.GetTopLeftCorner() );
	m_pSliderButton = m_pGraphicsElementManager->CreateGroup( vecpButtonElement, btn_local_topleft );


	// For slider button elements, the following 2 things need to be done separately
	// 1. register to parent dialog renderer
	//    - register the subgroup of slider button elements
	// 2. set local layer offsets
	//    - set for each element

	// register the subgroup to the parent dialog renderer
	RegisterGraphicsElementToParentDialog( m_pSliderButton );

	// set different local layer offset for each grouped element
	SetLocalLayerOffset( 0, m_pSliderButtonDot );
//	SetLocalLayerOffset( 0, m_pSliderButtonFrameRect );
	SetLocalLayerOffset( 1, m_pSliderButtonRect );

	// register elements and set local layer offset to determine rendering order
	// - these guys don't belong to any subgroup of the renderer so each of them can be
	//   registered with a single call of RegisterGraphicsElement()
//	RegisterGraphicsElement( 2, m_pFrameRect );
	RegisterGraphicsElement( 3, m_pRect );

	// register elements that chages colors depending on states
//	RegisterColoredElement( m_pFrameRect );
//	RegisterColoredElement( m_pSliderButtonFrameRect );
	RegisterColoredElement( m_pRect->FrameElement() );
	RegisterColoredElement( m_pSliderButtonRect->FrameElement() );

}