Jump to content

[TOPIC: topicViewTemplate]
[GLOBAL: userSmallPhoto]
Photo

widget.newtabbar: width passed is too small to fit the tab items inside
Started by CoronaChris Oct 03 2018 03:33 AM

7 replies to this topic

Best Answer Rob Miracle , 05 October 2018 - 07:58 AM

In your second example, you don't appear to be using the tabBar widget, instead, you're creating your own tabbar. In doing so, you're creating your own display.newImageRect() objects and explicitly changing the width and height to 25 each.

 

In your first example, you're feeding 400 pixel images into the widget and 400 pixel images X 5 buttons is 2000 pixels which is wider than the width of the tabBar.

 

Your config.lua comes into play two ways. First, your settings your tabBar width to display.contentWidth, which is the value of "width" that you put in config.lua. If you're using 320 or 800 or some other value, you still can't fit 2000 pixels of buttons into that space.

 

Secondly, your config.lua contains code that defines when at @2x and @4x images are used, which you don't appear to be using.

 

Rob

[TOPIC CONTROLS]
[/TOPIC CONTROLS]
[modOptionsDropdown]
[/modOptionsDropdown]
[reputationFilter]
[TOPIC: post.html]
#1

CoronaChris

[GLOBAL: userInfoPane.html]
CoronaChris
  • Contributor

  • 161 posts
  • Corona SDK

Dear Corona-community,

 

I am trying to change my bottom-menu symbols from separate image files to symbols coming from an imageSheet to reduce memory usage.

 

Here is my code in a simplified main.lua:

-----------------------------------------------------------------------------------------
--
-- main.lua
--
-----------------------------------------------------------------------------------------

-- Your code here
local widget = require("widget")

-- Image sheet options and declaration
local options = {
	frames =
	{
		{ x=0, y=0, width=400, height=400 },
		{ x=400, y=0, width=400, height=400 },
		{ x=0, y=400, width=400, height=400 },
		{ x=400, y=400, width=400, height=400 },
		{ x=0, y=800, width=400, height=400 },
		{ x=400, y=800, width=400, height=400 },
		{ x=0, y=1200, width=400, height=400 },
		{ x=400, y=1200, width=400, height=400 },
		{ x=0, y=1600, width=400, height=400 },
		{ x=400, y=1600, width=400, height=400 },
		{ x = 0, y = 0, width = 1, height = 1}
	},
	sheetContentWidth = 800,
	sheetContentHeight = 2000
}
local tabBarSheet = graphics.newImageSheet( "menuSheet.png", options )

-- create menu options
local tabButtons = {
	{
		size = 25,
		defaultFrame = 1,
		overFrame = 2,
		selected = true,
		onPress = function() print("blub") end
	},
	{
		size = 25,
		defaultFrame = 3,
		overFrame = 4,
		onPress = function() print("blub") end
	},
	{
		size = 25,
		defaultFrame = 5,
		overFrame = 6,
		onPress = function() print("blub") end
	},
	{
		size = 25,
		defaultFrame = 7,
		overFrame = 8,
		onPress = function() print("blub") end
	},
	{
		size = 25,
		defaultFrame = 9,
		overFrame = 10,
		onPress = function() print("blub") end
	}
}

local tabBar = widget.newTabBar(
	{
		sheet = tabBarSheet,
		height = 50,
		width = display.contentWidth,
		top = display.actualContentHeight + display.screenOriginY - 50,
		x = screenOriginX,
		buttons = tabButtons,
		tabSelectedLeftFrame = 11,
		tabSelectedMiddleFrame = 11,
		tabSelectedRightFrame = 11,
		tabSelectedFrameWidth = 1,
		tabSelectedFrameHeight = 1,
		backgroundFrameWidth = 0, 
		backgroundFrameHeight = 0
	}
)

Unfortunately, I get the following error:

 

widget.newTabBar: width passed is too small to fit the tab items inside, you need a width of at least 2000 to fit your tab items inside

 

I dont get why I need at least 2000 pixels as width. I understand that this comes from adding up the width-values (400px) for each button, but shouldnt the newTabBar just scale that down for me as I specified "size = 25" in my tabButtons table?

 

I attached a sample project that demonstrates my problem.
 

Attached Files



[TOPIC: post.html]
#2

CoronaChris

[GLOBAL: userInfoPane.html]
CoronaChris
  • Contributor

  • 161 posts
  • Corona SDK

I still don't understand why I get the error above, but I found a possible workaround and would like to ask if that's sensitive in terms of memory-usage for example:

 

I now have a "menubar.lua" module file that contains my buttons, all of which are in a group to allow showing and hiding the menu:

local globalSpace = require("globals")
local composer = require( "composer" )

