-
Notifications
You must be signed in to change notification settings - Fork 1
Release 0.15.0 #26
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Release 0.15.0 #26
Conversation
- Added *StartDelayCall* method to *ICoroutineService* to allow deferred methods to be safely executed within the bounds of a Unity Coroutine - Added the possibility to know the current state of an *IAsyncCoroutine* - Added the access to the Sample Entity used to generete new entites within an *IObjectPool<T>* and destroy it when disposing the object pool - Added the possibility to reset an *IObjectPool<T>* to a new state
📝 WalkthroughWalkthroughThis pull request introduces significant enhancements to the coroutine and object pooling systems. The changes include adding new methods to the Changes
Sequence DiagramsequenceDiagram
participant User
participant CoroutineService
participant AsyncCoroutine
User->>CoroutineService: StartDelayCall(callback, delay)
CoroutineService->>AsyncCoroutine: Create and Schedule
Note over AsyncCoroutine: Wait for delay
AsyncCoroutine->>User: Execute Callback
Possibly related PRs
Poem
Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media? 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
CodeRabbit Configuration File (
|
WalkthroughThe changes include the addition of new methods and functionalities related to coroutines and object pooling. The Changes
Uplevel your code reviews with CodeRabbit ProCodeRabbit ProIf you like this project, please support us by purchasing the Pro version. The Pro version has advanced context, superior noise reduction and several proprietary improvements compared to the open source version. Moreover, CodeRabbit Pro is free for open source projects. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Files selected (5)
- CHANGELOG.md (1)
- Runtime/CoroutineService.cs (9)
- Runtime/ObjectPool.cs (9)
- Runtime/PoolService.cs (3)
- Tests/Editor/PlayMode/CoroutineServiceTest.cs (1)
Files ignored due to filter (1)
- package.json
Review comments generated (15)
- Review: 15
- LGTM: 0
Tips
Chat with
CodeRabbit Bot (@coderabbitai)
- Reply on review comments left by this bot to ask follow-up questions. A review comment is a comment on a diff or a file.
- Invite the bot into a review comment chain by tagging
@coderabbitaiin a reply.
Code suggestions
- The bot may make code suggestions, but please review them carefully before committing since the line number ranges may be misaligned.
- You can edit the comment made by the bot and manually tweak the suggestion if it is slightly off.
Pausing incremental reviews
- Add
@coderabbitai: ignoreanywhere in the PR description to pause further reviews from the bot.
| var asyncCoroutine = _coroutineService.StartAsyncCoroutine(TestCoroutine(testValue1), testValue2); | ||
| asyncCoroutine.OnComplete(newValue => testCompleted = newValue); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The signature of the StartAsyncCoroutine method has changed. The second argument, testValue2, is no longer needed when calling the method. Instead, you can directly attach the completion callback using the OnComplete method.
- var asyncCoroutine = _coroutineService.StartAsyncCoroutine(TestCoroutine(testValue1), testValue2);
- asyncCoroutine.OnComplete(newValue => testCompleted = newValue);
+ var asyncCoroutine = _coroutineService.StartAsyncCoroutine<int>(TestCoroutine(testValue1));
+ asyncCoroutine.OnComplete(newValue => testCompleted = newValue);| T Spawn<T, TData>(TData data) where T : class, IPoolEntitySpawn<TData>; | ||
|
|
||
| /// <inheritdoc cref="IObjectPool{T}.Despawn"/> | ||
| /// <inheritdoc cref="IObjectPool{T}.Despawn(T)"/> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| /// <inheritdoc cref="IObjectPool{T}.Dispose(bool)"/> | ||
| void Dispose<T>(bool disposeSampleEntity) where T : class; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| /// <inheritdoc /> | ||
| public void Dispose<T>(bool disposeSampleEntity) where T : class | ||
| { | ||
| GetPool<T>().Dispose(disposeSampleEntity); | ||
| RemovePool<T>(); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The implementation of the Dispose method has changed. Please update the comment accordingly.
- /// <inheritdoc />
+ /// <inheritdoc cref="IPoolService.Dispose{T}"/>
public void Dispose<T>(bool disposeSampleEntity) where T : class
{
GetPool<T>().Dispose(disposeSampleEntity);
RemovePool<T>();
}| GetPool<T>().Dispose(disposeSampleEntity); | ||
| RemovePool<T>(); | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| public virtual void Dispose(bool disposeSampleEntity) | ||
| { | ||
| if (disposeSampleEntity) | ||
| { | ||
| _sampleEntity = null; | ||
| } | ||
|
|
||
| Dispose(); | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| /// <inheritdoc /> | ||
| public virtual void Dispose() | ||
| { | ||
| Clear(); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| public class ObjectPool<T> : ObjectPoolBase<T> where T : class | ||
| { | ||
| public ObjectPool(uint initSize, T sampleEntity, Func<T, T> instantiator) : base(initSize, sampleEntity, instantiator) | ||
| { | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| /// <inheritdoc /> | ||
| public override void Dispose(bool disposeSampleEntity) | ||
| { | ||
| Object.Destroy(SampleEntity); | ||
|
|
||
| base.Dispose(disposeSampleEntity); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
| /// <inheritdoc /> | ||
| public override void Dispose(bool disposeSampleEntity) | ||
| { | ||
| Object.Destroy(SampleEntity.gameObject); | ||
|
|
||
| base.Dispose(disposeSampleEntity); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The GameObjectPool<T> class has been updated to override the Dispose(bool disposeSampleEntity) method. This method destroys the sample entity's game object using Object.Destroy and then calls the base Dispose method.
Suggestions
-
Consistency: In the
IObjectPoolinterface, theDisposemethod should be placed before theDespawnAllmethod for consistency in the order of methods. -
Error Handling: It would be beneficial to add error handling in case the
DisposeorResetmethods are called multiple times on the same object pool instance. This can prevent potential issues and provide better feedback to developers. -
Naming Convention: The name
Resetfor the method in theIObjectPoolinterface could be improved to be more descriptive. Consider renaming it to something likeResetPoolorClearAndReset. -
Performance: In the
Resetmethod implementation ofObjectPoolBase<T>, consider using aforloop instead of aforeachloop when pushing new instances of the entity onto the stack. This can potentially improve performance by avoiding the overhead of iterating over the collection. -
Security: Ensure that the
Disposemethod properly handles the disposal of resources and prevents any potential memory leaks or security vulnerabilities. Make sure that all disposable resources are properly disposed of and any references to them are cleared. -
Testing: Consider adding unit tests to cover the new methods and functionalities added to the object pooling classes. This can help ensure the correctness and robustness of the implementation.
Overall, the changes made to the Runtime/ObjectPool.cs file introduce new methods and functionalities to enhance object pooling. However, there are some areas where improvements can be made in terms of consistency, error handling, performance, security, and testing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actionable comments posted: 1
🧹 Nitpick comments (6)
Runtime/CoroutineService.cs (5)
29-32: Good addition ofStartTime.
This property helps in measuring elapsed time. Consider clarifying if it’s real time or scaled time. Currently, it's set fromTime.time, which is scaled by timeScale in Unity.
82-82: Documentation clarity.
Highlights thatdatais passed into the coroutine. This is beneficial for usage clarity.
85-95:StartDelayCallmethods are a solid addition.
Enabling delayed callbacks in a unified pattern is useful. Consider mentioning in docs whether time scaling (Time.timeScale) affects the delay or if unscaled time is desired.
210-216:InternalDelayCoroutinelogic.
Simple delay usage withWaitForSeconds. If unscaled time is required, considerWaitForSecondsRealtime.
273-274: Callback invocation inOnCompleteTrigger.
Implementation is clear. Make sure you handle exceptions within_onCompleteto avoid silent coroutine failures.Runtime/ObjectPool.cs (1)
102-106:SampleEntityproperty exposure.
Allowing read-only access to the sample entity is beneficial for debugging or advanced usage.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro
📒 Files selected for processing (6)
CHANGELOG.md(1 hunks)Runtime/CoroutineService.cs(9 hunks)Runtime/ObjectPool.cs(9 hunks)Runtime/PoolService.cs(3 hunks)Tests/Editor/PlayMode/CoroutineServiceTest.cs(1 hunks)package.json(1 hunks)
✅ Files skipped from review due to trivial changes (1)
- package.json
🔇 Additional comments (39)
Runtime/CoroutineService.cs (21)
4-4: No immediate concerns with alias usage.
Defining aliases forActionandObjecthelps resolve naming collisions with Unity classes. This implementation is acceptable.
17-20: Clear documentation forIsRunning.
The property is straightforward. Ensure subsequent code sets the coroutine tonullconsistently so it accurately reflects whether the coroutine is still running.
38-41: Ensure consistent usage oftriggerOnComplete.
Stopping the coroutine and optionally triggeringOnCompletecan be beneficial, but confirm that it’s not called in unexpected scenarios.
44-45: Inheritance structure is logical.
CombiningIAsyncCoroutine<T>withIAsyncCoroutinekeeps code DRY.
50-50: Potential concurrency considerations forData.
Allowing both get and set can be convenient, but be aware of possible race conditions if used in multi-threaded contexts.
54-56: Streamlined callback signature.
Removing the data parameter fromOnCompleteclarifies usage and avoids confusion.
84-84: Additional overload forStartAsyncCoroutine.
Accepting extra data simplifies code that needs to pass parameters. This is a valuable API addition.
109-109: Game object creation is correct.
Naming the object after its MonoBehaviour is a good convention.
143-143: InstantiatingAsyncCoroutine.
This usage is straightforward. Make sure to handle exceptions if theroutineis null.
151-153: Generic data parameter inStartAsyncCoroutine<T>.
This design improves flexibility. Ensure that code consistently initializesData.
159-181:StartDelayCallimplementation.
Implementation is well-structured. The automatic callback upon completion is intuitive. Confirm that prematurely stopping the routine still behaves as expected regarding callback invocation.
227-228: Private backing field for_coroutineService.
Storing the service reference is standard practice. No issues found.
231-231:IsRunningrelies onCoroutine != null.
Ensure that the coroutine is always set to null after completion soIsRunningdoes not return a false positive.
234-234: Initialization ofStartTimewithTime.time.
Straightforward initialization that captures the start moment.
236-241: Overloaded constructor usage.
Having a private constructor plus a public one is safe for controlled instantiation. The design is consistent.
269-271: Marking completed.
Correctly setsIsCompleted = trueand clearsCoroutine. This ensures the state is synchronized.
279-279: Generic extensionAsyncCoroutine<T>.
Proper inheritance from base class. Good to see typed data usage.
282-283:_onCompletemoves from typed delegate.
This pattern is consistent. Great for storing typed callbacks.
285-287: Constructor injectingdata.
Storing the passed indatais essential and well-implemented. Confirm thatdatais never null when usage requires it non-null.
290-290:OnComplete(Action<T>)setter.
Straightforward approach for hooking a typed completion callback.
295-297: ExtendedOnCompleteTrigger.
Calls base trigger first, then typed callback. The order is correct, ensuring base logic completes prior to typed callback.Runtime/ObjectPool.cs (13)
91-91:DespawnsAlldoc improvement.
Adding documentation is helpful.
92-96: Overload ofDispose(bool disposeSampleEntity).
This clarifies whether the sample entity should be destroyed. This is a welcome addition for resource management.
117-121:Resetmethod signature.
AcceptingsampleEntityplusinitSizestreamlines reinitialization. Avoid usage if it can lead to concurrency issues (e.g., resetting while actively in use).
169-169: Spacing or reorganization.
No functional change—just a minor tweak.
170-173: Transition to private_sampleEntity.
Encapsulation is improved. The public property now safely returns_sampleEntity.
180-180: Constructor updated to store_sampleEntity.
Clean approach to store the entity reference.
204-216:Resetmethod implementation.
Disposing prior contents before reinitializing the pool is crucial. Confirmation that the newly assigned_sampleEntityis valid for subsequent instantiations is recommended.
238-247:Dispose(bool disposeSampleEntity)override.
Nullifying_sampleEntityif requested, then falling back toDispose()is an elegant approach. Ensure that disposing sampleEntity in child classes is consistent.
307-308: VirtualDispose()method remains for backward compatibility.
Clear usage. Ensure that calls toDispose(bool)do not conflict with directDispose()calls.
365-365: Class inheritance change toObjectPoolBase<T>.
Ensures better alignment with base pool structure. Good step toward consistency.
367-369: Constructors updated to match new inheritance.
All references to the base class remain consistent. No further concerns.
396-402:Dispose(bool disposeSampleEntity)inGameObjectPool.
Destroying the sample GameObject then calling base ensures correct resource cleanup.
467-474:Dispose(bool disposeSampleEntity)inGameObjectPool<T>.
Mirrors the same pattern for typed GameObject pools. Consistency is good.Tests/Editor/PlayMode/CoroutineServiceTest.cs (1)
70-71: Update toStartAsyncCoroutine_WithData_Successfully().
The new method signature correctly passestestValue2as data. This ensures the typed callback setstestCompletedproperly.Runtime/PoolService.cs (3)
53-53: Clarified doc reference forDespawn<T>(T entity).
Documentation is more explicit. No implementation issues noted.
73-75: Reference toIObjectPool{T}.Dispose(bool).
Helps highlight the new disposal overload.
150-156: NewDispose<T>(bool disposeSampleEntity)inPoolService.
This provides selective disposal for specific pool types. Confirm that removing the pool from_poolsafter disposal is the intended behavior.CHANGELOG.md (1)
7-14: Accurate version update with new features.
Documenting core additions—StartDelayCall, asynchronous coroutine state, object pool sample-entity disposal, and reset functionalities—is thorough.
| public void StopCoroutine(bool triggerOnComplete = false) | ||
| { | ||
| _coroutineService.StopCoroutine(Coroutine); | ||
|
|
||
| OnCompleteTrigger(); | ||
| } | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
🛠️ Refactor suggestion
StopCoroutine body completeness.
Implementation stops the coroutine, then triggers the completion callback if requested. If stopping means incomplete, consider skipping OnCompleteTrigger altogether.
New:
Summary by CodeRabbit
StartAsyncCoroutine_WithData_Successfullymethod to simplify usage and changed the signature ofStartAsyncCoroutine.GameLovers.Servicesnamespace to support the new functionality.SampleEntityinObjectPoolBase<T>,ObjectPool<T>, andGameObjectPool<T>, and refactored theDisposemethod in these classes.Dispose<T>method in thePoolServiceclass.Summary by CodeRabbit
New Features
StartDelayCallmethod to enable deferred method execution in Unity CoroutinesIAsyncCoroutinewith state tracking capabilitiesIObjectPool<T>with sample entity access and reset functionalityBug Fixes
Chores