Home AMX User Forum NetLinx Studio

Structures within Structures - can it be done?

I have created a structure to hold channel presets, with a name and a number. No problem. The thing I can't quite wrap my head around is how to create a structure WITHIN a structure. I was hoping to be able to create another structure to contain 6 different users each with their own custom presets, but when i tried to do it, I locked up not only Netlinx studio, but my PC as well, effectively corrupting the project and forcing me to extract from the src file. So...I really don't want that to happen again. I tried something like this:
STRUCTURE _tvpreset  //preset info
{
	CHAR sChanName[15] 
	INTEGER nChanNum
}  
DEFINE_VARIABLE
PERSISTENT _tvpreset uSATPresets[20]  //20 presets to store #s
which gave me a structure with 2 elements(1 name, 1 number) to start with.
I then tried to create a structure within a structure:
STRUCTURE _users  
{
    _tvpreset uTVusers  //creating a data type already identified in a prior structure
    CHAR sName  //to describe the person selecting the presets info
}
It seems like it is possible, but am I looking at this backwards or something?

Comments

  • viningvining Posts: 4,368
    Here's an example:
    DEFINE_TYPE 	//_sSS_BrowseState
    
    STRUCTURE _sSS_BrowseState 
         
         {//   Browsing state information:
         INTEGER nContextSession ;
         LONG nNumLines ;				//   Number of lines for this browse session
         INTEGER nLevel ;					//   Current "level" for this browse session
         }
    
    DEFINE_TYPE 	//_sSS_DoExtOpcode
    
    STRUCTURE _sSS_DoExtOpcode 
         
         {
         INTEGER nOpCode ;
         
         // Most extended commands
    
         INTEGER  nIntParam1 ;
         INTEGER  nIntParam2 ;
    
         // Specifically used for SS_DoExtCommand
    
         SLONG nParam1 ;
         }
    
    DEFINE_TYPE 	//_sSS_UI_DoCommand 
    
    STRUCTURE _sSS_UI_DoCommand 
    
         {
         INTEGER nOpCode ;
         INTEGER nParam1 ;
         CHAR cParam1[SS_LEN_Item] ;
         }
    
    DEFINE_TYPE 	//_sSS_QueueFile
    
    STRUCTURE _sSS_QueueFile 
    
         {
         INTEGER nType ;
    
         // Specify either the URL *OR* the itemID to queue
    
         CHAR cItem[SS_LEN_URL] ;
         LONG nID_Item ;
    
         // Filtering criteria
    
         LONG nID_Genre ;
         LONG nID_Artist ;
         LONG nID_Album ;
         LONG nID_Plylist ;
    
         // Filtering criteria (via QueueFile API - if written)
    
         CHAR cGenre[SS_LEN_Genre] ;
         CHAR cArtist[SS_LEN_Artist] ;
         CHAR cAlbum[SS_LEN_Album] ;
         }
         
    // Packets sent from SlimServer module to caller
    DEFINE_TYPE 	//_sSS_StatusInfo 
    
    STRUCTURE _sSS_StatusInfo 
         
         {// Response to a status request:
         CHAR cPlayerName[32] ;		//   Player name (size can be increased if needed)
         CHAR cPlayerIP[15] ;               //   IP address of player
         CHAR cPlayTime[20] ; 
         CHAR cID[20] ; 
         CHAR cCanSeek[20] ; 
         CHAR cPL_TmStamp[20] ; 
         CHAR cPL_Mode[20] ; 
         CHAR cTitle[20] ; 
         CHAR cGenre[20] ; 
         CHAR cArtist[20] ; 
         CHAR cAlbum[20] ; 
         CHAR cSeqNo[20] ;
         INTEGER nPlayer_Connected ;	//   Player currently connected?
         INTEGER nPower ;			//   Player currently powered on?
         INTEGER nSignalStrength ;		//   Signal Strength (1-100, 0 if not wireless)
         INTEGER nMode ;			//   Play mode (see SS_PlayMode_* constants)
         //INTEGER nSongTime ;		//   Seconds of song that have been played
    //     INTEGER nSongDuration ;		//   Total seconds of current song
         INTEGER nSleepTime ;		//   Number of minutes player was set to sleep
         INTEGER nSleepRemaining ;		//   Number of minutes remaining prior to sleep (if sleepTime is set)
         SINTEGER nRate ;			//   Rate (Rewinding: <0, Fast Fwd: >1, Play: 1
         INTEGER nMixVolume ;		//   Current Volume Setting: 0-100
         INTEGER nIRVolume ;		//   Current Volume Setting: 0-40  (Like Squeezebox display)
         INTEGER nMixBalance ;		//   Reserved: Current Balance Setting: 0-100
         INTEGER nMixBass ;			//   Reserved: Current Bass Setting: 0-100
         INTEGER nMixTreble ;		//   Reserved: Current Treble Setting: 0-100
         INTEGER nMixPitch ;		//   Reserved: Current Pitch Setting: 80-120
         INTEGER nPlylistRepeat ;		//   Playlist Repeat State (0: Stop at end, 1: Repeat current song, 2: Repeat all songs)
         INTEGER nPlylistShuffle ;		//   Playlist Shuffle State (0: None, 1: Songs, 2: Albums)
         LONG nPlylistCurIndx ;		//   Index of currently played item (1 is first item)
         LONG nPlylistTracks ;		//   Total number of tracks in sSqzBox.sPlaylist
         }
    
    DEFINE_TYPE 	//_sSS_Playlist 
    
    STRUCTURE _sSS_Playlist 
    
         {// Response to a status sSqzBox.sPlaylist request:
         LONG nIndx ;			//   Index of this song in the sSqzBox.sPlaylist
         LONG nID ;				//   Internal database ID of item in sSqzBox.sPlaylist
         CHAR cTitle[SS_LEN_Title] ;	//   Remaining fields: Tag data
         CHAR cArtist[SS_LEN_Artist] ;
         CHAR cAlbum[SS_LEN_Album] ;
         CHAR cGenre[SS_LEN_Genre] ;
         CHAR cPath[128] ;
         LONG nSongTime
         LONG nSongDuration ;
         LONG nSentSongTime
         LONG nSentSongDuration ;
         INTEGER nRemote ;
         }
    
    DEFINE_TYPE 	//_sSS_UI_ErrorResult 
    
    STRUCTURE _sSS_UI_ErrorResult 
         {// Response if a UI command fails in some way
         INTEGER nLevel ;			//   Current depth/level of UI code
         INTEGER nErrCode ;			//   Error code from SlimServer UI component
         CHAR cErrText[SS_MAX_UI_errText] ;	//   Error text from SlimServer UI component
         }
    
    DEFINE_TYPE 	//_sSS_GetBrowseInfo
    
    STRUCTURE _sSS_GetBrowseInfo 
         {// Packet to fetch browse information
         INTEGER nType ;				//   Type of fetch operation
         LONG nStartItem ;				//   Starting item number to fetch
         LONG nCountItem ;				//   Number of items to fetch for page
         INTEGER nSortTrack ;			//   If getting title list, sort by track?
    
         // Filtering criteria
    
         LONG nID_Artist ;
         LONG nID_Album ;
         LONG nID_Genre ;
         LONG nID_PlyList ;
         // Perform "search" (limit list of items returned to those containing search string)
    
         CHAR cListDir[SS_LEN_URL] ;		//   Directory/URL for sSqzBox.sPlaylist
         CHAR cSearch[SS_LEN_Item] ;		//   Search restriction text
    
         // Returned once query is performed
    
         LONG nMaxItems ;				//   Maximum number of items available
         }
    
    DEFINE_TYPE 	//_sUI_List
    
    STRUCTURE _sUI_List
         {
         CHAR cItem[MAX_NUM_BROWSE_LINES][SS_LEN_Item] ;
         CHAR cGenre[MAX_NUM_BROWSE_LINES][SS_LEN_Item] ;
         CHAR cArtist[MAX_NUM_BROWSE_LINES][SS_LEN_Item] ;
         CHAR cAlbum[MAX_NUM_BROWSE_LINES][SS_LEN_Item] ;
         CHAR cURL[MAX_NUM_BROWSE_LINES][SS_LEN_URL] ;
         LONG nID[MAX_NUM_BROWSE_LINES] ;
         LONG nDuration[MAX_NUM_BROWSE_LINES] ;
        // LONG ID_PlyList[MAX_NUM_BROWSE_LINES] ;
         }
         
    DEFINE_TYPE 	//_sSS_Player 
    
    STRUCTURE _sSS_Player 
    
         {// Player state information:
         INTEGER nDev_Instance ;
         CHAR    cIP[21] ;
         CHAR    cStrMAC[17] ;
         CHAR    cArtHost[21] ;
         //CHAR    cLstArtHost[21] ;
         CHAR    cLstCmd[128] ;
         CHAR    cJump[12] ;
         INTEGER nServerMAC[6] ;
         INTEGER nRealMAC[6] ;
         LONG    nPort ;
         INTEGER nPower ;
         INTEGER nIP_ConnectState ;
         INTEGER nIP_ConnectAttempts ;
         INTEGER nUI_Active ;
         INTEGER nQ_HasItems ;
         INTEGER nListen_On ;
         INTEGER nNum_UIs ;
         INTEGER nDeBug ;
         }
     
    DEFINE_TYPE 	//sSqzBox_sStructure
    
    STRUCTURE _sStructure
         
         {
         _sSS_Player sPlayer ;
         _sSS_BrowseState sBrowseState ;
         _sSS_GetBrowseInfo sInfoSearch[MAX_UI_Level] ;
         _sUI_List sUI_List[MAX_UI_Level] ;
         _sSS_PlayList sPlaylist[2] ;
         _sSS_PlayList sOldPlaylist[2] ;
         _sSS_StatusInfo sStatus ;
         _sSS_StatusInfo sOldStatus
         } 
         
    DEFINE_VARIABLE //STRUCTURES
    
    VOLATILE _sStructure    sSqzBox ;
    

    The last structure contains all the previous declared structures which could also include structures if there was a need. I'm not sure how deep you can go but you can go pretty deep. It just makes writing a variable really, really long.
  • vegastechvegastech Posts: 369
    Thanks. Looking at your example really helped! I now have a structure within a structure, and I haven't crashed my PC yet! cooooool...........
  • AuserAuser Posts: 506
    Just be aware that unless it's been fixed in recent firmware there's a bug performing variable_to_xml <-> xml_to_variable tranlsations on struct variables which have structures as members - they won't survive the round trip.
  • DHawthorneDHawthorne Posts: 4,584
    Every time you make a DEV an element of a structure, you've put a structure inside a structure.

    I tend to go lightly with it though; referencing an element three-four levels deep can get dang confusing, especially if you are working with arrays of structures (like I usually am). I find for simplicity's sake it's often easier to keep it at two levels, tops.
  • ericmedleyericmedley Posts: 4,177
    DHawthorne wrote: »
    Every time you make a DEV an element of a structure, you've put a structure inside a structure.

    I tend to go lightly with it though; referencing an element three-four levels deep can get dang confusing, especially if you are working with arrays of structures (like I usually am). I find for simplicity's sake it's often easier to keep it at two levels, tops.

    I agree with this. My poor addled brain gets lost in the endless dots and [] when working with the variables. I find that keeping them separate keeps me saner when in the program itself.
  • As others have said, yes you can declare a instance of a structure as a item in another structure. However keep in mind if a structure gets too large you can't view or edit the current values of the structure in Debug mode while testing.
  • ericmedleyericmedley Posts: 4,177
    Every time you declare a structure within a structure, somewhere a puppy dies.
  • PhreaKPhreaK Posts: 966
    ericmedley wrote: »
    Every time you declare a structure within a structure, somewhere a puppy dies.

    Every time you declare 300 variables at the top of a file there's a puppy massacre.

    I much prefer embedded structures as it's so much easier to keep context and group related data. Maybe that's just me attempting to cling to anything that remotely resembles object orientation though.
Sign In or Register to comment.