-- table holding that tabbar
local tabBar = {}

-- set height for tabbar
tabBar.menuHeight = 50

-- initialize buttons
tabBar.btn1 = nil
tabBar.btn2 = nil
tabBar.btn3 = nil
tabBar.btn4 = nil
tabBar.btn5 = nil

-- initialize group for buttons
tabBar.buttonGroup = nil

-- draw line on top of menu
tabBar.topline = nil

-- initially enable tapping on symbols
tabBar.isEnabled = true


function tabBar.createMenu()

	-- options for imageSheet
	local options = {
		frames =
		{
			{ x=0, y=0, width=400, height=400 },
			{ x=400, y=0, width=400, height=400 },
			{ x=0, y=400, width=400, height=400 },
			{ x=400, y=400, width=400, height=400 },
			{ x=0, y=800, width=400, height=400 },
			{ x=400, y=800, width=400, height=400 },
			{ x=0, y=1200, width=400, height=400 },
			{ x=400, y=1200, width=400, height=400 },
			{ x=0, y=1600, width=400, height=400 },
			{ x=400, y=1600, width=400, height=400 }
		},
		sheetContentWidth = 800,
		sheetContentHeight = 2000
	}
	
	-- actual imageSheet with menu-symbols on it
	local tabBarSheet = graphics.newImageSheet( "menuSheet.png", options )

	-- group holding the symbol-Sprites
	tabBar.buttonGroup = display.newGroup()
	
	tabBar.topline = display.newRect(display.contentCenterX, display.screenOriginY + display.actualContentHeight - 50, display.contentWidth, 1)
	tabBar.topline:setFillColor(0.9)
	tabBar.buttonGroup:insert(tabBar.topline)

	-- home-button
	tabBar.btn1 = display.newSprite(tabBar.buttonGroup, tabBarSheet, {name="home", start=1, count=2})
	tabBar.btn1:setFrame(1)
	tabBar.btn1.width = 25
	tabBar.btn1.height = 25
	tabBar.btn1.x = display.contentWidth * 0.1
	tabBar.btn1.y = display.screenOriginY + display.actualContentHeight - 25
	tabBar.btn1:addEventListener("tap", function()
	
		if(tabBar.isEnabled == false) then return true end
		composer.gotoScene("dofaver")
		
		end
	)
	
	-- add-button
	tabBar.btn2 = display.newSprite(tabBar.buttonGroup, tabBarSheet, {name="add", start=3, count=2})
	tabBar.btn2:setFrame(1)
	tabBar.btn2.width = 25
	tabBar.btn2.height = 25
	tabBar.btn2.x = display.contentWidth * 0.3
	tabBar.btn2.y = display.screenOriginY + display.actualContentHeight - 25
	tabBar.btn2:addEventListener("tap", function()
	
		if(tabBar.isEnabled == false) then return true end
		composer.gotoScene("addFirst")
		
		end
	)
	
	-- faver-button
	tabBar.btn3 = display.newSprite(tabBar.buttonGroup, tabBarSheet, {name="faver", start=5, count=2})
	tabBar.btn3:setFrame(1)
	tabBar.btn3.width = 25
	tabBar.btn3.height = 25
	tabBar.btn3.x = display.contentWidth * 0.5
	tabBar.btn3.y = display.screenOriginY + display.actualContentHeight - 25
	tabBar.btn3:addEventListener("tap", function()
	
		if(tabBar.isEnabled == false) then return true end
		composer.gotoScene("myfavers")
		
		end
	)
	
	-- search-button
	tabBar.btn4 = display.newSprite(tabBar.buttonGroup, tabBarSheet, {name="search", start=7, count=2})
	tabBar.btn4:setFrame(1)
	tabBar.btn4.width = 25
	tabBar.btn4.height = 25
	tabBar.btn4.x = display.contentWidth * 0.7
	tabBar.btn4.y = display.screenOriginY + display.actualContentHeight - 25
	tabBar.btn4:addEventListener("tap", function()
			print("search coming")
		end
	)
	
	-- profile-button
	tabBar.btn5 = display.newSprite(tabBar.buttonGroup, tabBarSheet, {name="profile", start=9, count=2})
	tabBar.btn5:setFrame(1)
	tabBar.btn5.width = 25
	tabBar.btn5.height = 25
	tabBar.btn5.x = display.contentWidth * 0.9
	tabBar.btn5.y = display.screenOriginY + display.actualContentHeight - 25
	tabBar.btn5:addEventListener("tap", function()
	
			if(tabBar.isEnabled == false) then return true end
			composer.gotoScene("setAccount")
			
		end
	)
	
	
	-- hide menu after creation and show it only when first scene is loaded
	tabBar.buttonGroup.isVisible = false

end


-- function to show menu
function tabBar.showMenu() tabBar.buttonGroup.isVisible = true end	

-- function to hide menu
function tabBar.hideMenu() tabBar.buttonGroup.isVisible = false end	

-- function to disable tabbar
function tabBar.preventTapping() tabBar.isEnabled = false end

-- function to enable tabbar
function tabBar.allowTapping() tabBar.isEnabled = true end


return tabBar

So, in my main.lua I can call

 

local tabbar = require("menubar")

tabbar.createMenu()

tabbar.showMenu()

 

to display the menubar. Since it initially resides outside composer scenes, the menubar is always on top of scene-content. But as some of my scenes show overlays which - of course - should be on top of the tabbar, I need to insert the tabbar into the sceneGroups. To do that, I call

 

sceneGroup:insert(tabbar.buttonGroup)

 

in scene:show - phase of every scene. If I understand correctly, the tabbar is now both globally available as well as handed from one sceneGroup to the other so that it is always inserted into the currently active scene.

 

Does that make sense? Is this memory-wise a good solution?

 

Would appreciate any help here :)

 

Thanks,

 

Chris



[TOPIC: post.html]
#3

Rob Miracle

[GLOBAL: userInfoPane.html]
Rob Miracle
  • Moderator

  • 24,969 posts
  • Corona Staff

You are trying to fit 400 pixel wide graphics in a space that's designed for 25 pixel wide images. You haven't shared your config.lua, but something tells me you're not using a 2000 pixel wide content area.

 

Even if you're using content scaling, you would have one image sheet with 25 pixel wide images, an @2x version at 50px per image and an @4x version that's 100px per image. You're still 4x bigger than the 4x images that would be used.

 

Rob



[TOPIC: post.html]
#4

CoronaChris

[GLOBAL: userInfoPane.html]
CoronaChris
  • Contributor

  • 161 posts
  • Corona SDK

Thanks Rob. I am not quite sure whether my config.lua plays a big role here. In my workaround in my second post, I also use 400px wide graphics (it's the exact same options table) and create the exact same imageSheet as in the original post. And I put them in 25px wide images without any problem using the exact same config.lua. Only difference is that I use display.newSprite instead of a widget.newTabbar.

 

I can't really explain this behaviour. Can you? :)



[TOPIC: post.html]
#5

Rob Miracle

[GLOBAL: userInfoPane.html]
Rob Miracle
  • Moderator

  • 24,969 posts
  • Corona Staff

  Best Answer

In your second example, you don't appear to be using the tabBar widget, instead, you're creating your own tabbar. In doing so, you're creating your own display.newImageRect() objects and explicitly changing the width and height to 25 each.

 

In your first example, you're feeding 400 pixel images into the widget and 400 pixel images X 5 buttons is 2000 pixels which is wider than the width of the tabBar.

 

Your config.lua comes into play two ways. First, your settings your tabBar width to display.contentWidth, which is the value of "width" that you put in config.lua. If you're using 320 or 800 or some other value, you still can't fit 2000 pixels of buttons into that space.

 

Secondly, your config.lua contains code that defines when at @2x and @4x images are used, which you don't appear to be using.

 

Rob



[TOPIC: post.html]
#6

CoronaChris

[GLOBAL: userInfoPane.html]
CoronaChris
  • Contributor

  • 161 posts
  • Corona SDK

Thanks Rob. It is still a little bit confusing. You write:

 

 

"In your first example, you're feeding 400 pixel images into the widget and 400 pixel images X 5 buttons is 2000 pixels which is wider than the width of the tabBar."

 

-----

 

 

I figured that with the help of:

 

local tabButtons = {
    {
        size = 25,
        defaultFrame = 1,
        overFrame = 2,
        selected = true,
        onPress = function() print("blub") end
    },

 

I wouldnt feed the widget with 400 pixel images, but scale them down to 25px each. In the docs it states that

 

size (optional)

Number. Font size (in pixels) for the tab button label. Default is 8.

 

My understanding is that by writing size = 25, the tabbar should understand that each button is only 25px wide. Looks like I got this wrong I guess...



[TOPIC: post.html]
#7

Rob Miracle

[GLOBAL: userInfoPane.html]
Rob Miracle
  • Moderator

  • 24,969 posts
  • Corona Staff

size (optional)

Number. Font size (in pixels) for the tab button label. Default is 8.

 

Note, this is the "font size", not the image size.

 

Rob



[TOPIC: post.html]
#8

CoronaChris

[GLOBAL: userInfoPane.html]
CoronaChris
  • Contributor

  • 161 posts
  • Corona SDK

Ouch, too much coding in progress, didnt see that at all. Argh...

 

Ok then, thanks for that last hint :)




[topic_controls]
[/topic_controls]